//Generated with EGF 1.6.1.201902111324
package org.eclipse.egf.emf.pattern.editor;

import org.eclipse.egf.emf.pattern.base.*;
import org.eclipse.emf.codegen.ecore.genmodel.util.GenModelUtil;
import org.eclipse.emf.codegen.ecore.genmodel.*;
import org.eclipse.emf.codegen.ecore.genmodel.impl.*;
import org.eclipse.emf.codegen.ecore.genmodel.generator.*;
import org.eclipse.emf.codegen.util.*;
import org.eclipse.emf.ecore.util.*;
import org.eclipse.emf.common.util.*;
import org.eclipse.egf.common.helper.*;
import java.util.*;
import org.eclipse.emf.ecore.*;
import org.eclipse.egf.model.pattern.*;
import org.eclipse.egf.pattern.execution.*;
import org.eclipse.egf.pattern.query.*;

public class PluginProperties extends org.eclipse.egf.emf.pattern.base.GenModelProperties {
	protected static String nl;

	public static synchronized PluginProperties create(String lineSeparator) {
		nl = lineSeparator;
		PluginProperties result = new PluginProperties();
		nl = null;
		return result;
	}

	public final String NL = nl == null ? (System.getProperties().getProperty("line.separator")) : nl;
	protected final String TEXT_1 = "";
	protected final String TEXT_2 = NL + NL + "pluginName = ";
	protected final String TEXT_3 = NL + "providerName = ";
	protected final String TEXT_4 = NL;
	protected final String TEXT_5 = NL + "_UI_";
	protected final String TEXT_6 = "_menu = &";
	protected final String TEXT_7 = " Editor";
	protected final String TEXT_8 = NL + "_UI_CreateChild_menu_item = &New Child" + NL
			+ "_UI_CreateSibling_menu_item = N&ew Sibling" + NL;
	protected final String TEXT_9 = NL + "_UI_ShowPropertiesView_menu_item = Show &Properties View" + NL
			+ "_UI_RefreshViewer_menu_item = &Refresh" + NL + "" + NL + "_UI_SelectionPage_label = Selection";
	protected final String TEXT_10 = NL + "_UI_ParentPage_label = Parent" + NL + "_UI_ListPage_label = List" + NL
			+ "_UI_TreePage_label = Tree" + NL + "_UI_TablePage_label = Table" + NL
			+ "_UI_TreeWithColumnsPage_label = Tree with Columns" + NL + "_UI_ObjectColumn_label = Object" + NL
			+ "_UI_SelfColumn_label = Self";
	protected final String TEXT_11 = NL + NL + "_UI_NoObjectSelected = Selected Nothing" + NL
			+ "_UI_SingleObjectSelected = Selected Object: {0}" + NL + "_UI_MultiObjectSelected = Selected {0} Objects"
			+ NL + "" + NL + "_UI_OpenEditorError_label = Open Editor" + NL + "" + NL
			+ "_UI_Wizard_category = Example EMF Model Creation Wizards" + NL + "" + NL
			+ "_UI_CreateModelError_message = Problems encountered in file \"{0}\"" + NL;
	protected final String TEXT_12 = "_label = ";
	protected final String TEXT_13 = " Model" + NL + "_UI_";
	protected final String TEXT_14 = "_description = Create a new ";
	protected final String TEXT_15 = " model" + NL;
	protected final String TEXT_16 = " Model Editor" + NL + "" + NL + "_UI_";
	protected final String TEXT_17 = "FilenameDefaultBase = My" + NL + "_UI_";
	protected final String TEXT_18 = "FilenameExtensions = ";
	protected final String TEXT_19 = NL + "_UI_Wizard_label = New" + NL + "" + NL
			+ "_WARN_FilenameExtension = The file name must end in ''.{0}''" + NL
			+ "_WARN_FilenameExtensions = The file name must have one of the following extensions: {0}" + NL + "" + NL
			+ "_UI_ModelObject = &Model Object" + NL + "_UI_XMLEncoding = &XML Encoding" + NL
			+ "_UI_XMLEncodingChoices = ";
	protected final String TEXT_20 = NL
			+ "_UI_Wizard_initial_object_description = Specify a file name and select a model object to create";
	protected final String TEXT_21 = NL + "_UI_Wizard_initial_object_description = Select a model object to create";
	protected final String TEXT_22 = NL + NL + "_UI_FileConflict_label = File Conflict" + NL
			+ "_WARN_FileConflict = There are unsaved changes that conflict with changes made outside the editor.  Do you wish to discard this editor's changes?"
			+ NL;
	protected final String TEXT_23 = "_ActionSet_label = ";
	protected final String TEXT_24 = " Action Set" + NL + "_UI_Perspective_label = ";
	protected final String TEXT_25 = NL + NL + "_UI_Browse_label = &Browse..." + NL + "_UI_File_label = &File" + NL
			+ "_UI_Question_title = Question" + NL
			+ "_WARN_FileConflict = The file \"{0}\" already exists.  Do you want to replace the existing file?" + NL
			+ "_UI_Error_title = Error" + NL + "_WARN_No_Editor = There is no editor registered for the file \"{0}\"."
			+ NL + "" + NL + "_UI_Application_title = ";
	protected final String TEXT_26 = " Application" + NL + "_UI_Menu_File_label = &File" + NL
			+ "_UI_Menu_New_label = &New" + NL + "_UI_Menu_Open_label = &Open..." + NL
			+ "_UI_Menu_Open_description = Opens a model object file" + NL + "_UI_Menu_OpenURI_label = &Open URI..."
			+ NL + "_UI_Menu_OpenURI_description = Opens a model object loading it from a URI" + NL
			+ "_UI_Menu_Edit_label = &Edit" + NL + "_UI_Menu_Window_label = &Window" + NL
			+ "_UI_Menu_Help_label = &Help" + NL + "_UI_Menu_About_label = ";
	protected final String TEXT_27 = " &About..." + NL + "_UI_About_title = ";
	protected final String TEXT_28 = " Application" + NL + "_UI_About_text = ";
	protected final String TEXT_29 = " Application about box goes here." + NL;
	protected final String TEXT_30 = " Model Action Set";
	protected final String TEXT_31 = NL;

