12 リスト・ビュー
この章では、JavaFXアプリケーションでリストを作成する方法について説明します。
ListView
クラスは項目のスクロールが可能なリストを表します。図12-1はホテル予約システムで利用できる部屋のタイプのリストを示しています。
setItems
メソッドを使用して項目を定義すると、リストを作成できます。また、setCellFactory
メソッドを適用すると、リスト内に項目のビューを作成できます。
リスト・ビューの作成
例12-1のコード・フラグメントは図12-1に示すString
項目をリストに実装します。
例12-1 リスト・ビュー・コントロールの作成
ListView<String> list = new ListView<>(); ObservableList<String> items =FXCollections.observableArrayList ( "Single", "Double", "Suite", "Family App"); list.setItems(items);
リスト・ビュー・コントロールのサイズと高さを変更するには、setPrefHeight
メソッドおよびsetPrefWidth
メソッドを使用します。例12-2は垂直方向リストを幅100ピクセル、高さ70ピクセルに制限しており、その結果を図12-2に示します。
ListView
オブジェクトは、オリエンテーション・プロパティをOrientation.HORIZONTAL
設定にすると水平方向に配置できます。これを行うには、list.setOrientation(Orientation.HORIZONTAL)
のようにします。図12-3に、図12-1と同じ項目を水平方向リストで示します。
SelectionModel
クラスおよびFocusModel
クラスでのListView
オブジェクトの選択とフォーカスは常に追跡できます。各項目の現在の状況を取得するには、次のメソッドを組み合せて使用します。
-
getSelectionModel().getSelectedIndex()
- 単一選択モードで現在選択されている項目の索引を返します -
getSelectionModel().getSelectedItem()
- 現在選択されている項目を返します -
getFocusModel().getFocusedIndex()
- 現在フォーカスされている項目の索引を返します -
getFocusModel().getFocusedItem()
- 現在フォーカスされている項目を返します
デフォルトのSelectionModel
は、ListView
のインスタント化がMultipleSelectionModel
抽象クラスの実装の場合に使用されます。ただし、selectionMode
プロパティのデフォルト値はSelectionMode.SINGLE
です。デフォルトのListView
インスタンスでの複数選択を可能にするには、次のコール・シーケンスを使用します。
listView.getSelectionModel().setSelectionMode(SelectionMode.MULTIPLE);
MultipleSelectionModel
には、selectedItems
プロパティおよびselectedIndices
プロパティがあり、どちらも複数選択を検出するためにモニターできる監視可能リストです。
リスト・ビューへのデータの移入
例12-1に、リスト・ビューへのデータ移入の簡単な方法を示します。リストを拡張するには、ListCell
クラス固有の拡張であるCheckBoxListCell
、ChoiceBoxListCell
、ComboBoxListCell
、TextFieldListCell
などを使用して、各種データを追加できます。これらのクラスによって、基本のリスト・セルに機能が追加されます。このようなクラスのセル・ファクトリを実装すると、開発者はリスト・ビューで直接データを変更できるようになります。
たとえば、リスト・セルの内容は、デフォルトでは編集できません。ただし、ComboBoxListCell
クラスではリスト・セル内部にコンボ・ボックスを描画できます。この変更によって、例12-3に示すように、ユーザーはコンボ・ボックスから名前を選択してリストをビルドできるようになります。
例12-3 リスト・ビューへのComboBoxListCell項目の追加
import javafx.application.Application;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.scene.Scene;
import javafx.scene.control.*;
import javafx.scene.control.cell.ComboBoxListCell;
import javafx.scene.layout.StackPane;
import javafx.stage.Stage;
public class ListViewSample extends Application {
public static final ObservableList names =
FXCollections.observableArrayList();
public static final ObservableList data =
FXCollections.observableArrayList();
public static void main(String[] args) {
launch(args);
}
@Override
public void start(Stage primaryStage) {
primaryStage.setTitle("List View Sample");
final ListView listView = new ListView(data);
listView.setPrefSize(200, 250);
listView.setEditable(true);
names.addAll(
"Adam", "Alex", "Alfred", "Albert",
"Brenda", "Connie", "Derek", "Donny",
"Lynne", "Myrtle", "Rose", "Rudolph",
"Tony", "Trudy", "Williams", "Zach"
);
for (int i = 0; i < 18; i++) {
data.add("anonym");
}
listView.setItems(data);
listView.setCellFactory(ComboBoxListCell.forListView(names));
StackPane root = new StackPane();
root.getChildren().add(listView);
primaryStage.setScene(new Scene(root, 200, 250));
primaryStage.show();
}
}
例に示す太字の行では、setCellFactory
メソッドをコールしてリスト・セルの実装を再定義します。この例をコンパイルして実行すると、図12-4に示すアプリケーション・ウィンドウが作成されます。
セル・ファクトリ・メカニズムはリスト・セルの代替の実装を適用可能にするだけでなく、セルの外観も完全にカスタマイズ可能にします。
リスト・ビューの内容のカスタマイズ
次のアプリケーションを調べ、セル・ファクトリを使用してリスト項目を生成する方法について学習します。例12-4に示すアプリケーションでは、色パターンのリストを作成しています。
例12-4 セル・ファクトリの作成
import javafx.application.Application; import javafx.collections.FXCollections; import javafx.collections.ObservableList; import javafx.scene.Scene; import javafx.scene.control.ListCell; import javafx.scene.control.ListView; import javafx.scene.layout.Priority; import javafx.scene.layout.VBox; import javafx.scene.paint.Color; import javafx.scene.shape.Rectangle; import javafx.stage.Stage; public class ListViewSample extends Application { ListView<String> list = new ListView<>(); ObservableList<String> data = FXCollections.observableArrayList( "chocolate", "salmon", "gold", "coral", "darkorchid", "darkgoldenrod", "lightsalmon", "black", "rosybrown", "blue", "blueviolet", "brown"); @Override public void start(Stage stage) { VBox box = new VBox(); Scene scene = new Scene(box, 200, 200); stage.setScene(scene); stage.setTitle("ListViewSample"); box.getChildren().addAll(list); VBox.setVgrow(list, Priority.ALWAYS); list.setItems(data); list.setCellFactory((ListView<String> l) -> new ColorRectCell()); stage.show(); } static class ColorRectCell extends ListCell<String> { @Override public void updateItem(String item, boolean empty) { super.updateItem(item, empty); Rectangle rect = new Rectangle(100, 20); if (item != null) { rect.setFill(Color.web(item)); setGraphic(rect); } } } public static void main(String[] args) { launch(args); } }
セル・ファクトリはListCell
オブジェクトを作成します。すべてのセルが単一データ項目と関連付けられており、リスト・ビューの単一の「行」を表示します。setGraphic
メソッドによってセルが表す内容には、その他のコントロール、テキスト、図形、またはイメージが含まれます。このアプリケーションでは、リスト・セルは四角形を表します。
アプリケーションのコンパイルと実行によって、図12-5に示すウィンドウが作成されます。
リストをスクロールして、いずれかの項目を選択および選択を解除できます。また、このアプリケーションを拡張して、次の項に示すように、色パターンでテキスト・ラベルを塗りつぶすことができます。
リスト項目選択の処理
例12-5に示すようにアプリケーションを変更し、特定のリスト項目を選択したときにイベントが処理されるようにします。
例12-5 リスト項目のイベントの処理
import javafx.application.Application; import javafx.beans.value.ObservableValue; import javafx.collections.FXCollections; import javafx.collections.ObservableList; import javafx.scene.Scene; import javafx.scene.control.Label; import javafx.scene.control.ListCell; import javafx.scene.control.ListView; import javafx.scene.layout.Priority; import javafx.scene.layout.VBox; import javafx.scene.paint.Color; import javafx.scene.shape.Rectangle; import javafx.scene.text.Font; import javafx.stage.Stage; public class ListViewSample extends Application { ListView<String> list = new ListView<>(); ObservableList<String> data = FXCollections.observableArrayList( "chocolate", "salmon", "gold", "coral", "darkorchid", "darkgoldenrod", "lightsalmon", "black", "rosybrown", "blue", "blueviolet", "brown"); final Label label = new Label(); @Override public void start(Stage stage) { VBox box = new VBox(); Scene scene = new Scene(box, 200, 200); stage.setScene(scene); stage.setTitle("ListViewSample"); box.getChildren().addAll(list, label); VBox.setVgrow(list, Priority.ALWAYS); label.setLayoutX(10); label.setLayoutY(115); label.setFont(Font.font("Verdana", 20)); list.setItems(data); list.setCellFactory((ListView<String> l) -> new ColorRectCell()); list.getSelectionModel().selectedItemProperty().addListener( (ObservableValue<? extends String> ov, String old_val, String new_val) -> { label.setText(new_val); label.setTextFill(Color.web(new_val)); }); stage.show(); } static class ColorRectCell extends ListCell<String> { @Override public void updateItem(String item, boolean empty) { super.updateItem(item, empty); Rectangle rect = new Rectangle(100, 20); if (item != null) { rect.setFill(Color.web(item)); setGraphic(rect); } else { setGraphic(null); } } } public static void main(String[] args) { launch(args); } }
selectedItemProperty
にコールされたaddListener
メソッドによって、新しいリスナーが作成され、選択した項目の変更が処理されます。たとえば、ダーク・オーキッドの項目を選択すると、ラベルは「darkorchid」キャプションを受け取り、対応する色で塗りつぶされます。変更したアプリケーションの出力を図12-6に示します。
関連ドキュメント