2016-04-08 50 views
1

請幫我做到這一點。它凍結而不是改變場景。Javafx如何通過函數創建按鈕?

Button b1 = new Button("Go to s2"); 
b1.setOnAction(e -> window.setScene(s2)); 
Button b2 = new Button("Go to s1"); 
b2.setOnAction(e -> window.setScene(s1)); 

,但我想,使其更加優雅...

import javafx.application.Application; 
import javafx.scene.Scene; 
import javafx.scene.control.Button; 
import javafx.stage.Stage; 

public class Main extends Application { 

    Stage window; 
    Scene s1,s2; 

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

    @Override 
    public void start(Stage primaryStage) throws Exception { 
     window = primaryStage; 

     Button b1 = makeButton("Go to s2", s2); 
     Button b2 = makeButton("Go to s1", s1); 

     s1 = new Scene(b1); 
     s2 = new Scene(b2); 

     primaryStage.setScene(s1); 
     primaryStage.show(); 
    } 

    public Button makeButton(String name, Scene destScene) { 
     Button button = new Button(name); 
     button.setOnAction(e -> window.setScene(destScene)); 
     return button; 
    } 
} 

非常感謝你提前: 按鈕創建這樣,當它工作正常!

回答

1

看一切是如何初始化的順序:

Button b1 = makeButton("Go to s2", s2); 
Button b2 = makeButton("Go to s1", s1); 

s1 = new Scene(b1); 
s2 = new Scene(b2); 

當你調用makeButton,你在當前存儲在s1s2參考的值傳遞。由於它從未初始化,所以它的默認值爲null。由於複製的參考文件,您在設置s1s2時不會發生變化。

在第一種情況下,您沒有同樣的問題,因爲您從不製作s1s2的副本。相反,您將EventHandler引用到當前實例Main中的字段,該字段在設置後會正確更新。所以,你原來的代碼是什麼相同的:

Button b1 = new Button("Go to s2"); 
b1.setOnAction(e -> window.setScene(this.s2)); 

所以你複製參考封閉Main實例,而不是參照按鈕本身。

不幸的是,我沒有看到任何微不足道的修復。我看到的最簡單的解決辦法是給你的函數改爲makeButton(String, EventHandler<ActionEvent>),並調用它像這樣:

Button b1 = makeButton("Go to s2", e -> window.setScene(s2)); 

不是像你一樣,你想要什麼,但它應該工作。

另一種可能的解決方案是將所有的Button s放入一個數組中,然後將索引傳入該數組中,並將其傳入makeButton。這看起來就像tihs:

public class Main extends Application { 
    Stage window; 
    Scene[] scenes = new Scene[2]; 

    @Override 
    public void start(Stage primaryStage) throws Exception { 
     window = primaryStage; 

     Button b1 = makeButton("Go to s2", 1); 
     Button b2 = makeButton("Go to s1", 0); 

     scenes[0] = new Scene(b1); 
     scenes[1] = new Scene(b2); 

     primaryStage.setScene(scenes[0]); 
     primaryStage.show(); 
    } 

    public Button makeButton(String name, int destScene) { 
     Button button = new Button(name); 
     button.setOnAction(e -> window.setScene(scenes[destScene])); 
     return button; 
    } 
} 

這改變了EventHandler引用的Mainscenes)字段,而不是一個局部變量(destScene)。