AbstractDataTable fireTableDataChanged()不刷新jtable

时间:2014-04-18 22:11:50

标签: java swing jtable

我在向jtable添加数据时遇到了困难。它首先加载来自集合的数据,用jtextfield我添加一个新数据,当然数据被添加到集合调试它但我无法在我的jtable中显示新添加的日期。我已经尝试了所有可能的方法,但无法做到。下面的代码是我工作的一部分。

由于

/*
 * To change this license header, choose License Headers in Project Properties.
 * To change this template file, choose Tools | Templates
 * and open the template in the editor.
 */
package com.example.gui;

import com.example.service.CustomerService;
import com.example.service.VehicleService;
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.GridBagLayout;
import java.awt.GridLayout;
import java.awt.HeadlessException;
import java.awt.Toolkit;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.ArrayList;
import javax.swing.DefaultListModel;
import javax.swing.JButton;
import javax.swing.JFrame;
import static javax.swing.JFrame.EXIT_ON_CLOSE;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.JTextField;
import javax.swing.SwingUtilities;
import javax.swing.event.TableModelEvent;
import javax.swing.table.AbstractTableModel;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableModel;

/**
 *
 * @author Tugrul
 */

public class VehicleTypes extends JFrame {

    private JLabel lblVehicleType;
    private JTextField txtVehicleType;
    private JButton btnCreateVehicleType;
    private JButton btnClearField;
    private JTable jtDataTable;
    private JPanel formPanel;
    private JPanel dataPanel;
    private JPanel buttonPanel;
    private JMenu jmFile;
    private JMenu jmCustomer;
    private JMenu jmServiceDesk;
    private JMenuBar appMenuBar;
    private JMenuItem jmiMainMenu;
    private JMenuItem jmiExit;
    private JMenuItem jmiPlaceBooking;
    private JMenuItem jmiRegister;
    private JMenuItem jmiVehicleTypes;
    private JMenuItem jmiCustomerType;
    private JMenuItem jmiVehicles;
    private JMenuItem jmiCustomers;
    private JMenuItem jmiManageBookings;
    private CustomDataTable customDataTable;

    public VehicleTypes() {
        drawForm();
    }

