简体   繁体   中英

JList not updating with custom ListModel

I have a TestListModel which extends AbstractListModel

public class TestListModel extends AbstractListModel {
List<Test> testlist = new ArrayList<Test>();

public Object getElementAt(int arg0) {
    return testlist.get(arg0);
}

public int getSize() {
    return testlist.size();
}
public void add(Test t) {
    System.out.println("adding");
    testlist.add(t);
    System.out.println(testlist.toString());
}
public void remove(Test t) {
    testlist.remove(t);
}

}

I have a JList like so

final TestListModel listModel = new TestListModel();
    listModel.add(new Test("test", "scen"));
    JPanel panel = new JPanel();
    final JList list = new JList(listModel);
    panel.add(list);
    list.setVisibleRowCount(3);
    list.setFont(new Font("Tahoma", Font.PLAIN, 14));
    list.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
    list.setBounds(0, 0, 100, 400);

I also have an Add Button that has an actionlister

public void actionPerformed(ActionEvent arg0) {
final JFileChooser fc = new JFileChooser();fc.setCurrentDirectory(new 
fc.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY);
int returnVal = fc.showOpenDialog(frmAtt);
if(returnVal == JFileChooser.APPROVE_OPTION) {
    listModel.add(getTest(fc.getSelectedFile().toString()));
}
}

The ArrayList appears to be updating when I add another test through the button but the GUI does not reflect this change. JList appears completely blank. It should be showing all the tests in the model.

Only the first test "scen" shows up in the JList which I added manually to the list (can see in the code above).

You're not firing any of the notification methods after changing the ListModel's data. The solution is to of course do this. Look at the AbstractListModel API at the methods that start with fireXXX(...) and call the appropriate one inside of your model whenever data is changed. ie, in these methods:

public void add(Test t) {
    testlist.add(t);
    int index0 = testlist.size() - 1;
    int index1 = index0;
    fireIntervalAdded(this, index0, index1);
}

public void remove(Test t) {
    int index0 = ... // this will depend on where t was in the testlist
    int index1 = ... // ditto
    testlist.remove(t);
    fireIntervalRemoved(this, index0, index1);
}

The reason to call these methods is because the model must notify its listeners that the data has been changed, else the listeners (your JList component) will not change their view of the data.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM