KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > eclipse > team > internal > ui > synchronize > ChangeSetModelProvider


1 /*******************************************************************************
2  * Copyright (c) 2000, 2006 IBM Corporation and others.
3  * All rights reserved. This program and the accompanying materials
4  * are made available under the terms of the Eclipse Public License v1.0
5  * which accompanies this distribution, and is available at
6  * http://www.eclipse.org/legal/epl-v10.html
7  *
8  * Contributors:
9  * IBM Corporation - initial API and implementation
10  *******************************************************************************/

11 package org.eclipse.team.internal.ui.synchronize;
12
13 import java.util.HashMap JavaDoc;
14 import java.util.Map JavaDoc;
15
16 import org.eclipse.compare.structuremergeviewer.IDiffElement;
17 import org.eclipse.core.runtime.IPath;
18 import org.eclipse.core.runtime.IProgressMonitor;
19 import org.eclipse.jface.resource.ImageDescriptor;
20 import org.eclipse.jface.util.IPropertyChangeListener;
21 import org.eclipse.jface.util.PropertyChangeEvent;
22 import org.eclipse.jface.viewers.ViewerSorter;
23 import org.eclipse.team.core.synchronize.*;
24 import org.eclipse.team.internal.core.subscribers.*;
25 import org.eclipse.team.internal.ui.*;
26 import org.eclipse.team.internal.ui.synchronize.actions.ChangeSetActionGroup;
27 import org.eclipse.team.ui.synchronize.*;
28
29 /**
30  * Model provider for showing change sets in a sync page.
31  */

