2

我创建了一个带有 GlazedLists 的表,以便能够过滤该表以进行搜索。现在的问题是如何删除、添加或更新此表中的行。我确实搜索了 API,但无法弄清楚。

谁能用一个简单的例子演示如何实现删除、添加、更新?

public static JTable retrieveArtikelTable(String filePath, String[] header, JTextField filterField) {
    EventList eventList = new BasicEventList();
    String[] headers = new String[0];
    CsvReader reader = null;
    JTable t = new JTable();
    if (filePath != null) {
        if (new File(filePath).exists()) {
            try {
                reader = new CsvReader(filePath, ';');
                if (header != null) {
                    headers = header;
                } else {
                    headers = reader.getHeaders();
                }
                while (reader.readRecord()) {
                    String[] values = reader.getValues();
                    eventList.add(new Artikel(values[0], values[1], values[2]));
                }
                reader.close();
                TextFilterator artikelFilterator = new TextFilterator() {
                    public void getFilterStrings(List baseList, Object element) {
                        Artikel artikel = (Artikel) element;
                        baseList.add(artikel.getCode());
                        baseList.add(artikel.getName());
                        baseList.add(artikel.getNumber());
                    }
                };
                TextComponentMatcherEditor matcherEditor = new TextComponentMatcherEditor(filterField, artikelFilterator);
                FilterList filteredArtikels = new FilterList(eventList, new ThreadedMatcherEditor(matcherEditor));

                // build a JTable
                TableFormat tf = GlazedLists.tableFormat(Artikel.class,headers, headers);
                t = new JTable(new EventTableModel(filteredArtikels, tf));
            } catch (Exception ex) {
                OeExceptionDialog.show(ex);
            } finally {
                assert reader != null;
                reader.close();
            }
        }
    }else{
        t=new JTable();
        JOptionPane.showMessageDialog(filterField.getParent(),"Attention: " +filePath+
                "There is no such a file to be able to create a table!");
    }


    return t;
}


header = new String[]{"Code","Name","Number"};
JTextField filterField = new JTextField();
JTable table = retrieveArtikelTable("c:\articl.csv", header, filterField)

int selectedRow = table.getSelectedRow();
EventTableModel tableModel = (EventTableModel) table.getModel();
// code for deleting a row from this table

// code for add row to this table

// code for updating row from this table

编辑:

EventList eventList = new BasicEventList();
JTable table = retrieveArtikelTable("c:\articl.csv", header, filterField, eventList)
int selectedRow = table.getSelectedRow();

// code for deleting a row from this table
 eventList.remove(selectedRow);
// code for add row to this table

// code for updating row from this table
4

1 回答 1

5

如果您对 EventList 进行更改,那么这些更改将通过表模型传播到 JTable。(也就是说,如果您向该列表添加一个新对象、删除一个或更新一个对象,则更改会自动发生。因此,“事件”前缀 - 列表中的事件将传达给模型。)

因此,您可能需要保留对 EventList 的引用,以确保它可以访问retrieveArtikelTable()您的案例之外的部分代码。

我觉得GlazedLists Developer的截屏视频非常适合涵盖所有基本主题。

编辑:只是提醒您如何使列表成为实例变量,以便可以通过任何方法访问它,而不仅仅是构造表的方法。

public class Example {
    private EventList<Person> eventList = new BasicEventList<Person>();

    public JTable createTable(...) { ... code to generate the table ...}

    public void manipulateTable() {
        // add to the table (via the eventList)
        eventList.add(new Person("Steve Jobs"));
        // remove first object in the table (and the list)
        eventList.remove(0);
        // update a row
        Person p = eventList.get(0);
        p.setName("A N Other");
        eventList.set(0,p); // overwrite the old object in the list

    }
}

编辑#2:我包含了一个更完整的示例,以说明您应该如何使用 EventSelectionModel 正确处理选择,它允许您准确知道在任何给定时间选择了哪些行,即使过滤器已经应用。

示例应用的屏幕截图

我复制了一个使用 Netbeans GUI 构建器部分生成的文件。但需要注意的关键点是:

  1. EventSelectionModel声明为实例变量,以便可以在类的其他地方访问它。

  2. btnDeleteActionPerformed()方法。这就是按下 Delete 按钮时发生的情况。首先,我检查是否选择了任何行。如果是这样,获取选定的项目(作为事件列表返回)并简单地将它们从主列表中删除。

这是 MyFrame.java 的示例代码

public class MyFrame extends javax.swing.JFrame {

    private EventList<Person> eventList = new BasicEventList<Person>();
    private EventSelectionModel<Person> selectionModel;

    /**
     * Creates new form MyFrame
     */
    public MyFrame() {
        initComponents();
        loadData();
        configureTable();
    }

    private void loadData() {

        eventList.add(new Person("Richard", "Dawkins"));
        eventList.add(new Person("Sam", "Harris"));
        eventList.add(new Person("Christopher", "Hitchens"));
        eventList.add(new Person("Daniel", "Dennett"));

    }

