关闭它后,将同一个JavaFx窗口联系起来

时间:2015-08-05 18:00:38

标签: javafx

我使用Jframe打开一个JavaFX应用程序。在使用JavaFx应用程序窗口后我关闭了窗口。并且想要再次打开同一个Javafx窗口但是发生错误 -  java.lang.IllegalStateException:不得多次调用应用程序启动

1 个答案:

答案 0 :(得分:0)

正如documentation中所述,多次调用Application.launch(...)会导致异常:

public static void launch(String... args)
     

启动独立应用程序。通常从中调用此方法   主要方法()。它不能被多次调用或调用   异常将被抛出。

如果需要混合使用Swing和JavaFX,则应将JavaFX片段嵌入JFXPanel并将其放在JFrame中。然后,您可以使用JFrame随时显示和隐藏setVisible(...)。以这种方式工作的应用程序根本不会有Application子类。

混合使用Swing和JavaFX很棘手,不建议初学者使用。问题是每个工具包都有自己的UI线程,并且必须在正确的 UI线程(即Swing / AWT组件的AWT事件调度线程和JavaFX应用程序)上执行UI的所有访问。 JavaFX组件的线程)。两者之间共享的数据必须提供适当的同步,以确保可以从多个线程安全地访问它。

这是一个非常简单的例子。单击该按钮将显示具有FX内容的窗口。如果您关闭该窗口,然后再次单击该按钮,它将再次显示。

import java.awt.BorderLayout;
import java.util.Random;

import javafx.application.Platform;
import javafx.embed.swing.JFXPanel;
import javafx.scene.Scene;
import javafx.scene.chart.LineChart;
import javafx.scene.chart.NumberAxis;
import javafx.scene.chart.XYChart.Data;
import javafx.scene.chart.XYChart.Series;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;


public class SwingFXExample {
    private JFrame mainFrame ;
    private JFrame fxFrame ;
    private JFXPanel fxPanel ;

    public SwingFXExample() {
        // must be on Swing thread...
        if (! SwingUtilities.isEventDispatchThread()) {
            throw new IllegalStateException("Not on Event Dispatch Thread");
        }

        mainFrame = new JFrame();
        JButton showFX = new JButton("Show FX Window");
        JPanel content = new JPanel();
        content.add(showFX);
        mainFrame.add(content, BorderLayout.CENTER);

        mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        fxFrame = new JFrame();
        fxPanel = new JFXPanel();
        fxFrame.add(fxPanel);
        fxFrame.setSize(640, 640);
        fxFrame.setLocationRelativeTo(null);


        Platform.runLater(() -> initFX()); 

        showFX.addActionListener(event -> fxFrame.setVisible(true));
    }

    private void initFX() {
        // must be on FX Application Thread...
        if (! Platform.isFxApplicationThread()) {
            throw new IllegalStateException("Not on FX Application Thread");
        }


        LineChart<Number, Number> chart = new LineChart<>(new NumberAxis(), new NumberAxis());
        Series<Number, Number> series = new Series<>();
        series.setName("Random data");
        Random rng = new Random();
        for (int i = 0; i <= 10; i++) {
            series.getData().add( new Data<>(i, 100*rng.nextDouble()) );
        }
        chart.getData().add(series);
        chart.setOnMouseClicked(evt -> {
            if (evt.getClickCount() == 2) {
                System.out.println("Double click!");
            }
        });
        fxPanel.setScene(new Scene(chart, 400, 400));
    }

    public void showMainWindow() {
        mainFrame.setSize(350, 120);
        mainFrame.setLocationRelativeTo(null);
        mainFrame.setVisible(true);
    }

    public static void main(String[] args) {
        SwingUtilities.invokeLater(() -> {
            SwingFXExample app = new SwingFXExample();
            app.showMainWindow();
        });
    }
}