diff options
| author | Philipp Thun | 2011-02-25 22:08:36 +0000 |
|---|---|---|
| committer | Matthias Sohn | 2011-02-25 22:08:36 +0000 |
| commit | e83b05232f92ed3b9cfc1227e80de3e6e959b72f (patch) | |
| tree | bc54a137fba13bd2aa01531b290ae19cfb03b198 | |
| parent | cc5c828bea8a4b16a7b10f8f632271d75d2dac50 (diff) | |
| download | egit-e83b05232f92ed3b9cfc1227e80de3e6e959b72f.tar.gz egit-e83b05232f92ed3b9cfc1227e80de3e6e959b72f.tar.xz egit-e83b05232f92ed3b9cfc1227e80de3e6e959b72f.zip | |
Reduce number of LabelProviderChangedEvents
When a resource changes there are several events fired that lead
towards re-decoration of this resource (and parent resources). These
events are often redundant, e.g. when checking out a different
branch, JGit fires a RefsChangedEvent and an IndexChangedEvent.
Furthermore Eclipse detects that a resource changed and thus fires a
ResourceChangeEvent. But in the end only one re-decoration should be
triggered, thus a mechanism is introduced that delays firing an event
for 100ms and ignores further events within this time frame.
Change-Id: I4dfb4156e289d573f5f115613f3c55604e9c6746
Signed-off-by: Philipp Thun <philipp.thun@sap.com>
Signed-off-by: Matthias Sohn <matthias.sohn@sap.com>
| -rw-r--r-- | org.eclipse.egit.ui/src/org/eclipse/egit/ui/internal/decorators/GitLightweightDecorator.java | 95 |
1 files changed, 74 insertions, 21 deletions
diff --git a/org.eclipse.egit.ui/src/org/eclipse/egit/ui/internal/decorators/GitLightweightDecorator.java b/org.eclipse.egit.ui/src/org/eclipse/egit/ui/internal/decorators/GitLightweightDecorator.java index f1d68208cf..af63b8f1dd 100644 --- a/org.eclipse.egit.ui/src/org/eclipse/egit/ui/internal/decorators/GitLightweightDecorator.java +++ b/org.eclipse.egit.ui/src/org/eclipse/egit/ui/internal/decorators/GitLightweightDecorator.java @@ -32,8 +32,11 @@ import org.eclipse.core.resources.ResourcesPlugin; import org.eclipse.core.resources.mapping.ResourceMapping; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IAdaptable; +import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.QualifiedName; +import org.eclipse.core.runtime.Status; +import org.eclipse.core.runtime.jobs.Job; import org.eclipse.egit.core.internal.util.ExceptionCollector; import org.eclipse.egit.core.project.GitProjectData; import org.eclipse.egit.core.project.RepositoryChangeListener; @@ -333,8 +336,8 @@ public class GitLightweightDecorator extends LabelProvider implements } } - // Re-trigger decoration process (in UI thread) - fireLabelEvent(new LabelProviderChangedEvent(this)); + // Immediately fire label provider changed event + fireLabelEvent(); } /** @@ -659,12 +662,12 @@ public class GitLightweightDecorator extends LabelProvider implements if (prop.equals(TeamUI.GLOBAL_IGNORES_CHANGED) || prop.equals(TeamUI.GLOBAL_FILE_TYPES_CHANGED) || prop.equals(Activator.DECORATORS_CHANGED)) { - postLabelEvent(new LabelProviderChangedEvent(this)); + postLabelEvent(null); } else if (prop.equals(UIPreferences.THEME_UncommittedChangeBackgroundColor) || prop.equals(UIPreferences.THEME_UncommittedChangeFont) || prop.equals(UIPreferences.THEME_UncommittedChangeForegroundColor)) { ensureFontAndColorsCreated(fonts, colors); - postLabelEvent(new LabelProviderChangedEvent(this)); // TODO do I really need this? + postLabelEvent(null); // TODO do I really need this? } } @@ -757,16 +760,15 @@ public class GitLightweightDecorator extends LabelProvider implements } } - postLabelEvent(new LabelProviderChangedEvent(this, resourcesToUpdate - .toArray())); + postLabelEvent(resourcesToUpdate.toArray()); } public void onIndexChanged(IndexChangedEvent e) { - postLabelEvent(new LabelProviderChangedEvent(this)); + postLabelEvent(null); } public void onRefsChanged(RefsChangedEvent e) { - postLabelEvent(new LabelProviderChangedEvent(this)); + postLabelEvent(null); } /** @@ -778,7 +780,7 @@ public class GitLightweightDecorator extends LabelProvider implements public void repositoryChanged(RepositoryMapping mapping) { // Until we find a way to refresh visible labels within a project // we have to use this blanket refresh that includes all projects. - postLabelEvent(new LabelProviderChangedEvent(this)); + postLabelEvent(null); } // -------- Helper methods -------- @@ -807,13 +809,13 @@ public class GitLightweightDecorator extends LabelProvider implements } /** - * Post the label event to the UI thread + * Post a label event to the LabelEventJob * - * @param event - * The event to post + * @param elements + * The elements to update */ - private void postLabelEvent(final LabelProviderChangedEvent event) { - if (event.getElement() == null) { + private void postLabelEvent(final Object[] elements) { + if (elements == null) { // Update all elements final IWorkspaceRoot root = ResourcesPlugin.getWorkspace() .getRoot(); @@ -824,11 +826,8 @@ public class GitLightweightDecorator extends LabelProvider implements } catch (CoreException e) { handleException(root, e); } - - fireLabelEvent(event); } else { // Update specific elements - Object[] elements = event.getElements(); for (Object element : elements) { final IResource resource = getResource(element); if (resource != null) @@ -839,13 +838,15 @@ public class GitLightweightDecorator extends LabelProvider implements // Ignore } } - - // Fire a generic event - fireLabelEvent(new LabelProviderChangedEvent(this)); } + + LabelEventJob.getInstance().postLabelEvent(this); } - private void fireLabelEvent(final LabelProviderChangedEvent event) { + void fireLabelEvent() { + final LabelProviderChangedEvent event = new LabelProviderChangedEvent( + this); + // Re-trigger decoration process (in UI thread) Display.getDefault().asyncExec(new Runnable() { public void run() { fireLabelProviderChanged(event); @@ -867,3 +868,55 @@ public class GitLightweightDecorator extends LabelProvider implements exceptions.handleException(e); } } + +/** + * Job reducing label events to prevent unnecessary (i.e. redundant) event + * processing + */ +class LabelEventJob extends Job { + + /** + * Constant defining the waiting time (in milliseconds) until an event is + * fired + */ + private static final long DELAY = 100L; + + private static LabelEventJob instance = new LabelEventJob("LabelEventJob"); //$NON-NLS-1$ + + /** + * Get the LabelEventJob singleton + * + * @return the LabelEventJob singleton + */ + static LabelEventJob getInstance() { + return instance; + } + + private LabelEventJob(final String name) { + super(name); + } + + private GitLightweightDecorator glwDecorator = null; + + /** + * Post a label event + * + * @param decorator + * The GitLightweightDecorator that is used to fire a + * LabelProviderChangedEvent + */ + void postLabelEvent(final GitLightweightDecorator decorator) { + if (this.glwDecorator == null) + this.glwDecorator = decorator; + if (getState() == SLEEPING || getState() == WAITING) + cancel(); + schedule(DELAY); + } + + @Override + protected IStatus run(IProgressMonitor monitor) { + if (glwDecorator != null) + glwDecorator.fireLabelEvent(); + return Status.OK_STATUS; + } +} |