    public void drawForm() {

        customDataTable = new CustomDataTable();
        jtDataTable = new JTable(customDataTable);
        /*Drawing root menu*/
        jmFile = new JMenu("File");
        jmCustomer = new JMenu("Customer");
        jmServiceDesk = new JMenu("Service Desk");
        appMenuBar = new JMenuBar();

        /*Drawing File Menu*/
        jmiMainMenu = new JMenuItem("Main Menu");
        jmiExit = new JMenuItem("Exit");
        jmFile.add(jmiMainMenu);
        jmFile.add(jmiExit);

        /*Drawing Customer Menu*/
        jmiPlaceBooking = new JMenuItem("Place Booking");
        jmiRegister = new JMenuItem("Register");
        jmCustomer.add(jmiPlaceBooking);
        jmCustomer.add(jmiRegister);

        /*Drawing Service Desk Menu*/
        jmiVehicleTypes = new JMenuItem("Vehicle Types");
        jmiCustomerType = new JMenuItem("Customer Types");
        jmiVehicles = new JMenuItem("Vehicles");
        jmiCustomers = new JMenuItem("Customers");
        jmiManageBookings = new JMenuItem("Manage Bookings");
        jmServiceDesk.add(jmiVehicleTypes);
        jmServiceDesk.add(jmiCustomerType);
        jmServiceDesk.add(jmiVehicles);
        jmServiceDesk.add(jmiCustomers);
        jmServiceDesk.add(jmiManageBookings);

        /*Add menus to menubar*/
        appMenuBar.add(jmFile);
        appMenuBar.add(jmCustomer);
        appMenuBar.add(jmServiceDesk);

        /*Adding listeners for each element*/
        jmiMainMenu.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                formListener(e);
            }
        });
        jmiExit.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                formListener(e);
            }
        });
        jmiPlaceBooking.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                formListener(e);
            }
        });
        jmiRegister.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                formListener(e);
            }
        });
        jmiVehicleTypes.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                formListener(e);
            }
        });
        jmiCustomerType.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                formListener(e);
            }
        });
        jmiVehicles.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                formListener(e);
            }
        });
        jmiCustomers.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                formListener(e);
            }
        });
        jmiManageBookings.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                formListener(e);
            }
        });

        lblVehicleType = new JLabel("Vehicle Type");
        txtVehicleType = new JTextField();
        btnCreateVehicleType = new JButton("Create");
        btnClearField = new JButton("Clear Fields");
        formPanel = new JPanel();
        dataPanel = new JPanel();
        buttonPanel = new JPanel();

        setSize(800, 600);
        setTitle("Vehicle Types");
        setDefaultCloseOperation(EXIT_ON_CLOSE);

        //Centering the application on screen
        Toolkit toolkit = getToolkit();
        Dimension size = toolkit.getScreenSize();
        setLocation(size.width / 2 - getWidth() / 2,
                size.height / 2 - getHeight() / 2);

        formPanel.add(lblVehicleType);
        formPanel.add(txtVehicleType);

        dataPanel.add(new JScrollPane(jtDataTable));

        buttonPanel.add(btnCreateVehicleType);
        buttonPanel.add(btnClearField);

        /*Setting layouts for panels*/
        formPanel.setLayout(new GridLayout(1, 1, 0, 0));
        dataPanel.setLayout(new GridLayout(1, 2, 10, 10));
        buttonPanel.setLayout(new GridLayout(2, 1, 5, 5));

        /*Adding panels to main jframe*/
        add(dataPanel, BorderLayout.NORTH);
        add(formPanel, BorderLayout.CENTER);
        add(buttonPanel, BorderLayout.SOUTH);
        setJMenuBar(appMenuBar);

        //Adding buttons to listeners
        btnCreateVehicleType.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                formListener(e);
            }
        });
        btnClearField.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                formListener(e);
            }
        });

    }

    private class CustomDataTable extends AbstractTableModel {

        private VehicleService vehicleService = new VehicleService();

        int rowCount = vehicleService.retrieveVehicleTypes().size();

        private String[] columnNames = {"Vehicle Type"};

        @Override
        public String getColumnName(int col) {
            return columnNames[col];
        }

        @Override
        public int getRowCount() {
            return rowCount;
        }

        @Override
        public int getColumnCount() {
            return columnNames.length;
        }

        @Override
        public Object getValueAt(int rowIndex, int columnIndex) {

            Object val = (Object) vehicleService.retrieveVehicleTypes().get(rowIndex);
            return val;
        }

        public void insertData(String values) {
            vehicleService.createVehicleType(values);

            fireTableDataChanged();
            System.out.println("affected data" + vehicleService.retrieveVehicleTypes().toString());
        }

    }

    public void clearFields() {
        txtVehicleType.setText("");
    }

    public void formListener(ActionEvent e) {

        VehicleService vehicleService = new VehicleService();

        String clickedItem = e.getActionCommand();
        String vehicleType = txtVehicleType.getText().toString();

        if (clickedItem.equals("Create")) {
            if (vehicleService.checkVehicleTypeAvailability(vehicleType)) {
                JOptionPane.showMessageDialog(null, vehicleType + "  Vehicle type already exists in Database",
                        "Vehicle Warning",
                        JOptionPane.WARNING_MESSAGE);
            } else {
                customDataTable.insertData(vehicleType);
                this.invalidate();

                this.validate();
                this.repaint();
                this.revalidate();
                jtDataTable.revalidate();
                jtDataTable.repaint();

            }
        }
        if (clickedItem.equals("Clear Fields")) {
            //clear field code
            clearFields();
        }

        //Jmenu listener
        if (clickedItem.equals("Main Menu")) {
            VehicleTypes customerTypes = new VehicleTypes();
            CustomerManagement customerManagement = new CustomerManagement();
            customerTypes.setVisible(false);
            customerManagement.setVisible(true);
        }
        if (clickedItem.equals("Exit")) {
            int dialogButton = JOptionPane.YES_NO_OPTION;
            int dialogResult = JOptionPane.showConfirmDialog(null, "Are you sure to leave the application", "Confim Process", dialogButton);
            if (dialogResult == 0) {
                System.exit(1);
            }
        }
        if (clickedItem.equals("Place Booking")) {

        }
        if (clickedItem.equals("Register")) {

        }
        if (clickedItem.equals("Vehicle Types")) {
            //dont do anything
        }
        if (clickedItem.equals("Customer Types")) {
            CustomerTypes customerTypes = new CustomerTypes();
            this.setVisible(false);
            customerTypes.setVisible(true);
        }
        if (clickedItem.equals("Vehicles")) {

        }
        if (clickedItem.equals("Customers")) {

        }
        if (clickedItem.equals("Manage Bookings")) {

        }

    }//Action listener end curly brace

    public static void main(String[] args) {

        try {
            for (javax.swing.UIManager.LookAndFeelInfo info : javax.swing.UIManager.getInstalledLookAndFeels()) {
                if ("Nimbus".equals(info.getName())) {
                    javax.swing.UIManager.setLookAndFeel(info.getClassName());
                    break;
                }
            }
        } catch (ClassNotFoundException ex) {
            System.out.println("Exception Caught " + ex);
        } catch (InstantiationException ex) {
            System.out.println("Exception Caught " + ex);
        } catch (IllegalAccessException ex) {
            System.out.println("Exception Caught " + ex);
        } catch (javax.swing.UnsupportedLookAndFeelException ex) {
            System.out.println("Exception Caught " + ex);
        }

        SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                new VehicleTypes().setVisible(true);
            }
        });
    }

}

1 个答案:

答案 0 :(得分:1)

这种方法实施得不好:

public void insertData(String values) {
    vehicleService.createVehicleType(values);
    fireTableDataChanged(); // No, call fireTableRowsInserted(...) instead
    ...
}

此时调用fireTableDateChanged()是过分且不必要的,因为您似乎在表中添加了一行。正确的实现应该按如下方式调用fireTableRowsInserted(int firstRow, int lastRow)

public void insertData(String values) {
    vehicleService.createVehicleType(values);
    int lastIndex = vehicleService.retrieveVehicleTypes().size() - 1;
    fireTableRowsInserted(lastIndex, lastIndex); // first and last indices are the same
}

此外,在向表模型添加新行之后,不需要revalidate()repaint()。只需通知听众就足够了:JTable是自己模型的监听者,并会在TableModelEvents上相应地重新绘制自己。