JavaFX GUI - Why does the Delete Button Function not work with the TableView?
NickName:BecauseTurtles Ask DateTime:2016-12-01T09:44:56

JavaFX GUI - Why does the Delete Button Function not work with the TableView?

Hello this is my first question as a newcomer to both Java and GUI design. I have come across an odd situation that I feel I am just looking over. I have TableView with some information, which can also be added with the Add Button. The Delete Button was working prior to me adding a FilterList constructor, so that I may filter search results by ID. Once I added the function, the Delete Button stopped working. I personally think that the deleteButtonClicked class isn't properly detecting the table anymore, because of the change by adding the Filter functionality. But as much as I try to keep both, one or the other usually stop working. I am currently trying to make it work without a Delete Button class, maybe by just making the product null.

The TableView functions are at the top of the code, while the delete button and functions are towards the bottom.

package application;

import javafx.application.Application;
import static javafx.application.Application.launch;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.collections.transformation.FilteredList;
import javafx.event.ActionEvent;
import javafx.event.EventHandler;
import javafx.geometry.Insets;
import javafx.geometry.Pos;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.control.Label;
import javafx.scene.control.TableColumn;
import javafx.scene.control.TableColumn.CellEditEvent;
import javafx.scene.control.TableView;
import javafx.scene.control.TextField;
import javafx.scene.layout.BorderPane;
import javafx.scene.layout.VBox;
import javafx.scene.text.Font;
import javafx.stage.Stage;
import javafx.scene.control.cell.PropertyValueFactory;
import javafx.scene.control.cell.TextFieldTableCell;
import javafx.scene.layout.HBox;
import javafx.scene.text.FontWeight;
import javafx.scene.text.Text;

public class MainApp extends Application {



    TableView<Product> table = new TableView<>();


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

