JavaFXでWindowを表示する
- JavaFXのアプリケーションはjavafx.application.Applicationを継承して作る。
- ちなみにjavafx.application.Applicationは抽象クラス(アブストラクトクラス)。
- startメソッドをオーバーライドして、そこで各種設定(部品配置等)を行う。startメソッドはJavaFXにおけるコンストラクタのような役割。
- アプリケーションの起動は「Application.launch(アプリケーションのクラス名.class);」で行う。
1 2 3 4 5 6 7 8 9 10 11 12 |
package lesson13.d00000; import javafx.application.Application; import javafx.stage.Stage; public class CounterApp extends Application { @Override public void start(Stage primaryStage) throws Exception { primaryStage.setTitle("カウンター"); primaryStage.show(); } } |
1 2 3 4 5 6 7 8 9 |
package lesson13.d00000; import javafx.application.Application; public class Main { public static void main(String[] args) { Application.launch(CounterApp.class); } } |
ボタンなどを配置する
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 |
package lesson13.d00000; import javafx.application.Application; import javafx.scene.Scene; import javafx.scene.control.Button; import javafx.scene.control.Label; import javafx.scene.layout.Pane; import javafx.stage.Stage; public class CounterApp extends Application { private Label label; private Button countButton; private Button resetButton; @Override public void start(Stage primaryStage) throws Exception { // ラベル label = new Label(); label.setText("0"); label.relocate(10, 10); // カウントボタン countButton = new Button(); countButton.setText("カウント"); countButton.relocate(10, 40); // リセットボタン resetButton = new Button(); resetButton.setText("リセット"); resetButton.relocate(10, 70); // ペイン(レイアウト) Pane pane = new Pane(); pane.getChildren().add(label); // ペインにラベルを追加 pane.getChildren().add(countButton); // ペインにカウントボタンを追加 pane.getChildren().add(resetButton); // ペインにリセットボタンを追加 // シーン Scene scene = new Scene(pane, 150, 200); primaryStage.setScene(scene); // シーンにペインをセット // 最初はこれだけ primaryStage.setTitle("カウンター"); primaryStage.show(); } } |
イベントハンドラー(オブザーバー)
- ボタンクラスはイベント(ボタンがクリックされた等)が発生した時に、何か処理をすること(させること)ができる。
- 「イベントが発生した時の処理」を担当するクラスを「イベントハンドラー(event handler)」という。
- もっと詳しく知りたい人へ: Observerパターン
- (JavaFxの場合)ButtonのイベントハンドラーはEventHandler
インターフェース を実装する。 - ボタンに関するイベントが発生すると、ボタンに登録したイベントハンドラーのhandleメソッドが実行される。
1 2 3 4 5 6 7 8 9 10 11 |
package lesson13.d00000; import javafx.event.ActionEvent; import javafx.event.EventHandler; public class ExampleHandler implements EventHandler<ActionEvent> { @Override public void handle(ActionEvent event) { System.out.println("イベント発生"); } } |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
// ハンドラー EventHandler<ActionEvent> handler = new ExampleHandler(); // カウントボタン countButton = new Button(); countButton.setText("カウント"); countButton.relocate(10, 40); countButton.setOnAction(handler); // リセットボタン resetButton = new Button(); resetButton.setText("リセット"); resetButton.relocate(10, 70); resetButton.setOnAction(handler); |
ExampleHandlerをきちんと動作させる(カウントボタンでラベルに表示されるカウンターを増やし、リセットボタンで0にする)には次の2つができるようにすればいいが、煩雑なコードになる。
- labelのsetTextメソッドを呼べるようにする
- countButtonとresetButtonのどちらからイベントが発生したか区別できるようにする
カウンターの機能をうまく実現するには、CounterAppがイベントを処理するようにするのが簡潔になる。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 |
package lesson13.d00000; import javafx.application.Application; import javafx.event.ActionEvent; import javafx.event.EventHandler; import javafx.scene.Scene; import javafx.scene.control.Button; import javafx.scene.control.Label; import javafx.scene.layout.Pane; import javafx.stage.Stage; public class CounterApp extends Application implements EventHandler<ActionEvent> { private Label label; private Button countButton; private Button resetButton; private int count = 0; @Override public void start(Stage primaryStage) throws Exception { // ラベル label = new Label(); label.setText("0"); label.relocate(10, 10); // カウントボタン countButton = new Button(); countButton.setText("カウント"); countButton.relocate(10, 40); countButton.setOnAction(this); // リセットボタン resetButton = new Button(); resetButton.setText("リセット"); resetButton.relocate(10, 70); resetButton.setOnAction(this); // ペイン(レイアウト) Pane pane = new Pane(); pane.getChildren().add(label); // ペインにラベルを追加 pane.getChildren().add(countButton); // ペインにカウントボタンを追加 pane.getChildren().add(resetButton); // ペインにリセットボタンを追加 // シーン Scene scene = new Scene(pane, 150, 200); primaryStage.setScene(scene); // シーンにペインをセット // 最初はこれだけ primaryStage.setTitle("カウンター"); primaryStage.show(); } @Override public void handle(ActionEvent event) { Object source = event.getSource(); // イベントの発生源となっているインスタンスを取得する if (source.equals(countButton)) { count++; } else if (source.equals(resetButton)) { count = 0; } label.setText(Integer.toString(count)); } } |