Как добавить пользовательский компонент в столбец JavaFX TableView? - PullRequest
2 голосов
/ 20 сентября 2019

Я хочу добавить пользовательский компонент (SwitchButton) в столбец в JavaFX TableView.Я посмотрел на некоторые примеры с кнопками, и я просто не понимаю, как это сделать.Ниже приведен код моей тренировочной таблицы вместе с кодом SwitchButton, который я хочу разместить в столбце «Активный / Неактивный».Значение для SwitchButton (Active или Inactive) будет считано из базы данных, и когда пользователь переключит его, я хочу вызвать действие, чтобы записать его в базу данных.

TableWithSwitchButtonView.fxml:

<?xml version="1.0" encoding="UTF-8"?>

<?import javafx.scene.control.TableColumn?>
<?import javafx.scene.control.TableView?>
<?import javafx.scene.layout.AnchorPane?>

<AnchorPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="248.0" prefWidth="271.0" xmlns="http://javafx.com/javafx/8.0.171" xmlns:fx="http://javafx.com/fxml/1" fx:controller="tabletest.TableWithSwitchButtonController">
   <children>
      <TableView fx:id="configTableView" prefHeight="240.0" prefWidth="271.0" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="0.0">
         <columns>
            <TableColumn fx:id="configColumn" prefWidth="138.0" text="Configuration Name" />
            <TableColumn fx:id="activeColumn" prefWidth="131.0" text="Active/Inactive" />
         </columns>
      </TableView>
   </children>
</AnchorPane>

TableWithSwitchButtonController.java:

package tabletest;

import java.net.URL;
import java.util.ResourceBundle;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.fxml.FXML;
import javafx.fxml.Initializable;
import javafx.scene.control.TableColumn;
import javafx.scene.control.TableView;
import javafx.scene.control.cell.PropertyValueFactory;

public class TableWithSwitchButtonController implements Initializable
{
    @FXML
    private TableColumn<Config, String> configColumn;
    @FXML
    private TableColumn<Config, String> activeColumn;
    @FXML
    private TableView<Config> configTableView;

    @Override
    public void initialize(URL url, ResourceBundle rb)
    {
        // Add Cell Value Factory
        configColumn.setCellValueFactory(new PropertyValueFactory<Config,
                String>("configName"));
        activeColumn.setCellValueFactory(new PropertyValueFactory<Config,
                String>("configActive"));

        // populate the Column lists (this will be coming from the database)
        ObservableList<Config> configList =
                FXCollections.<Config>observableArrayList(
                        new Config("Config 1", "active"),
                        new Config("Config 2", "active"),
                        new Config("Config 3", "inactive")
                        );

        configTableView.getItems().addAll(configList);
    }  

    public class Config
    {
        private String configName;
        private String configActive;

        public Config(String name, String active)
        {
            configName = name;
            configActive = active;
        }

        public String getConfigName()
        {
            return configName;
        }

        public void setConfigName(String name)
        {
            configName = name;
        }

        public String getConfigActive()
        {
            return configActive;
        }

        public void setConfigActive(String active)
        {
           configActive = active;
        }
    };
}

TableTest.java:

package tabletest;

import java.io.IOException;
import javafx.application.Application;
import javafx.fxml.FXMLLoader;
import javafx.scene.Parent;
import javafx.scene.Scene;
import javafx.stage.Stage;

public class TableTest extends Application
{
    @Override
    public void start(Stage primaryStage)
    {
        try
        {
            FXMLLoader loader = new FXMLLoader(getClass().getResource("TableWithSwitchButtonView.fxml"));
            Scene scene = new Scene((Parent) loader.load());
            primaryStage.setScene(scene);
            primaryStage.setTitle("Table Test");
            primaryStage.show();
        }
        catch (IOException ignored)
        {
        }
    }

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

SwitchButton.java:

package tabletest;

import javafx.beans.property.SimpleBooleanProperty;
import javafx.beans.value.ChangeListener;
import javafx.beans.value.ObservableValue;
import javafx.event.ActionEvent;
import javafx.event.EventHandler;
import javafx.scene.control.Button;
import javafx.scene.control.ContentDisplay;
import javafx.scene.control.Label;

public class SwitchButton extends Label
{
    private SimpleBooleanProperty switchedOn = new SimpleBooleanProperty(true);

    public SwitchButton()
    {
        Button switchBtn = new Button();
        switchBtn.setPrefWidth(40);
        switchBtn.setOnAction(new EventHandler<ActionEvent>()
        {
            @Override
            public void handle(ActionEvent t)
            {
                switchedOn.set(!switchedOn.get());
            }
        });

        setGraphic(switchBtn);

        switchedOn.addListener(new ChangeListener<Boolean>()
        {
            @Override
            public void changed(ObservableValue<? extends Boolean> ov,
                Boolean t, Boolean t1)
            {
                if (t1)
                {
                    setText("ACTIVE");
                    setStyle("-fx-background-color: green;-fx-text-fill:white;");
                    setContentDisplay(ContentDisplay.RIGHT);
                }
                else
                {
                    setText("INACTIVE");
                    setStyle("-fx-background-color: grey;-fx-text-fill:black;");
                    setContentDisplay(ContentDisplay.LEFT);
                }
            }
        });

        switchedOn.set(false);
    }

    public SimpleBooleanProperty switchOnProperty() { return switchedOn; }
}
...