    @Override
    public void start(Stage primaryStage) throws Exception {
        BorderPane root = new BorderPane();

        BorderPane leftPane = new BorderPane();

        FilteredList<Product> filterList = new FilteredList<>(productData);

        table.setEditable(true);
        //table.setItems(productData); // DELETE BUTTON WORKS WHEN THIS ONE IS ONLY SET
        table.setItems(filterList); // DELETE BUTTON DOESN'T WORK WHEN
                                    // THIS IS SET BUT, IS NEEDED TO FILTER SEARCH FUNCTIONS

        TableColumn<Product, String> idNumberCol = new TableColumn<>("ID Number");
        idNumberCol.setMinWidth(50);
        idNumberCol.setCellValueFactory(new PropertyValueFactory<>("idNumber"));

        idNumberCol.setCellFactory(TextFieldTableCell.<Product>forTableColumn());
        idNumberCol.setOnEditCommit(
        (CellEditEvent<Product, String> t) -> {
        ((Product) t.getTableView().getItems().get(
            t.getTablePosition().getRow())
            ).setIdNumber(t.getNewValue());
});

        TableColumn<Product, String> desCol = new TableColumn<>("Description");
        desCol.setMinWidth(150);
        desCol.setCellValueFactory(new PropertyValueFactory<>("description")); 

        desCol.setCellFactory(TextFieldTableCell.<Product>forTableColumn());
        desCol.setOnEditCommit(
        (CellEditEvent<Product, String> t) -> {
        ((Product) t.getTableView().getItems().get(
            t.getTablePosition().getRow())
            ).setDescription(t.getNewValue());
});

        TableColumn<Product, String> expCol = new TableColumn<>("Expiration");
        expCol.setMinWidth(100);
        expCol.setCellValueFactory(new PropertyValueFactory<>("expiration"));

        expCol.setCellFactory(TextFieldTableCell.<Product>forTableColumn());
        expCol.setOnEditCommit(
        (CellEditEvent<Product, String> t) -> {
        ((Product) t.getTableView().getItems().get(
            t.getTablePosition().getRow())
            ).setExpiration(t.getNewValue());
});


        table.getColumns().addAll(idNumberCol, desCol, expCol);


        VBox leftVbox = new VBox(); 
        leftVbox.setPadding(new Insets(10, 20, 20, 20)); 
        leftVbox.setSpacing(10);
        leftVbox.getChildren().addAll(table);

        BorderPane topPane = new BorderPane();

        HBox topHbox = new HBox(); //Create HBox
        topHbox.setPadding(new Insets(20, 20, 10, 20)); // Set padding and spacing for the hbox
        topHbox.setSpacing(10); // The hbox will appropriately space out more

        Text txtSearch = new Text("Search: ");
        topHbox.getChildren().add(txtSearch);
        txtSearch.setFont(Font.font("Tahoma", FontWeight.NORMAL, 16));

        TextField txt = new TextField(""); // Create new TextField
        txt.setPrefWidth(250);
        txt.setPromptText("Search A Product ID"); // Sets up hint text inside the TextField
        topHbox.getChildren().add(txt); // Add the TextField to the second hbox

        HBox rightHbox = new HBox(); //Create HBox
        rightHbox.setPadding(new Insets(20, 20, 10, 20)); // Set padding and spacing for the hbox
        rightHbox.setSpacing(10); // The hbox will appropriately space out more

        Text txtDetails = new Text("Product Details");
        rightHbox.getChildren().add(txtDetails);
        txtDetails.setFont(Font.font("Tahoma", FontWeight.NORMAL, 20));

        txt.textProperty().addListener((obsVal, oldValue, newValue) -> {
        filterList.setPredicate(product -> product.getIdNumber().contains(newValue));
        });


        BorderPane rightPane = new BorderPane();

        VBox rightVbox = new VBox();
        rightVbox.setPadding(new Insets(20, 10, 10, 20));
        rightVbox.setSpacing(30);
        rightVbox.setAlignment(Pos.TOP_LEFT);

        Text txtId = new Text("ID: ");
        rightVbox.getChildren().add(txtId);
        txtId.setFont(Font.font("Tahoma", FontWeight.NORMAL, 16));

        Text txtDes = new Text("Description: ");
        rightVbox.getChildren().add(txtDes);
        txtDes.setFont(Font.font("Tahoma", FontWeight.NORMAL, 16)); 

        Text txtExp = new Text("Expiration: ");
        rightVbox.getChildren().add(txtExp);
        txtExp.setFont(Font.font("Tahoma", FontWeight.NORMAL, 16)); 

        Text txtStatus = new Text("Status: ");
        rightVbox.getChildren().add(txtStatus);
        txtStatus.setFont(Font.font("Tahoma", FontWeight.NORMAL, 16)); 

        Text txtEnter = new Text("Entered By: ");
        rightVbox.getChildren().add(txtEnter);
        txtEnter.setFont(Font.font("Tahoma", FontWeight.NORMAL, 16)); 

        //EMPTY PLACE HOLDER INFORMATION TO POPULATE THE DATA
        Label lblId;
        Label lblDes;
        Label lblExp;
        Label lblStatus;
        Label lblEnter;

        HBox bottomHbox2 = new HBox();
        bottomHbox2.setPadding(new Insets(20, 20, 20, 20));
        bottomHbox2.setSpacing(10);
        bottomHbox2.setAlignment(Pos.BOTTOM_RIGHT);


        Button btnNew = new Button("Add...");
        bottomHbox2.getChildren().add(btnNew);
        btnNew.setOnAction(new EventHandler<ActionEvent>() {
            @Override
            public void handle(ActionEvent event) {

            Stage secondStage = new Stage();

            BorderPane dialogPane = new BorderPane();

            VBox dialogVbox = new VBox();
            dialogVbox.setPadding(new Insets(20, 10, 20, 20));
            dialogVbox.setSpacing(20);     

            TextField addId = new TextField();
            addId.setPromptText("ID Number");
            addId.setMinWidth(50);
            //addId.setMaxWidth(idNumberCol.getPrefWidth());

            TextField addDes = new TextField();
            addDes.setPromptText("Description");
            addDes.setMinWidth(100);
            //addDes.setMaxWidth(desCol.getPrefWidth());

            TextField addExp = new TextField();
            addExp.setPromptText("Expiration Date");
            addExp.setMinWidth(50);
            //addExp.setMaxWidth(expCol.getPrefWidth());

            dialogVbox.getChildren().addAll(addId, addDes, addExp);

            VBox dialogVbox2 = new VBox();
            dialogVbox2.setPadding(new Insets(20, 20, 20, 10));
            dialogVbox2.setSpacing(20);     

            Text txtIdLabel = new Text("ID: ");
            dialogVbox2.getChildren().add(txtIdLabel);
            txtIdLabel.setFont(Font.font("Tahoma", FontWeight.NORMAL, 16));

            Text txtDesLabel = new Text("Description: ");
            dialogVbox2.getChildren().add(txtDesLabel);
            txtDesLabel.setFont(Font.font("Tahoma", FontWeight.NORMAL, 16)); 

            Text txtExpLabel = new Text("Expiration: ");
            dialogVbox2.getChildren().add(txtExpLabel);
            txtExpLabel.setFont(Font.font("Tahoma", FontWeight.NORMAL, 16)); 

            HBox addHbox = new HBox();
            addHbox.setPadding(new Insets(20, 10, 50, 20));
            addHbox.setSpacing(10);
            addHbox.setAlignment(Pos.BOTTOM_RIGHT);

            Button btnAdd = new Button("Add Product");
            addHbox.getChildren().add(btnAdd);

            btnAdd.setOnAction((ActionEvent e) -> {
            productData.add(new Product(
                    addId.getText(),
                    addDes.getText(),
                    addExp.getText()));
            addId.clear();
            addDes.clear();
            addExp.clear();
        });

                Button btnClose = new Button("Close");
        addHbox.getChildren().add(btnClose);

        btnClose.setOnAction(new EventHandler<ActionEvent>(){

                 @Override
                 public void handle(ActionEvent arg0) {
                     secondStage.close();
                 }

             });

            dialogPane.setCenter(dialogVbox);
            dialogPane.setLeft(dialogVbox2);
            dialogPane.setBottom(addHbox);

            Scene scene2 = new Scene(dialogPane, 400, 200);

            secondStage.setTitle("Add New Product");
            secondStage.setScene(scene2);
            secondStage.show();

                //Set position of second window, related to primary window.
                secondStage.setX(primaryStage.getX() + 250);
                secondStage.setY(primaryStage.getY() + 100);

                secondStage.show();
            }
        });

        // DELETE BUTTON & EVENT HANDLER
        Button btnDelete = new Button("Delete");
        bottomHbox2.getChildren().add(btnDelete);

        btnDelete.setOnAction(new EventHandler<ActionEvent>(){

                 @Override
                 public void handle(ActionEvent arg0) {
                     deleteButtonClicked();
                 }

             });


        Button btnSave = new Button("Save & Exit");
        bottomHbox2.getChildren().add(btnSave);

        btnSave.setOnAction(new EventHandler<ActionEvent>(){

                 @Override
                 public void handle(ActionEvent arg0) {
                     primaryStage.close();
                 }

             });

        rightVbox.getChildren().add(bottomHbox2);

        topPane.setLeft(topHbox);
        topPane.setCenter(rightHbox);
        leftPane.setLeft(leftVbox);
        rightPane.setLeft(rightVbox);
        //rightPane.setCenter(bottomHbox2);

        root.setTop(topPane);
        root.setLeft(leftPane);
        root.setCenter(rightPane);

        Scene scene = new Scene(root, 650, 500);
        primaryStage.setTitle("Perishables Application");
        primaryStage.setScene(scene);
        primaryStage.show();
    }

