Notice: This Wiki is now read only and edits are no longer possible. Please see: https://gitlab.eclipse.org/eclipsefdn/helpdesk/-/wikis/Wiki-shutdown-plan for the plan.
EMF Compare/Specifications/LogicalModelView
Contents
- 1 Logical Model View
- 1.1 Functional specification
- 1.2 Technical specification
Logical Model View
Functional specification
EMF Compare does not act simply on the selected files, but on their whole logical model (a given model can be split through multiple files through EMF control action). Thanks to that, if you try and compare a model file that reference other model files, the comparison will still be able to take these "other" files into account. For example, if you try and compare a genmodel file (that depends on its underlying ecore file), then both files will be taken into account for the comparison.
The EMF compare Logical Model View allows to see, for a given model (or set of models), the resulting logical model computed by EMF Compare.
- All models that are part of the logical model will be display as a flat list.
- The list will be non editable.
- The model (or set of models) used to compute the logical model will be highlighted in a specific color (to be determined), to remember to the user which model(s) are at the origin of the logical model displayed.
- A contextual menu with classic actions (as those in the Package Explorer View) will be available for each item of the list.
- A new action will be added to this contextual menu : Show In Package Explorer. It will allow to select the corresponding model in the Package Explorer (if it is present).
- A button Link with Editor and Selection will be added in the toolbar of the view. This button will synchronize the Logical Model View to the active editor or the selected element in the Package Explorer View.
- The editors taken into account to populate the View will be: EMF Compare's comparison models editor, Papyrus editors, and EMF Reflective Model editors.
- Any EMF model selected in the Package Explorer View will populate the View.
- This button will be disabled by default.
- When the Logical Model View is opened for the first time, the button is disabled, and no model is displayed in the view, even if one is selected in the Package Explorer View or the active editor.
- When the button is enabled, the synchronization becomes active.
- When the button is disabled, the synchronization becomes inactive. The last logical model computed and displayed in the View will remains until the button was enabled again and a new editor be active or a model was selected, or else the View was closed.
Possible evolutions
The models displayed in the Logical Model View could be presented as trees.
A View Menu button could be added to switch the presentation between flat list and trees.
Technical specification
How to listen to active editor ?
Eclipse allows to listen to active editors with the org.eclipse.ui.IPartService.
IPartService service = PlatformUI.getWorkbench().getActiveWorkbenchWindow().getPartService();
service.addPartListener(new IPartListener() {
@Override
public void partOpened(IWorkbenchPart part) {
}
@Override
public void partDeactivated(IWorkbenchPart part) {
}
@Override
public void partClosed(IWorkbenchPart part) {
}
@Override
public void partBroughtToTop(IWorkbenchPart part) {
}
@Override
public void partActivated(IWorkbenchPart part) {
}
});
When the focus switch to an editor, the partActivated(IWorkbenchPart part) is called. We need to insert our code here. The listener has to be added when the synchronization button is enabled. The listener has to be removed when the synchronization button is disabled.
How to listen to current selection ?
Eclipse allows to listen to the current selection with the org.eclipse.ui.ISelectionService.
ISelectionService service = PlatformUI.getWorkbench().getActiveWorkbenchWindow().getSelectionService();
service.addPostSelectionListener(new ISelectionListener() {
@Override
public void selectionChanged(IWorkbenchPart part, ISelection selection) {
}
});
The listener has to be added when the synchronization button is enabled. The listener has to be removed when the synchronization button is disabled.
How to compute/recompute/retrieve the logical model ?
In all cases, the goal is to call SynchronizationModel getLatestModel() from org.eclipse.emf.compare.ide.ui.internal.logical.EMFResourceMapping. The SynchronizationModel provides a method Set<IResource> getResources(). That's the one we need to poulate our View.
IFiles are IResources. We can create org.eclipse.team.internal.ui.synchronize.LocalResourceTypedElement from IResources. LocalResourceTypedElement implements ITypedElement.
The method org.eclipse.emf.compare.ide.ui.tests.egit.fixture.GitTestRepository.getResourceMappings(IFile file) is a good entry to get an EMFResourceMapping from an IFile.
It is important to execute this code in a separate thread. The computation of the logical model can be a long process. It must not freeze the UI during this time.
In case of an active Editor of type EMF Compare
In this case, the logical model has already been computed. We have to retrieve it.
From an IWorkbenchPart of type org.eclipse.compare.internal.CompareEditor the following code allows to retrieve left, right and ancestor :
IEditorInput input = ((CompareEditor) part).getEditorInput();
if (input instanceof SaveablesCompareEditorInput) {
Object compareResult = ((SaveablesCompareEditorInput) input).getCompareResult();
if (compareResult instanceof ICompareInput) {
ITypedElement left = ((ICompareInput) compareResult).getLeft();
ITypedElement right = ((ICompareInput) compareResult).getRight();
ITypedElement ancestor = ((ICompareInput) compareResult).getAncestor();
}
}
In case of an active Editor of type EMF
In this case, we have to compute the logical model.
The first step is to retrieve the file (org.eclipse.core.resources.IFile) corresponding to the editor. All EMF Editors (Papyrus, Ecore, Reflectives) are WorbenchPart of type org.eclipse.ui.IEditorPart.
IEditorInput editorInput = ((IEditorPart) part).getEditorInput();
if (editorInput instanceof FileEditorInput) {
IFile fileInput = ((FileEditorInput) editorInput).getFile();
}
In case of a selected model in the Package Explorer View
In this case, we have to compute the logical model.
The first step is to retrieve the file (org.eclipse.core.resources.IFile) corresponding to the selection.
In case of Papyrus model, the selection corresponds to a org.eclipse.papyrus.infra.onefile.model.IPapyrusFile or a org.eclipse.papyrus.infra.onefile.model.ISubResourceFile. If this is a IPapyrusFile, getMainFile() allows to retrieve the IFile corresponding. If this is a ISubResourceFile, getFile() allows to retrieve the IFile corresponding.
Allow other types of editors/selection to populate the Logical Model View
We need to allow other types of editors to populate the Logical Model View. An extension point has to be created. This extension will propose to implement this interface :
public interface ILogicalModelEditor {
Collection<IResource> getLogicalModelResources(IWorkbenchPart part);
}
Then, all we have to do is to display the IResources in the Viewer.
We need to allow other types of selection to populate the Logical Model View. An extension point has to be created. This extension will propose to implement this interface :
public interface ILogicalModelSelection {
Collection<IResource> getLogicalModelResources(ISelection selection);
}
Then, all we have to do is to display the IResources in the Viewer.
We could also provide an abstract implementation of this interface with useful methods.
How to display the result of the logical model as a flat view / trees ?
The Common Navigator Framework (CNF) seems to be the appropriate way to display elements in the viewer. The CNF uses the idea of Navigator Content Extensions (NCE) which can refer to a content provider, a label provider and a contextual menu. The Project Explorer View uses the CNF. It will allow us to reuse the label provider and the contextual menu of the Project Explorer View.
More links: