2017-10-24 19 views
0

テーブルヘッダーをダブルクリックして列ヘッダーの値を変更できるJavaFXでTableViewを作成しようとしています。 テキストボックスが表示され、新しい値を入力した後、その値を列ヘッダーに割り当てる必要があります。TableView JavaFXの値の列ヘッダーを変更

Example of output below

+0

は、次のアプローチを試してみてください。代わりに、列にテキストを設定するので、ラベルにグラフィックを設定します。マウスのリスナーをダブルクリックするとグラフィックをテキストフィールドに変更するラベルを登録し、ユーザーがEnterキーを押したときやテキストフィールドがフォーカスを失ったときにラベルに戻すテキストフィールドをリスナーに登録できます。 (ここでの欠点は、テーブルの組み込みメニューボタンの使用が禁止されていることです)これを実装する際に問題がある場合は、特定の質問を投稿してください。 –

答えて

1

A・ジェームズ・コメントで概説さよりもわずかに異なるアプローチ:

  • ソートに干渉するダブルクリック(上の表
  • とマウスハンドラを登録...それはです別の問題)、tableColumnを表すTableColumnHeaderが見つかった場合は
  • TextFieldを作成してワイヤリングし、列のグラフィックとして設定します(James提案のとおり)

TableColumnHeaderのパッケージはバージョンに依存することに注意してください.fx8の場合、com.xx.skinにある内部APIと見なされます.fx9の場合はjavafx.xx.skinで公開されます。

例:

public class TableHeaderWithInput extends Application { 
    TableView<Locale> table; 

    protected void installHeaderHandler(Observable s) { 
     table.addEventFilter(MouseEvent.MOUSE_PRESSED, e -> { 
      if (e.isPrimaryButtonDown() && e.getClickCount() > 1) { 
       EventTarget target = e.getTarget(); 
       TableColumnBase<?, ?> column = null; 
       while (target instanceof Node) { 
        target = ((Node) target).getParent(); 
        // beware: package of TableColumnHeader is version specific 
        if (target instanceof TableColumnHeader) { 
         column = ((TableColumnHeader) target).getTableColumn(); 
         if (column != null) break; 
        } 
       } 
       if (column != null) { 
        TableColumnBase<?,?> tableColumn = column; 
        TextField textField = new TextField(column.getText()); 
        textField.setMaxWidth(column.getWidth()); 
        textField.setOnAction(a -> { 
         tableColumn.setText(textField.getText()); 
         tableColumn.setGraphic(null); 
        }); 
        textField.focusedProperty().addListener((src, ov, nv) -> { 
         if (!nv) tableColumn.setGraphic(null); 
        }); 
        column.setGraphic(textField); 
        textField.requestFocus(); 
       } 
       e.consume(); 
      } 
     }); 
    } 

    private Parent getContent() { 
     table = new TableView<>(FXCollections.observableArrayList(
       Locale.getAvailableLocales())); 
     table.setTableMenuButtonVisible(true); 
     // quick hack: don't let sorting interfere ... 
     table.setSortPolicy(e -> {return false;}); 
     TableColumn<Locale, String> countryCode = new TableColumn<>("CountryCode"); 
     countryCode.setCellValueFactory(new PropertyValueFactory<>("country")); 
     TableColumn<Locale, String> language = new TableColumn<>("Language"); 
     language.setCellValueFactory(new PropertyValueFactory<>("language")); 
     table.getColumns().addAll(countryCode, language); 
     table.skinProperty().addListener(this::installHeaderHandler); 
     BorderPane pane = new BorderPane(table); 
     return pane; 
    } 

    @Override 
    public void start(Stage primaryStage) throws Exception { 
     primaryStage.setScene(new Scene(getContent(), 800, 400)); 
     primaryStage.setTitle(FXUtils.version()); 
     primaryStage.show(); 
    } 

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

    @SuppressWarnings("unused") 
    private static final Logger LOG = Logger 
      .getLogger(TableHeaderWithInput.class.getName()); 
} 
関連する問題