    // DELETE BUTTON FUNCTION
    public void deleteButtonClicked() {
        ObservableList<Product> productSelected, productData;
        productData = table.getItems();
        productSelected = table.getSelectionModel().getSelectedItems();

        productSelected.forEach(productData::remove);
    }

    public ObservableList<Product> productData = FXCollections.observableArrayList(
    new Product("001", "Cereal", "1/1/2017"),
    new Product("002", "Dog Food", "3/3/2017"),
    new Product("003", "Juice", "1/1/2018")
    );


}

Any suggestions are greatly appreciated. Thanks for reading.

Copyright Notice:Content Author:「BecauseTurtles」,Reproduced under the CC 4.0 BY-SA copyright license with a link to the original source and this disclaimer.
Link to original article:https://stackoverflow.com/questions/40901292/javafx-gui-why-does-the-delete-button-function-not-work-with-the-tableview

More about “JavaFX GUI - Why does the Delete Button Function not work with the TableView?” related questions

JavaFX GUI - Why does the Delete Button Function not work with the TableView?

Hello this is my first question as a newcomer to both Java and GUI design. I have come across an odd situation that I feel I am just looking over. I have TableView with some information, which can ...

Show Detail

Delete Button function to delete selected row from javafx tableView and SQLite table row

I am a newbie working on a Javafx project for the first time and can really use some help and direction. I have read and tried several variations for the correct syntax, methods and suggestions. So...

Show Detail

JavaFX deleting from TableView

I'm working on a JavaFX app and am using a TableView as part of the GUI as follows: public TableView&lt;Meal&gt; meals; And to it I assigned a button that is supposed to delete elements which are

Show Detail

JavaFX TableView getItems().remove(i) does not work - why

I have a situation where I'd like to delete all rows from a TableView. So I did the following code inside a button's setOnAction lambda expression. But this code doesn't work for me. None of the

Show Detail

JavaFX: TableView not showing up in GUI

I am attempting to bind my program to the GUI designed in SceneBuilder. I have managed to get my 'Accounts.class' ID's displayed as wanted in the far left list. Now I need to get the TableView wor...

Show Detail

Adding new row with button to javafx tableview

I have defined a tableview in fxml. It is something like the following: SNO Name DOB Action The Action column would contain buttons in each row with text "delete". I have two questions: How do I...

Show Detail

Why isnt JavaFX TableView displaying data?

I've been working on a project to try and learn Java and I've been having trouble with getting Tableview to work. I've reviewed the other posts and so far I've made sure that: Getters and Setters ...

Show Detail

Swipe to delete function in tableview does not work properly

I've just added the swipe to delete function to my tableview controller. However is doesn't work properly. It deletes the item in my Firebase Database. But it doesn't delete the row out of my table...

Show Detail

JavaFx tableview RuntimeException

I am just trying to build a simple Gui with SceneBuilder and JavaFx however I can't figure out why I can't populate my TableView, it just stays empty even after inserting simple Testobjects. Here i...

Show Detail

Display all items in TableView from a List of objects that have a List as a data field (JavaFX, TableView, FXML)

Couldn't think of a good title, but bear with me... Person class: public class Person { private int pid; private List&lt;Insurance&gt; insurances; } Insurance class public class Insurance {

Show Detail