[505651] Add contextual menu in diagram editor to launch generations

Bug: 505651
Change-Id: I47215b400044664866c94a69c11965447739652c
diff --git a/org.eclipse.emf.ecoretools.design.ui/plugin.xml b/org.eclipse.emf.ecoretools.design.ui/plugin.xml
index 82042a0..f4407ce 100644
--- a/org.eclipse.emf.ecoretools.design.ui/plugin.xml
+++ b/org.eclipse.emf.ecoretools.design.ui/plugin.xml
@@ -32,6 +32,10 @@
             actionClass="org.eclipse.emf.ecoretools.design.ui.action.CreateDynamicInstanceAction"
             id="org.eclipse.emf.ecoretools.design.action.createDynamicInstanceActionID">
       </javaActions>
+      <javaActions
+            actionClass="org.eclipse.emf.ecoretools.design.ui.action.GenerateAllAction"
+            id="org.eclipse.emf.ecoretools.design.action.generateAllID">
+      </javaActions>
    </extension>
    <!--
    <extension
diff --git a/org.eclipse.emf.ecoretools.design.ui/src/org/eclipse/emf/ecoretools/design/ui/action/GenerateAllAction.java b/org.eclipse.emf.ecoretools.design.ui/src/org/eclipse/emf/ecoretools/design/ui/action/GenerateAllAction.java
new file mode 100644
index 0000000..5267284
--- /dev/null
+++ b/org.eclipse.emf.ecoretools.design.ui/src/org/eclipse/emf/ecoretools/design/ui/action/GenerateAllAction.java
@@ -0,0 +1,111 @@
+/*******************************************************************************
+ * Copyright (c) 2016 Obeo.
+ * 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:
+ *     Obeo - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.emf.ecoretools.design.ui.action;
+
+import java.util.Collection;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import org.eclipse.emf.codegen.ecore.CodeGenEcorePlugin;
+import org.eclipse.emf.codegen.ecore.generator.Generator;
+import org.eclipse.emf.codegen.ecore.genmodel.GenModel;
+import org.eclipse.emf.codegen.ecore.genmodel.generator.GenBaseGeneratorAdapter;
+import org.eclipse.emf.codegen.ecore.genmodel.presentation.GeneratorUIUtil;
+import org.eclipse.emf.codegen.ecore.genmodel.provider.GenModelEditPlugin;
+import org.eclipse.emf.ecore.EObject;
+import org.eclipse.sirius.tools.api.ui.IExternalJavaAction;
+import org.eclipse.sirius.viewpoint.DSemanticDecorator;
+import org.eclipse.swt.widgets.Display;
+import org.eclipse.ui.IEditorPart;
+import org.eclipse.ui.IWorkbench;
+import org.eclipse.ui.PlatformUI;
+import org.eclipse.ui.progress.IProgressService;
+
+import com.google.common.collect.Iterables;
+import com.google.common.collect.Lists;
+import com.google.common.collect.Sets;
+
+public class GenerateAllAction implements IExternalJavaAction {
+
+	/**
+	 * The action expects a single EClass as input.
+	 */
+	public boolean canExecute(Collection<? extends EObject> selections) {
+		return true;
+	}
+
+	public void execute(Collection<? extends EObject> selections, Map<String, Object> parameters) {
+		Object genmodelsParamValue = parameters.get("genmodels");
+		String scope = (String) parameters.get("scope");
+		if (scope == null) {
+			scope = "model, edit, editor, tests";
+		}
+		if (genmodelsParamValue != null && genmodelsParamValue instanceof Collection) {
+			launchEMFGeneration(genmodelsParamValue, scope);
+
+		}
+
+	}
+
+	private void launchEMFGeneration(Object genmodelsParamValue, final String scope) {
+		final List<GenModel> gens = Lists
+				.newArrayList(Iterables.filter((Collection<?>) genmodelsParamValue, GenModel.class));
+
+		Display.getDefault().syncExec(new Runnable() {
+
+			public void run() {
+				IEditorPart activeEditorPart = PlatformUI.getWorkbench().getActiveWorkbenchWindow().getActivePage()
+						.getActiveEditor();
+				GeneratorUIUtil.GeneratorOperation operation = new GeneratorUIUtil.GeneratorOperation(
+						activeEditorPart.getSite().getShell());
+				for (GenModel genModel : gens) {
+					genModel.reconcile();
+					genModel.setCanGenerate(true);
+					Generator generator = new Generator();
+					generator.setInput(genModel);
+					if (scope.contains("model")) {
+						operation.addGeneratorAndArguments(generator, genModel,
+								GenBaseGeneratorAdapter.MODEL_PROJECT_TYPE,
+								CodeGenEcorePlugin.INSTANCE.getString("_UI_ModelProject_name"));
+					}
+					if (scope.contains("edit")) {
+						operation.addGeneratorAndArguments(generator, genModel,
+								GenBaseGeneratorAdapter.EDIT_PROJECT_TYPE,
+								CodeGenEcorePlugin.INSTANCE.getString("_UI_EditProject_name"));
+					}
+					if (scope.contains("editor")) {
+						operation.addGeneratorAndArguments(generator, genModel,
+								GenBaseGeneratorAdapter.EDITOR_PROJECT_TYPE,
+								CodeGenEcorePlugin.INSTANCE.getString("_UI_EditorProject_name"));
+					}
+					if (scope.contains("tests")) {
+						operation.addGeneratorAndArguments(generator, genModel,
+								GenBaseGeneratorAdapter.TESTS_PROJECT_TYPE,
+								CodeGenEcorePlugin.INSTANCE.getString("_UI_TestsProject_name"));
+					}
+				}
+				try {
+
+					IWorkbench wb = PlatformUI.getWorkbench();
+					IProgressService ps = wb.getProgressService();
+					ps.busyCursorWhile(operation);
+
+				} catch (Exception exception) {
+					// Something went wrong that shouldn't.
+					//
+					GenModelEditPlugin.INSTANCE.log(exception);
+				}
+			}
+		});
+	}
+
+}
diff --git a/org.eclipse.emf.ecoretools.design/description/ecore.odesign b/org.eclipse.emf.ecoretools.design/description/ecore.odesign
index 028ff88..332f9e5 100644
--- a/org.eclipse.emf.ecoretools.design/description/ecore.odesign
+++ b/org.eclipse.emf.ecoretools.design/description/ecore.odesign
@@ -193,6 +193,53 @@
           </style>
         </containerMappings>
         <toolSections name="Existing Elements">
