0

I'm trying to add spring to my pom but I'm wondering if my build will look like this. Could someone help me how can I do this spring integration with java fx?

my pom:

    <properties>
        <java.version>12</java.version>
    </properties>

    <dependencies>
       <dependency>
            <groupId>org.openjfx</groupId>
            <artifactId>javafx-controls</artifactId>
            <version>12.0.2</version>
        </dependency>
        <dependency>
            <groupId>org.openjfx</groupId>
            <artifactId>javafx-fxml</artifactId>
            <version>12.0.2</version>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-jpa</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-mail</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-quartz</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-devtools</artifactId>
            <scope>runtime</scope>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <scope>runtime</scope>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>

</project>

main class:

public class App extends Application {
    private static Scene scene;
    @Override
    public void start(Stage stage) throws IOException {
        scene = new Scene(loadFXML("primary"));
        stage.setScene(scene);
        stage.show();
    }
    static void setRoot(String fxml) throws IOException {
        scene.setRoot(loadFXML(fxml));
    }
    private static Parent loadFXML(String fxml) throws IOException {
        FXMLLoader fxmlLoader = new FXMLLoader(App.class.getResource(fxml + ".fxml"));
        return fxmlLoader.load();
    }
    public static void main(String[] args) {
        launch();
    } }

I searched and found nothing about integrating javafx with spring Could someone help me how I can integrate spring?

I tried to use what I used in my swing project but it didn't work out

Joao Spirit
  • 113
  • 3
  • 15

1 Answers1

1

Your main app has to maintain Spring's application context like this.

import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.support.AbstractApplicationContext;

@Configuration // or @SpringBootApplication if you used spring boot.
public class App extends Application {
    private static Scene scene;
    private AbstractApplicationContext context;

    @Override
    public void init() throws Exception {
        this.context = new AnnotationConfigApplicationContext(App.class);
        super.init();
    }

    @Override
    public void start(Stage stage) throws IOException {
        SpringFxmlLoader loader = new SpringFxmlLoader(this.context);
        Parent root = loader.loadFromResource("primary.fxml");
        stage.setScene(new Scene(root));
        stage.show();
    }

    public static void main(String[] args) {
        launch();
    }
}

use SpringFxmlLoader for returning a controller as a spring bean.

import java.io.IOException;
import java.io.InputStream;
import java.net.URL;

import org.springframework.context.ApplicationContext;

import javafx.fxml.FXMLLoader;

public class SpringFxmlLoader extends FXMLLoader {
    private ApplicationContext context;

    protected SpringFxmlLoader() {
    }

    public SpringFxmlLoader(ApplicationContext context) {
        this.context = context;
        setControllerFactory(context::getBean);     // return a spring bean from spring's application context.
    }

    public ApplicationContext getContext() {
        return this.context;
    }

    public <T> T loadFromResource(String resource) throws IOException {
        return loadFromResource(resource, null);
    }

    public <T> T loadFromResource(String resource, Class<?> root) throws IOException {
        URL resourceURL = context.getResource(resource).getURL();
        setLocation(resourceURL);
        if(root != null) setRoot(root);
        try (InputStream fxml = resourceURL.openStream()) {
            return load(fxml);
        }
    }
}

Your controller should be looked like this as a spring bean.

@Controller
@Scope("prototype")
public class PrimaryController {
    @FXML private Parent rootView;
    @FXML private TitledPane settingPane;

    @Autowired private SomeBean someBean;   // now you can autowire spring beans.
    // braa....

}

Don't forget specify the controller class in your primary.fxml with fx:controller attribute.

Charles Lee
  • 361
  • 1
  • 5
  • Now i have this problem with maven if you can help me : https://stackoverflow.com/questions/57410152/javafx-12-spring-maven-no-plugin-found-for-prefix – Joao Spirit Aug 08 '19 at 10:46