	public PluginProperties() {
		//Here is the constructor
		StringBuffer stringBuffer = new StringBuffer();

		// add initialisation of the pattern variables (declaration has been already done).

	}

	public String generate(Object argument) throws Exception {
		final StringBuffer stringBuffer = new StringBuffer();

		InternalPatternContext ctx = (InternalPatternContext) argument;
		Map<String, String> queryCtx = null;
		IQuery.ParameterDescription paramDesc = null;
		Node.Container currentNode = ctx.getNode();

		List<Object> parameterList = null;
		//this pattern can only be called by another (i.e. it's not an entry point in execution)

		for (Object parameterParameter : parameterList) {

			this.parameter = (org.eclipse.emf.codegen.ecore.genmodel.GenModel) parameterParameter;

			if (preCondition(ctx)) {
				ctx.setNode(new Node.Container(currentNode, getClass()));
				orchestration(ctx);
			}

		}
		ctx.setNode(currentNode);
		if (ctx.useReporter()) {
			ctx.getReporter().executionFinished(OutputManager.computeExecutionOutput(ctx), ctx);
		}

		stringBuffer.append(TEXT_31);
		stringBuffer.append(TEXT_31);
		return stringBuffer.toString();
	}

	public String orchestration(PatternContext ctx) throws Exception {
		InternalPatternContext ictx = (InternalPatternContext) ctx;

		super.orchestration(new SuperOrchestrationContext(ictx));

		method_preGenerate(new StringBuffer(), ictx);

		method_doGenerate(new StringBuffer(), ictx);
		{
			final Map<String, Object> parameters = getParameters();
			CallbackContext ctx_callback = new CallbackContext(ictx);
			CallHelper.callBack(ctx_callback, parameters);
		}

		method_postGenerate(new StringBuffer(), ictx);

		if (ictx.useReporter()) {
			Map<String, Object> parameterValues = new HashMap<String, Object>();
			parameterValues.put("parameter", this.parameter);
			String outputWithCallBack = OutputManager.computeLoopOutput(ictx);
			String loop = OutputManager.computeLoopOutputWithoutCallback(ictx);
			ictx.getReporter().loopFinished(loop, outputWithCallBack, ictx, parameterValues);
		}
		return null;
	}

