AbstractJavaFXGriffonView.java
001 /*
002  * Copyright 2008-2016 the original author or authors.
003  *
004  * Licensed under the Apache License, Version 2.0 (the "License");
005  * you may not use this file except in compliance with the License.
006  * You may obtain a copy of the License at
007  *
008  *     http://www.apache.org/licenses/LICENSE-2.0
009  *
010  * Unless required by applicable law or agreed to in writing, software
011  * distributed under the License is distributed on an "AS IS" BASIS,
012  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013  * See the License for the specific language governing permissions and
014  * limitations under the License.
015  */
016 package org.codehaus.griffon.runtime.javafx.artifact;
017 
018 import griffon.core.GriffonApplication;
019 import griffon.core.artifact.GriffonClass;
020 import griffon.core.artifact.GriffonController;
021 import griffon.core.controller.Action;
022 import griffon.exceptions.GriffonException;
023 import griffon.javafx.support.JavaFXAction;
024 import griffon.javafx.support.JavaFXUtils;
025 import javafx.fxml.FXMLLoader;
026 import javafx.fxml.JavaFXBuilderFactory;
027 import javafx.scene.Node;
028 import javafx.scene.Parent;
029 import org.codehaus.griffon.runtime.core.artifact.AbstractGriffonView;
030 
031 import javax.annotation.Nonnull;
032 import javax.annotation.Nullable;
033 import javax.inject.Inject;
034 import java.io.IOException;
035 import java.net.URL;
036 
037 import static griffon.util.ConfigUtils.stripFilenameExtension;
038 import static griffon.util.GriffonNameUtils.isBlank;
039 import static griffon.util.GriffonNameUtils.requireNonBlank;
040 
041 /**
042  * JavaFX-friendly implementation of the GriffonView interface.
043  *
044  @author Andres Almiray
045  @since 2.0.0
046  */
047 public abstract class AbstractJavaFXGriffonView extends AbstractGriffonView {
048     private static final String FXML_SUFFIX = ".fxml";
049 
050     public AbstractJavaFXGriffonView() {
051 
052     }
053 
054     /**
055      * Creates a new instance of this class.
056      *
057      @param application the GriffonApplication that holds this artifact.
058      @deprecated Griffon prefers field injection over constructor injector for artifacts as of 2.1.0
059      */
060     @Inject
061     @Deprecated
062     public AbstractJavaFXGriffonView(@Nonnull GriffonApplication application) {
063         super(application);
064     }
065 
066     @Nullable
067     protected Node loadFromFXML() {
068         return loadFromFXML(resolveBasename());
069     }
070 
071     @Nullable
072     protected Node loadFromFXML(@Nonnull String baseName) {
073         requireNonBlank(baseName, "Argument 'baseName' must not be blank");
074         if (baseName.endsWith(FXML_SUFFIX)) {
075             baseName = stripFilenameExtension(baseName);
076         }
077         baseName = baseName.replace('.''/');
078         String viewName = baseName + FXML_SUFFIX;
079         String styleName = baseName + ".css";
080 
081         URL viewResource = getResourceAsURL(viewName);
082         if (viewResource == null) {
083             return null;
084         }
085 
086         FXMLLoader fxmlLoader = new FXMLLoader(viewResource);
087         fxmlLoader.setResources(getApplication().getMessageSource().asResourceBundle());
088         fxmlLoader.setBuilderFactory(new JavaFXBuilderFactory(getApplication().getApplicationClassLoader().get()));
089         fxmlLoader.setClassLoader(getApplication().getApplicationClassLoader().get());
090         fxmlLoader.setControllerFactory(klass -> getMvcGroup().getView());
091 
092         try {
093             fxmlLoader.load();
094         catch (IOException e) {
095             throw new GriffonException(e);
096         }
097 
098         Parent node = fxmlLoader.getRoot();
099 
100         URL cssResource = getResourceAsURL(styleName);
101         if (cssResource != null) {
102             String uriToCss = cssResource.toExternalForm();
103             node.getStylesheets().add(uriToCss);
104         }
105 
106         return node;
107     }
108 
109     @Nonnull
110     protected String resolveBasename() {
111         GriffonClass griffonClass = getGriffonClass();
112         String packageName = griffonClass.getPackageName();
113         String baseName = griffonClass.getLogicalPropertyName();
114         if (!isBlank(packageName)) {
115             baseName = packageName + "." + baseName;
116         }
117         return baseName;
118     }
119 
120     protected void connectActions(@Nonnull Object node, @Nonnull GriffonController controller) {
121         JavaFXUtils.connectActions(node, controller);
122     }
123 
124     @Nullable
125     protected JavaFXAction toolkitActionFor(@Nonnull GriffonController controller, @Nonnull String actionName) {
126         Action action = actionFor(controller, actionName);
127         return action != null (JavaFXActionaction.getToolkitAction() null;
128     }
129 }