问题描述
我经常遇到一个问题,我有一个JList,希望用新内容进行更新.我使用的是DefaultListModel,它提供了将新内容添加到列表的方法,但是当使用这些方法时,我发现一定比例的调用会导致完全空白的JList.更新是否有效似乎是随机的,与发送的数据无关.
I have a recurring problem where I have a JList which I wish to update with new contents. I'm using a DefaultListModel which provides methods for adding new content to the list but when using these methods I find that some proportion of the calls result in a completely blank JList. Whether or not the update works seems to be random, and not related to the data which is sent.
下面是一个演示问题的简单程序.它只是生成一个大小不断增加的列表以更新JList,但是运行时,列表内容似乎是随机出现和消失的.
Below is a simple program which demonstrates the problem. It simply generates a list of an increasing size to update a JList, but when run the list contents appear and disappear seemingly at random.
据我所知,我正在使用正确的API来执行此操作,但我想我肯定缺少一些基本信息.
As far as I can tell I'm following the correct API to do this, but I guess there must be something fundamental I'm missing.
import java.awt.BorderLayout;
import javax.swing.*;
public class ListUpdateTest extends JPanel {
private JList list;
private DefaultListModel model;
public ListUpdateTest () {
model = new DefaultListModel();
list = new JList(model);
setLayout(new BorderLayout());
add(new JScrollPane(list),BorderLayout.CENTER);
new UpdateRunner();
}
public void updateList (String [] entries) {
model.removeAllElements();
for (int i=0;i<entries.length;i++) {
model.addElement(entries[i]);
}
}
private class UpdateRunner implements Runnable {
public UpdateRunner () {
Thread t = new Thread(this);
t.start();
}
public void run() {
while (true) {
int entryCount = model.size()+1;
System.out.println("Should be "+entryCount+" entries");
String [] entries = new String [entryCount];
for (int i=0;i<entries.length;i++) {
entries[i] = "Entry "+i;
}
updateList(entries);
try {
Thread.sleep(1000);
}
catch (InterruptedException e) {}
}
}
}
public static void main (String [] args) {
JDialog dialog = new JDialog();
dialog.setContentPane(new ListUpdateTest());
dialog.setSize(200,400);
dialog.setDefaultCloseOperation(JDialog.DISPOSE_ON_CLOSE);
dialog.setModal(true);
dialog.setVisible(true);
System.exit(0);
}
}
任何指针都将受到欢迎.
Any pointers would be very welcome.
推荐答案
看下面的代码:
import java.awt.BorderLayout;
import javax.swing.*;
import javax.swing.SwingWorker;
import java.util.Arrays;
import java.util.List;
public class ListUpdateTest extends JPanel {
private JList list;
private DefaultListModel model;
public ListUpdateTest () {
model = new DefaultListModel();
list = new JList(model);
setLayout(new BorderLayout());
add(new JScrollPane(list),BorderLayout.CENTER);
(new UpdateRunner()).execute();
}
public void updateList (List<String> entries) {
model.removeAllElements();
for (String entry : entries) {
model.addElement(entry);
}
}
private class UpdateRunner extends SwingWorker<List<String>, List<String>>{
@Override
public List<String> doInBackground() {
while (true) {
int entryCount = model.size()+1;
System.out.println("Should be "+entryCount+" entries");
String [] entries = new String [entryCount];
for (int i=0;i<entries.length;i++) {
entries[i] = "Entry "+i;
}
publish(Arrays.asList(entries));
try {
Thread.sleep(1000);
}
catch (InterruptedException e) {}
}
return null;
}
@Override
protected void process(List<List<String>> entries) {
for (List<String> entry : entries) {
updateList(entry);
}
}
@Override
protected void done() {
updateList(Arrays.asList("done"));
}
}
public static void main (String [] args) {
JDialog dialog = new JDialog();
dialog.setContentPane(new ListUpdateTest());
dialog.setSize(200,400);
dialog.setDefaultCloseOperation(JDialog.DISPOSE_ON_CLOSE);
dialog.setModal(true);
dialog.setVisible(true);
System.exit(0);
}
}
由SwingWorker实施.工作顺利.
Implemented by SwingWorker. Works smooth.
这篇关于通过列表模型更新内容后,为什么有时会得到空白的JLists?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!