KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > eclipse > team > ui > synchronize > ModelSynchronizeParticipant


1 /*******************************************************************************
2  * Copyright (c) 2000, 2007 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.ui.synchronize;
12
13 import java.io.IOException JavaDoc;
14 import java.util.ArrayList JavaDoc;
15 import java.util.List JavaDoc;
16
17 import org.eclipse.compare.structuremergeviewer.ICompareInput;
18 import org.eclipse.core.resources.mapping.*;
19 import org.eclipse.core.runtime.*;
20 import org.eclipse.core.runtime.jobs.Job;
21 import org.eclipse.jface.preference.PreferencePage;
22 import org.eclipse.jface.preference.PreferenceStore;
23 import org.eclipse.osgi.util.NLS;
24 import org.eclipse.swt.widgets.Shell;
25 import org.eclipse.team.core.mapping.*;
26 import org.eclipse.team.core.mapping.provider.*;
27 import org.eclipse.team.internal.core.subscribers.SubscriberDiffTreeEventHandler;
28 import org.eclipse.team.internal.ui.*;
29 import org.eclipse.team.internal.ui.mapping.ModelEnablementPreferencePage;
30 import org.eclipse.team.internal.ui.mapping.ModelSynchronizePage;
31 import org.eclipse.team.internal.ui.preferences.SyncViewerPreferencePage;
32 import org.eclipse.team.internal.ui.synchronize.*;
33 import org.eclipse.team.ui.TeamUI;
34 import org.eclipse.team.ui.mapping.*;
35 import org.eclipse.ui.*;
36 import org.eclipse.ui.part.IPageBookViewPage;
37
38 /**
39  * Synchronize participant that obtains it's synchronization state from
40  * a {@link ISynchronizationContext}.
41  * <p>
42  * This class may be subclassed by clients.
43  *
44  * @since 3.2
45  */