32 public class ChangeSetModelProvider extends CompositeModelProvider {
33
34     private ViewerSorter viewerSorter;
35     
36     // The id of the sub-provider
37
private final String JavaDoc subProvierId;
38     
39     private Map JavaDoc rootToProvider = new HashMap JavaDoc(); // Maps ISynchronizeModelElement -> AbstractSynchronizeModelProvider
40

41     private ViewerSorter embeddedSorter;
42     
43     private SyncInfoSetChangeSetCollector checkedInCollector;
44     
45     private IChangeSetChangeListener changeSetListener = new IChangeSetChangeListener() {
46         
47         /* (non-Javadoc)
48          * @see org.eclipse.team.core.subscribers.IChangeSetChangeListener#setAdded(org.eclipse.team.core.subscribers.ChangeSet)
49          */

50         public void setAdded(final ChangeSet set) {
51             final SyncInfoTree syncInfoSet;
52             // TODO: May need to be modified to work with two-way
53
if (set instanceof CheckedInChangeSet) {
54                 syncInfoSet = checkedInCollector.getSyncInfoSet(set);
55             } else {
56                 syncInfoSet = activeCollector.getSyncInfoSet(set);
57             }
58             if (syncInfoSet != null)
59                 createChangeSetModelElement(set, syncInfoSet);
60         }
61
62         /* (non-Javadoc)
63          * @see org.eclipse.team.core.subscribers.IChangeSetChangeListener#defaultSetChanged(org.eclipse.team.core.subscribers.ChangeSet, org.eclipse.team.core.subscribers.ChangeSet)
64          */

65         public void defaultSetChanged(final ChangeSet previousDefault, final ChangeSet set) {
66             refreshLabel(previousDefault);
67             refreshLabel(set);
68         }
69
70         /* (non-Javadoc)
71          * @see org.eclipse.team.core.subscribers.IChangeSetChangeListener#setRemoved(org.eclipse.team.core.subscribers.ChangeSet)
72          */

73         public void setRemoved(final ChangeSet set) {
74             removeModelElementForSet(set);
75         }
76
77         /* (non-Javadoc)
78          * @see org.eclipse.team.core.subscribers.IChangeSetChangeListener#nameChanged(org.eclipse.team.core.subscribers.ChangeSet)
79          */

80         public void nameChanged(final ChangeSet set) {
81             refreshLabel(set);
82         }
83
84         /* (non-Javadoc)
85          * @see org.eclipse.team.core.subscribers.IChangeSetChangeListener#resourcesChanged(org.eclipse.team.core.subscribers.ChangeSet, org.eclipse.core.resources.IResource[])
86          */

87         public void resourcesChanged(ChangeSet set, IPath[] paths) {
88             // The sub-providers listen directly to the sets for changes
89
// There is no global action to be taken for such changes
90
}
91     };
92     
93     private ActiveChangeSetCollector activeCollector;
94     
95     /* *****************************************************************************
96      * Descriptor for this model provider
97      */

98     public static class ChangeSetModelProviderDescriptor implements ISynchronizeModelProviderDescriptor {
99         public static final String JavaDoc ID = TeamUIPlugin.ID + ".modelprovider_cvs_changelog"; //$NON-NLS-1$
100
public String JavaDoc getId() {
101             return ID;
102         }
103         public String JavaDoc getName() {
104             return TeamUIMessages.ChangeLogModelProvider_5;
105         }
106         public ImageDescriptor getImageDescriptor() {
107             return TeamUIPlugin.getImageDescriptor(ITeamUIImages.IMG_CHANGE_SET);
108         }
109     };
110     private static final ChangeSetModelProviderDescriptor descriptor = new ChangeSetModelProviderDescriptor();
111     
112     protected ChangeSetModelProvider(ISynchronizePageConfiguration configuration, SyncInfoSet set, String JavaDoc subProvierId) {
113         super(configuration, set);
114         this.subProvierId = subProvierId;
115         ChangeSetCapability changeSetCapability = getChangeSetCapability();
116         if (changeSetCapability.supportsCheckedInChangeSets()) {
117             checkedInCollector = changeSetCapability.createSyncInfoSetChangeSetCollector(configuration);
118             checkedInCollector.setProvider(this);
119             checkedInCollector.addListener(changeSetListener);
120         }
121         if (changeSetCapability.supportsActiveChangeSets()) {
122             activeCollector = new ActiveChangeSetCollector(configuration, this);
123             activeCollector.setChangeSetChangeListener(changeSetListener);
124             configuration.addMenuGroup(ISynchronizePageConfiguration.P_CONTEXT_MENU, ChangeSetActionGroup.CHANGE_SET_GROUP);
125         }
126     }
127
128     /* (non-Javadoc)
129      * @see org.eclipse.team.internal.ui.synchronize.AbstractSynchronizeModelProvider#handleChanges(org.eclipse.team.core.synchronize.ISyncInfoTreeChangeEvent, org.eclipse.core.runtime.IProgressMonitor)
130      */

131     protected void handleChanges(ISyncInfoTreeChangeEvent event, IProgressMonitor monitor) {
132         boolean handled = false;
133         if (checkedInCollector != null && getChangeSetCapability().enableCheckedInChangeSetsFor(getConfiguration())) {
134             checkedInCollector.handleChange(event);
135             handled = true;
136         }
137         if (activeCollector != null && getChangeSetCapability().enableActiveChangeSetsFor(getConfiguration())) {
138             activeCollector.handleChange(event);
139             handled = true;
140         }
141         if (!handled) {
142             // Forward the event to the root provider
143
ISynchronizeModelProvider provider = getProviderRootedAt(getModelRoot());
144             if (provider != null) {
145                 SyncInfoSet set = provider.getSyncInfoSet();
146                 try {
147                     set.beginInput();
148                     set.removeAll(event.getRemovedResources());
149                     SyncInfo[] added = event.getAddedResources();
150                     for (int i = 0; i < added.length; i++) {
151                         SyncInfo info = added[i];
152                         set.add(info);
153                     }
154                     SyncInfo[] changed = event.getChangedResources();
155                     for (int i = 0; i < changed.length; i++) {
156                         SyncInfo info = changed[i];
157                         set.add(info);
158                     }
159                 } finally {
160                     set.endInput(monitor);
161                 }
162             }
163         }
164     }
165     
166     /* (non-Javadoc)
167      * @see org.eclipse.team.internal.ui.synchronize.CompositeModelProvider#handleAddition(org.eclipse.team.core.synchronize.SyncInfo)
168      */

169     protected void handleAddition(SyncInfo info) {
170         // Nothing to do since change handling was bypassed
171
}
172
173     /* (non-Javadoc)
174      * @see org.eclipse.team.internal.ui.synchronize.AbstractSynchronizeModelProvider#buildModelObjects(org.eclipse.team.ui.synchronize.ISynchronizeModelElement)
175      */

176     protected IDiffElement[] buildModelObjects(ISynchronizeModelElement node) {
177         // This method is invoked on a reset after the provider state has been cleared.
178
// Resetting the collector will rebuild the model
179

180         if (node == getModelRoot()) {
181             
182             // First, disable the collectors
183
if (checkedInCollector != null) {
184                 checkedInCollector.reset(null);
185                 checkedInCollector.removeListener(changeSetListener);
186             }
187             if (activeCollector != null) {
188                 activeCollector.setChangeSetChangeListener(null);
189                 activeCollector.reset(null);
190             }
191             
192             // Then, re-enable the proper collection method
193
boolean handled = false;
194             if (checkedInCollector != null && getChangeSetCapability().enableCheckedInChangeSetsFor(getConfiguration())) {
195                 checkedInCollector.addListener(changeSetListener);
196                 checkedInCollector.reset(getSyncInfoSet());
197                 handled = true;
198             }
199             if (activeCollector != null && getChangeSetCapability().enableActiveChangeSetsFor(getConfiguration())) {
200                 activeCollector.setChangeSetChangeListener(changeSetListener);
201                 activeCollector.reset(getSyncInfoSet());
202                 handled = true;
203             }
204             if (!handled) {
205                 // Forward the sync info to the root provider and trigger a build
206
ISynchronizeModelProvider provider = getProviderRootedAt(getModelRoot());
207                 if (provider != null) {
208                     ((SynchronizeModelProvider)provider).getSyncInfoSet().addAll(getSyncInfoSet());
209                 }
210             }
211         }
212         return new IDiffElement[0];
213     }
214
215     /* (non-Javadoc)
216      * @see org.eclipse.team.internal.ui.synchronize.ISynchronizeModelProvider#getDescriptor()
217      */

218     public ISynchronizeModelProviderDescriptor getDescriptor() {
219         return descriptor;
220     }
221
222     /* (non-Javadoc)
223      * @see org.eclipse.team.internal.ui.synchronize.ISynchronizeModelProvider#getViewerSorter()
224      */

225     public ViewerSorter getViewerSorter() {
226         if (viewerSorter == null) {
227             viewerSorter = new ChangeSetModelSorter(this, ChangeSetActionGroup.getSortCriteria(getConfiguration()));
228         }
229         return viewerSorter;
230     }
231
232     /*
233      * Method to allow ChangeSetActionGroup to set the viewer sorter of this provider.
234      */

235     public void setViewerSorter(ViewerSorter viewerSorter) {
236         this.viewerSorter = viewerSorter;
237         firePropertyChange(ISynchronizeModelProvider.P_VIEWER_SORTER, null, null);
238     }
239
240     /* (non-Javadoc)
241      * @see org.eclipse.team.internal.ui.synchronize.AbstractSynchronizeModelProvider#createActionGroup()
242      */

243     protected SynchronizePageActionGroup createActionGroup() {
244         return new ChangeSetActionGroup(this);
245     }
246     
247     private ISynchronizeModelProvider createProviderRootedAt(ISynchronizeModelElement parent, SyncInfoTree set) {
248         ISynchronizeModelProvider provider = createModelProvider(parent, getSubproviderId(), set);
249         addProvider(provider);
250         rootToProvider.put(parent, provider);
251         return provider;
252     }
253
254     private ISynchronizeModelProvider getProviderRootedAt(ISynchronizeModelElement parent) {
255         return (ISynchronizeModelProvider)rootToProvider.get(parent);
256     }
257     
258     /* (non-Javadoc)
259      * @see org.eclipse.team.internal.ui.synchronize.CompositeModelProvider#removeProvider(org.eclipse.team.internal.ui.synchronize.AbstractSynchronizeModelProvider)
260      */

261     protected void removeProvider(ISynchronizeModelProvider provider) {
262         rootToProvider.remove(provider.getModelRoot());
263         super.removeProvider(provider);
264     }
265     
266     /**
267      * Return the id of the sub-provider used by the commit set provider.
268      * @return the id of the sub-provider used by the commit set provider
269      */

270     public String JavaDoc getSubproviderId() {
271         return subProvierId;
272     }
273
274     /**
275      * Return the sorter associated with the sub-provider being used.
276      * @return the sorter associated with the sub-provider being used
277      */

278     public ViewerSorter getEmbeddedSorter() {
279         return embeddedSorter;
280     }
281     
282     /* (non-Javadoc)
283      * @see org.eclipse.team.internal.ui.synchronize.CompositeModelProvider#clearModelObjects(org.eclipse.team.ui.synchronize.ISynchronizeModelElement)
284      */

285     protected void recursiveClearModelObjects(ISynchronizeModelElement node) {
286         super.recursiveClearModelObjects(node);
287         if (node == getModelRoot()) {
288             rootToProvider.clear();
289             // Throw away the embedded sorter
290
embeddedSorter = null;
291             createRootProvider();
292         }
293     }
294
295     /*
296      * Create the root subprovider which is used to display resources
297      * that are not in a commit set. This provider is created even if
298      * it is empty so we can have access to the appropriate sorter
299      * and action group
300      */

301     private void createRootProvider() {
302         // Recreate the sub-provider at the root and use it's viewer sorter and action group
303
SyncInfoTree tree;
304         if (activeCollector != null && getChangeSetCapability().enableActiveChangeSetsFor(getConfiguration())) {
305             // When in outgoing mode, use the root set of the active change set collector at the root
306
tree = activeCollector.getRootSet();
307         } else {
308             tree = new SyncInfoTree();
309         }
310         final ISynchronizeModelProvider provider = createProviderRootedAt(getModelRoot(), tree);
311         embeddedSorter = provider.getViewerSorter();
312         if (provider instanceof AbstractSynchronizeModelProvider) {
313             SynchronizePageActionGroup actionGroup = ((AbstractSynchronizeModelProvider)provider).getActionGroup();
314             if (actionGroup != null) {
315                 // This action group will be disposed when the provider is disposed
316
getConfiguration().addActionContribution(actionGroup);
317                 provider.addPropertyChangeListener(new IPropertyChangeListener() {
318                     public void propertyChange(PropertyChangeEvent event) {
319                         if (event.getProperty().equals(P_VIEWER_SORTER)) {
320                             embeddedSorter = provider.getViewerSorter();
321                             ChangeSetModelProvider.this.firePropertyChange(P_VIEWER_SORTER, null, null);
322                         }
323                     }
324                 });
325             }
326         }
327     }
328     
329     /*
330      * Find the root element for the given change set.
331      * A linear search is used.
332      */

333     protected ISynchronizeModelElement getModelElement(ChangeSet set) {
334         IDiffElement[] children = getModelRoot().getChildren();
335         for (int i = 0; i < children.length; i++) {
336             IDiffElement element = children[i];
337             if (element instanceof ChangeSetDiffNode && ((ChangeSetDiffNode)element).getSet() == set) {
338                 return (ISynchronizeModelElement)element;
339             }
340         }
341         return null;
342     }
343
344     /*
345      * Return the change set capability
346      */

347     public ChangeSetCapability getChangeSetCapability() {
348         ISynchronizeParticipant participant = getConfiguration().getParticipant();
349         if (participant instanceof IChangeSetProvider) {
350             IChangeSetProvider provider = (IChangeSetProvider) participant;
351             return provider.getChangeSetCapability();
352         }
353         return null;
354     }
355     
356     public void dispose() {
357         if (checkedInCollector != null) {
358             checkedInCollector.removeListener(changeSetListener);
359             checkedInCollector.dispose();
360         }
361         if (activeCollector != null) {
362             activeCollector.setChangeSetChangeListener(null);
363             activeCollector.dispose();
364         }
365         super.dispose();
366     }
367     
368     
369     public void waitUntilDone(IProgressMonitor monitor) {
370         super.waitUntilDone(monitor);
371         if (checkedInCollector != null) {
372             checkedInCollector.waitUntilDone(monitor);
373             // Wait for the provider again since the change set handler may have queued UI updates
374
super.waitUntilDone(monitor);
375         }
376     }
377     
378     void removeModelElementForSet(final ChangeSet set) {
379         ISynchronizeModelElement node = getModelElement(set);
380         if (node != null) {
381             ISynchronizeModelProvider provider = getProviderRootedAt(node);
382             removeFromViewer(new ISynchronizeModelElement[] { node });
383             removeProvider(provider);
384         }
385     }
386
387     public void createChangeSetModelElement(ChangeSet set, SyncInfoTree tree) {
388         // Add the model element and provider for the set
389
ISynchronizeModelElement node = getModelElement(set);
390         ISynchronizeModelProvider provider = null;
391         if (node != null) {
392             provider = getProviderRootedAt(node);
393         }
394         if (provider == null) {
395             provider = createProvider(set, tree);
396             provider.prepareInput(null);
397         }
398     }
399     
400     private ISynchronizeModelProvider createProvider(ChangeSet set, SyncInfoTree tree) {
401         ChangeSetDiffNode node = new ChangeSetDiffNode(getModelRoot(), set);
402         addToViewer(node);
403         return createProviderRootedAt(node, tree);
404     }
405
406     public void refreshLabel(ChangeSet set) {
407         ISynchronizeModelElement node = getModelElement(set);
408         if (node != null) {
409             getViewer().refresh(node);
410         }
411     }
412 }
413
Popular Tags