Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/spring/13.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何让Spring在初始化节点bean时使用JavaFX应用程序线程?_Java_Spring_Javafx - Fatal编程技术网

如何让Spring在初始化节点bean时使用JavaFX应用程序线程?

如何让Spring在初始化节点bean时使用JavaFX应用程序线程?,java,spring,javafx,Java,Spring,Javafx,我正在尝试使用JavaFX作为UI框架创建一个客户端应用程序,它与Spring集成,以利用现代UI、依赖项注入、AOP和丰富的RESTAPI。在我的JavaFX应用程序的init()方法中,将创建一个SpringApplication,以自动连接节点场景所需的bean。这些节点bean使用@Component注释进行注释,还使用init()方法和@PostConstruct注释进行初始化,并在构造后设计每个节点。现在我意识到大多数init()方法都需要JavaFX应用程序线程。如何强制Sprin

我正在尝试使用JavaFX作为UI框架创建一个客户端应用程序,它与Spring集成,以利用现代UI、依赖项注入、AOP和丰富的RESTAPI。在我的JavaFX
应用程序的
init()
方法中,将创建一个
SpringApplication
,以自动连接
节点
场景所需的bean。这些
节点
bean使用
@Component
注释进行注释,还使用
init()
方法和
@PostConstruct
注释进行初始化,并在构造后设计每个节点。现在我意识到大多数
init()
方法都需要
JavaFX应用程序线程
。如何强制Spring在初始化这些节点时使用
JavaFX应用程序线程
?我可能需要在这里重构代码

示例代码

@Configuration
@EnableAsync
@EnableScheduling
@EnableCaching
// Component scanning for JavaFX Nodes
@ComponentScan("path.to.view.nodes")
public class MyConfiguration {

   // bean definitiions here
}

public class MyApplication extends Application {

    private ConfigurableApplicationContext configurableApplicationContext;

    @Autowired
    private RootPane rootPane;

    @Override
    public void init() throws Exception {
        SpringApplication application;
        application = new SpringApplication();
        application.getSources().add(MyConfiguration.class);
        application.setWebEnvironment(false);
        application.setShowBanner(false);
        application.setRegisterShutdownHook(true);
        configurableApplicationContext = application.run();
        ConfigurableListableBeanFactory beanFactory;
        beanFactory = configurableApplicationContext.getBeanFactory();
        beanFactory.registerSingleton(getClass().getSimpleName(), this);
        beanFactory.autowireBean(this);
    }

    @Override
    public void start(Stage primaryStage) throws Exception {
        primaryStage.setScene(new Scene(rootPane));
        primaryStage.centerOnScreen();
        primaryStage.show();
    }

    @Override
    public void stop() throws Exception {
        configurableApplicationContext.close();
    }

    public static void main(String... args) {
        Application.launch(MyApplication.class, args);
    }

}

@Component
public class RootPane extends BorderPane {

    @PostConstruct
    public void init() {
        setRight(new Button("Click me"));
    }

}
现在我意识到大多数init()方法都需要JavaFX应用程序线程

这种假设是错误的,您可以在JavaFX应用程序线程之外初始化节点

您不能在JavaFX应用程序线程之外修改活动场景图中的节点。但是,只有在调用Application start()方法后,才会有一个活动场景图,这要等到init()方法完成后才会发生。有关更多信息,请阅读javafxjavadoc

在Application init()方法中,没有活动的场景图,无论在哪个线程上对节点执行什么操作,只要在将场景附加到start()方法中提供的阶段之前完成所有工作,就不会违反任何JavaFX线程规则

我所知道的这个规则(对于JavaFX8)的唯一例外是,它必须仅从FX线程创建和访问

所以,我不是在回答你原来的问题,但也许不需要回答