如何更改TableView的选择行为?

时间:2016-01-11 12:58:03

标签: javafx tableview selection

我已将多种选择模式设置为我的TableView,我希望使用Lclick选择多行,而不是Ctrl + Lclick。有没有一种简单的方法可以做到这一点。

我尝试使用null实现table.setOnMouseClicked(),但它不会阻止选择目标行,并且可以取消选择以前选择的行setOnMousePressed()setOnMouseReleased()

我真的不想重新实施TableView.TableViewSelectionModel。点击和调用之间应该有一个层TableView.TableViewSelectionModel.clearAndSelect()

UPD 我刚发现few questions有类似问题,但不完全相同。那些家伙想要拖动并选择多个,当我想逐个选择,但没有键盘。

1 个答案:

答案 0 :(得分:3)

通常,更改JavaFX UI控件的行为很困难(或者不可能),通常我建议只接受默认行为(即使它们不是您的用户可能真正想要的)。

在这种情况下,我认为您可以通过向表行添加事件过滤器来实现此功能,实现所需的选择行为并使用事件(以防止调用默认行为)。

以下是一个例子:

import java.util.function.Function;

import javafx.application.Application;
import javafx.beans.property.SimpleStringProperty;
import javafx.beans.property.StringProperty;
import javafx.beans.value.ObservableValue;
import javafx.scene.Scene;
import javafx.scene.control.SelectionMode;
import javafx.scene.control.TableColumn;
import javafx.scene.control.TableRow;
import javafx.scene.control.TableView;
import javafx.scene.input.MouseEvent;
import javafx.scene.layout.BorderPane;
import javafx.stage.Stage;

public class MultipleSelectTable extends Application {

    @Override
    public void start(Stage primaryStage) {
        TableView<Person> table = new TableView<>();

        table.getSelectionModel().setSelectionMode(SelectionMode.MULTIPLE);

        table.setRowFactory(tv -> {
            TableRow<Person> row = new TableRow<>();
            row.addEventFilter(MouseEvent.MOUSE_PRESSED, e-> {
                if (! row.isEmpty() && e.getClickCount() == 1) {
                    Person person = row.getItem() ;
                    if (table.getSelectionModel().getSelectedItems().contains(person)) {
                        int index = row.getIndex() ;
                        table.getSelectionModel().clearSelection(index);
                    } else {
                        table.getSelectionModel().select(person);
                    }
                    e.consume();
                }
            });
            return row ;
        });

        table.getColumns().add(column("First Name", Person::firstNameProperty));
        table.getColumns().add(column("Last Name", Person::lastNameProperty));
        table.getColumns().add(column("Email", Person::emailProperty));

        table.getItems().addAll(
                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")        
        );

        BorderPane root = new BorderPane(table);
        Scene scene = new Scene(root, 600, 600);
        primaryStage.setScene(scene);
        primaryStage.show();
    }

    private static <S,T> TableColumn<S,T> column(String text, Function<S,ObservableValue<T>> property) {
        TableColumn<S,T> col = new TableColumn<>(text);
        col.setCellValueFactory(cellData -> property.apply(cellData.getValue()));
        col.setPrefWidth(200);
        return col ;
    }

    private static class Person {
        private final StringProperty firstName = new SimpleStringProperty();
        private final StringProperty lastName = new SimpleStringProperty();
        private final StringProperty email = new SimpleStringProperty();

        public Person(String firstName, String lastName, String email) {
            setFirstName(firstName);
            setLastName(lastName);
            setEmail(email);
        }

        public final StringProperty firstNameProperty() {
            return this.firstName;
        }


        public final java.lang.String getFirstName() {
            return this.firstNameProperty().get();
        }


        public final void setFirstName(final java.lang.String firstName) {
            this.firstNameProperty().set(firstName);
        }


        public final StringProperty lastNameProperty() {
            return this.lastName;
        }


        public final java.lang.String getLastName() {
            return this.lastNameProperty().get();
        }


        public final void setLastName(final java.lang.String lastName) {
            this.lastNameProperty().set(lastName);
        }


        public final StringProperty emailProperty() {
            return this.email;
        }


        public final java.lang.String getEmail() {
            return this.emailProperty().get();
        }


        public final void setEmail(final java.lang.String email) {
            this.emailProperty().set(email);
        }



    }

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