我有一项任务,我必须创建一个图像库,使用SwingWorker
从文件加载图像,一旦图像加载,您可以翻转图像并进行幻灯片播放。我无法使用SwingWorker
获取已加载图像的列表。
这是在后台发生的事情,它只是将结果发布到TextArea
// In a thread
@Override
public List<Image> doInBackground() {
List<Image> images = new ArrayList<Image>();
for (File filename : filenames) {
try {
//File file = new File(filename);
System.out.println("Attempting to add: " + filename.getAbsolutePath());
images.add(ImageIO.read(filename));
publish("Loaded " + filename);
System.out.println("Added file" + filename.getAbsolutePath());
} catch (IOException ioe) {
publish("Error loading " + filename);
}
}
return images;
}
}
完成后我只需将图像插入List<Image>
就可以了。
// In the EDT
@覆盖 protected void done(){ 试试{
for (Image image : get()) {
list.add(image);
}
} catch (Exception e) { }
}
我还创建了一个方法,返回名为list
的{{1}}我需要获取的是来自getImages()
的列表,但是当我调用getImages()
时,它不能正常工作例如
execute()
一旦到达MySwingWorkerClass swingworker = new MySwingWorkerClass(log,list,filenames);
swingworker.execute();
imageList = swingworker.getImage()
它就不会返回任何内容我能够获得列表的唯一方法就是当我使用imageList
代替run()
时,还有另一种方式获取列表或execute()
方法是唯一的方法吗?或者我可能不理解run()
班级。
答案 0 :(得分:1)
我认为你有点误解和SwingWorker
。大多数是正确的,但是你不能在getImage()
之后立即调用execute()
- 执行调用立即返回,并且你的图像正在工作线程上加载。因此,立即调用getImages()
无法获取图像。
要解决此问题,您应该在done()
覆盖中进行图像处理,例如将图像添加到将显示它们的UI组件。
答案 1 :(得分:1)
...或者我可能不理解
SwingWorker
班级。
您应该了解SwingWorker
的生命周期。当您调用execute时,您的处理将切换到后台线程,并且当前线程将立即返回。这就是你的getImages
没有返回任何内容的原因。来自javadoc:
<强>工作流强>
SwingWorker的生命周期涉及三个线程:
当前线程:在此线程上调用execute()方法。它安排SwingWorker在工作线程上执行并立即返回。可以使用get方法等待SwingWorker完成。
工作线程:在此线程上调用doInBackground()方法。这是所有背景活动应该发生的地方。要通知PropertyChangeListeners有关绑定属性的更改,请使用firePropertyChange和getPropertyChangeSupport()方法。默认情况下,有两个可用的绑定属性:状态和进度。
事件调度线程:此线程上发生所有与Swing相关的活动。 SwingWorker调用process和done()方法并通知此线程上的任何PropertyChangeListeners。
答案 2 :(得分:0)
为什么不使用发布过程机制将后台工作线程的中间结果发送到EDT
?似乎您正在使用SwingWorker#publish(V)
向用户说明任务的进度,您可以检查线程进度或更新PropertyChangeListener
。
更改您的工作人员以发送图片引用EDT
并覆盖SwingWorkerprocess(List<V> chunks)
方法以在EDT
上接收图像,并更新组件的模型以显示图片。
public class SwingWorker<Void,Image> {
@Override
public Void doInBackground() {
Image img;
while(....) {
img = downloadImage();
publish(img);
}
}
@Override
public void process(List<Image> images) {
//you are on the EDT now
}
}
调用SwingWorker#get()方法可以阻止EDT,同时使用发布 - 处理机制,您可以在每张照片可用时更新您的UI,而其他人仍在从Internet下载或从磁盘加载。 / p>