46 public class ModelSynchronizeParticipant extends
47         AbstractSynchronizeParticipant {
48     
49     /**
50      * Property constant used to store and retrieve the id of the active
51      * {@link ModelProvider} from an {@link ISynchronizePageConfiguration}. The
52      * active model provider will be the only one visible in the page. If
53      * <code>null</code> or <code>ALL_MODEL_PROVIDERS_ACTIVE</code> is
54      * returned, all model providers are considered active and are visible.
55      */

56     public static final String JavaDoc P_VISIBLE_MODEL_PROVIDER = TeamUIPlugin.ID + ".activeModelProvider"; //$NON-NLS-1$
57

58     /**
59      * Constant used with the <code>P_ACTIVE_MODEL_PROVIDER</code> property to indicate
60      * that all enabled model providers are active.
61      */

62     public static final String JavaDoc ALL_MODEL_PROVIDERS_VISIBLE = TeamUIPlugin.ID + ".activeModelProvider"; //$NON-NLS-1$
63

64     /**
65      * Property constant used during property change notification to indicate
66      * that the enabled model providers for this participant have changed.
67      */

68     public static final String JavaDoc PROP_ENABLED_MODEL_PROVIDERS = TeamUIPlugin.ID + ".ENABLED_MODEL_PROVIDERS"; //$NON-NLS-1$
69

70     /**
71      * Property constant used during property change notification to indicate
72      * that the active model of this participant has changed.
73      */

74     public static final String JavaDoc PROP_ACTIVE_SAVEABLE = TeamUIPlugin.ID + ".ACTIVE_SAVEABLE"; //$NON-NLS-1$
75

76     /**
77      * Property constant used during property change notification to indicate
78      * that the dirty state for the active saveable model of this participant has changed.
79      */

80     public static final String JavaDoc PROP_DIRTY = TeamUIPlugin.ID + ".DIRTY"; //$NON-NLS-1$
81

82     /*
83      * Key for settings in memento
84      */

85     private static final String JavaDoc CTX_PARTICIPANT_SETTINGS = TeamUIPlugin.ID + ".MODEL_PARTICIPANT_SETTINGS"; //$NON-NLS-1$
86

87     /*
88      * Key for schedule in memento
89      */

90     private static final String JavaDoc CTX_REFRESH_SCHEDULE_SETTINGS = TeamUIPlugin.ID + ".MODEL_PARTICIPANT_REFRESH_SCHEDULE"; //$NON-NLS-1$
91

92     /*
93      * Key for description in memento
94      */

95     private static final String JavaDoc CTX_DESCRIPTION = TeamUIPlugin.ID + ".MODEL_PARTICIPANT_DESCRIPTION"; //$NON-NLS-1$
96

97     /*
98      * Constants used to save and restore this scope
99      */

100     private static final String JavaDoc CTX_PARTICIPANT_MAPPINGS = TeamUIPlugin.ID + ".MODEL_PARTICIPANT_MAPPINGS"; //$NON-NLS-1$
101
private static final String JavaDoc CTX_MODEL_PROVIDER_ID = "modelProviderId"; //$NON-NLS-1$
102
private static final String JavaDoc CTX_MODEL_PROVIDER_MAPPINGS = "mappings"; //$NON-NLS-1$
103
private static final String JavaDoc CTX_STARTUP_ACTION = "startupAction"; //$NON-NLS-1$
104

105     private SynchronizationContext context;
106     private boolean mergingEnabled = true;
107     protected SubscriberRefreshSchedule refreshSchedule;
108     private String JavaDoc description;
109     private SaveableComparison activeSaveable;
110     private PreferenceStore preferences = new PreferenceStore() {
111         public void save() throws IOException JavaDoc {
112             // Nothing to do. Preference will be saved with participant
113
}
114     };
115
116     private IPropertyListener dirtyListener = new IPropertyListener() {
117         public void propertyChanged(Object JavaDoc source, int propId) {
118             if (source instanceof SaveableComparison && propId == SaveableComparison.PROP_DIRTY) {
119                 SaveableComparison scm = (SaveableComparison) source;
120                 boolean isDirty = scm.isDirty();
121                 firePropertyChange(ModelSynchronizeParticipant.this, PROP_DIRTY, Boolean.valueOf(!isDirty), Boolean.valueOf(isDirty));
122             }
123         }
124     };
125
126     /**
127      * Create a participant for the given context
128      * @param context the synchronization context
129      * @param name the name of the participant
130      * @return a participant for the given context
131      */

132     public static ModelSynchronizeParticipant createParticipant(SynchronizationContext context, String JavaDoc name) {
133         return new ModelSynchronizeParticipant(context, name);
134     }
135     
136     /*
137      * Create a participant for the given context
138      * @param context the synchronization context
139      * @param name the name of the participant
140      */

141     private ModelSynchronizeParticipant(SynchronizationContext context, String JavaDoc name) {
142         initializeContext(context);
143         try {
144             setInitializationData(TeamUI.getSynchronizeManager().getParticipantDescriptor("org.eclipse.team.ui.synchronization_context_synchronize_participant")); //$NON-NLS-1$
145
} catch (CoreException e) {
146             TeamUIPlugin.log(e);
147         }
148         setSecondaryId(Long.toString(System.currentTimeMillis()));
149         setName(name);
150         refreshSchedule = new SubscriberRefreshSchedule(createRefreshable());
151     }
152
153     /**
154      * Create a participant for the given context
155      * @param context the synchronization context
156      */

157     public ModelSynchronizeParticipant(SynchronizationContext context) {
158         initializeContext(context);
159         refreshSchedule = new SubscriberRefreshSchedule(createRefreshable());
160     }
161     
162     /**
163      * Create a participant in order to restore it from saved state.
164      */

165     public ModelSynchronizeParticipant() {
166     }
167
168     /* (non-Javadoc)
169      * @see org.eclipse.team.ui.synchronize.AbstractSynchronizeParticipant#getName()
170      */

171     public String JavaDoc getName() {
172         String JavaDoc name = super.getName();
173         if (description == null)
174             description = Utils.getScopeDescription(getContext().getScope());
175         return NLS.bind(TeamUIMessages.SubscriberParticipant_namePattern, new String JavaDoc[] { name, description });
176     }
177
178     /**
179      * Return the name of the participant as specified in the plugin manifest file.
180      * This method is provided to give access to this name since it is masked by
181      * the <code>getName()</code> method defined in this class.
182      * @return the name of the participant as specified in the plugin manifest file
183      * @since 3.1
184      */

185     protected final String JavaDoc getShortName() {
186         return super.getName();
187     }
188     
189     /* (non-Javadoc)
190      * @see org.eclipse.team.ui.synchronize.AbstractSynchronizeParticipant#initializeConfiguration(org.eclipse.team.ui.synchronize.ISynchronizePageConfiguration)
191      */

192     protected void initializeConfiguration(
193             ISynchronizePageConfiguration configuration) {
194         if (isMergingEnabled()) {
195             // The context menu groups are defined by the org.eclipse.ui.navigator.viewer extension
196
configuration.addMenuGroup(ISynchronizePageConfiguration.P_TOOLBAR_MENU, ModelSynchronizeParticipantActionGroup.MERGE_ACTION_GROUP);
197             configuration.addActionContribution(createMergeActionGroup());
198         }
199         configuration.setSupportedModes(ISynchronizePageConfiguration.ALL_MODES);
200         configuration.setMode(ISynchronizePageConfiguration.BOTH_MODE);
201         configuration.setProperty(ITeamContentProviderManager.P_SYNCHRONIZATION_CONTEXT, getContext());
202         configuration.setProperty(ITeamContentProviderManager.P_SYNCHRONIZATION_SCOPE, getContext().getScope());
203         if (getHandler() != null)
204             configuration.setProperty(StartupPreferencePage.STARTUP_PREFERENCES, preferences);
205     }
206
207     /**
208      * Create the merge action group for this participant.
209      * Subclasses can override in order to provide a
210      * merge action group that configures certain aspects
211      * of the merge actions.
212      * @return the merge action group for this participant
213      */

214     protected ModelSynchronizeParticipantActionGroup createMergeActionGroup() {
215         return new ModelSynchronizeParticipantActionGroup();
216     }
217
218     /* (non-Javadoc)
219      * @see org.eclipse.team.ui.synchronize.ISynchronizeParticipant#createPage(org.eclipse.team.ui.synchronize.ISynchronizePageConfiguration)
220      */

221     public final IPageBookViewPage createPage(
222             ISynchronizePageConfiguration configuration) {
223         return new ModelSynchronizePage(configuration);
224     }
225
226     /* (non-Javadoc)
227      * @see org.eclipse.team.ui.synchronize.ISynchronizeParticipant#run(org.eclipse.ui.IWorkbenchPart)
228      */

229     public void run(IWorkbenchPart part) {
230         refresh(part != null ? part.getSite() : null, context.getScope().getMappings());
231     }
232
233     /**
234      * Refresh a participant in the background the result of the refresh are shown in the progress view. Refreshing
235      * can also be considered synchronizing, or refreshing the synchronization state. Basically this is a long
236      * running operation that will update the participant's context with new changes detected on the
237      * server.
238      *
239      * @param site the workbench site the synchronize is running from. This can be used to notify the site
240      * that a job is running.
241      * @param mappings the resource mappings to be refreshed
242      */

243     public final void refresh(IWorkbenchSite site, ResourceMapping[] mappings) {
244         IRefreshSubscriberListener listener = new RefreshUserNotificationPolicy(this);
245         internalRefresh(mappings, null, null, site, listener);
246     }
247     
248     /* (non-Javadoc)
249      * @see org.eclipse.team.ui.synchronize.ISynchronizeParticipant#dispose()
250      */

251     public void dispose() {
252         context.dispose();
253         Job.getJobManager().cancel(this);
254         refreshSchedule.dispose();
255     }
256     
257     /**
258      * Set the context of this participant. This method must be invoked
259      * before a page is obtained from the participant.
260      * @param context the context for this participant
261      */

262     protected void initializeContext(SynchronizationContext context) {
263         this.context = context;
264         mergingEnabled = context instanceof IMergeContext;
265         SubscriberDiffTreeEventHandler handler = getHandler();
266         if (handler != null) {
267             preferences.setDefault(StartupPreferencePage.PROP_STARTUP_ACTION, StartupPreferencePage.STARTUP_ACTION_NONE);
268             if (isSynchronizeOnStartup()) {
269                 run(null); // TODO: Would like to get the Sync view part if possible
270
} else if (isPopulateOnStartup()) {
271                 handler.initializeIfNeeded();
272             }
273         }
274     }
275
276     private boolean isPopulateOnStartup() {
277         String JavaDoc pref = preferences.getString(StartupPreferencePage.PROP_STARTUP_ACTION);
278         return pref != null && pref.equals(StartupPreferencePage.STARTUP_ACTION_POPULATE);
279     }
280
281     private boolean isSynchronizeOnStartup() {
282         String JavaDoc pref = preferences.getString(StartupPreferencePage.PROP_STARTUP_ACTION);
283         return pref != null && pref.equals(StartupPreferencePage.STARTUP_ACTION_SYNCHRONIZE);
284     }
285
286     /**
287      * Return the synchronization context for this participant.
288      * @return the synchronization context for this participant
289      */

290     public ISynchronizationContext getContext() {
291         return context;
292     }
293     
294     /**
295      * Return a compare input for the given model object or <code>null</code>
296      * if the object is not eligible for comparison.
297      * @param object the model object
298      * @return a compare input for the model object or <code>null</code>
299      */

300     public ICompareInput asCompareInput(Object JavaDoc object) {
301         if (object instanceof ICompareInput) {
302             return (ICompareInput) object;
303         }
304         // Get a compare input from the model provider's compare adapter
305
ISynchronizationCompareAdapter adapter = Utils.getCompareAdapter(object);
306         if (adapter != null)
307             return adapter.asCompareInput(getContext(), object);
308         return null;
309     }
310
311     /**
312      * Return whether their is a compare input associated with the given object.
313      * In other words, return <code>true</code> if {@link #asCompareInput(Object) }
314      * would return a value and <code>false</code> if it would return <code>null</code>.
315      * @param object the object.
316      * @return whether their is a compare input associated with the given object
317      */

318     public boolean hasCompareInputFor(Object JavaDoc object) {
319         // Get a content viewer from the model provider's compare adapter
320
ISynchronizationCompareAdapter adapter = Utils.getCompareAdapter(object);
321         if (adapter != null)
322             return adapter.hasCompareInput(getContext(), object);
323         return false;
324     }
325
326     /**
327      * Return whether merge capabilities are enabled for this participant.
328      * If merging is enabled, merge actions can be shown. If merging is disabled, no
329      * merge actions should be surfaced.
330      * @return whether merge capabilities should be enabled for this participant
331      */

332     public boolean isMergingEnabled() {
333         return mergingEnabled;
334     }
335
336     /**
337      * Set whether merge capabilities should be enabled for this participant.
338      * @param mergingEnabled whether merge capabilities should be enabled for this participant
339      */

340     public void setMergingEnabled(boolean mergingEnabled) {
341         this.mergingEnabled = mergingEnabled;
342     }
343     
344     private void internalRefresh(ResourceMapping[] mappings, String JavaDoc jobName, String JavaDoc taskName, IWorkbenchSite site, IRefreshSubscriberListener listener) {
345         if (jobName == null)
346             jobName = getShortTaskName();
347         if (taskName == null)
348             taskName = getLongTaskName(mappings);
349         Job.getJobManager().cancel(this);
350         RefreshParticipantJob job = new RefreshModelParticipantJob(this, jobName, taskName, mappings, listener);
351         job.setUser(true);
352         Utils.schedule(job, site);
353         
354         // Remember the last participant synchronized
355
TeamUIPlugin.getPlugin().getPreferenceStore().setValue(IPreferenceIds.SYNCHRONIZING_DEFAULT_PARTICIPANT, getId());
356         TeamUIPlugin.getPlugin().getPreferenceStore().setValue(IPreferenceIds.SYNCHRONIZING_DEFAULT_PARTICIPANT_SEC_ID, getSecondaryId());
357     }
358     
359     /**
360      * Returns the short task name (e.g. no more than 25 characters) to describe
361      * the behavior of the refresh operation to the user. This is typically
362      * shown in the status line when this participant is refreshed in the
363      * background. When refreshed in the foreground, only the long task name is
364      * shown.
365      *
366      * @return the short task name to show in the status line.
367      */

368     protected String JavaDoc getShortTaskName() {
369         return NLS.bind(TeamUIMessages.Participant_synchronizingDetails, getShortName());
370     }
371     
372     /**
373      * Returns the long task name to describe the behavior of the refresh
374      * operation to the user. This is typically shown in the status line when
375      * this subscriber is refreshed in the background.
376      *
377      * @param mappings the mappings being refreshed
378      * @return the long task name
379      * @since 3.1
380      */

381     protected String JavaDoc getLongTaskName(ResourceMapping[] mappings) {
382         if (mappings == null) {
383             // If the mappings are null, assume we are refreshing everything
384
mappings = getContext().getScope().getMappings();
385         }
386         int mappingCount = mappings.length;
387         if (mappingCount == getContext().getScope().getMappings().length) {
388             // Assume we are refreshing everything and only use the input mapping count
389
mappings = getContext().getScope().getInputMappings();
390             mappingCount = mappings.length;
391         }
392         if (mappingCount == 1) {
393             return NLS.bind(TeamUIMessages.Participant_synchronizingMoreDetails, new String JavaDoc[] { getShortName(), Utils.getLabel(mappings[0]) });
394         }
395         return NLS.bind(TeamUIMessages.Participant_synchronizingResources, new String JavaDoc[] { getShortName(), Integer.toString(mappingCount) });
396     }
397     
398     private IRefreshable createRefreshable() {
399         return new IRefreshable() {
400         
401             public RefreshParticipantJob createJob(String JavaDoc interval) {
402                 String JavaDoc jobName = NLS.bind(TeamUIMessages.RefreshSchedule_15, new String JavaDoc[] { ModelSynchronizeParticipant.this.getName(), interval });
403                 return new RefreshModelParticipantJob(ModelSynchronizeParticipant.this,
404                         jobName,
405                         jobName,
406                         context.getScope().getMappings(),
407                         new RefreshUserNotificationPolicy(ModelSynchronizeParticipant.this));
408             }
409             public ISynchronizeParticipant getParticipant() {
410                 return ModelSynchronizeParticipant.this;
411             }
412             public void setRefreshSchedule(SubscriberRefreshSchedule schedule) {
413                 ModelSynchronizeParticipant.this.setRefreshSchedule(schedule);
414             }
415             public SubscriberRefreshSchedule getRefreshSchedule() {
416                 return refreshSchedule;
417             }
418         
419         };
420     }
421     
422     /* (non-Javadoc)
423      * @see org.eclipse.core.runtime.PlatformObject#getAdapter(java.lang.Class)
424      */

425     public Object JavaDoc getAdapter(Class JavaDoc adapter) {
426         if (adapter == IRefreshable.class && refreshSchedule != null) {
427             return refreshSchedule.getRefreshable();
428             
429         }
430         if (adapter == SubscriberRefreshSchedule.class) {
431             return refreshSchedule;
432         }
433         return super.getAdapter(adapter);
434     }
435     
436     /* (non-Javadoc)
437      * @see org.eclipse.team.ui.synchronize.ISynchronizeParticipant#saveState(org.eclipse.ui.IMemento)
438      */

439     public void saveState(IMemento memento) {
440         super.saveState(memento);
441         IMemento settings = memento.createChild(CTX_PARTICIPANT_SETTINGS);
442         if (description != null)
443             settings.putString(CTX_DESCRIPTION, description);
444         refreshSchedule.saveState(settings.createChild(CTX_REFRESH_SCHEDULE_SETTINGS));
445         saveMappings(settings);
446         settings.putString(CTX_STARTUP_ACTION, preferences.getString(StartupPreferencePage.PROP_STARTUP_ACTION));
447     }
448
449     private void saveMappings(IMemento settings) {
450         ISynchronizationScope inputScope = getContext().getScope().asInputScope();
451         ModelProvider[] providers = inputScope.getModelProviders();
452         for (int i = 0; i < providers.length; i++) {
453             ModelProvider provider = providers[i];
454             ISynchronizationCompareAdapter adapter = Utils.getCompareAdapter(provider);
455             if (adapter != null) {
456                 IMemento child = settings.createChild(CTX_PARTICIPANT_MAPPINGS);
457                 String JavaDoc id = provider.getDescriptor().getId();
458                 child.putString(CTX_MODEL_PROVIDER_ID, id);
459                 adapter.save(inputScope.getMappings(id), child.createChild(CTX_MODEL_PROVIDER_MAPPINGS));
460             }
461         }
462     }
463
464     /* (non-Javadoc)
465      * @see org.eclipse.team.ui.synchronize.ISynchronizeParticipant#init(org.eclipse.ui.IMemento)
466      */

467     public void init(String JavaDoc secondaryId, IMemento memento) throws PartInitException {
468         super.init(secondaryId, memento);
469         if(memento != null) {
470             IMemento settings = memento.getChild(CTX_PARTICIPANT_SETTINGS);
471             String JavaDoc startupAction = settings.getString(StartupPreferencePage.PROP_STARTUP_ACTION);
472             if (startupAction != null)
473                 preferences.putValue(StartupPreferencePage.PROP_STARTUP_ACTION, startupAction);
474             ResourceMapping[] mappings = loadMappings(settings);
475             if (mappings.length == 0)
476                 throw new PartInitException(NLS.bind(TeamUIMessages.ModelSynchronizeParticipant_0, getId()));
477             initializeContext(mappings);
478             if(settings != null) {
479                 SubscriberRefreshSchedule schedule = SubscriberRefreshSchedule.init(settings.getChild(CTX_REFRESH_SCHEDULE_SETTINGS), createRefreshable());
480                 description = settings.getString(CTX_DESCRIPTION);
481                 setRefreshSchedule(schedule);
482                 if(schedule.isEnabled()) {
483                     schedule.startJob();
484                 }
485             }
486         }
487     }
488     
489     private ResourceMapping[] loadMappings(IMemento settings) throws PartInitException {
490         List JavaDoc result = new ArrayList JavaDoc();
491         IMemento[] children = settings.getChildren(CTX_PARTICIPANT_MAPPINGS);
492         for (int i = 0; i < children.length; i++) {
493             IMemento memento = children[i];
494             String JavaDoc id = memento.getString(CTX_MODEL_PROVIDER_ID);
495             if (id != null) {
496                 IModelProviderDescriptor desc = ModelProvider.getModelProviderDescriptor(id);
497                 try {
498                     ModelProvider provider = desc.getModelProvider();
499                     ISynchronizationCompareAdapter adapter = Utils.getCompareAdapter(provider);
500                     if (adapter != null) {
501                         ResourceMapping[] mappings = adapter.restore(memento.getChild(CTX_MODEL_PROVIDER_MAPPINGS));
502                         for (int j = 0; j < mappings.length; j++) {
503                             ResourceMapping mapping = mappings[j];
504                             result.add(mapping);
505                         }
506                     }
507                 } catch (CoreException e) {
508                     TeamUIPlugin.log(e);
509                 }
510             }
511         }
512         return (ResourceMapping[]) result.toArray(new ResourceMapping[result.size()]);
513     }
514
515     private void initializeContext(ResourceMapping[] mappings) throws PartInitException {
516         try {
517             ISynchronizationScopeManager manager = createScopeManager(mappings);
518             MergeContext context = restoreContext(manager);
519             initializeContext(context);
520         } catch (CoreException e) {
521             TeamUIPlugin.log(e);
522             throw new PartInitException(e.getStatus());
523         }
524     }
525
526     /**
527      * Recreate the context for this participant. This method is invoked when
528      * the participant is restored after a restart. Although it is provided
529      * with a progress monitor, long running operations should be avoided.
530      * @param manager the restored scope
531      * @return the context for this participant
532      * @throws CoreException
533      */

534     protected MergeContext restoreContext(ISynchronizationScopeManager manager) throws CoreException {
535         throw new PartInitException(NLS.bind(TeamUIMessages.ModelSynchronizeParticipant_1, getId()));
536     }
537
538     /**
539      * Create and return a scope manager that can be used to build the scope of this
540      * participant when it is restored after a restart. By default, this method
541      * returns a scope manager that uses the local content.
542      * This method can be overridden by subclasses.
543      *
544      * @param mappings the restored mappings
545      * @return a scope manager that can be used to build the scope of this
546      * participant when it is restored after a restart
547      */

548     protected ISynchronizationScopeManager createScopeManager(ResourceMapping[] mappings) {
549         return new SynchronizationScopeManager(super.getName(), mappings, ResourceMappingContext.LOCAL_CONTEXT, true);
550     }
551     
552     /* private */ void setRefreshSchedule(SubscriberRefreshSchedule schedule) {
553         if (refreshSchedule != schedule) {
554             if (refreshSchedule != null) {
555                 refreshSchedule.dispose();
556             }
557             this.refreshSchedule = schedule;
558         }
559         // Always fir the event since the schedule may have been changed
560
firePropertyChange(this, AbstractSynchronizeParticipant.P_SCHEDULED, schedule, schedule);
561     }
562
563     /**
564      * Return the active saveable for this participant.
565      * There is at most one saveable active at any
566      * time.
567      * @return the active saveable for this participant
568      * or <code>null</code>
569      */

570     public SaveableComparison getActiveSaveable() {
571         return activeSaveable;
572     }
573
574     /**
575      * Set the active saveable of this participant.
576      * @param activeSaveable the active saveable (may be <code>null</code>)
577      */

578     public void setActiveSaveable(SaveableComparison activeSaveable) {
579         boolean wasDirty = false;
580         SaveableComparison oldModel = this.activeSaveable;
581         if (oldModel != null) {
582             oldModel.removePropertyListener(dirtyListener);
583             wasDirty = oldModel.isDirty();
584         }
585         this.activeSaveable = activeSaveable;
586         firePropertyChange(this, PROP_ACTIVE_SAVEABLE, oldModel, activeSaveable);
587         boolean isDirty = false;
588         if (activeSaveable != null) {
589             activeSaveable.addPropertyListener(dirtyListener);
590             isDirty = activeSaveable.isDirty();
591         }
592         if (isDirty != wasDirty)
593             firePropertyChange(this, PROP_DIRTY, Boolean.valueOf(wasDirty), Boolean.valueOf(isDirty));
594     }
595     
596     /**
597      * Convenience method for switching the active saveable of this participant
598      * to the saveable of the given input.
599      * @param shell a shell
600      * @param input the compare input about to be displayed
601      * @param cancelAllowed whether the display of the compare input can be canceled
602      * @param monitor a progress monitor or <code>null</code> if progress reporting is not required
603      * @return whether the user choose to continue with the display of the given compare input
604      * @throws CoreException
605      */

606     public boolean checkForBufferChange(Shell shell, ISynchronizationCompareInput input, boolean cancelAllowed, IProgressMonitor monitor) throws CoreException {
607         SaveableComparison currentBuffer = getActiveSaveable();
608         SaveableComparison targetBuffer = input.getSaveable();
609         if (monitor == null)
610             monitor = new NullProgressMonitor();
611         try {
612             ModelParticipantAction.handleTargetSaveableChange(shell, targetBuffer, currentBuffer, cancelAllowed, Policy.subMonitorFor(monitor, 10));
613         } catch (InterruptedException JavaDoc e) {
614             return false;
615         }
616         setActiveSaveable(targetBuffer);
617         return true;
618     }
619     
620     /**
621      * Return the list of model providers that are enabled for the participant.
622      * By default, the list is those model providers that contain mappings
623      * in the scope. Subclasses may override to add additional model providers.
624      * @return the list of model providers that are active for the participant
625      */

626     public ModelProvider[] getEnabledModelProviders() {
627         return getContext().getScope().getModelProviders();
628     }
629     
630     /* (non-Javadoc)
631      * @see org.eclipse.team.ui.synchronize.AbstractSynchronizeParticipant#getPreferencePages()
632      */

633     public PreferencePage[] getPreferencePages() {
634         List JavaDoc pages = new ArrayList JavaDoc();
635         SyncViewerPreferencePage syncViewerPreferencePage = new SyncViewerPreferencePage();
636         syncViewerPreferencePage.setIncludeDefaultLayout(false);
637         pages.add(syncViewerPreferencePage);
638         pages.add(new ModelEnablementPreferencePage());
639         ITeamContentProviderDescriptor[] descriptors = TeamUI.getTeamContentProviderManager().getDescriptors();
640         for (int i = 0; i < descriptors.length; i++) {
641             ITeamContentProviderDescriptor descriptor = descriptors[i];
642             if (isIncluded(descriptor)) {
643                 try {
644                     PreferencePage page = (PreferencePage)descriptor.createPreferencePage();
645                     if (page != null) {
646                         pages.add(page);
647                     }
648                 } catch (CoreException e) {
649                     TeamUIPlugin.log(e);
650                 }
651             }
652         }
653         if (getHandler() != null) {
654             pages.add(new StartupPreferencePage(preferences));
655         }
656         return (PreferencePage[]) pages.toArray(new PreferencePage[pages.size()]);
657     }
658
659     private boolean isIncluded(ITeamContentProviderDescriptor descriptor) {
660         ModelProvider[] providers = getEnabledModelProviders();
661         for (int i = 0; i < providers.length; i++) {
662             ModelProvider provider = providers[i];
663             if (provider.getId().equals(descriptor.getModelProviderId())) {
664                 return true;
665             }
666         }
667         return false;
668     }
669     
670     private SubscriberDiffTreeEventHandler getHandler() {
671         return (SubscriberDiffTreeEventHandler)Utils.getAdapter(context, SubscriberDiffTreeEventHandler.class);
672     }
673     
674 }
675
Popular Tags