I have a JList that is sorted absed upon 2 values, a Queue position and a name
if my ListModel I fireContentsChange but it never resorts the data:
public void setQueuePos(String sUser, int nQueuePos) {
User u = getUser(sUser);
if(u != null) u.setQueuePos(nQueuePos);
fireContentsChanged(this, 0, getSize()-1);
}
What do I need to do to force the model to re-sort?
Peter
PS. Full code with test below
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.Random;
import java.util.TreeSet;
import javax.swing.AbstractListModel;
import javax.swing.DefaultListModel;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JList;
import javax.swing.JScrollPane;
import javax.swing.ListSelectionModel;
import javax.swing.SwingUtilities;
@SuppressWarnings("serial")
public class testlist extends JFrame {
private JList _list = new JList(new ListData());
private JScrollPane _scroll = new JScrollPane(_list);
private int _ctr = 0;
private String[] _users = { "Peter", "Bob", "Steve", "George" };
protected testlist() {
this.setLayout(new BorderLayout());
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
_list.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
_list.setSelectedIndex(0);
add(_scroll, BorderLayout.CENTER);
JButton b = new JButton("add");
b.addActionListener(new ActionListener () {
public void actionPerformed(ActionEvent arg0) {
onAdd();
}
});
add(b, BorderLayout.SOUTH);
JButton b2 = new JButton("shuffle");
b2.addActionListener(new ActionListener () {
public void actionPerformed(ActionEvent arg0) {
onShuffle();
}
});
add(b2, BorderLayout.NORTH);
this.setPreferredSize(new Dimension(300, 600));
pack();
}
protected void onAdd() {
((ListData)_list.getModel()).addUser(_users[_ctr++]);
}
protected void onShuffle() {
Random r = new Random();
int i = r.nextInt(4);
ListData l = (ListData)_list.getModel();
l.clearQueue();
l.setQueuePos(_users, 1);
System.out.println("Setting "+_users[i]);
_list.invalidate();
_list.validate();
}
class User implements Comparable<Object> {
protected String _sUser;
protected int nQueuePos = Integer.MAXVALUE;
public User(String strUser) {
_sUser = strUser;
}
public String toString() {
return _sUser;
}
public void setQueuePos(int nQuePos) {
_nQueuePos = nQuePos;
}
public int getQueuePos() { return _nQueuePos; }
@Override
public int compareTo(Object o) {
if (!(o instanceof User))
throw new ClassCastException();
User u = (User) o;
System.out.print("Comparing "+this._sUser+":"+this._nQueuePos);
System.out.println(" with "+u._sUser+":"+u._nQueuePos);
// sort first by queue
if (_nQueuePos < u._nQueuePos)
return -1;
if (_nQueuePos > u._nQueuePos)
return 1;
return sUser.compareTo(u.sUser);
}
@Override
public boolean equals (Object o) {
return sUser.equals(((User)o).sUser);
}
}
class ListData extends DefaultListModel {
protected TreeSet<User> model;
public ListData() {
model = new TreeSet<User>();
}
@Override
public Object getElementAt(int index) {
return model.toArray()[index];
}
@Override
public int getSize() {
return model.size();
}
public void addUser(String sUser) {
User u = new User(sUser);
if (model.add(u)) {
fireContentsChanged(this, 0, getSize()-1);
}
}
public User getUser(String sUser) {
for (User u : model)
if (u.toString().equals(sUser))
return u;
return null;
}
public void clearQueue() {
for (User u : model)
u.setQueuePos(Integer.MAX_VALUE);
}
public void setQueuePos(String sUser, int nQueuePos) {
User u = getUser(sUser);
if(u != null) u.setQueuePos(nQueuePos);
fireContentsChanged(this, 0, getSize()-1);
}
public void clear() {
model.clear();
fireContentsChanged(this, 0, getSize());
}
public boolean contains(Object element) {
return model.contains(element);
}
public Object firstElement() {
return model.first();
}
public Object lastElement() {
return model.last();
}
public boolean removeElement(Object element) {
boolean removed = model.remove(element);
if (removed) {
fireContentsChanged(this, 0, getSize());
}
return removed;
}
}
public static void main(String[] args) {
final testlist t = new testlist();
SwingUtilities.invokeLater(new Runnable() {
public void run() {
t.setVisible(true);
}
});
}
}