【问题标题】:JavaFX TableView edit not editingJavaFX TableView 编辑不编辑
【发布时间】:2017-06-11 14:13:39
【问题描述】:

在 JavaFX 8 中,我试图在向表中添加新行后编辑一个单元格,以优化用户体验。

    hourTableView.getSelectionModel().select(newHour);
    int row = hourTableView.getSelectionModel().getSelectedIndex();
    hourTableView.edit(row, hourTableAmountTableColumn);

选择了正确的行,但单元格没有进入编辑模式。好吧,我看到它发生得很偶然,但很难重现。我做错了什么?

【问题讨论】:

  • 列是否可编辑?表格可以编辑吗?专栏是否有支持编辑并正确实现startEditCellFactoryMCVE 将非常有帮助。
  • 是的,单元格可以通过鼠标单击来编辑(该列使用 PropertyValueFactory)。整个应用程序功能齐全,这是用户体验改进之一,您在树中单击,然后应该放置焦点 + 编辑,因此您可以立即开始输入值。我会尝试看看那个 MCVE(我当然希望得到一个快速提示)。

标签: java javafx tableview


【解决方案1】:

Insert row in JavaFX TableView and start editing is not working correctly找到解决方案

您需要先致电hourTableView.layout(),然后再致电hourTableView.edit()。 当新行不可见时会变得更加复杂,我发现 hourTableView.scrollTo() 如果在 before hourTableView.layout() 之前调用它会有所帮助。

【讨论】:

    【解决方案2】:

    如果您想在刚插入的行上开始编辑,表格的行为会很奇怪。我可以毫无问题地开始编辑任何行。但是新添加的行并没有像预期的那样工作。我用一个线程延迟了编辑调用,然后它工作了...... 请看以下示例代码:

    import javafx.application.Application;
    import javafx.application.Platform;
    import javafx.beans.property.SimpleStringProperty;
    import javafx.beans.property.StringProperty;
    import javafx.collections.FXCollections;
    import javafx.collections.ObservableList;
    import javafx.scene.Scene;
    import javafx.scene.control.Button;
    import javafx.scene.control.TableColumn;
    import javafx.scene.control.TableView;
    import javafx.scene.control.cell.PropertyValueFactory;
    import javafx.scene.control.cell.TextFieldTableCell;
    import javafx.scene.layout.VBox;
    import javafx.stage.Stage;
    
    public class jfxtest extends Application {
    
        private ObservableList<Person> data;
        private TableView<Person> tableView;
        private TableColumn<Person, String> firstNameCol;
    
        public static void main(String[] args) {
            launch(args);
        }
    
        @Override
        public void start(Stage primaryStage) throws Exception {
            Button addButton = new Button("add new row");
            addButton.setOnMouseClicked(event -> addRow());
            VBox vbox = new VBox(addButton, createContent());
            primaryStage.setScene(new Scene(vbox));
            primaryStage.show();
        }
    
        private void addRow() {
            data.add(new Person("peter", "parker", "spiderman@aol.com"));
            new Thread(() -> {
                try {
                    Thread.sleep(50);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                Platform.runLater(() -> {
                    int row = data.size() - 1;
                    tableView.getSelectionModel().select(row);
                    tableView.getSelectionModel().focus(row);
                    tableView.edit(row, firstNameCol);
                });
            }).start();
        }
    
        private TableView createContent() {
            data = FXCollections.observableArrayList(
                new Person("Jacob", "Smith", "jacob.smith@example.com"),
                new Person("Isabella", "Johnson", "isabella.johnson@example.com"),
                new Person("Ethan", "Williams", "ethan.williams@example.com"),
                new Person("Emma", "Jones", "emma.jones@example.com"),
                new Person("Michael", "Brown", "michael.brown@example.com")
            );
            firstNameCol = new TableColumn<>("First");
            firstNameCol.setCellValueFactory(new PropertyValueFactory<>("firstName"));
            firstNameCol.setEditable(true);
            firstNameCol.setCellFactory(TextFieldTableCell.forTableColumn());
            firstNameCol.setOnEditCommit(
                t -> t.getTableView().getItems().get(
                    t.getTablePosition().getRow()).firstNameProperty().setValue(t.getNewValue())
            );
    
            TableColumn<Person, String> lastNameCol = new TableColumn<>("Last");
            lastNameCol.setCellValueFactory(new PropertyValueFactory<>("lastName"));
    
            TableColumn<Person, String> emailCol = new TableColumn<>("Email");
            emailCol.setCellValueFactory(new PropertyValueFactory<>("email"));
    
            tableView = new TableView<>();
            tableView.setEditable(true);
            tableView.setItems(data);
            tableView.getColumns().addAll(firstNameCol, lastNameCol, emailCol);
            return tableView;
        }
    
    
        public class Person {
            private StringProperty firstName;
            private StringProperty lastName;
            private StringProperty email;
    
            Person(String fName, String lName, String email) {
                this.firstName = new SimpleStringProperty(fName);
                this.lastName = new SimpleStringProperty(lName);
                this.email = new SimpleStringProperty(email);
            }
    
            public StringProperty firstNameProperty() {
                return firstName;
            }
    
            public StringProperty lastNameProperty() {
                return lastName;
            }
    
            public StringProperty emailProperty() {
                return email;
            }
        }
    }
    

    【讨论】:

    • 经过更多研究后发现,TableView 上的“刷新”调用导致了问题。向 TableView 底层的可观察列表添加新条目当然已经触发了 UI 的刷新,因此不需要显式刷新调用。删除后,单元格将被编辑,即使它是刚刚添加的。除非该行是视图中的第一行,否则焦点存在于单元格上,但未放置光标。上面的建议并没有解决这个问题。搜索继续。
    • 使用java.util.Timer 比使用Thread 更好;不是我喜欢它,而是更好的做法。
    猜你喜欢
    • 2014-10-19
    • 2012-10-05
    • 2014-10-14
    • 2014-02-22
    • 1970-01-01
    • 1970-01-01
    • 2013-09-14
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多