当前位置: 首页 > 知识库问答 >
问题:

如何使用控制器类(以ActionEvent为参数)切换场景?

冯阳云
2023-03-14

我想制作一个可以在场景之间切换的基本GUI。我知道以前有人问过这个问题,相信我,我已经试着寻找解决方案好几个小时了,但都没有结果,所以我求助于此。

以下是相关代码:

public class MainMenuController implements Initializable {

public void startNewGame(ActionEvent event) throws IOException {
    Parent tableViewParent = FXMLLoader.load(getClass().getResource("Game.fxml"));
    Scene tableViewScene = new Scene(tableViewParent);

    Stage window = (Stage)((Node)event.getSource()).getScene().getWindow();

    window.setScene(tableViewScene);
    window.show();
}

@Override
public void initialize(URL url, ResourceBundle rb) {

}

这里是主端:

public class MainApplication extends Application {

@Override
public void start(Stage primaryStage) throws Exception{
    Parent root = FXMLLoader.load(getClass().getResource("MainMenu.fxml"));
    primaryStage.setTitle("Main Menu");
    primaryStage.setScene(new Scene(root));
    primaryStage.show();
}

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

当我运行它时,它给出了这个错误:

Exception in Application start method
java.lang.reflect.InvocationTargetException
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.base/java.lang.reflect.Method.invoke(Method.java:567)
    at javafx.graphics/com.sun.javafx.application.LauncherImpl.launchApplicationWithArgs(LauncherImpl.java:464)
    at javafx.graphics/com.sun.javafx.application.LauncherImpl.launchApplication(LauncherImpl.java:363)
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.base/java.lang.reflect.Method.invoke(Method.java:567)
    at java.base/sun.launcher.LauncherHelper$FXHelper.main(LauncherHelper.java:1051)
Caused by: java.lang.RuntimeException: Exception in Application start method
    at javafx.graphics/com.sun.javafx.application.LauncherImpl.launchApplication1(LauncherImpl.java:900)
    at javafx.graphics/com.sun.javafx.application.LauncherImpl.lambda$launchApplication$2(LauncherImpl.java:195)
    at java.base/java.lang.Thread.run(Thread.java:835)
Caused by: javafx.fxml.LoadException: Error resolving onAction='#startNewGame', either the event handler is not in the Namespace or there is an error in the script.
...

    at javafx.fxml/javafx.fxml.FXMLLoader.constructLoadException(FXMLLoader.java:2621)
    at javafx.fxml/javafx.fxml.FXMLLoader$Element.processEventHandlerAttributes(FXMLLoader.java:618)
    at javafx.fxml/javafx.fxml.FXMLLoader$ValueElement.processEndElement(FXMLLoader.java:778)
    at javafx.fxml/javafx.fxml.FXMLLoader.processEndElement(FXMLLoader.java:2838)
    at javafx.fxml/javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:2557)
    at javafx.fxml/javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:2466)
    at javafx.fxml/javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3237)
    at javafx.fxml/javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3194)
    at javafx.fxml/javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3163)
    at javafx.fxml/javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3136)
    at javafx.fxml/javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3113)
    at javafx.fxml/javafx.fxml.FXMLLoader.load(FXMLLoader.java:3106)
    at GUI.MainApplication.start(MainApplication.java:13)
    at javafx.graphics/com.sun.javafx.application.LauncherImpl.lambda$launchApplication1$9(LauncherImpl.java:846)
    at javafx.graphics/com.sun.javafx.application.PlatformImpl.lambda$runAndWait$12(PlatformImpl.java:455)
    at javafx.graphics/com.sun.javafx.application.PlatformImpl.lambda$runLater$10(PlatformImpl.java:428)
    at java.base/java.security.AccessController.doPrivileged(AccessController.java:389)
    at javafx.graphics/com.sun.javafx.application.PlatformImpl.lambda$runLater$11(PlatformImpl.java:427)
    at javafx.graphics/com.sun.glass.ui.InvokeLaterDispatcher$Future.run(InvokeLaterDispatcher.java:96)
    at javafx.graphics/com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
    at javafx.graphics/com.sun.glass.ui.win.WinApplication.lambda$runLoop$3(WinApplication.java:174)
    ... 1 more
Exception running application GUI.MainApplication

所以我知道这是由处理按钮动作的方法引起的。我可以成功地使用操作制作其他按钮,只要它们没有参数ActionEvent

似乎每当我添加这个参数来访问动作事件时,这个方法就不能被识别。我认为我在设置主应用程序或控制器甚至fxml时犯了根本性的错误。我看了那么多教程,也不是很懂,因为我也有类似的东西。

