3

我正在尝试在我的 RCP 应用程序中构建一个视图,该视图只包含一个TreeViewer.

树可以包含文件夹或叶子,文件夹可以包含文件夹和叶子。当我将文件夹添加到根文件夹的后端数据模型时,UI 会自动更新,但如果我将文件夹添加到任何分支文件夹,则 UI 不会自动更新。请告诉我我的代码有什么问题。

模型类:

public class TreeNode extends BindableObject {

    private Folder parent;

    private String name;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        super.firePropertyChange("name", this.name, this.name = name);
    }

    public Folder getParent() {
        return parent;
    }

    public void setParent(Folder parent) {
        this.parent = parent;
    }

}
public class Folder extends TreeNode {

    private List<TreeNode> children = new ArrayList<TreeNode>();

    public List<TreeNode> getChildren() {
        return children;
    }

    public void setChildren(List<TreeNode> children) {
        this.children = children;
    }

    public void add(TreeNode node){
        children.add(node);
    }

}

风景 :

public class ExplorerView extends ViewPart {

    private WritableList data;
    private TreeViewer treeViewer;

    public WritableList getData() {
        return data;
    }

    public TreeViewer getViewer(){
        return treeViewer;
    }

    public ExplorerView() {
        // TODO Auto-generated constructor stub
    }

    @Override
    public void createPartControl(Composite parent) {
        parent.setLayout(new FillLayout(SWT.HORIZONTAL));
        treeViewer = new TreeViewer(parent, SWT.BORDER);
        treeViewer.setContentProvider(new ObservableListTreeContentProvider(new ExplorerObservableFactory(), new ExploerTreeStructureAdvisor()));
        treeViewer.setLabelProvider(new ExplorerTreeLabelProvider());
        ArrayList<TreeNode> list = new ArrayList<TreeNode>();
        list.add(new ExplorerDataModel().getElements()[0]);
        data = new WritableList(list, TreeNode.class);
        treeViewer.setInput(data);
    }

    @Override
    public void setFocus() {

    }

}

可观察工厂:

public class ExplorerObservableFactory implements IObservableFactory {

    @Override
    public IObservable createObservable(Object target) {
        System.out.println(target.getClass().getName());
        if(target instanceof WritableList){
            return (WritableList)target;
        }
        else if(target instanceof Folder){
            List<TreeNode> children = ((Folder)target).getChildren();
            return new WritableList(children, TreeNode.class);
        }
        return null;
    }

}

树结构顾问:

public class ExploerTreeStructureAdvisor extends TreeStructureAdvisor {

    @Override
    public Object getParent(Object element) {
        return ((TreeNode)element).getParent();
    }

    @Override
    public Boolean hasChildren(Object element) {
        if(element instanceof Folder){
            return true;
        }else{
            return false;
        }
    }



}

数据 :

public class ExplorerDataModel {
    public TreeNode[] getElements() {
        Folder f1 = new Folder();
        f1.setName("Database Connections");
        Folder f11 = new Folder();
        f11.setName("Credit Test");
        TreeNode t1 = new TreeNode();
        t1.setName("bank@localhost");
        f11.add(t1);
        t1.setParent(f11);
        TreeNode t2 = new TreeNode();
        t2.setName("credit@localhost");
        f11.add(t2);
        t2.setParent(f11);
        Folder f12 = new Folder();
        f12.setName("Credit Product");
        TreeNode t3 = new TreeNode();
        t3.setName("nbcbcredit@localhost");
        f12.add(t3);
        t3.setParent(f12);
        TreeNode t4 = new TreeNode();
        t4.setName("nbcbcredit_bak@localhost");
        f12.add(t4);
        t4.setParent(f12);
        f1.add(f11);
        f11.setParent(f1);
        f1.add(f12);
        f12.setParent(f1);
        return new TreeNode[] { f1 };
    }
}

测试命令处理程序:

public Object execute(ExecutionEvent event) throws ExecutionException {
    ExplorerView v =(ExplorerView) HandlerUtil.getActiveWorkbenchWindow(event).getActivePage().findView("com.amarsoft.dmp.explorer.explorerView");
        Folder f = new Folder();
        f.setName("ODA Flat Files");
        v.getData().add(f);

        Folder f1 = (Folder) v.getData().get(0);
        f1.setName("Database Connections (3)");

        Folder f2 = new Folder();
        f2.setName("Report Test");
        f1.add(f2);

        return null;
    }

如果我执行上面的命令,添加的文件夹“ODA Flat Files”将立即出现在树中,但添加的文件夹“Report Test”将不存在,如果调用TreeViewer#refresh() 一切正常,但我想知道为什么。

4

3 回答 3

4

修改您的模型不会通知您的树。刷新是告诉树数据已更改并且需要更新的一种方式。如果您在 Eclipse 中浏览 jface 查看器的 java 文档,您会发现以下引用

要处理结构更改,请改用刷新方法。

于 2012-06-25T15:23:40.380 回答
2

看来您错误配置了数据绑定...

看看官方的片段:

玩得开心!(没有任何刷新;-))

附言。对于 EMF,只需看看这个:http ://tomsondev.bestsolution.at/2009/06/08/galileo-emf-databinding-%E2%80%93-part-3/

于 2013-03-01T20:35:44.153 回答
1

在你的ExplorerObservableFactory替换

... else if(target instanceof Folder){
            List<TreeNode> children = ((Folder)target).getChildren();
            return new WritableList(children, TreeNode.class);
     }

依照指示

     else if(target instanceof Folder){                
            return BeansObservables.observeList(target, "children");
     }

如果返回WritableList这里,contentProvider 的监听器就注册在上面(它应该注册在 Folder bean 上)

于 2013-04-27T18:32:22.353 回答