package org.jabref.gui.util; import javafx.event.EventHandler; import javafx.scene.Node; import javafx.scene.control.ListCell; import javafx.scene.control.ListView; import javafx.scene.control.Tooltip; import javafx.scene.input.MouseEvent; import javafx.scene.paint.Paint; import javafx.scene.text.Text; import javafx.util.Callback; import org.jabref.model.strings.StringUtil; import de.jensd.fx.glyphs.GlyphIcons; import de.jensd.fx.glyphs.materialdesignicons.utils.MaterialDesignIconFactory; /** * Constructs a {@link ListCell} based on the view model of the row and a bunch of specified converter methods. * * @param <T> cell value */ public class ViewModelListCellFactory<T> implements Callback<ListView<T>, ListCell<T>> { private Callback<T, String> toText; private Callback<T, Node> toGraphic; private Callback<T, String> toTooltip; private Callback<T, EventHandler<? super MouseEvent>> toOnMouseClickedEvent; private Callback<T, String> toStyleClass; public ViewModelListCellFactory<T> withText(Callback<T, String> toText) { this.toText = toText; return this; } public ViewModelListCellFactory<T> withGraphic(Callback<T, Node> toGraphic) { this.toGraphic = toGraphic; return this; } public ViewModelListCellFactory<T> withIcon(Callback<T, GlyphIcons> toIcon) { this.toGraphic = viewModel -> MaterialDesignIconFactory.get().createIcon(toIcon.call(viewModel)); return this; } public ViewModelListCellFactory<T> withIcon(Callback<T, GlyphIcons> toIcon, Callback<T, Paint> toColor) { this.toGraphic = viewModel -> { Text graphic = MaterialDesignIconFactory.get().createIcon(toIcon.call(viewModel)); graphic.setFill(toColor.call(viewModel)); return graphic; }; return this; } public ViewModelListCellFactory<T> withTooltip(Callback<T, String> toTooltip) { this.toTooltip = toTooltip; return this; } public ViewModelListCellFactory<T> withStyleClass(Callback<T, String> toStyleClass) { this.toStyleClass = toStyleClass; return this; } public ViewModelListCellFactory<T> withOnMouseClickedEvent( Callback<T, EventHandler<? super MouseEvent>> toOnMouseClickedEvent) { this.toOnMouseClickedEvent = toOnMouseClickedEvent; return this; } @Override public ListCell<T> call(ListView<T> param) { return new ListCell<T>() { @Override protected void updateItem(T item, boolean empty) { super.updateItem(item, empty); T viewModel = getItem(); if (empty || viewModel == null) { setText(null); setGraphic(null); setOnMouseClicked(null); setTooltip(null); } else { if (toText != null) { setText(toText.call(viewModel)); } if (toGraphic != null) { setGraphic(toGraphic.call(viewModel)); } if (toOnMouseClickedEvent != null) { setOnMouseClicked(toOnMouseClickedEvent.call(viewModel)); } if (toStyleClass != null) { getStyleClass().setAll(toStyleClass.call(viewModel)); } if (toTooltip != null) { String tooltipText = toTooltip.call(viewModel); if (StringUtil.isNotBlank(tooltipText)) { setTooltip(new Tooltip(tooltipText)); } } } getListView().refresh(); } }; } }