这是fxml文件。开始场景(MainMenu.fxml):

    <?xml version="1.0" encoding="UTF-8"?>

    <?import javafx.scene.control.Button?>
    <?import javafx.scene.control.Label?>
    <?import javafx.scene.layout.AnchorPane?>
    <?import javafx.scene.text.Font?>

    <AnchorPane fx:id="ap" maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="658.0" prefWidth="885.0" xmlns="http://javafx.com/javafx/11.0.1" xmlns:fx="http://javafx.com/fxml/1" fx:controller="GUI.MainMenuController">
       <children>
          <Label fx:id="title" layoutX="322.0" layoutY="30.0" prefHeight="48.0" prefWidth="241.0" text="Text Adventure">
             <font>
                <Font size="35.0" />
             </font>
          </Label>
          <Button layoutX="384.0" layoutY="204.0" mnemonicParsing="false" onAction="#startNewGame" prefHeight="51.0" prefWidth="117.0" text="Start New Game" />
       </children>
    </AnchorPane>

将切换到的场景 (Game.fxml):

 <?xml version="1.0" encoding="UTF-8"?>

<?import javafx.scene.control.Label?>
<?import javafx.scene.control.RadioButton?>
<?import javafx.scene.control.ToggleGroup?>
<?import javafx.scene.layout.AnchorPane?>
<?import javafx.scene.text.Font?>

<AnchorPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="658.0" prefWidth="885.0" xmlns="http://javafx.com/javafx/11.0.1" xmlns:fx="http://javafx.com/fxml/1" fx:controller="GUI.GameController">
   <children>
      <RadioButton fx:id="radio1" layoutX="201.0" layoutY="337.0" mnemonicParsing="false" onAction="#radio1Click" text="RadioButton">
         <toggleGroup>
            <ToggleGroup fx:id="group" />
         </toggleGroup>
      </RadioButton>
      <RadioButton fx:id="radio2" layoutX="201.0" layoutY="402.0" mnemonicParsing="false" onAction="#radio2Click" text="RadioButton" toggleGroup="$group" />
      <RadioButton fx:id="radio3" layoutX="201.0" layoutY="469.0" mnemonicParsing="false" onAction="#radio3Click" text="RadioButton" toggleGroup="$group" />
      <Label fx:id="output" layoutX="169.0" layoutY="25.0" prefHeight="231.0" prefWidth="462.0" text="Label">
         <font>
            <Font size="17.0" />
         </font>
      </Label>
   </children>
</AnchorPane>

共有1个答案

袁奇玮
2023-03-14

经过数小时的头痛和浪费时间,答案是Netbean导入了错误版本的ActionEvent(java.awt版本而不是javafx版本)。万一将来有人遇到这个问题,请确保您以这种方式导入:

import javafx.event.ActionEvent;
 类似资料:
  • 问题内容: 有什么方法可以从关联的类控制器获取FXML加载文件的Scene对象。 我正在做这样的事情: 但是我想要一个不引用AnchorPane控件的解决方案。 问题答案: 为什么不?Controller是一个抽象类,除非您有意让他知道,否则他不了解UI。 节点(包括AnchorPane)是另一个故事,它们几乎不存在于场景图的外部。因此,最好向Node询问有关其父母或场景的信息。 如果您仍然想单独

  • 但我想要一个不引用AnchorPane控件的解决方案。

  • 我有一个调查表列表,每个表都有一个按钮/asp操作,可以查看至少3个竞争对手的答案。但我需要使用模式选择调查表中的竞争对手。在该模式中,我应该在主体中填充一个复选框,其中包含回答该调查表的竞争对手。如何将数据切换模式导入控制器? 以下是我的看法: 这是我的控制器,它应该将值返回到索引模式: 我应该在正文中填入回答该调查表的竞争对手的复选框。但每当我单击“查看竞争对手”时,它不会转发给控制器。

  • 我是spring的新手,我设法在JSP视图中从表单收集数据,并将表单提交给控制器。根据从视图中获取的数据,我正在实例化一个模型对象,其中还包含其他模型对象: 我怎样才能用更少的行替换整个@刚体属性行?我是否还需要将@ModelAtinn注释添加到模型类(Form结果,主题,波)? 谢谢。

  • 我是新手,正在尝试学习JavaFX和FXML。我的大部分应用程序逻辑都在FXMLController类中,基类几乎是空的,除了NetBeans IDE生成的基本代码,如下所示 我有一个ID为input1的元素,类型为TextField。如何通过ID访问此(或任何其他)控件?(请记住,我是控制器类而不是主类)。 我在下面找到了这个问题,这正是我要找的,但情况不同,因为它们在定义< code>scen