Eclipse插件:如何异步向TableViewer添加项目?

时间:2012-05-12 10:03:27

标签: java eclipse eclipse-plugin jface tableviewer

在我的Eclipse插件中,我有一个显示一些数据的TableViewer。从远程REST服务检索这些数据。因此,检索所有项目需要几秒钟。这就是为什么我想在检索项目后立即向TableViewer的{​​{1}}添加项目。我在一个单独的线程中执行我的REST查询:

ContentProvider

在这个帖子中,我将项目添加到Thread retrieveThread = new RetrieveThread(); retrieveThread.run();

TableViewer

MyView.instance.addItems(items); 中的相同方法:

MyView

我希望此过程会将项目添加到public void addItems(List<Result> items) { ModelProvider.INSTANCE.addItems(items); resultLabel.setText(ModelProvider.INSTANCE.getItems().size() + " items"); PlatformUI.getWorkbench().getDisplay().asyncExec(new Runnable() { @Override public void run() { viewer.refresh(); } }); } ,然后刷新视图。但现在发生的事情是我的Eclipse冻结并同时添加所有项目。我怎样才能以更敏感的方式做到这一点?

1 个答案:

答案 0 :(得分:2)

问题是您直接调用线程的run方法。这不会产生新的线程,它只是在线调用run方法。 retrieveThread.start()会为您提供您正在寻找的行为。

然而,有更好的方法(至少更多'eclipse friendly'),那就是使用Eclipse Job而不是原始的Thread

    Job retrieveJob = new Job("Retrieving Data") 
    {           
        @Override
        protected IStatus run(IProgressMonitor monitor) {
            // do your REST call
            ModelProvider.INSTANCE.addItems(items);
            // if something goes wrong - don't return ok, obviously 
            return Status.OK_STATUS;                
        }
    };
    retrieveJob.addJobChangeListener(new JobChangeAdapter() {

        @Override
        public void done(IJobChangeEvent event) {
            if(event.getResult().isOK())
            {
                resultLabel.setText(ModelProvider.INSTANCE.getItems().size() + " items");
                viewer.refresh();
            }
        }           
    });
    // this will run in a background thread 
    // and nicely integrate with the UI
    retrieveJob.schedule();