    private void configureTable() {
        String[] headers = new String[]{"Firstname", "Lastname"};
        String[] properties = new String[]{"firstname", "lastname"};


        TextFilterator<Person> personTextFilterator = new TextFilterator<Person>() {

            @Override
            public void getFilterStrings(List list, Person p) {
                list.add(p.getFirstname());
                list.add(p.getLastname());
            }
        };

        MatcherEditor<Person> textMatcherEditor = new TextComponentMatcherEditor<Person>(txtFilter, personTextFilterator);

        FilterList<Person> filterList = new FilterList<Person>(eventList, textMatcherEditor);

        TableFormat tf = GlazedLists.tableFormat(properties, headers);
        EventTableModel<Person> model = new EventTableModel<Person>(filterList, tf);

        selectionModel = new EventSelectionModel<Person>(filterList);
        tblNames.setSelectionModel(selectionModel);

        tblNames.setModel(model);
    }

    /**
     * This method is called from within the constructor to initialize the form.
     * WARNING: Do NOT modify this code. The content of this method is always
     * regenerated by the Form Editor.
     */
    @SuppressWarnings("unchecked")
    // <editor-fold defaultstate="collapsed" desc="Generated Code">                          
    private void initComponents() {

        jLabel1 = new javax.swing.JLabel();
        txtFilter = new javax.swing.JTextField();
        jScrollPane1 = new javax.swing.JScrollPane();
        tblNames = new javax.swing.JTable();
        btnDelete = new javax.swing.JButton();
        btnReload = new javax.swing.JButton();

        setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE);
        setTitle("GlazedLists test");

        jLabel1.setText("Filter");

        tblNames.setModel(new javax.swing.table.DefaultTableModel(
            new Object [][] {
                {null, null, null, null},
                {null, null, null, null},
                {null, null, null, null},
                {null, null, null, null}
            },
            new String [] {
                "Title 1", "Title 2", "Title 3", "Title 4"
            }
        ));
        jScrollPane1.setViewportView(tblNames);

        btnDelete.setText("Delete");
        btnDelete.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                btnDeleteActionPerformed(evt);
            }
        });

        btnReload.setText("Reload data");
        btnReload.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                btnReloadActionPerformed(evt);
            }
        });

        javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane());
        getContentPane().setLayout(layout);
        layout.setHorizontalGroup(
            layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)
            .add(layout.createSequentialGroup()
                .addContainerGap()
                .add(layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)
                    .add(layout.createSequentialGroup()
                        .add(jLabel1)
                        .addPreferredGap(org.jdesktop.layout.LayoutStyle.RELATED)
                        .add(txtFilter))
                    .add(jScrollPane1, org.jdesktop.layout.GroupLayout.DEFAULT_SIZE, 388, Short.MAX_VALUE)
                    .add(org.jdesktop.layout.GroupLayout.TRAILING, layout.createSequentialGroup()
                        .add(btnReload)
                        .addPreferredGap(org.jdesktop.layout.LayoutStyle.RELATED, org.jdesktop.layout.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
                        .add(btnDelete)))
                .addContainerGap())
        );
        layout.setVerticalGroup(
            layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)
            .add(layout.createSequentialGroup()
                .addContainerGap()
                .add(layout.createParallelGroup(org.jdesktop.layout.GroupLayout.BASELINE)
                    .add(jLabel1)
                    .add(txtFilter, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE, org.jdesktop.layout.GroupLayout.DEFAULT_SIZE, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE))
                .addPreferredGap(org.jdesktop.layout.LayoutStyle.UNRELATED)
                .add(jScrollPane1, org.jdesktop.layout.GroupLayout.DEFAULT_SIZE, 240, Short.MAX_VALUE)
                .addPreferredGap(org.jdesktop.layout.LayoutStyle.RELATED)
                .add(layout.createParallelGroup(org.jdesktop.layout.GroupLayout.BASELINE)
                    .add(btnDelete)
                    .add(btnReload))
                .addContainerGap())
        );

        pack();
    }// </editor-fold>                        

    private void btnDeleteActionPerformed(java.awt.event.ActionEvent evt) {                                          
        if (!selectionModel.isSelectionEmpty()) {
            eventList.removeAll(selectionModel.getSelected());
        }
    }                                         

    private void btnReloadActionPerformed(java.awt.event.ActionEvent evt) {                                          
        eventList.clear();
        loadData();
    }                                         

    /**
     * @param args the command line arguments
     */
    public static void main(String args[]) {

        /*
         * Create and display the form
         */
        java.awt.EventQueue.invokeLater(new Runnable() {

            @Override
            public void run() {
                new MyFrame().setVisible(true);
            }
        });
    }
    // Variables declaration - do not modify                     
    private javax.swing.JButton btnDelete;
    private javax.swing.JButton btnReload;
    private javax.swing.JLabel jLabel1;
    private javax.swing.JScrollPane jScrollPane1;
    private javax.swing.JTable tblNames;
    private javax.swing.JTextField txtFilter;
    // End of variables declaration                   
}

我在示例中使用了 Person 类,它是一个非常简单的POJO

public class Person {

    private String firstname;
    private String lastname;

    public Person() {
    }

    public Person(String firstname, String lastname) {
        this.firstname = firstname;
        this.lastname = lastname;
    }

    public String getFirstname() {
        return firstname;
    }

    public void setFirstname(String firstname) {
        this.firstname = firstname;
    }

    public String getLastname() {
        return lastname;
    }

    public void setLastname(String lastname) {
        this.lastname = lastname;
    }

}

我个人建议将数据加载与创建表的方法分开。我使用了loadData()填充列表的方法。如果没有要加载的数据,或者您要从中加载的文件有问题,那么仍然会创建表,但其中没有任何内容,因为列表仍然是空的。

于 2012-05-30T10:10:17.970 回答