	public Map<String, Object> getParameters() {
		final Map<String, Object> parameters = new HashMap<String, Object>();
		parameters.put("parameter", this.parameter);
		return parameters;
	}

	protected void method_setReporterVariables(final StringBuffer stringBuffer, final PatternContext ctx)
			throws Exception {

		GenModel genModel = parameter;
		targetPathName = genModel.getEditorProjectDirectory() + "/" + genModel.getEditorBundleLocalization()
				+ ".properties";

		InternalPatternContext ictx = (InternalPatternContext) ctx;
		new Node.DataLeaf(ictx.getNode(), getClass(), "setReporterVariables", stringBuffer.toString());
	}

	protected void method_setArgument(final StringBuffer stringBuffer, final PatternContext ctx) throws Exception {

		GenModel genModel = parameter;
		argument = parameter;

		InternalPatternContext ictx = (InternalPatternContext) ctx;
		new Node.DataLeaf(ictx.getNode(), getClass(), "setArgument", stringBuffer.toString());
	}

	protected void method_ensureProjectExists(final StringBuffer stringBuffer, final PatternContext ctx)
			throws Exception {

		new CodegenGeneratorAdapter(parameter).ensureProjectExists(genModel.getEditorDirectory(), genModel,
				GenBaseGeneratorAdapter.EDITOR_PROJECT_TYPE, genModel.isUpdateClasspath(), new BasicMonitor());

		InternalPatternContext ictx = (InternalPatternContext) ctx;
		new Node.DataLeaf(ictx.getNode(), getClass(), "ensureProjectExists", stringBuffer.toString());
	}

