使用FXML的方式切换场景(SceneBuilder)

3
我有两个场景,场景1上有一个标签,上面只写着“This is scene 1”,还有一个按钮,上面写着“按我进入场景2”。场景2和场景1类似,但是标签和文字相反。
问题很简单,或者至少应该是简单的。我可以用JavaFX的方式解决这个问题,但是好像无法使用FXML的方式解决。
我有一个主类 -
import java.io.IOException;

import javafx.application.Application;
import javafx.fxml.FXMLLoader;
import javafx.scene.Scene;
import javafx.scene.layout.AnchorPane;
import javafx.stage.Stage;

public class ManinApp extends Application
{
Stage primaryStage;
private AnchorPane rootLayout;

public static void main(String [] args)
{
    launch(args);
}
public void start(Stage primaryStage)
{
    this.primaryStage = primaryStage;
    this.primaryStage.setTitle("Two Scenes");

    initRootLayout();
    //showSecondScene();
}
public void initRootLayout()
{
    try
    {
        FXMLLoader loader = new FXMLLoader();
        loader.setLocation(ManinApp.class.getResource("Scene1.fxml"));
        rootLayout = (AnchorPane) loader.load();

        Scene scene = new Scene(rootLayout);
        primaryStage.setScene(scene);
        primaryStage.show();

    }
    catch(IOException e)
    {
        e.printStackTrace();
    }
}
/**
public void showSecondScene()
{
    try
    {
        FXMLLoader loader = new FXMLLoader();
        loader.setLocation(ManinApp.class.getResource("Scene2.fxml"));
        AnchorPane secondScene = (AnchorPane)loader.load();
        rootLayout.getChildren().add(secondScene);



    }
    catch(IOException e)
    {
        e.printStackTrace();
    }
}
*/
public Stage getPrimaryStage()
{
    return primaryStage;
}

目前,showSecondScene()已被注释掉。我的理解是您还需要一个Controller类将代码与SceneBuilder连接起来?

采用FX方式的解决方案如下:

         btnscene1.setOnAction(e ->
            {
        if(e.getSource() == btnscene1)
            thestage.setScene(scene2);
        else
            thestage.setScene(scene1);

            });
        btnscene2.setOnAction(e ->
           {
       if(e.getSource()==btnscene2)
        thestage.setScene(scene1);
        else
           thestage.setScene(scene2);
      });

对于格式问题表示抱歉!

我如何使用控制器类来操作在主类中声明的主舞台和两个场景?

希望我的表述清晰易懂。

2个回答

2

我认为你做得很好。FXML(和SceneBuilder)在这里被正确使用。

我建议以下几点:

  • 使用根容器(例如StackPane)来托管scene1或scene2(更好的名称应该是layout1/layout2)。您不需要在此处使用不同的场景。
  • 在初始化时加载两个fxml文件(如果需要,可以进行延迟加载)
  • 通过删除根容器的内容并添加另一个容器来从一个容器切换到另一个容器。

现在,如果布局很大,并且涉及大量CSS,并且您需要经常从layout1切换到layout2,则可以将两个布局添加到根容器中。然后使用:

setVisible()
setManaged()

在您想要隐藏/显示的布局的根上设置此属性。 这样做可以避免在场景图中添加节点时执行的布局和css步骤。


太棒了,感谢您抽出时间回答问题。我会在某个时候尝试这个方法,但为了我的任务,我已经选择了使用JavaFX的编码方式。在提交之后,我将开始尝试FXML并尝试这个方法。 - Treeno1

0

虽然我在技术上理解你想要实现的内容,但我仍然不明白背后的原因。

如果你只是想切换窗口的“主”内容,请使用StackPane作为根节点,在该堆栈中添加多个布局,并通过切换要处理的布局#toFront()来解决问题。

通常情况下,堆栈上的布局是透明的(当然,除了像按钮之类的控件),因此你需要设置堆叠布局的背景或者(我更喜欢这种方式)切换后面的那个布局的可见性(或将不透明度设置为0等等)。


太好了。我一定会试一下的。谢谢。 - Treeno1
如果这对您有帮助,请考虑点赞。谢谢。 - dzim

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接