+          <ownedTools xsi:type="tool:PopupMenu" name="Generate" precondition="aql:OrderedSet{self.target}->select(e | e.eInverse().eClass().ePackage.nsURI->includes('http://www.eclipse.org/emf/2002/GenModel'))">
+            <menuItemDescription xsi:type="tool:OperationAction" name="Generate Model Code" precondition="aql:OrderedSet{views.target}.eInverse().eContainerOrSelf(genmodel::GenModel)->asSet()->select(m | m.modelDirectory.size() > 0)->size() > 0" icon="/org.eclipse.emf.ecoretools.design/icons/full/obj16/GenModel.gif">
+              <view name="views"/>
+              <initialOperation>
+                <firstModelOperations xsi:type="tool:ExternalJavaAction" name="Generate All" id="org.eclipse.emf.ecoretools.design.action.generateAllID">
+                  <parameters name="genmodels" value="aql:OrderedSet{views.target}.eInverse().eContainerOrSelf(genmodel::GenModel)->asSet()"/>
+                  <parameters name="scope" value="model"/>
+                </firstModelOperations>
+              </initialOperation>
+            </menuItemDescription>
+            <menuItemDescription xsi:type="tool:OperationAction" name="Generate Edit Code" precondition="aql:OrderedSet{views.target}.eInverse().eContainerOrSelf(genmodel::GenModel)->asSet()->select(m | m.editDirectory.size() > 0)->size() > 0" icon="/org.eclipse.emf.ecoretools.design/icons/full/obj16/GenModel.gif">
+              <view name="views"/>
+              <initialOperation>
+                <firstModelOperations xsi:type="tool:ExternalJavaAction" name="Generate All" id="org.eclipse.emf.ecoretools.design.action.generateAllID">
+                  <parameters name="genmodels" value="aql:OrderedSet{views.target}.eInverse().eContainerOrSelf(genmodel::GenModel)->asSet()"/>
+                  <parameters name="scope" value="edit"/>
+                </firstModelOperations>
+              </initialOperation>
+            </menuItemDescription>
+            <menuItemDescription xsi:type="tool:OperationAction" name="Generate Editor Code" precondition="aql:OrderedSet{views.target}.eInverse().eContainerOrSelf(genmodel::GenModel)->asSet()->select(m | m.editorDirectory.size() > 0)->size() > 0" icon="/org.eclipse.emf.ecoretools.design/icons/full/obj16/GenModel.gif">
+              <view name="views"/>
+              <initialOperation>
+                <firstModelOperations xsi:type="tool:ExternalJavaAction" name="Generate All" id="org.eclipse.emf.ecoretools.design.action.generateAllID">
+                  <parameters name="genmodels" value="aql:OrderedSet{views.target}.eInverse().eContainerOrSelf(genmodel::GenModel)->asSet()"/>
+                  <parameters name="scope" value="editor"/>
+                </firstModelOperations>
+              </initialOperation>
+            </menuItemDescription>
+            <menuItemDescription xsi:type="tool:OperationAction" name="Generate Tests Code" precondition="aql:OrderedSet{views.target}.eInverse().eContainerOrSelf(genmodel::GenModel)->asSet()->select(m | m.testsDirectory.size() > 0)->size() > 0" icon="/org.eclipse.emf.ecoretools.design/icons/full/obj16/GenModel.gif">
+              <view name="views"/>
+              <initialOperation>
+                <firstModelOperations xsi:type="tool:ExternalJavaAction" name="Generate All" id="org.eclipse.emf.ecoretools.design.action.generateAllID">
+                  <parameters name="genmodels" value="aql:OrderedSet{views.target}.eInverse().eContainerOrSelf(genmodel::GenModel)->asSet()"/>
+                  <parameters name="scope" value="tests"/>
+                </firstModelOperations>
+              </initialOperation>
+            </menuItemDescription>
+            <menuItemDescription xsi:type="tool:OperationAction" name="Generate All" precondition="aql:OrderedSet{self.target}->select(e | e.eInverse().eClass().ePackage.nsURI->includes('http://www.eclipse.org/emf/2002/GenModel'))" icon="/org.eclipse.emf.ecoretools.design/icons/full/obj16/GenModel.gif">
+              <view name="views"/>
+              <initialOperation>
+                <firstModelOperations xsi:type="tool:ExternalJavaAction" name="Generate All" id="org.eclipse.emf.ecoretools.design.action.generateAllID">
+                  <parameters name="genmodels" value="aql:OrderedSet{views.target}.eInverse().eContainerOrSelf(genmodel::GenModel)->asSet()"/>
+                  <parameters name="scope" value="model, edit, editor, tests"/>
+                </firstModelOperations>
+              </initialOperation>
+            </menuItemDescription>
+          </ownedTools>
           <ownedTools xsi:type="tool:SelectionWizardDescription" name="Add" precondition="aql:container.oclIsKindOf(ecore::EPackage)" forceRefresh="true" candidatesExpression="aql:self.getValidsForDiagram(containerView)->asSet() - diagram.getDisplayedEClassifiers()" multiple="true" tree="true" rootExpression="service:rootEPackages" childrenExpression="feature:eContents" iconPath="/org.eclipse.emf.ecoretools.design/icons/full/etools16/search.gif" windowTitle="Select element to add in diagram">
             <element name="element"/>
             <containerView name="containerView"/>
diff --git a/org.eclipse.emf.ecoretools.design/icons/full/obj16/GenModel.gif b/org.eclipse.emf.ecoretools.design/icons/full/obj16/GenModel.gif
new file mode 100644
index 0000000..239367a
--- /dev/null
+++ b/org.eclipse.emf.ecoretools.design/icons/full/obj16/GenModel.gif
Binary files differ