Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKevin Barnes2006-01-18 20:54:16 +0000
committerKevin Barnes2006-01-18 20:54:16 +0000
commit8915ee74280e60250b975c4d990bab9f79e93ad0 (patch)
tree92fc6696715cec72ed898762231b65df542dda15 /org.eclipse.debug.ui
parentb9c31085fdd20248d0d40a485bb91246e21a7455 (diff)
downloadeclipse.platform.debug-8915ee74280e60250b975c4d990bab9f79e93ad0.tar.gz
eclipse.platform.debug-8915ee74280e60250b975c4d990bab9f79e93ad0.tar.xz
eclipse.platform.debug-8915ee74280e60250b975c4d990bab9f79e93ad0.zip
Bug 123163 - AsynchronousTreeViewer should use SWT.VIRTUAL.
Diffstat (limited to 'org.eclipse.debug.ui')
-rw-r--r--org.eclipse.debug.ui/.options2
-rw-r--r--org.eclipse.debug.ui/META-INF/MANIFEST.MF3
-rw-r--r--org.eclipse.debug.ui/build.properties3
-rw-r--r--org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousTreeViewer.java1812
-rw-r--r--org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousTreeViewerContentManager.java100
-rw-r--r--org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousViewer.java88
-rw-r--r--org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/update/ThreadEventHandler.java10
-rw-r--r--org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/views/variables/VariablesView.java2
-rw-r--r--org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/views/variables/VariablesViewer.java2
-rw-r--r--org.eclipse.debug.ui/ui/org/eclipse/debug/ui/InspectPopupDialog.java2
10 files changed, 1122 insertions, 902 deletions
diff --git a/org.eclipse.debug.ui/.options b/org.eclipse.debug.ui/.options
new file mode 100644
index 000000000..a2688151a
--- /dev/null
+++ b/org.eclipse.debug.ui/.options
@@ -0,0 +1,2 @@
+org.eclipse.debug.ui/debug = false
+org.eclipse.debug.ui/debug/viewer_cache_debug = false
diff --git a/org.eclipse.debug.ui/META-INF/MANIFEST.MF b/org.eclipse.debug.ui/META-INF/MANIFEST.MF
index 3a6a3b5fd..550c37d6c 100644
--- a/org.eclipse.debug.ui/META-INF/MANIFEST.MF
+++ b/org.eclipse.debug.ui/META-INF/MANIFEST.MF
@@ -11,6 +11,8 @@ Export-Package: org.eclipse.debug.internal.ui;x-internal:=true,
org.eclipse.debug.internal.ui.actions.breakpointGroups;x-internal:=true,
org.eclipse.debug.internal.ui.actions.breakpoints,
org.eclipse.debug.internal.ui.actions.context;x-internal:=true,
+ org.eclipse.debug.internal.ui.actions.expressions,
+ org.eclipse.debug.internal.ui.actions.variables,
org.eclipse.debug.internal.ui.contexts;x-internal:=true,
org.eclipse.debug.internal.ui.elements.adapters;x-internal:=true,
org.eclipse.debug.internal.ui.importexport.breakpoints;x-internal:=true,
@@ -49,3 +51,4 @@ Require-Bundle: org.eclipse.core.expressions;bundle-version="[3.2.0,4.0.0)",
org.eclipse.ui.editors;bundle-version="[3.2.0,4.0.0)",
org.eclipse.core.runtime;bundle-version="[3.1.0,4.0.0)"
Eclipse-LazyStart: true
+Bundle-ClassPath: .
diff --git a/org.eclipse.debug.ui/build.properties b/org.eclipse.debug.ui/build.properties
index 10a4ee194..e17542238 100644
--- a/org.eclipse.debug.ui/build.properties
+++ b/org.eclipse.debug.ui/build.properties
@@ -13,7 +13,8 @@ bin.includes = icons/,\
plugin.properties,\
.,\
about.html,\
- META-INF/
+ META-INF/,\
+ .options
source.. = ui/
src.includes = about.html,\
diff --git a/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousTreeViewer.java b/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousTreeViewer.java
index 2207d546b..1e873e685 100644
--- a/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousTreeViewer.java
+++ b/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousTreeViewer.java
@@ -22,8 +22,10 @@ import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.Status;
import org.eclipse.jface.resource.ImageDescriptor;
+import org.eclipse.jface.util.Assert;
import org.eclipse.jface.viewers.ISelection;
import org.eclipse.jface.viewers.StructuredSelection;
+import org.eclipse.jface.viewers.ViewerFilter;
import org.eclipse.jface.viewers.ViewerSorter;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.MouseEvent;
@@ -35,8 +37,11 @@ import org.eclipse.swt.graphics.Font;
import org.eclipse.swt.graphics.FontData;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.graphics.RGB;
+import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Control;
+import org.eclipse.swt.widgets.Event;
+import org.eclipse.swt.widgets.Listener;
import org.eclipse.swt.widgets.Tree;
import org.eclipse.swt.widgets.TreeItem;
import org.eclipse.swt.widgets.Widget;
@@ -60,912 +65,981 @@ import org.eclipse.ui.progress.WorkbenchJob;
*
* @since 3.2
*/
-public class AsynchronousTreeViewer extends AsynchronousViewer {
-
- /**
- * A map of widget to parent widgets used to avoid requirement for parent
- * access in UI thread. Currently used by update objects to detect/cancel
- * updates on updates of children.
- */
- private Map fItemToParentItem = new HashMap();
-
- /**
- * The tree
- */
- private Tree fTree;
-
- /**
- * Collection of tree paths to be expanded. A path is removed from the
- * collection when it is expanded. The entire list is cleared when the
- * input to the viewer changes.
- */
- private List fPendingExpansion = new ArrayList();
-
- /**
- * Creates an asynchronous tree viewer on a newly-created tree control under
- * the given parent. The tree control is created using the SWT style bits
- * <code>MULTI, H_SCROLL, V_SCROLL,</code> and <code>BORDER</code>. The
- * viewer has no input, no content provider, a default label provider, no
- * sorter, and no filters.
- *
- * @param parent the parent control
- */
- public AsynchronousTreeViewer(Composite parent) {
- this(parent, SWT.MULTI | SWT.H_SCROLL | SWT.V_SCROLL);
- }
-
- /**
- * Creates an asynchronous tree viewer on a newly-created tree control under
- * the given parent. The tree control is created using the given SWT style
- * bits. The viewer has no input.
- *
- * @param parent the parent control
- * @param style the SWT style bits used to create the tree.
- */
- public AsynchronousTreeViewer(Composite parent, int style) {
- this(new Tree(parent, style));
- }
-
- /**
- * Creates an asynchronous tree viewer on the given tree control. The viewer
- * has no input, no content provider, a default label provider, no sorter,
- * and no filters.
- *
- * @param tree the tree control
- */
- public AsynchronousTreeViewer(Tree tree) {
- super();
- fTree = tree;
- hookControl(fTree);
- setUseHashlookup(false);
- tree.addTreeListener(new TreeListener() {
- public void treeExpanded(TreeEvent e) {
- ((TreeItem) e.item).setExpanded(true);
- internalRefresh(e.item.getData(), e.item);
- }
+public class AsynchronousTreeViewer extends AsynchronousViewer implements Listener {
- public void treeCollapsed(TreeEvent e) {
- }
- });
- tree.addMouseListener(new MouseListener() {
+ private static final Rectangle NOT_VISIBLE = new Rectangle(0, 0, 0, 0);
- public void mouseUp(MouseEvent e) {
- }
+ /**
+ * A map of widget to parent widgets used to avoid requirement for parent
+ * access in UI thread. Currently used by update objects to detect/cancel
+ * updates on updates of children.
+ */
+ private Map fItemToParentItem = new HashMap();
- public void mouseDown(MouseEvent e) {
- }
+ private AsynchronousTreeViewerContentManager fContentManager = new AsynchronousTreeViewerContentManager();
- public void mouseDoubleClick(MouseEvent e) {
- TreeItem item = ((Tree) e.widget).getItem(new Point(e.x, e.y));
- if (item != null) {
- if (item.getExpanded()) {
- item.setExpanded(false);
- } else {
- item.setExpanded(true);
- internalRefresh(item.getData(), item);
- }
- }
- }
- });
- }
-
- /**
- * Returns the tree control for this viewer.
- *
- * @return the tree control for this viewer
- */
- public Tree getTree() {
- return fTree;
- }
-
- /**
- * Updates whether the given element has children.
- *
- * @param element element to update
- * @param widget widget associated with the element in this viewer's tree
- */
- protected void updateHasChildren(Object element, Widget widget) {
- IAsynchronousTreeContentAdapter adapter = getTreeContentAdapter(element);
- if (adapter != null) {
- IContainerRequestMonitor update = new ContainerRequestMonitor(widget, this);
- schedule(update);
- adapter.isContainer(element, getPresentationContext(), update);
- }
- }
-
- /**
- * Updates the children of the given element.
- *
- * @param parent element of which to update children
- * @param widget widget associated with the element in this viewer's tree
- */
- protected void updateChildren(Object parent, Widget widget) {
- IAsynchronousTreeContentAdapter adapter = getTreeContentAdapter(parent);
- if (adapter != null) {
- IChildrenRequestMonitor update = new ChildrenRequestMonitor(widget, this);
- schedule(update);
- adapter.retrieveChildren(parent, getPresentationContext(), update);
- }
- }
-
- /**
- * Returns the tree element adapter for the given element or
- * <code>null</code> if none.
- *
- * @param element element to retrieve adapter for
- * @return presentation adapter or <code>null</code>
- */
- protected IAsynchronousTreeContentAdapter getTreeContentAdapter(Object element) {
- IAsynchronousTreeContentAdapter adapter = null;
- if (element instanceof IAsynchronousTreeContentAdapter) {
- adapter = (IAsynchronousTreeContentAdapter) element;
- } else if (element instanceof IAdaptable) {
- IAdaptable adaptable = (IAdaptable) element;
- adapter = (IAsynchronousTreeContentAdapter) adaptable.getAdapter(IAsynchronousTreeContentAdapter.class);
- }
- return adapter;
- }
-
- /**
- * Expands all elements in the given tree selection.
- *
- * @param selection
- */
- public synchronized void expand(ISelection selection) {
- if (selection instanceof TreeSelection) {
+ /**
+ * The tree
+ */
+ private Tree fTree;
+
+ /**
+ * Collection of tree paths to be expanded. A path is removed from the
+ * collection when it is expanded. The entire list is cleared when the input
+ * to the viewer changes.
+ */
+ private List fPendingExpansion = new ArrayList();
+
+ /**
+ * Creates an asynchronous tree viewer on a newly-created tree control under
+ * the given parent. The tree control is created using the SWT style bits
+ * <code>MULTI, H_SCROLL, V_SCROLL,</code> and <code>BORDER</code>. The
+ * viewer has no input, no content provider, a default label provider, no
+ * sorter, and no filters.
+ *
+ * @param parent
+ * the parent control
+ */
+ public AsynchronousTreeViewer(Composite parent) {
+ this(parent, SWT.MULTI | SWT.H_SCROLL | SWT.V_SCROLL | SWT.VIRTUAL);
+ }
+
+ /**
+ * Creates an asynchronous tree viewer on a newly-created tree control under
+ * the given parent. The tree control is created using the given SWT style
+ * bits. The viewer has no input.
+ *
+ * @param parent
+ * the parent control
+ * @param style
+ * the SWT style bits used to create the tree.
+ */
+ public AsynchronousTreeViewer(Composite parent, int style) {
+ this(new Tree(parent, style));
+ }
+
+ /**
+ * Creates an asynchronous tree viewer on the given tree control. The viewer
+ * has no input, no content provider, a default label provider, no sorter,
+ * and no filters.
+ *
+ * @param tree
+ * the tree control
+ */
+ public AsynchronousTreeViewer(Tree tree) {
+ super();
+ Assert.isTrue((tree.getStyle() & SWT.VIRTUAL) != 0);
+
+ fTree = tree;
+ hookControl(fTree);
+ setUseHashlookup(false);
+
+ tree.addTreeListener(new TreeListener() {
+ public void treeExpanded(TreeEvent e) {
+ ((TreeItem) e.item).setExpanded(true);
+ internalRefresh(e.item.getData(), e.item);
+ }
+
+ public void treeCollapsed(TreeEvent e) {
+ }
+ });
+
+ tree.addMouseListener(new MouseListener() {
+ public void mouseUp(MouseEvent e) {
+ }
+
+ public void mouseDown(MouseEvent e) {
+ }
+
+ public void mouseDoubleClick(MouseEvent e) {
+ TreeItem item = ((Tree) e.widget).getItem(new Point(e.x, e.y));
+ if (item != null) {
+ if (item.getExpanded()) {
+ item.setExpanded(false);
+ } else {
+ item.setExpanded(true);
+ internalRefresh(item.getData(), item);
+ }
+ }
+ }
+ });
+ tree.addListener(SWT.SetData, this);
+ }
+
+ /**
+ * Returns the tree control for this viewer.
+ *
+ * @return the tree control for this viewer
+ */
+ public Tree getTree() {
+ return fTree;
+ }
+
+ /**
+ * Updates whether the given element has children.
+ *
+ * @param element
+ * element to update
+ * @param widget
+ * widget associated with the element in this viewer's tree
+ */
+ protected void updateHasChildren(Object element, Widget widget) {
+ IAsynchronousTreeContentAdapter adapter = getTreeContentAdapter(element);
+ if (adapter != null) {
+ IContainerRequestMonitor update = new ContainerRequestMonitor(widget, this);
+ schedule(update);
+ adapter.isContainer(element, getPresentationContext(), update);
+ }
+ }
+
+ /**
+ * Updates the children of the given element.
+ *
+ * @param parent
+ * element of which to update children
+ * @param widget
+ * widget associated with the element in this viewer's tree
+ */
+ protected void updateChildren(Object parent, Widget widget) {
+ IAsynchronousTreeContentAdapter adapter = getTreeContentAdapter(parent);
+ if (adapter != null) {
+ IChildrenRequestMonitor update = new ChildrenRequestMonitor(widget, this);
+ schedule(update);
+ adapter.retrieveChildren(parent, getPresentationContext(), update);
+ }
+ }
+
+ /**
+ * Returns the tree element adapter for the given element or
+ * <code>null</code> if none.
+ *
+ * @param element
+ * element to retrieve adapter for
+ * @return presentation adapter or <code>null</code>
+ */
+ protected IAsynchronousTreeContentAdapter getTreeContentAdapter(Object element) {
+ IAsynchronousTreeContentAdapter adapter = null;
+ if (element instanceof IAsynchronousTreeContentAdapter) {
+ adapter = (IAsynchronousTreeContentAdapter) element;
+ } else if (element instanceof IAdaptable) {
+ IAdaptable adaptable = (IAdaptable) element;
+ adapter = (IAsynchronousTreeContentAdapter) adaptable.getAdapter(IAsynchronousTreeContentAdapter.class);
+ }
+ return adapter;
+ }
+
+ /**
+ * Expands all elements in the given tree selection.
+ *
+ * @param selection
+ */
+ public synchronized void expand(ISelection selection) {
+ if (selection instanceof TreeSelection) {
TreePath[] paths = ((TreeSelection) selection).getPaths();
for (int i = 0; i < paths.length; i++) {
fPendingExpansion.add(paths[i]);
}
- if (getControl().getDisplay().getThread() == Thread.currentThread()) {
- attemptExpansion();
- } else {
- WorkbenchJob job = new WorkbenchJob("attemptExpansion") { //$NON-NLS-1$
- public IStatus runInUIThread(IProgressMonitor monitor) {
- attemptExpansion();
- return Status.OK_STATUS;
- }
+ if (getControl().getDisplay().getThread() == Thread.currentThread()) {
+ attemptExpansion();
+ } else {
+ WorkbenchJob job = new WorkbenchJob("attemptExpansion") { //$NON-NLS-1$
+ public IStatus runInUIThread(IProgressMonitor monitor) {
+ attemptExpansion();
+ return Status.OK_STATUS;
+ }
- };
- job.setSystem(true);
- job.schedule();
- }
- }
- }
+ };
+ job.setSystem(true);
+ job.schedule();
+ }
+ }
+ }
- /**
- * Attempts to expand all pending expansions.
- */
- synchronized void attemptExpansion() {
- if (fPendingExpansion != null) {
+ /**
+ * Attempts to expand all pending expansions.
+ */
+ synchronized void attemptExpansion() {
+ if (fPendingExpansion != null) {
for (Iterator i = fPendingExpansion.iterator(); i.hasNext();) {
TreePath path = (TreePath) i.next();
if (attemptExpansion(path)) {
i.remove();
}
}
- }
- }
-
- /**
- * Attempts to expand the given tree path and returns whether the expansion
- * was completed.
- *
- * @param path path to exapand
- * @return whether the expansion was completed
- */
- synchronized boolean attemptExpansion(TreePath path) {
- int segmentCount = path.getSegmentCount();
- for (int j = segmentCount - 1; j >= 0; j--) {
- Object element = path.getSegment(j);
- Widget[] treeItems = getWidgets(element);
- if (treeItems != null) {
- for (int k = 0; k < treeItems.length; k++) {
- if (treeItems[k] instanceof TreeItem) {
- TreeItem treeItem = (TreeItem) treeItems[k];
- TreePath treePath = getTreePath(treeItem);
- if (path.startsWith(treePath)) {
- if (!treeItem.getExpanded() && treeItem.getItemCount() > 0) {
- update(element);
- updateChildren(element, treeItem);
- expand(treeItem);
- if (path.getSegmentCount() == treePath.getSegmentCount()) {
- return true;
- }
- return false;
- }
- }
- }
- }
- }
- }
- return false;
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.jface.viewers.Viewer#getControl()
- */
- public Control getControl() {
- return fTree;
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.jface.viewers.StructuredViewer#unmapAllElements()
- */
- protected synchronized void unmapAllElements() {
- super.unmapAllElements();
- fItemToParentItem.clear();
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.jface.viewers.Viewer#inputChanged(java.lang.Object,
- * java.lang.Object)
- */
- synchronized protected void inputChanged(Object input, Object oldInput) {
+ }
+ }
+
+ /**
+ * Attempts to expand the given tree path and returns whether the expansion
+ * was completed.
+ *
+ * @param path path to expand
+ * @return whether the expansion was completed
+ */
+ synchronized boolean attemptExpansion(TreePath path) {
+ int segmentCount = path.getSegmentCount();
+ for (int j = segmentCount - 1; j >= 0; j--) {
+ Object element = path.getSegment(j);
+ Widget[] treeItems = getWidgets(element);
+ if (treeItems != null) {
+ for (int k = 0; k < treeItems.length; k++) {
+ if (treeItems[k] instanceof TreeItem) {
+ TreeItem treeItem = (TreeItem) treeItems[k];
+ TreePath treePath = getTreePath(treeItem);
+ if (path.startsWith(treePath)) {
+ if (!treeItem.isDisposed() && !treeItem.getExpanded() && treeItem.getItemCount() > 0) {
+ update(element);
+ updateChildren(element, treeItem);
+ expand(treeItem);
+ if (path.getSegmentCount() == treePath.getSegmentCount()) {
+ return true;
+ }
+ return false;
+ }
+ }
+ }
+ }
+ }
+ }
+ return false;
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.jface.viewers.Viewer#getControl()
+ */
+ public Control getControl() {
+ return fTree;
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.jface.viewers.StructuredViewer#unmapAllElements()
+ */
+ protected synchronized void unmapAllElements() {
+ super.unmapAllElements();
+ fItemToParentItem.clear();
+ fContentManager.clearAll();
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.jface.viewers.Viewer#inputChanged(java.lang.Object,
+ * java.lang.Object)
+ */
+ synchronized protected void inputChanged(Object input, Object oldInput) {
fPendingExpansion.clear();
- super.inputChanged(input, oldInput);
- map(input, fTree);
- refresh();
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#map(java.lang.Object,
- * org.eclipse.swt.widgets.Widget)
- */
- protected void map(Object element, Widget item) {
- super.map(element, item);
- if (item instanceof TreeItem) {
- TreeItem treeItem = (TreeItem) item;
- TreeItem parentItem = treeItem.getParentItem();
- if (parentItem != null) {
- fItemToParentItem.put(treeItem, parentItem);
- }
- }
- }
-
- /**
- * Returns all paths to the given element or <code>null</code> if none.
- *
- * @param element
- * @return paths to the given element or <code>null</code>
- */
- public synchronized TreePath[] getTreePaths(Object element) {
- Widget[] widgets = getWidgets(element);
- if (widgets == null) {
- return null;
- }
- TreePath[] paths = new TreePath[widgets.length];
- for (int i = 0; i < widgets.length; i++) {
- List path = new ArrayList();
- path.add(element);
- Widget widget = widgets[i];
- TreeItem parent = null;
- if (widget instanceof TreeItem) {
- TreeItem treeItem = (TreeItem) widget;
- parent = getParentItem(treeItem);
- }
- while (parent != null) {
- Object data = getElement(parent);
- if (data == null) {
- // if the parent is unmapped while attempting selection
- return null;
- }
- path.add(0, data);
- parent = getParentItem(parent);
- }
- if (!path.get(0).equals(getInput())) {
- path.add(0, getInput());
- }
- paths[i] = new TreePath(path.toArray());
- if (widget instanceof TreeItem) {
- paths[i].setTreeItem((TreeItem) widget);
- }
- }
- return paths;
- }
-
- /**
- * Constructs and returns a tree path for the given item. Must be called
- * from the UI thread.
- *
- * @param item item to constuct a path for
- * @return tree path for the item
- */
- protected synchronized TreePath getTreePath(TreeItem item) {
- TreeItem parent = item;
- List path = new ArrayList();
- while (parent != null) {
- path.add(0, parent.getData());
- parent = parent.getParentItem();
- }
- path.add(0, fTree.getData());
- return new TreePath(path.toArray());
- }
-
- /**
- * Called by <code>ContainerRequestMonitor</code> after it is determined
- * if the widget contains children.
- *
- * @param widget
- * @param containsChildren
- */
- synchronized void setIsContainer(Widget widget, boolean containsChildren) {
- TreeItem[] prevChildren = null;
- if (widget instanceof Tree) {
- Tree tree = (Tree) widget;
- prevChildren = tree.getItems();
- } else {
- prevChildren = ((TreeItem) widget).getItems();
- }
- if (containsChildren) {
- if (prevChildren.length == 0) {
- if (widget instanceof Tree) {
- // update root elements in the tree
- updateChildren(widget.getData(), widget);
- } else {
- // insert new dummy node to add +
- newTreeItem(widget, 0);
- if (((TreeItem) widget).getExpanded()) {
- updateChildren(widget.getData(), widget);
- }
- }
- } else {
- if (widget instanceof Tree || ((TreeItem) widget).getExpanded()) {
- // if expanded, update the children
- updateChildren(widget.getData(), widget);
- }
- }
- } else if (prevChildren.length > 0) {
- // dispose previous children
- for (int i = 0; i < prevChildren.length; i++) {
- TreeItem prevChild = prevChildren[i];
- unmap(prevChild.getData(), prevChild);
- prevChild.dispose();
- }
- }
- attemptExpansion();
- }
-
- /**
- * Adds a child at end of parent.
- *
- * @param parent
- * @param child
- */
- synchronized void add(Widget parent, Object child) {
- // refresh vs. add if not expanded
- boolean expanded = true;
- if (parent instanceof TreeItem) {
- expanded = ((TreeItem)parent).getExpanded();
- }
- if (expanded) {
- Object[] objects = filter(new Object[]{child});
- if (objects.length == 1) {
- child = objects[0];
- TreeItem item = newTreeItem(parent);
- map(child, item);
- internalRefresh(child, item);
- }
- } else {
- internalRefresh(parent.getData(), parent);
- }
- attemptExpansion();
- attemptSelection(false);
- }
-
- /**
- * Called by <code>ChildrenRequestMonitor</code> after children have been
- * retrieved.
- *
- * @param widget
- * @param newChildren
- */
- synchronized void setChildren(final Widget widget, final List newChildren) {
- preservingSelection(new Runnable() {
+ super.inputChanged(input, oldInput);
+ map(input, fTree);
+ refresh();
+ }
- public void run() {
- // apply filters
- Object[] children = filter(newChildren.toArray());
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#map(java.lang.Object,
+ * org.eclipse.swt.widgets.Widget)
+ */
+ protected void map(Object element, Widget item) {
+ super.map(element, item);
+ if (item instanceof TreeItem) {
+ TreeItem treeItem = (TreeItem) item;
+ TreeItem parentItem = treeItem.getParentItem();
+ if (parentItem != null) {
+ fItemToParentItem.put(treeItem, parentItem);
+ }
+ }
+ }
- // sort filtered children
- ViewerSorter viewerSorter = getSorter();
- if (viewerSorter != null) {
- viewerSorter.sort(AsynchronousTreeViewer.this, children);
- }
+ /**
+ * Returns all paths to the given element or <code>null</code> if none.
+ *
+ * @param element
+ * @return paths to the given element or <code>null</code>
+ */
+ public synchronized TreePath[] getTreePaths(Object element) {
+ Widget[] widgets = getWidgets(element);
+ if (widgets == null) {
+ return null;
+ }
+ TreePath[] paths = new TreePath[widgets.length];
+ for (int i = 0; i < widgets.length; i++) {
+ List path = new ArrayList();
+ path.add(element);
+ Widget widget = widgets[i];
+ TreeItem parent = null;
+ if (widget instanceof TreeItem) {
+ TreeItem treeItem = (TreeItem) widget;
+ parent = getParentItem(treeItem);
+ }
+ while (parent != null) {
+ Object data = getElement(parent);
+ if (data == null) {
+ // if the parent is unmapped while attempting selection
+ return null;
+ }
+ path.add(0, data);
+ parent = getParentItem(parent);
+ }
+ if (!path.get(0).equals(getInput())) {
+ path.add(0, getInput());
+ }
+ paths[i] = new TreePath(path.toArray());
+ if (widget instanceof TreeItem) {
+ paths[i].setTreeItem((TreeItem) widget);
+ }
+ }
+ return paths;
+ }
- // update tree
- TreeItem[] prevItems = null;
- if (widget instanceof Tree) {
- Tree tree = (Tree) widget;
- prevItems = tree.getItems();
- } else {
- prevItems = ((TreeItem) widget).getItems();
- }
+ /**
+ * Constructs and returns a tree path for the given item. Must be called
+ * from the UI thread.
+ *
+ * @param item
+ * item to constuct a path for
+ * @return tree path for the item
+ */
+ protected synchronized TreePath getTreePath(TreeItem item) {
+ TreeItem parent = item;
+ List path = new ArrayList();
+ while (parent != null && !parent.isDisposed()) {
+ Object parentElement = parent.getData();
+ if (parentElement == null) {
+ return new TreePath(new Object[0]);
+ }
+ path.add(0, parentElement);
+ parent = parent.getParentItem();
+ }
+ path.add(0, fTree.getData());
+ return new TreePath(path.toArray());
+ }
+
+ /**
+ * Called by <code>ContainerRequestMonitor</code> after it is determined
+ * if the widget contains children.
+ *
+ * @param widget
+ * @param containsChildren
+ */
+ synchronized void setIsContainer(Widget widget, boolean containsChildren) {
+ TreeItem[] prevChildren = getItems(widget);
+
+ if (containsChildren) {
+ if (prevChildren.length == 0) {
+ setItemCount(widget, 1);
+ if (widget instanceof Tree) {
+ updateChildren(widget.getData(), widget);
+ } else {
+ TreeItem treeItem = (TreeItem) widget;
+ if (treeItem.getExpanded()) {
+ updateChildren(widget.getData(), widget);
+ }
+ }
+ } else {
+ if (widget instanceof Tree || ((TreeItem) widget).getExpanded()) {
+ // if expanded, update the children
+ updateChildren(widget.getData(), widget);
+ }
+ }
+ } else {
+ for (int i = 0; i < prevChildren.length; i++) {
+ TreeItem item = prevChildren[i];
+ Object element = getElement(item);
+ unmap(element, item);
+ }
+ setItemCount(widget, 0);
+ }
+
+ attemptExpansion();
+ attemptSelection(true);
+ }
+
+ /**
+ * Adds a child at end of parent.
+ *
+ * @param parent
+ * @param child
+ */
+ synchronized void add(Widget parentWidget, Object child) {
+ Object[] children = filter(new Object[] { child });
+ if (children.length == 0) {
+ return; // added element was filtered out.
+ }
+
+ //TODO sort???
+
+ fContentManager.addChildElement(parentWidget, child);
+ int childCount = fContentManager.getChildCount(parentWidget);
+ setItemCount(parentWidget, childCount);
- int index = 0;
- for (; index < children.length; index++) {
- Object kid = children[index];
- TreeItem item = null;
- if (index < prevItems.length) {
- item = prevItems[index];
- Object oldData = item.getData();
- if (kid.equals(oldData)) {
- if (kid != oldData) {
- // if equal but not identical, remap the element
- remap(kid, item);
- }
- } else {
- unmap(oldData, item);
- map(kid, item);
- }
+ attemptExpansion();
+ attemptSelection(false);
+ }
+
+ /**
+ * Called by <code>ChildrenRequestMonitor</code> after children have been
+ * retrieved.
+ *
+ * @param widget
+ * @param newChildren
+ */
+ synchronized void setChildren(final Widget widget, final List newChildren) {
+ // apply filters
+ final Object[] children = filter(newChildren.toArray());
+
+ // sort filtered children
+ ViewerSorter viewerSorter = getSorter();
+ if (viewerSorter != null) {
+ viewerSorter.sort(AsynchronousTreeViewer.this, children);
+ }
+
+ preservingSelection(new Runnable() {
+ public void run() {
+ //unmap all old children
+ TreeItem[] currentChildItems = getItems(widget);
+ for (int i = 0; i < currentChildItems.length; i++) {
+ TreeItem item = currentChildItems[i];
+ if (!item.isDisposed()) {
+ Object oldElement = item.getData();
+ if (oldElement != null) {
+ unmap(oldElement, item);
+ }
+ }
+ }
+
+ //map new children
+ for (int i = 0; i < currentChildItems.length; i++) {
+ TreeItem item = currentChildItems[i];
+ if (i >= children.length) {
+ item.dispose();
+ } else if (isVisible(item)) {
+ map(children[i], item);
+ internalRefresh(children[i], item);
} else {
- item = newTreeItem(widget, index);
- map(kid, item);
+ clear(item);
}
- internalRefresh(kid, item);
- }
- // remove left over old items
- while (index < prevItems.length) {
- TreeItem oldItem = prevItems[index];
- unmap(oldItem.getData(), oldItem);
- oldItem.dispose();
- index++;
}
+
+ // update parent to children map
+ fContentManager.setChildElements(widget, children);
+
+ //set item count
+ Widget theWidget = widget;
+ setItemCount(widget, children.length);
}
-
});
- attemptExpansion();
- attemptSelection(true);
- }
-
- /**
- * Expands the given tree item and all of its parents. Does *not* update
- * elements or retrieve children.
- *
- * @param child item to expand
- */
- private void expand(TreeItem child) {
- if (!child.getExpanded()) {
- child.setExpanded(true);
-
- TreeItem parent = child.getParentItem();
- if (parent != null) {
- expand(parent);
- }
- }
- }
-
- /**
- * Creates a new tree item as a child of the given widget at the specified
- * index.
- *
- * @param parent parent widget - a Tree or TreeItem
- * @param index index at which to create new child
- * @return tree item
- */
- protected TreeItem newTreeItem(Widget parent, int index) {
- if (parent instanceof Tree) {
- return new TreeItem((Tree) parent, SWT.NONE, index);
- }
- return new TreeItem((TreeItem) parent, SWT.NONE, index);
- }
-
- /**
- * Creates a new tree item as a child of the given widget as last.
- *
- * @param parent parent widget - a Tree or TreeItem
- * @return tree item
- */
- protected TreeItem newTreeItem(Widget parent) {
- if (parent instanceof Tree) {
- return new TreeItem((Tree) parent, SWT.NONE);
- }
- return new TreeItem((TreeItem) parent, SWT.NONE);
- }
-
- /**
- * Unmaps the given item, and unmaps and disposes of all children of that
- * item. Does not dispose of the given item.
- *
- * @param kid
- * @param oldItem
- */
- protected synchronized void unmap(Object kid, Widget widget) {
- if (kid == null) {
- // when unmapping a dummy item
- return;
- }
-
- TreeItem[] selection = fTree.getSelection();
- if (selection.length == 1 && isChild(widget, selection[0])) {
- setSelection(null);
- }
-
- super.unmap(kid, widget);
- fItemToParentItem.remove(widget);
- if (widget instanceof TreeItem) {
- TreeItem item = (TreeItem) widget;
- TreeItem[] children = item.getItems();
- for (int i = 0; i < children.length; i++) {
- TreeItem child = children[i];
- unmap(child.getData(), child);
- child.dispose();
- }
- }
- }
+ attemptExpansion();
+ attemptSelection(true);
+ }
- private boolean isChild(Widget parent, TreeItem child) {
- if (child==null) {
- return false;
- } else if (parent == child) {
- return true;
- }
- return isChild(parent, child.getParentItem());
- }
-
- /**
- * Returns the parent item for an item or <code>null</code> if none.
- *
- * @param item item for which parent is requested
- * @return parent item or <code>null</code>
- */
- protected synchronized TreeItem getParentItem(TreeItem item) {
- return (TreeItem) fItemToParentItem.get(item);
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.jface.viewers.StructuredViewer#doFindInputItem(java.lang.Object)
- */
- protected Widget doFindInputItem(Object element) {
- if (element.equals(getInput())) {
- return fTree;
- }
- return null;
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.jface.viewers.StructuredViewer#doFindItem(java.lang.Object)
- */
- protected Widget doFindItem(Object element) {
- Widget[] widgets = getWidgets(element);
- if (widgets != null && widgets.length > 0) {
- return widgets[0];
- }
- return null;
- }
-
- /* (non-Javadoc)
- * @see org.eclipse.debug.internal.ui.viewers.AsynchronousViewer#newSelectionFromWidget()
- */
- protected ISelection newSelectionFromWidget() {
- Control control = getControl();
- if (control == null || control.isDisposed()) {
- return StructuredSelection.EMPTY;
- }
- List list = getSelectionFromWidget();
- return new TreeSelection((TreePath[]) list.toArray());
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.jface.viewers.StructuredViewer#getSelectionFromWidget()
- */
- protected synchronized List getSelectionFromWidget() {
- TreeItem[] selection = fTree.getSelection();
- TreePath[] paths = new TreePath[selection.length];
- for (int i = 0; i < selection.length; i++) {
- paths[i] = getTreePath(selection[i]);
- }
- return Arrays.asList(paths);
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#internalRefresh(java.lang.Object,
- * org.eclipse.swt.widgets.Widget)
- */
- protected synchronized void internalRefresh(Object element, Widget item) {
- super.internalRefresh(element, item);
- updateHasChildren(element, item);
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.jface.viewers.StructuredViewer#reveal(java.lang.Object)
- */
- public void reveal(Object element) {
- Widget[] widgets = getWidgets(element);
- if (widgets != null && widgets.length > 0) {
- // TODO: only reveals the first occurrence - should we reveal all?
- TreeItem item = (TreeItem) widgets[0];
- Tree tree = (Tree) getControl();
- tree.showItem(item);
- }
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#doAttemptSelectionToWidget(org.eclipse.jface.viewers.ISelection,
- * boolean)
- */
- protected synchronized ISelection doAttemptSelectionToWidget(ISelection selection, boolean reveal) {
- List remaining = new ArrayList();
- if (!selection.isEmpty()) {
- List toSelect = new ArrayList();
- List theElements = new ArrayList();
- TreeSelection treeSelection = (TreeSelection) selection;
- TreePath[] paths = treeSelection.getPaths();
- for (int i = 0; i < paths.length; i++) {
- TreePath path = paths[i];
- if (path == null) {
- continue;
- }
- TreePath[] treePaths = getTreePaths(path.getLastSegment());
- boolean selected = false;
- if (treePaths != null) {
- for (int j = 0; j < treePaths.length; j++) {
- TreePath existingPath = treePaths[j];
- if (existingPath.equals(path)) {
- TreeItem treeItem = existingPath.getTreeItem();
- toSelect.add(treeItem);
- theElements.add(path.getLastSegment());
- selected = true;
- break;
- }
- }
- }
- if (!selected) {
- remaining.add(path);
- }
- }
- if (!toSelect.isEmpty()) {
- final TreeItem[] items = (TreeItem[]) toSelect.toArray(new TreeItem[toSelect.size()]);
- // TODO: hack to ensure selection contains 'selected' element
- // instead of 'equivalent' element. Handles synch problems
- // between
- // set selection & refresh
- for (int i = 0; i < items.length; i++) {
- TreeItem item = items[i];
- Object element = theElements.get(i);
- if (item.getData() != element) {
- remap(element, item);
- }
- }
- fTree.setSelection(items);
- if (reveal) {
- fTree.showItem(items[0]);
- }
- }
- } else {
- fTree.setSelection(new TreeItem[0]);
- }
- return new TreeSelection((TreePath[]) remaining.toArray(new TreePath[remaining.size()]));
- }
-
- /**
- * Collapses all items in the tree.
- */
- public void collapseAll() {
- TreeItem[] items = fTree.getItems();
- for (int i = 0; i < items.length; i++) {
- TreeItem item = items[i];
- if (item.getExpanded())
- collapse(item);
- }
- }
-
- /**
- * Collaspes the given item and all of its children items.
- *
- * @param item item to collapose recursively
- */
- protected void collapse(TreeItem item) {
- TreeItem[] items = item.getItems();
- for (int i = 0; i < items.length; i++) {
- TreeItem child = items[i];
- if (child.getExpanded()) {
- collapse(child);
- }
- }
- item.setExpanded(false);
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#setColor(org.eclipse.swt.widgets.Widget,
- * org.eclipse.swt.graphics.RGB, org.eclipse.swt.graphics.RGB)
- */
- void setColors(Widget widget, RGB[] foregrounds, RGB[] backgrounds) {
- if (widget instanceof TreeItem) {
- TreeItem item = (TreeItem) widget;
- Color[] fgs = getColor(foregrounds);
- Color[] bgs = getColor(backgrounds);
- for (int i = 0; i < bgs.length; i++) {
- item.setForeground(i, fgs[i]);
- item.setBackground(i, bgs[i]);
- }
- }
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#setFont(org.eclipse.swt.widgets.Widget,
- * org.eclipse.swt.graphics.FontData)
- */
- void setFonts(Widget widget, FontData[] fontData) {
- if (widget instanceof TreeItem) {
- TreeItem item = (TreeItem) widget;
- Font[] fonts = getFonts(fontData);
- for (int i = 0; i < fonts.length; i++) {
- item.setFont(i, fonts[i]);
+ protected void doUpdateItem(Widget item, Object element, boolean fullMap) {
+ super.doUpdateItem(item, element, fullMap);
+ updateHasChildren(element, item);
+ }
+
+ private void setItemCount(Widget widget, int itemCount) {
+ if (widget == fTree) {
+ fTree.setItemCount(itemCount);
+ } else {
+ ((TreeItem) widget).setItemCount(itemCount);
+ }
+ }
+
+ private TreeItem[] getItems(Widget widget) {
+ if (widget instanceof TreeItem) {
+ return ((TreeItem) widget).getItems();
+ } else {
+ return fTree.getItems();
+ }
+ }
+
+ public synchronized void handleEvent(final Event event) {
+ preservingSelection(new Runnable() {
+ public void run() {
+ TreeItem item = (TreeItem) event.item;
+ Widget parentItem = item.getParentItem();
+ int index = 0;
+ if (parentItem != null) {
+ index = ((TreeItem) parentItem).indexOf(item);
+ } else {
+ parentItem = fTree;
+ index = fTree.indexOf(item);
+ }
+
+ Object element = fContentManager.getChildElement(parentItem, index);
+ if (element != null) {
+ map(element, item);
+ internalRefresh(element, true);
+ }
+ }
+ });
+ }
+
+ /**
+ * Expands the given tree item and all of its parents. Does *not* update
+ * elements or retrieve children.
+ *
+ * @param child
+ * item to expand
+ */
+ private void expand(TreeItem child) {
+ if (!child.getExpanded()) {
+ child.setExpanded(true);
+
+ TreeItem parent = child.getParentItem();
+ if (parent != null) {
+ expand(parent);
+ }
+ }
+ }
+
+ /**
+ * Unmaps the given item, and unmaps and disposes of all children of that
+ * item. Does not dispose of the given item.
+ *
+ * @param kid
+ * @param oldItem
+ */
+ protected synchronized void unmap(Object element, Widget widget) {
+ TreeItem[] selection = fTree.getSelection();
+ if (selection.length == 1 && isChild(widget, selection[0])) {
+ setSelection(null);
+ }
+
+ TreeItem[] items = getItems(widget);
+ for (int i = 0; i < items.length; i++) {
+ TreeItem childItem = items[i];
+ Object childElement = getElement(childItem);
+ if (childElement != null) {
+ unmap(childElement, childItem);
}
}
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#getParent(org.eclipse.swt.widgets.Widget)
- */
- protected Widget getParent(Widget widget) {
- return (Widget) fItemToParentItem.get(widget);
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#acceptsSelection(org.eclipse.jface.viewers.ISelection)
- */
- protected boolean acceptsSelection(ISelection selection) {
- return selection instanceof TreeSelection;
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#getEmptySelection()
- */
- protected ISelection getEmptySelection() {
- return new TreeSelection(new TreePath[0]);
- }
-
- /**
- * Adds the item specified by the given tree path to this tree.
- * Can be called in a non-UI thread.
- *
- * @param treePath
- */
- public synchronized void add(TreePath treePath) {
- int parentIndex = treePath.getSegmentCount() - 2;
- if (parentIndex >= 0) {
- // find the paths to the parent, if it's present
- Object parent = treePath.getSegment(parentIndex);
- TreePath[] paths = getTreePaths(parent);
- if (paths != null) {
- // find the right path
- for (int i = 0; i < paths.length; i++) {
- TreePath path = paths[i];
- if (treePath.startsWith(path)) {
- Widget widget = path.getTreeItem();
- if (widget == null) {
- widget = getTree();
- }
- AddRequestMonitor addRequest = new AddRequestMonitor(widget, treePath, this);
- schedule(addRequest);
- addRequest.done();
- return;
- }
- }
- }
- // refresh the leaf parent, if any
- for (int i = parentIndex -1; i >= 0; i++) {
- parent = treePath.getSegment(i);
- paths = getTreePaths(parent);
- if (paths != null) {
- for (int j = 0; j < paths.length; j++) {
- TreePath path = paths[j];
- if (treePath.startsWith(path)) {
- Widget widget = path.getTreeItem();
- if (widget == null) {
- widget = getTree();
- }
- internalRefresh(parent, widget);
- return;
- }
- }
- }
- }
+
+ super.unmap(element, widget);
+
+ fItemToParentItem.remove(widget);
+ fContentManager.remove(widget);
+ }
+
+ private void clear(Widget widget) {
+ if (widget instanceof TreeItem) {
+ TreeItem item = (TreeItem) widget;
+ item.clearAll(true);
+ } else {
+ fTree.clearAll(true);
+ }
+ }
+
+ private boolean isVisible(TreeItem item) {
+ Rectangle itemBounds = item.getBounds();
+ return !NOT_VISIBLE.equals(itemBounds);
+ }
+
+ private boolean isChild(Widget parent, TreeItem child) {
+ if (child == null) {
+ return false;
+ } else if (parent == child) {
+ return true;
+ }
+ return isChild(parent, child.getParentItem());
+ }
+
+ /**
+ * Returns the parent item for an item or <code>null</code> if none.
+ *
+ * @param item
+ * item for which parent is requested
+ * @return parent item or <code>null</code>
+ */
+ protected synchronized TreeItem getParentItem(TreeItem item) {
+ return (TreeItem) fItemToParentItem.get(item);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.jface.viewers.StructuredViewer#doFindInputItem(java.lang.Object)
+ */
+ protected Widget doFindInputItem(Object element) {
+ if (element.equals(getInput())) {
+ return fTree;
+ }
+ return null;
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.jface.viewers.StructuredViewer#doFindItem(java.lang.Object)
+ */
+ protected Widget doFindItem(Object element) {
+ Widget[] widgets = getWidgets(element);
+ if (widgets != null && widgets.length > 0) {
+ return widgets[0];
+ }
+ return null;
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.debug.internal.ui.viewers.AsynchronousViewer#newSelectionFromWidget()
+ */
+ protected ISelection newSelectionFromWidget() {
+ Control control = getControl();
+ if (control == null || control.isDisposed()) {
+ return StructuredSelection.EMPTY;
+ }
+ List list = getSelectionFromWidget();
+ return new TreeSelection((TreePath[]) list.toArray());
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.jface.viewers.StructuredViewer#getSelectionFromWidget()
+ */
+ protected synchronized List getSelectionFromWidget() {
+ TreeItem[] selection = fTree.getSelection();
+ TreePath[] paths = new TreePath[selection.length];
+ for (int i = 0; i < selection.length; i++) {
+ paths[i] = getTreePath(selection[i]);
+ }
+ return Arrays.asList(paths);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#internalRefresh(java.lang.Object,
+ * org.eclipse.swt.widgets.Widget)
+ */
+ protected synchronized void internalRefresh(Object element, Widget item) {
+ super.internalRefresh(element, item);
+ updateHasChildren(element, item);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.jface.viewers.StructuredViewer#reveal(java.lang.Object)
+ */
+ public void reveal(Object element) {
+ Widget[] widgets = getWidgets(element);
+ if (widgets != null && widgets.length > 0) {
+ // TODO: only reveals the first occurrence - should we reveal all?
+ TreeItem item = (TreeItem) widgets[0];
+ Tree tree = (Tree) getControl();
+ tree.showItem(item);
+ }
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#doAttemptSelectionToWidget(org.eclipse.jface.viewers.ISelection,
+ * boolean)
+ */
+ protected synchronized ISelection doAttemptSelectionToWidget(ISelection selection, boolean reveal) {
+ List remaining = new ArrayList();
+ if (!selection.isEmpty()) {
+ List toSelect = new ArrayList();
+ List theElements = new ArrayList();
+ TreeSelection treeSelection = (TreeSelection) selection;
+ TreePath[] paths = treeSelection.getPaths();
+ for (int i = 0; i < paths.length; i++) {
+ TreePath path = paths[i];
+ if (path == null) {
+ continue;
+ }
+ TreePath[] treePaths = getTreePaths(path.getLastSegment());
+ boolean selected = false;
+ if (treePaths != null) {
+ for (int j = 0; j < treePaths.length; j++) {
+ TreePath existingPath = treePaths[j];
+ if (existingPath.equals(path)) {
+ TreeItem treeItem = existingPath.getTreeItem();
+ if (!treeItem.isDisposed()) {
+ toSelect.add(treeItem);
+ theElements.add(path.getLastSegment());
+ selected = true;
+ break;
+ }
+ }
+ }
+ }
+ if (!selected) {
+ remaining.add(path);
+ }
+ }
+ if (!toSelect.isEmpty()) {
+ final TreeItem[] items = (TreeItem[]) toSelect.toArray(new TreeItem[toSelect.size()]);
+ // TODO: hack to ensure selection contains 'selected' element
+ // instead of 'equivalent' element. Handles synch problems
+ // between
+ // set selection & refresh
+ for (int i = 0; i < items.length; i++) {
+ TreeItem item = items[i];
+ Object element = theElements.get(i);
+ if (!item.isDisposed() && item.getData() != element) {
+ remap(element, item);
+ }
+ }
+ fTree.setSelection(items);
+ if (reveal) {
+ fTree.showItem(items[0]);
+ }
+ }
+ } else {
+ fTree.setSelection(new TreeItem[0]);
+ }
+ return new TreeSelection((TreePath[]) remaining.toArray(new TreePath[remaining.size()]));
+ }
+
+ /**
+ * Collapses all items in the tree.
+ */
+ public void collapseAll() {
+ TreeItem[] items = fTree.getItems();
+ for (int i = 0; i < items.length; i++) {
+ TreeItem item = items[i];
+ if (item.getExpanded())
+ collapse(item);
+ }
+ }
+
+ /**
+ * Collaspes the given item and all of its children items.
+ *
+ * @param item
+ * item to collapose recursively
+ */
+ protected void collapse(TreeItem item) {
+ TreeItem[] items = item.getItems();
+ for (int i = 0; i < items.length; i++) {
+ TreeItem child = items[i];
+ if (child.getExpanded()) {
+ collapse(child);
+ }
+ }
+ item.setExpanded(false);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#setColor(org.eclipse.swt.widgets.Widget,
+ * org.eclipse.swt.graphics.RGB, org.eclipse.swt.graphics.RGB)
+ */
+ void setColors(Widget widget, RGB[] foregrounds, RGB[] backgrounds) {
+ if (widget instanceof TreeItem) {
+ TreeItem item = (TreeItem) widget;
+ Color[] fgs = getColor(foregrounds);
+ Color[] bgs = getColor(backgrounds);
+ for (int i = 0; i < bgs.length; i++) {
+ item.setForeground(i, fgs[i]);
+ item.setBackground(i, bgs[i]);
+ }
+ }
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#setFont(org.eclipse.swt.widgets.Widget,
+ * org.eclipse.swt.graphics.FontData)
+ */
+ void setFonts(Widget widget, FontData[] fontData) {
+ if (widget instanceof TreeItem) {
+ TreeItem item = (TreeItem) widget;
+ Font[] fonts = getFonts(fontData);
+ for (int i = 0; i < fonts.length; i++) {
+ item.setFont(i, fonts[i]);
+ }
+ }
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#getParent(org.eclipse.swt.widgets.Widget)
+ */
+ protected Widget getParent(Widget widget) {
+ return (Widget) fItemToParentItem.get(widget);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#acceptsSelection(org.eclipse.jface.viewers.ISelection)
+ */
+ protected boolean acceptsSelection(ISelection selection) {
+ return selection instanceof TreeSelection;
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.debug.ui.viewers.AsynchronousViewer#getEmptySelection()
+ */
+ protected ISelection getEmptySelection() {
+ return new TreeSelection(new TreePath[0]);
+ }
+
+ /**
+ * Adds the item specified by the given tree path to this tree. Can be
+ * called in a non-UI thread.
+ *
+ * @param treePath
+ */
+ public synchronized void add(TreePath treePath) {
+ Object element = treePath.getLastSegment();
+ int parentIndex = treePath.getSegmentCount() - 2;
+ Object parentElement = getInput();
+ if (parentIndex > 0) {
+ parentElement = treePath.getSegment(parentIndex);
+ }
+
+ ViewerFilter[] filters = getFilters();
+ for (int i = 0; i < filters.length; i++) {
+ ViewerFilter filter = filters[i];
+ boolean select = filter.select(this, parentElement, element);
+ if (!select) {
+ return; // added item filtered out.
+ }
}
- }
-
-
- /**
- * Removes the item specified in the given tree path from this tree.
- * Can be called in a non-UI thread.
- *
- * @param treePath
- */
- public synchronized void remove(TreePath treePath) {
+
+ //TODO Sorting... if there's a sorter, it needs to be consulted
+
+ if (parentIndex >= 0) {
+ // find the paths to the parent, if it's present
+ Object parent = treePath.getSegment(parentIndex);
+ TreePath[] paths = getTreePaths(parent);
+ if (paths != null) {
+ // find the right path
+ for (int i = 0; i < paths.length; i++) {
+ TreePath path = paths[i];
+ if (treePath.startsWith(path)) {
+ Widget widget = path.getTreeItem();
+ if (widget == null) {
+ widget = getTree();
+ }
+ AddRequestMonitor addRequest = new AddRequestMonitor(widget, treePath, this);
+ schedule(addRequest);
+ addRequest.done();
+ return;
+ }
+ }
+ }
+ // refresh the leaf parent, if any
+ for (int i = parentIndex - 1; i >= 0; i++) {
+ parent = treePath.getSegment(i);
+ paths = getTreePaths(parent);
+ if (paths != null) {
+ for (int j = 0; j < paths.length; j++) {
+ TreePath path = paths[j];
+ if (treePath.startsWith(path)) {
+ Widget widget = path.getTreeItem();
+ if (widget == null) {
+ widget = getTree();
+ }
+ internalRefresh(parent, widget);
+ return;
+ }
+ }
+ }
+ }
+ }
+ }
+
+ /**
+ * Removes the item specified in the given tree path from this tree. Can be
+ * called in a non-UI thread.
+ *
+ * @param treePath
+ */
+ public synchronized void remove(TreePath treePath) {
for (Iterator i = fPendingExpansion.iterator(); i.hasNext();) {
TreePath expansionPath = (TreePath) i.next();
if (expansionPath.startsWith(treePath)) {
i.remove();
}
}
- if (treePath.getSegmentCount() > 1) {
- // find the paths to the element, if it's present
- Object element = treePath.getLastSegment();
- TreePath[] paths = getTreePaths(element);
- if (paths != null) {
- // find the right path
- for (int i = 0; i < paths.length; i++) {
- TreePath path = paths[i];
- if (treePath.equals(path)) {
- TreeItem item = path.getTreeItem();
- RemoveRequestMonitor request = new RemoveRequestMonitor(item, treePath, this);
- schedule(request);
- request.done();
- return;
- }
- }
- }
- // refresh the parent, if present
- if (treePath.getSegmentCount() >= 2) {
- element = treePath.getSegment(treePath.getSegmentCount() - 2);
- paths = getTreePaths(element);
- if (paths != null) {
- // find the right path
- for (int i = 0; i < paths.length; i++) {
- TreePath path = paths[i];
- if (treePath.startsWith(path)) {
- Widget widget = path.getTreeItem();
- if (widget == null) {
- widget = getTree();
- }
- internalRefresh(element, widget);
- return;
- }
- }
- }
- }
- }
- }
+ if (treePath.getSegmentCount() > 1) {
+ // find the paths to the element, if it's present
+ Object element = treePath.getLastSegment();
+ TreePath[] paths = getTreePaths(element);
+ if (paths != null) {
+ // find the right path
+ for (int i = 0; i < paths.length; i++) {
+ TreePath path = paths[i];
+ if (treePath.equals(path)) {
+ TreeItem item = path.getTreeItem();
+ RemoveRequestMonitor request = new RemoveRequestMonitor(item, treePath, this);
+ schedule(request);
+ request.done();
+ return;
+ }
+ }
+ }
+ // refresh the parent, if present
+ if (treePath.getSegmentCount() >= 2) {
+ element = treePath.getSegment(treePath.getSegmentCount() - 2);
+ paths = getTreePaths(element);
+ if (paths != null) {
+ // find the right path
+ for (int i = 0; i < paths.length; i++) {
+ TreePath path = paths[i];
+ if (treePath.startsWith(path)) {
+ Widget widget = path.getTreeItem();
+ if (widget == null) {
+ widget = getTree();
+ }
+ internalRefresh(element, widget);
+ return;
+ }
+ }
+ }
+ }
+ }
+ }
- synchronized void remove(final Widget widget) {
- preservingSelection(new Runnable() {
- public void run() {
- Object element = widget.getData();
- unmap(element, widget);
- widget.dispose();
- }
- });
- }
-
- void setLabels(Widget widget, String[] text, ImageDescriptor[] image) {
- if (widget instanceof TreeItem) {
- TreeItem item = (TreeItem) widget;
- item.setText(text);
- item.setImage(getImages(image));
- }
- }
+ synchronized void remove(final Widget widget) {
+ preservingSelection(new Runnable() {
+ public void run() {
+ if (!(widget instanceof TreeItem)) {
+ return;
+ }
+
+ fContentManager.remove(widget);
+ TreeItem item = (TreeItem) widget;
+ Widget parentWidget = item.getParentItem();
+ if (parentWidget == null)
+ parentWidget = fTree;
+
+ Object element = getElement(widget);
+ if (element != null)
+ unmap(element, widget);
+
+ item.dispose();
+ setItemCount(parentWidget, fContentManager.getChildCount(parentWidget));
+ }
+ });
+ }
+
+ synchronized void setLabels(Widget widget, String[] text, ImageDescriptor[] image) {
+ if (widget instanceof TreeItem) {
+ TreeItem item = (TreeItem) widget;
+ if (!item.isDisposed()) {
+ item.setText(text);
+ item.setImage(getImages(image));
+ }
+ }
+ }
}
diff --git a/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousTreeViewerContentManager.java b/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousTreeViewerContentManager.java
new file mode 100644
index 000000000..fda668fe3
--- /dev/null
+++ b/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousTreeViewerContentManager.java
@@ -0,0 +1,100 @@
+/*******************************************************************************
+ * Copyright (c) 2005 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * IBM Corporation - initial API and implementation
+ *******************************************************************************/
+
+package org.eclipse.debug.internal.ui.viewers;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.eclipse.swt.widgets.TreeItem;
+import org.eclipse.swt.widgets.Widget;
+
+public class AsynchronousTreeViewerContentManager {
+
+ private static final Object[] EMPTY = new Object[0];
+ private Map fWidgetToChildElements = new HashMap();
+
+ public void clearAll() {
+ fWidgetToChildElements.clear();
+ }
+
+ public Object[] getChildElements(Widget parentWidget) {
+ Object[] childElements = (Object[]) fWidgetToChildElements.get(parentWidget);
+ if (childElements == null)
+ childElements = EMPTY;
+ return childElements;
+ }
+
+ public void addChildElement(Widget parentWidget, Object child) {
+ Object[] originalChildren = getChildElements(parentWidget);
+ Object[] newChildren = new Object[originalChildren.length + 1];
+ System.arraycopy(originalChildren, 0, newChildren, 0, originalChildren.length);
+ newChildren[originalChildren.length] = child;
+ fWidgetToChildElements.put(parentWidget, newChildren);
+ }
+
+ public int getChildCount(Widget parentWidget) {
+ return getChildElements(parentWidget).length;
+ }
+
+ public void setChildElements(Widget parentWidget, Object[] children) {
+ fWidgetToChildElements.put(parentWidget, children);
+ }
+
+ public Object getChildElement(Widget parentWidget, int index) {
+ Object[] childElements = getChildElements(parentWidget);
+ if (index < childElements.length)
+ return childElements[index];
+ else
+ return null;
+ }
+
+ public void remove(Widget widget) {
+ if (widget instanceof TreeItem) {
+ TreeItem treeItem = (TreeItem) widget;
+ removeChildren(treeItem);
+
+ Object data = treeItem.getData();
+ if (data != null) {
+ Widget parentWidget = treeItem.getParentItem();
+ if (parentWidget == null)
+ parentWidget = treeItem.getParent();
+
+ removeFromParent(parentWidget, data);
+ }
+ } else {
+ fWidgetToChildElements.clear();
+ }
+ }
+
+ private void removeFromParent(Widget parentWidget, Object data) {
+ Object[] childElements = getChildElements(parentWidget);
+ for (int i = 0; i < childElements.length; i++) {
+ Object object = childElements[i];
+ if (data.equals(object)) {
+ Object[] newChildren = new Object[childElements.length - 1];
+ System.arraycopy(childElements, 0, newChildren, 0, i);
+ System.arraycopy(childElements, i + 1, newChildren, i, newChildren.length - i);
+ fWidgetToChildElements.put(parentWidget, newChildren);
+ return;
+ }
+ }
+ }
+
+ private void removeChildren(TreeItem item) {
+ TreeItem[] items = item.getItems();
+ for (int i = 0; i < items.length; i++) {
+ removeChildren(items[i]);
+ }
+
+ fWidgetToChildElements.remove(item);
+ }
+}
diff --git a/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousViewer.java b/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousViewer.java
index f2e48b95b..c6a9246aa 100644
--- a/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousViewer.java
+++ b/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/AsynchronousViewer.java
@@ -63,6 +63,8 @@ import org.eclipse.ui.progress.WorkbenchJob;
*/
public abstract class AsynchronousViewer extends StructuredViewer {
+ public static boolean DEBUG_CACHE;
+
/**
* A map of elements to associated tree items or tree
*/
@@ -344,6 +346,11 @@ public abstract class AsynchronousViewer extends StructuredViewer {
fElementsToWidgets.clear();
fWidgetsToElements.clear();
disposeAllModelProxies();
+ if (DEBUG_CACHE) {
+ System.out.println("unmapped all elements"); //$NON-NLS-1$
+ System.out.println("\tfWidgetsToElements.size() " + fWidgetsToElements.size()); //$NON-NLS-1$
+ System.out.println("\tfElementsToWidgets.size() " + fElementsToWidgets.size()); //$NON-NLS-1$
+ }
}
/**
@@ -390,7 +397,13 @@ public abstract class AsynchronousViewer extends StructuredViewer {
fElementsToWidgets.put(element, items);
}
installModelProxy(element);
- }
+
+ if (DEBUG_CACHE) {
+ System.out.println("mapped " + element + " to " + item + "(hashcode: " + item.hashCode()+")"); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$
+ System.out.println("\tfWidgetsToElements.size() " + fWidgetsToElements.size()); //$NON-NLS-1$
+ System.out.println("\tfElementsToWidgets.size() " + fElementsToWidgets.size()); //$NON-NLS-1$
+ }
+ }
/**
* Updates the cached information that maps the given element to the
@@ -402,9 +415,23 @@ public abstract class AsynchronousViewer extends StructuredViewer {
*/
protected void remap(Object element, Widget item) {
item.setData(element);
+ installModelProxy(element);
fWidgetsToElements.put(item, element);
- Object widgets = fElementsToWidgets.remove(element);
- fElementsToWidgets.put(element, widgets);
+ Widget[] widgets = (Widget[]) fElementsToWidgets.remove(element);
+ if (widgets == null) {
+ fElementsToWidgets.put(element, new Widget[] {item});
+ } else {
+ Widget[] newArray = new Widget[widgets.length + 1];
+ System.arraycopy(widgets, 0, newArray, 0, widgets.length);
+ newArray[widgets.length] = item;
+ fElementsToWidgets.put(element, newArray);
+ }
+
+ if (DEBUG_CACHE) {
+ System.out.println("remapped " + element + " to " + item + "(hashcode: " + item.hashCode()+")"); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$
+ System.out.println("\tfWidgetsToElements.size() " + fWidgetsToElements.size()); //$NON-NLS-1$
+ System.out.println("\tfElementsToWidgets.size() " + fElementsToWidgets.size()); //$NON-NLS-1$
+ }
}
public IUpdatePolicy createUpdatePolicy() {
@@ -478,9 +505,8 @@ public abstract class AsynchronousViewer extends StructuredViewer {
if (kid == null) {
// when unmapping a dummy item
return;
- }
+ }
Widget[] widgets = getWidgets(kid);
- fWidgetsToElements.remove(widget);
if (widgets != null) {
for (int i = 0; i < widgets.length; i++) {
Widget item = widgets[i];
@@ -500,6 +526,14 @@ public abstract class AsynchronousViewer extends StructuredViewer {
}
}
}
+
+ fWidgetsToElements.remove(widget);
+
+ if (DEBUG_CACHE) {
+ System.out.println("unmapped " + kid + " to " + widget + "(hashcode: " + widget.hashCode()+")"); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$
+ System.out.println("\tfWidgetsToElements.size() " + fWidgetsToElements.size()); //$NON-NLS-1$
+ System.out.println("\tfElementsToWidgets.size() " + fElementsToWidgets.size()); //$NON-NLS-1$
+ }
}
Image[] getImages(ImageDescriptor[] descriptors) {
@@ -669,7 +703,9 @@ public abstract class AsynchronousViewer extends StructuredViewer {
if (!force && !overrideSelection(fCurrentSelection, selection)) {
return;
}
+
fPendingSelection = selection;
+
if (getControl().getDisplay().getThread() == Thread.currentThread()) {
attemptSelection(reveal);
} else {
@@ -783,21 +819,25 @@ public abstract class AsynchronousViewer extends StructuredViewer {
*
* @param reveal whether to reveal the selection
*/
- protected synchronized void attemptSelection(boolean reveal) {
- if (fPendingSelection != null) {
- ISelection remaining = doAttemptSelectionToWidget(fPendingSelection, reveal);
- if (!fPendingSelection.equals(remaining) ||
- (fPendingSelection.isEmpty() && fPendingSelection.equals(remaining))) {
- fPendingSelection = remaining;
- if (fPendingSelection.isEmpty()) {
- fPendingSelection = null;
- }
- ISelection currentSelection = newSelectionFromWidget();
- if (isSuppressEqualSelections() && currentSelection.equals(fCurrentSelection)) {
- return;
- }
- updateSelection(currentSelection);
- }
+ protected void attemptSelection(boolean reveal) {
+ if (fPendingSelection != null && !fPendingSelection.isEmpty()) {
+ ISelection currentSelection = null;
+
+ synchronized (this) {
+ ISelection remaining = doAttemptSelectionToWidget(fPendingSelection, reveal);
+
+ if (!fPendingSelection.equals(remaining) || (fPendingSelection.isEmpty() && fPendingSelection.equals(remaining))) {
+ fPendingSelection = remaining;
+ currentSelection = newSelectionFromWidget();
+ if (isSuppressEqualSelections() && currentSelection.equals(fCurrentSelection)) {
+ return;
+ }
+ }
+ }
+
+ if (currentSelection != null) {
+ updateSelection(currentSelection);
+ }
}
}
@@ -805,11 +845,11 @@ public abstract class AsynchronousViewer extends StructuredViewer {
* Controls whether selection change notification is sent even when
* successive selections are equal.
*
- * TODO: what we really want is to fire selection change on ACTIVATE
- * model change, even when selection is the same.
+ * TODO: what we really want is to fire selection change on ACTIVATE model
+ * change, even when selection is the same.
*
* @return whether to suppress change notification for equal successive
- * selections
+ * selections
*/
protected boolean isSuppressEqualSelections() {
return true;
@@ -871,7 +911,7 @@ public abstract class AsynchronousViewer extends StructuredViewer {
* @see org.eclipse.jface.viewers.StructuredViewer#preservingSelection(java.lang.Runnable)
*/
protected synchronized void preservingSelection(Runnable updateCode) {
- if (fPendingSelection == null) {
+ if (fPendingSelection == null || fPendingSelection.isEmpty()) {
ISelection oldSelection = null;
try {
// preserve selection
diff --git a/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/update/ThreadEventHandler.java b/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/update/ThreadEventHandler.java
index 4d7a9a694..a0a40589a 100644
--- a/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/update/ThreadEventHandler.java
+++ b/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/viewers/update/ThreadEventHandler.java
@@ -61,7 +61,7 @@ public class ThreadEventHandler extends DebugEventHandler {
IThread thread = (IThread) event.getSource();
if (event.isEvaluation()) {
ModelDelta delta = buildRootDelta();
- ModelDelta node = addPathToThraed(delta, thread);
+ ModelDelta node = addPathToThread(delta, thread);
try {
IStackFrame frame = thread.getTopStackFrame();
if (frame != null) {
@@ -121,14 +121,14 @@ public class ThreadEventHandler extends DebugEventHandler {
return new ModelDelta(DebugPlugin.getDefault().getLaunchManager(), IModelDelta.NOCHANGE);
}
- private ModelDelta addPathToThraed(ModelDelta delta, IThread thread) {
+ private ModelDelta addPathToThread(ModelDelta delta, IThread thread) {
delta = delta.addNode(thread.getLaunch(), IModelDelta.NOCHANGE);
- return delta.addNode(thread.getDebugTarget(), IModelDelta.NOCHANGE);
+ return delta.addNode(thread.getDebugTarget(), IModelDelta.EXPAND);
}
private void fireDeltaAndClearTopFrame(IThread thread, int flags) {
ModelDelta delta = buildRootDelta();
- ModelDelta node = addPathToThraed(delta, thread);
+ ModelDelta node = addPathToThread(delta, thread);
node.addNode(thread, flags);
synchronized (this) {
fLastTopFrame.remove(thread);
@@ -138,7 +138,7 @@ public class ThreadEventHandler extends DebugEventHandler {
private void fireDeltaUpdatingTopFrame(IThread thread, int flags) {
ModelDelta delta = buildRootDelta();
- ModelDelta node = addPathToThraed(delta, thread);
+ ModelDelta node = addPathToThread(delta, thread);
IStackFrame prev = null;
synchronized (this) {
prev = (IStackFrame) fLastTopFrame.get(thread);
diff --git a/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/views/variables/VariablesView.java b/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/views/variables/VariablesView.java
index f0ef0ef30..bf1cc15d4 100644
--- a/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/views/variables/VariablesView.java
+++ b/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/views/variables/VariablesView.java
@@ -604,7 +604,7 @@ public class VariablesView extends AbstractDebugView implements IDebugContextLis
setSashForm(new SashForm(parent, SWT.NONE));
// add tree viewer
- final VariablesViewer variablesViewer = new VariablesViewer(getSashForm(), SWT.MULTI | SWT.V_SCROLL | SWT.H_SCROLL, this);
+ final VariablesViewer variablesViewer = new VariablesViewer(getSashForm(), SWT.MULTI | SWT.V_SCROLL | SWT.H_SCROLL | SWT.VIRTUAL, this);
variablesViewer.setUseHashlookup(false);
variablesViewer.getControl().addFocusListener(new FocusAdapter() {
/* (non-Javadoc)
diff --git a/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/views/variables/VariablesViewer.java b/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/views/variables/VariablesViewer.java
index 0c7434e1d..315d955e4 100644
--- a/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/views/variables/VariablesViewer.java
+++ b/org.eclipse.debug.ui/ui/org/eclipse/debug/internal/ui/views/variables/VariablesViewer.java
@@ -53,7 +53,7 @@ public class VariablesViewer extends AsynchronousTreeViewer{
*/
protected void internalRefresh(Object element, Widget item) {
super.internalRefresh(element, item);
- if (element.equals(((IStructuredSelection)getSelection()).getFirstElement())) {
+ if (fView != null && element.equals(((IStructuredSelection)getSelection()).getFirstElement())) {
fView.populateDetailPane();
}
}
diff --git a/org.eclipse.debug.ui/ui/org/eclipse/debug/ui/InspectPopupDialog.java b/org.eclipse.debug.ui/ui/org/eclipse/debug/ui/InspectPopupDialog.java
index 66644e00c..783bfcc78 100644
--- a/org.eclipse.debug.ui/ui/org/eclipse/debug/ui/InspectPopupDialog.java
+++ b/org.eclipse.debug.ui/ui/org/eclipse/debug/ui/InspectPopupDialog.java
@@ -122,7 +122,7 @@ public class InspectPopupDialog extends DebugPopup {
VariablesView view = getViewToEmulate();
- fVariablesViewer = new VariablesViewer(fSashForm, SWT.NO_TRIM, null);
+ fVariablesViewer = new VariablesViewer(fSashForm, SWT.NO_TRIM | SWT.VIRTUAL, null);
fVariablesViewer.setContext(new PresentationContext(view));
fModelPresentation = new VariablesViewModelPresentation();

Back to the top