以 FXML 方式切换场景 (SceneBuilder)
Switching scenes the FXML way (SceneBuilder)
我有两个场景,场景 1 上有一个简单显示 "This is scene 1" 的标签,它还有一个带有文本 "Press me to go to scene 2" 的按钮。场景2与场景1类似,但场景2的标签和文字说明相反
问题很简单,至少应该是这样。我能够以 javaFX 方式执行此操作,但似乎无法以 FXML 方式执行此操作。
我有一个主class -
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() 目前已被注释掉。我的理解是您还需要一个控制器 class 来将代码连接到 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);
});
抱歉格式问题!
我如何使用控制器 class 来做到这一点,从中我可以使用主要阶段和在我的主要 class 中声明的两个场景?
我希望它有意义
虽然我在技术上理解你想要实现的目标,但我仍然不知道其背后的原因。
如果您只想切换 window 的 "main" 内容,请使用 StackPane 作为根,向该堆栈添加多个布局,然后通过切换您想要的那个来解决您的问题在 #toFront() 上工作。
一般情况下堆叠的Layouts是透明的(当然按钮等控件除外),所以要么需要给堆叠的Layouts设置背景OR(我更喜欢)切换后面那个的可见性(或将不透明度设置为 0,或类似的设置)。
我觉得你做得很好。此处正确使用了 FXML(和 SceneBuilder)。
我会提出一些建议:
- 使用根容器(例如 StackPane)来托管场景 1 或场景 2
(更好的名字是 layout1 / layout2)。你不需要使用
这里有不同的场景。
- 在初始化时加载两个 fxml 文件(或在需要时延迟加载)
- 通过删除根容器的内容并添加另一个来从一个切换到另一个。
现在,如果布局很大,涉及很多 css,并且您需要经常从布局 1 切换到布局 2,您可能需要在根容器中添加这两个布局。然后,使用:
setVisible()
setManaged()
...在您要隐藏/显示的布局的根目录上。
这样做可以避免在场景图中添加节点后立即完成的布局和 css 步骤。
我有两个场景,场景 1 上有一个简单显示 "This is scene 1" 的标签,它还有一个带有文本 "Press me to go to scene 2" 的按钮。场景2与场景1类似,但场景2的标签和文字说明相反
问题很简单,至少应该是这样。我能够以 javaFX 方式执行此操作,但似乎无法以 FXML 方式执行此操作。
我有一个主class -
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() 目前已被注释掉。我的理解是您还需要一个控制器 class 来将代码连接到 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);
});
抱歉格式问题!
我如何使用控制器 class 来做到这一点,从中我可以使用主要阶段和在我的主要 class 中声明的两个场景?
我希望它有意义
虽然我在技术上理解你想要实现的目标,但我仍然不知道其背后的原因。
如果您只想切换 window 的 "main" 内容,请使用 StackPane 作为根,向该堆栈添加多个布局,然后通过切换您想要的那个来解决您的问题在 #toFront() 上工作。
一般情况下堆叠的Layouts是透明的(当然按钮等控件除外),所以要么需要给堆叠的Layouts设置背景OR(我更喜欢)切换后面那个的可见性(或将不透明度设置为 0,或类似的设置)。
我觉得你做得很好。此处正确使用了 FXML(和 SceneBuilder)。
我会提出一些建议:
- 使用根容器(例如 StackPane)来托管场景 1 或场景 2 (更好的名字是 layout1 / layout2)。你不需要使用 这里有不同的场景。
- 在初始化时加载两个 fxml 文件(或在需要时延迟加载)
- 通过删除根容器的内容并添加另一个来从一个切换到另一个。
现在,如果布局很大,涉及很多 css,并且您需要经常从布局 1 切换到布局 2,您可能需要在根容器中添加这两个布局。然后,使用:
setVisible()
setManaged()
...在您要隐藏/显示的布局的根目录上。 这样做可以避免在场景图中添加节点后立即完成的布局和 css 步骤。