2017-01-23 14 views
0

Я такая ситуацию: ExampleКак выделить столбец, который я выбираю через флажок в JavaFX

В тот момент, когда я выбираю флажок (один или несколько), я хочу, чтобы выделить соответствующие колонны.

Я пытаюсь сделать это глупо и грубо solution, но он работает только в заголовке столбцов.

+0

[это не работает, когда я отключил флажок] (https://i.stack.imgur.com/etE3A.png) –

+0

Являются ли они взаимоисключающие флажки? –

+0

Нет, я могу выбрать любой флажок. Для каждого выбранного флажка я хочу отобразить соответствующий столбец, выделенный и для каждого снятого флажка, я не хочу отображать соответствующий столбец. –

ответ

0

Если вы хотите выделить весь столбец, вам нужно использовать фабрику ячеек в столбце и выделить ячейки. Это похоже на природу: JavaFX - Detect & highlight TableColumn being dragged onto, но вам нужно выделить несколько столбцов. Для этого используйте ObservableSet<TableColumn<?,?>, чтобы отслеживать, какие столбцы должны быть выделены, и добавлять/удалять столбцы из него.

Ниже приведен пример, адаптированный из примера связаны выше:

import java.util.Arrays; 
import java.util.List; 
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.collections.FXCollections; 
import javafx.collections.ObservableSet; 
import javafx.collections.SetChangeListener.Change; 
import javafx.css.PseudoClass; 
import javafx.scene.Scene; 
import javafx.scene.control.CheckBox; 
import javafx.scene.control.TableCell; 
import javafx.scene.control.TableColumn; 
import javafx.scene.control.TableView; 
import javafx.scene.layout.BorderPane; 
import javafx.scene.layout.VBox; 
import javafx.stage.Stage; 
import javafx.util.Callback; 

public class TableColumnHighlightByCheckBox extends Application { 

    @Override 
    public void start(Stage primaryStage) { 
     TableView<Person> table = new TableView<>(); 
     table.getColumns().add(column("First Name", Person::firstNameProperty)); 
     table.getColumns().add(column("Last Name", Person::lastNameProperty)); 
     table.getColumns().add(column("Email", Person::emailProperty)); 

     ObservableSet<TableColumn<?,?>> highlightColumns = FXCollections.observableSet(); 

     table.getItems().addAll(createData()); 

     VBox checkBoxes = new VBox(5); 
     checkBoxes.getStyleClass().add("controls"); 
     table.getColumns().forEach(col -> 
      checkBoxes.getChildren().add(createHighlightColumnCheckBox(col, highlightColumns))); 

     table.getColumns().forEach(col -> highlightColumnWhenNeeded(col, highlightColumns)); 

     BorderPane root = new BorderPane(table); 
     root.setTop(checkBoxes); 

     Scene scene = new Scene(root, 800, 600); 
     scene.getStylesheets().add("style.css"); 
     primaryStage.setScene(scene); 
     primaryStage.show(); 
    } 

    private <S,T> CheckBox createHighlightColumnCheckBox(TableColumn<S,T> column, ObservableSet<TableColumn<?,?>> highlightColumns) { 


     CheckBox checkBox = new CheckBox(); 
     checkBox.textProperty().bind(column.textProperty()); 
     checkBox.selectedProperty().addListener((obs, wasSelected, isNowSelected) -> { 
      if (isNowSelected) { 
       highlightColumns.add(column); 
      } else { 
       highlightColumns.remove(column); 
      } 
     }); 

     return checkBox ; 
    } 

    private <S,T> void highlightColumnWhenNeeded(TableColumn<S,T> column, ObservableSet<TableColumn<?,?>> highlightColumns) { 

     Callback<TableColumn<S,T>, TableCell<S,T>> currentCellFactory = column.getCellFactory() ; 

     PseudoClass highlight = PseudoClass.getPseudoClass("highlight"); 

     column.setCellFactory(tc -> { 
      TableCell<S,T> cell = currentCellFactory.call(tc); 
      highlightColumns.addListener((Change<? extends TableColumn<?,?>> c) -> 
        cell.pseudoClassStateChanged(highlight, 
         highlightColumns.contains(column))); 

      cell.pseudoClassStateChanged(highlight, highlightColumns.contains(column)); 

      return cell ; 
     }); 
    } 

    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())); 
     return col ; 
    } 

    private List<Person> createData() { 
     return Arrays.asList(
       new Person("Jacob", "Smith", "[email protected]"), 
       new Person("Isabella", "Johnson", "[email protected]"), 
       new Person("Ethan", "Williams", "[email protected]"), 
       new Person("Emma", "Jones", "[email protected]"), 
       new Person("Michael", "Brown", "[email protected]")  
     ); 
    } 

    public 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 String getFirstName() { 
      return this.firstNameProperty().get(); 
     } 



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



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



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



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



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



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



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



    } 

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

И в таблице стилей:

.table-cell:highlight { 
    -fx-background-color: -fx-background ; 
    -fx-background: yellow ; 
    -fx-border-color: -fx-table-cell-border-color -fx-table-cell-border-color transparent transparent ; 
} 
.controls { 
    -fx-padding: 10 ; 
} 

Я просто сделал всю клетку ярко-желтого цвета, если столбец она находится в подсвечивается , но вы можете изменить таблицу стилей, чтобы использовать любой стиль, который вам нравится для выделения.

enter image description here

+0

Спасибо, что ваше решение помогло мне и [это мое простое решение] (http://pastebin.com/2R8Sz0p5). Я начинающий Java, вы можете объяснить мне свой метод highlightColumnWhenNeeded? Я не очень хорошо понимаю шаблоны и дженерики типа –

+0

'TableColumn ' just mean "TableColumn неизвестного типа". Поскольку вы просто храните их в наборе, вам все равно, какой тип они есть, поэтому хорошо держать этот генерал. –

+0

Хорошо, спасибо! Однако есть проблема: после выбора флажка, если я просматриваю представление таблицы, некоторая строка не будет подсвечена. Он подсвечивается всей ячейкой только я выбираю другой флажок ... [посмотреть это видео, чтобы понять проблему] (https://www.youtube.com/watch?v=t4DnnOFIUtc). Это проблема компоновки в fxml или java-коде? –