Skip to main content
summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorrschnekenbu2010-07-23 13:35:12 +0000
committerrschnekenbu2010-07-23 13:35:12 +0000
commita8c658f4e821ca24bdc083a9a2016042bc71295d (patch)
treed42750fc0d2c00c49ed3fecc52db0995143e21e8 /plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue
parentf27e36dcf7b8efa4d1f084de5722f7b6d6211fef (diff)
downloadorg.eclipse.papyrus-a8c658f4e821ca24bdc083a9a2016042bc71295d.tar.gz
org.eclipse.papyrus-a8c658f4e821ca24bdc083a9a2016042bc71295d.tar.xz
org.eclipse.papyrus-a8c658f4e821ca24bdc083a9a2016042bc71295d.zip
Updated the xtext editors not to have an intermediate file for the editing.
Diffstat (limited to 'plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue')
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/PopupEditorConfiguration.java9
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/IEObjectContextUpdater.java40
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/IXTextEditorContextUpdater.java31
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/MultiPageEditorSite.java540
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PartReactivationUtil.java168
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PopupXtextEditorHelper.java529
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PopupXtextEditorKeyListener.java5
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/StringUtil.java33
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/HighlightingHelper.java161
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/HighlightingReconciler.java291
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/IActionContributor.java47
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/IPartialContentAssistParser.java24
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/ISyntheticResourceProvider.java24
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/OperationHistoryListener.java44
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/PartialContentAssistContextFactory.java37
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/PartialModelEditor.java151
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/SourceViewerHandle.java94
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/SourceViewerHandleFactory.java127
-rw-r--r--plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/SyntheticResourceProvider.java47
19 files changed, 1290 insertions, 1112 deletions
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/PopupEditorConfiguration.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/PopupEditorConfiguration.java
index 8cdf156b2c2..760d38ef05c 100644
--- a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/PopupEditorConfiguration.java
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/PopupEditorConfiguration.java
@@ -21,10 +21,8 @@ import org.eclipse.papyrus.extensionpoints.editors.configuration.IPopupEditorCon
import org.eclipse.papyrus.extensionpoints.editors.ui.IPopupEditorHelper;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.widgets.Composite;
-import org.eclipse.xtext.gmf.glue.edit.part.IEObjectContextUpdater;
import org.eclipse.xtext.gmf.glue.edit.part.IXtextEMFReconciler;
import org.eclipse.xtext.gmf.glue.edit.part.PopupXtextEditorHelper;
-import org.eclipse.xtext.gmf.glue.edit.part.IXTextEditorContextUpdater;
import com.google.inject.Injector;
@@ -69,17 +67,13 @@ public abstract class PopupEditorConfiguration implements IPopupEditorConfigurat
* @return IPopupEditorHelper
*/
public IPopupEditorHelper createPopupEditorHelper(IGraphicalEditPart editPart,
- Injector xtextInjector,
- IEObjectContextUpdater eobjectContextUpdater,
- IXTextEditorContextUpdater xtextEditorContextUpdater,
+ Injector xtextInjector,
IXtextEMFReconciler modelReconciler,
String textToEdit,
String fileExtension) {
return new PopupXtextEditorHelper(editPart,
xtextInjector,
- eobjectContextUpdater,
- xtextEditorContextUpdater,
modelReconciler,
textToEdit,
fileExtension);
@@ -130,6 +124,7 @@ public abstract class PopupEditorConfiguration implements IPopupEditorConfigurat
this.language = "" + language ;
}
+
public IInputValidator getInputValidator() {
// Auto-generated method stub
return null;
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/IEObjectContextUpdater.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/IEObjectContextUpdater.java
deleted file mode 100644
index 8b8fd18e326..00000000000
--- a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/IEObjectContextUpdater.java
+++ /dev/null
@@ -1,40 +0,0 @@
-/*****************************************************************************
- * Copyright (c) 2010 CEA LIST.
- *
- *
- * 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:
- * CEA LIST - Initial API and implementation
- *
- *****************************************************************************/
-
-package org.eclipse.xtext.gmf.glue.edit.part;
-
-import org.eclipse.emf.ecore.EObject;
-
-
-/**
- * @author CEA LIST - Initial contribution and API
- * This interface is used for establishing a link between a textual specification in the context of
- * popup xtext editor, and the corresponding UML model element.
- * It is used for:
- * - preventing the usage of explicit "import" rules in the xtext grammars
- * (in order to have the link towards the context UML model)
- * - determining what is the actual model element being edited
- * (i.e., in the case where multiple popup editors are opened,
- * each editor keeps an up-to-date link with the associated UML model element)
- * An EObjectContextUpdater is passed as a parameter for the creation of a {@link PopupXtextEditorHelper}.
- */
-public interface IEObjectContextUpdater {
-
- /**
- * This method is automatically called when a given popup xtext editor gets the focus.
- * @param context The contextual model element for a given popup xtext editor. This element is then used
- * for scoping, verification, etc.
- */
- void updateContext(EObject context) ;
-}
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/IXTextEditorContextUpdater.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/IXTextEditorContextUpdater.java
deleted file mode 100644
index 25bf4301301..00000000000
--- a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/IXTextEditorContextUpdater.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/*****************************************************************************
- * Copyright (c) 2010 CEA LIST.
- *
- *
- * 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:
- * CEA LIST - Initial API and implementation
- *
- *****************************************************************************/
-package org.eclipse.xtext.gmf.glue.edit.part;
-
-import org.eclipse.xtext.ui.editor.XtextEditor;
-
-/**
- * @author CEA LIST - Initial contribution and API
- * This interface is used for updating the currently selected popup xtext editor
- * (i.e., when multiple editors are opened).
- */
-public interface IXTextEditorContextUpdater {
-
- /**
- * This method is called when a popup xtext editor gets the focus
- * @param currentEditor The newly selected editor
- */
- void updateCurrentEditor(XtextEditor currentEditor) ;
-
-}
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/MultiPageEditorSite.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/MultiPageEditorSite.java
deleted file mode 100644
index 9ce72f41036..00000000000
--- a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/MultiPageEditorSite.java
+++ /dev/null
@@ -1,540 +0,0 @@
-/*******************************************************************************
- * Copyright (c) 2010 itemis AG (http://www.itemis.eu) 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
- *******************************************************************************/
-package org.eclipse.xtext.gmf.glue.edit.part;
-
-
-
-import java.util.ArrayList;
-
-import org.eclipse.core.runtime.Assert;
-import org.eclipse.jface.action.MenuManager;
-import org.eclipse.jface.viewers.ILabelDecorator;
-import org.eclipse.jface.viewers.IPostSelectionProvider;
-import org.eclipse.jface.viewers.ISelectionChangedListener;
-import org.eclipse.jface.viewers.ISelectionProvider;
-import org.eclipse.jface.viewers.SelectionChangedEvent;
-import org.eclipse.swt.widgets.Control;
-import org.eclipse.swt.widgets.Shell;
-import org.eclipse.ui.IActionBars;
-import org.eclipse.ui.IEditorActionBarContributor;
-import org.eclipse.ui.IEditorPart;
-import org.eclipse.ui.IEditorSite;
-import org.eclipse.ui.IKeyBindingService;
-import org.eclipse.ui.INestableKeyBindingService;
-import org.eclipse.ui.IWorkbenchPage;
-import org.eclipse.ui.IWorkbenchPart;
-import org.eclipse.ui.IWorkbenchPartSite;
-import org.eclipse.ui.IWorkbenchWindow;
-import org.eclipse.ui.internal.PartSite;
-import org.eclipse.ui.internal.PopupMenuExtender;
-import org.eclipse.ui.internal.WorkbenchPlugin;
-import org.eclipse.ui.internal.services.INestable;
-import org.eclipse.ui.internal.services.IServiceLocatorCreator;
-import org.eclipse.ui.internal.services.IWorkbenchLocationService;
-import org.eclipse.ui.internal.services.ServiceLocator;
-import org.eclipse.ui.internal.services.WorkbenchLocationService;
-import org.eclipse.ui.part.EditorActionBarContributor;
-import org.eclipse.ui.part.MultiPageSelectionProvider;
-import org.eclipse.ui.services.IDisposable;
-import org.eclipse.ui.services.IServiceLocator;
-import org.eclipse.ui.services.IServiceScopes;
-
-/**
- * Site for a nested editor within a multi-page editor. Selection is handled by
- * forwarding the event to the multi-page editor's selection listeners; most
- * other methods are forwarded to the multi-page editor's site.
- * <p>
- * The base implementation of <code>MultiPageEditor.createSite</code> creates an instance of this class. This class may be instantiated or subclassed.
- * </p>
- *
- *
- */
-public class MultiPageEditorSite implements IEditorSite, INestable {
-
-
- /**
- * The actionBarContributor associated to the site. Can be null. In this case,
- * use the multiEditor ActionBarContributor.
- */
- protected EditorActionBarContributor actionBarContributor;
-
- /**
- * The nested editor.
- */
- private IEditorPart editor;
-
- /**
- * The list of popup menu extenders; <code>null</code> if none registered.
- */
- private ArrayList menuExtenders;
-
- /**
- * The main editor EditorSite.
- */
- public IEditorSite mainEditorSite;
-
- /**
- * The post selection changed listener.
- */
- private ISelectionChangedListener postSelectionChangedListener = null;
-
- /**
- * The selection change listener, initialized lazily; <code>null</code> if
- * not yet created.
- */
- private ISelectionChangedListener selectionChangedListener = null;
-
- /**
- * The selection provider; <code>null</code> if none.
- *
- * @see MultiPageEditorSite#setSelectionProvider(ISelectionProvider)
- */
- private ISelectionProvider selectionProvider = null;
-
- /**
- * The cached copy of the key binding service specific to this multi-page
- * editor site. This value is <code>null</code> if it is not yet
- * initialized.
- */
- private IKeyBindingService service = null;
-
- /**
- * The local service locator for this multi-page editor site. This value is
- * never <code>null</code>.
- */
- private final ServiceLocator serviceLocator;
-
- /**
- * Creates a site for the given editor nested within the given multi-page
- * editor.
- *
- * @param mainEditorSite
- * the multi-page editor
- * @param editor
- * the nested editor
- * @param actionBarContributor
- * @param editDomain
- * The shared editDomain.
- */
- public MultiPageEditorSite(IEditorSite mainEditorSite, IEditorPart editor, EditorActionBarContributor actionBarContributor) {
- Assert.isNotNull(mainEditorSite);
- Assert.isNotNull(editor);
- this.mainEditorSite = mainEditorSite;
- this.editor = editor;
- this.actionBarContributor = actionBarContributor;
-
- final IServiceLocator parentServiceLocator = mainEditorSite;
- IServiceLocatorCreator slc = (IServiceLocatorCreator)parentServiceLocator.getService(IServiceLocatorCreator.class);
- this.serviceLocator = (ServiceLocator)slc.createServiceLocator(mainEditorSite, null, new IDisposable() {
-
- public void dispose() {
- final Control control = ((PartSite)getMainEditorSite()).getPane().getControl();
- if(control != null && !control.isDisposed()) {
- ((PartSite)getMainEditorSite()).getPane().doHide();
- }
- }
- });
-
- initializeDefaultServices();
- }
-
- /**
- * Return the site of the main editor.
- *
- * @return
- */
- private IWorkbenchPartSite getMainEditorSite() {
- return mainEditorSite;
- }
-
- /**
- * Return the EditorSite of the main editor.
- * This is the same object as getMainEditorSite.
- * TODO: Remove this one.
- *
- * @return
- */
- private IEditorSite getMainEditorEditorSite() {
- return mainEditorSite;
- }
-
- /**
- * Initialize the slave services for this site.
- */
- private void initializeDefaultServices() {
- serviceLocator.registerService(IWorkbenchLocationService.class, new WorkbenchLocationService(IServiceScopes.MPESITE_SCOPE, getWorkbenchWindow().getWorkbench(), getWorkbenchWindow(), getMainEditorSite(), this, null, 3));
- }
-
- /**
- * Notifies the multi page editor service that the component within which it
- * exists has become active.
- *
- * @since 3.2
- */
- public final void activate() {
- serviceLocator.activate();
- }
-
- /**
- * Notifies the multi page editor service that the component within which it
- * exists has been deactived.
- *
- * @since 3.2
- */
- public final void deactivate() {
- serviceLocator.deactivate();
- }
-
- /**
- * Dispose the contributions.
- */
- public void dispose() {
- if(menuExtenders != null) {
- for(int i = 0; i < menuExtenders.size(); i++) {
- ((PopupMenuExtender)menuExtenders.get(i)).dispose();
- }
- menuExtenders = null;
- }
-
- // Remove myself from the list of nested key binding services.
- if(service != null) {
- IKeyBindingService parentService = getEditor().getSite().getKeyBindingService();
- if(parentService instanceof INestableKeyBindingService) {
- INestableKeyBindingService nestableParent = (INestableKeyBindingService)parentService;
- nestableParent.removeKeyBindingService(this);
- }
- service = null;
- }
-
- if(serviceLocator != null) {
- serviceLocator.dispose();
- }
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IEditorSite</code> method returns the EditorActionBarContributor associated
- * to the site if one is defined,
- * or the EditorActionBarContributor of the multiEditor.
- *
- * @return <code>null</code>
- */
- public IEditorActionBarContributor getActionBarContributor() {
-
- // If we use an action bar contributor, look for a registered ActionBarContributor.
- // TODO : enable next asap
- // ActionBarContributor contributor = multiPageEditor.getEditorSite().getActionBarContributor();
- // if(contributor instanceof ComposedActionBarContributor)
- // {
- // ComposedActionBarContributor composedContributor = (ComposedActionBarContributor)contributor;
- // return composedContributor.getContributorFor(editor);
- // }
-
- // Return the main ActionBarContributor, usually ComposedActionBarContributor
-
- if(actionBarContributor != null)
- return actionBarContributor;
- else
- return getMainEditorEditorSite().getActionBarContributor();
- // return null;
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IEditorSite</code> method forwards to the multi-page editor to
- * return the action bars.
- *
- * @return The action bars from the parent multi-page editor.
- */
- public IActionBars getActionBars() {
- return getMainEditorEditorSite().getActionBars();
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.core.runtime.IAdaptable#getAdapter(java.lang.Class)
- */
- public Object getAdapter(Class adapter) {
- return null;
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IWorkbenchPartSite</code> method forwards to the multi-page editor
- * to return the decorator manager.
- *
- * @return The decorator from the workbench window.
- * @deprecated use IWorkbench.getDecoratorManager()
- */
- @Deprecated
- public ILabelDecorator getDecoratorManager() {
- return getWorkbenchWindow().getWorkbench().getDecoratorManager().getLabelDecorator();
- }
-
- /**
- * Returns the nested editor.
- *
- * @return the nested editor
- */
- public IEditorPart getEditor() {
- return editor;
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IWorkbenchPartSite</code> method returns an empty string since the
- * nested editor is not created from the registry.
- *
- * @return An empty string.
- */
- public String getId() {
- return ""; //$NON-NLS-1$
- }
-
- /*
- * (non-Javadoc) Method declared on IEditorSite.
- */
- public IKeyBindingService getKeyBindingService() {
- if(service == null) {
- service = getMainEditorEditorSite().getKeyBindingService();
- if(service instanceof INestableKeyBindingService) {
- INestableKeyBindingService nestableService = (INestableKeyBindingService)service;
- service = nestableService.getKeyBindingService(this);
-
- } else {
- /*
- * This is an internal reference, and should not be copied by
- * client code. If you are thinking of copying this, DON'T DO
- * IT.
- */
- WorkbenchPlugin
- .log("MultiPageEditorSite.getKeyBindingService() Parent key binding service was not an instance of INestableKeyBindingService. It was an instance of " + service.getClass().getName() + " instead."); //$NON-NLS-1$ //$NON-NLS-2$
- }
- }
- return service;
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IWorkbenchPartSite</code> method forwards to the multi-page editor
- * to return the workbench page.
- *
- * @return The workbench page in which this editor site resides.
- */
- public IWorkbenchPage getPage() {
- return getMainEditorSite().getPage();
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.eclipse.ui.IWorkbenchPartSite#getPart()
- */
- public IWorkbenchPart getPart() {
- return editor;
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IWorkbenchPartSite</code> method returns an empty string since the
- * nested editor is not created from the registry.
- *
- * @return An empty string.
- */
- public String getPluginId() {
- return ""; //$NON-NLS-1$
- }
-
- /**
- * Returns the post selection change listener which listens to the nested
- * editor's selection changes.
- *
- * @return the post selection change listener.
- */
- private ISelectionChangedListener getPostSelectionChangedListener() {
- if(postSelectionChangedListener == null) {
- postSelectionChangedListener = new ISelectionChangedListener() {
-
- public void selectionChanged(SelectionChangedEvent event) {
- MultiPageEditorSite.this.handlePostSelectionChanged(event);
- }
- };
- }
- return postSelectionChangedListener;
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IWorkbenchPartSite</code> method returns an empty string since the
- * nested editor is not created from the registry.
- *
- * @return An empty string.
- */
- public String getRegisteredName() {
- return ""; //$NON-NLS-1$
- }
-
- /**
- * Returns the selection changed listener which listens to the nested
- * editor's selection changes, and calls <code>handleSelectionChanged</code> .
- *
- * @return the selection changed listener
- */
- private ISelectionChangedListener getSelectionChangedListener() {
- if(selectionChangedListener == null) {
- selectionChangedListener = new ISelectionChangedListener() {
-
- public void selectionChanged(SelectionChangedEvent event) {
- MultiPageEditorSite.this.handleSelectionChanged(event);
- }
- };
- }
- return selectionChangedListener;
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IWorkbenchPartSite</code> method returns the selection provider set
- * by <code>setSelectionProvider</code>.
- *
- * @return The current selection provider.
- */
- public ISelectionProvider getSelectionProvider() {
- return selectionProvider;
- }
-
- public final Object getService(final Class key) {
- return serviceLocator.getService(key);
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IWorkbenchPartSite</code> method forwards to the multi-page editor
- * to return the shell.
- *
- * @return The shell in which this editor site resides.
- */
- public Shell getShell() {
- return getMainEditorSite().getShell();
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IWorkbenchPartSite</code> method forwards to the multi-page editor
- * to return the workbench window.
- *
- * @return The workbench window in which this editor site resides.
- */
- public IWorkbenchWindow getWorkbenchWindow() {
- return getMainEditorSite().getWorkbenchWindow();
- }
-
- /**
- * Handles a post selection changed even from the nexted editor.
- * <p>
- * Subclasses may extend or reimplement this method
- *
- * @param event
- * the event
- *
- * @since 3.2
- */
- protected void handlePostSelectionChanged(SelectionChangedEvent event) {
- ISelectionProvider parentProvider = getMainEditorSite().getSelectionProvider();
- if(parentProvider instanceof MultiPageSelectionProvider) {
- SelectionChangedEvent newEvent = new SelectionChangedEvent(parentProvider, event.getSelection());
- MultiPageSelectionProvider prov = (MultiPageSelectionProvider)parentProvider;
- prov.firePostSelectionChanged(newEvent);
- }
- }
-
- /**
- * Handles a selection changed event from the nested editor. The default
- * implementation gets the selection provider from the multi-page editor's
- * site, and calls <code>fireSelectionChanged</code> on it (only if it is an
- * instance of <code>MultiPageSelectionProvider</code>), passing a new event
- * object.
- * <p>
- * Subclasses may extend or reimplement this method.
- * </p>
- *
- * @param event
- * the event
- */
- protected void handleSelectionChanged(SelectionChangedEvent event) {
- ISelectionProvider parentProvider = getMainEditorSite().getSelectionProvider();
- if(parentProvider instanceof MultiPageSelectionProvider) {
- SelectionChangedEvent newEvent = new SelectionChangedEvent(parentProvider, event.getSelection());
- MultiPageSelectionProvider prov = (MultiPageSelectionProvider)parentProvider;
- prov.fireSelectionChanged(newEvent);
- }
- }
-
- public final boolean hasService(final Class key) {
- return serviceLocator.hasService(key);
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IWorkbenchPartSite</code> method forwards to the multi-page editor
- * for registration.
- *
- * @param menuManager
- * The menu manager
- * @param selProvider
- * The selection provider.
- */
- public void registerContextMenu(MenuManager menuManager, ISelectionProvider selProvider) {
- getMainEditorSite().registerContextMenu(menuManager, selProvider);
- }
-
- public final void registerContextMenu(final MenuManager menuManager, final ISelectionProvider selectionProvider, final boolean includeEditorInput) {
- registerContextMenu(getId(), menuManager, selectionProvider, includeEditorInput);
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IWorkbenchPartSite</code> method forwards to the multi-page editor
- * for registration.
- *
- * @param menuID
- * The identifier for the menu.
- * @param menuMgr
- * The menu manager
- * @param selProvider
- * The selection provider.
- */
- public void registerContextMenu(String menuID, MenuManager menuMgr, ISelectionProvider selProvider) {
- if(menuExtenders == null) {
- menuExtenders = new ArrayList(1);
- }
- PartSite.registerContextMenu(menuID, menuMgr, selProvider, true, editor, menuExtenders);
- }
-
- public final void registerContextMenu(final String menuId, final MenuManager menuManager, final ISelectionProvider selectionProvider, final boolean includeEditorInput) {
- if(menuExtenders == null) {
- menuExtenders = new ArrayList(1);
- }
- PartSite.registerContextMenu(menuId, menuManager, selectionProvider, includeEditorInput, editor, menuExtenders);
- }
-
- /**
- * The <code>MultiPageEditorSite</code> implementation of this <code>IWorkbenchPartSite</code> method remembers the selection provider,
- * and also hooks a listener on it, which calls <code>handleSelectionChanged</code> when a selection changed event
- * occurs.
- *
- * @param provider
- * The selection provider.
- * @see MultiPageEditorSite#handleSelectionChanged(SelectionChangedEvent)
- */
- public void setSelectionProvider(ISelectionProvider provider) {
- ISelectionProvider oldSelectionProvider = selectionProvider;
- selectionProvider = provider;
- if(oldSelectionProvider != null) {
- oldSelectionProvider.removeSelectionChangedListener(getSelectionChangedListener());
- if(oldSelectionProvider instanceof IPostSelectionProvider) {
- ((IPostSelectionProvider)oldSelectionProvider).removePostSelectionChangedListener(getPostSelectionChangedListener());
- }
- }
- if(selectionProvider != null) {
- selectionProvider.addSelectionChangedListener(getSelectionChangedListener());
- if(selectionProvider instanceof IPostSelectionProvider) {
- ((IPostSelectionProvider)selectionProvider).addPostSelectionChangedListener(getPostSelectionChangedListener());
- }
- }
- }
-} \ No newline at end of file
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PartReactivationUtil.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PartReactivationUtil.java
deleted file mode 100644
index 6fbd1fda80a..00000000000
--- a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PartReactivationUtil.java
+++ /dev/null
@@ -1,168 +0,0 @@
-/*******************************************************************************
- * Copyright (c) 2009 itemis AG (http://www.itemis.eu) 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
- *******************************************************************************/
-package org.eclipse.xtext.gmf.glue.edit.part;
-
-import org.eclipse.core.commands.operations.IOperationHistory;
-import org.eclipse.core.commands.operations.IUndoContext;
-import org.eclipse.core.commands.operations.OperationHistoryFactory;
-import org.eclipse.papyrus.core.utils.EditorUtils;
-import org.eclipse.papyrus.editor.PapyrusMultiDiagramEditor;
-import org.eclipse.papyrus.extensionpoints.editors.preferences.PapyrusEmbeddedEditorsPreferencePage;
-import org.eclipse.ui.IActionBars;
-import org.eclipse.ui.IEditorPart;
-import org.eclipse.ui.IEditorSite;
-import org.eclipse.ui.IViewPart;
-import org.eclipse.ui.IViewReference;
-import org.eclipse.ui.IWorkbenchCommandConstants;
-import org.eclipse.ui.IWorkbenchPage;
-import org.eclipse.ui.IWorkbenchPart;
-import org.eclipse.ui.IWorkbenchPartSite;
-import org.eclipse.ui.PlatformUI;
-import org.eclipse.ui.handlers.IHandlerService;
-import org.eclipse.ui.keys.IBindingService;
-import org.eclipse.ui.operations.LinearUndoViolationUserApprover;
-import org.eclipse.ui.operations.OperationHistoryActionHandler;
-import org.eclipse.ui.operations.RedoActionHandler;
-import org.eclipse.ui.operations.UndoActionHandler;
-import org.eclipse.ui.part.MultiPageEditorSite;
-import org.eclipse.ui.texteditor.IAbstractTextEditorHelpContextIds;
-import org.eclipse.ui.texteditor.ITextEditorActionConstants;
-import org.eclipse.ui.texteditor.ResourceAction;
-import org.eclipse.ui.texteditor.TextOperationAction;
-
-/**
- * When closing the popup {@link XtextEditor}, the keybindings are lost. This tool offers a hack to restore them.
- *
- * @author koehnlein
- */
-public class PartReactivationUtil {
-
- /**
- * Hack: Reactivate the given editor to restore its keybindings. Unfortunately that only works by switching to
- * another part and back. If there is no other part, we use Java reflection to unset the active part first.
- *
- * @param partToBeReactivated
- */
- public static void forceReactivation(IWorkbenchPart partToBeReactivated) {
- try {
-// IWorkbenchPage page = partToBeReactivated.getSite().getPage();
-// IWorkbenchPart otherVisiblePart = findOtherVisiblePart(page, partToBeReactivated);
-// if (otherVisiblePart != null) {
-// page.activate(otherVisiblePart);
-// } else {
-// // evil reflective call of invisible method
-// Method declaredMethod = page.getClass().getDeclaredMethod("setActivePart", IWorkbenchPart.class,
-// Boolean.TYPE);
-// declaredMethod.setAccessible(true);
-// declaredMethod.invoke(page, null, true);
-// }
-
- //EditorUtils.lookupActiveDiagramEditor().setFocus() ;
-
- //EditorUtils.getMultiDiagramEditor().createPartControl(EditorUtils.getMultiDiagramEditor()) ;
- //EditorUtils.getMultiDiagramEditor().getSite().getPage().activate(partToBeReactivated) ;
-
- //PopupXtextEditorHelper.multiPageSelectionProvider.removeSelectionChangedListener(listener) ;
- //PartSite tot = (PartSite)EditorUtils.getMultiDiagramEditor().getEditorSite() ;
-
-// for (Field f :tot.getClass().getFields()) {
-// System.out.println(f);
-// }
- //((KeyBindingService)EditorUtils.getMultiDiagramEditor().getEditorSite().getKeyBindingService()).dispose() ;
-// Field keyBindingServiceField = PartSite.class.getDeclaredField("keyBindingService") ;
-// keyBindingServiceField.setAccessible(true) ;
-// keyBindingServiceField.set(EditorUtils.getMultiDiagramEditor().getSite(), PopupXtextEditorHelper.oldKeyBindingService) ;
-//
-// IHandlerService service = (IHandlerService) Workbench.getInstance().getService(IHandlerService.class) ;
-// IBindingService bindingService = (IBindingService) Workbench.getInstance().getService(IBindingService.class);
-
- //Object o = bindingService.getActiveBindingsFor("org.eclipse.ui.edit.undo") ;
-// Binding binding = bindingService.getPerfectMatch(bindingService.getActiveBindingsFor("org.eclipse.ui.edit.undo")[0]) ;
-// IWorkbenchPart p = EditorUtils.getMultiDiagramEditor().getSite().getPart() ;
-// IHandler handler = binding.getParameterizedCommand().getCommand().getHandler() ;
-// ActionHandler handler2 = (ActionHandler)handler ;
-// Object o = handler2.getAction() ;
-// System.out.println(binding) ;
-// reCreateUndoRedoActions() ;
-// EditorUtils.getMultiDiagramEditor().getServicesRegistry().disposeService() ;
-// Field servicesRegistryField = CoreMultiDiagramEditor.class.getDeclaredField("servicesRegistry") ;
-// servicesRegistryField.setAccessible(true) ;
-// servicesRegistryField.set(EditorUtils.getMultiDiagramEditor(), null) ;
-
- //EditorUtils.getMultiDiagramEditor().getSite().getPage().activate(EditorUtils.getMultiDiagramEditor()) ;
- //EditorUtils.getMultiDiagramEditor().getSite().getKeyBindingService() ;
-
- //EditorUtils.getMultiDiagramEditor().getSite().setSelectionProvider(PopupXtextEditorHelper.multiPageSelectionProvider) ;
-// EditorUtils.getMultiDiagramEditor().getSite().getKeyBindingService() ;
-//
-//
-// //((KeyBindingService)EditorUtils.getMultiDiagramEditor().getEditorSite().getKeyBindingService()).dispose() ;
-//
-// IWorkbenchPage page = partToBeReactivated.getSite().getPage();
-// page = EditorUtils.getMultiDiagramEditor().getEditorSite().getPage() ;
-// IWorkbenchPart otherVisiblePart = findOtherVisiblePart(page, partToBeReactivated);
-// if (otherVisiblePart != null) {
-// page.activate(otherVisiblePart);
-// } else {
-// // evil reflective call of invisible method
-// Method declaredMethod = page.getClass().getDeclaredMethod("setActivePart", IWorkbenchPart.class,
-// Boolean.TYPE);
-// declaredMethod.setAccessible(true);
-// declaredMethod.invoke(page, null, true);
-// }
-
- //((org.eclipse.papyrus.sasheditor.internal.eclipsecopy.MultiPageEditorSite)partToBeReactivated.getSite()).activate() ;
-
- //((KeyBindingService)EditorUtils.getMultiDiagramEditor().getEditorSite().getKeyBindingService()).dispose() ;
- //EditorUtils.getMultiDiagramEditor().getActiveEditor().setFocus() ;
- //((KeyBindingService)EditorUtils.getMultiDiagramEditor().getEditorSite().getKeyBindingService()).activateKeyBindingService(site) ;
- //((org.eclipse.papyrus.sasheditor.internal.eclipsecopy.MultiPageEditorSite)partToBeReactivated.getSite()).activate() ;
- //((PapyrusMultiDiagramEditor)EditorUtils.getMultiDiagramEditor()).getISashWindowsContainer().refreshTabs() ;
- //((KeyBindingService)EditorUtils.getMultiDiagramEditor().getEditorSite().getService(KeyBindingService.class)).dispose() ;
- //((PapyrusMultiDiagramEditor)EditorUtils.getMultiDiagramEditor()).getISashWindowsContainer().refreshTabs() ;
-
- //((PapyrusMultiDiagramEditor)EditorUtils.getMultiDiagramEditor()).getISashWindowsContainer().refreshTabs() ;
-
- //IEditorSite toto = EditorUtils.getMultiDiagramEditor().getEditorSite() ;
- //((KeyBindingService)partToBeReactivated.getSite().getKeyBindingService()).activateKeyBindingService(toto) ;
- //((KeyBindingService)EditorUtils.getMultiDiagramEditor().getEditorSite().getKeyBindingService()).dispose() ;
- //((KeyBindingService)EditorUtils.getMultiDiagramEditor().getEditorSite().getKeyBindingService()).activateKeyBindingService(null) ;
- //((KeyBindingService)EditorUtils.getMultiDiagramEditor().getEditorSite().getKeyBindingService()).activateKeyBindingService(partToBeReactivated.getSite()) ;
- //EditorSite toto2 = (EditorSite)toto ;
- //toto2.dispose() ;
- //toto2.activateActionBars(true) ;
-
- //partToBeReactivated.setFocus() ;
- //partToBeReactivated.getSite().getPage().activate(partToBeReactivated) ;
-
- //EditorUtils.getMultiDiagramEditor().getSite().getPage().activate(partToBeReactivated) ;
-
-
- } catch (Exception e) {
- e.printStackTrace();
- }
- }
-
- private static IWorkbenchPart findOtherVisiblePart(IWorkbenchPage page, IWorkbenchPart partToBeReactivated) {
- IViewReference[] viewReferences = page.getViewReferences();
- if (viewReferences != null) {
- for (IViewReference viewReference : viewReferences) {
- // hmmm, getPartState does always return IWorkbenchPage.STATE_RESTORED
- if (page.getPartState(viewReference) == IWorkbenchPage.STATE_RESTORED) {
- IViewPart part = viewReference.getView(false);
- if (part != partToBeReactivated) {
- return part;
- }
- }
- }
- }
- return null;
- }
-
-
-}
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PopupXtextEditorHelper.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PopupXtextEditorHelper.java
index 18fc1c137d3..b7322c08dbf 100644
--- a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PopupXtextEditorHelper.java
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PopupXtextEditorHelper.java
@@ -7,83 +7,70 @@
*******************************************************************************/
package org.eclipse.xtext.gmf.glue.edit.part;
-import java.io.File;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.PrintStream;
-import java.lang.reflect.Field;
-import javax.swing.text.JTextComponent.KeyBinding;
+import java.util.List;
+import java.util.Map;
-
-import org.eclipse.core.commands.IHandler;
-import org.eclipse.core.resources.IFile;
+import org.eclipse.core.commands.operations.IOperationHistory;
+import org.eclipse.core.commands.operations.IUndoContext;
+import org.eclipse.core.commands.operations.OperationHistoryFactory;
+import org.eclipse.core.expressions.Expression;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.Status;
import org.eclipse.draw2d.IFigure;
import org.eclipse.draw2d.geometry.Rectangle;
-import org.eclipse.emf.common.util.URI;
import org.eclipse.emf.ecore.EObject;
import org.eclipse.emf.ecore.resource.Resource;
-import org.eclipse.gef.EditPartViewer;
-import org.eclipse.gmf.runtime.diagram.ui.editparts.DiagramRootEditPart;
import org.eclipse.gmf.runtime.diagram.ui.editparts.IGraphicalEditPart;
import org.eclipse.gmf.runtime.diagram.ui.parts.DiagramEditDomain;
import org.eclipse.gmf.runtime.diagram.ui.parts.IDiagramEditDomain;
-import org.eclipse.jface.bindings.Binding;
+import org.eclipse.jface.action.IAction;
import org.eclipse.jface.commands.ActionHandler;
-import org.eclipse.jface.text.BadLocationException;
-import org.eclipse.jface.viewers.ISelectionProvider;
-import org.eclipse.papyrus.core.utils.EditorUtils;
+import org.eclipse.jface.text.ITextOperationTarget;
+import org.eclipse.jface.text.source.ISourceViewer;
+import org.eclipse.jface.text.source.SourceViewer;
+import org.eclipse.jface.text.templates.TemplateException;
import org.eclipse.papyrus.extensionpoints.editors.ui.IPopupEditorHelper;
-//import org.eclipse.papyrus.sasheditor.internal.eclipsecopy.MultiPageEditorSite;
import org.eclipse.swt.SWT;
import org.eclipse.swt.custom.StyledText;
+import org.eclipse.swt.events.DisposeEvent;
+import org.eclipse.swt.events.DisposeListener;
import org.eclipse.swt.events.FocusEvent;
import org.eclipse.swt.events.FocusListener;
import org.eclipse.swt.graphics.Font;
import org.eclipse.swt.graphics.FontData;
+import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.layout.FillLayout;
import org.eclipse.swt.widgets.Composite;
-import org.eclipse.swt.widgets.Control;
-import org.eclipse.swt.widgets.Decorations;
import org.eclipse.swt.widgets.Shell;
+import org.eclipse.text.undo.DocumentUndoManagerRegistry;
+import org.eclipse.text.undo.IDocumentUndoManager;
+import org.eclipse.ui.ActiveShellExpression;
import org.eclipse.ui.IEditorInput;
import org.eclipse.ui.IEditorPart;
-import org.eclipse.ui.IEditorSite;
-import org.eclipse.ui.IKeyBindingService;
-import org.eclipse.ui.INestableKeyBindingService;
-import org.eclipse.ui.IPartListener;
-import org.eclipse.ui.IWorkbenchPage;
-import org.eclipse.ui.IWorkbenchPart;
-import org.eclipse.ui.IWorkbenchPartSite;
+import org.eclipse.ui.IWorkbenchCommandConstants;
import org.eclipse.ui.PlatformUI;
+import org.eclipse.ui.console.actions.TextViewerAction;
+import org.eclipse.ui.handlers.IHandlerActivation;
import org.eclipse.ui.handlers.IHandlerService;
-import org.eclipse.ui.internal.KeyBindingService;
-import org.eclipse.ui.internal.PartSite;
-import org.eclipse.ui.internal.Workbench;
-import org.eclipse.ui.internal.WorkbenchPlugin;
-import org.eclipse.ui.internal.services.INestable;
-import org.eclipse.ui.keys.IBindingService;
-import org.eclipse.ui.part.FileEditorInputFactory;
-import org.eclipse.ui.services.IServiceLocator;
+import org.eclipse.ui.texteditor.ITextEditorActionConstants;
+import org.eclipse.ui.texteditor.ITextEditorActionDefinitionIds;
+import org.eclipse.ui.texteditor.IUpdate;
import org.eclipse.xtext.gmf.glue.Activator;
-import org.eclipse.xtext.gmf.glue.editingdomain.ChangeAggregatorAdapter;
-import org.eclipse.xtext.gmf.glue.editingdomain.UpdateXtextResourceTextCommand;
+import org.eclipse.xtext.gmf.glue.partialEditing.ISyntheticResourceProvider;
+import org.eclipse.xtext.gmf.glue.partialEditing.PartialModelEditor;
+import org.eclipse.xtext.gmf.glue.partialEditing.SourceViewerHandle;
+import org.eclipse.xtext.gmf.glue.partialEditing.SourceViewerHandleFactory;
+import org.eclipse.xtext.gmf.glue.partialEditing.OperationHistoryListener;
import org.eclipse.xtext.parser.IParseResult;
-import org.eclipse.xtext.parsetree.CompositeNode;
-import org.eclipse.xtext.parsetree.NodeAdapter;
-import org.eclipse.xtext.parsetree.NodeUtil;
import org.eclipse.xtext.resource.XtextResource;
-import org.eclipse.xtext.ui.editor.CompoundXtextEditorCallback;
-import org.eclipse.xtext.ui.editor.XtextEditor;
-import org.eclipse.xtext.ui.editor.XtextSourceViewer;
-import org.eclipse.xtext.ui.editor.info.ResourceWorkingCopyFileEditorInput;
+
import org.eclipse.xtext.ui.editor.model.IXtextDocument;
import org.eclipse.xtext.util.concurrent.IUnitOfWork;
-import com.google.inject.Binder;
-import com.google.inject.Guice;
+import com.google.common.collect.Lists;
+import com.google.common.collect.Maps;
import com.google.inject.Injector;
-import com.google.inject.Module;
/**
* Base class to handle a small in-diagram XtextEditor.
@@ -111,48 +98,31 @@ import com.google.inject.Module;
public class PopupXtextEditorHelper implements IPopupEditorHelper {
- private static int MIN_EDITOR_WIDTH = 100;
-
- private static int MIN_EDITOR_HEIGHT = 20;
-
private IGraphicalEditPart hostEditPart;
-
private IEditorPart diagramEditor;
-
- private XtextEditor xtextEditor;
-
private int editorOffset;
-
private int initialEditorSize;
-
private int initialDocumentSize;
-
private Composite xtextEditorComposite;
private final Injector xtextInjector;
-
private XtextResource xtextResource;
-
private String semanticElementFragment;
-
- private IEObjectContextUpdater eobjectContextUpdater ;
-
- private IXTextEditorContextUpdater xtextEditorContextUpdater ;
-
private EObject semanticElement ;
-
private String textToEdit ;
-
- private String fileExtension ;
-
- private static int uniqueID = 0 ;
-
- private String temporaryFilePath = "" ;
-
+ /**
+ * The file extension used to dynamically select the appropriate xtext editor
+ */
+ public static String fileExtension ;
private IXtextEMFReconciler modelReconciler;
-
-
- private IPartListener addedPartListener ;
-
+ private ISyntheticResourceProvider resourceProvider ;
+ private SourceViewerHandle sourceViewerHandle ;
+ private PartialModelEditor partialEditor ;
+ private Shell diagramShell ;
+ private OperationHistoryListener operationHistoryListener;
+ /**
+ * The context EObject for this editor. It can be used for content assist, verification, etc.
+ */
+ public static EObject context ;
/**
* This element was originally undocumented in the XText/GMF integration example
@@ -169,19 +139,15 @@ public class PopupXtextEditorHelper implements IPopupEditorHelper {
*
*/
public PopupXtextEditorHelper(IGraphicalEditPart editPart,
- Injector xtextInjector,
- IEObjectContextUpdater eobjectContextUpdater,
- IXTextEditorContextUpdater xtextEditorContextUpdater,
+ Injector xtextInjector,
IXtextEMFReconciler modelReconciler,
String textToEdit,
String fileExtension) {
this.hostEditPart = editPart;
this.xtextInjector = xtextInjector ;
this.textToEdit = "" + textToEdit ;
- this.fileExtension = "" + fileExtension ;
- this.eobjectContextUpdater = eobjectContextUpdater ;
- this.xtextEditorContextUpdater = xtextEditorContextUpdater ;
this.modelReconciler = modelReconciler ;
+ this.fileExtension = "" + fileExtension ;
}
/**
@@ -196,7 +162,7 @@ public class PopupXtextEditorHelper implements IPopupEditorHelper {
if (semanticElement == null) {
return;
}
- this.eobjectContextUpdater.updateContext(semanticElement) ;
+ this.context = semanticElement ;
Resource semanticResource = semanticElement.eResource();
semanticElementFragment = semanticResource.getURIFragment(semanticElement);
@@ -207,36 +173,13 @@ public class PopupXtextEditorHelper implements IPopupEditorHelper {
diagramEditor = ((DiagramEditDomain) diagramEditDomain).getEditorPart();
+ createXtextEditor(null) ;
- try {
- IFile file2 = (IFile) Workbench.getInstance().getActiveWorkbenchWindow().getActivePage().getActiveEditor().getEditorInput().
- getAdapter(IFile.class);
-
- String portablePath = file2.getRawLocation().toPortableString() ;
- portablePath = new String(portablePath.substring(0, portablePath.lastIndexOf("/")+1)) + "tmpXtextFile" + uniqueID++ + fileExtension ;
-
- temporaryFilePath = "" + portablePath ;
- File file = new File(temporaryFilePath);
- FileOutputStream outputStream = null ;
- PrintStream data = null ;
- file.createNewFile();
- outputStream = new FileOutputStream(file) ;
- data = new PrintStream(outputStream) ;
- data.print(textToEdit) ;
- xtextResource = (XtextResource)semanticResource.getResourceSet().createResource(URI.createFileURI(file.getAbsolutePath())) ;
- xtextResource.load(null) ;
-
- createXtextEditor(new ResourceWorkingCopyFileEditorInput(xtextResource));
-
- }
- catch (IOException e) {
- Activator.logError(e);
- }
} catch (Exception e) {
Activator.logError(e);
}
}
-
+
/**
* This element was originally not documented in the XText/GMF integration example.
*
@@ -247,20 +190,14 @@ public class PopupXtextEditorHelper implements IPopupEditorHelper {
* @param isReconcile Determines whether a reconciliation must be performed or not
*/
public void closeEditor(boolean isReconcile) {
- if (xtextEditor != null) {
+ if (sourceViewerHandle != null) {
if (isReconcile) {
try {
- final IXtextDocument xtextDocument = xtextEditor.getDocument();
+ final IXtextDocument xtextDocument = sourceViewerHandle.getDocument();
if (!isDocumentHasErrors(xtextDocument)) {
int documentGrowth = xtextDocument.getLength() - initialDocumentSize ;
String newText = xtextDocument.get(editorOffset , initialEditorSize + documentGrowth) ;
- //UpdateXtextResourceTextCommand.createUpdateCommand(xtextResource, editorOffset,
- // initialEditorSize, newText).execute(null, null);
-
- //TODO: test
- UpdateXtextResourceTextCommand.createUpdateCommand(xtextResource, editorOffset,
- textToEdit.length(), newText).execute(null, null);
-
+ xtextResource = partialEditor.createResource(newText) ;
if (xtextResource.getAllContents().hasNext())
modelReconciler.reconcile(semanticElement, xtextResource.getAllContents().next()) ;
}
@@ -269,27 +206,13 @@ public class PopupXtextEditorHelper implements IPopupEditorHelper {
}
}
xtextEditorComposite.setVisible(false);
- deactivateServices(false) ;
- xtextEditor.dispose() ;
-
- MultiPageEditorSite site = (MultiPageEditorSite)xtextEditor.getSite() ;
- site.dispose() ;
-
- diagramEditor.getSite().getPage().removePartListener(this.addedPartListener) ;
-
- ////////////////////////////////////////////
- // TODO: Deletion of the temp file does not always work...
- // TODO: When it works, how to update the content of the outline?
- try {
- xtextResource.unload() ;
- xtextResource.delete(null) ;
- }
- catch (Exception e) {
- e.printStackTrace() ;
- }
+ xtextEditorComposite.dispose() ;
+
}
}
+
+
/**
* This element was originally not documented in the XText/GMF integration example
*
@@ -300,114 +223,91 @@ public class PopupXtextEditorHelper implements IPopupEditorHelper {
* @param editorInput
*/
private void createXtextEditor(IEditorInput editorInput) throws Exception {
- Shell diagramShell = diagramEditor.getSite().getShell();
- xtextEditorComposite = new Decorations(diagramShell, SWT.RESIZE | SWT.ON_TOP | SWT.BORDER);
+ diagramShell = diagramEditor.getSite().getShell();
+ xtextEditorComposite = new Shell(SWT.RESIZE) ;
xtextEditorComposite.setLayout(new FillLayout());
- IEditorSite editorSite = (IEditorSite)EditorUtils.getMultiDiagramEditor().getSite() ;
- xtextEditor = xtextInjector.getInstance(XtextEditor.class);
- // remove dirty state editor callback
- xtextEditor.setXtextEditorCallback(new CompoundXtextEditorCallback(Guice.createInjector(new Module() {
- public void configure(Binder binder) {
- }
- })));
-
- editorSite = new MultiPageEditorSite((IEditorSite)EditorUtils.getMultiDiagramEditor().getSite(), xtextEditor, null) ;
-
- xtextEditor.init(editorSite, editorInput);
- xtextEditor.createPartControl(xtextEditorComposite);
-
- this.activateServices() ;
-
+ resourceProvider = xtextInjector.getInstance(ISyntheticResourceProvider.class) ;
+ SourceViewerHandleFactory factory = xtextInjector.getInstance(SourceViewerHandleFactory.class) ;
+ sourceViewerHandle = factory.create(xtextEditorComposite, resourceProvider) ;
+ partialEditor = sourceViewerHandle.createPartialEditor("", textToEdit, "") ;
registerKeyListener();
- setEditorRegion();
setEditorBounds();
- xtextEditorComposite.addFocusListener(new FocusListener() {
+ initializeActions();
+ installUndoRedoSupport(sourceViewerHandle.getViewer());
+
+ sourceViewerHandle.getViewer().getTextWidget().addFocusListener(new FocusListener() {
public void focusLost(FocusEvent e) {
- eobjectContextUpdater.updateContext(semanticElement) ;
- xtextEditorContextUpdater.updateCurrentEditor(xtextEditor) ;
+ // TODO Auto-generated method stub
+ context = semanticElement ;
+ closeEditor(true) ;
}
public void focusGained(FocusEvent e) {
- eobjectContextUpdater.updateContext(semanticElement) ;
- xtextEditorContextUpdater.updateCurrentEditor(xtextEditor) ;
+ // TODO Auto-generated method stub
+
+ context = semanticElement ;
}
}) ;
xtextEditorComposite.setVisible(true);
- xtextEditorComposite.forceFocus();
- xtextEditor.setFocus();
-
- IWorkbenchPage page = diagramEditor.getSite().getPage();
- addedPartListener = new IPartListener() {
- public void partActivated(IWorkbenchPart part) {
- closeEditor(false);
- }
- public void partBroughtToTop(IWorkbenchPart part) {
- System.out.println("part brought to top") ;
- }
- public void partClosed(IWorkbenchPart part) {
- closeEditor(false);
- }
- public void partDeactivated(IWorkbenchPart part) {
- closeEditor(false);
- }
- public void partOpened(IWorkbenchPart part) {
- closeEditor(false);
- }
- } ;
- page.addPartListener(this.addedPartListener);
-
- setEditorRegion() ;
- }
+ sourceViewerHandle.getViewer().showAnnotationsOverview(true) ;
+ sourceViewerHandle.getViewer().getTextWidget().setFocus() ;
+ }
+
+ private PopupXtextEditorKeyListener keyListener ;
+
private void registerKeyListener() {
- XtextSourceViewer sourceViewer = (XtextSourceViewer) xtextEditor.getInternalSourceViewer();
- final StyledText xtextTextWidget = sourceViewer.getTextWidget();
- PopupXtextEditorKeyListener keyListener = new PopupXtextEditorKeyListener(this, sourceViewer
- .getContentAssistant());
+ //XtextSourceViewer sourceViewer = (XtextSourceViewer) xtextEditor.getInternalSourceViewer();
+ final StyledText xtextTextWidget = sourceViewerHandle.getViewer().getTextWidget();
+ keyListener =
+ new PopupXtextEditorKeyListener
+ (this, sourceViewerHandle.getViewer().getContentAssistant());
+ //keyListener.installUndoRedoSupport(sourceViewerHandle.getViewer()) ;
xtextTextWidget.addVerifyKeyListener(keyListener);
xtextTextWidget.addKeyListener(keyListener);
}
- /**
- * This element was originally not documented in the XText/GMF integration example
- */
- private void setEditorRegion() throws BadLocationException {
- final IXtextDocument xtextDocument = xtextEditor.getDocument();
- boolean success = xtextEditor.getDocument().modify(new IUnitOfWork<Boolean, XtextResource>() {
-
- public Boolean exec(XtextResource state) throws Exception {
- EObject semanticElementInDocument = state.getEObject(semanticElementFragment);
-
- if (semanticElementInDocument == null) {
- return false;
- }
-
- CompositeNode xtextNode = getCompositeNode(semanticElementInDocument);
- if (xtextNode == null) {
- return false;
- }
-
- editorOffset = xtextNode.getOffset();
- initialEditorSize = xtextNode.getLength() ;
- initialDocumentSize = xtextDocument.getLength();
-
- xtextDocument.replace(editorOffset + 1 + initialEditorSize, 0, "\n");
-
- return true;
- }
-
- });
-
- if (success) {
- xtextEditor.showHighlightRangeOnly(true);
- xtextEditor.setHighlightRange(editorOffset + 1, initialEditorSize, true);
- xtextEditor.setFocus();
- }
- }
+// /**
+// * This element was originally not documented in the XText/GMF integration example
+// */
+// private void setEditorRegion() throws BadLocationException {
+// final IXtextDocument xtextDocument = sourceViewer.getDocument();
+// boolean success = sourceViewer.getDocument().modify(new IUnitOfWork<Boolean, XtextResource>() {
+//
+// public Boolean exec(XtextResource state) throws Exception {
+// EObject semanticElementInDocument = state.getEObject(semanticElementFragment);
+//
+// if (semanticElementInDocument == null) {
+// return false;
+// }
+//
+// CompositeNode xtextNode = getCompositeNode(semanticElementInDocument);
+// if (xtextNode == null) {
+// return false;
+// }
+//
+// editorOffset = xtextNode.getOffset();
+// initialEditorSize = xtextNode.getLength() ;
+// initialDocumentSize = xtextDocument.getLength();
+//
+// //xtextDocument.replace(editorOffset + 1 + initialEditorSize, 0, "\n");
+// xtextDocument.replace(editorOffset + initialEditorSize, 0, "\n");
+//
+// return true;
+// }
+//
+// });
+//
+//// if (success) {
+//// xtextEditor.showHighlightRangeOnly(true);
+//// xtextEditor.setHighlightRange(editorOffset + 1, initialEditorSize, true);
+//// xtextEditor.setFocus();
+//// }
+// }
/**
* This element was originally not documented in the XText/GMF integration example
@@ -417,54 +317,31 @@ public class PopupXtextEditorHelper implements IPopupEditorHelper {
* This still needs some work...
*/
private void setEditorBounds() {
- final IXtextDocument xtextDocument = xtextEditor.getDocument();
- // mind the added newlines
- String editString = "";
- try {
- editString = xtextDocument.get(editorOffset + 1, initialEditorSize);
- } catch (BadLocationException exc) {
- Activator.logError(exc);
- }
- //int numLines = StringUtil.getNumLines(editString);
- int numLines = StringUtil.getNumLines(textToEdit);
- int numColumns = 0;
- for (int i = 0 ; i<xtextDocument.getNumberOfLines();i++) {
- try {
- numColumns = Math.max(xtextDocument.getLineLength(i), numColumns) ;
- } catch (Exception e) {}
- }
-
- IFigure figure = hostEditPart.getFigure();
+
+ String editString = "" + textToEdit ;
+ int[] numLinesNumColums = StringUtil.getNumLinesNumColumns(editString) ;
+ int numLines = numLinesNumColums[0] ;
+ int numColumns = numLinesNumColums[1];
+
+ IFigure figure = hostEditPart.getFigure() ;
Rectangle bounds = figure.getBounds().getCopy();
- DiagramRootEditPart diagramEditPart = (DiagramRootEditPart) hostEditPart.getRoot();
- IFigure contentPane = diagramEditPart.getContentPane();
- contentPane.translateToAbsolute(bounds);
- EditPartViewer viewer = hostEditPart.getViewer();
- Control control = viewer.getControl();
- while (control != null && false == control instanceof Shell) {
- bounds.translate(control.getBounds().x, control.getBounds().y);
- control = control.getParent();
- }
-
+ figure.translateToAbsolute(bounds) ;
+ Point newCoord = diagramShell.getDisplay().map(hostEditPart.getViewer().getControl(), null, new Point(bounds.x, bounds.y)) ;
+ bounds.x = newCoord.x ;
+ bounds.y = newCoord.y ;
+
Font font = figure.getFont();
FontData fontData = font.getFontData()[0];
int fontHeightInPixel = fontData.getHeight();
-
- // TODO: this needs some work...
- int width = Math.max(fontHeightInPixel * (numColumns + 6), hostEditPart.getContentPane().getBounds().width);
- int height = Math.max(fontHeightInPixel * (numLines + 6), MIN_EDITOR_HEIGHT);
+ // TODO: this needs some work...
+ int width = hostEditPart.getContentPane().getBounds().width ;
+ int height = fontHeightInPixel * (numLines+4) ;
+
xtextEditorComposite.setBounds(bounds.x, bounds.y, width, height);
}
- private CompositeNode getCompositeNode(EObject semanticElement) {
- NodeAdapter nodeAdapter = NodeUtil.getNodeAdapter(semanticElement);
- if (nodeAdapter != null) {
- final CompositeNode parserNode = nodeAdapter.getParserNode();
- return parserNode;
- }
- return null;
- }
+
private boolean isDocumentHasErrors(final IXtextDocument xtextDocument) {
return (xtextDocument.readOnly(new IUnitOfWork<Boolean, XtextResource>() {
@@ -474,58 +351,98 @@ public class PopupXtextEditorHelper implements IPopupEditorHelper {
}
}));
}
-
+ protected Status createErrorStatus(String message, TemplateException e) {
+ return new Status(IStatus.ERROR,
+ "org.eclipse.papyrus.property.editor.xtext",message, e);
+
+ }
+
+
+ protected void installUndoRedoSupport(SourceViewer viewer) {
+ IDocumentUndoManager undoManager = DocumentUndoManagerRegistry.getDocumentUndoManager(viewer.getDocument());
+ final IUndoContext context = undoManager.getUndoContext();
+ IOperationHistory operationHistory = OperationHistoryFactory.getOperationHistory() ;
+ operationHistoryListener = new OperationHistoryListener(context, new IUpdate() {
+ public void update() {
+ updateAction(ITextEditorActionConstants.REDO);
+ updateAction(ITextEditorActionConstants.UNDO);
+ }
+ });
+ operationHistory.addOperationHistoryListener(operationHistoryListener);
+ }
+
+ private Map<String, org.eclipse.ui.console.actions.TextViewerAction> fGlobalActions= Maps.newHashMapWithExpectedSize(10);
+ private List<String> fSelectionActions = Lists.newArrayListWithExpectedSize(3);
+
+ protected void updateAction(String actionId) {
+ IAction action= fGlobalActions.get(actionId);
+ if (action instanceof IUpdate)
+ ((IUpdate) action).update();
+ }
+
+ protected void uninstallUndoRedoSupport() {
+ IOperationHistory operationHistory = PlatformUI.getWorkbench().getOperationSupport().getOperationHistory();
+ operationHistory.removeOperationHistoryListener(operationHistoryListener);
+ operationHistoryListener = null;
+ }
+ private void initializeActions() {
+ final List<IHandlerActivation> handlerActivations= Lists.newArrayListWithExpectedSize(3);
+ final IHandlerService handlerService= (IHandlerService) PlatformUI.getWorkbench().getAdapter(IHandlerService.class);
+ final Expression expression= new ActiveShellExpression(sourceViewerHandle.getViewer().getControl().getShell());
+
+ diagramShell.addDisposeListener(new DisposeListener() {
+ public void widgetDisposed(DisposeEvent e) {
+ handlerService.deactivateHandlers(handlerActivations);
+ }
+ });
- /**
- * @author CEA LIST
- * This method is used for explicitly re-activating the key binding of the context diagram editor
- */
- @SuppressWarnings({ "restriction", "deprecation" })
- private void activateServices() {
-
- // Get the service
- final IKeyBindingService service = EditorUtils.getMultiDiagramEditor().getEditorSite().getKeyBindingService();
+ TextViewerAction action= new TextViewerAction(sourceViewerHandle.getViewer(), ITextOperationTarget.UNDO);
+ action.setText("UNDO");
+ fGlobalActions.put(ITextEditorActionConstants.UNDO, action);
+ action= new TextViewerAction(sourceViewerHandle.getViewer(), ITextOperationTarget.REDO);
+ action.setText("REDO");
+ fGlobalActions.put(ITextEditorActionConstants.REDO, action);
- final IEditorPart editor = xtextEditor ;
+ action= new TextViewerAction(sourceViewerHandle.getViewer(), ITextOperationTarget.CUT);
+ action.setText("CUT");
+ fGlobalActions.put(ITextEditorActionConstants.CUT, action);
- if(editor != null) {
- // active the service for this inner editor
- if(service instanceof INestableKeyBindingService) {
- final INestableKeyBindingService nestableService = (INestableKeyBindingService)service;
- nestableService.activateKeyBindingService(editor.getEditorSite());
+ action= new TextViewerAction(sourceViewerHandle.getViewer(), ITextOperationTarget.COPY);
+ action.setText("COPY");
+ fGlobalActions.put(ITextEditorActionConstants.COPY, action);
- } else {
- WorkbenchPlugin.log("MultiPageEditorPart.activateSite() Parent key binding service was not an instance of INestableKeyBindingService. It was an instance of " + service.getClass().getName() + " instead."); //$NON-NLS-1$ //$NON-NLS-2$
- }
- }
- }
+ action= new TextViewerAction(sourceViewerHandle.getViewer(), ITextOperationTarget.PASTE);
+ action.setText("PASTE");
+ fGlobalActions.put(ITextEditorActionConstants.PASTE, action);
- /**
- * @author CEA LIST
- *
- * Deactivate services: old nested site if any and keybinding service if there is no active editor.
- * Deactivate the key binding service.
- * Deactivate it only if there is no editor selected.
- *
- * This method is used for explicitly re-activating the key binding of the context diagram editor
- */
- @SuppressWarnings({ "restriction", "deprecation" })
- private void deactivateServices(boolean immediate) {
+ action= new TextViewerAction(sourceViewerHandle.getViewer(), ITextOperationTarget.SELECT_ALL);
+ action.setText("SELECT_ALL");
+ fGlobalActions.put(ITextEditorActionConstants.SELECT_ALL, action);
+
+ action= new TextViewerAction(sourceViewerHandle.getViewer(), ISourceViewer.CONTENTASSIST_PROPOSALS);
+ action.setText("CONTENTASSIST_PROPOSALS");
+ fGlobalActions.put(ITextEditorActionConstants.CONTENT_ASSIST, action);
- final IEditorPart editor = xtextEditor;
- final IKeyBindingService service = EditorUtils.getMultiDiagramEditor().getEditorSite().getKeyBindingService();
- if(editor != null || immediate) {
- // There is no selected page, so deactivate the active service.
- if(service instanceof INestableKeyBindingService) {
- final INestableKeyBindingService nestableService = (INestableKeyBindingService)service;
- nestableService.activateKeyBindingService(null);
- } else {
- WorkbenchPlugin.log("MultiPageEditorPart.deactivateSite() Parent key binding service was not an instance of INestableKeyBindingService. It was an instance of " + service.getClass().getName() + " instead."); //$NON-NLS-1$ //$NON-NLS-2$
+ fSelectionActions.add(ITextEditorActionConstants.CUT);
+ fSelectionActions.add(ITextEditorActionConstants.COPY);
+ fSelectionActions.add(ITextEditorActionConstants.PASTE);
+
+ sourceViewerHandle.getViewer().getTextWidget().addFocusListener(new FocusListener() {
+ public void focusLost(FocusEvent e) {
+ handlerService.deactivateHandlers(handlerActivations);
}
- }
+ public void focusGained(FocusEvent e) {
+ IAction action= fGlobalActions.get(ITextEditorActionConstants.REDO);
+ handlerActivations.add(handlerService.activateHandler(IWorkbenchCommandConstants.EDIT_REDO, new ActionHandler(action), expression));
+ action= fGlobalActions.get(ITextEditorActionConstants.UNDO);
+ handlerActivations.add(handlerService.activateHandler(IWorkbenchCommandConstants.EDIT_UNDO, new ActionHandler(action), expression));
+ action= fGlobalActions.get(ITextEditorActionConstants.CONTENT_ASSIST);
+ handlerActivations.add(handlerService.activateHandler(ITextEditorActionDefinitionIds.CONTENT_ASSIST_PROPOSALS, new ActionHandler(action), expression));
+ }
+ });
+
}
-
}
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PopupXtextEditorKeyListener.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PopupXtextEditorKeyListener.java
index 75d3851c245..4123aa99000 100644
--- a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PopupXtextEditorKeyListener.java
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/PopupXtextEditorKeyListener.java
@@ -51,6 +51,10 @@ public class PopupXtextEditorKeyListener extends KeyAdapter implements VerifyKey
this.popupXtextEditorHelper.closeEditor(false);
}
}
+ if ((e.stateMask & SWT.CTRL) != 0 && (keyCode == ' ')) {
+ this.contentAssistant.showPossibleCompletions() ;
+ this.isIgnoreNextESC = true ;
+ }
}
public void verifyKey(VerifyEvent e) {
@@ -65,4 +69,5 @@ public class PopupXtextEditorKeyListener extends KeyAdapter implements VerifyKey
private boolean isContentAssistActive() {
return contentAssistant != null && contentAssistant.hasProposalPopupFocus();
}
+
} \ No newline at end of file
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/StringUtil.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/StringUtil.java
index 4f5cdda23c8..ee203a0d217 100644
--- a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/StringUtil.java
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/edit/part/StringUtil.java
@@ -17,32 +17,25 @@ public class StringUtil {
* @param s
* @return int
*/
- public static int getNumLines(String s) {
+ public static int[] getNumLinesNumColumns(String s) {
int numLines = 1;
+ int numColumns = 0;
+ int[] dimensions = new int[2] ;
+ dimensions[0] = numLines ;
+ dimensions[1] = 0 ;
for (char c : s.toCharArray()) {
if (c == '\n') {
++numLines;
+ dimensions[1] = Math.max(dimensions[1], numColumns) ;
+ numColumns = 0 ;
}
- }
- return numLines;
- }
-
- /**
- * This element comes from the XText/GMF integration example, and was not originally documented.
- * @param s
- * @return int
- */
- public static int getMaxColumns(String s) {
- int maxColumns = 0;
- int currentColumns = 0;
- for (char c : s.toCharArray()) {
- if (c == '\n') {
- maxColumns = Math.max(maxColumns, currentColumns);
- currentColumns = 0;
- } else {
- ++currentColumns;
+ else {
+ ++numColumns;
}
}
- return Math.max(currentColumns, maxColumns);
+ dimensions[0] = numLines ;
+ dimensions[1] = Math.max(dimensions[1], numColumns) ;
+ return dimensions;
}
+
}
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/HighlightingHelper.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/HighlightingHelper.java
new file mode 100644
index 00000000000..291a136202f
--- /dev/null
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/HighlightingHelper.java
@@ -0,0 +1,161 @@
+/*******************************************************************************
+ * Copyright (c) 2010 itemis AG (http://www.itemis.eu) 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
+ *******************************************************************************/
+package org.eclipse.xtext.gmf.glue.partialEditing;
+
+import org.eclipse.jface.util.IPropertyChangeListener;
+import org.eclipse.jface.util.PropertyChangeEvent;
+import org.eclipse.xtext.ui.editor.XtextPresentationReconciler;
+import org.eclipse.xtext.ui.editor.XtextSourceViewer;
+import org.eclipse.xtext.ui.editor.XtextSourceViewerConfiguration;
+import org.eclipse.xtext.ui.editor.preferences.IPreferenceStoreAccess;
+import org.eclipse.xtext.ui.editor.syntaxcoloring.HighlightingPresenter;
+
+import com.google.inject.Inject;
+import com.google.inject.Provider;
+
+/**
+ * @author Sebastian Zarnekow - Initial contribution and API
+ */
+public class HighlightingHelper implements IPropertyChangeListener {
+
+ @Inject
+ private Provider<HighlightingReconciler> reconcilerProvider;
+
+ @Inject
+ private Provider<HighlightingPresenter> presenterProvider;
+
+ @Inject
+ private IPreferenceStoreAccess preferenceStoreAccessor;
+
+ /** Highlighting presenter */
+ private HighlightingPresenter fPresenter;
+ /** Highlighting reconciler */
+ private HighlightingReconciler fReconciler;
+
+ /** The source viewer */
+ private XtextSourceViewer fSourceViewer;
+ /** The source viewer configuration */
+ private XtextSourceViewerConfiguration fConfiguration;
+ /** The presentation reconciler */
+ private XtextPresentationReconciler fPresentationReconciler;
+
+ /**
+ * @param configuration
+ * @param sourceViewer
+ *
+ */
+ public void install(XtextSourceViewerConfiguration configuration, XtextSourceViewer sourceViewer) {
+ fSourceViewer= sourceViewer;
+ fConfiguration= configuration;
+ fPresentationReconciler= (XtextPresentationReconciler) fConfiguration.getPresentationReconciler(sourceViewer);
+ preferenceStoreAccessor.getPreferenceStore().addPropertyChangeListener(this);
+ enable();
+ }
+
+ /**
+ * Enable advanced highlighting.
+ */
+ private void enable() {
+ fPresenter= getPresenterProvider().get();
+ fPresenter.install(fSourceViewer, fPresentationReconciler);
+
+ if (fSourceViewer.getDocument() != null) {
+ fReconciler= reconcilerProvider.get();
+ fReconciler.install(fSourceViewer, fPresenter);
+ }
+ }
+
+ /**
+ *
+ */
+ public void uninstall() {
+ disable();
+ preferenceStoreAccessor.getPreferenceStore().removePropertyChangeListener(this);
+ fSourceViewer= null;
+ fConfiguration= null;
+ fPresentationReconciler= null;
+ }
+
+ /**
+ * Disable advanced highlighting.
+ */
+ private void disable() {
+ if (fReconciler != null) {
+ fReconciler.uninstall();
+ fReconciler= null;
+ }
+
+ if (fPresenter != null) {
+ fPresenter.uninstall();
+ fPresenter= null;
+ }
+ }
+
+ /**
+ * Returns this hightlighter's reconciler.
+ *
+ * @return the highlighter reconciler or <code>null</code> if none
+ */
+ public HighlightingReconciler getReconciler() {
+ return fReconciler;
+ }
+
+ /**
+ * @param reconcilerProvider
+ *
+ */
+ public void setReconcilerProvider(Provider<HighlightingReconciler> reconcilerProvider) {
+ this.reconcilerProvider = reconcilerProvider;
+ }
+
+ /**
+ * @return Provider<HightlightingReconciler>
+ *
+ */
+ public Provider<HighlightingReconciler> getReconcilerProvider() {
+ return reconcilerProvider;
+ }
+
+ /**
+ * @param presenterProvider
+ *
+ */
+
+ public void setPresenterProvider(Provider<HighlightingPresenter> presenterProvider) {
+ this.presenterProvider = presenterProvider;
+ }
+
+ /**
+ * @return Provider<HightlightingPresented>
+ */
+ public Provider<HighlightingPresenter> getPresenterProvider() {
+ return presenterProvider;
+ }
+
+ /**
+ * @param preferenceStoreAccessor
+ *
+ */
+ public void setPreferenceStoreAccessor(IPreferenceStoreAccess preferenceStoreAccessor) {
+ this.preferenceStoreAccessor = preferenceStoreAccessor;
+ }
+
+ /**
+ * @return IPreferenceStoreAccessor
+ *
+ */
+ public IPreferenceStoreAccess getPreferenceStoreAccessor() {
+ return preferenceStoreAccessor;
+ }
+
+ public void propertyChange(PropertyChangeEvent event) {
+ if (fReconciler != null && event.getProperty().contains(".syntaxColorer.tokenStyles"))
+ fReconciler.refresh();
+ }
+}
+
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/HighlightingReconciler.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/HighlightingReconciler.java
new file mode 100644
index 00000000000..add01a1cbbd
--- /dev/null
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/HighlightingReconciler.java
@@ -0,0 +1,291 @@
+/*******************************************************************************
+ * Copyright (c) 2010 itemis AG (http://www.itemis.eu) 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
+ *******************************************************************************/
+package org.eclipse.xtext.gmf.glue.partialEditing;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.eclipse.jface.text.IDocument;
+import org.eclipse.jface.text.ITextInputListener;
+import org.eclipse.jface.text.TextAttribute;
+import org.eclipse.jface.text.TextPresentation;
+import org.eclipse.swt.widgets.Display;
+import org.eclipse.xtext.resource.XtextResource;
+import org.eclipse.xtext.ui.editor.XtextSourceViewer;
+import org.eclipse.xtext.ui.editor.model.IXtextDocument;
+import org.eclipse.xtext.ui.editor.model.IXtextModelListener;
+import org.eclipse.xtext.ui.editor.model.XtextDocument;
+import org.eclipse.xtext.ui.editor.syntaxcoloring.AttributedPosition;
+import org.eclipse.xtext.ui.editor.syntaxcoloring.HighlightingPresenter;
+import org.eclipse.xtext.ui.editor.syntaxcoloring.IHighlightedPositionAcceptor;
+import org.eclipse.xtext.ui.editor.syntaxcoloring.ISemanticHighlightingCalculator;
+import org.eclipse.xtext.ui.editor.syntaxcoloring.ITextAttributeProvider;
+import org.eclipse.xtext.ui.editor.syntaxcoloring.MergingHighlightedPositionAcceptor;
+import org.eclipse.xtext.util.concurrent.IUnitOfWork;
+
+import com.google.inject.Inject;
+
+/**
+ * @author Sebastian Zarnekow - Initial contribution and API
+ */
+public class HighlightingReconciler implements ITextInputListener, IXtextModelListener, IHighlightedPositionAcceptor {
+
+ @Inject(optional=true)
+ private ISemanticHighlightingCalculator calculator;
+
+ @Inject
+ private ITextAttributeProvider attributeProvider;
+
+ /** The source viewer this highlighting reconciler is installed on */
+ private XtextSourceViewer sourceViewer;
+ /** The highlighting presenter */
+ private HighlightingPresenter presenter;
+
+ /** Background job's added highlighted positions */
+ private final List<AttributedPosition> addedPositions = new ArrayList<AttributedPosition>();
+ /** Background job's removed highlighted positions */
+ private List<AttributedPosition> removedPositions = new ArrayList<AttributedPosition>();
+ /** Number of removed positions */
+ private int removedPositionCount;
+
+ /**
+ * Reconcile operation lock.
+ *
+ * @since 3.2
+ */
+ private final Object fReconcileLock = new Object();
+ /**
+ * <code>true</code> if any thread is executing <code>reconcile</code>, <code>false</code> otherwise.
+ *
+ * @since 3.2
+ */
+ private boolean reconciling = false;
+
+ /**
+ * Start reconciling positions.
+ */
+ private void startReconcilingPositions() {
+ presenter.addAllPositions(removedPositions);
+ removedPositionCount = removedPositions.size();
+ }
+
+ /**
+ * Reconcile positions based on the AST subtrees
+ *
+ * @param subtrees
+ * the AST subtrees
+ */
+ private void reconcilePositions(XtextResource resource) {
+ // for (int i= 0, n= subtrees.length; i < n; i++)
+ // subtrees[i].accept(fCollector);
+ MergingHighlightedPositionAcceptor acceptor = new MergingHighlightedPositionAcceptor(calculator);
+ acceptor.provideHighlightingFor(resource, this);
+// calculator.provideHighlightingFor(resource, this);
+ List<AttributedPosition> oldPositions = removedPositions;
+ List<AttributedPosition> newPositions = new ArrayList<AttributedPosition>(removedPositionCount);
+ for (int i = 0, n = oldPositions.size(); i < n; i++) {
+ AttributedPosition current = oldPositions.get(i);
+ if (current != null)
+ newPositions.add(current);
+ }
+ removedPositions = newPositions;
+ }
+
+ /**
+ * Add a position with the given range and highlighting if it does not exist already.
+ * @param offset The range offset
+ * @param length The range length
+ * @param highlighting The highlighting
+ */
+ public void addPosition(int offset, int length, String... ids) {
+ TextAttribute highlighting = ids.length == 1 ?
+ attributeProvider.getAttribute(ids[0])
+ : attributeProvider.getMergedAttributes(ids);
+ boolean isExisting= false;
+ // TODO: use binary search
+ for (int i= 0, n= removedPositions.size(); i < n; i++) {
+ AttributedPosition position= removedPositions.get(i);
+ if (position == null)
+ continue;
+ if (position.isEqual(offset, length, highlighting)) {
+ isExisting= true;
+ removedPositions.set(i, null);
+ removedPositionCount--;
+ break;
+ }
+ }
+
+ if (!isExisting) {
+ AttributedPosition position= presenter.createHighlightedPosition(offset, length, highlighting);
+ addedPositions.add(position);
+ }
+ }
+
+ /**
+ * Update the presentation.
+ *
+ * @param textPresentation
+ * the text presentation
+ * @param addedPositions
+ * the added positions
+ * @param removedPositions
+ * the removed positions
+ */
+ private void updatePresentation(TextPresentation textPresentation, List<AttributedPosition> addedPositions,
+ List<AttributedPosition> removedPositions) {
+ Runnable runnable = presenter.createUpdateRunnable(textPresentation, addedPositions, removedPositions);
+ if (runnable == null)
+ return;
+
+ Display display = getDisplay();
+ display.asyncExec(runnable);
+ }
+
+ private Display getDisplay() {
+ return this.sourceViewer.getControl().getDisplay();
+ }
+
+ /**
+ * Stop reconciling positions.
+ */
+ private void stopReconcilingPositions() {
+ removedPositions.clear();
+ removedPositionCount = 0;
+ addedPositions.clear();
+ }
+
+ /**
+ * Install this reconciler on the given editor and presenter.
+ *
+ * @param editor
+ * the editor
+ * @param sourceViewer
+ * the source viewer
+ * @param presenter
+ * the highlighting presenter
+ */
+ public void install(XtextSourceViewer sourceViewer, HighlightingPresenter presenter) {
+ this.presenter = presenter;
+ this.sourceViewer = sourceViewer;
+ if (calculator != null) {
+ ((IXtextDocument) sourceViewer.getDocument()).addModelListener(this);
+ sourceViewer.addTextInputListener(this);
+ }
+ refresh();
+ }
+
+ /**
+ * Uninstall this reconciler from the editor
+ */
+ public void uninstall() {
+ if (presenter != null)
+ presenter.setCanceled(true);
+
+ if (sourceViewer.getDocument() != null) {
+ if (calculator != null) {
+ XtextDocument document = (XtextDocument) sourceViewer.getDocument();
+ document.removeModelListener(this);
+ sourceViewer.removeTextInputListener(this);
+ }
+ }
+
+ sourceViewer = null;
+ presenter = null;
+ }
+
+ /*
+ * @see org.eclipse.jface.text.ITextInputListener#inputDocumentAboutToBeChanged(org.eclipse.jface.text.IDocument, org.eclipse.jface.text.IDocument)
+ */
+ public void inputDocumentAboutToBeChanged(IDocument oldInput, IDocument newInput) {
+ if (oldInput != null)
+ ((IXtextDocument) oldInput).removeModelListener(this);
+ }
+
+ /*
+ * @see org.eclipse.jface.text.ITextInputListener#inputDocumentChanged(org.eclipse.jface.text.IDocument, org.eclipse.jface.text.IDocument)
+ */
+ public void inputDocumentChanged(IDocument oldInput, IDocument newInput) {
+ if (newInput != null) {
+ refresh();
+ ((IXtextDocument) newInput).addModelListener(this);
+ }
+ }
+
+ /**
+ * Refreshes the highlighting.
+ */
+ public void refresh() {
+ if (calculator != null) {
+ ((XtextDocument) sourceViewer.getDocument()).readOnly(new IUnitOfWork.Void<XtextResource>() {
+ @Override
+ public void process(XtextResource state) throws Exception {
+ modelChanged(state);
+ }
+ });
+ } else {
+ Display display = getDisplay();
+ display.asyncExec(presenter.createSimpleUpdateRunnable());
+ }
+ }
+
+ public void modelChanged(XtextResource resource) {
+ // ensure at most one thread can be reconciling at any time
+ synchronized (fReconcileLock) {
+ if (reconciling)
+ return;
+ reconciling = true;
+ }
+ final HighlightingPresenter highlightingPresenter = presenter;
+ try {
+ if (highlightingPresenter == null)
+ return;
+
+ highlightingPresenter.setCanceled(false);
+
+ if (highlightingPresenter.isCanceled())
+ return;
+
+ startReconcilingPositions();
+
+ if (!highlightingPresenter.isCanceled()) {
+ reconcilePositions(resource);
+ }
+
+ final TextPresentation[] textPresentation = new TextPresentation[1];
+ if (!highlightingPresenter.isCanceled()) {
+ textPresentation[0] = highlightingPresenter.createPresentation(addedPositions, removedPositions);
+ }
+
+ if (!highlightingPresenter.isCanceled())
+ updatePresentation(textPresentation[0], addedPositions, removedPositions);
+
+ stopReconcilingPositions();
+ }
+ finally {
+ synchronized (fReconcileLock) {
+ reconciling = false;
+ }
+ }
+ }
+
+ /**
+ * @param calculator
+ *
+ */
+ public void setCalculator(ISemanticHighlightingCalculator calculator) {
+ this.calculator = calculator;
+ }
+
+ /**
+ * @return ISemanticHighlightingCalculator
+ *
+ */
+ public ISemanticHighlightingCalculator getCalculator() {
+ return calculator;
+ }
+}
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/IActionContributor.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/IActionContributor.java
new file mode 100644
index 00000000000..b144cd697ad
--- /dev/null
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/IActionContributor.java
@@ -0,0 +1,47 @@
+/*******************************************************************************
+ * Copyright (c) 2010 itemis AG (http://www.itemis.eu) 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
+ *******************************************************************************/
+package org.eclipse.xtext.gmf.glue.partialEditing;
+
+import java.util.List;
+
+import com.google.inject.Binding;
+import com.google.inject.Inject;
+import com.google.inject.Injector;
+import com.google.inject.Singleton;
+import com.google.inject.TypeLiteral;
+
+/**
+ *
+ */
+public interface IActionContributor {
+ /**
+ * hook used to contribute any actions on editor start up.
+ * @param editor
+ */
+ public void contributeActions(PartialModelEditor editor);
+
+
+ /**
+ * composite action contributor delegating call to all registered {@link IActionContributor}
+ */
+ @Singleton
+ public class CompositeImpl implements IActionContributor {
+
+ @Inject
+ private Injector injector;
+
+ public void contributeActions(PartialModelEditor editor) {
+ List<Binding<IActionContributor>> bindingsByType = injector.findBindingsByType(TypeLiteral.get(IActionContributor.class));
+ for (Binding<IActionContributor> binding : bindingsByType) {
+ IActionContributor actionContributor = injector.getInstance(binding.getKey());
+ actionContributor.contributeActions(editor);
+ }
+ }
+
+ }
+} \ No newline at end of file
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/IPartialContentAssistParser.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/IPartialContentAssistParser.java
new file mode 100644
index 00000000000..4254ccdc46f
--- /dev/null
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/IPartialContentAssistParser.java
@@ -0,0 +1,24 @@
+/*******************************************************************************
+ * Copyright (c) 2010 itemis AG (http://www.itemis.eu) 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
+ *******************************************************************************/
+package org.eclipse.xtext.gmf.glue.partialEditing;
+
+import org.eclipse.xtext.AbstractRule;
+import org.eclipse.xtext.ui.editor.contentassist.antlr.IContentAssistParser;
+
+/**
+ * @author Sebastian Zarnekow - Initial contribution and API
+ */
+public interface IPartialContentAssistParser extends IContentAssistParser {
+
+ /**
+ * @param rule
+ *
+ */
+ void initializeFor(AbstractRule rule);
+
+}
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/ISyntheticResourceProvider.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/ISyntheticResourceProvider.java
new file mode 100644
index 00000000000..00bde3f1779
--- /dev/null
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/ISyntheticResourceProvider.java
@@ -0,0 +1,24 @@
+/*******************************************************************************
+ * Copyright (c) 2010 itemis AG (http://www.itemis.eu) 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
+ *******************************************************************************/
+package org.eclipse.xtext.gmf.glue.partialEditing;
+
+import org.eclipse.xtext.resource.XtextResource;
+
+import com.google.inject.ImplementedBy;
+
+/**
+ *
+ */
+@ImplementedBy(SyntheticResourceProvider.class)
+public interface ISyntheticResourceProvider {
+ /**
+ * @return XtextResource
+ *
+ */
+ XtextResource createResource();
+} \ No newline at end of file
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/OperationHistoryListener.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/OperationHistoryListener.java
new file mode 100644
index 00000000000..1cc544abb1c
--- /dev/null
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/OperationHistoryListener.java
@@ -0,0 +1,44 @@
+/*******************************************************************************
+ * Copyright (c) 2010 itemis AG (http://www.itemis.eu) 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
+ *******************************************************************************/
+package org.eclipse.xtext.gmf.glue.partialEditing;
+
+import org.eclipse.core.commands.operations.IOperationHistoryListener;
+import org.eclipse.core.commands.operations.IUndoContext;
+import org.eclipse.core.commands.operations.OperationHistoryEvent;
+import org.eclipse.ui.texteditor.IUpdate;
+
+/**
+ *
+ */
+public class OperationHistoryListener implements IOperationHistoryListener {
+ private final IUndoContext context;
+ private final IUpdate update;
+
+ /**
+ * @param context
+ * @param update
+ *
+ */
+ public OperationHistoryListener(IUndoContext context, IUpdate update) {
+ this.context = context;
+ this.update = update;
+ }
+
+ public void historyNotification(OperationHistoryEvent event) {
+ final int type= event.getEventType();
+ switch (type) {
+ case OperationHistoryEvent.UNDONE:
+ case OperationHistoryEvent.REDONE:
+ case OperationHistoryEvent.OPERATION_NOT_OK:
+ // if this is one of our operations
+ if (event.getOperation().hasContext(context)) {
+ update.update();
+ }
+ }
+ }
+} \ No newline at end of file
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/PartialContentAssistContextFactory.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/PartialContentAssistContextFactory.java
new file mode 100644
index 00000000000..b2368590ca0
--- /dev/null
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/PartialContentAssistContextFactory.java
@@ -0,0 +1,37 @@
+/*******************************************************************************
+ * Copyright (c) 2010 itemis AG (http://www.itemis.eu) 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
+ *******************************************************************************/
+package org.eclipse.xtext.gmf.glue.partialEditing;
+
+import org.eclipse.xtext.AbstractRule;
+import org.eclipse.xtext.ui.editor.contentassist.antlr.ParserBasedContentAssistContextFactory;
+
+import com.google.inject.Inject;
+
+/**
+ * @author Sebastian Zarnekow - Initial contribution and API
+ */
+public class PartialContentAssistContextFactory extends ParserBasedContentAssistContextFactory {
+
+ /**
+ * @param partialContentAssistParser
+ *
+ */
+ @Inject
+ public void setPartialParser(IPartialContentAssistParser partialContentAssistParser) {
+ super.setParser(partialContentAssistParser);
+ }
+
+ /**
+ * @param rule
+ *
+ */
+ public void initializeFor(AbstractRule rule) {
+ ((IPartialContentAssistParser) getParser()).initializeFor(rule);
+ }
+
+}
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/PartialModelEditor.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/PartialModelEditor.java
new file mode 100644
index 00000000000..0499773fd0a
--- /dev/null
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/PartialModelEditor.java
@@ -0,0 +1,151 @@
+package org.eclipse.xtext.gmf.glue.partialEditing;
+
+import java.util.Collections;
+
+import org.eclipse.jface.text.BadLocationException;
+import org.eclipse.jface.text.IDocument;
+import org.eclipse.jface.text.IRegion;
+import org.eclipse.jface.text.ISynchronizable;
+import org.eclipse.jface.text.source.AnnotationModel;
+import org.eclipse.jface.text.source.SourceViewer;
+import org.eclipse.xtext.resource.XtextResource;
+import org.eclipse.xtext.ui.editor.model.XtextDocument;
+import org.eclipse.xtext.util.StringInputStream;
+
+/**
+ *
+ */
+public class PartialModelEditor {
+
+ private final SourceViewer viewer;
+ private final boolean insertLineBreaks;
+ private final ISyntheticResourceProvider resourceProvider;
+ //private final Injector xtextInjector ;
+
+ /**
+ * @param viewer
+ * @param resourceProvider
+ * @param insertLineBreaks
+ *
+ */
+ public PartialModelEditor(SourceViewer viewer, ISyntheticResourceProvider resourceProvider, boolean insertLineBreaks) {
+ //this.xtextInjector = xtextInjector ;
+ this.viewer = viewer;
+ this.resourceProvider = resourceProvider;
+ this.insertLineBreaks = insertLineBreaks;
+ }
+
+ /**
+ * @param document
+ * @param prefix
+ * @param editablePart
+ * @param suffix
+ *
+ */
+ public void setModel(XtextDocument document, String prefix, String editablePart, String suffix) {
+ if (insertLineBreaks) {
+ String delimiter = document.getLegalLineDelimiters()[0];
+ prefix = prefix + delimiter;
+ suffix = delimiter + suffix;
+ }
+ String model = prefix + editablePart + suffix;
+ document.set(model);
+ XtextResource resource = createResource(model);
+ document.setInput(resource);
+ AnnotationModel annotationModel = new AnnotationModel();
+ if (document instanceof ISynchronizable) {
+ Object lock= ((ISynchronizable)document).getLockObject();
+ if (lock == null) {
+ lock= new Object();
+ ((ISynchronizable)document).setLockObject(lock);
+ }
+ ((ISynchronizable) annotationModel).setLockObject(lock);
+ }
+ viewer.setDocument(document, annotationModel, prefix.length(), editablePart.length());
+ viewer.getUndoManager().reset();
+ }
+
+ /**
+ * @param content
+ * @return XtextResource
+ *
+ */
+ public XtextResource createResource(String content) {
+ XtextResource result = resourceProvider.createResource();
+ try {
+ result.load(new StringInputStream(content, result.getEncoding()), Collections.emptyMap());
+ } catch (Exception e) {
+ throw new RuntimeException(e);
+ }
+ return result;
+ }
+
+ /**
+ * @param prefix
+ * @param editablePart
+ * @param suffix
+ *
+ */
+ public void updateModel(String prefix, String editablePart, String suffix) {
+ IDocument document= viewer.getDocument();
+ if (insertLineBreaks) {
+ String delimiter = document.getLegalLineDelimiters()[0];
+ prefix = prefix + delimiter;
+ suffix = delimiter + suffix;
+ }
+ String model = prefix + editablePart + suffix;
+ viewer.setRedraw(false);
+ viewer.getUndoManager().disconnect();
+ document.set(model);
+ viewer.setVisibleRegion(prefix.length(), editablePart.length());
+ viewer.getUndoManager().connect(viewer);
+ viewer.setRedraw(true);
+ }
+
+ /**
+ * @param prefix
+ *
+ */
+ public void updatePrefix(String prefix) {
+ try {
+ IDocument document= viewer.getDocument();
+ IRegion visibleRegion = viewer.getVisibleRegion();
+ String editablePart = document.get(visibleRegion.getOffset(), visibleRegion.getLength());
+ int suffixOffset = visibleRegion.getOffset() + visibleRegion.getLength();
+ String suffix = "";
+ if (document.getLength() - suffixOffset > 0) {
+ suffix = document.get(suffixOffset, document.getLength() - suffixOffset);
+ if (insertLineBreaks) {
+ String delimiter = document.getLegalLineDelimiters()[0];
+ suffix = suffix.substring(delimiter.length());
+ }
+ }
+ updateModel(prefix, editablePart, suffix);
+ } catch(BadLocationException e) {
+ throw new RuntimeException(e);
+ }
+ }
+
+ /**
+ * @return String
+ *
+ */
+ public String getEditablePart() {
+ IDocument doc= viewer.getDocument();
+ IRegion visible= viewer.getVisibleRegion();
+ try {
+ return doc.get(visible.getOffset(), visible.getLength());
+ } catch (BadLocationException e) {
+ return ""; //$NON-NLS-1$
+ }
+ }
+
+ /**
+ * @return String
+ *
+ */
+ public String getSerializedModel() {
+ return viewer.getDocument().get();
+ }
+
+}
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/SourceViewerHandle.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/SourceViewerHandle.java
new file mode 100644
index 00000000000..d9b5fb00cea
--- /dev/null
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/SourceViewerHandle.java
@@ -0,0 +1,94 @@
+/*******************************************************************************
+ * Copyright (c) 2010 itemis AG (http://www.itemis.eu) 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
+ *******************************************************************************/
+package org.eclipse.xtext.gmf.glue.partialEditing;
+
+import org.eclipse.xtext.ui.editor.XtextSourceViewer;
+import org.eclipse.xtext.ui.editor.XtextSourceViewerConfiguration;
+import org.eclipse.xtext.ui.editor.model.XtextDocument;
+import org.eclipse.xtext.ui.editor.validation.IValidationIssueProcessor;
+
+import com.google.inject.Injector;
+
+/**
+ *
+ */
+public class SourceViewerHandle {
+ private IValidationIssueProcessor issueProcessor;
+ private final XtextSourceViewer viewer;
+ private final ISyntheticResourceProvider resourceProvider;
+ private final XtextDocument document;
+ private final XtextSourceViewerConfiguration configuration;
+
+ SourceViewerHandle(XtextDocument document, XtextSourceViewer viewer, XtextSourceViewerConfiguration configuration, ISyntheticResourceProvider resourceProvider, Injector xtextInjector) {
+ this.document = document;
+ this.viewer = viewer;
+ this.configuration = configuration;
+ this.resourceProvider = resourceProvider;
+ }
+
+ /**
+ * @param issueProcessor
+ *
+ */
+ public void setIssueProcessor(IValidationIssueProcessor issueProcessor) {
+ this.issueProcessor = issueProcessor;
+ }
+
+ /**
+ * @return IValidationIssueProcessor
+ *
+ */
+ public IValidationIssueProcessor getIssueProcessor() {
+ return issueProcessor;
+ }
+
+ /**
+ * @return XtextSourceViewer
+ *
+ */
+ public XtextSourceViewer getViewer() {
+ return viewer;
+ }
+
+ /**
+ * @return XtextDocument
+ *
+ */
+ public XtextDocument getDocument() {
+ return document;
+ }
+
+ /**
+ * @return XtextSourceViewerConfiguration
+ *
+ */
+ public XtextSourceViewerConfiguration getConfiguration() {
+ return configuration;
+ }
+
+ /**
+ * @param prefix
+ * @param editablePart
+ * @param suffix
+ * @return PartialModelEditor
+ *
+ */
+ public PartialModelEditor createPartialEditor(String prefix, String editablePart, String suffix) {
+ PartialModelEditor result = new PartialModelEditor(viewer, resourceProvider, false);
+ result.setModel(getDocument(), prefix, editablePart, suffix);
+ return result;
+ }
+
+ /**
+ * @return PartialModelEditor
+ *
+ */
+ public PartialModelEditor createPartialEditor() {
+ return createPartialEditor("", "", "");
+ }
+} \ No newline at end of file
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/SourceViewerHandleFactory.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/SourceViewerHandleFactory.java
new file mode 100644
index 00000000000..a633c1d40a8
--- /dev/null
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/SourceViewerHandleFactory.java
@@ -0,0 +1,127 @@
+/*******************************************************************************
+ * Copyright (c) 2010 itemis AG (http://www.itemis.eu) 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
+ *******************************************************************************/
+package org.eclipse.xtext.gmf.glue.partialEditing;
+
+import java.util.Iterator;
+import java.util.List;
+
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.jface.text.source.ISharedTextColors;
+import org.eclipse.jface.text.source.IVerticalRuler;
+import org.eclipse.jface.text.source.VerticalRuler;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.events.DisposeEvent;
+import org.eclipse.swt.events.DisposeListener;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.ui.editors.text.EditorsUI;
+import org.eclipse.ui.texteditor.AnnotationPreference;
+import org.eclipse.ui.texteditor.DefaultMarkerAnnotationAccess;
+import org.eclipse.ui.texteditor.MarkerAnnotationPreferences;
+import org.eclipse.ui.texteditor.SourceViewerDecorationSupport;
+import org.eclipse.xtext.ui.editor.XtextSourceViewer;
+import org.eclipse.xtext.ui.editor.XtextSourceViewerConfiguration;
+import org.eclipse.xtext.ui.editor.model.XtextDocument;
+import org.eclipse.xtext.ui.editor.preferences.IPreferenceStoreAccess;
+import org.eclipse.xtext.ui.editor.quickfix.IssueResolutionProvider;
+import org.eclipse.xtext.ui.editor.validation.AnnotationIssueProcessor;
+import org.eclipse.xtext.ui.editor.validation.IValidationIssueProcessor;
+import org.eclipse.xtext.ui.editor.validation.ValidationJob;
+import org.eclipse.xtext.validation.CheckMode;
+import org.eclipse.xtext.validation.IResourceValidator;
+import org.eclipse.xtext.validation.Issue;
+
+import com.google.common.collect.Iterators;
+import com.google.inject.Inject;
+import com.google.inject.Injector;
+import com.google.inject.Provider;
+
+/**
+ * @author Sebastian Zarnekow - Initial contribution and API
+ */
+public class SourceViewerHandleFactory {
+
+ @Inject
+ private XtextSourceViewer.Factory sourceViewerFactory;
+
+ @Inject
+ private Provider<XtextSourceViewerConfiguration> sourceViewerConfigurationProvider;
+
+ @Inject
+ private Provider<XtextDocument> documentProvider;
+
+ @Inject
+ private IResourceValidator resourceValidator;
+
+ @Inject
+ private IPreferenceStoreAccess preferenceStoreAccess;
+
+ private Injector xtextInjector ;
+
+ protected static final int VERTICAL_RULER_WIDTH= 12;
+
+ /**
+ * @param parent
+ * @param resourceProvider
+ * @return SourceViewerHandle
+ *
+ */
+ public SourceViewerHandle create(Composite parent, ISyntheticResourceProvider resourceProvider) {
+ //final XtextSourceViewer viewer= sourceViewerFactory.createSourceViewer(parent, null, null, false, SWT.BORDER | SWT.V_SCROLL | SWT.H_SCROLL);
+ final IVerticalRuler ruler = new VerticalRuler(VERTICAL_RULER_WIDTH, null) ;
+ final XtextSourceViewer viewer = sourceViewerFactory.createSourceViewer(parent, ruler, null, true, SWT.None);
+ XtextSourceViewerConfiguration viewerConfiguration = sourceViewerConfigurationProvider.get();
+// SourceViewerConfiguration configuration= new SourceViewerConfiguration() {
+// public IContentAssistant getContentAssistant(ISourceViewer sourceViewer) {
+//
+// ContentAssistant assistant= new ContentAssistant();
+// assistant.enableAutoActivation(true);
+// assistant.enableAutoInsert(true);
+// assistant.setContentAssistProcessor(fTemplateProcessor, IDocument.DEFAULT_CONTENT_TYPE);
+// return assistant;
+// }
+// };
+ viewer.configure(viewerConfiguration);
+
+ final SourceViewerDecorationSupport viewerDecorationSupport = new SourceViewerDecorationSupport(viewer, null, new DefaultMarkerAnnotationAccess(), getSharedColors());
+ MarkerAnnotationPreferences annotationPreferences = new MarkerAnnotationPreferences();
+ Iterator<AnnotationPreference> e= Iterators.filter(annotationPreferences.getAnnotationPreferences().iterator(), AnnotationPreference.class);
+ while (e.hasNext())
+ viewerDecorationSupport.setAnnotationPreference(e.next());
+ viewerDecorationSupport.install(preferenceStoreAccess.getPreferenceStore());
+ parent.addDisposeListener(new DisposeListener() {
+ public void widgetDisposed(DisposeEvent e) {
+ viewerDecorationSupport.dispose();
+ }
+ });
+ final XtextDocument document = documentProvider.get();
+ final SourceViewerHandle result = new SourceViewerHandle(document, viewer, viewerConfiguration, resourceProvider, xtextInjector);
+ ValidationJob job = new ValidationJob(resourceValidator, document,
+ new IValidationIssueProcessor() {
+ private AnnotationIssueProcessor annotationIssueProcessor;
+
+ public void processIssues(List<Issue> issues, IProgressMonitor monitor) {
+ IValidationIssueProcessor issueProcessor = result.getIssueProcessor();
+ if (issueProcessor != null)
+ issueProcessor.processIssues(issues, monitor);
+ if (annotationIssueProcessor == null) {
+ annotationIssueProcessor = new AnnotationIssueProcessor(document,
+ viewer.getAnnotationModel(),
+ new IssueResolutionProvider.NullImpl());
+ }
+ if (annotationIssueProcessor != null)
+ annotationIssueProcessor.processIssues(issues, monitor);
+ }
+ }, CheckMode.FAST_ONLY);
+ document.setValidationJob(job);
+ return result;
+ }
+
+ protected ISharedTextColors getSharedColors() {
+ return EditorsUI.getSharedTextColors();
+ }
+}
diff --git a/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/SyntheticResourceProvider.java b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/SyntheticResourceProvider.java
new file mode 100644
index 00000000000..edfafb303e2
--- /dev/null
+++ b/plugins/core/org.eclipse.xtext.gmf.glue/src/org/eclipse/xtext/gmf/glue/partialEditing/SyntheticResourceProvider.java
@@ -0,0 +1,47 @@
+/*******************************************************************************
+ * Copyright (c) 2010 itemis AG (http://www.itemis.eu) 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
+ *******************************************************************************/
+package org.eclipse.xtext.gmf.glue.partialEditing;
+
+import org.eclipse.emf.common.util.URI;
+import org.eclipse.emf.ecore.resource.Resource;
+import org.eclipse.emf.ecore.resource.ResourceSet;
+import org.eclipse.emf.ecore.util.EcoreUtil;
+import org.eclipse.xtext.IGrammarAccess;
+import org.eclipse.xtext.gmf.glue.edit.part.PopupXtextEditorHelper;
+import org.eclipse.xtext.resource.XtextResource;
+import org.eclipse.xtext.ui.resource.IResourceSetProvider;
+
+import com.google.inject.Inject;
+
+/**
+ * @author Sebastian Zarnekow - Initial contribution and API
+ */
+public class SyntheticResourceProvider implements ISyntheticResourceProvider {
+
+ /**
+ *
+ */
+ public static final String SYNTHETIC_SCHEME = "synthetic";
+
+ @Inject
+ private IResourceSetProvider resourceSetProvider;
+
+ @Inject
+ private IGrammarAccess grammarAccess;
+
+ public XtextResource createResource() {
+ ResourceSet resourceSet = resourceSetProvider.get(null);
+ Resource grammarResource = resourceSet.createResource(
+ URI.createURI(SYNTHETIC_SCHEME + ":/" + grammarAccess.getGrammar().getName() + ".xtext"));
+ grammarResource.getContents().add(EcoreUtil.copy(grammarAccess.getGrammar()));
+ XtextResource result = (XtextResource) resourceSet.createResource(
+ URI.createURI(SYNTHETIC_SCHEME + ":/" + grammarAccess.getGrammar().getName() + "." + PopupXtextEditorHelper.fileExtension));
+ resourceSet.getResources().add(result);
+ return result;
+ }
+}

Back to the top