	protected void method_doGenerate(final StringBuffer stringBuffer, final PatternContext ctx) throws Exception {

		/**
		 * Copyright (c) 2002-2006 IBM Corporation and others.
		 * All rights reserved.   This program and the accompanying materials
		 * are made available under the terms of the Eclipse Public License v2.0
		 * which accompanies this distribution, and is available at
		 * http://www.eclipse.org/legal/epl-v20.html
		 * 
		 * Contributors: 
		 *   IBM - Initial API and implementation
		 */

		GenModel genModel = (GenModel) argument;
		/* Trick to import java.util.* without warnings */Iterator.class.getName();
		stringBuffer.append(TEXT_1);
		{
			//<%@ egf:patternCall patternId="platform:/plugin/org.eclipse.egf.emf.pattern.base/egf/EMF_Pattern_Base.fcore#LogicalName=org.eclipse.egf.emf.pattern.base.HeaderProperties" args="parameter:argument"%>

			InternalPatternContext ictx = (InternalPatternContext) ctx;
			new Node.DataLeaf(ictx.getNode(), getClass(), null, stringBuffer.toString());
			stringBuffer.setLength(0);

			final Map<String, Object> callParameters = new HashMap<String, Object>();
			callParameters.put("argument", parameter);
			CallHelper.executeWithParameterInjection(
					"platform:/plugin/org.eclipse.egf.emf.pattern.base/egf/EMF_Pattern_Base.fcore#_FEoPwCwuEd-jc5T-XaRJlg",
					new ExecutionContext((InternalPatternContext) ctx), callParameters);
			stringBuffer.setLength(0);
		}

		stringBuffer.append(TEXT_2);
		stringBuffer.append(genModel.getEditorBundleName());
		stringBuffer.append(TEXT_3);
		stringBuffer.append(genModel.getEditorBundleVendorName());
		if (genModel.getRuntimePlatform() != GenRuntimePlatform.GWT) {
			stringBuffer.append(TEXT_4);
			boolean hasMultiPageEditor = false;
			for (GenPackage genPackage : genModel.getAllGenPackagesWithClassifiers()) {
				if (genPackage.isMultipleEditorPages()) {
					hasMultiPageEditor = true;
				}
				stringBuffer.append(TEXT_5);
				stringBuffer.append(genPackage.getEditorClassName());
				stringBuffer.append(TEXT_6);
				stringBuffer.append(genPackage.getPrefix());
				stringBuffer.append(TEXT_7);
			}
			stringBuffer.append(TEXT_4);
			if (genModel.isCreationCommands()) {
				stringBuffer.append(TEXT_8);
			}
			stringBuffer.append(TEXT_9);
			if (hasMultiPageEditor) {
				stringBuffer.append(TEXT_10);
			}
			stringBuffer.append(TEXT_11);
			for (GenPackage genPackage : genModel.getAllGenPackagesWithClassifiers()) {
				if (genPackage.isGenerateModelWizard()) {
					stringBuffer.append(TEXT_5);
					stringBuffer.append(genPackage.getModelWizardClassName());
					stringBuffer.append(TEXT_12);
					stringBuffer.append(genPackage.getPrefix());
					stringBuffer.append(TEXT_13);
					stringBuffer.append(genPackage.getModelWizardClassName());
					stringBuffer.append(TEXT_14);
					stringBuffer.append(genPackage.getPrefix());
					stringBuffer.append(TEXT_15);
				}
				stringBuffer.append(TEXT_5);
				stringBuffer.append(genPackage.getEditorClassName());
				stringBuffer.append(TEXT_12);
				stringBuffer.append(genPackage.getPrefix());
				stringBuffer.append(TEXT_16);
				stringBuffer.append(genPackage.getEditorClassName());
				stringBuffer.append(TEXT_17);
				stringBuffer.append(genPackage.getEditorClassName());
				stringBuffer.append(TEXT_18);
				stringBuffer.append(genPackage.getFileExtensions());
				stringBuffer.append(TEXT_4);
			}
			stringBuffer.append(TEXT_19);
			stringBuffer.append(genModel.getXMLEncodingChoices());
			if (genModel.isRichClientPlatform()) {
				stringBuffer.append(TEXT_20);
			} else {
				stringBuffer.append(TEXT_21);
			}
			stringBuffer.append(TEXT_22);
			if (genModel.isRichClientPlatform()) {
				stringBuffer.append(TEXT_5);
				stringBuffer.append(genModel.getEditorAdvisorClassName());
				stringBuffer.append(TEXT_23);
				stringBuffer.append(genModel.getModelName());
				stringBuffer.append(TEXT_24);
				stringBuffer.append(genModel.getModelName());
				stringBuffer.append(TEXT_25);
				stringBuffer.append(genModel.getModelName());
				stringBuffer.append(TEXT_26);
				stringBuffer.append(genModel.getModelName());
				stringBuffer.append(TEXT_27);
				stringBuffer.append(genModel.getModelName());
				stringBuffer.append(TEXT_28);
				stringBuffer.append(genModel.getModelName());
				stringBuffer.append(TEXT_29);
				for (GenPackage genPackage : genModel.getAllGenPackagesWithClassifiers()) {
					if (genPackage.isGenerateModelWizard()) {
						stringBuffer.append(TEXT_5);
						stringBuffer.append(genPackage.getModelWizardClassName());
						stringBuffer.append(TEXT_23);
						stringBuffer.append(genPackage.getPrefix());
						stringBuffer.append(TEXT_30);
					}
				}
				stringBuffer.append(TEXT_4);
			}
		}
		stringBuffer.append(TEXT_4);
		InternalPatternContext ictx = (InternalPatternContext) ctx;
		new Node.DataLeaf(ictx.getNode(), getClass(), "doGenerate", stringBuffer.toString());
	}

	public boolean preCondition(PatternContext ctx) throws Exception {
		GenModel genModel = parameter;
		genModel = parameter.getGenModel();
		boolean canGenerate = new CodegenGeneratorAdapter(parameter)
				.canGenerate("org.eclipse.emf.codegen.ecore.genmodel.generator.EditorProject");
		canGenerate = canGenerate && true;
		return canGenerate;
	}
}