Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorQuentin Le Menez2017-11-23 16:01:02 +0000
committerQuentin Le Menez2017-12-22 11:03:11 +0000
commitba7ed2a3bcea1819b70c50f822694519fa915beb (patch)
treeca6ee533cdf368cbef52f8d05b5ae2a76f8aee18 /layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus
parente99862e1dc1881c570ad724bba4bc6b0b07ed069 (diff)
downloadorg.eclipse.papyrus.incubation-ba7ed2a3bcea1819b70c50f822694519fa915beb.tar.gz
org.eclipse.papyrus.incubation-ba7ed2a3bcea1819b70c50f822694519fa915beb.tar.xz
org.eclipse.papyrus.incubation-ba7ed2a3bcea1819b70c50f822694519fa915beb.zip
Bug 529135 - [Layers] Test to regenerate the model code
- still needed a lot of manual fixing, may have overlooked stuff Change-Id: I6c6435488a04939eddb659d87538e713e6282e39 Signed-off-by: Quentin Le Menez <quentin.lemenez@cea.fr>
Diffstat (limited to 'layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus')
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/Activator.java52
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/BadStateException.java64
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/InstanciationException.java64
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/LayersException.java77
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/NotFoundException.java64
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/PropertyValueFactory.java116
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/command/ComputePropertyValueCommand.java39
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/ExpressionMatcher.java416
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/IValueChangedEventListener.java35
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/ValueChangedEventNotifier.java336
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/ValueChangedEventNotifierFactory.java70
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/ILayerOperatorDescriptorRegistryLoader.java33
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/LayerOperatorDescriptorRegistryLoader.java121
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/LayersConfigModel.java259
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/LayersConfigModelUtils.java113
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/RegistriesLoader.java99
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/DiagramViewChangedEventNotifier.java208
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/DiagramViewChangedEventNotifierFactory.java70
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/DiagramViewEventNotifier.java211
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/IDiagramViewEventListener.java44
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/ILayersTreeEventListener.java67
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/IUmlNamedElementChangedEventListener.java34
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/LayersTreeEventNotifier.java207
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/LayersTreeEventNotifierFactory.java70
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/UmlNamedElementChangedEventNotifier.java181
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/UmlNamedElementChangedEventNotifierFactory.java70
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/package-info.java18
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/BooleanAndOperator.java93
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/BooleanOrOperator.java93
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/CustomPropertyOperatorsInstance.java34
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/FillAverageOperator.java101
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/Collections3.java76
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/DiagramViewToListSynchronizer.java118
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/LayerDiagramViewPredicate.java64
-rwxr-xr-xlayers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/ObservableListView.java353
35 files changed, 4070 insertions, 0 deletions
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/Activator.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/Activator.java
new file mode 100755
index 0000000..0d635da
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/Activator.java
@@ -0,0 +1,52 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model;
+
+import org.eclipse.core.runtime.Plugin;
+import org.eclipse.papyrus.infra.core.log.LogHelper;
+import org.osgi.framework.BundleContext;
+
+public class Activator extends Plugin {
+
+ private static BundleContext context;
+
+ /** Logging helper */
+ public static LogHelper log;
+
+ static BundleContext getContext() {
+ return context;
+ }
+
+ // TODO and the ID ?
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.osgi.framework.BundleActivator#start(org.osgi.framework.BundleContext)
+ */
+ @Override
+ public void start(BundleContext bundleContext) throws Exception {
+ Activator.context = bundleContext;
+ // register the login helper
+ log = new LogHelper(this);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.osgi.framework.BundleActivator#stop(org.osgi.framework.BundleContext)
+ */
+ @Override
+ public void stop(BundleContext bundleContext) throws Exception {
+ Activator.context = null;
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/BadStateException.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/BadStateException.java
new file mode 100755
index 0000000..94f00f7
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/BadStateException.java
@@ -0,0 +1,64 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model;
+
+
+/**
+ * @author cedric dumoulin
+ *
+ */
+public class BadStateException extends LayersException {
+
+ /**
+ *
+ */
+ private static final long serialVersionUID = -5674451388263111557L;
+
+ /**
+ * Constructor.
+ *
+ */
+ public BadStateException() {
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param message
+ */
+ public BadStateException(String message) {
+ super(message);
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param cause
+ */
+ public BadStateException(Throwable cause) {
+ super(cause);
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param message
+ * @param cause
+ */
+ public BadStateException(String message, Throwable cause) {
+ super(message, cause);
+ // TODO Auto-generated constructor stub
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/InstanciationException.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/InstanciationException.java
new file mode 100755
index 0000000..3e4b4a0
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/InstanciationException.java
@@ -0,0 +1,64 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model;
+
+
+/**
+ * @author dumoulin
+ *
+ */
+public class InstanciationException extends LayersException {
+
+ /**
+ *
+ */
+ private static final long serialVersionUID = 2070317356365033045L;
+
+ /**
+ * Constructor.
+ *
+ */
+ public InstanciationException() {
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param message
+ */
+ public InstanciationException(String message) {
+ super(message);
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param cause
+ */
+ public InstanciationException(Throwable cause) {
+ super(cause);
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param message
+ * @param cause
+ */
+ public InstanciationException(String message, Throwable cause) {
+ super(message, cause);
+ // TODO Auto-generated constructor stub
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/LayersException.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/LayersException.java
new file mode 100755
index 0000000..81e3d57
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/LayersException.java
@@ -0,0 +1,77 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model;
+
+
+/**
+ * @author dumoulin
+ *
+ */
+public class LayersException extends Exception {
+
+ /**
+ *
+ */
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * Constructor.
+ *
+ */
+ public LayersException() {
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param message
+ */
+ public LayersException(String message) {
+ super(message);
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param cause
+ */
+ public LayersException(Throwable cause) {
+ super(cause);
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param message
+ * @param cause
+ */
+ public LayersException(String message, Throwable cause) {
+ super(message, cause);
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param message
+ * @param cause
+ * @param enableSuppression
+ * @param writableStackTrace
+ */
+ // public LayersException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) {
+ // super(message, cause, enableSuppression, writableStackTrace);
+ // // TODO Auto-generated constructor stub
+ // }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/NotFoundException.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/NotFoundException.java
new file mode 100755
index 0000000..43e8063
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/NotFoundException.java
@@ -0,0 +1,64 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model;
+
+
+/**
+ * @author dumoulin
+ *
+ */
+public class NotFoundException extends LayersException {
+
+ /**
+ *
+ */
+ private static final long serialVersionUID = 2070317356365033045L;
+
+ /**
+ * Constructor.
+ *
+ */
+ public NotFoundException() {
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param message
+ */
+ public NotFoundException(String message) {
+ super(message);
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param cause
+ */
+ public NotFoundException(Throwable cause) {
+ super(cause);
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param message
+ * @param cause
+ */
+ public NotFoundException(String message, Throwable cause) {
+ super(message, cause);
+ // TODO Auto-generated constructor stub
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/PropertyValueFactory.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/PropertyValueFactory.java
new file mode 100755
index 0000000..8770d6c
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/PropertyValueFactory.java
@@ -0,0 +1,116 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model;
+
+import org.eclipse.core.runtime.Platform;
+import org.eclipse.emf.ecore.EClass;
+import org.eclipse.emf.ecore.EObject;
+import org.eclipse.emf.ecore.EPackage;
+import org.osgi.framework.Bundle;
+
+
+/**
+ * @author cedric dumoulin
+ *
+ */
+public class PropertyValueFactory {
+
+ /**
+ * Constructor.
+ *
+ */
+ public PropertyValueFactory() {
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * Create an instance of the specified class, located in the specified plugin.
+ *
+ * @param pluginId
+ * @param classname
+ * @return
+ * @throws ClassNotFoundException
+ * @throws IllegalAccessException
+ * @throws InstantiationException
+ */
+ public Object newInstance(String pluginId, String classname) throws ClassNotFoundException, InstantiationException, IllegalAccessException {
+
+
+ Class<?> classType = loadClass(pluginId, classname);
+
+ return classType.newInstance();
+ }
+
+ /**
+ * Load requested class from the current classloader. If not found, try to get it from the
+ * specified plugin.
+ *
+ * @param declaringID
+ * @param className
+ * @return
+ * @throws ClassNotFoundException
+ */
+ public Class<?> loadClass(String declaringID, String className) throws ClassNotFoundException {
+ Class<?> factoryClass;
+ try {
+ factoryClass = Class.forName(className);
+ } catch (ClassNotFoundException e) {
+ // try another way
+ try {
+ Bundle bundle = Platform.getBundle(declaringID);
+ factoryClass = bundle.loadClass(className);
+ } catch (ClassNotFoundException e1) {
+ throw new ClassNotFoundException("Can't find class " + className
+ + "in plugin " + declaringID, e1);
+ } catch (NullPointerException e1) {
+ throw new ClassNotFoundException("Can't find plugin " + declaringID, e1);
+ }
+ }
+ return factoryClass;
+
+ }
+
+ /**
+ * Create an instance of the specified model concept.
+ *
+ * @param nsURI
+ * @param propertyName
+ * @return
+ * @throws ClassNotFoundException
+ * @throws InstantiationException
+ * @throws IllegalAccessException
+ */
+ public EObject newEClassInstance(String nsURI, String propertyName) throws ClassNotFoundException {
+
+
+
+ EPackage modelPackage = EPackage.Registry.INSTANCE.getEPackage(nsURI);
+ if (modelPackage == null) {
+ throw new ClassNotFoundException("Can't get EPAckage for model '" + nsURI + "'");
+ }
+
+ EClass classifier = (EClass) modelPackage.getEClassifier(propertyName);
+ if (classifier == null) {
+ throw new ClassNotFoundException("Can't get classifier '" + propertyName + "' in model '" + nsURI + "'");
+ }
+
+ return modelPackage.getEFactoryInstance().create(classifier);
+ }
+
+ public Object getEObjectPropertyValue(EObject eObject, String propertyName) {
+ return eObject.eGet(eObject.eClass().getEStructuralFeature(propertyName));
+ }
+
+ public void setEObjectPropertyValue(EObject eObject, String propertyName, Object value) {
+ eObject.eSet(eObject.eClass().getEStructuralFeature(propertyName), value);
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/command/ComputePropertyValueCommand.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/command/ComputePropertyValueCommand.java
new file mode 100755
index 0000000..d2ef20c
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/command/ComputePropertyValueCommand.java
@@ -0,0 +1,39 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.command;
+
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.LayersException;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStack;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.TypeInstance;
+
+
+/**
+ * This command is used to compute a property value in {@link LayersStack}.
+ * The effective computation is done when the {@link #getValue()} method is called.
+ *
+ *
+ * @author cedric dumoulin
+ *
+ */
+public interface ComputePropertyValueCommand {
+
+
+ /**
+ * Execute the command and return the computed value.
+ * Compute the value of the Property, and return it.
+ *
+ * @return The computed value of the Property.
+ * @throws LayersException
+ * If something goes wrong
+ */
+ public TypeInstance getCmdValue() throws LayersException;
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/ExpressionMatcher.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/ExpressionMatcher.java
new file mode 100755
index 0000000..aa8ef88
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/ExpressionMatcher.java
@@ -0,0 +1,416 @@
+/*****************************************************************************
+ * Copyright (c) 2013 Cedric Dumoulin.
+ *
+ *
+ * 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:
+ * Cedric Dumoulin Cedric.dumoulin@lifl.fr - Initial API and implementation
+ *
+ *****************************************************************************/
+
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.exprmatcher;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.List;
+
+import org.eclipse.core.runtime.NullProgressMonitor;
+import org.eclipse.emf.common.notify.Notification;
+import org.eclipse.emf.ecore.EClass;
+import org.eclipse.emf.ecore.EClassifier;
+import org.eclipse.emf.ecore.EObject;
+import org.eclipse.emf.query.conditions.eobjects.EObjectCondition;
+import org.eclipse.emf.query.ocl.conditions.BooleanOCLCondition;
+import org.eclipse.emf.query.statements.FROM;
+import org.eclipse.emf.query.statements.IQueryResult;
+import org.eclipse.emf.query.statements.SELECT;
+import org.eclipse.emf.query.statements.WHERE;
+import org.eclipse.gmf.runtime.notation.NotationPackage;
+import org.eclipse.gmf.runtime.notation.View;
+import org.eclipse.ocl.ParserException;
+import org.eclipse.ocl.ecore.OCL;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.LayersException;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.util.Collections3;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.util.ObservableListView;
+
+/**
+ * This class evaluate its associated expression against the associated models.
+ * It provide a list of elements matching the expression in the model.
+ * The list of matching elements is synchronized by the matcher. The list can be provided at construction
+ * time. The ExpressinMatcher takes care to minimize the number of write to the underlying list of matching elements.
+ * Usually, there is two writes (see {@link Collections3#resetListTo(Collection, Collection)}. <br>
+ * It is possible to be inform of changes in the underlying list by wrapping it in an {@link ObservableListView}.
+ *
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class ExpressionMatcher implements IValueChangedEventListener {
+
+ protected String expression = "";
+
+ /**
+ * List of element matching the expression.
+ * This class maintains the list.
+ */
+ protected List<View> matchingElements;
+
+ /**
+ * List of element used as starting point for search.
+ */
+ protected List<EObject> searchRoots;
+
+ /**
+ * OCL Condition computed from the expr.
+ */
+ protected EObjectCondition condition;
+ protected OCL ocl;
+
+
+ /**
+ *
+ * Constructor.
+ *
+ */
+ public ExpressionMatcher() {
+ this.expression = "";
+ this.searchRoots = Collections.emptyList();
+ // init matchingElements
+ matchingElements = new ArrayList<View>();
+ }
+
+ /**
+ *
+ * Constructor.
+ *
+ * @param searchRoots
+ * @throws LayersException
+ */
+ public ExpressionMatcher(List<View> matchingElementsList) {
+ this.expression = "";
+ this.searchRoots = Collections.emptyList();
+ // init matchingElements
+ matchingElements = matchingElementsList;
+ }
+
+ /**
+ *
+ * Constructor.
+ *
+ * @param searchRoots
+ * @throws LayersException
+ */
+ // public ExpressionMatcher(List<EObject> searchRoots) {
+ // this.expression = "";
+ // setSearchRoots(searchRoots);
+ // // init matchingElements
+ // matchingElements = new ObservableListView<View>(new ArrayList<View>());
+ // }
+
+ /**
+ *
+ * Constructor.
+ *
+ * @param searchRoot
+ * @throws LayersException
+ */
+ public ExpressionMatcher(EObject searchRoot) {
+ this.expression = "";
+ setSearchRoots(Collections.singletonList(searchRoot));
+ // init matchingElements
+ matchingElements = new ArrayList<View>();
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param expression
+ * @param searchRoots
+ * @throws LayersException
+ * If the Condition can't be computed from the expression.
+ */
+ public ExpressionMatcher(String expression, List<EObject> searchRoots) throws LayersException {
+ this.searchRoots = searchRoots;
+ matchingElements = new ArrayList<View>();
+
+ // compute expr
+ setExpression(expression);
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param expression
+ * @param searchRoots
+ * @throws LayersException
+ * If the Condition can't be computed from the expression.
+ */
+ public ExpressionMatcher(String expression, List<View> matchingElementsList, List<EObject> searchRoots) throws LayersException {
+ this.searchRoots = searchRoots;
+ matchingElements = matchingElementsList;
+
+ // compute expr
+ setExpression(expression);
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param expression
+ * @param searchRoots
+ * @throws LayersException
+ * If the Condition can't be computed from the expression.
+ */
+ public ExpressionMatcher(String expression, EObject searchRoot) throws LayersException {
+ this(expression, Collections.singletonList(searchRoot));
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param expression
+ * @param searchRoots
+ * @throws LayersException
+ * If the Condition can't be computed from the expression.
+ */
+ public ExpressionMatcher(String expression, List<View> matchingElementsList, EObject searchRoot) throws LayersException {
+ this(expression, matchingElementsList, Collections.singletonList(searchRoot));
+ }
+
+ /**
+ * Compute the condition from the expr.
+ */
+ private void computeCondition() throws LayersException {
+ // silently fails if the expr is not set.
+ if (getExpression() == null || getExpression().length() == 0) {
+ return;
+ }
+
+ if (ocl == null) {
+ ocl = OCL.newInstance();
+ }
+ // Create the condition
+ try {
+ // If the 3rd args is null, this is a context free condition.
+
+ condition = new BooleanOCLCondition<EClassifier, EClass, EObject>(
+ ocl.getEnvironment(),
+ // "self.oclIsKindOf(Shape)",
+ // "self.oclIsKindOf(Shape) and self.oclAsType(Shape).visible = true",
+ // "self.oclAsType(Shape).visible = true",
+ getExpression(),
+ NotationPackage.Literals.VIEW
+ // null
+ );
+ } catch (ParserException e) {
+ // TODO Auto-generated catch block
+ condition = null;
+ throw new LayersException("Can't parse expression : " + e.getMessage(), e);
+ }
+
+ }
+
+ /**
+ * Recompute the matching elements.
+ * This lead to firing Events (added and removed)
+ */
+ public void refreshMatchingElements() {
+
+
+ if (condition == null) {
+ // If the condition is not set, the list should be empty
+ if (!getMatchingElements().isEmpty()) {
+ resetMatchingElements(Collections.EMPTY_LIST);
+ }
+ return;
+ }
+
+ // Create the OCL statement
+ SELECT statement = new SELECT(SELECT.UNBOUNDED, false,
+ new FROM(getSearchRoots()), new WHERE(condition),
+ new NullProgressMonitor());
+
+ // Execute the OCL statement
+ IQueryResult results = statement.execute();
+
+ /**
+ * Reset the matching elements with the new result.
+ */
+ resetMatchingElements(results);
+ }
+
+ /**
+ * Reset the {@link #matchingElements} and let it contain the specified collection.
+ * This fire added and removed events.
+ *
+ * @param results
+ */
+ @SuppressWarnings("unchecked")
+ private void resetMatchingElements(Collection<?> newElements) {
+
+ Collections3.resetListTo(matchingElements, (Collection<View>) newElements);
+ // matchingElements.resetTo((Collection<View>)newElements);
+
+ // // Compute views to add
+ // // This are views in the newElements, but not in the actual list of matchingElement
+ // // viewsToAdd = results - getViews()
+ // List<View> viewsToAdd = new ArrayList<View>();
+ // for( Object o : newElements ) {
+ // View v = (View)o;
+ // if( !getMatchingElements().contains(v)) {
+ // viewsToAdd.add(v);
+ // }
+ // }
+ //
+ // // Compute views to remove
+ // // Their is two ways to compute it:
+ // // - viewsToremove = diagramViews - results
+ // // - or viewsToremove = getViews() - result
+ // // Use the cheaper one.
+ // // The computed viewsToRemove list contains also views that are not in the layer,
+ // // But this is cheaper than checking for the existence.
+ //
+ // // List<View> viewsToRemove = new ArrayList<View>();
+ // // for( View v : (views.size()<getViews().size()?views:getViews()) ) {
+ // // if( !results.contains(v)) {
+ // // viewsToRemove.add(v);
+ // // }
+ // // }
+ //
+ // // Do operations
+ // getMatchingElements().retainAll(newElements);
+ // // getViews().removeAll(viewsToRemove);
+ // getMatchingElements().addAll(viewsToAdd);
+
+ }
+
+ /**
+ * @return the expression
+ */
+ public String getExpression() {
+ return expression;
+ }
+
+
+ /**
+ * @param expression
+ * the expression to set
+ * @throws LayersException
+ * If the Condition can't be computed from the expression.
+ */
+ public void setExpression(String expression) throws LayersException {
+
+ if (expression == null || expression.length() == 0) {
+ // standardize noop expr
+ expression = "";
+ }
+ if (expression.equals(this.expression)) {
+ return;
+ }
+
+ this.expression = expression;
+
+ computeCondition();
+ refreshMatchingElements();
+ }
+
+
+ /**
+ * @return the matchingElements
+ */
+ public List<View> getMatchingElements() {
+ return matchingElements;
+ }
+
+
+ /**
+ * @return the searchRoots
+ */
+ public List<EObject> getSearchRoots() {
+ return searchRoots;
+ }
+
+ /**
+ *
+ * @param searchRoots
+ */
+ public void setSearchRoots(List<EObject> searchRoots) {
+
+ // Remove any existing observers
+ removeSearchRootsObservers();
+
+ if (searchRoots == null) {
+ searchRoots = Collections.emptyList();
+ }
+ this.searchRoots = searchRoots;
+ // add observers on roots changes
+ addSearchRootsObservers();
+
+ // Do not refresh. Let user do it.
+ }
+
+ /**
+ *
+ * @param searchRoots
+ */
+ public void setSearchRoots(EObject searchRoot) {
+ if (searchRoot == null) {
+ // Remove any existing observers
+ removeSearchRootsObservers();
+ searchRoots = Collections.emptyList();
+ return;
+ }
+
+ setSearchRoots(Collections.singletonList(searchRoot));
+ }
+
+ /**
+ * Observes all searchRoots for changes. If a change occurs, refresh the matching elements.
+ *
+ */
+ protected void addSearchRootsObservers() {
+
+ if (searchRoots == null) {
+ return;
+ }
+
+
+ for (EObject root : searchRoots) {
+ ValueChangedEventNotifier notifier = ValueChangedEventNotifierFactory.instance.adapt(root);
+ notifier.addEventListener(this);
+ }
+ }
+
+ /**
+ * Observes all searchRoots for changes. If a change occurs, refresh the matching elements.
+ *
+ */
+ protected void removeSearchRootsObservers() {
+
+ if (searchRoots == null) {
+ return;
+ }
+
+ for (EObject root : searchRoots) {
+ ValueChangedEventNotifier notifier = ValueChangedEventNotifierFactory.instance.adapt(root);
+ notifier.removeEventListener(this);
+ }
+ }
+
+ /**
+ * Called when a value change in one of the elements of the observed roots.
+ *
+ * @param msg
+ */
+ @Override
+ public void valueChanged(Notification msg) {
+ refreshMatchingElements();
+ }
+
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/IValueChangedEventListener.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/IValueChangedEventListener.java
new file mode 100755
index 0000000..96cfbca
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/IValueChangedEventListener.java
@@ -0,0 +1,35 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.exprmatcher;
+
+import org.eclipse.emf.common.notify.Notification;
+import org.eclipse.emf.ecore.EObject;
+
+
+/**
+ * Class implementing this interface can listen to event from EObject.
+ * This class is used by {@link ExpressionMatcher} to be informed when it need to be refreshed.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public interface IValueChangedEventListener {
+
+ /**
+ * Called by events when a property is changed in a {@link EObject}
+ *
+ * @param msg
+ */
+ public void valueChanged(Notification msg);
+
+
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/ValueChangedEventNotifier.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/ValueChangedEventNotifier.java
new file mode 100755
index 0000000..f07f347
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/ValueChangedEventNotifier.java
@@ -0,0 +1,336 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.exprmatcher;
+
+import static org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.Activator.log;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.eclipse.emf.common.notify.Adapter;
+import org.eclipse.emf.common.notify.Notification;
+import org.eclipse.emf.ecore.EObject;
+import org.eclipse.emf.ecore.util.EContentAdapter;
+import org.eclipse.gmf.runtime.notation.Diagram;
+import org.eclipse.gmf.runtime.notation.NotationPackage;
+import org.eclipse.gmf.runtime.notation.View;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStack;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStackApplication;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier.LayersTreeEventNotifier;
+import org.eclipse.uml2.uml.NamedElement;
+import org.eclipse.uml2.uml.UMLPackage;
+
+
+/**
+ * An EMF {@link Adapter} listening on uml::NamedElement properties changes.
+ *
+ * This class listen to a {@link NamedElement} and send following events to listeners:
+ * <ul>
+ * <li>valueChanged</li>
+ * </ul>
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class ValueChangedEventNotifier extends EContentAdapter {
+
+ boolean isDisposed = false;
+
+ /**
+ * List of listener to notify.
+ */
+ protected List<IValueChangedEventListener> listeners = new ArrayList<IValueChangedEventListener>();
+
+ /**
+ * Something happen on the tree of object
+ *
+ * @see org.eclipse.emf.ecore.util.EContentAdapter#notifyChanged(org.eclipse.emf.common.notify.Notification)
+ *
+ * @param msg
+ */
+ @Override
+ public void notifyChanged(Notification notification) {
+
+ // Self atttach
+ super.notifyChanged(notification);
+
+ // Take into account the domain hierarchy found from the notation.
+
+ // Now, filter
+ if (isDiagramRootView(notification)) {
+ fireValueChangedEvent(notification);
+ } else if (isUmlDomainElementChanged(notification)) {
+ fireValueChangedEvent(notification);
+ }
+
+
+ // // We are only interested in NamedElement (from newValue if set, or oldValue if removed)
+ // Object newValue = notification.getNewValue();
+ // if( ! (newValue instanceof NamedElement || notification.getOldValue() instanceof NamedElement ) ) {
+ // return;
+ // }
+ // // Check diagram modification
+ // // There is 4 sources: View::persistedChildren and View::transientChildren
+ // // Diagram::persistedChildren and Diagram::transientChildren
+ // Object feature = notification.getFeature();
+ // if( feature == UMLPackage.eINSTANCE.getNamedElement()
+ // || feature == NotationPackage.eINSTANCE.getView_TransientChildren()
+ // || feature == NotationPackage.eINSTANCE.getDiagram_PersistedEdges()
+ // || feature == NotationPackage.eINSTANCE.getDiagram_TransientEdges() ) {
+ // // LayerOperator::layers || LayersStack::layers
+ // // check the event type.
+ // switch(notification.getEventType()) {
+ // case Notification.SET:
+ //
+ // break;
+ // case Notification.ADD:
+ // // A view is added
+ // fireValueChangedEvent(notification);
+ // break;
+ // case Notification.REMOVE:
+ // // A layer is removed
+ // fireDiagramViewRemovedEvent(notification);
+ // break;
+ // }
+ // }
+
+ };
+
+ /**
+ * Return true if the notification indicates a change in a uml element.
+ *
+ * @param notification
+ * @return
+ */
+ private boolean isUmlDomainElementChanged(Notification notification) {
+ // Notifier should be the diagram
+ if (!(notification.getNotifier() instanceof NamedElement)) {
+ return false;
+ }
+
+ Object feature = notification.getFeature();
+
+ if (feature == UMLPackage.eINSTANCE.getNamedElement_Name()) {
+ // check the event type.
+ switch (notification.getEventType()) {
+ case Notification.SET:
+ case Notification.ADD:
+ case Notification.REMOVE:
+
+ return true;
+ }
+ }
+ return false;
+ }
+
+ /**
+ * Return true if the notification indicates that a Diagram root view is modifified.
+ *
+ * @param notification
+ * @return
+ */
+ private boolean isDiagramRootView(Notification notification) {
+
+ // Notifier should be the diagram
+ if (!(notification.getNotifier() instanceof Diagram)) {
+ return false;
+ }
+
+ Object feature = notification.getFeature();
+
+ if (feature == NotationPackage.eINSTANCE.getView_PersistedChildren()
+ || feature == NotationPackage.eINSTANCE.getView_TransientChildren()
+ || feature == NotationPackage.eINSTANCE.getDiagram_PersistedEdges()
+ || feature == NotationPackage.eINSTANCE.getDiagram_TransientEdges()) {
+ // LayerOperator::layers || LayersStack::layers
+ // check the event type.
+ switch (notification.getEventType()) {
+ case Notification.SET:
+ case Notification.ADD:
+ case Notification.REMOVE:
+
+ return true;
+ }
+ }
+ return false;
+ }
+
+ /**
+ * This Adapter is for {@link LayersTreeEventNotifier}.
+ *
+ * @see org.eclipse.emf.common.notify.impl.AdapterImpl#isAdapterForType(java.lang.Object)
+ *
+ * @param type
+ * @return
+ */
+ @Override
+ public boolean isAdapterForType(Object type) {
+ return type == ValueChangedEventNotifier.class;
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param layersModel
+ */
+ public ValueChangedEventNotifier() {
+ }
+
+ /**
+ * Dispose the synchronizer
+ */
+ public void dispose() {
+
+ if (isDisposed()) {
+ return;
+ }
+
+ isDisposed = true;
+ listeners.clear();
+ }
+
+ /**
+ * Return true if the object is disposed.
+ *
+ * @return
+ */
+ public boolean isDisposed() {
+ return isDisposed == true;
+ }
+
+ /**
+ * Add the specified listener to the list of listener.
+ * Do not add it if the listener is already in the list.
+ *
+ * @param listener
+ */
+ public void addEventListener(IValueChangedEventListener listener) {
+
+ if (listener == null) {
+ return;
+ }
+
+ // Check if exist
+ if (listeners.contains(listener)) {
+ return;
+ }
+
+ listeners.add(listener);
+ }
+
+ /**
+ * Remove the specified listener from the list of listeners.
+ *
+ * @param listener
+ */
+ public void removeEventListener(IValueChangedEventListener listener) {
+
+ listeners.remove(listener);
+ }
+
+ /**
+ * Called by events when a {@link LayersStack} is added to the {@link LayersStackApplication}
+ *
+ * @param msg
+ */
+ protected void fireValueChangedEvent(Notification msg) {
+ for (IValueChangedEventListener listener : listeners) {
+ listener.valueChanged(msg);
+ }
+ }
+
+ /**
+ * Handle View::element hierarchy in the self adapt mechanism.
+ * Handles a notification by calling {@link #handleContainment handleContainment} for any containment-based notification.
+ */
+ @Override
+ protected void selfAdapt(Notification notification) {
+ if (log.isDebugEnabled()) {
+ log.debug(this.getClass().getSimpleName() + ".selfAdapt(" + notification + ")");
+ }
+
+ if (notification.getFeature() == NotationPackage.eINSTANCE.getView_Element()) {
+ handleContainment(notification);
+ } else {
+ super.selfAdapt(notification);
+ }
+ }
+
+ /**
+ * Handle View::element hierarchy in the self adapt mechanism.
+ *
+ * @see org.eclipse.emf.ecore.util.EContentAdapter#setTarget(org.eclipse.emf.ecore.EObject)
+ *
+ * @param target
+ */
+ @Override
+ protected void setTarget(EObject target) {
+ if (log.isDebugEnabled()) {
+ log.debug(this.getClass().getSimpleName() + ".setTarget(" + target + ")");
+ }
+
+ // Handle the View::element tree
+ if (target instanceof View) {
+ EObject extraTarget = ((View) target).getElement();
+ if (extraTarget != null) {
+ log.info(this.getClass().getSimpleName() + ".setExtraTarget(" + extraTarget + ")");
+ // copied from org.eclipse.emf.ecore.util.EContentAdapter.setTarget(EObject)
+ // basicSetTarget(target);
+ // Add the extra object
+ addAdapter(extraTarget);
+ // Add the content of the extra object
+ // for (Iterator<? extends Notifier> i = resolve() ?
+ // extraTarget.eContents().iterator() :
+ // ((InternalEList<? extends Notifier>)extraTarget.eContents()).basicIterator();
+ // i.hasNext(); )
+ // {
+ // Notifier notifier = i.next();
+ // addAdapter(notifier);
+ // }
+
+ }
+ }
+ }
+
+ /**
+ * Handle View::element hierarchy in the self adapt mechanism.
+ *
+ * @see org.eclipse.emf.ecore.util.EContentAdapter#unsetTarget(org.eclipse.emf.ecore.EObject)
+ *
+ * @param target
+ */
+ @Override
+ protected void unsetTarget(EObject target) {
+ // TODO Auto-generated method stub
+ super.unsetTarget(target);
+ // Handle the View::element tree
+ if (target instanceof View) {
+ EObject extraTarget = ((View) target).getElement();
+ if (extraTarget != null) {
+ // copied from org.eclipse.emf.ecore.util.EContentAdapter.setTarget(EObject)
+ // basicSetTarget(target);
+ // Remove the extra object
+ removeAdapter(extraTarget);
+ // Remove contents of the extra object
+ // for (Iterator<? extends Notifier> i = resolve() ?
+ // extraTarget.eContents().iterator() :
+ // ((InternalEList<? extends Notifier>)extraTarget.eContents()).basicIterator();
+ // i.hasNext(); )
+ // {
+ // Notifier notifier = i.next();
+ // removeAdapter(notifier);
+ // }
+
+ }
+ }
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/ValueChangedEventNotifierFactory.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/ValueChangedEventNotifierFactory.java
new file mode 100755
index 0000000..fb0f66c
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/exprmatcher/ValueChangedEventNotifierFactory.java
@@ -0,0 +1,70 @@
+/*****************************************************************************
+ * Copyright (c) 2013 Cedric Dumoulin.
+ *
+ *
+ * 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:
+ * Cedric Dumoulin Cedric.dumoulin@lifl.fr - Initial API and implementation
+ *
+ *****************************************************************************/
+
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.exprmatcher;
+
+import org.eclipse.emf.common.notify.Adapter;
+import org.eclipse.emf.common.notify.Notifier;
+import org.eclipse.emf.common.notify.impl.AdapterFactoryImpl;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStack;
+
+/**
+ * Factory used to create a {@link ValueChangedEventNotifier}.
+ * The factory ensures that there is only one Notifier for a given {@link LayersStack}.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class ValueChangedEventNotifierFactory extends AdapterFactoryImpl {
+
+ /**
+ * Global factory.
+ */
+ static public ValueChangedEventNotifierFactory instance = new ValueChangedEventNotifierFactory();
+
+ /**
+ * Convenience method.
+ *
+ * @param target
+ * @return
+ */
+ public ValueChangedEventNotifier adapt(Notifier target) {
+ return (ValueChangedEventNotifier) adapt(target, ValueChangedEventNotifier.class);
+ }
+
+ /**
+ *
+ * @see org.eclipse.emf.common.notify.impl.AdapterFactoryImpl#createAdapter(org.eclipse.emf.common.notify.Notifier)
+ *
+ * @param target
+ * @return
+ */
+ @Override
+ protected Adapter createAdapter(Notifier target) {
+ return new ValueChangedEventNotifier();
+ }
+
+ /**
+ * This Factory is for {@link ValueChangedEventNotifier}.
+ *
+ * @see org.eclipse.emf.common.notify.impl.AdapterFactoryImpl#isFactoryForType(java.lang.Object)
+ *
+ * @param type
+ * @return
+ */
+ @Override
+ public boolean isFactoryForType(Object type) {
+ return type == ValueChangedEventNotifier.class;
+ }
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/ILayerOperatorDescriptorRegistryLoader.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/ILayerOperatorDescriptorRegistryLoader.java
new file mode 100755
index 0000000..69a6805
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/ILayerOperatorDescriptorRegistryLoader.java
@@ -0,0 +1,33 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders;
+
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayerOperatorDescriptorRegistry;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.PropertyRegistry;
+
+
+/**
+ * Interface that a {@link LayerOperatorDescriptorRegistry} loader should implements.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public interface ILayerOperatorDescriptorRegistryLoader {
+
+ /**
+ * Load the specified registry. Initialize its Descriptors and its Operators.
+ *
+ * @param layerOperatorDescriptorRegistry
+ * @param propertyRegistry
+ */
+ public void loadLayerOperatorDescriptorRegistry(LayerOperatorDescriptorRegistry descriptorRegistry, PropertyRegistry propertyRegistry);
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/LayerOperatorDescriptorRegistryLoader.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/LayerOperatorDescriptorRegistryLoader.java
new file mode 100755
index 0000000..9f5522c
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/LayerOperatorDescriptorRegistryLoader.java
@@ -0,0 +1,121 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders;
+
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.NotFoundException;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.CustomPropertyOperator;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayerOperatorDescriptor;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayerOperatorDescriptorRegistry;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersFactory;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.PropertyRegistry;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.operators.BooleanAndOperator;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.operators.BooleanOrOperator;
+
+
+/**
+ * Class used to load a {@link LayerOperatorDescriptorRegistry}.
+ *
+ * @author cedric dumoulin
+ *
+ * @deprecated use {@link RegistriesLoader} instead.
+ *
+ */
+@Deprecated
+public class LayerOperatorDescriptorRegistryLoader implements ILayerOperatorDescriptorRegistryLoader {
+
+ /**
+ * Load the specified registry. Initialize its Descriptors and its Operators.
+ *
+ * @param layerOperatorDescriptorRegistry
+ * @param propertyRegistry
+ */
+ public void loadRegistryOld(LayerOperatorDescriptorRegistry descriptorRegistry, PropertyRegistry propertyRegistry) {
+
+ // Custom operator declarations
+ // operatorName, operatorImplementationClass
+ String[] operatorDeclarations = new String[] {
+ "booleanOr", BooleanOrOperator.class.getName(),
+ "booleanAnd", BooleanAndOperator.class.getName(),
+
+ };
+
+ // Load operators
+ for (int i = 0; i < operatorDeclarations.length; i += 2) {
+ CustomPropertyOperator operator = LayersFactory.eINSTANCE.createCustomPropertyOperator();
+ operator.setName(operatorDeclarations[i]);
+ operator.setClassname(operatorDeclarations[i + 1]);
+ descriptorRegistry.addPropertyOperator(operator);
+ }
+
+ // AndLayerStackOperatorDescriptor
+ // propertyName, operatorName
+ String[] andDescriptorDeclarations = new String[] {
+ "isVisible", "booleanAnd",
+ };
+
+ LayerOperatorDescriptor andDescriptor = LayersFactory.eINSTANCE.createAndStackedLayerOperatorDescriptor();
+ descriptorRegistry.addLayerOperatorDescriptor(andDescriptor);
+
+ // attach operator to layer and property
+ String descriptorName = andDescriptor.getName();
+ for (int i = 0; i < andDescriptorDeclarations.length; i += 2) {
+ try {
+ descriptorRegistry.attachOperatorToDescriptor(propertyRegistry.getProperty(andDescriptorDeclarations[i]), andDescriptorDeclarations[i + 1], descriptorName);
+ } catch (NotFoundException e) {
+ // TODO Auto-generated catch block
+ e.printStackTrace();
+ }
+ }
+
+ // OrLayerStackOperatorDescriptor
+ // propertyName, operatorName
+ String[] orDescriptorDeclarations = new String[] {
+ "isVisible", "booleanOr",
+ };
+
+ LayerOperatorDescriptor orDescriptor = LayersFactory.eINSTANCE.createOrStackedLayerOperatorDescriptor();
+ descriptorRegistry.addLayerOperatorDescriptor(orDescriptor);
+
+ // attach operator to layer and property
+ descriptorName = orDescriptor.getName();
+ for (int i = 0; i < orDescriptorDeclarations.length; i += 2) {
+ try {
+ descriptorRegistry.attachOperatorToDescriptor(propertyRegistry.getProperty(orDescriptorDeclarations[i]), orDescriptorDeclarations[i + 1], descriptorName);
+ } catch (NotFoundException e) {
+ // TODO Auto-generated catch block
+ e.printStackTrace();
+ }
+ }
+ }
+
+ /**
+ * @see org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders.ILayerOperatorDescriptorRegistryLoader#loadLayerOperatorDescriptorRegistry(org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayerOperatorDescriptorRegistry,
+ * org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.PropertyRegistry)
+ *
+ * @param descriptorRegistry
+ * @param propertyRegistry
+ */
+ @Override
+ public void loadLayerOperatorDescriptorRegistry(LayerOperatorDescriptorRegistry descriptorRegistry, PropertyRegistry propertyRegistry) {
+
+ createLayersConfigModel();
+
+ }
+
+ /**
+ * Create a Model
+ */
+ private void createLayersConfigModel() {
+ // TODO Auto-generated method stub
+
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/LayersConfigModel.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/LayersConfigModel.java
new file mode 100755
index 0000000..8ec211a
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/LayersConfigModel.java
@@ -0,0 +1,259 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders;
+
+import static org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders.LayersConfigModelUtils.createFolder;
+import static org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders.LayersConfigModelUtils.createLayerOperatorConfig;
+import static org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders.LayersConfigModelUtils.createLayerOperatorsMultipleBinding;
+import static org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders.LayersConfigModelUtils.createOperatorBinding;
+import static org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders.LayersConfigModelUtils.createPropertyId;
+import static org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders.LayersConfigModelUtils.createPropertyOperatorConfig;
+import static org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders.LayersConfigModelUtils.createTypeConfig;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.eclipse.emf.common.util.TreeIterator;
+import org.eclipse.emf.common.util.URI;
+import org.eclipse.emf.ecore.EObject;
+import org.eclipse.emf.ecore.resource.Resource;
+import org.eclipse.emf.ecore.resource.ResourceSet;
+import org.eclipse.emf.ecore.resource.impl.ResourceSetImpl;
+import org.eclipse.emf.ecore.xmi.impl.XMIResourceFactoryImpl;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersPackage;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.operators.BooleanAndOperator;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.operators.BooleanOrOperator;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.operators.FillAverageOperator;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.Folder;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.LayerOperatorConfig;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.LayerOperatorMultipleBinding;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.LayersconfigFactory;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.OperatorBinding;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.OperatorConfig;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.PropertyId;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.TypeConfig;
+
+
+/**
+ * This class encapsulate an LayersConfig model.
+ * It provides a default instance initialized with a model.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class LayersConfigModel {
+
+ /**
+ * The default instance used by all applications.
+ */
+ static final protected LayersConfigModel instance;
+
+ protected Resource resource;
+
+
+
+ /**
+ * Create and initialize default instance.
+ */
+ static {
+ instance = new LayersConfigModel();
+ instance.initDefaultModel();
+ }
+
+ /**
+ * Constructor.
+ *
+ */
+ public LayersConfigModel() {
+ createResourceAndRootFolder();
+ }
+
+
+ /**
+ * @return the instance
+ */
+ public static LayersConfigModel getInstance() {
+ return instance;
+ }
+
+ /**
+ * Init the object with a default model.
+ */
+ private void initDefaultModel() {
+ // Create model
+ Folder layeropFolder = createFolder(getRootFolder(), "layerOp");
+
+ LayerOperatorConfig stackedLayersOperatorConfig = createLayerOperatorConfig(layeropFolder, "stackedLayersOperator", LayersPackage.eINSTANCE.getStackedLayerOperatorDescriptor().getName());
+ LayerOperatorConfig stackedLayersOperatorMinimunConfig = createLayerOperatorConfig(layeropFolder, "stackedLayersOperatorMinimum", LayersPackage.eINSTANCE.getStackedLayerOperatorDescriptor().getName());
+ createLayerOperatorConfig(layeropFolder, "stackedLayersOperatorMaximum", LayersPackage.eINSTANCE.getStackedLayerOperatorDescriptor().getName());
+ LayerOperatorConfig stackedLayersOperatorAverage = createLayerOperatorConfig(layeropFolder, "stackedLayersOperatorAverage", LayersPackage.eINSTANCE.getStackedLayerOperatorDescriptor().getName());
+
+ // Create Operators
+ Folder operatorFolder = createFolder(getRootFolder(), "operatorDesc");
+ OperatorConfig operatorBooleanAnd = createPropertyOperatorConfig(operatorFolder, "operatorBooleanAnd", BooleanAndOperator.class.getName());
+ OperatorConfig operatorBooleanOr = createPropertyOperatorConfig(operatorFolder, "operatorBooleanOr", BooleanOrOperator.class.getName());
+ OperatorConfig operatorFillAverage = createPropertyOperatorConfig(operatorFolder, "operatorFillAverage", FillAverageOperator.class.getName());
+
+
+ // Create basic types
+ Folder typeFolder = createFolder(getRootFolder(), "types");
+ TypeConfig typeBoolean = createTypeConfig(typeFolder, "boolean");
+ TypeConfig typeInt = createTypeConfig(typeFolder, "int");
+ TypeConfig typeString = createTypeConfig(typeFolder, "String");
+ TypeConfig typeFont = createTypeConfig(typeFolder, "Font");
+ TypeConfig typeColor = createTypeConfig(typeFolder, "Color");
+ TypeConfig typeFill = createTypeConfig(typeFolder, "Fill");
+ TypeConfig typeLine = createTypeConfig(typeFolder, "Line");
+
+ // Create properties
+ Folder propertiesFolder = createFolder(getRootFolder(), "properties");
+ // PropertyId propertyIsVisible = createPropertyId(propertiesFolder, "isVisible", typeBoolean);
+ // PropertyId propertyIsAbstract = createPropertyId(propertiesFolder, "isAbstract", typeBoolean);
+ // PropertyId propertyFill = createPropertyId(propertiesFolder, "fill", typeFill);
+ PropertyId propertyLine = createPropertyId(propertiesFolder, "line", typeLine);
+ PropertyId propertyFont = createPropertyId(propertiesFolder, "font", typeFont);
+ PropertyId propertyBgcolor = createPropertyId(propertiesFolder, "bgcolor", typeColor);
+ PropertyId propertyFgcolor = createPropertyId(propertiesFolder, "fgcolor", typeColor);
+
+ PropertyId propertyCSS = createPropertyId(propertiesFolder, "css", typeString);
+
+ // Bind operators to layers
+ Folder opBindingFolder = createFolder(getRootFolder(), "opBindings");
+
+ LayerOperatorMultipleBinding layerOpBindingsA = createLayerOperatorsMultipleBinding(opBindingFolder, stackedLayersOperatorConfig);
+ // createOperatorBinding(layerOpBindingsA, propertyIsVisible, operatorBooleanAnd);
+ // createOperatorBinding(layerOpBindingsA, propertyIsAbstract, operatorBooleanAnd);
+ // createOperatorBinding(layerOpBindingsA, propertyFill, operatorFillAverage);
+
+ LayerOperatorMultipleBinding layerOpBindingsB = createLayerOperatorsMultipleBinding(opBindingFolder, stackedLayersOperatorMinimunConfig);
+ // createOperatorBinding(layerOpBindingsB, propertyIsVisible, operatorBooleanOr);
+ // createOperatorBinding(layerOpBindingsB, propertyIsAbstract, operatorBooleanOr);
+ // createOperatorBinding(layerOpBindingsB, propertyFill, operatorFillAverage);
+
+ LayerOperatorMultipleBinding layerOpBindingsAverage = createLayerOperatorsMultipleBinding(opBindingFolder, stackedLayersOperatorAverage);
+ // createOperatorBinding(layerOpBindingsAverage, propertyIsVisible, operatorBooleanOr);
+ // createOperatorBinding(layerOpBindingsAverage, propertyIsAbstract, operatorBooleanOr);
+ // createOperatorBinding(layerOpBindingsAverage, propertyFill, operatorFillAverage);
+
+ }
+
+ /**
+ * Create the resource and add it the root folder.
+ *
+ * @return
+ */
+ protected Folder createResourceAndRootFolder() {
+ // Create a resource set.
+ ResourceSet resourceSet = new ResourceSetImpl();
+
+ // Register the default resource factory -- only needed for stand-alone!
+ resourceSet.getResourceFactoryRegistry().getExtensionToFactoryMap().put(
+ Resource.Factory.Registry.DEFAULT_EXTENSION, new XMIResourceFactoryImpl());
+
+ // Get the URI of the model file.
+ URI fileURI = URI.createURI("config.layersconfig");
+
+ // Create a resource for this file.
+ resource = resourceSet.createResource(fileURI);
+ Folder parent = LayersconfigFactory.eINSTANCE.createFolder();
+ resource.getContents().add(parent);
+ return parent;
+ }
+
+
+ /**
+ * @return the resource
+ */
+ public Resource getResource() {
+ return resource;
+ }
+
+ /**
+ * Get the root folder of the model.
+ * There is always a root folder
+ *
+ * @return
+ */
+ public Folder getRootFolder() {
+ return (Folder) getResource().getContents().get(0);
+ }
+
+ /**
+ * Get all {@link LayerOperatorConfig} contained in the model.
+ *
+ * @return
+ */
+ public List<LayerOperatorConfig> getAllLayerOperatorConfig() {
+
+ List<LayerOperatorConfig> res = new ArrayList<LayerOperatorConfig>();
+
+ TreeIterator<EObject> iter = resource.getAllContents();
+ while (iter.hasNext()) {
+ EObject obj = iter.next();
+ if (obj instanceof LayerOperatorConfig) {
+ res.add((LayerOperatorConfig) obj);
+ }
+ }
+ return res;
+ }
+
+ /**
+ * Get all object of the specified type contained in the model.
+ *
+ * @param type
+ * The expected type for objects
+ *
+ * @return A list of object with the specified type.
+ */
+ @SuppressWarnings("unchecked")
+ public <T extends EObject> List<T> getAllOfType(Class<T> type) {
+ List<T> res = new ArrayList<T>();
+
+ TreeIterator<EObject> iter = resource.getAllContents();
+ while (iter.hasNext()) {
+ EObject obj = iter.next();
+ if (type.isInstance(obj)) {
+ res.add((T) obj);
+ }
+ }
+ return res;
+ }
+
+ /**
+ * Get all operators config objects.
+ *
+ * @return
+ */
+ public List<OperatorConfig> getAllOperatorConfig() {
+
+ return getAllOfType(OperatorConfig.class);
+ }
+
+
+ /**
+ * Get all {@link OperatorBinding} declared in the model.
+ *
+ * @return
+ */
+ public List<OperatorBinding> getAllOperatorBinding() {
+ return getAllOfType(OperatorBinding.class);
+ }
+
+
+ /**
+ * Initialize the provided model with some defs for tests.
+ *
+ * @param model
+ */
+ private void initLayersConfigModel(LayersConfigModel model) {
+
+ }
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/LayersConfigModelUtils.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/LayersConfigModelUtils.java
new file mode 100755
index 0000000..e2032f3
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/LayersConfigModelUtils.java
@@ -0,0 +1,113 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders;
+
+import org.eclipse.papyrus.layers.configmodel.layersconfig.Folder;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.LayerOperatorConfig;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.LayerOperatorMultipleBinding;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.LayersconfigFactory;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.OperatorBinding;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.OperatorConfig;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.PropertyId;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.TypeConfig;
+
+
+/**
+ * Set of utility methods to create elements in a {@link LayersConfigModel}.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class LayersConfigModelUtils {
+
+ /**
+ * Create a {@link Folder} element
+ *
+ * @param parent
+ * @param name
+ * @return
+ */
+ static public Folder createFolder(Folder parent, String name) {
+ Folder folder = LayersconfigFactory.eINSTANCE.createFolder();
+ folder.setName(name);
+ parent.getFolderElements().add(folder);
+ return folder;
+ }
+
+ /**
+ * Create a {@link LayerOperatorConfig} element
+ *
+ * @param parent
+ * @param ID
+ * @param classname
+ * @return
+ */
+ static public LayerOperatorConfig createLayerOperatorConfig(Folder parent, String ID, String classname) {
+ LayerOperatorConfig config = LayersconfigFactory.eINSTANCE.createLayerOperatorConfig();
+ config.setName(ID);
+ config.setClassname(classname);
+ parent.getFolderElements().add(config);
+ return config;
+ }
+
+ /**
+ * Create a {@link OperatorConfig} element
+ *
+ * @param parent
+ * @param ID
+ * @param classname
+ * @return
+ */
+ static public OperatorConfig createPropertyOperatorConfig(Folder parent, String ID, String classname) {
+ OperatorConfig config = LayersconfigFactory.eINSTANCE.createOperatorConfig();
+ config.setName(ID);
+ config.setClassname(classname);
+ parent.getFolderElements().add(config);
+ return config;
+ }
+
+ /**
+ *
+ * @param owner
+ * @param layerOperator
+ * @return
+ */
+ static public LayerOperatorMultipleBinding createLayerOperatorsMultipleBinding(Folder owner, LayerOperatorConfig layerOperator) {
+ LayerOperatorMultipleBinding config = LayersconfigFactory.eINSTANCE.createLayerOperatorMultipleBinding();
+ config.setLayerOperatorConfig(layerOperator);
+ owner.getFolderElements().add(config);
+ return config;
+ }
+
+ static public OperatorBinding createOperatorBinding(LayerOperatorMultipleBinding owner, PropertyId propertyId, OperatorConfig operatorConfig) {
+ OperatorBinding binding = LayersconfigFactory.eINSTANCE.createOperatorBinding();
+ binding.setPropertyId(propertyId);
+ binding.setOperator(operatorConfig);
+ binding.setOwner(owner);
+ return binding;
+ }
+
+ static public PropertyId createPropertyId(Folder parent, String ID, TypeConfig type) {
+ PropertyId propertyId = LayersconfigFactory.eINSTANCE.createPropertyId();
+ propertyId.setName(ID);
+ propertyId.setType(type);
+ parent.getFolderElements().add(propertyId);
+ return propertyId;
+ }
+
+ static public TypeConfig createTypeConfig(Folder parent, String ID) {
+ TypeConfig config = LayersconfigFactory.eINSTANCE.createTypeConfig();
+ config.setName(ID);
+ parent.getFolderElements().add(config);
+ return config;
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/RegistriesLoader.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/RegistriesLoader.java
new file mode 100755
index 0000000..50c9bd1
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/layers/loaders/RegistriesLoader.java
@@ -0,0 +1,99 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders;
+
+import static org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.Activator.log;
+
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.InstanciationException;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.NotFoundException;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayerOperatorDescriptor;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayerOperatorDescriptorRegistry;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.Property;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.PropertyOperator;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.PropertyRegistry;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.LayerOperatorConfig;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.OperatorBinding;
+import org.eclipse.papyrus.layers.configmodel.layersconfig.OperatorConfig;
+
+
+/**
+ * A loader used to load various Registries from a unique {@link LayersConfigModel}.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class RegistriesLoader implements ILayerOperatorDescriptorRegistryLoader {
+
+ /**
+ * The model used to load the registries.
+ *
+ */
+ protected LayersConfigModel model;
+
+ /**
+ * Constructor.
+ *
+ * @param model
+ */
+ public RegistriesLoader(LayersConfigModel model) {
+ this.model = model;
+ }
+
+ /**
+ * Load the {@link LayerOperatorDescriptorRegistry} from the {@link LayersConfigModel}.
+ *
+ * @see org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.loaders.ILayerOperatorDescriptorRegistryLoader#loadLayerOperatorDescriptorRegistry(org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayerOperatorDescriptorRegistry,
+ * org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.PropertyRegistry)
+ *
+ * @param descriptorRegistry
+ * @param propertyRegistry
+ */
+ @Override
+ public void loadLayerOperatorDescriptorRegistry(LayerOperatorDescriptorRegistry descriptorRegistry, PropertyRegistry propertyRegistry) {
+
+ // Load LayerOperators
+ for (LayerOperatorConfig layerOperatorConfig : model.getAllLayerOperatorConfig()) {
+ try {
+ LayerOperatorDescriptor descriptor = layerOperatorConfig.createLayersOperatorDescriptor();
+ descriptorRegistry.addLayerOperatorDescriptor(descriptor);
+ } catch (InstanciationException e) {
+ log.error("LOG - " + this.getClass().getName() + " - " + e.getMessage(), e);
+ }
+ }
+
+ // Load operators
+ for (OperatorConfig operatorConfig : model.getAllOperatorConfig()) {
+ try {
+ PropertyOperator operator = operatorConfig.createOperatorDescriptor();
+ descriptorRegistry.addPropertyOperator(operator);
+ } catch (InstanciationException e) {
+ log.error("LOG - " + this.getClass().getName() + " - " + e.getMessage(), e);
+ }
+
+ }
+
+ // Populate LayerOperator with operators
+ for (OperatorBinding binding : model.getAllOperatorBinding()) {
+ try {
+ System.err.println("binding.getPropertyId().getName(): " + binding.getPropertyId().getName());
+ Property property = propertyRegistry.getProperty(binding.getPropertyId().getName());
+ String layerDescriptorName = binding.getLayerOperatorConfig().getName();
+ String operatorName = binding.getOperator().getName();
+ descriptorRegistry.attachOperatorToDescriptor(property, operatorName, layerDescriptorName);
+ } catch (NotFoundException e) {
+ log.error("LOG - " + this.getClass().getName() + " - " + e.getMessage(), e);
+ }
+
+ }
+
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/DiagramViewChangedEventNotifier.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/DiagramViewChangedEventNotifier.java
new file mode 100755
index 0000000..171c3ce
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/DiagramViewChangedEventNotifier.java
@@ -0,0 +1,208 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.eclipse.emf.common.notify.Adapter;
+import org.eclipse.emf.common.notify.Notification;
+import org.eclipse.emf.ecore.util.EContentAdapter;
+import org.eclipse.gmf.runtime.notation.Diagram;
+import org.eclipse.gmf.runtime.notation.NotationPackage;
+import org.eclipse.gmf.runtime.notation.View;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStack;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStackApplication;
+
+
+/**
+ * An EMF {@link Adapter} listening on notation::diagram::view added and removed.
+ *
+ * This class listen to a {@link Diagram} and send following events to listeners:
+ * <ul>
+ * <li>view removed</li>
+ * <li>view added</li>
+ * </ul>
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class DiagramViewChangedEventNotifier extends EContentAdapter {
+
+ boolean isDisposed = false;
+
+ /**
+ * List of listener to notify.
+ */
+ protected List<IDiagramViewEventListener> listeners = new ArrayList<IDiagramViewEventListener>();
+
+ /**
+ * Something happen on the tree of object
+ *
+ * @see org.eclipse.emf.ecore.util.EContentAdapter#notifyChanged(org.eclipse.emf.common.notify.Notification)
+ *
+ * @param msg
+ */
+ @Override
+ public void notifyChanged(Notification notification) {
+
+ // Self atttach
+ super.notifyChanged(notification);
+
+ // We are only interested in views (from newValue if set, or oldValue if removed)
+ // TODO Use an appropriate filter / Predicate to filter views.
+ Object newValue = notification.getNewValue();
+ if (!(newValue instanceof View || notification.getOldValue() instanceof View)) {
+ return;
+ }
+ // Check diagram modification
+ // There is 4 sources: View::persistedChildren and View::transientChildren
+ // Diagram::persistedChildren and Diagram::transientChildren
+ Object feature = notification.getFeature();
+ if (feature == NotationPackage.eINSTANCE.getView_PersistedChildren()
+ || feature == NotationPackage.eINSTANCE.getView_TransientChildren()
+ || feature == NotationPackage.eINSTANCE.getDiagram_PersistedEdges()
+ || feature == NotationPackage.eINSTANCE.getDiagram_TransientEdges()) {
+ // LayerOperator::layers || LayersStack::layers
+ // check the event type.
+ switch (notification.getEventType()) {
+ case Notification.SET:
+
+ break;
+ case Notification.ADD:
+ // A view is added
+ fireDiagramViewAddedEvent(notification);
+ break;
+ case Notification.REMOVE:
+ // A layer is removed
+ fireDiagramViewRemovedEvent(notification);
+ break;
+ }
+ }
+
+ };
+
+ /**
+ * This Adapter is for {@link LayersTreeEventNotifier}.
+ *
+ * @see org.eclipse.emf.common.notify.impl.AdapterImpl#isAdapterForType(java.lang.Object)
+ *
+ * @param type
+ * @return
+ */
+ @Override
+ public boolean isAdapterForType(Object type) {
+ return type == DiagramViewChangedEventNotifier.class;
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param layersModel
+ */
+ public DiagramViewChangedEventNotifier() {
+ }
+
+ /**
+ * Dispose the synchronizer
+ */
+ public void dispose() {
+
+ if (isDisposed()) {
+ return;
+ }
+
+ isDisposed = true;
+ listeners.clear();
+ }
+
+ /**
+ * Return true if the object is disposed.
+ *
+ * @return
+ */
+ public boolean isDisposed() {
+ return isDisposed == true;
+ }
+
+ /**
+ * Add the specified listener to the list of listener.
+ * Do not add it if the listener is already in the list.
+ *
+ * @param listener
+ */
+ public void addEventListener(IDiagramViewEventListener listener) {
+
+ if (listener == null) {
+ return;
+ }
+
+ // Check if exist
+ if (listeners.contains(listener)) {
+ return;
+ }
+
+ listeners.add(listener);
+ }
+
+ /**
+ * Remove the specified listener from the list of listeners.
+ *
+ * @param listener
+ */
+ public void removeEventListener(IDiagramViewEventListener listener) {
+
+ listeners.remove(listener);
+ }
+
+ /**
+ * Called by events when a {@link LayersStack} is added to the {@link LayersStackApplication}
+ *
+ * @param msg
+ */
+ protected void fireDiagramViewAddedEvent(Notification msg) {
+ for (IDiagramViewEventListener listener : listeners) {
+ listener.diagramViewAdded(msg);
+ }
+ }
+
+ /**
+ * Called by events when a {@link LayersStack} is added to the {@link LayersStackApplication}
+ *
+ * @param msg
+ */
+ protected void fireDiagramViewRemovedEvent(Notification msg) {
+ for (IDiagramViewEventListener listener : listeners) {
+ listener.diagramViewRemoved(msg);
+ }
+ }
+
+ /**
+ * Get the removed diagram in case of diagramRemoved event
+ *
+ * @param msg
+ * @return
+ */
+ public static View viewAddedEvent_getAddedView(Notification msg) {
+ return (View) msg.getNewValue();
+ }
+
+ /**
+ * Get the removed diagram in case of diagramRemoved event
+ *
+ * @param msg
+ * @return
+ */
+ public static View viewAddedEvent_getRemovedView(Notification msg) {
+ return (View) msg.getOldValue();
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/DiagramViewChangedEventNotifierFactory.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/DiagramViewChangedEventNotifierFactory.java
new file mode 100755
index 0000000..1f987ea
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/DiagramViewChangedEventNotifierFactory.java
@@ -0,0 +1,70 @@
+/*****************************************************************************
+ * Copyright (c) 2013 Cedric Dumoulin.
+ *
+ *
+ * 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:
+ * Cedric Dumoulin Cedric.dumoulin@lifl.fr - Initial API and implementation
+ *
+ *****************************************************************************/
+
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier;
+
+import org.eclipse.emf.common.notify.Adapter;
+import org.eclipse.emf.common.notify.Notifier;
+import org.eclipse.emf.common.notify.impl.AdapterFactoryImpl;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStack;
+
+/**
+ * Factory used to create a {@link DiagramViewChangedEventNotifier}.
+ * The factory ensures that there is only one Notifier for a given {@link LayersStack}.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class DiagramViewChangedEventNotifierFactory extends AdapterFactoryImpl {
+
+ /**
+ * Global factory.
+ */
+ static public DiagramViewChangedEventNotifierFactory instance = new DiagramViewChangedEventNotifierFactory();
+
+ /**
+ * Convenience method.
+ *
+ * @param target
+ * @return
+ */
+ public DiagramViewChangedEventNotifier adapt(Notifier target) {
+ return (DiagramViewChangedEventNotifier) adapt(target, DiagramViewChangedEventNotifier.class);
+ }
+
+ /**
+ *
+ * @see org.eclipse.emf.common.notify.impl.AdapterFactoryImpl#createAdapter(org.eclipse.emf.common.notify.Notifier)
+ *
+ * @param target
+ * @return
+ */
+ @Override
+ protected Adapter createAdapter(Notifier target) {
+ return new DiagramViewChangedEventNotifier();
+ }
+
+ /**
+ * This Factory is for {@link DiagramViewChangedEventNotifier}.
+ *
+ * @see org.eclipse.emf.common.notify.impl.AdapterFactoryImpl#isFactoryForType(java.lang.Object)
+ *
+ * @param type
+ * @return
+ */
+ @Override
+ public boolean isFactoryForType(Object type) {
+ return type == DiagramViewChangedEventNotifier.class;
+ }
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/DiagramViewEventNotifier.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/DiagramViewEventNotifier.java
new file mode 100755
index 0000000..497dd16
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/DiagramViewEventNotifier.java
@@ -0,0 +1,211 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.eclipse.emf.common.notify.Adapter;
+import org.eclipse.emf.common.notify.Notification;
+import org.eclipse.emf.ecore.util.EContentAdapter;
+import org.eclipse.gmf.runtime.notation.Diagram;
+import org.eclipse.gmf.runtime.notation.NotationPackage;
+import org.eclipse.gmf.runtime.notation.View;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStack;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStackApplication;
+
+
+/**
+ * This class listen to a {@link Diagram} and send following events to listeners:
+ * <ul>
+ * <li>view removed</li>
+ * <li>view added</li>
+ * </ul>
+ *
+ * @author cedric dumoulin
+ * @deprecated use {@link DiagramViewChangedEventNotifier} instead.
+ */
+@Deprecated
+public class DiagramViewEventNotifier {
+
+ protected Diagram diagram;
+
+ /**
+ * List of listener to notify.
+ */
+ protected List<IDiagramViewEventListener> listeners = new ArrayList<IDiagramViewEventListener>();
+
+ protected Adapter diagramViewListener = new EContentAdapter() {
+
+ /**
+ * Something happen on the tree of object
+ *
+ * @see org.eclipse.emf.ecore.util.EContentAdapter#notifyChanged(org.eclipse.emf.common.notify.Notification)
+ *
+ * @param msg
+ */
+ @Override
+ public void notifyChanged(Notification notification) {
+
+ // Self atttach
+ super.notifyChanged(notification);
+
+ // We are only interested in views (from newValue if set, or oldValue if removed)
+ Object newValue = notification.getNewValue();
+ if (!(newValue instanceof View || notification.getOldValue() instanceof View)) {
+ return;
+ }
+ // Check diagram modification
+ // There is 4 sources: View::persistedChildren and View::transientChildren
+ // Diagram::persistedChildren and Diagram::transientChildren
+ Object feature = notification.getFeature();
+ if (feature == NotationPackage.eINSTANCE.getView_PersistedChildren()
+ || feature == NotationPackage.eINSTANCE.getView_TransientChildren()
+ || feature == NotationPackage.eINSTANCE.getDiagram_PersistedEdges()
+ || feature == NotationPackage.eINSTANCE.getDiagram_TransientEdges()) {
+ // LayerOperator::layers || LayersStack::layers
+ // check the event type.
+ switch (notification.getEventType()) {
+ case Notification.SET:
+
+ break;
+ case Notification.ADD:
+ // A view is added
+ fireDiagramViewAddedEvent(notification);
+ break;
+ case Notification.REMOVE:
+ // A layer is removed
+ fireDiagramViewRemovedEvent(notification);
+ break;
+ }
+ }
+ }
+
+ };
+
+ /**
+ * Constructor.
+ *
+ * @param layersModel
+ */
+ public DiagramViewEventNotifier(Diagram diagram) {
+ this.diagram = diagram;
+ activate();
+ }
+
+ /**
+ * Activate the listeners.
+ *
+ */
+ protected void activate() {
+ // Listen on diagram removed events
+ diagram.eAdapters().add(diagramViewListener);
+ }
+
+ /**
+ * Deactivate listeners
+ */
+ protected void deactivate() {
+ // Listen on diagram removed events
+ diagram.eAdapters().remove(diagramViewListener);
+ }
+
+ /**
+ * Dispose the synchronizer
+ */
+ public void dispose() {
+ // Deactivate listeners
+ deactivate();
+ diagram = null;
+ }
+
+ /**
+ * Return true if the object is disposed.
+ *
+ * @return
+ */
+ public boolean isDisposed() {
+ return diagram == null;
+ }
+
+ /**
+ * Add the specified listener to the list of listener.
+ * Do not add it if the listener is already in the list.
+ *
+ * @param listener
+ */
+ public void addEventListener(IDiagramViewEventListener listener) {
+
+ if (listener == null) {
+ return;
+ }
+
+ // Check if exist
+ if (listeners.contains(listener)) {
+ return;
+ }
+
+ listeners.add(listener);
+ }
+
+ /**
+ * Remove the specified listener from the list of listeners.
+ *
+ * @param listener
+ */
+ public void removeEventListener(IDiagramViewEventListener listener) {
+
+ listeners.remove(listener);
+ }
+
+ /**
+ * Called by events when a {@link LayersStack} is added to the {@link LayersStackApplication}
+ *
+ * @param msg
+ */
+ protected void fireDiagramViewAddedEvent(Notification msg) {
+ for (IDiagramViewEventListener listener : listeners) {
+ listener.diagramViewAdded(msg);
+ }
+ }
+
+ /**
+ * Called by events when a {@link LayersStack} is added to the {@link LayersStackApplication}
+ *
+ * @param msg
+ */
+ protected void fireDiagramViewRemovedEvent(Notification msg) {
+ for (IDiagramViewEventListener listener : listeners) {
+ listener.diagramViewRemoved(msg);
+ }
+ }
+
+ /**
+ * Get the removed diagram in case of diagramRemoved event
+ *
+ * @param msg
+ * @return
+ */
+ public static View viewAddedEvent_getAddedView(Notification msg) {
+ return (View) msg.getNewValue();
+ }
+
+ /**
+ * Get the removed diagram in case of diagramRemoved event
+ *
+ * @param msg
+ * @return
+ */
+ public static View viewAddedEvent_getRemovedView(Notification msg) {
+ return (View) msg.getOldValue();
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/IDiagramViewEventListener.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/IDiagramViewEventListener.java
new file mode 100755
index 0000000..338d513
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/IDiagramViewEventListener.java
@@ -0,0 +1,44 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier;
+
+import org.eclipse.emf.common.notify.Notification;
+import org.eclipse.gmf.runtime.notation.Diagram;
+import org.eclipse.gmf.runtime.notation.View;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStackApplication;
+
+
+/**
+ * Class implementing this interface can listen to event from a {@link LayersStackApplication}.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public interface IDiagramViewEventListener {
+
+ /**
+ * Called by events when a {@link View} is added to the {@link Diagram} or one of its contained
+ * elements.
+ *
+ * @param msg
+ */
+ public void diagramViewAdded(Notification msg);
+
+ /**
+ * Called by events when a {@link View} is removed from the {@link Diagram} or one of its contained
+ * elements.
+ *
+ * @param msg
+ */
+ public void diagramViewRemoved(Notification msg);
+
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/ILayersTreeEventListener.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/ILayersTreeEventListener.java
new file mode 100755
index 0000000..116f048
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/ILayersTreeEventListener.java
@@ -0,0 +1,67 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier;
+
+import org.eclipse.emf.common.notify.Notification;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayerOperator;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStack;
+
+
+/**
+ * Class implementing this interface can listen to event from a {@link LayersStack}.
+ * Interface for listeners whising to be informed of change in the Tree of Layers structure. <br>
+ * Listeners of such events should register themself to the notifier {@link LayersTreeEventNotifier}. <br>
+ * The following events are fired:
+ * <ul>
+ * <li>LayerAdded</li>
+ * <li>LayerRemoved</li>
+ * <li>LayerMoved</li>
+ * <li>LayerSet</li>
+ * </ul>
+ *
+ * @author cedric dumoulin
+ *
+ */
+public interface ILayersTreeEventListener {
+
+ /**
+ * Method called when a layer is added to one layer.
+ * The event contains: the layer.
+ *
+ * @param notification
+ */
+ public void layerAdded(Notification notification);
+
+ /**
+ * Method called when a layer is removed from one layer.
+ * The event contains: the layer.
+ *
+ * @param notification
+ */
+ public void layerRemoved(Notification notification);
+
+ /**
+ * Method called when a layer is moved inside a {@link LayerOperator}.
+ * The event contains: the layer.
+ *
+ * @param notification
+ */
+ public void layerMoved(Notification notification);
+
+ /**
+ * Method called when a layer is set.
+ * The event contains: the layer.
+ *
+ * @param notification
+ */
+ public void layerSet(Notification notification);
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/IUmlNamedElementChangedEventListener.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/IUmlNamedElementChangedEventListener.java
new file mode 100755
index 0000000..41c11e3
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/IUmlNamedElementChangedEventListener.java
@@ -0,0 +1,34 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier;
+
+import org.eclipse.emf.common.notify.Notification;
+import org.eclipse.uml2.uml.NamedElement;
+
+
+/**
+ * Class implementing this interface can listen to event from a {@link NamedElement}.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public interface IUmlNamedElementChangedEventListener {
+
+ /**
+ * Called by events when a property is changed in a {@link NamedElement}
+ *
+ * @param msg
+ */
+ public void valueChanged(Notification msg);
+
+
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/LayersTreeEventNotifier.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/LayersTreeEventNotifier.java
new file mode 100755
index 0000000..59df8ac
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/LayersTreeEventNotifier.java
@@ -0,0 +1,207 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier;
+
+import static org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.Activator.log;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.eclipse.emf.common.notify.Notification;
+import org.eclipse.emf.ecore.util.EContentAdapter;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersPackage;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStack;
+
+
+/**
+ * Notifier/observers firing events concerning the structure of the tree of layers.
+ * Obeserver should implements {@link ILayersTreeEventListener} and register themself to this
+ * notifier.
+ *
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class LayersTreeEventNotifier extends EContentAdapter {
+
+ /**
+ * List of listener to notify.
+ */
+ protected List<ILayersTreeEventListener> listeners = new ArrayList<ILayersTreeEventListener>();
+
+ /**
+ * Constructor.
+ *
+ * @param layersStack
+ * The observed {@link LayersStack}.
+ */
+ public LayersTreeEventNotifier() {
+ }
+
+ /**
+ * Dispose this object.
+ */
+ public void dispose() {
+ if (isDisposed()) {
+ return;
+ }
+ listeners.clear();
+ listeners = null;
+ }
+
+ /**
+ * Return true if the object is disposed.
+ *
+ * @return
+ */
+ public boolean isDisposed() {
+ return listeners == null;
+ }
+
+ /**
+ * Called when something happen on the tree.
+ *
+ * @see org.eclipse.emf.ecore.util.EContentAdapter#notifyChanged(org.eclipse.emf.common.notify.Notification)
+ *
+ * @param notification
+ */
+ @Override
+ public void notifyChanged(Notification notification) {
+ if (log.isDebugEnabled()) {
+ log.debug(this.getClass().getSimpleName() + ".notifyChanged( "
+ + notification.getFeature() + ")");
+ }
+
+ // Self atttach
+ super.notifyChanged(notification);
+
+ // Check layers modification
+ // There is two sources: LayerOperator::layers and LayersStack::layers
+ if (notification.getFeature() == LayersPackage.eINSTANCE.getLayerOperator_Layers()
+ || notification.getFeature() == LayersPackage.eINSTANCE.getLayersStack_Layers()) {
+ // LayerOperator::layers || LayersStack::layers
+ // check the event type.
+ switch (notification.getEventType()) {
+ case Notification.SET:
+ fireLayerSet(notification);
+ break;
+ case Notification.ADD:
+ // A layer is added
+ fireLayerAdded(notification);
+ break;
+ case Notification.REMOVE:
+ // A layer is removed
+ fireLayerRemoved(notification);
+ break;
+ case Notification.MOVE:
+ // A layer is moved
+ fireLayerMoved(notification);
+ break;
+ }
+ }
+ }
+
+ /**
+ * This Adapter is for {@link LayersTreeEventNotifier}.
+ *
+ * @see org.eclipse.emf.common.notify.impl.AdapterImpl#isAdapterForType(java.lang.Object)
+ *
+ * @param type
+ * @return
+ */
+ @Override
+ public boolean isAdapterForType(Object type) {
+ return type == LayersTreeEventNotifier.class;
+ }
+
+ /**
+ * Add the specified listener to the list of listener.
+ * Do not add it if the listener is already in the list.
+ *
+ * @param listener
+ */
+ public void addLayersModelEventListener(ILayersTreeEventListener listener) {
+
+ if (listener == null) {
+ return;
+ }
+
+ // Check if exist
+ if (listeners.contains(listener)) {
+ return;
+ }
+
+ listeners.add(listener);
+ }
+
+ /**
+ * Remove the specified listener from the list of listeners.
+ *
+ * @param listener
+ */
+ public void removeLayersModelEventListener(ILayersTreeEventListener listener) {
+
+ listeners.remove(listener);
+ }
+
+ /**
+ * Method called when a layer is added to one layer.
+ * The event contains: the layer.
+ *
+ * @param notification
+ */
+ public void fireLayerSet(Notification notification) {
+
+ for (ILayersTreeEventListener listener : listeners) {
+ listener.layerSet(notification);
+ }
+ }
+
+ /**
+ * Method called when a layer is added to one layer.
+ * The event contains: the layer.
+ *
+ * @param notification
+ */
+ public void fireLayerAdded(Notification notification) {
+
+ for (ILayersTreeEventListener listener : listeners) {
+ listener.layerAdded(notification);
+ }
+ }
+
+ /**
+ * Method called when a layer is removed from one layer.
+ * The event contains: the layer.
+ *
+ * @param notification
+ */
+ public void fireLayerRemoved(Notification notification) {
+
+ for (ILayersTreeEventListener listener : listeners) {
+ listener.layerRemoved(notification);
+ }
+ }
+
+ /**
+ * Method called when a layer is moved in LayerStack.
+ * The event contains: the layer.
+ *
+ * @param notification
+ */
+ public void fireLayerMoved(Notification notification) {
+
+ for (ILayersTreeEventListener listener : listeners) {
+ listener.layerMoved(notification);
+ }
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/LayersTreeEventNotifierFactory.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/LayersTreeEventNotifierFactory.java
new file mode 100755
index 0000000..a7a0c2a
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/LayersTreeEventNotifierFactory.java
@@ -0,0 +1,70 @@
+/*****************************************************************************
+ * Copyright (c) 2013 Cedric Dumoulin.
+ *
+ *
+ * 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:
+ * Cedric Dumoulin Cedric.dumoulin@lifl.fr - Initial API and implementation
+ *
+ *****************************************************************************/
+
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier;
+
+import org.eclipse.emf.common.notify.Adapter;
+import org.eclipse.emf.common.notify.Notifier;
+import org.eclipse.emf.common.notify.impl.AdapterFactoryImpl;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStack;
+
+/**
+ * Factory used to create a {@link LayersTreeEventNotifier}.
+ * The factory ensures that there is only one Notifier for a given {@link LayersStack}.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class LayersTreeEventNotifierFactory extends AdapterFactoryImpl {
+
+ /**
+ * Global factory.
+ */
+ static public LayersTreeEventNotifierFactory instance = new LayersTreeEventNotifierFactory();
+
+ /**
+ * Convenience method.
+ *
+ * @param target
+ * @return
+ */
+ public LayersTreeEventNotifier adapt(Notifier target) {
+ return (LayersTreeEventNotifier) adapt(target, LayersTreeEventNotifier.class);
+ }
+
+ /**
+ *
+ * @see org.eclipse.emf.common.notify.impl.AdapterFactoryImpl#createAdapter(org.eclipse.emf.common.notify.Notifier)
+ *
+ * @param target
+ * @return
+ */
+ @Override
+ protected Adapter createAdapter(Notifier target) {
+ return new LayersTreeEventNotifier();
+ }
+
+ /**
+ * This Factory is for {@link LayersTreeEventNotifier}.
+ *
+ * @see org.eclipse.emf.common.notify.impl.AdapterFactoryImpl#isFactoryForType(java.lang.Object)
+ *
+ * @param type
+ * @return
+ */
+ @Override
+ public boolean isFactoryForType(Object type) {
+ return type == LayersTreeEventNotifier.class;
+ }
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/UmlNamedElementChangedEventNotifier.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/UmlNamedElementChangedEventNotifier.java
new file mode 100755
index 0000000..a4ca69b
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/UmlNamedElementChangedEventNotifier.java
@@ -0,0 +1,181 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.eclipse.emf.common.notify.Adapter;
+import org.eclipse.emf.common.notify.Notification;
+import org.eclipse.emf.ecore.util.EContentAdapter;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStack;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStackApplication;
+import org.eclipse.uml2.uml.NamedElement;
+
+
+/**
+ * An EMF {@link Adapter} listening on uml::NamedElement properties changes.
+ *
+ * This class listen to a {@link NamedElement} and send following events to listeners:
+ * <ul>
+ * <li>valueChanged</li>
+ * </ul>
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class UmlNamedElementChangedEventNotifier extends EContentAdapter {
+
+ boolean isDisposed = false;
+
+ /**
+ * List of listener to notify.
+ */
+ protected List<IUmlNamedElementChangedEventListener> listeners = new ArrayList<IUmlNamedElementChangedEventListener>();
+
+ /**
+ * Something happen on the tree of object
+ *
+ * @see org.eclipse.emf.ecore.util.EContentAdapter#notifyChanged(org.eclipse.emf.common.notify.Notification)
+ *
+ * @param msg
+ */
+ @Override
+ public void notifyChanged(Notification notification) {
+
+ // Self atttach
+ super.notifyChanged(notification);
+
+ // Retain only NamedElement
+ if (!(notification.getNotifier() instanceof NamedElement)) {
+ return;
+ }
+
+ // No more filter: all events are forwarded
+ fireValueChangedEvent(notification);
+
+ // // We are only interested in NamedElement (from newValue if set, or oldValue if removed)
+ // Object newValue = notification.getNewValue();
+ // if( ! (newValue instanceof NamedElement || notification.getOldValue() instanceof NamedElement ) ) {
+ // return;
+ // }
+ // // Check diagram modification
+ // // There is 4 sources: View::persistedChildren and View::transientChildren
+ // // Diagram::persistedChildren and Diagram::transientChildren
+ // Object feature = notification.getFeature();
+ // if( feature == UMLPackage.eINSTANCE.getNamedElement()
+ // || feature == NotationPackage.eINSTANCE.getView_TransientChildren()
+ // || feature == NotationPackage.eINSTANCE.getDiagram_PersistedEdges()
+ // || feature == NotationPackage.eINSTANCE.getDiagram_TransientEdges() ) {
+ // // LayerOperator::layers || LayersStack::layers
+ // // check the event type.
+ // switch(notification.getEventType()) {
+ // case Notification.SET:
+ //
+ // break;
+ // case Notification.ADD:
+ // // A view is added
+ // fireValueChangedEvent(notification);
+ // break;
+ // case Notification.REMOVE:
+ // // A layer is removed
+ // fireDiagramViewRemovedEvent(notification);
+ // break;
+ // }
+ // }
+
+ };
+
+ /**
+ * This Adapter is for {@link LayersTreeEventNotifier}.
+ *
+ * @see org.eclipse.emf.common.notify.impl.AdapterImpl#isAdapterForType(java.lang.Object)
+ *
+ * @param type
+ * @return
+ */
+ @Override
+ public boolean isAdapterForType(Object type) {
+ return type == UmlNamedElementChangedEventNotifier.class;
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param layersModel
+ */
+ public UmlNamedElementChangedEventNotifier() {
+ }
+
+ /**
+ * Dispose the synchronizer
+ */
+ public void dispose() {
+
+ if (isDisposed()) {
+ return;
+ }
+
+ isDisposed = true;
+ listeners.clear();
+ }
+
+ /**
+ * Return true if the object is disposed.
+ *
+ * @return
+ */
+ public boolean isDisposed() {
+ return isDisposed == true;
+ }
+
+ /**
+ * Add the specified listener to the list of listener.
+ * Do not add it if the listener is already in the list.
+ *
+ * @param listener
+ */
+ public void addEventListener(IUmlNamedElementChangedEventListener listener) {
+
+ if (listener == null) {
+ return;
+ }
+
+ // Check if exist
+ if (listeners.contains(listener)) {
+ return;
+ }
+
+ listeners.add(listener);
+ }
+
+ /**
+ * Remove the specified listener from the list of listeners.
+ *
+ * @param listener
+ */
+ public void removeEventListener(IUmlNamedElementChangedEventListener listener) {
+
+ listeners.remove(listener);
+ }
+
+ /**
+ * Called by events when a {@link LayersStack} is added to the {@link LayersStackApplication}
+ *
+ * @param msg
+ */
+ protected void fireValueChangedEvent(Notification msg) {
+ for (IUmlNamedElementChangedEventListener listener : listeners) {
+ listener.valueChanged(msg);
+ }
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/UmlNamedElementChangedEventNotifierFactory.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/UmlNamedElementChangedEventNotifierFactory.java
new file mode 100755
index 0000000..e461611
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/UmlNamedElementChangedEventNotifierFactory.java
@@ -0,0 +1,70 @@
+/*****************************************************************************
+ * Copyright (c) 2013 Cedric Dumoulin.
+ *
+ *
+ * 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:
+ * Cedric Dumoulin Cedric.dumoulin@lifl.fr - Initial API and implementation
+ *
+ *****************************************************************************/
+
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier;
+
+import org.eclipse.emf.common.notify.Adapter;
+import org.eclipse.emf.common.notify.Notifier;
+import org.eclipse.emf.common.notify.impl.AdapterFactoryImpl;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersStack;
+
+/**
+ * Factory used to create a {@link UmlNamedElementChangedEventNotifier}.
+ * The factory ensures that there is only one Notifier for a given {@link LayersStack}.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class UmlNamedElementChangedEventNotifierFactory extends AdapterFactoryImpl {
+
+ /**
+ * Global factory.
+ */
+ static public UmlNamedElementChangedEventNotifierFactory instance = new UmlNamedElementChangedEventNotifierFactory();
+
+ /**
+ * Convenience method.
+ *
+ * @param target
+ * @return
+ */
+ public UmlNamedElementChangedEventNotifier adapt(Notifier target) {
+ return (UmlNamedElementChangedEventNotifier) adapt(target, UmlNamedElementChangedEventNotifier.class);
+ }
+
+ /**
+ *
+ * @see org.eclipse.emf.common.notify.impl.AdapterFactoryImpl#createAdapter(org.eclipse.emf.common.notify.Notifier)
+ *
+ * @param target
+ * @return
+ */
+ @Override
+ protected Adapter createAdapter(Notifier target) {
+ return new UmlNamedElementChangedEventNotifier();
+ }
+
+ /**
+ * This Factory is for {@link UmlNamedElementChangedEventNotifier}.
+ *
+ * @see org.eclipse.emf.common.notify.impl.AdapterFactoryImpl#isFactoryForType(java.lang.Object)
+ *
+ * @param type
+ * @return
+ */
+ @Override
+ public boolean isFactoryForType(Object type) {
+ return type == UmlNamedElementChangedEventNotifier.class;
+ }
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/package-info.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/package-info.java
new file mode 100755
index 0000000..3462554
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/notifier/package-info.java
@@ -0,0 +1,18 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+/**
+ * This package provides reusable event notifiers.
+ *
+ * @author cedric dumoulin
+ *
+ */
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier;
+
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/BooleanAndOperator.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/BooleanAndOperator.java
new file mode 100755
index 0000000..7002f0c
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/BooleanAndOperator.java
@@ -0,0 +1,93 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.operators;
+
+import org.eclipse.emf.common.util.EList;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.LayersException;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.command.ComputePropertyValueCommand;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.BooleanInstance;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersFactory;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.TypeInstance;
+
+
+/**
+ * @author cedric dumoulin
+ *
+ */
+public class BooleanAndOperator implements CustomPropertyOperatorsInstance {
+
+ public static final BooleanInstance FALSE_INSTANCE;
+ public static final BooleanInstance TRUE_INSTANCE;
+
+ static {
+ FALSE_INSTANCE = LayersFactory.eINSTANCE.createBooleanInstance();
+ FALSE_INSTANCE.setValue(false);
+ TRUE_INSTANCE = LayersFactory.eINSTANCE.createBooleanInstance();
+ TRUE_INSTANCE.setValue(true);
+ }
+
+ /**
+ *
+ * @see org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.operators.CustomPropertyOperatorsInstance#getComputePropertyValueCommand(org.eclipse.emf.common.util.EList)
+ *
+ * @param property
+ * @return
+ * @throws LayersException
+ */
+ @Override
+ public ComputePropertyValueCommand getComputePropertyValueCommand(EList<ComputePropertyValueCommand> nestedCommand) throws LayersException {
+ return new BooleanAndOperatorCommand(nestedCommand);
+ }
+
+
+ /**
+ * Class implementing an And command.
+ *
+ */
+ class BooleanAndOperatorCommand implements ComputePropertyValueCommand {
+
+ EList<ComputePropertyValueCommand> nestedCommand;
+
+ /**
+ *
+ * Constructor.
+ *
+ * @param nestedCommand
+ */
+ public BooleanAndOperatorCommand(EList<ComputePropertyValueCommand> nestedCommand) {
+ this.nestedCommand = nestedCommand;
+ }
+
+ /**
+ * Compute the value.
+ *
+ * @see org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.command.ComputePropertyValueCommand#getCmdValue()
+ *
+ * @return
+ * @throws LayersException
+ */
+ @Override
+ public TypeInstance getCmdValue() throws LayersException {
+
+ // Do an boolean and: all value should be true.
+ // Return as soon as a false is encountered
+ for (ComputePropertyValueCommand curCmd : nestedCommand) {
+ boolean curCmdRes = ((BooleanInstance) curCmd.getCmdValue()).isValue();
+ if (curCmdRes == false) {
+ return FALSE_INSTANCE;
+ }
+ }
+
+ return TRUE_INSTANCE;
+ }
+
+ }
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/BooleanOrOperator.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/BooleanOrOperator.java
new file mode 100755
index 0000000..9816faf
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/BooleanOrOperator.java
@@ -0,0 +1,93 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.operators;
+
+import org.eclipse.emf.common.util.EList;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.LayersException;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.command.ComputePropertyValueCommand;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.BooleanInstance;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersFactory;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.TypeInstance;
+
+
+/**
+ * @author cedric dumoulin
+ *
+ */
+public class BooleanOrOperator implements CustomPropertyOperatorsInstance {
+
+ public static final BooleanInstance FALSE_INSTANCE;
+ public static final BooleanInstance TRUE_INSTANCE;
+
+ static {
+ FALSE_INSTANCE = LayersFactory.eINSTANCE.createBooleanInstance();
+ FALSE_INSTANCE.setValue(false);
+ TRUE_INSTANCE = LayersFactory.eINSTANCE.createBooleanInstance();
+ TRUE_INSTANCE.setValue(true);
+ }
+
+ /**
+ *
+ * @see org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.operators.CustomPropertyOperatorsInstance#getComputePropertyValueCommand(org.eclipse.emf.common.util.EList)
+ *
+ * @param property
+ * @return
+ * @throws LayersException
+ */
+ @Override
+ public ComputePropertyValueCommand getComputePropertyValueCommand(EList<ComputePropertyValueCommand> nestedCommand) throws LayersException {
+ return new BooleanOrOperatorCommand(nestedCommand);
+ }
+
+
+ /**
+ * Class implementing an And command.
+ *
+ */
+ class BooleanOrOperatorCommand implements ComputePropertyValueCommand {
+
+ EList<ComputePropertyValueCommand> nestedCommand;
+
+ /**
+ *
+ * Constructor.
+ *
+ * @param nestedCommand
+ */
+ public BooleanOrOperatorCommand(EList<ComputePropertyValueCommand> nestedCommand) {
+ this.nestedCommand = nestedCommand;
+ }
+
+ /**
+ * Compute the value.
+ *
+ * @see org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.command.ComputePropertyValueCommand#getCmdValue()
+ *
+ * @return
+ * @throws LayersException
+ */
+ @Override
+ public TypeInstance getCmdValue() throws LayersException {
+
+ // Do an boolean or: at least one value should be true.
+ // Return as soon as a true is encountered
+ for (ComputePropertyValueCommand curCmd : nestedCommand) {
+ boolean curCmdRes = ((BooleanInstance) curCmd.getCmdValue()).isValue();
+ if (curCmdRes == true) {
+ return TRUE_INSTANCE;
+ }
+ }
+
+ return FALSE_INSTANCE;
+ }
+
+ }
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/CustomPropertyOperatorsInstance.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/CustomPropertyOperatorsInstance.java
new file mode 100755
index 0000000..a4601be
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/CustomPropertyOperatorsInstance.java
@@ -0,0 +1,34 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.operators;
+
+import org.eclipse.emf.common.util.EList;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.LayersException;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.command.ComputePropertyValueCommand;
+
+
+/**
+ * Interface to be implemented by operators declared as "custom".
+ *
+ * @author cedric dumoulin
+ *
+ */
+public interface CustomPropertyOperatorsInstance {
+
+ /**
+ * Return the command allowing to compute the value resulting on applying this operator on the specified properties.
+ *
+ * @param property
+ * @return The command returning the result
+ * @throws LayersException
+ */
+ public ComputePropertyValueCommand getComputePropertyValueCommand(EList<ComputePropertyValueCommand> property) throws LayersException;
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/FillAverageOperator.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/FillAverageOperator.java
new file mode 100755
index 0000000..964f8fb
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/operators/FillAverageOperator.java
@@ -0,0 +1,101 @@
+/*******************************************************************************
+ * Copyright (c) 2013 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:
+ * Cedric Dumoulin - cedric.dumoulin@lifl.fr
+ ******************************************************************************/
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.operators;
+
+import org.eclipse.emf.common.util.EList;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.LayersException;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.command.ComputePropertyValueCommand;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.BooleanInstance;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.ColorInstance;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.FillInstance;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.LayersFactory;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.TypeInstance;
+
+
+/**
+ * @author cedric dumoulin
+ *
+ */
+public class FillAverageOperator implements CustomPropertyOperatorsInstance {
+
+ public static final BooleanInstance FALSE_INSTANCE;
+ public static final BooleanInstance TRUE_INSTANCE;
+
+ static {
+ FALSE_INSTANCE = LayersFactory.eINSTANCE.createBooleanInstance();
+ FALSE_INSTANCE.setValue(false);
+ TRUE_INSTANCE = LayersFactory.eINSTANCE.createBooleanInstance();
+ TRUE_INSTANCE.setValue(true);
+ }
+
+ /**
+ *
+ * @see org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.operators.CustomPropertyOperatorsInstance#getComputePropertyValueCommand(org.eclipse.emf.common.util.EList)
+ *
+ * @param property
+ * @return
+ * @throws LayersException
+ */
+ @Override
+ public ComputePropertyValueCommand getComputePropertyValueCommand(EList<ComputePropertyValueCommand> nestedCommand) throws LayersException {
+ return new FillAverageCommand(nestedCommand);
+ }
+
+
+ /**
+ * Class implementing an And command.
+ *
+ */
+ class FillAverageCommand implements ComputePropertyValueCommand {
+
+ EList<ComputePropertyValueCommand> nestedCommand;
+
+ /**
+ *
+ * Constructor.
+ *
+ * @param nestedCommand
+ */
+ public FillAverageCommand(EList<ComputePropertyValueCommand> nestedCommand) {
+ this.nestedCommand = nestedCommand;
+ }
+
+ /**
+ * Compute the value.
+ *
+ * @see org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.command.ComputePropertyValueCommand#getCmdValue()
+ *
+ * @return
+ * @throws LayersException
+ */
+ @Override
+ public TypeInstance getCmdValue() throws LayersException {
+
+ int fill = 0;
+ int color = 0;
+ // compute the average values
+ for (ComputePropertyValueCommand curCmd : nestedCommand) {
+ FillInstance curValue = ((FillInstance) curCmd.getCmdValue());
+ fill += curValue.getTransparency();
+ color += curValue.getFillColor().getValue();
+ }
+
+ // Create a result
+ FillInstance res = LayersFactory.eINSTANCE.createFillInstance();
+ ColorInstance colorInstance = LayersFactory.eINSTANCE.createColorInstance();
+ res.setFillColor(colorInstance);
+ res.setTransparency(fill / nestedCommand.size());
+ res.getFillColor().setValue(color / nestedCommand.size());
+ return res;
+ }
+
+ }
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/Collections3.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/Collections3.java
new file mode 100755
index 0000000..ca54419
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/Collections3.java
@@ -0,0 +1,76 @@
+/*****************************************************************************
+ * Copyright (c) 2013 Cedric Dumoulin.
+ *
+ *
+ * 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:
+ * Cedric Dumoulin Cedric.dumoulin@lifl.fr - Initial API and implementation
+ *
+ *****************************************************************************/
+
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.util;
+
+import java.util.ArrayList;
+import java.util.Collection;
+
+import com.google.common.collect.Collections2;
+
+/**
+ * Set of utility methods for Collections.
+ *
+ * @see Collections2
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class Collections3 {
+
+ /**
+ * Reset the toChange list to the content of the newContent list.
+ * Minimize the change calls on the toChange list.
+ * This method ensure that there is at most 2 writing calls to the list to modify: one
+ * removeAll(toBeRemoved) and one addAll(toBeAdded).
+ *
+ * @param toChange
+ * @param newContent
+ */
+ public static <E> void resetListTo(Collection<E> toChange, Collection<E> newContent) {
+
+ // Compute removed and added
+ Collection<E> elementsToRemove = new ArrayList<E>();
+ Collection<E> elementsToAdd = new ArrayList<E>();
+
+ // Compute added and removed elements. Walk both list 2 times.
+ // This could certainly be improved.
+ // TODO improve the algorithm
+
+ // Compute added elements
+ for (E o : newContent) {
+ if (!toChange.contains(o)) {
+ elementsToAdd.add(o);
+ continue;
+ }
+ }
+
+ // Compute removed elements
+ for (E o : toChange) {
+ if (!newContent.contains(o)) {
+ elementsToRemove.add(o);
+ continue;
+ }
+ }
+
+ // Change the list
+ if (!elementsToRemove.isEmpty()) {
+ toChange.removeAll(elementsToRemove);
+ }
+ if (!elementsToAdd.isEmpty()) {
+ toChange.addAll(elementsToAdd);
+ }
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/DiagramViewToListSynchronizer.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/DiagramViewToListSynchronizer.java
new file mode 100755
index 0000000..29eadd2
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/DiagramViewToListSynchronizer.java
@@ -0,0 +1,118 @@
+/*****************************************************************************
+ * Copyright (c) 2013 Cedric Dumoulin.
+ *
+ *
+ * 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:
+ * Cedric Dumoulin Cedric.dumoulin@lifl.fr - Initial API and implementation
+ *
+ *****************************************************************************/
+
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.util;
+
+import java.util.Collection;
+
+import org.eclipse.emf.common.notify.Notification;
+import org.eclipse.gmf.runtime.notation.Diagram;
+import org.eclipse.gmf.runtime.notation.View;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier.DiagramViewChangedEventNotifier;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier.DiagramViewChangedEventNotifierFactory;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.notifier.IDiagramViewEventListener;
+
+import com.google.common.collect.Iterables;
+
+/**
+ * This class allows to synchronize a specfied list with {@link View} elements from the specified {@link Diagram}.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class DiagramViewToListSynchronizer {
+
+ protected Diagram diagram;
+
+ protected Collection<View> synchronizedList;
+
+ /**
+ * Listener on Diagram's View event.
+ * Synchronize the associated list according to the event.
+ */
+ private IDiagramViewEventListener viewEventListener = new IDiagramViewEventListener() {
+
+ @Override
+ public void diagramViewRemoved(Notification msg) {
+ // Add the removed view from the list
+ synchronizedList.remove(msg.getOldValue());
+
+ }
+
+ @Override
+ public void diagramViewAdded(Notification msg) {
+
+ View view = (View) msg.getNewValue();
+ if (synchronizedList.contains(view)) {
+ return;
+ }
+ // add element
+ synchronizedList.add(view);
+ }
+ };
+
+ /**
+ * Constructor.
+ *
+ * @param diagram
+ * @param synchronizedList
+ */
+ public DiagramViewToListSynchronizer(Diagram diagram, Collection<View> synchronizedList) {
+ this.synchronizedList = synchronizedList;
+
+ // Listen to diagram's view event
+ setDiagram(diagram);
+ }
+
+ /**
+ * The diagram should be set later.
+ * Constructor.
+ *
+ * @param synchronizedList
+ */
+ public DiagramViewToListSynchronizer(Collection<View> synchronizedList) {
+ this.synchronizedList = synchronizedList;
+ }
+
+ /**
+ * Set the diagram synchronized to the list.
+ *
+ * @param diagram
+ */
+ public void setDiagram(Diagram diagram) {
+
+ DiagramViewChangedEventNotifier notifier;
+ // stop listening on old diagram if any
+ Diagram oldDiagram = this.diagram;
+ if (oldDiagram != null) {
+ notifier = DiagramViewChangedEventNotifierFactory.instance.adapt(oldDiagram);
+ notifier.removeEventListener(viewEventListener);
+ }
+ // Reset the list and add view responding to the predicate
+ synchronizedList.clear();
+
+ Iterable<View> filteredList = Iterables.filter(diagram.getChildren(), LayerDiagramViewPredicate.instance);
+ for (View view : filteredList) {
+ synchronizedList.add(view);
+ }
+
+ // attach to new diagram
+ this.diagram = diagram;
+ if (diagram != null) {
+ notifier = DiagramViewChangedEventNotifierFactory.instance.adapt(diagram);
+ notifier.addEventListener(viewEventListener);
+ }
+
+ }
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/LayerDiagramViewPredicate.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/LayerDiagramViewPredicate.java
new file mode 100755
index 0000000..f047af3
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/LayerDiagramViewPredicate.java
@@ -0,0 +1,64 @@
+/*****************************************************************************
+ * Copyright (c) 2013 Cedric Dumoulin.
+ *
+ *
+ * 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:
+ * Cedric Dumoulin Cedric.dumoulin@lifl.fr - Initial API and implementation
+ *
+ *****************************************************************************/
+
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.util;
+
+import org.eclipse.emf.ecore.EObject;
+import org.eclipse.gmf.runtime.notation.Edge;
+import org.eclipse.gmf.runtime.notation.Shape;
+import org.eclipse.gmf.runtime.notation.View;
+import org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.layers.Layer;
+import org.eclipse.uml2.uml.NamedElement;
+
+import com.google.common.base.Predicate;
+
+/**
+ * A Predicate used to filter {@link View} allowed by {@link Layer}.
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class LayerDiagramViewPredicate implements Predicate<View> {
+
+ /**
+ * Singleton instnace.
+ */
+ public static final LayerDiagramViewPredicate instance = new LayerDiagramViewPredicate();
+
+ /**
+ * Return true if the view is allowed by Layers.
+ *
+ * @see com.google.common.base.Predicate#apply(java.lang.Object)
+ *
+ * @param view
+ * @return
+ */
+ @Override
+ public boolean apply(View view) {
+
+ // View should be Shape or Edge
+ if (!(view instanceof Shape || view instanceof Edge)) {
+ return false;
+ }
+
+ // Domain element should be set and should be NamedElement
+ EObject ele = view.getElement();
+ if (ele == null || !(ele instanceof NamedElement)) {
+ return false;
+ }
+ // ok
+ return true;
+ }
+
+}
diff --git a/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/ObservableListView.java b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/ObservableListView.java
new file mode 100755
index 0000000..3c6b9aa
--- /dev/null
+++ b/layers/plugins/org.eclipse.papyrus.infra.gmfdiag.layers.model/src/org/eclipse/papyrus/internal/infra/gmfdiag/layers/model/util/ObservableListView.java
@@ -0,0 +1,353 @@
+/*****************************************************************************
+ * Copyright (c) 2013 Cedric Dumoulin.
+ *
+ *
+ * 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:
+ * Cedric Dumoulin Cedric.dumoulin@lifl.fr - Initial API and implementation
+ *
+ *****************************************************************************/
+
+package org.eclipse.papyrus.internal.infra.gmfdiag.layers.model.util;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.List;
+
+import com.google.common.collect.ForwardingList;
+import com.google.common.collect.Lists;
+import com.google.common.eventbus.EventBus;
+
+/**
+ * An observable list notifying of events on the delegated list.
+ * This view allows to observe a provided list.
+ * The following events are notified:
+ * <ul>
+ * <li>elements added</li>
+ * <li>elements removed</li>
+ * <li></li>
+ * <li></li>
+ * </ul>
+ *
+ * @author cedric dumoulin
+ *
+ */
+public class ObservableListView<E> extends ForwardingList<E> {
+
+ protected List<E> delegate;
+
+ protected EventBus eventBus = new EventBus(ObservableListView.class.getName());
+
+ /**
+ * Construct an observable list with a {@link ArrayList} as delegate.
+ * Constructor.
+ *
+ */
+ public ObservableListView() {
+ this(new ArrayList<E>());
+ }
+
+ /**
+ * Constructor.
+ * Build an observable list based on the provided list.
+ *
+ * @param delegate
+ */
+ public ObservableListView(List<E> delegate) {
+ this.delegate = delegate;
+ }
+
+ @Override
+ protected List<E> delegate() {
+ return delegate;
+ }
+
+ /**
+ * @return the eventBus
+ */
+ public EventBus getEventBus() {
+ return eventBus;
+ }
+
+ @Override
+ public boolean add(E element) {
+ boolean isModified = delegate().add(element);
+ if (isModified) {
+ eventBus.post(new ObservableListEvent(element));
+ }
+
+ return isModified;
+ }
+
+ @Override
+ public boolean addAll(Collection<? extends E> collection) {
+ boolean isModified = delegate().addAll(collection);
+ if (isModified) {
+ eventBus.post(new ObservableListEvent(collection));
+ }
+
+ return isModified;
+ }
+
+ @Override
+ public void add(int index, E element) {
+ delegate().add(index, element);
+ eventBus.post(new ObservableListEvent(element));
+ }
+
+ @Override
+ public boolean addAll(int index, Collection<? extends E> elements) {
+ // TODO Auto-generated method stub
+ boolean isModified = delegate().addAll(index, elements);
+ if (isModified) {
+ eventBus.post(new ObservableListEvent(elements));
+ }
+
+ return isModified;
+ }
+
+ @Override
+ public E remove(int index) {
+ E removed = super.remove(index);
+ getEventBus().post(new ObservableListEvent(null, removed));
+
+ return removed;
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public boolean remove(Object object) {
+ boolean isRemoved = super.remove(object);
+ if (isRemoved) {
+ getEventBus().post(new ObservableListEvent(null, (E) object));
+ }
+ return isRemoved;
+ }
+
+ /**
+ *
+ * @see com.google.common.collect.ForwardingCollection#removeAll(java.util.Collection)
+ *
+ * @param collection
+ * @return
+ */
+ @Override
+ public boolean removeAll(Collection<?> collection) {
+ // Compute the removed elements (for the events)
+ List<E> removedElements = Lists.newArrayList(delegate());
+ removedElements.retainAll(collection);
+
+ // Do remove
+ boolean isRemoved = super.removeAll(collection);
+ if (isRemoved) {
+ getEventBus().post(new ObservableListEvent(null, removedElements));
+ }
+ return isRemoved;
+ }
+
+ /**
+ * Reset the collection to the specified collection.
+ * Throw events containing the added and removed elements.
+ *
+ * @param collection
+ * @return
+ */
+ public boolean resetTo(Collection<? extends E> collection) {
+
+ // Compute removed and added
+ Collection<E> elementsToRemove = new ArrayList<E>();
+ Collection<E> elementsToAdd = new ArrayList<E>();
+
+ // Cached list of attached elements
+ Collection<? extends E> attachedElements = delegate();
+
+ // Compute added and removed elements. Walk both list 2 times.
+ // This could certainly be improved.
+ // TODO improve the algorithm
+
+ // Compute added elements
+ for (E o : collection) {
+ if (!attachedElements.contains(o)) {
+ elementsToAdd.add(o);
+ continue;
+ }
+ }
+
+ // Compute removed elements
+ for (E o : attachedElements) {
+ if (!collection.contains(o)) {
+ elementsToRemove.add(o);
+ continue;
+ }
+ }
+
+ // Change the list
+ delegate().clear();
+ delegate().addAll(collection);
+
+ // Fire event
+ boolean isModified = !(elementsToAdd.isEmpty() && elementsToRemove.isEmpty());
+ if (isModified) {
+ getEventBus().post(new ObservableListEvent(elementsToAdd, elementsToRemove));
+ }
+
+ return isModified;
+ }
+
+ /**
+ * Event used to specify that the list is changed
+ *
+ * @author cedric dumoulin
+ *
+ */
+ public class ObservableListEvent {
+
+ Collection<? extends E> addedElements = Collections.emptyList();
+ Collection<? extends E> removedElements = Collections.emptyList();
+
+ /**
+ *
+ * Constructor.
+ *
+ */
+ public ObservableListEvent() {
+ this.addedElements = Collections.emptyList();
+ this.removedElements = Collections.emptyList();
+ }
+
+ /**
+ *
+ * Constructor.
+ *
+ */
+ public ObservableListEvent(Collection<? extends E> addedElements) {
+ if (addedElements != null) {
+ this.addedElements = addedElements;
+ } else {
+ this.addedElements = Collections.emptyList();
+ }
+
+ this.removedElements = Collections.emptyList();
+ }
+
+ /**
+ * Constructor.
+ *
+ * @param addedElements
+ * added elements or null
+ * @param removedElements
+ * removed elements or null
+ */
+ public ObservableListEvent(Collection<? extends E> addedElements, Collection<? extends E> removedElements) {
+ if (addedElements != null) {
+ this.addedElements = addedElements;
+ } else {
+ this.addedElements = Collections.emptyList();
+ }
+
+ if (removedElements != null) {
+ this.removedElements = removedElements;
+ } else {
+ this.removedElements = Collections.emptyList();
+ }
+ }
+
+ /**
+ *
+ * Constructor.
+ *
+ * @param addedElement
+ * An element added or null;
+ * @param removedElement
+ * An element added or null
+ */
+ public ObservableListEvent(E addedElement, E removedElement) {
+
+ if (addedElement != null) {
+ addedElements = Collections.singletonList(addedElement);
+ } else {
+ addedElements = Collections.emptyList();
+ }
+
+ if (removedElement != null) {
+ removedElements = Collections.singletonList(removedElement);
+ } else {
+ removedElements = Collections.emptyList();
+ }
+ }
+
+ /**
+ *
+ * Constructor.
+ *
+ * @param addedElement
+ * An element added or null;
+ */
+ public ObservableListEvent(E addedElement) {
+
+ if (addedElement != null) {
+ addedElements = Collections.singletonList(addedElement);
+ } else {
+ addedElements = Collections.emptyList();
+ }
+ removedElements = Collections.emptyList();
+ }
+
+ /**
+ * @return the addedElements
+ */
+ public Collection<? extends E> getAddedElements() {
+ return addedElements;
+ }
+
+ // /**
+ // * @param addedElements the addedElements to set
+ // */
+ // public void setAddedElements(List<E> addedElements) {
+ // this.addedElements = addedElements;
+ // }
+ //
+ // /**
+ // * @param addedElements the addedElements to set
+ // */
+ // public void setAddedElements(E addedElement) {
+ // this.addedElements = Collections.singletonList(addedElement);
+ // }
+
+ /**
+ * @return the removedElements
+ */
+ public Collection<? extends E> getRemovedElements() {
+ return removedElements;
+ }
+
+ // /**
+ // * @param removedElements the removedElements to set
+ // */
+ // public void setRemovedElements(List<E> removedElements) {
+ // this.removedElements = removedElements;
+ // }
+ //
+ // /**
+ // * @param removedElements the removedElements to set
+ // */
+ // public void setRemovedElements(E removedElement) {
+ // this.removedElements = Collections.singletonList(removedElement);
+ // }
+ }
+
+ /**
+ * Return the underlying list. This can be used as an unnotifying version of the list.
+ *
+ * @return
+ */
+ public List<E> getUnnotifyingList() {
+ return delegate();
+
+ }
+}

Back to the top