Bug 103747 - [Viewers] calling refresh on treeviewer in treeExpanded function, but it mess
Summary: [Viewers] calling refresh on treeviewer in treeExpanded function, but it mess
Status: VERIFIED FIXED
Alias: None
Product: Platform
Classification: Eclipse Project
Component: UI (show other bugs)
Version: 3.1   Edit
Hardware: PC Windows XP
: P3 normal (vote)
Target Milestone: 3.4 M1   Edit
Assignee: Boris Bokowski CLA
QA Contact:
URL:
Whiteboard:
Keywords: investigate
Depends on:
Blocks:
 
Reported: 2005-07-13 20:27 EDT by Michael Permana CLA
Modified: 2007-09-18 13:58 EDT (History)
2 users (show)

See Also:


Attachments
the test case to reproduce this bug (8.06 KB, text/plain)
2005-07-13 20:29 EDT, Michael Permana CLA
no flags Details

Note You need to log in before you can comment on or make changes to this bug.
Description Michael Permana CLA 2005-07-13 20:27:43 EDT
I tried calling refresh on treeviewer in treeExpanded function. The result is 
it mess up the tree, there is only one children without a label.

Code to reproduce: 
public void createPartControl(Composite parent) {
		viewer = new TreeViewer(parent, SWT.MULTI | SWT.H_SCROLL | 
SWT.V_SCROLL);
		drillDownAdapter = new DrillDownAdapter(viewer);
		viewer.setContentProvider(new ViewContentProvider());
		viewer.setLabelProvider(new ViewLabelProvider());
		viewer.setSorter(new NameSorter());
		viewer.setInput(getViewSite());
		viewer.addTreeListener(new ITreeViewerListener() {

			public void treeCollapsed(TreeExpansionEvent event) {
			}

			public void treeExpanded(TreeExpansionEvent event) {
				viewer.refresh(event.getElement());
			}});

	}
Comment 1 Michael Permana CLA 2005-07-13 20:29:13 EDT
Created attachment 24711 [details]
the test case to reproduce this bug
Comment 2 Michael Permana CLA 2005-07-20 18:19:57 EDT
workaround is doing this:
viewer.getControl().getDisplay().asyncExec(new Runnable() {
  public void run() {
    viewer.refresh(byUserId);
  }
});
Comment 3 Gail Jakubowski CLA 2005-08-05 10:09:47 EDT
(In reply to comment #2)
Have seen this problem when objects are added to the model, this workaround 
also forces the treeviewer to redraw properly:

viewer.refresh(true);
Object[] objs = viewer.getExpandedElements();
viewer.expandAll();
viewer.collapseAll();
viewer.setExpandedElements(objs);
Comment 4 Chris Beams CLA 2007-05-27 11:47:38 EDT
This bug has been open for quite a while, and while it does have a workaround, it still causes considerable confusion.  I just ran into it while learning how to use ITreeViewerListener, and it took two or three hours of trying different things before I found this issue and thus the workaround.

Perhaps it could be looked into and resolved properly?

The good news is that the workarounds do work, with apparently little negative impact.  I'm using the variant that Michael posted above, but I found the 'byUserId' variable he used in as an argument to refresh() to be confusing.  Here's another snippet that should be more context-complete and general purpose for those freshly running into this problem:

new ITreeViewerListener() {
    public void treeExpanded(final TreeExpansionEvent event) {
        // add items to the node, do whatever you need to do, e.g.:
        MyTreeNode node = (MyTreeNode) event.getElement();
        node.addChild(new MyTreeNode("foo");

        // execute the workaround that refreshes the newly updated node
        viewer.getControl().getDisplay().asyncExec(new Runnable() {
            public void run() {
                viewer.refresh(event.getElement());
            }
        });
    }
};
Comment 5 Boris Bokowski CLA 2007-06-21 16:53:09 EDT
TreeViewer is not designed to allow recursive back-calls like this one. I've released code that checks for this and logs a warning. The snippet from comment #4 is the recommended workaround.
Comment 6 Boris Bokowski CLA 2007-09-18 13:58:57 EDT
Verified that the log entry is produced when expanding an item in the attached view. I20070918-0010.