Skip to main content
summaryrefslogtreecommitdiffstats
path: root/core
diff options
context:
space:
mode:
authorMikhail Sennikovsky2007-04-26 13:07:39 -0400
committerMikhail Sennikovsky2007-04-26 13:07:39 -0400
commitc5603e5a0edba5569a4835e2ffed9d14c1958c9d (patch)
tree7fe1781e1c8833334c2b73ee9776c22369aeb56a /core
parent6741a8d019b2908ddd9ae80d086448eff4fba303 (diff)
downloadorg.eclipse.cdt-c5603e5a0edba5569a4835e2ffed9d14c1958c9d.tar.gz
org.eclipse.cdt-c5603e5a0edba5569a4835e2ffed9d14c1958c9d.tar.xz
org.eclipse.cdt-c5603e5a0edba5569a4835e2ffed9d14c1958c9d.zip
Template Engine submission from Bala Torati (Symbian) with some modifications and bug-fixes (see Bug 160012)
Diffstat (limited to 'core')
-rw-r--r--core/org.eclipse.cdt.core.tests/.classpath1
-rw-r--r--core/org.eclipse.cdt.core.tests/build.properties5
-rw-r--r--core/org.eclipse.cdt.core.tests/plugin.xml43
-rw-r--r--core/org.eclipse.cdt.core.tests/suite/org/eclipse/cdt/core/suite/AutomatedIntegrationSuite.java2
-rw-r--r--core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/AllTemplateEngineTests.java52
-rw-r--r--core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TemplateEngineTestsHelper.java103
-rw-r--r--core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestProcesses.java261
-rw-r--r--core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestSharedDefaults.java124
-rw-r--r--core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestTemplateCore.java70
-rw-r--r--core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestTemplateEngine.java64
-rw-r--r--core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestValueStore.java79
-rw-r--r--core/org.eclipse.cdt.core.tests/testdata/AddFile.xml24
-rw-r--r--core/org.eclipse.cdt.core.tests/testdata/AddFiles.xml22
-rw-r--r--core/org.eclipse.cdt.core.tests/testdata/AddLink.xml22
-rw-r--r--core/org.eclipse.cdt.core.tests/testdata/Append.xml36
-rw-r--r--core/org.eclipse.cdt.core.tests/testdata/AppendCreate.xml23
-rw-r--r--core/org.eclipse.cdt.core.tests/testdata/Basename.cpp37
-rw-r--r--core/org.eclipse.cdt.core.tests/testdata/Basename.h27
-rw-r--r--core/org.eclipse.cdt.core.tests/testdata/Copy.xml22
-rw-r--r--core/org.eclipse.cdt.core.tests/testdata/CreateResourceIdentifier.xml35
-rw-r--r--core/org.eclipse.cdt.core.tests/testdata/CreateSourceFolder.xml16
-rw-r--r--core/org.eclipse.cdt.core/.classpath1
-rw-r--r--core/org.eclipse.cdt.core/META-INF/MANIFEST.MF3
-rw-r--r--core/org.eclipse.cdt.core/build.properties5
-rw-r--r--core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/settings/model/CProjectDescription.java2
-rw-r--r--core/org.eclipse.cdt.core/plugin.xml84
-rw-r--r--core/org.eclipse.cdt.core/schema/TemplateDescriptorSchema.xsd220
-rw-r--r--core/org.eclipse.cdt.core/schema/templateProcessTypes.exsd307
-rw-r--r--core/org.eclipse.cdt.core/schema/templates.exsd196
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/SharedDefaults.java325
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateCore.java257
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateDescriptor.java198
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngine.java344
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngineHelper.java221
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngineMessages.java32
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngineUtil.java51
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateInfo.java129
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/messages.properties31
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ConditionalProcessGroup.java284
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/Process.java201
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessArgument.java435
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessFailureException.java66
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessHelper.java232
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessParameter.java111
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessRunner.java115
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessRunnerFactory.java101
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/TemplateProcessHandler.java92
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AddFile.java90
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AddFiles.java107
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AddLink.java58
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/Append.java67
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AppendCreate.java89
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/Copy.java86
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/CreateResourceIdentifier.java42
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/CreateSourceFolder.java148
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/Messages.java32
-rw-r--r--core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/messages.properties58
-rw-r--r--core/org.eclipse.cdt.ui/.classpath1
-rw-r--r--core/org.eclipse.cdt.ui/META-INF/MANIFEST.MF9
-rw-r--r--core/org.eclipse.cdt.ui/build.properties5
-rw-r--r--core/org.eclipse.cdt.ui/icons/dlcl16/list-add.gifbin0 -> 551 bytes
-rw-r--r--core/org.eclipse.cdt.ui/icons/dlcl16/list-delete.gifbin0 -> 564 bytes
-rw-r--r--core/org.eclipse.cdt.ui/icons/dlcl16/list-edit.gifbin0 -> 554 bytes
-rw-r--r--core/org.eclipse.cdt.ui/icons/dlcl16/list-movedown.gifbin0 -> 349 bytes
-rw-r--r--core/org.eclipse.cdt.ui/icons/dlcl16/list-moveup.gifbin0 -> 349 bytes
-rw-r--r--core/org.eclipse.cdt.ui/icons/elcl16/list-add.gifbin0 -> 569 bytes
-rw-r--r--core/org.eclipse.cdt.ui/icons/elcl16/list-delete.gifbin0 -> 586 bytes
-rw-r--r--core/org.eclipse.cdt.ui/icons/elcl16/list-edit.gifbin0 -> 577 bytes
-rw-r--r--core/org.eclipse.cdt.ui/icons/elcl16/list-movedown.gifbin0 -> 371 bytes
-rw-r--r--core/org.eclipse.cdt.ui/icons/elcl16/list-moveup.gifbin0 -> 365 bytes
-rw-r--r--core/org.eclipse.cdt.ui/plugin.properties2
-rw-r--r--core/org.eclipse.cdt.ui/plugin.xml26
-rw-r--r--core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/CDTUIImages.java84
-rw-r--r--core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/CUIPlugin.java13
-rw-r--r--core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CDTCommonProjectWizard.java2
-rw-r--r--core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CDTMainWizardPage.java44
-rw-r--r--core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CWizardHandler.java3
-rw-r--r--core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/EntryDescriptor.java8
-rw-r--r--core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/ICWizardHandler.java2
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/internal/templateengine/wizard/TemplateCNewWizard.java54
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/FormBrowser.java80
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/IPagesAfterTemplateSelectionProvider.java40
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/ITemplatesListProvider.java28
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/IWizardDataPage.java24
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/Messages.java32
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/ProjectSelectionPage.java330
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/SimpleElementException.java62
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/Template.java210
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateClassWizard.java132
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateDrivenWizard.java184
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateEngineUI.java110
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateEngineUIUtil.java93
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateListSelectionPage.java271
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplatesChoiceWizard.java204
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/WizardNode.java138
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/event/PatternEvent.java83
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/event/PatternEventListener.java35
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/messages.properties40
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/Messages.java32
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/NewProjectCreationPage.java109
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/TemplateInputDialog.java328
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/TemplatePreferencePage.java589
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/UIPage.java158
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/UIPagesProvider.java170
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/UIWizardPage.java330
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/messages.properties27
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/GenericUIElementGroup.java174
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/IPatternMatchingTable.java26
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/IUIElementTreeBuilderHelper.java31
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/IUIElementTreeBuilderManager.java32
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/InputUIElement.java78
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/SimpleUIElementGroup.java64
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIAttributes.java27
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIElement.java131
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIElementTreeBuilderHelper.java183
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIElementTreeBuilderManager.java112
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIGroupTypeEnum.java42
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIBooleanWidget.java148
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIBrowseWidget.java114
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIComposite.java120
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UISelectWidget.java183
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UISpecialListWidget.java82
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIStringListWidget.java166
-rw-r--r--core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UITextWidget.java318
-rw-r--r--core/org.eclipse.cdt.ui/utils.ui/org/eclipse/cdt/utils/ui/controls/FileListControl.java832
-rw-r--r--core/org.eclipse.cdt.ui/utils.ui/org/eclipse/cdt/utils/ui/controls/IFileListChangeListener.java15
126 files changed, 12837 insertions, 21 deletions
diff --git a/core/org.eclipse.cdt.core.tests/.classpath b/core/org.eclipse.cdt.core.tests/.classpath
index f0d7b04646..5b2e2ed7c0 100644
--- a/core/org.eclipse.cdt.core.tests/.classpath
+++ b/core/org.eclipse.cdt.core.tests/.classpath
@@ -6,6 +6,7 @@
<classpathentry kind="src" path="parser"/>
<classpathentry kind="src" path="suite"/>
<classpathentry kind="src" path="regression"/>
+ <classpathentry kind="src" path="templateengine"/>
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/J2SE-1.4"/>
<classpathentry kind="con" path="org.eclipse.pde.core.requiredPlugins"/>
<classpathentry kind="output" path="bin"/>
diff --git a/core/org.eclipse.cdt.core.tests/build.properties b/core/org.eclipse.cdt.core.tests/build.properties
index f8584cb74a..a249c7cb71 100644
--- a/core/org.eclipse.cdt.core.tests/build.properties
+++ b/core/org.eclipse.cdt.core.tests/build.properties
@@ -1,5 +1,5 @@
###############################################################################
-# Copyright (c) 2005, 2006 IBM Corporation and others.
+# Copyright (c) 2005, 2007 IBM Corporation and others.
# All rights reserved. This program and the accompanying materials
# are made available under the terms of the Eclipse Public License v1.0
# which accompanies this distribution, and is available at
@@ -24,7 +24,8 @@ source.cdtcoretests.jar = failures/,\
parser/,\
suite/,\
misc/,\
- regression/
+ regression/,\
+ templateengine/
jre.compilation.profile=J2SE-1.4
javacSource=1.4
diff --git a/core/org.eclipse.cdt.core.tests/plugin.xml b/core/org.eclipse.cdt.core.tests/plugin.xml
index 1f18da7ae6..c26068255f 100644
--- a/core/org.eclipse.cdt.core.tests/plugin.xml
+++ b/core/org.eclipse.cdt.core.tests/plugin.xml
@@ -45,6 +45,7 @@
class="org.eclipse.cdt.internal.pdom.tests.GeneratePDOMApplicationTest$TestProjectProvider4">
</ExportProjectProvider>
</extension>
+
<extension
point="org.eclipse.cdt.core.CConfigurationDataProvider"
id="testCfgDataProvider">
@@ -61,4 +62,46 @@
</provider>
</extension>
+ <extension
+ point="org.eclipse.cdt.core.templates">
+ <template
+ filterPattern=".*AddFile"
+ isCategory="true"
+ location="testdata/AddFile.xml"
+ projectType="org.eclipse.cdt.core.tests.projectType">
+ </template>
+ <template
+ filterPattern=".*AddFiles"
+ location="testdata/AddFiles.xml"
+ projectType="org.eclipse.cdt.core.tests.projectType">
+ <toolChain id="org.eclipse.cdt.core.tests.toolChain1"/>
+ <toolChain id="org.eclipse.cdt.core.tests.toolChain2"/>
+ </template>
+ <template
+ filterPattern=".*AddLink"
+ location="testdata/AddLink.xml"
+ projectType="org.eclipse.cdt.core.tests.projectType">
+ </template>
+ <template
+ filterPattern=".*Append"
+ location="testdata/Append.xml"
+ projectType="org.eclipse.cdt.core.tests.projectType"/>
+ <template
+ filterPattern=".*AppendCreate"
+ location="testdata/AppendCreate.xml"
+ projectType="org.eclipse.cdt.core.tests.projectType"/>
+ <template
+ filterPattern=".*Copy"
+ location="testdata/Copy.xml"
+ projectType="org.eclipse.cdt.core.tests.projectType"/>
+ <template
+ filterPattern=".*CreateResourceIdentifier"
+ location="testdata/CreateResourceIdentifier.xml"
+ projectType="org.eclipse.cdt.core.tests.projectType"/>
+ <template
+ filterPattern=".*CreateSourceFolder"
+ location="testdata/CreateSourceFolder.xml"
+ projectType="org.eclipse.cdt.core.tests.projectType"/>
+ </extension>
+
</plugin>
diff --git a/core/org.eclipse.cdt.core.tests/suite/org/eclipse/cdt/core/suite/AutomatedIntegrationSuite.java b/core/org.eclipse.cdt.core.tests/suite/org/eclipse/cdt/core/suite/AutomatedIntegrationSuite.java
index aa1e66eb93..2318458a06 100644
--- a/core/org.eclipse.cdt.core.tests/suite/org/eclipse/cdt/core/suite/AutomatedIntegrationSuite.java
+++ b/core/org.eclipse.cdt.core.tests/suite/org/eclipse/cdt/core/suite/AutomatedIntegrationSuite.java
@@ -91,6 +91,8 @@ public class AutomatedIntegrationSuite extends TestSuite {
suite.addTestSuite(STLFailedTests.class);
suite.addTestSuite(FailedCompleteParseASTTest.class);
+// suite.addTest(AllTemplateEngineTests.suite());
+
return suite;
}
diff --git a/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/AllTemplateEngineTests.java b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/AllTemplateEngineTests.java
new file mode 100644
index 0000000000..df276976f5
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/AllTemplateEngineTests.java
@@ -0,0 +1,52 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.tests.templateengine;
+
+import junit.framework.Test;
+import junit.framework.TestSuite;
+
+/**
+ * This is a TestSuite, the TestCases created to test Template engine are
+ * added to testsuite.
+ * The test suite will execute all the Testcases added to the Suite.
+ *
+ * @since 4.0
+ */
+
+public class AllTemplateEngineTests extends TestSuite{
+
+ public static void main(String[] args) {
+ junit.swingui.TestRunner.run(AllTemplateEngineTests.class);
+ }
+
+ /**
+ * Since the TemplateEngine consists of UI(Wizard).
+ * A TestWizard is created to which the dynamically generated
+ * UIPages are added. The Wizard is launched from here.
+ * The TestCases created to test the TemplateEngine is initialized here.
+ * @return
+ *
+ * @since 4.0
+ */
+ public static Test suite() {
+ TestSuite suite = new TestSuite("Template engine tests"); //$NON-NLS-1$
+ //$JUnit-BEGIN$
+
+ suite.addTestSuite(TestTemplateEngine.class);
+ suite.addTestSuite(TestTemplateCore.class);
+ suite.addTestSuite(TestValueStore.class);
+ suite.addTestSuite(TestSharedDefaults.class);
+ suite.addTestSuite(TestProcesses.class);
+
+ //$JUnit-END$
+ return suite;
+ }
+}
diff --git a/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TemplateEngineTestsHelper.java b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TemplateEngineTestsHelper.java
new file mode 100644
index 0000000000..a087fc5a36
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TemplateEngineTestsHelper.java
@@ -0,0 +1,103 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.tests.templateengine;
+
+import java.io.IOException;
+import java.net.URL;
+import java.util.List;
+
+import junit.framework.Assert;
+
+import org.eclipse.cdt.core.templateengine.TemplateDescriptor;
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+import org.eclipse.cdt.core.testplugin.CTestPlugin;
+import org.eclipse.core.resources.IWorkspace;
+import org.eclipse.core.resources.IWorkspaceDescription;
+import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.FileLocator;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.Path;
+import org.eclipse.core.runtime.Platform;
+import org.osgi.framework.Bundle;
+import org.w3c.dom.Element;
+import org.w3c.dom.NamedNodeMap;
+
+/**
+ *
+ * All supporting functions which are not part of Testing class.
+ *
+ * @since 4.0
+*/
+
+public class TemplateEngineTestsHelper {
+
+ public static final String LOGGER_FILE_NAME="TemplateEngineTests"; //$NON-NLS-1$
+
+ /**
+ * get the url of a xml template, by passing the xml file name.
+ * @param templateName
+ * @return URL
+ */
+ public static URL getTemplateURL(String templateName){
+ Bundle bundle = Platform.getBundle(CTestPlugin.PLUGIN_ID);
+ URL url = FileLocator.find(bundle, new Path("testdata/"+templateName), null); //$NON-NLS-1$
+ if ( url != null )
+ {
+ try {
+ url = FileLocator.toFileURL(url);
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ }
+ return url;
+ }
+
+ public static int getChildCount(TemplateDescriptor templateDescriptor, String propertyGroupID){
+ List list = templateDescriptor.getPropertyGroupList();
+ for (int i = 0, l = list.size(); i < l; i++) {
+ Element element = (Element) list.get(i);
+ NamedNodeMap attributes = element.getAttributes();
+ for (int j = 0, l1 = attributes.getLength(); j < l1; j++) {
+ String value = attributes.item(j).getNodeValue();
+ if (value.equals(propertyGroupID)) {
+ return TemplateEngine.getChildrenOfElement(element).size();
+ }
+ }
+ }
+ return 0;
+ }
+
+ public static boolean failIfErrorStatus(IStatus[] statuses) {
+ for(int i=0; i<statuses.length; i++) {
+ IStatus status = statuses[i];
+ if (status.getCode() == IStatus.ERROR) {
+ Assert.fail(status.getMessage());
+ return true;
+ }
+ IStatus[] children = status.getChildren();
+ if (children != null) {
+ if (failIfErrorStatus(children)) {
+ return true;
+ }
+ }
+ }
+ return false;
+ }
+
+ public static void turnOffAutoBuild() throws CoreException {
+ IWorkspace workspace = ResourcesPlugin.getWorkspace();
+ IWorkspaceDescription workspaceDesc = workspace.getDescription();
+ workspaceDesc.setAutoBuilding(false);
+ workspace.setDescription(workspaceDesc);
+ }
+
+}
diff --git a/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestProcesses.java b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestProcesses.java
new file mode 100644
index 0000000000..66ff1d573f
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestProcesses.java
@@ -0,0 +1,261 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.tests.templateengine;
+
+import java.io.File;
+import java.util.Map;
+
+import junit.framework.TestCase;
+
+import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+import org.eclipse.core.resources.IFile;
+import org.eclipse.core.resources.IFolder;
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.resources.IProjectDescription;
+import org.eclipse.core.resources.IWorkspace;
+import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IPath;
+import org.eclipse.core.runtime.Platform;
+
+public class TestProcesses extends TestCase {
+
+ private static final String workspaceLocation = ResourcesPlugin.getWorkspace().getRoot().getRawLocation().toOSString();
+ private static final String PROJECT_NAME = "TemplateEngineTestsProject"; //$NON-NLS-1$
+ private static final String SOURCE_FOLDER = "Source"; //$NON-NLS-1$
+ private static final String FILE_NAME = "File"; //$NON-NLS-1$
+ private static final String LINK = "Link"; //$NON-NLS-1$
+ private static final String CPP_EXT = ".cpp"; //$NON-NLS-1$
+ private static final String H_EXT = ".h"; //$NON-NLS-1$
+
+ private static final String PROJECT_TYPE = "org.eclipse.cdt.core.tests.projectType"; //$NON-NLS-1$
+
+ protected void setUp() throws Exception {
+ TemplateEngineTestsHelper.turnOffAutoBuild();
+ IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject(PROJECT_NAME);
+ IPath projectLocation = project.getRawLocation();
+
+ if (project.exists()) {
+ project.delete(true, true, null);
+ }
+ IWorkspace workspace = ResourcesPlugin.getWorkspace();
+ IProjectDescription description = workspace.newProjectDescription(project.getName());
+
+ if ((projectLocation != null) && (!projectLocation.equals(Platform.getLocation()))) {
+ description.setLocation(projectLocation);
+ }
+
+ CCorePlugin.getDefault().createCDTProject(description, project, null);
+ if (!project.isOpen()) {
+ project.open(null);
+ }
+
+ }
+
+ public void testAddFile() {
+ TemplateCore template = TemplateEngine.getDefault().getFirstTemplate(PROJECT_TYPE, null, ".*AddFile"); //$NON-NLS-1$
+ Map valueStore = template.getValueStore();
+ valueStore.put("projectName", PROJECT_NAME); //$NON-NLS-1$
+ valueStore.put("projectType", PROJECT_TYPE); //$NON-NLS-1$
+ valueStore.put("location", ""); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("isCProject", "false"); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("baseName", FILE_NAME); //$NON-NLS-1$
+
+ if (TemplateEngineTestsHelper.failIfErrorStatus(template.executeTemplateProcesses(null, false))) {
+ return;
+ }
+
+ IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject(PROJECT_NAME);
+ assertTrue(project.exists());
+ IFile file = project.getFile(FILE_NAME + CPP_EXT);
+ assertTrue(file.exists());
+ file = project.getFile(FILE_NAME + H_EXT);
+ assertTrue(file.exists());
+ }
+
+ public void testAddFiles() {
+ TemplateCore template = TemplateEngine.getDefault().getFirstTemplate(PROJECT_TYPE, null, ".*AddFiles"); //$NON-NLS-1$
+ Map valueStore = template.getValueStore();
+ valueStore.put("projectName", PROJECT_NAME); //$NON-NLS-1$
+ valueStore.put("projectType", PROJECT_TYPE); //$NON-NLS-1$
+ valueStore.put("location", ""); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("isCProject", "false"); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("baseName", FILE_NAME); //$NON-NLS-1$
+
+ if (TemplateEngineTestsHelper.failIfErrorStatus(template.executeTemplateProcesses(null, false))) {
+ return;
+ }
+
+ IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject(PROJECT_NAME);
+ assertTrue(project.exists());
+ IFile file = project.getFile(FILE_NAME + CPP_EXT);
+ assertTrue(file.exists());
+ file = project.getFile(FILE_NAME + H_EXT);
+ assertTrue(file.exists());
+ }
+
+ public void testAddLink() {
+ TemplateCore template = TemplateEngine.getDefault().getFirstTemplate(PROJECT_TYPE, null, ".*AddLink"); //$NON-NLS-1$
+ Map valueStore = template.getValueStore();
+ valueStore.put("projectName", PROJECT_NAME); //$NON-NLS-1$
+ valueStore.put("projectType", PROJECT_TYPE); //$NON-NLS-1$
+ valueStore.put("location", ""); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("isCProject", "false"); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("baseName", FILE_NAME); //$NON-NLS-1$
+
+ if (TemplateEngineTestsHelper.failIfErrorStatus(template.executeTemplateProcesses(null, false))) {
+ return;
+ }
+
+ try {
+ IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject(PROJECT_NAME);
+ assertTrue(project.exists());
+ project.refreshLocal(1, null);
+ IFile file = project.getFile(FILE_NAME + CPP_EXT);
+ assertTrue(file.exists());
+ file = project.getFile(FILE_NAME + LINK + CPP_EXT);
+ assertTrue(file.exists());
+ } catch (CoreException e) {
+ fail(e.getMessage());
+ }
+ }
+
+ public void testAppend() {
+ TemplateCore template = TemplateEngine.getDefault().getFirstTemplate(PROJECT_TYPE, null, ".*Append"); //$NON-NLS-1$
+ Map valueStore = template.getValueStore();
+ valueStore.put("projectName", PROJECT_NAME); //$NON-NLS-1$
+ valueStore.put("projectType", PROJECT_TYPE); //$NON-NLS-1$
+ valueStore.put("location", ""); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("isCProject", "false"); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("baseName", FILE_NAME); //$NON-NLS-1$
+
+ valueStore.put("targetSourceName", workspaceLocation + File.separator + PROJECT_NAME + File.separator + FILE_NAME + CPP_EXT); //$NON-NLS-1$
+ valueStore.put("targetHeaderName", workspaceLocation + File.separator + PROJECT_NAME + File.separator + FILE_NAME + H_EXT); //$NON-NLS-1$
+
+ if (TemplateEngineTestsHelper.failIfErrorStatus(template.executeTemplateProcesses(null, false))) {
+ return;
+ }
+
+ try {
+ IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject(PROJECT_NAME);
+ assertTrue(project.exists());
+ project.refreshLocal(1, null);
+ IFile file = project.getFile(FILE_NAME + CPP_EXT);
+ assertTrue(file.exists());
+ file = project.getFile(FILE_NAME + H_EXT);
+ assertTrue(file.exists());
+ } catch (CoreException e) {
+ fail(e.getMessage());
+ }
+ }
+
+ public void testAppendCreate() {
+ TemplateCore template = TemplateEngine.getDefault().getFirstTemplate(PROJECT_TYPE, null, ".*AppendCreate"); //$NON-NLS-1$
+ Map valueStore = template.getValueStore();
+ valueStore.put("projectName", PROJECT_NAME); //$NON-NLS-1$
+ valueStore.put("projectType", PROJECT_TYPE); //$NON-NLS-1$
+ valueStore.put("location", ""); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("isCProject", "false"); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("baseName", FILE_NAME); //$NON-NLS-1$
+
+ valueStore.put("targetSourceName", FILE_NAME + CPP_EXT); //$NON-NLS-1$
+ valueStore.put("targetHeaderName", FILE_NAME + H_EXT); //$NON-NLS-1$
+
+ if (TemplateEngineTestsHelper.failIfErrorStatus(template.executeTemplateProcesses(null, false))) {
+ return;
+ }
+
+ IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject(PROJECT_NAME);
+ assertTrue(project.exists());
+ IFile file = project.getFile(FILE_NAME + CPP_EXT);
+ assertTrue(file.exists());
+ file = project.getFile(FILE_NAME + H_EXT);
+ assertTrue(file.exists());
+ }
+
+ public void testCopy() {
+ TemplateCore template = TemplateEngine.getDefault().getFirstTemplate(PROJECT_TYPE, null, ".*Copy"); //$NON-NLS-1$
+ Map valueStore = template.getValueStore();
+ valueStore.put("projectName", PROJECT_NAME); //$NON-NLS-1$
+ valueStore.put("projectType", PROJECT_TYPE); //$NON-NLS-1$
+ valueStore.put("location", ""); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("isCProject", "false"); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("baseName", FILE_NAME); //$NON-NLS-1$
+
+ valueStore.put("targetSourceName", workspaceLocation + File.separator + PROJECT_NAME + File.separator + FILE_NAME + CPP_EXT); //$NON-NLS-1$
+ valueStore.put("targetHeaderName", workspaceLocation + File.separator + PROJECT_NAME + File.separator + FILE_NAME + H_EXT); //$NON-NLS-1$
+
+ if (TemplateEngineTestsHelper.failIfErrorStatus(template.executeTemplateProcesses(null, false))) {
+ return;
+ }
+
+ try {
+ IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject(PROJECT_NAME);
+ assertTrue(project.exists());
+ project.refreshLocal(1, null);
+ IFile file = project.getFile(FILE_NAME + CPP_EXT);
+ assertTrue(file.exists());
+ file = project.getFile(FILE_NAME + H_EXT);
+ assertTrue(file.exists());
+ } catch (CoreException e) {
+ fail(e.getMessage());
+ }
+ }
+
+ public void testCreateResourceIdentifier() {
+ TemplateCore template = TemplateEngine.getDefault().getFirstTemplate(PROJECT_TYPE, null, ".*CreateResourceIdentifier"); //$NON-NLS-1$
+ Map valueStore = template.getValueStore();
+ valueStore.put("projectName", PROJECT_NAME); //$NON-NLS-1$
+ valueStore.put("projectType", PROJECT_TYPE); //$NON-NLS-1$
+ valueStore.put("location", ""); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("isCProject", "false"); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("valueName1", "baseName1"); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("appName1", "Hello"); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("valueName2", "baseName2"); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("appName2", "He"); //$NON-NLS-1$ //$NON-NLS-2$
+
+ if (TemplateEngineTestsHelper.failIfErrorStatus(template.executeTemplateProcesses(null, false))) {
+ return;
+ }
+
+ IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject(PROJECT_NAME);
+ assertTrue(project.exists());
+ IFile file = project.getFile("HELL" + CPP_EXT); //$NON-NLS-1$
+ assertTrue(file.exists());
+ file = project.getFile("HEXX" + CPP_EXT); //$NON-NLS-1$
+ assertTrue(file.exists());
+ }
+
+ public void testCreateSourceFolder() {
+ TemplateCore template = TemplateEngine.getDefault().getFirstTemplate(PROJECT_TYPE, null, ".*CreateSourceFolder"); //$NON-NLS-1$
+ Map valueStore = template.getValueStore();
+ valueStore.put("projectName", PROJECT_NAME); //$NON-NLS-1$
+ valueStore.put("projectType", PROJECT_TYPE); //$NON-NLS-1$
+ valueStore.put("location", ""); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("isCProject", "false"); //$NON-NLS-1$ //$NON-NLS-2$
+ valueStore.put("sourceDir1", SOURCE_FOLDER + 1); //$NON-NLS-1$
+ valueStore.put("sourceDir2", SOURCE_FOLDER + 2); //$NON-NLS-1$
+
+ if (TemplateEngineTestsHelper.failIfErrorStatus(template.executeTemplateProcesses(null, false))) {
+ return;
+ }
+
+ IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject(PROJECT_NAME);
+ assertTrue(project.exists());
+ IFolder folder = project.getFolder(SOURCE_FOLDER + 1);
+ assertTrue(folder.exists());
+ folder = project.getFolder(SOURCE_FOLDER + 2);
+ assertTrue(folder.exists());
+ }
+
+}
diff --git a/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestSharedDefaults.java b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestSharedDefaults.java
new file mode 100644
index 0000000000..5fa2d6a886
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestSharedDefaults.java
@@ -0,0 +1,124 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.tests.templateengine;
+
+
+import java.util.Iterator;
+import java.util.Map;
+import java.util.Set;
+
+import junit.framework.TestCase;
+
+import org.eclipse.cdt.core.templateengine.SharedDefaults;
+
+
+/**
+* Executes all the test cases of SharedDefaults backend functionality
+*/
+
+public class TestSharedDefaults extends TestCase {
+ private SharedDefaults sharedDefaults;
+
+ /*
+ * @see TestCase#setUp()
+ */
+ protected void setUp() throws Exception {
+ sharedDefaults = SharedDefaults.getInstance();
+ }
+
+ /*
+ * @see TestCase#tearDown()
+ */
+
+ protected void tearDown(){
+ sharedDefaults = null;
+ }
+
+ /**
+ * This test checks if data gets added to the back end
+ * New data gets persisted in SharedDefault XML file
+ */
+
+ public void testAddToBackEndStorage() {
+ Map actualSharedDefaults=sharedDefaults.getSharedDefaultsMap();
+
+ actualSharedDefaults.put("provider.name","eclipse"); //$NON-NLS-1$ //$NON-NLS-2$
+ actualSharedDefaults.put("copyright","Symbian Software Ltd."); //$NON-NLS-1$ //$NON-NLS-2$
+ actualSharedDefaults.put("author","Bala Torati"); //$NON-NLS-1$ //$NON-NLS-2$
+
+ Map expectedSharedDefaults=sharedDefaults.getSharedDefaultsMap();
+
+ assertEquals("Contents are different :", //$NON-NLS-1$
+ expectedSharedDefaults,
+ actualSharedDefaults);
+
+ }
+
+
+ /**
+ * This tests the updateToBackEndStorage of SharedDefaults
+ * to verify whether the key-value pair gets updated with new value
+ * New data gets persisted in SharedDefault XML file
+ */
+
+ public void testUpdateToBackEndStorage() {
+ Map actualSharedDefaults = sharedDefaults.getSharedDefaultsMap();
+ Set keySet = actualSharedDefaults.keySet();
+ Iterator iterator = keySet.iterator();
+
+ while (iterator.hasNext()) {
+ Object key = iterator.next();
+ Object value = actualSharedDefaults.get(key);
+ String keyName = (String)key;
+ String valueName = (String)value;
+ if (keyName.equals("org.eclipse.cdt.templateengine.project.HelloWorld.basename")){ //$NON-NLS-1$
+ valueName = "Astala Vista"; //$NON-NLS-1$
+ actualSharedDefaults.put(keyName, valueName);
+ sharedDefaults.updateToBackEndStorage("org.eclipse.cdt.templateengine.project.HelloWorld.basename", valueName); //$NON-NLS-1$
+ }
+ }
+
+ Map expectedSharedDefaults=sharedDefaults.getSharedDefaultsMap();
+
+ assertEquals("Contents are different :", //$NON-NLS-1$
+ expectedSharedDefaults,
+ actualSharedDefaults);
+ }
+
+ /**
+ * This tests the deleteBackEndStorage of SharedDefaults
+ * to verify whether the key-value pair gets deleted at the backend
+ */
+
+ public void testDeleteBackEndStorage() {
+ Map actualSharedDefaults=sharedDefaults.getSharedDefaultsMap();
+ Set keySet = actualSharedDefaults.keySet();
+ Iterator iterator = keySet.iterator();
+ String keyName = null;
+
+ while (iterator.hasNext()) {
+
+ Object key = iterator.next();
+ keyName = (String)key;
+ if (keyName.equals("org.eclipse.cdt.templateengine.project.HelloWorld.basename")) { //$NON-NLS-1$
+ actualSharedDefaults.remove(keyName);
+ break;
+ }
+ }
+
+ sharedDefaults.deleteBackEndStorage(new String[]{keyName});
+ Map expectedSharedDefaults=sharedDefaults.getSharedDefaultsMap();
+
+ assertEquals("Contents are different :", //$NON-NLS-1$
+ expectedSharedDefaults,
+ actualSharedDefaults);
+ }
+}
diff --git a/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestTemplateCore.java b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestTemplateCore.java
new file mode 100644
index 0000000000..fd3c19ed83
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestTemplateCore.java
@@ -0,0 +1,70 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.tests.templateengine;
+
+import junit.framework.TestCase;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+
+/**
+ * Test the functionality of Tempalte Class.
+ */
+public class TestTemplateCore extends TestCase {
+
+ public TemplateCore[] templates = null;
+
+ protected void setUp() throws Exception {
+ super.setUp();
+ templates = TemplateEngine.getDefault().getTemplates();
+ }
+
+ /*
+ * @see TestCase#tearDown()
+ */
+ protected void tearDown() throws Exception {
+ super.tearDown();
+ }
+
+ /**
+ * Constructor for Template.
+ * @param name
+ */
+ public TestTemplateCore(String name) {
+ super(name);
+ }
+
+ /**
+ * check that the Template contains a Non Null ValueStore
+ */
+ public void testValueStoreNotNull(){
+ for (int i=0; i < templates.length; i++) {
+ assertNotNull(templates[i].getValueStore());
+ }
+ }
+
+ /**
+ * Check the IDs to be persisited in SharedDefaults.
+ */
+ public void testPersistTrueIDs(){
+ for (int i=0; i < templates.length; i++) {
+ assertNotNull(templates[i].getPersistTrueIDs());
+ }
+ }
+
+ public void testGetAllMissingMacrosInProcesses(){
+ for (int i=0; i < templates.length; i++) {
+ assertNotNull(templates[i].getAllMissingMacrosInProcesses());
+ assertTrue(templates[i].getAllMissingMacrosInProcesses().size() > 0);
+ }
+ }
+
+}
diff --git a/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestTemplateEngine.java b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestTemplateEngine.java
new file mode 100644
index 0000000000..98cf4fd551
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestTemplateEngine.java
@@ -0,0 +1,64 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.tests.templateengine;
+
+import junit.framework.TestCase;
+
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+
+/**
+ * Test the functionality of TemplateEngine.
+ */
+public class TestTemplateEngine extends TestCase {
+
+
+ TemplateEngine templateEngine = null;
+
+ /*
+ * @see TestCase#setUp()
+ */
+ protected void setUp() throws Exception {
+ super.setUp();
+
+ templateEngine = TemplateEngine.getDefault();
+ }
+
+ /*
+ * @see TestCase#tearDown()
+ */
+ protected void tearDown() throws Exception {
+ super.tearDown();
+ }
+
+ /**
+ * Constructor for TestTemplateEngine.
+ * @param name
+ */
+ public TestTemplateEngine(String name) {
+ super(name);
+ }
+
+ /**
+ * check for non null SharedDefaults
+ *
+ */
+ public void testSharedDefaults(){
+ assertNotNull(templateEngine.getSharedDefaults());
+ }
+
+ /**
+ * check that the instace is created once(Singleton).
+ */
+ public void testSingleton(){
+ assertSame(templateEngine, TemplateEngine.getDefault());
+ }
+
+}
diff --git a/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestValueStore.java b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestValueStore.java
new file mode 100644
index 0000000000..744d91f29d
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/templateengine/org/eclipse/cdt/core/tests/templateengine/TestValueStore.java
@@ -0,0 +1,79 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.tests.templateengine;
+
+import java.util.Iterator;
+import java.util.Map;
+
+import junit.framework.TestCase;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateDescriptor;
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+
+
+/**
+ * Test the functionality of the ValueStore class.
+ */
+public class TestValueStore extends TestCase {
+
+
+ /**
+ * setUp is called before execution of test method.
+ */
+ protected void setUp() throws Exception {
+ super.setUp();
+ }
+
+ /**
+ * release resources held.
+ */
+ protected void tearDown() throws Exception {
+ super.tearDown();
+ }
+
+ public TestValueStore(String name) {
+ super(name);
+ }
+
+ /**
+ * Test ValueStore for Not Null condition.
+ *
+ */
+ public void testValueStoreNotNull(){
+ TemplateCore[] templates = TemplateEngine.getDefault().getTemplates();
+ for (int i=0; i <templates.length; i++) {
+ Map valueStore = templates[i].getValueStore();
+ assertNotNull(valueStore);
+ }
+ }
+
+ /**
+ * ValueStore is expected to consist all the IDs from
+ * FactoryDefaults. Test the same.
+ */
+ public void testCompareValueStoreWithTemplateDefaluts(){
+ TemplateCore[] templates = TemplateEngine.getDefault().getTemplates();
+ for (int i=0; i <templates.length; i++) {
+ Map valueStore = templates[i].getValueStore();
+ TemplateDescriptor templateDescriptor = templates[i].getTemplateDescriptor();
+ Map templateDefaults = templateDescriptor.getTemplateDefaults(templateDescriptor.getRootElement());
+
+ Iterator defaultsIterator = templateDefaults.keySet().iterator();
+ while(defaultsIterator.hasNext()){
+ String key = (String)defaultsIterator.next();
+ assertNotNull(valueStore.get(key));
+ }
+ }
+ }
+
+
+}
diff --git a/core/org.eclipse.cdt.core.tests/testdata/AddFile.xml b/core/org.eclipse.cdt.core.tests/testdata/AddFile.xml
new file mode 100644
index 0000000000..eab25ef12c
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/testdata/AddFile.xml
@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<template type="TestTemplate" version="1.0" supplier="Symbian" revision="1.0" author="Symbian"
+ id="??" label="Add File test" description="Testing Template Engines AddFile Process"
+ help="help.html">
+
+ <process type="org.eclipse.cdt.core.AddFile">
+ <simple name="projectName" value="$(projectName)"/>
+ <complex name="file">
+ <simple name="source" value="Basename.cpp"/>
+ <simple name="target" value="$(baseName).cpp"/>
+ <simple name="replaceable" value="true"/>
+ </complex>
+ </process>
+
+ <process type="org.eclipse.cdt.core.AddFile">
+ <simple name="projectName" value="$(projectName)"/>
+ <complex name="file">
+ <simple name="source" value="Basename.h"/>
+ <simple name="target" value="$(baseName).h"/>
+ <simple name="replaceable" value="true"/>
+ </complex>
+ </process>
+</template>
+
diff --git a/core/org.eclipse.cdt.core.tests/testdata/AddFiles.xml b/core/org.eclipse.cdt.core.tests/testdata/AddFiles.xml
new file mode 100644
index 0000000000..977c27b34a
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/testdata/AddFiles.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<template type="TestTemplate" version="1.0" supplier="Symbian" revision="1.0" author="Symbian"
+ id="??" label="Add Files test" description="Testing Template Engines AddFiles Process"
+ help="help.html">
+
+ <process type="org.eclipse.cdt.core.AddFiles">
+ <simple name="projectName" value="$(projectName)"/>
+ <complex-array name="files">
+ <element>
+ <simple name="source" value="Basename.h"/>
+ <simple name="target" value="$(baseName).h"/>
+ <simple name="replaceable" value="true"/>
+ </element>
+ <element>
+ <simple name="source" value="Basename.cpp"/>
+ <simple name="target" value="$(baseName).cpp"/>
+ <simple name="replaceable" value="true"/>
+ </element>
+ </complex-array>
+ </process>
+</template>
+
diff --git a/core/org.eclipse.cdt.core.tests/testdata/AddLink.xml b/core/org.eclipse.cdt.core.tests/testdata/AddLink.xml
new file mode 100644
index 0000000000..5612a96f99
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/testdata/AddLink.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<template type="TestTemplate" version="1.0" supplier="Symbian" revision="1.0" author="Symbian"
+ id="??" label="Add File test" description="Testing Template Engines AddFile Process"
+ help="help.html">
+
+ <process type="org.eclipse.cdt.core.AddFile">
+ <simple name="projectName" value="$(projectName)"/>
+ <complex name="file">
+ <simple name="source" value="Basename.cpp"/>
+ <simple name="target" value="$(baseName).cpp"/>
+ <simple name="replaceable" value="true"/>
+ </complex>
+ </process>
+
+ <process type="org.eclipse.cdt.core.AddLink">
+ <simple name="projectName" value="$(projectName)"/>
+ <simple name="filePath" value="$(baseName).cpp"/>
+ <simple name="targetPath" value="$(baseName)Link.cpp"/>
+ </process>
+
+</template>
+
diff --git a/core/org.eclipse.cdt.core.tests/testdata/Append.xml b/core/org.eclipse.cdt.core.tests/testdata/Append.xml
new file mode 100644
index 0000000000..4bdb482078
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/testdata/Append.xml
@@ -0,0 +1,36 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<template type="TestTemplate" version="1.0" supplier="Symbian" revision="1.0" author="Symbian"
+ id="??" label="Append test" description="Testing Template Engines Append Process"
+ help="help.html">
+
+ <process type="org.eclipse.cdt.core.Copy">
+ <complex-array name="files">
+ <element>
+ <simple name="source" value="Basename.cpp"/>
+ <simple name="target" value="$(targetSourceName)"/>
+ <simple name="replaceable" value="true"/>
+ </element>
+ <element>
+ <simple name="source" value="Basename.h"/>
+ <simple name="target" value="$(targetHeaderName)"/>
+ <simple name="replaceable" value="true"/>
+ </element>
+ </complex-array>
+ </process>
+
+ <process type="org.eclipse.cdt.core.Append">
+ <complex-array name="files">
+ <element>
+ <simple name="source" value="Basename.cpp"/>
+ <simple name="target" value="$(targetSourceName)"/>
+ <simple name="replaceable" value="true"/>
+ </element>
+ <element>
+ <simple name="source" value="Basename.h"/>
+ <simple name="target" value="$(targetHeaderName)"/>
+ <simple name="replaceable" value="true"/>
+ </element>
+ </complex-array>
+ </process>
+</template>
+
diff --git a/core/org.eclipse.cdt.core.tests/testdata/AppendCreate.xml b/core/org.eclipse.cdt.core.tests/testdata/AppendCreate.xml
new file mode 100644
index 0000000000..6f2bbb7e0c
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/testdata/AppendCreate.xml
@@ -0,0 +1,23 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<template type="TestTemplate" version="1.0" supplier="Symbian" revision="1.0" author="Symbian"
+ id="??" label="AppendCreate test" description="Testing Template Engines AppendCreate Process"
+ help="help.html">
+
+ <process type="org.eclipse.cdt.core.AppendCreate">
+ <simple name="projectName" value="$(projectName)"/>
+ <complex-array name="files">
+ <element>
+ <simple name="source" value="Basename.cpp"/>
+ <simple name="target" value="$(targetSourceName)"/>
+ <simple name="replaceable" value="true"/>
+ </element>
+ <element>
+ <simple name="source" value="Basename.h"/>
+ <simple name="target" value="$(targetHeaderName)"/>
+ <simple name="replaceable" value="true"/>
+ </element>
+ </complex-array>
+ </process>
+
+</template>
+
diff --git a/core/org.eclipse.cdt.core.tests/testdata/Basename.cpp b/core/org.eclipse.cdt.core.tests/testdata/Basename.cpp
new file mode 100644
index 0000000000..f3e3376e87
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/testdata/Basename.cpp
@@ -0,0 +1,37 @@
+/*
+============================================================================
+ Name : $(baseName).cpp
+ Author : $(author)
+ Version :
+ Copyright : $(copyright)
+ Description : Exe source file
+============================================================================
+*/
+
+// Include Files
+
+#include "$(baseName).h"
+
+// Defined Constants
+
+#define Constant "CONSTANT"
+
+
+// Global Variables
+
+static int globalValue;
+
+// Local Functions
+
+void printMessage(char* message) {
+ printf(message);
+}
+
+// Main Function
+
+int main(int nArgs, char **args) {
+ printMessage("Hello, world!\n");
+ printMessage("$(baseName)");
+}
+
+
diff --git a/core/org.eclipse.cdt.core.tests/testdata/Basename.h b/core/org.eclipse.cdt.core.tests/testdata/Basename.h
new file mode 100644
index 0000000000..3c5300af32
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/testdata/Basename.h
@@ -0,0 +1,27 @@
+/*
+============================================================================
+ Name : $(baseName).h
+ Author : $(author)
+ Version :
+ Copyright : $(copyright)
+ Description : Exe header file
+============================================================================
+*/
+
+#ifndef __$(baseName)_H__
+#define __$(baseName)_H__
+
+
+// Include Files
+
+#include <stdio.h>
+
+
+// Function Prototypes
+
+void printMessage(char*);
+
+
+#endif // __$(baseName)_H__
+
+
diff --git a/core/org.eclipse.cdt.core.tests/testdata/Copy.xml b/core/org.eclipse.cdt.core.tests/testdata/Copy.xml
new file mode 100644
index 0000000000..8fa2c96157
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/testdata/Copy.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<template type="TestTemplate" version="1.0" supplier="Symbian" revision="1.0" author="Symbian"
+ id="??" label="Copy test" description="Testing Template Engines Copy Process"
+ help="help.html">
+
+ <process type="org.eclipse.cdt.core.Copy">
+ <complex-array name="files">
+ <element>
+ <simple name="source" value="Basename.cpp"/>
+ <simple name="target" value="$(targetSourceName)"/>
+ <simple name="replaceable" value="true"/>
+ </element>
+ <element>
+ <simple name="source" value="Basename.h"/>
+ <simple name="target" value="$(targetHeaderName)"/>
+ <simple name="replaceable" value="true"/>
+ </element>
+ </complex-array>
+ </process>
+
+</template>
+
diff --git a/core/org.eclipse.cdt.core.tests/testdata/CreateResourceIdentifier.xml b/core/org.eclipse.cdt.core.tests/testdata/CreateResourceIdentifier.xml
new file mode 100644
index 0000000000..fd5a43800c
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/testdata/CreateResourceIdentifier.xml
@@ -0,0 +1,35 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<template type="TestTemplate" version="1.0" supplier="Symbian" revision="1.0" author="Symbian"
+ id="??" label="Create Resource Identifier test" description="CreateResourceIdentifier test"
+ help="help.html">
+
+ <process type="org.eclipse.cdt.core.CreateResourceIdentifier">
+ <simple name="valueName" value="$(valueName1)"/>
+ <simple name="appName" value="$(appName1)"/>
+ </process>
+
+ <process type="org.eclipse.cdt.core.CreateResourceIdentifier">
+ <simple name="valueName" value="$(valueName2)"/>
+ <simple name="appName" value="$(appName2)"/>
+ </process>
+
+ <process type="org.eclipse.cdt.core.AddFile">
+ <simple name="projectName" value="$(projectName)"/>
+ <complex name="file">
+ <simple name="source" value="Basename.cpp"/>
+ <simple name="target" value="$(baseName1).cpp"/>
+ <simple name="replaceable" value="true"/>
+ </complex>
+ </process>
+
+ <process type="org.eclipse.cdt.core.AddFile">
+ <simple name="projectName" value="$(projectName)"/>
+ <complex name="file">
+ <simple name="source" value="Basename.cpp"/>
+ <simple name="target" value="$(baseName2).cpp"/>
+ <simple name="replaceable" value="true"/>
+ </complex>
+ </process>
+
+</template>
+
diff --git a/core/org.eclipse.cdt.core.tests/testdata/CreateSourceFolder.xml b/core/org.eclipse.cdt.core.tests/testdata/CreateSourceFolder.xml
new file mode 100644
index 0000000000..6faa32118c
--- /dev/null
+++ b/core/org.eclipse.cdt.core.tests/testdata/CreateSourceFolder.xml
@@ -0,0 +1,16 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<template type="TestTemplate" version="1.0" supplier="Symbian" revision="1.0" author="Symbian"
+ id="??" label="Create Source Folder test" description="Create Source Folder test"
+ help="help.html">
+
+ <process type="org.eclipse.cdt.core.CreateSourceFolder">
+ <simple name="projectName" value="$(projectName)"/>
+ <simple name="path" value="$(sourceDir1)"/>
+ </process>
+
+ <process type="org.eclipse.cdt.core.CreateSourceFolder">
+ <simple name="projectName" value="$(projectName)"/>
+ <simple name="path" value="$(sourceDir2)"/>
+ </process>
+</template>
+
diff --git a/core/org.eclipse.cdt.core/.classpath b/core/org.eclipse.cdt.core/.classpath
index c23d8a7724..7628a2b870 100644
--- a/core/org.eclipse.cdt.core/.classpath
+++ b/core/org.eclipse.cdt.core/.classpath
@@ -5,6 +5,7 @@
<classpathentry kind="src" path="src"/>
<classpathentry kind="src" path="utils"/>
<classpathentry kind="src" path="parser"/>
+ <classpathentry kind="src" path="templateengine"/>
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/J2SE-1.4"/>
<classpathentry kind="con" path="org.eclipse.pde.core.requiredPlugins"/>
<classpathentry kind="output" path="bin"/>
diff --git a/core/org.eclipse.cdt.core/META-INF/MANIFEST.MF b/core/org.eclipse.cdt.core/META-INF/MANIFEST.MF
index 4b16b1ed43..81d9531f20 100644
--- a/core/org.eclipse.cdt.core/META-INF/MANIFEST.MF
+++ b/core/org.eclipse.cdt.core/META-INF/MANIFEST.MF
@@ -37,6 +37,9 @@ Export-Package: org.eclipse.cdt.core,
org.eclipse.cdt.core.settings.model.extension,
org.eclipse.cdt.core.settings.model.extension.impl,
org.eclipse.cdt.core.settings.model.util,
+ org.eclipse.cdt.core.templateengine,
+ org.eclipse.cdt.core.templateengine.process,
+ org.eclipse.cdt.core.templateengine.process.processes,
org.eclipse.cdt.internal.core;x-friends:="org.eclipse.cdt.ui",
org.eclipse.cdt.internal.core.browser.util;x-friends:="org.eclipse.cdt.ui",
org.eclipse.cdt.internal.core.cdtvariables,
diff --git a/core/org.eclipse.cdt.core/build.properties b/core/org.eclipse.cdt.core/build.properties
index 53ae47b468..2540a6ae90 100644
--- a/core/org.eclipse.cdt.core/build.properties
+++ b/core/org.eclipse.cdt.core/build.properties
@@ -1,5 +1,5 @@
###############################################################################
-# Copyright (c) 2003, 2006 IBM Corporation and others.
+# Copyright (c) 2003, 2007 IBM Corporation and others.
# All rights reserved. This program and the accompanying materials
# are made available under the terms of the Eclipse Public License v1.0
# which accompanies this distribution, and is available at
@@ -21,6 +21,7 @@ javadoc.packages = org.eclipse.cdt.core.*,\
org.eclipse.cdt.core.index.*,\
org.eclipse.cdt.core.model.*,\
org.eclipse.cdt.core.resources.*,\
+ org.eclipse.cdt.core.templateengine.*,\
org.eclipse.cdt.utils.*,\
org.eclipse.cdt.utils.elf.*,\
org.eclipse.cdt.utils.spawner.*
@@ -28,6 +29,7 @@ source.. = src/,\
model/,\
parser/,\
browser/,\
+ templateengine/,\
utils/
jre.compilation.profile=J2SE-1.4
@@ -36,6 +38,7 @@ javacTarget=1.4
source.library.jar = model/,\
browser/,\
src/,\
+ templateengine/,\
utils/,\
parser/
\ No newline at end of file
diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/settings/model/CProjectDescription.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/settings/model/CProjectDescription.java
index e798815229..3f31ce75cd 100644
--- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/settings/model/CProjectDescription.java
+++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/settings/model/CProjectDescription.java
@@ -116,7 +116,7 @@ public class CProjectDescription implements ICProjectDescription, ICDataProxyCon
if(cfg.getProjectDescription() != CProjectDescription.this)
throw new IllegalArgumentException();
- if(!fCfg.getId().equals(getId()))
+ if(!cfg.getId().equals(getId()))
return;
fIsModified = true;
diff --git a/core/org.eclipse.cdt.core/plugin.xml b/core/org.eclipse.cdt.core/plugin.xml
index 35e3869554..038e70b319 100644
--- a/core/org.eclipse.cdt.core/plugin.xml
+++ b/core/org.eclipse.cdt.core/plugin.xml
@@ -624,7 +624,89 @@
</extension>
<!-- =================================================================================== -->
-<!-- Dynamic Variables -->
+<!-- Template engine extension points -->
<!-- =================================================================================== -->
+ <extension-point id="templates" name="Templates Extension point"
+ schema="schema/templates.exsd"/>
+ <extension-point id="templateProcessTypes" name="Process Types Extension point" schema="schema/templateProcessTypes.exsd"/>
+
+ <extension
+ point="org.eclipse.cdt.core.templateProcessTypes">
+ <processType
+ name="Copy"
+ processRunner="org.eclipse.cdt.core.templateengine.process.processes.Copy">
+ <complexArray name="files">
+ <baseType>
+ <simple name="source"/>
+ <simple name="target"/>
+ <simple name="replaceable"/>
+ </baseType>
+ </complexArray>
+ </processType>
+ <processType
+ name="Append"
+ processRunner="org.eclipse.cdt.core.templateengine.process.processes.Append">
+ <complexArray name="files">
+ <baseType>
+ <simple name="source"/>
+ <simple name="target"/>
+ <simple name="replaceable"/>
+ </baseType>
+ </complexArray>
+ </processType>
+ <processType
+ name="AddFile"
+ processRunner="org.eclipse.cdt.core.templateengine.process.processes.AddFile">
+ <simple name="projectName"/>
+ <complex name="file">
+ <simple name="source"/>
+ <simple name="target"/>
+ <simple name="replaceable"/>
+ </complex>
+ </processType>
+ <processType
+ name="AddFiles"
+ processRunner="org.eclipse.cdt.core.templateengine.process.processes.AddFiles">
+ <simple name="projectName"/>
+ <complexArray name="files">
+ <baseType>
+ <simple name="source"/>
+ <simple name="target"/>
+ <simple name="replaceable"/>
+ </baseType>
+ </complexArray>
+ </processType>
+ <processType
+ name="CreateSourceFolder"
+ processRunner="org.eclipse.cdt.core.templateengine.process.processes.CreateSourceFolder">
+ <simple name="projectName"/>
+ <simple name="path"/>
+ </processType>
+ <processType
+ name="AddLink"
+ processRunner="org.eclipse.cdt.core.templateengine.process.processes.AddLink">
+ <simple name="projectName"/>
+ <simple name="filePath"/>
+ <simple name="targetPath"/>
+ </processType>
+ <processType
+ name="AppendCreate"
+ processRunner="org.eclipse.cdt.core.templateengine.process.processes.AppendCreate">
+ <simple name="projectName"/>
+ <complexArray name="files">
+ <baseType>
+ <simple name="source"/>
+ <simple name="target"/>
+ <simple name="replaceable"/>
+ </baseType>
+ </complexArray>
+ </processType>
+ <processType
+ name="CreateResourceIdentifier"
+ processRunner="org.eclipse.cdt.core.templateengine.process.processes.CreateResourceIdentifier">
+ <simple name="valueName"/>
+ <simple name="appName"/>
+ </processType>
+ </extension>
</plugin>
diff --git a/core/org.eclipse.cdt.core/schema/TemplateDescriptorSchema.xsd b/core/org.eclipse.cdt.core/schema/TemplateDescriptorSchema.xsd
new file mode 100644
index 0000000000..cca9d453c7
--- /dev/null
+++ b/core/org.eclipse.cdt.core/schema/TemplateDescriptorSchema.xsd
@@ -0,0 +1,220 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- edited with XMLSpy v2005 rel. 3 U (http://www.altova.com) by Bala Torati (Symbian) -->
+<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema">
+ <xsd:element name="template">
+ <xsd:complexType>
+ <xsd:sequence>
+ <xsd:element name="property-group" minOccurs="0" maxOccurs="unbounded">
+ <xsd:complexType>
+ <xsd:sequence>
+ <xsd:element name="property" minOccurs="0" maxOccurs="unbounded">
+ <xsd:complexType>
+ <xsd:sequence>
+ <xsd:element name="item" minOccurs="0" maxOccurs="unbounded">
+ <xsd:complexType>
+ <xsd:attribute name="label" type="xsd:string"/>
+ <xsd:attribute name="selected">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:boolean">
+ <xsd:pattern value="true|false"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ <xsd:attribute name="name" type="xsd:string"/>
+ </xsd:complexType>
+ </xsd:element>
+ </xsd:sequence>
+ <xsd:attribute name="id">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:string">
+ <xsd:pattern value="[a-zA-Z0-9.]*"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ <xsd:attribute name="label">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:string">
+ <xsd:pattern value="[a-zA-Z0-9 ]*"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ <xsd:attribute name="description" type="xsd:string"/>
+ <xsd:attribute name="type">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:string">
+ <xsd:enumeration value="input"/>
+ <xsd:enumeration value="multiline"/>
+ <xsd:enumeration value="select"/>
+ <xsd:enumeration value="boolean"/>
+ <xsd:enumeration value="stringlist"/>
+ <xsd:enumeration value="speciallist"/>
+ <xsd:enumeration value="browse"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ <xsd:attribute name="default" type="xsd:string"/>
+ <xsd:attribute name="pattern" type="xsd:string"/>
+ <xsd:attribute name="size">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:integer">
+ <xsd:pattern value="[0-9]*"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ <xsd:attribute name="checkproject" use="optional" default="false">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:boolean">
+ <xsd:pattern value="true|false"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ <xsd:attribute name="persist" default="false">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:boolean">
+ <xsd:pattern value="true|false"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ <xsd:attribute name="hidden" default="false">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:boolean">
+ <xsd:pattern value="true|false"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ <xsd:attribute name="mandatory" default="false">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:boolean">
+ <xsd:pattern value="true|false"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ </xsd:complexType>
+ </xsd:element>
+ </xsd:sequence>
+ <xsd:attribute name="id">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:string">
+ <xsd:pattern value="[a-zA-Z0-9_.]*"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ <xsd:attribute name="label" type="xsd:string"/>
+ <xsd:attribute name="description" type="xsd:string"/>
+ <xsd:attribute name="type">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:string">
+ <xsd:pattern value="[A-Z]*-[A-Z]*"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ <xsd:attribute name="branding-icon">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:string">
+ <xsd:pattern value="([/][a-zA-Z0-9]*[/])?[a-zA-Z0-9]*[\\.][a-zA-Z]*"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ <xsd:attribute name="help">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:string">
+ <xsd:pattern value="[a-zA-Z.]*"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ </xsd:complexType>
+ </xsd:element>
+ <!-- End of Property-Group Element-->
+ <xsd:element name="if" minOccurs="0" maxOccurs="unbounded">
+ <xsd:complexType>
+ <xsd:sequence>
+ <xsd:element ref="process" maxOccurs="unbounded"/>
+ </xsd:sequence>
+ <xsd:attribute name="condition" type="xsd:string" use="optional"/>
+ </xsd:complexType>
+ </xsd:element>
+ <xsd:element ref="process" minOccurs="0" maxOccurs="unbounded"/>
+ </xsd:sequence>
+ <xsd:attribute name="id" type="xsd:string"/>
+ <xsd:attribute name="type" type="xsd:string"/>
+ <xsd:attribute name="version" type="xsd:string"/>
+ <xsd:attribute name="supplier" type="xsd:string"/>
+ <xsd:attribute name="revision" type="xsd:string"/>
+ <xsd:attribute name="author" type="xsd:string"/>
+ <xsd:attribute name="copyright" type="xsd:string" use="optional"/>
+ <xsd:attribute name="label" type="xsd:string"/>
+ <xsd:attribute name="description" type="xsd:string"/>
+ <xsd:attribute name="help" type="xsd:string" use="optional"/>
+ <xsd:attribute name="preview-icon" use="optional">
+ <xsd:simpleType>
+ <xsd:restriction base="xsd:string">
+ <xsd:pattern value="([/][a-zA-Z0-9]*[/])?[a-zA-Z0-9]*[\\.][a-zA-Z]*"/>
+ </xsd:restriction>
+ </xsd:simpleType>
+ </xsd:attribute>
+ </xsd:complexType>
+ </xsd:element>
+ <xsd:element name="simple">
+ <xsd:complexType>
+ <xsd:attribute name="name" use="required"/>
+ <xsd:attribute name="value" use="optional"/>
+ </xsd:complexType>
+ </xsd:element>
+ <xsd:element name="simple-array">
+ <xsd:complexType>
+ <xsd:sequence>
+ <xsd:element name="element" minOccurs="0" maxOccurs="unbounded">
+ <xsd:complexType>
+ <xsd:attribute name="value" use="required"/>
+ </xsd:complexType>
+ </xsd:element>
+ </xsd:sequence>
+ <xsd:attribute name="name" use="required"/>
+ </xsd:complexType>
+ </xsd:element>
+ <xsd:element name="complex">
+ <xsd:complexType>
+ <xsd:sequence>
+ <xsd:choice maxOccurs="unbounded">
+ <xsd:element ref="simple"/>
+ <xsd:element ref="simple-array"/>
+ <xsd:element ref="complex"/>
+ <xsd:element ref="complex-array"/>
+ </xsd:choice>
+ </xsd:sequence>
+ <xsd:attribute name="name" use="required"/>
+ </xsd:complexType>
+ </xsd:element>
+ <xsd:element name="process">
+ <xsd:complexType>
+ <xsd:sequence>
+ <xsd:choice minOccurs="0" maxOccurs="unbounded">
+ <xsd:element ref="simple"/>
+ <xsd:element ref="simple-array"/>
+ <xsd:element ref="complex"/>
+ <xsd:element ref="complex-array"/>
+ </xsd:choice>
+ </xsd:sequence>
+ <xsd:attribute name="type" type="xsd:string" use="required"/>
+ </xsd:complexType>
+ </xsd:element>
+ <xsd:element name="complex-array">
+ <xsd:complexType>
+ <xsd:sequence>
+ <xsd:element name="element" minOccurs="0" maxOccurs="unbounded">
+ <xsd:complexType>
+ <xsd:sequence>
+ <xsd:choice maxOccurs="unbounded">
+ <xsd:element ref="simple"/>
+ <xsd:element ref="simple-array"/>
+ <xsd:element ref="complex"/>
+ <xsd:element ref="complex-array"/>
+ </xsd:choice>
+ </xsd:sequence>
+ </xsd:complexType>
+ </xsd:element>
+ </xsd:sequence>
+ <xsd:attribute name="name" use="required"/>
+ </xsd:complexType>
+ </xsd:element>
+</xsd:schema>
diff --git a/core/org.eclipse.cdt.core/schema/templateProcessTypes.exsd b/core/org.eclipse.cdt.core/schema/templateProcessTypes.exsd
new file mode 100644
index 0000000000..6dcd8a8b55
--- /dev/null
+++ b/core/org.eclipse.cdt.core/schema/templateProcessTypes.exsd
@@ -0,0 +1,307 @@
+<?xml version='1.0' encoding='UTF-8'?>
+<!-- Schema file written by PDE -->
+<schema targetNamespace="org.eclipse.cdt.core">
+<annotation>
+ <appInfo>
+ <meta.schema plugin="org.eclipse.cdt.core" id="templateProcessTypes" name="Processes Extension point"/>
+ </appInfo>
+ <documentation>
+ This extension point is to be extended to define new processes to be used in template descriptors by template writers.
+ </documentation>
+ </annotation>
+
+ <element name="extension">
+ <annotation>
+ <documentation>
+ One or more elements of processType should be added as children to this element.
+ </documentation>
+ </annotation>
+ <complexType>
+ <sequence>
+ <element ref="processType" minOccurs="1" maxOccurs="unbounded"/>
+ </sequence>
+ <attribute name="point" type="string" use="required">
+ <annotation>
+ <documentation>
+
+ </documentation>
+ </annotation>
+ </attribute>
+ <attribute name="id" type="string">
+ <annotation>
+ <documentation>
+
+ </documentation>
+ </annotation>
+ </attribute>
+ </complexType>
+ </element>
+
+ <element name="processType">
+ <annotation>
+ <documentation>
+ This element defines a single process. A process is analogous to a procedure with a set of parameters. In similar terms, one can say that this element defines the prototype of this process procedure. One needs to specify all the parameters expected by this process. In the eventual template xml, one needs to specify arguments for the process matching the types and order of these parameters.
+ </documentation>
+ </annotation>
+ <complexType>
+ <sequence>
+ <choice minOccurs="0" maxOccurs="unbounded">
+ <element ref="simple"/>
+ <element ref="simpleArray"/>
+ <element ref="complex"/>
+ <element ref="complexArray"/>
+ </choice>
+ </sequence>
+ <attribute name="name" type="string" use="required">
+ <annotation>
+ <documentation>
+ The value of this attribute is used (fully qualified with the namespace in which the extension is declared), to uniquely identify this processType. e.g. a value such as AddFiles will mean that the usage in the template.xml should be something like &amp;lt;process type=&quot;&amp;lt;plugin_id&amp;gt;.AddFiles&amp;gt;
+ </documentation>
+ </annotation>
+ </attribute>
+ <attribute name="processRunner" type="string" use="required">
+ <annotation>
+ <documentation>
+ A class that extends org.eclipse.cdt.templateengine.process.ProcessRunner abstract class and implements all its abstract methods. This is the code that actually processes.
+ </documentation>
+ <appInfo>
+ <meta.attribute kind="java" basedOn="org.eclipse.cdt.templateengine.process.ProcessRunner"/>
+ </appInfo>
+ </annotation>
+ </attribute>
+ </complexType>
+ </element>
+
+ <element name="simple">
+ <annotation>
+ <documentation>
+ A simple string parameter. In the eventual template xml, one needs to specify the same name as the value of the name attribute of a simple argument alongwith the corresponding value attribute.
+ </documentation>
+ </annotation>
+ <complexType>
+ <attribute name="name" type="string" use="required">
+ <annotation>
+ <documentation>
+ Name of the parameter. This should be used exactly as is in the name attribute of a simple argument in the template xml.
+ </documentation>
+ </annotation>
+ </attribute>
+ <attribute name="external" type="boolean">
+ <annotation>
+ <documentation>
+ This is an optional attribute. If specified with a true value, it implies that the template xml need not mention this argument for this param. The attribute does not have any meaning in the context of a child of a complex param or of a child of a complexArray param.
+
+Another thing to note is that arguments corresponding to external=true type params, if not mentioned in the template xml, should be supplied directly through the ValueStore with the key as the param&apos;s name.
+
+If not mentioned, this attribute&apos;s is treated as false.
+ </documentation>
+ </annotation>
+ </attribute>
+ <attribute name="nullable" type="boolean">
+ <annotation>
+ <documentation>
+ This is an optional attribute. If specified with a true value, it implies that the template xml need not mention the value attribute of the argument for this param. The attribute does not have any meaning in the context of a child of a complex param or of a child of a complexArray param.
+
+If not mentioned, this attribute&apos;s is treated as false.
+ </documentation>
+ </annotation>
+ </attribute>
+ </complexType>
+ </element>
+
+ <element name="simpleArray">
+ <annotation>
+ <documentation>
+ A simple string array parameter. In the eventual template xml, one needs to specify the same name as the value of the name attribute of a simple-array argument alongwith the corresponding element children, one child per array element with the corresponding value attribute.
+ </documentation>
+ </annotation>
+ <complexType>
+ <attribute name="name" type="string" use="required">
+ <annotation>
+ <documentation>
+ Name of the parameter. This should be used exactly as is in the name attribute of a simple-array argument in the template xml.
+ </documentation>
+ </annotation>
+ </attribute>
+ </complexType>
+ </element>
+
+ <element name="complex">
+ <annotation>
+ <documentation>
+ A complex parameter that groups together any number of simple, simpleArray, complex, complexArray parameters. This is equivalent of an object parameter. In the eventual template xml, one needs to specify the same name as the value of the name attribute of a simple argument alongwith the corresponding children, each child matching the type of the corresponding child of this element.
+ </documentation>
+ </annotation>
+ <complexType>
+ <sequence minOccurs="1" maxOccurs="unbounded">
+ <choice>
+ <element ref="simple"/>
+ <element ref="simpleArray"/>
+ <element ref="complex"/>
+ <element ref="complexArray"/>
+ </choice>
+ </sequence>
+ <attribute name="name" type="string" use="required">
+ <annotation>
+ <documentation>
+ Name of the parameter. This should be used exactly as is in the name attribute of a complex argument in the template xml.
+ </documentation>
+ </annotation>
+ </attribute>
+ </complexType>
+ </element>
+
+ <element name="complexArray">
+ <annotation>
+ <documentation>
+ A complex array parameter. Each element of this parameter is of the same base complex type as specified by the baseType child of this element. In the eventual template xml, one needs to specify the same name as the value of the name attribute of a complex-array argument alongwith the corresponding element children, one child per array element with the corresponding complex type arguments (based on baseType definition).
+ </documentation>
+ </annotation>
+ <complexType>
+ <sequence>
+ <element ref="baseType"/>
+ </sequence>
+ <attribute name="name" type="string" use="required">
+ <annotation>
+ <documentation>
+ Name of the parameter. This should be used exactly as is in the name attribute of a complex-array argument in the template xml.
+ </documentation>
+ </annotation>
+ </attribute>
+ </complexType>
+ </element>
+
+ <element name="baseType">
+ <annotation>
+ <documentation>
+ This is not a direct parameter of a process. This simply acts as a complex grouping of parameters to be used as the base type of complexArray parameters.
+ </documentation>
+ </annotation>
+ <complexType>
+ <sequence minOccurs="1" maxOccurs="unbounded">
+ <choice>
+ <element ref="simple"/>
+ <element ref="simpleArray"/>
+ <element ref="complex"/>
+ <element ref="complexArray"/>
+ </choice>
+ </sequence>
+ </complexType>
+ </element>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="since"/>
+ </appInfo>
+ <documentation>
+ This extension point was added in CDT 4.0
+ </documentation>
+ </annotation>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="examples"/>
+ </appInfo>
+ <documentation>
+ The following is an example of the extension point usage:
+&lt;p&gt;
+&lt;pre&gt;
+ &lt;extension
+ id=&quot;processExample&quot;
+ name=&quot;Process Example&quot;
+ point=&quot;org.eclipse.cdt.core.templateengine.processTypes&quot;&gt;
+
+ &lt;processType
+ name=&quot;NewManagedProject&quot;
+ processRunner=&quot;org.eclipse.cdt.core.templateengine.process.processes.NewManagedProject&quot;&gt;
+ &lt;simple name=&quot;name&quot;/&gt;
+ &lt;simple
+ external=&quot;true&quot;
+ name=&quot;projectType&quot;/&gt;
+ &lt;simple
+ external=&quot;true&quot;
+ name=&quot;location&quot;
+ nullable=&quot;true&quot;/&gt;
+ &lt;simple name=&quot;targetType&quot;/&gt;
+ &lt;/processType&gt;
+
+ &lt;processType
+ name=&quot;SetMBSBooleanOptionValue&quot;
+ processRunner=&quot;org.eclipse.cdt.core.templateengine.process.processes.SetMBSBooleanOptionValue&quot;&gt;
+ &lt;simple name=&quot;projectName&quot;/&gt;
+ &lt;complexArray name=&quot;resourcePaths&quot;&gt;
+ &lt;baseType&gt;
+ &lt;simple name=&quot;id&quot;/&gt;
+ &lt;simple name=&quot;value&quot;/&gt;
+ &lt;simple name=&quot;path&quot;/&gt;
+ &lt;/baseType&gt;
+ &lt;/complexArray&gt;
+ &lt;/processType&gt;
+
+ &lt;processType
+ name=&quot;AddFile&quot;
+ processRunner=&quot;org.eclipse.cdt.core.templateengine.process.processes.AddFile&quot;&gt;
+ &lt;simple name=&quot;projectName&quot;/&gt;
+ &lt;complex name=&quot;file&quot;&gt;
+ &lt;simple name=&quot;source&quot;/&gt;
+ &lt;simple name=&quot;target&quot;/&gt;
+ &lt;simple name=&quot;replaceable&quot;/&gt;
+ &lt;/complex&gt;
+ &lt;/processType&gt;
+
+ &lt;processType
+ name=&quot;AppendToMBSStringListOptionValues&quot;
+ processRunner=&quot;org.eclipse.cdt.core.templateengine.process.processes.AppendToMBSStringListOptionValues&quot;&gt;
+ &lt;simple name=&quot;projectName&quot;/&gt;
+ &lt;complexArray name=&quot;resourcePaths&quot;&gt;
+ &lt;baseType&gt;
+ &lt;simple name=&quot;id&quot;/&gt;
+ &lt;simpleArray name=&quot;values&quot;/&gt;
+ &lt;simple name=&quot;path&quot;/&gt;
+ &lt;/baseType&gt;
+ &lt;/complexArray&gt;
+ &lt;/processType&gt;
+
+ &lt;/extension&gt;
+&lt;/pre&gt;
+
+For more details on how to define your own templates, please check examples provided under
+&lt;samp&gt;org.eclipse.cdt.gnu.templates&lt;/samp&gt;
+ </documentation>
+ </annotation>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="apiInfo"/>
+ </appInfo>
+ <documentation>
+
+ </documentation>
+ </annotation>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="implementation"/>
+ </appInfo>
+ <documentation>
+ An implementation of this extension point is supplied in &lt;samp&gt;org.eclipse.cdt.core.templateengine&lt;/samp&gt;
+ </documentation>
+ </annotation>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="copyright"/>
+ </appInfo>
+ <documentation>
+ Copyright (c) 2007 Symbian Software Limited and others.
+All rights reserved. This program and the accompanying materials
+are made available under the terms of the Eclipse Public License v1.0
+which accompanies this distribution, and is available at
+http://www.eclipse.org/legal/epl-v10.html
+
+Contributors:
+Bala Torati (Symbian) - Initial API and implementation
+ </documentation>
+ </annotation>
+
+</schema>
diff --git a/core/org.eclipse.cdt.core/schema/templates.exsd b/core/org.eclipse.cdt.core/schema/templates.exsd
new file mode 100644
index 0000000000..eee1c10679
--- /dev/null
+++ b/core/org.eclipse.cdt.core/schema/templates.exsd
@@ -0,0 +1,196 @@
+<?xml version='1.0' encoding='UTF-8'?>
+<!-- Schema file written by PDE -->
+<schema targetNamespace="org.eclipse.cdt.core">
+<annotation>
+ <appInfo>
+ <meta.schema plugin="org.eclipse.cdt.core" id="templates" name="Template Extension point"/>
+ </appInfo>
+ <documentation>
+ This templates extension point facilitates the users to contribute their Template XMLs to the Template Engine plugin.
+ </documentation>
+ </annotation>
+
+ <element name="extension">
+ <annotation>
+ <documentation>
+ Extension point added to Template Engine plugin. Any plugin, which intends to contribute XML templates to Temaplate Engine has to extend this extension point, and add template element.
+ </documentation>
+ </annotation>
+ <complexType>
+ <sequence>
+ <element ref="template" minOccurs="1" maxOccurs="unbounded"/>
+ </sequence>
+ <attribute name="point" type="string" use="required">
+ <annotation>
+ <documentation>
+
+ </documentation>
+ </annotation>
+ </attribute>
+ <attribute name="id" type="string">
+ <annotation>
+ <documentation>
+ Id for the extension in the extender plugin.
+ </documentation>
+ </annotation>
+ </attribute>
+ <attribute name="name" type="string">
+ <annotation>
+ <documentation>
+ Optional name attribute.
+ </documentation>
+ <appInfo>
+ <meta.attribute translatable="true"/>
+ </appInfo>
+ </annotation>
+ </attribute>
+ </complexType>
+ </element>
+
+ <element name="template">
+ <annotation>
+ <documentation>
+ By adding the templates extension point the users can contribute there Template XMLs to the Template Engine plugin.
+ </documentation>
+ </annotation>
+ <complexType>
+ <sequence>
+ <element ref="toolChain" minOccurs="0" maxOccurs="unbounded"/>
+ </sequence>
+ <attribute name="location" type="string" use="required">
+ <annotation>
+ <documentation>
+ The location of the template(relative within the extender plugin).
+This is a must enter, attribute.
+ </documentation>
+ <appInfo>
+ <meta.attribute kind="resource"/>
+ </appInfo>
+ </annotation>
+ </attribute>
+ <attribute name="filterPattern" type="string">
+ <annotation>
+ <documentation>
+ Any filterPatter associated with this Template to be used by TemplateEngine.
+This is an optional attribute.
+ </documentation>
+ </annotation>
+ </attribute>
+ <attribute name="usageDescription" type="string">
+ <annotation>
+ <documentation>
+ A notation describing how this template is used. Usually used to filter the list of templates on offer depending on other wizard attributes.
+This is an optional attribute.
+ </documentation>
+ </annotation>
+ </attribute>
+ <attribute name="pagesAfterTemplateSelectionProvider" type="string">
+ <annotation>
+ <documentation>
+ A class that implements org.eclipse.cdt.templateengine.IPagesAfterTemplateSelectionProvider interface to create pages that will be appended to the pages returned from TemplatesChoiceWizard.getPagesAfterTemplateSelection().
+ </documentation>
+ <appInfo>
+ <meta.attribute kind="java" basedOn="org.eclipse.cdt.ui.templateengine.IPagesAfterTemplateSelectionProvider"/>
+ </appInfo>
+ </annotation>
+ </attribute>
+ <attribute name="isCategory" type="boolean">
+ <annotation>
+ <documentation>
+
+ </documentation>
+ </annotation>
+ </attribute>
+ <attribute name="projectType" type="string" use="required">
+ <annotation>
+ <documentation>
+
+ </documentation>
+ </annotation>
+ </attribute>
+ </complexType>
+ </element>
+
+ <element name="toolChain">
+ <complexType>
+ <attribute name="id" type="string" use="required">
+ <annotation>
+ <documentation>
+
+ </documentation>
+ </annotation>
+ </attribute>
+ </complexType>
+ </element>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="since"/>
+ </appInfo>
+ <documentation>
+ This extension point was added in CDT 4.0
+ </documentation>
+ </annotation>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="examples"/>
+ </appInfo>
+ <documentation>
+ The following is an example of the extension point usage:
+&lt;p&gt;
+&lt;pre&gt;
+ &lt;extension
+ id=&quot;simpleEXETemplateExample&quot;
+ name=&quot;Simple EXE Template Example&quot;
+ point=&quot;org.eclipse.cdt.templateengine.templates&quot;&gt;
+ &lt;template
+ filterPattern=&quot;.*&quot;
+ usageDescription=&quot;Simple EXE&quot;
+ location=&quot;templates/org/eclipse/cdt/templates/projecttemplates/Simple EXE/template.xml&quot;
+ projectType=&quot;org.eclipse.cdt.build.projectType.exe&quot;
+ wizardId=&quot;org.eclipse.cdt.templates.ui.NewManagedProjectWizard&quot;&gt;
+ &lt;/template&gt;
+ &lt;/extension&gt;
+&lt;/pre&gt;
+
+For more details on how to define your own templates, please check examples provided under
+&lt;samp&gt;org.eclipse.cdt.templates&lt;/samp&gt;
+ </documentation>
+ </annotation>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="apiInfo"/>
+ </appInfo>
+ <documentation>
+
+ </documentation>
+ </annotation>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="implementation"/>
+ </appInfo>
+ <documentation>
+ An implementation of this extension point is supplied in &lt;samp&gt;org.eclipse.cdt.templateengine&lt;/samp&gt;
+ </documentation>
+ </annotation>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="copyright"/>
+ </appInfo>
+ <documentation>
+ Copyright (c) 2007 Symbian Software Limited and others.
+All rights reserved. This program and the accompanying materials
+are made available under the terms of the Eclipse Public License v1.0
+which accompanies this distribution, and is available at
+http://www.eclipse.org/legal/epl-v10.html
+
+Contributors:
+Symbian - Initial API and implementation
+ </documentation>
+ </annotation>
+
+</schema>
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/SharedDefaults.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/SharedDefaults.java
new file mode 100644
index 0000000000..7872ba64e3
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/SharedDefaults.java
@@ -0,0 +1,325 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine;
+
+import java.io.File;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+
+import javax.xml.parsers.DocumentBuilderFactory;
+import javax.xml.parsers.ParserConfigurationException;
+import javax.xml.transform.Result;
+import javax.xml.transform.TransformerFactory;
+import javax.xml.transform.dom.DOMSource;
+import javax.xml.transform.stream.StreamResult;
+
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+import org.w3c.dom.Node;
+
+
+/**
+ * Processes the shared default values. Updates and Persists new key - value (default) pair
+ */
+
+public class SharedDefaults extends HashMap/*<String, String>*/ {
+ private static final long serialVersionUID = 0000000000L;
+
+ public Document document;
+ private File parsedXML;
+ private File backUpSharedXML;
+
+ /**
+ * HashMap's for persistence
+ */
+ private HashMap/*<String, String>*/ sharedDefaultsMap;
+ private HashMap/*<String, String>*/ persistDataMap;
+ private HashMap/*<String, String>*/ tableDataMap;
+
+ /**
+ * Two XML files here supports to provide consistent writing of data into
+ * them even during some destructive events which can happen during data
+ * persistence
+ */
+ private static final String SHARED_DEFAULTS_DOT_XML = "shareddefaults.xml"; //$NON-NLS-1$
+ private static final String SHARED_DEFAULTS_DOT_BACKUP_DOT_XML = "shareddefaults.backup.xml"; //$NON-NLS-1$
+
+ /**
+ * Static reference string for getting (GET) and storing (SET)
+ * shareddefaults.xml
+ */
+
+ public static final String SET = "SET"; //$NON-NLS-1$
+ public static final String GET = "GET"; //$NON-NLS-1$
+
+ /**
+ * Specifies the folder name present in the plugin
+ */
+ public static final String ResourceFolder = "resources"; //$NON-NLS-1$
+
+ /**
+ * Static reference of Singleton SharedDefault Instance
+ */
+ private static SharedDefaults SHAREDDEFAULTS = new SharedDefaults();
+
+ /**
+ * Returns static SharedDefaults Instance
+ *
+ * @return
+ */
+
+ public static SharedDefaults getInstance() {
+ return SHAREDDEFAULTS;
+ }
+
+ /**
+ * Default Constructor for creating and instantiating objects. On the
+ * startup of Template Engine, if it checks for the existence of
+ * TempSharedDefaultsXML file, then it is determined that the last Template
+ * Engine process under went some System destructive events and takes up
+ * reconstructive process to regain the consistent data by persisting all
+ * information first into temporary file and then into actual file.
+ */
+
+ public SharedDefaults() {
+ sharedDefaultsMap = new HashMap/*<String, String>*/();
+ persistDataMap = new HashMap/*<String, String>*/();
+ tableDataMap = new HashMap/*<String, String>*/();
+
+ // The conditional controls here is provided to have consistent
+ // data storage in the file during System crash or
+ // Power shutdown during data persistence into the file.
+
+ parsedXML = TemplateEngineHelper.getSharedDefaultLocation(SHARED_DEFAULTS_DOT_XML);
+ backUpSharedXML = TemplateEngineHelper.getSharedDefaultLocation(SHARED_DEFAULTS_DOT_BACKUP_DOT_XML);
+
+ if (backUpSharedXML.exists())
+ swapXML();
+
+ initSharedDefaults();
+ }
+
+ /**
+ * This method instantiates the SharedDefaults process by gathering XML
+ * document and creating shared key-value pair in HashMap. Also creates a
+ * new XML file if none exists and adds the default XML format.
+ */
+
+ private void initSharedDefaults() {
+ String key = null;
+ String value = null;
+
+ try {
+ long length = parsedXML.length();
+ // Adds defaultXML format if the file length is zero
+ if (length == 0) {
+ parsedXML = createDefaultXMLFormat(parsedXML);
+ }
+ document = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(parsedXML.toURL().openStream());
+ } catch (Exception exp) {
+ TemplateEngineUtil.log(exp);
+ }
+
+ List/*<Element>*/ sharedElementList = TemplateEngine.getChildrenOfElement(document.getDocumentElement());
+ int listSize = sharedElementList.size();
+ for (int i = 0; i < listSize; i++) {
+ Element xmlElement = (Element) sharedElementList.get(i);
+ key = xmlElement.getAttribute(TemplateEngineHelper.ID);
+ value = xmlElement.getAttribute(TemplateEngineHelper.VALUE);
+ if (key != null && !key.trim().equals("")) {
+ sharedDefaultsMap.put(key, value);
+ }
+ }
+ }
+
+ /**
+ * This method updates the HashMap with new key-value pair into the XML file
+ *
+ * @param sharedMap
+ */
+
+ public void updateShareDefaultsMap(Map/*<String, String>*/ sharedMap) {
+ sharedDefaultsMap.putAll(sharedMap);
+ persistSharedValueMap();
+ }
+
+ /**
+ * This method persists the latest data (HashMap) in the XML file New data
+ * obtained from the PreferencePage GUI.
+ */
+
+ public void persistSharedValueMap() {
+ generateSharedXML(backUpSharedXML);
+ generateSharedXML(parsedXML);
+ swapXML();
+ }
+
+ /**
+ * This method returns the latest key value pair (HashMap)
+ *
+ * @return HashMap
+ */
+
+ public Map/*<String, String>*/ getSharedDefaultsMap() {
+ return sharedDefaultsMap;
+ }
+
+ /**
+ * Adds data to the backend XML (persistence) Data obtained from the
+ * PreferencePage GUI.
+ */
+
+ public void addToBackEndStorage(String name, String value) {
+ if (sharedDefaultsMap != null) {
+ tableDataMap.putAll(sharedDefaultsMap);
+ }
+
+ tableDataMap.put(name, value);
+ updateShareDefaultsMap(tableDataMap);
+ }
+
+ /**
+ * Updates backend with changed value for a specific key(name)
+ *
+ * @param updateName
+ * @param updateValue
+ */
+
+ public void updateToBackEndStorage(String updateName, String updateValue) {
+ try {
+ document = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(parsedXML.toURL().openStream());
+ } catch (Exception exp) {
+ TemplateEngineUtil.log(exp);
+ }
+
+ persistDataMap.putAll(sharedDefaultsMap);
+ List/*<Element>*/ sharedElementList = TemplateEngine.getChildrenOfElement(document.getDocumentElement());
+ int elementListSize = sharedElementList.size();
+
+ for (int i = 0; i < elementListSize; i++) {
+ Element xmlElement = (Element) sharedElementList.get(i);
+ String name = xmlElement.getAttribute(TemplateEngineHelper.ID);
+
+ if (updateName.equals(name)) {
+ persistDataMap.put(updateName, updateValue);
+ }
+ }
+
+ updateShareDefaultsMap(persistDataMap);
+ }
+
+ /**
+ * Deletes the key-value pair from the backend with Key as identifier.
+ *
+ * @param deleteName
+ */
+ public void deleteBackEndStorage(String[] deleteName) {
+
+ try {
+ document = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(parsedXML.toURL().openStream());
+ } catch (Exception exp) {
+ TemplateEngineUtil.log(exp);
+ }
+
+ List/*<Element>*/ sharedElementList = TemplateEngine.getChildrenOfElement(document.getDocumentElement());
+ int elementListSize = sharedElementList.size();
+ for (int i = 0; i < elementListSize; i++) {
+
+ Element xmlElement = (Element) sharedElementList.get(i);
+ String name = xmlElement.getAttribute(TemplateEngineHelper.ID);
+
+ for (int k = 0; k < deleteName.length; k++) {
+ if (deleteName[k].equals(name)) {
+ xmlElement.removeAttribute(name);
+ sharedDefaultsMap.remove(name);
+ }
+ }
+ }
+
+ updateShareDefaultsMap(sharedDefaultsMap);
+ }
+
+ /**
+ * This method returns the default XMLFormat for the newly created XML file
+ *
+ * @param parsedXML
+ * @return
+ */
+
+ private File createDefaultXMLFormat(File xmlFile) {
+ Document d;
+ try {
+ d = DocumentBuilderFactory.newInstance().newDocumentBuilder().newDocument();
+ } catch (ParserConfigurationException e) {
+ TemplateEngineUtil.log(e);
+ return xmlFile;
+ }
+ Node rootElement = d.appendChild(d.createElement("SharedRoot")); //$NON-NLS-1$
+ Element element = (Element) rootElement.appendChild(d.createElement("SharedProperty")); //$NON-NLS-1$
+ element.setAttribute(TemplateEngineHelper.ID, ""); //$NON-NLS-1$
+ element.setAttribute(TemplateEngineHelper.VALUE, ""); //$NON-NLS-1$
+
+ DOMSource domSource = new DOMSource(d);
+ TransformerFactory transFactory = TransformerFactory.newInstance();
+ Result fileResult = new StreamResult(xmlFile);
+ try {
+ transFactory.newTransformer().transform(domSource, fileResult);
+ } catch (Throwable t) {
+ TemplateEngineUtil.log(t);
+ }
+ return xmlFile;
+ }
+
+ /**
+ * This method generates XML file for backupshareddefaults and
+ * shareddefaults to support consistent persistency
+ */
+
+ private void generateSharedXML(File xmlFile) {
+ Document d;
+ try {
+ d = DocumentBuilderFactory.newInstance().newDocumentBuilder().newDocument();
+ } catch (ParserConfigurationException e) {
+ TemplateEngineUtil.log(e);
+ return;
+ }
+ Node rootElement = d.appendChild(d.createElement("SharedRoot")); //$NON-NLS-1$
+
+ for(Iterator i = sharedDefaultsMap.keySet().iterator(); i.hasNext(); ) {
+ String key = (String) i.next();
+ Element element = (Element) rootElement.appendChild(d.createElement("SharedProperty")); //$NON-NLS-1$
+ element.setAttribute(TemplateEngineHelper.ID, key);
+ element.setAttribute(TemplateEngineHelper.VALUE, (String) sharedDefaultsMap.get(key));
+ }
+
+ DOMSource domSource = new DOMSource(d);
+ TransformerFactory transFactory = TransformerFactory.newInstance();
+ Result fileResult = new StreamResult(xmlFile);
+ try {
+ transFactory.newTransformer().transform(domSource, fileResult);
+ } catch (Throwable t) {
+ TemplateEngineUtil.log(t);
+ }
+ }
+
+ /**
+ * This method swaps the backup file name to XML file containing latest or
+ * persisted data
+ */
+
+ private void swapXML() {
+ if (parsedXML.exists())
+ parsedXML.delete();
+ backUpSharedXML.renameTo(parsedXML);
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateCore.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateCore.java
new file mode 100644
index 0000000000..5e28f4ddc9
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateCore.java
@@ -0,0 +1,257 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine;
+
+import java.io.IOException;
+import java.util.Comparator;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.TreeSet;
+
+import javax.xml.parsers.ParserConfigurationException;
+
+import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.core.templateengine.process.TemplateProcessHandler;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.Status;
+import org.xml.sax.SAXException;
+
+
+/**
+ * TemplateCore class is responsible providing the non-UI part of template and
+ * initiating process part of Template Engine. This is created per TemplateDescriptor basis.
+ * Once The Template is created it creates a TemplateDescriptor for the XML file name given.
+ * Template class extends this class with additional UI elements that are part of the template.
+ *
+ * @since 4.0
+ */
+public class TemplateCore {
+
+ private static final String DESCRIPTION = "description"; //$NON-NLS-1$
+ private static final String LABEL = "label"; //$NON-NLS-1$
+ private static final String ID = "id"; //$NON-NLS-1$
+
+ private static Map/*<TemplateInfo, Template>*/ templateCache = new HashMap/*<TemplateInfo, Template>*/();
+
+ public static final Comparator/*<Template>*/ TEMPLATE_ID_CASE_INSENSITIVE_COMPARATOR = new Comparator/*<Template>*/() {
+ public int compare(Object/*Template*/ t1, Object/*Template*/ t2) {
+ return String.CASE_INSENSITIVE_ORDER.compare(((TemplateCore)t1).getTemplateId(), ((TemplateCore)t2).getTemplateId());
+ }
+ };
+
+ private TemplateDescriptor templateDescriptor;
+ private Map/*<String, String>*/ valueStore;
+ private TemplateInfo templateInfo;
+ private Set/*<String>*/ allMacrosInProcesses;
+ private TemplateProcessHandler processHandler;
+ private String description;
+ private String label;
+ private String templateId;
+ private boolean fireDirtyEvents;
+
+ /**
+ * Constructor
+ *
+ * @param templateInfo
+ * @throws IOException
+ * @throws SAXException
+ * @throws ParserConfigurationException
+ */
+
+ protected TemplateCore(TemplateInfo templateInfo) throws IOException, SAXException, ParserConfigurationException {
+ this.templateInfo = templateInfo;
+ templateDescriptor = new TemplateDescriptor(TemplateEngineHelper.getTemplateResourceURL(templateInfo.getPluginId(), templateInfo.getTemplatePath()));
+ valueStore = new ValueStore/*<String, String>*/(this);
+ valueStore.putAll(templateDescriptor.getTemplateDefaults(templateDescriptor.getRootElement()));
+ valueStore.putAll(TemplateEngine.getDefault().getSharedDefaults());
+ valueStore.put("projectType", templateInfo.getProjectType()); //$NON-NLS-1$
+
+ processHandler = new TemplateProcessHandler(this);
+ allMacrosInProcesses = processHandler.getAllMacros();
+
+ fireDirtyEvents = true;
+ }
+
+ /**
+ * Returns All Missing Macros In Processes.
+ * @return Set
+ */
+ public Set/*<String>*/ getAllMissingMacrosInProcesses() {
+ Set/*<String>*/ set = new TreeSet/*<String>*/(allMacrosInProcesses);
+ if (set != null) {
+ for (Iterator iter = set.iterator(); iter.hasNext();) {
+ if (valueStore.get(iter.next()) != null) {
+ iter.remove();
+ }
+ }
+ }
+ return set;
+ }
+
+ /**
+ * return the ValueStore maintained by this Template.
+ * @return ValueStore.
+ */
+ public Map/*<String, String>*/ getValueStore() {
+ return valueStore;
+ }
+
+ /**
+ * This is the List of IDs from TemplateDescriptor with "attribute" Persist
+ * as "true"
+ *
+ * @return Vector of IDs.
+ */
+ public List/*<String>*/ getPersistTrueIDs() {
+ return templateDescriptor.getPersistTrueIDs();
+ }
+
+ /**
+ * return the TemplateInfo instance corresponding to this Template.
+ * @return TemplateInfo.
+ */
+ public TemplateInfo getTemplateInfo() {
+ return templateInfo;
+ }
+
+ /**
+ * TemplateDescriptor for which, this Template is created.
+ */
+ public TemplateDescriptor getTemplateDescriptor() {
+ return templateDescriptor;
+ }
+
+ /**
+ * @return String, which contains the description
+ */
+ public String getDescription() {
+ if (description == null) {
+ description = templateDescriptor.getRootElement().getAttribute(DESCRIPTION).trim();
+ }
+ return description;
+ }
+
+ /**
+ * @return String, which contains the id of the template
+ */
+ public String getTemplateId() {
+ if (templateId == null) {
+ templateId = templateDescriptor.getRootElement().getAttribute(ID).trim();
+ }
+ return templateId;
+ }
+
+ /**
+ * @return String, which contains the Label
+ */
+ public String getLabel() {
+ if (label == null) {
+ label = templateDescriptor.getRootElement().getAttribute(LABEL).trim();
+ }
+ return label;
+ }
+
+ /**
+ * TemplateDescriptor for which, this Template is created.
+ */
+ public TemplateProcessHandler getProcessHandler() {
+ return processHandler;
+ }
+
+ public String toString()
+ {
+ return getLabel();
+ }
+ /**
+ * sets Dirty
+ *
+ */
+ public void setDirty() {
+ if (fireDirtyEvents) {
+ synchronized (templateCache) {
+ templateCache.remove(templateInfo);
+ }
+ }
+ }
+
+ /**
+ * initializeProcessBlockList() will create the ProcessBlockList,
+ * processPorcessBlockList() will invoke each process execution by assigning
+ * resources to each process (Ref. ProcessResourceManager).
+ * @param monitor
+ */
+ public IStatus[] executeTemplateProcesses(IProgressMonitor monitor, final boolean showError) {
+ setDirty();
+ TemplateEngine.getDefault().updateSharedDefaults(this);
+ final IStatus[][] result = new IStatus[1][];
+ try {
+ result[0] = getProcessHandler().processAll(monitor);
+ } catch (ProcessFailureException e) {
+ TemplateEngineUtil.log(e);
+ result[0] = new IStatus[] {new Status(IStatus.ERROR, CCorePlugin.PLUGIN_ID, IStatus.ERROR, e.getMessage(), e)};
+ }
+ return result[0];
+ }
+
+ /**
+ * Gets the Template
+ *
+ * @param templateInfo
+ * @throws IOException
+ * @throws ProcessFailureException
+ * @throws SAXException
+ * @throws ParserConfigurationException
+ *
+ * @since 4.0
+ */
+ public static TemplateCore getTemplate(TemplateInfo templateInfo) throws IOException, ProcessFailureException, SAXException, ParserConfigurationException {
+ synchronized (templateCache) {
+ TemplateCore template = (TemplateCore) templateCache.get(templateInfo);
+ if (template == null) {
+ template = new TemplateCore(templateInfo);
+ templateCache.put(templateInfo, template);
+ }
+ return template;
+ }
+ }
+
+ private static class ValueStore/*<K, V>*/ extends HashMap/*<K, V>*/ {
+ private static final long serialVersionUID = -4523467333437879406L;
+ private TemplateCore template;
+
+ ValueStore(TemplateCore template) {
+ this.template = template;
+ }
+
+ public Object/*V*/ put(Object/*K*/ key, Object/*V*/ value) {
+ Object/*V*/ v = super.put(key, value);
+ template.setDirty();
+ return v;
+ }
+
+ public void putAll(Map/*<? extends K, ? extends V>*/ map) {
+ super.putAll(map);
+ template.setDirty();
+ }
+
+ public Object/*V*/ remove(Object key) {
+ Object/*V*/ v = super.remove(key);
+ template.setDirty();
+ return v;
+ }
+
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateDescriptor.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateDescriptor.java
new file mode 100644
index 0000000000..bacec4f40a
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateDescriptor.java
@@ -0,0 +1,198 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine;
+
+import java.io.IOException;
+import java.net.URL;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import javax.xml.parsers.DocumentBuilderFactory;
+import javax.xml.parsers.ParserConfigurationException;
+
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+import org.xml.sax.SAXException;
+
+
+/**
+ * This class contains methods to get first process block element, next process block
+ * element and checks for next process block element.
+ */
+public class TemplateDescriptor {
+ public static final String PROPERTY_GROUP = "property-group"; //$NON-NLS-1$
+ public static final String PROCESS = "process"; //$NON-NLS-1$
+ public static final String IF = "if"; //$NON-NLS-1$
+ public static final String ID = "id"; //$NON-NLS-1$
+ public static final String DEFAULT = "default"; //$NON-NLS-1$
+ public static final String PERSIST = "persist"; //$NON-NLS-1$
+ public static final String BOOL_TRUE = "true"; //$NON-NLS-1$
+
+ private Document document;
+ private Element rootElement;
+ private List/*<String>*/ persistVector;
+
+ /**
+ * Constructor which construct the Document based the URL
+ * @param descriptorURL
+ * @throws SAXException
+ * @throws IOException
+ * @throws ParserConfigurationException
+ */
+ public TemplateDescriptor(URL descriptorURL) throws SAXException, IOException, ParserConfigurationException {
+ document = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(descriptorURL.openStream());
+ rootElement = document.getDocumentElement();
+ persistVector = new ArrayList/*<String>*/();
+ }
+
+ /**
+ * This method is to get the default key value pair (HashMap) form template
+ * descriptor root element.
+ *
+ * @return default values with keys
+ */
+ public Map/*<String, String>*/ getTemplateDefaults(Element rootElement) {
+ Map/*<String, String>*/ templateDefaults = new HashMap/*<String, String>*/();
+ Element propertyGroupElement;
+ List/*<Element>*/ children = TemplateEngine.getChildrenOfElement(rootElement);
+ for (int i = 0, l = children.size(); i < l; i++) {
+ propertyGroupElement = (Element) children.get(i);
+ if (isNestedElement(propertyGroupElement)) {
+ templateDefaults = getTemplateDefaults(propertyGroupElement);
+ }
+ propertyElements(templateDefaults, propertyGroupElement);
+ }
+ return templateDefaults;
+ }
+
+ /**
+ * Checks whether element nested or not
+ * @param element
+ * @return
+ */
+ private boolean isNestedElement(Element element){
+ boolean result=false;
+ if (element!=null){
+ List/*<Element>*/ children = TemplateEngine.getChildrenOfElement(element);
+ String elementName = element.getNodeName();
+ Element testElement;
+ String testElementName = null;
+ if (children.size() > 0){
+ testElement = (Element) children.get(0);
+ testElementName=testElement.getNodeName();
+ }
+ if(elementName.equals(testElementName))
+ result=true;
+ else result=false;
+ }
+ return result;
+ }
+
+ /**
+ * This method is to get the list of property-group elements from template
+ * descriptor root element
+ *
+ * @param aRootElement
+ * root element of type JDOM Element
+ * @return list of property-group elements
+ */
+ public List getPropertyGroupList() {
+ List resultList = null;
+ List/*<Element>*/ list = new ArrayList/*<Element>*/();
+ resultList = list;
+ if (rootElement != null) {
+ List/*<Element>*/ tempList = TemplateEngine.getChildrenOfElement(rootElement);
+ for (int i = 0, l = tempList.size(); i < l; i++) {
+ Element nextPropertyGroup = (Element) tempList.get(i);
+ String nextPGName = nextPropertyGroup.getNodeName();
+ if (nextPGName.equalsIgnoreCase(PROPERTY_GROUP)) {
+ list.add(nextPropertyGroup);
+ }
+ }
+ }
+ return resultList;
+ }
+
+ /**
+ * This mehtod is to get the complex property-group from template descriptor
+ * root element. complex means a property-group contains other
+ * property-group(s)
+ *
+ * @param rootElement
+ * root element of type JDOM Element
+ * @return porperty-group root element of type JDOM Element
+ */
+ public Element getRootPropertyGroup(Element rootElement) {
+ if (rootElement != null) {
+ String rootElementName = rootElement.getNodeName();
+ if (rootElementName.equalsIgnoreCase(PROPERTY_GROUP) && isNestedElement(rootElement)) {
+ return rootElement;
+ }
+ return rootElement;
+ } else {
+ String nextPGElementName = null;
+ List/*<Element>*/ propertyGroupList = TemplateEngine.getChildrenOfElement(rootElement);
+ for (int i = 0, l = propertyGroupList.size(); i < l; i++) {
+ Element nextPGElement = (Element) propertyGroupList.get(i);
+ if (isNestedElement(nextPGElement))
+ nextPGElementName = nextPGElement.getNodeName();
+ if (nextPGElementName.equalsIgnoreCase(PROPERTY_GROUP) && isNestedElement(nextPGElement)) {
+ return nextPGElement;
+ }
+ }
+ }
+ return null;
+ }
+
+ /**
+ * This private method is used in getTemplateDefaults() to get defaults from
+ * property elements
+ *
+ * @param defaults
+ * HashMap to store deraults
+ * @param propertyGroupElement
+ * traverse the complex property-group element
+ */
+ private void propertyElements(Map/*<String, String>*/ defaults, Element propertyGroupElement) {
+ List/*<Element>*/ children = TemplateEngine.getChildrenOfElement(propertyGroupElement);
+ for (int i = 0, l = children.size(); i < l; i++) {
+ Element propertyElement = (Element) children.get(i);
+ String key = propertyElement.getAttribute(ID);
+ String value = propertyElement.getAttribute(DEFAULT);
+ if (key != null && !key.equals("")) {
+ defaults.put(key, value);
+ }
+
+ String persist = propertyElement.getAttribute(PERSIST);
+ if ((persist != null) && (persist.trim().equalsIgnoreCase(BOOL_TRUE))) {
+ persistVector.add(key);
+ }
+ }
+ }
+
+ /**
+ * added to return root of this document.
+ */
+ public Element getRootElement() {
+ return rootElement;
+ }
+
+ /**
+ * return the list of IDs whose Persist attribute is true.
+ *
+ * @return Vector.
+ */
+ public List/*<String>*/ getPersistTrueIDs() {
+ return persistVector;
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngine.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngine.java
new file mode 100644
index 0000000000..dea101fe82
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngine.java
@@ -0,0 +1,344 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine;
+
+import java.io.IOException;
+import java.net.URL;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.core.runtime.FileLocator;
+import org.eclipse.core.runtime.IConfigurationElement;
+import org.eclipse.core.runtime.IExtension;
+import org.eclipse.core.runtime.Platform;
+import org.w3c.dom.Element;
+import org.w3c.dom.Node;
+import org.w3c.dom.NodeList;
+
+
+/**
+ * TemplateEngine is implemented as a Singleton. TemplateEngine is responsible for
+ * creating SharedDefaults and initializing the SharedDefaults. Template instances
+ * are obtained from TemplateEngine.
+ *
+ * @since 4.0
+ */
+public class TemplateEngine {
+
+ public static String TEMPLATES_EXTENSION_ID = CCorePlugin.PLUGIN_ID + ".templates"; //$NON-NLS-1$
+
+ /**
+ * static reference to the Singleton TemplateEngine instance.
+ */
+ private static TemplateEngine TEMPLATE_ENGINE = new TemplateEngine();
+
+ /**
+ * This is a Map <WizardID, TemplateInfo>.
+ */
+ private Map/*<String, List<TemplateInfo>>*/ templateInfoMap;
+
+ /**
+ * TemplateEngine constructor, create and initialize SharedDefaults.
+ */
+ private TemplateEngine() {
+ templateInfoMap = new HashMap/*<String, List<TemplateInfo>>*/();
+ initializeTemplateInfoMap();
+ }
+
+ /**
+ * get All the templates, no filtering is done.
+ *
+ * @return
+ */
+ public TemplateCore[] getTemplates() {
+ TemplateInfo[] templateInfoArray = getTemplateInfos();
+ List/*<Template>*/ templatesList = new ArrayList/*<Template>*/();
+ for (int i=0; i<templateInfoArray.length; i++) {
+ TemplateInfo info = templateInfoArray[i];
+ try {
+ templatesList.add(TemplateCore.getTemplate(info));
+ } catch (Exception e) {
+ }
+ }
+ return (TemplateCore[]) templatesList.toArray(new TemplateCore[templatesList.size()]);
+ }
+
+ /**
+ * This method will be called by Contianer UIs (Wizard, PropertyPage,
+ * PreferencePage). Create a Template instance, update the ValueStore, with
+ * SharedDefaults. This method calls the getTemplate(URL), after getting URL
+ * for the given String TemplateDescriptor.
+ *
+ * @param StringTemplateDescriptor,
+ * TemplateDescriptor name.
+ * @throws IOException
+ */
+ public TemplateCore getFirstTemplate(String projectType) {
+ return getFirstTemplate(projectType, null, null);
+ }
+
+ public TemplateCore getFirstTemplate(String projectType, String toolChain, String usageFilter) {
+ try {
+ return TemplateCore.getTemplate(getTemplateInfos(projectType, toolChain, usageFilter)[0]);
+ } catch (Exception e) {
+ // ignore
+ }
+ return null;
+ }
+
+ /**
+ * This method will be called by Contianer UIs (Wizard, PropertyPage,
+ * PreferencePage). Create a Template instance, update the ValueStore, with
+ * SharedDefaults. This method calls the getTemplate(URL), after getting URL
+ * for the given String TemplateDescriptor.
+ */
+ public TemplateCore[] getTemplates(String projectType, String toolChain, String usageFilter) {
+ TemplateInfo[] templateInfoArray = getTemplateInfos(projectType, toolChain, usageFilter);
+ List/*<Template>*/ templatesList = new ArrayList/*<Template>*/();
+ for (int i=0; i<templateInfoArray.length; i++) {
+ TemplateInfo info = templateInfoArray[i];
+ try {
+ templatesList.add(TemplateCore.getTemplate(info));
+ } catch (Exception e) {
+ }
+ }
+ return (TemplateCore[]) templatesList.toArray(new TemplateCore[templatesList.size()]);
+ }
+
+ public TemplateCore[] getTemplates(String projectType, String toolChain) {
+ return getTemplates(projectType, toolChain, null);
+ }
+
+ public TemplateCore[] getTemplates(String projectType) {
+ return getTemplates(projectType, null);
+ }
+
+ public TemplateCore getTemplateById(String templateId) {
+ TemplateCore[] templates = getTemplates();
+
+ for(int i=0; i<templates.length; i++) {
+ TemplateCore template = templates[i];
+ if (template.getTemplateId().equalsIgnoreCase(templateId)) {
+ return template;
+ }
+ }
+ return null;
+ }
+
+ /**
+ * return the SharedDefaults.
+ *
+ * @return
+ */
+ public Map/*<String, String>*/ getSharedDefaults() {
+ return SharedDefaults.getInstance().getSharedDefaultsMap();
+ }
+
+ /**
+ * update The SharedDefaults Map. This method will be called by Container
+ * UIs. After collecting data from UIPages, the IDs with Persist attribute
+ * as true, has to be persisted in SharedDefaults XML. For the same this
+ * method is called by passing the ValueStore(updated with user entered
+ * values). Get the PersistTrueIDs from TemplateDescriptor. Persist the
+ * values of IDs in ValueStore, which are also present in PersistTrueIDs
+ * vector.
+ * @param template
+ * @param aSharedValue
+ */
+ public void updateSharedDefaults(TemplateCore template) {
+ Map/*<String, String>*/ tobePersisted = new HashMap/*<String, String>*/();
+ Map/*<String, String>*/ valueStore = template.getValueStore();
+
+ for (Iterator i = template.getPersistTrueIDs().iterator(); i.hasNext();) {
+ String key = (String) i.next();
+ tobePersisted.put(key, valueStore.get(key));
+ }
+ SharedDefaults.getInstance().updateShareDefaultsMap(tobePersisted);
+ }
+
+ /**
+ * create the singleton instance, check for null condition of
+ * TEMPLATE_ENGINE. If TEMPLATE_ENGINE is null create the TemplateEngine
+ * instance assign it to TEMPLATE_ENGINE. There is no need to have
+ * synchronized here(while creating TemplateEngine).
+ *
+ * @return TEMPLATE_ENGINE, instance of TemplateEngine.
+ *
+ * @since 4.0
+ */
+ public static TemplateEngine getDefault() {
+ return TEMPLATE_ENGINE;
+ }
+
+ /**
+ * From the extension point take the class implementing the required
+ * functionality. Update the local HashMap of page-id and URL. This is for
+ * extension point "templates"
+ */
+ private void initializeTemplateInfoMap() {
+ String location = null;
+ String pluginId = null;
+ String projectType = null;
+ String filterPattern = null;
+ String usage = null;
+ boolean isCategory = false;
+ String extraPagesProvider = null;
+
+ IExtension[] extensions = Platform.getExtensionRegistry().getExtensionPoint(TEMPLATES_EXTENSION_ID).getExtensions();
+ for(int i=0; i<extensions.length; i++) {
+ IExtension extension = extensions[i];
+ IConfigurationElement[] configElements = extension.getConfigurationElements();
+ pluginId = extension.getNamespaceIdentifier(); // Plugin-id of the extending plugin.
+ for(int j=0; j<configElements.length; j++) {
+ IConfigurationElement config = configElements[j];
+ location = config.getAttribute(TemplateEngineHelper.LOCATION);
+ projectType = config.getAttribute(TemplateEngineHelper.PROJECT_TYPE);
+ filterPattern = config.getAttribute(TemplateEngineHelper.FILTER_PATTERN);
+ usage = config.getAttribute(TemplateEngineHelper.USAGE_DESCRIPTION);
+ isCategory = Boolean.valueOf(config.getAttribute(TemplateEngineHelper.IS_CATEGORY)).booleanValue();
+ extraPagesProvider = config.getAttribute(TemplateEngineHelper.EXTRA_PAGES_PROVIDER);
+
+ IConfigurationElement[] toolChainConfigs = config.getChildren(TemplateEngineHelper.TOOL_CHAIN);
+ Set toolChainIdSet = new HashSet();
+ for (int k=0; k < toolChainConfigs.length; k++) {
+ toolChainIdSet.add(toolChainConfigs[k].getAttribute(TemplateEngineHelper.ID));
+ }
+
+ TemplateInfo templateInfo = new TemplateInfo(projectType, filterPattern, location,
+ pluginId, toolChainIdSet,
+ usage, extraPagesProvider, isCategory);
+ if (!templateInfoMap.containsKey(projectType)) {
+ templateInfoMap.put(projectType, new ArrayList/*<TemplateInfo>*/());
+ }
+ ((List/*<TemplateInfo>*/)templateInfoMap.get(projectType)).add(templateInfo);
+ }
+ }
+ }
+
+ /**
+ * Gets an array of template info objects matching the criteria passed as params.
+ */
+ public TemplateInfo[] getTemplateInfos(String projectType, String toolChain, String usageFilter) {
+ List/*<TemplateInfo>*/ templateInfoList = (List/*<TemplateInfo*/) templateInfoMap.get(projectType.trim());
+ List/*<TemplateInfo>*/ matchedTemplateInfoList = new ArrayList/*<TemplateInfo>*/();
+
+ if (templateInfoList != null) {
+ for (Iterator i = templateInfoList.iterator(); i.hasNext(); ) {
+ TemplateInfo templateInfo = (TemplateInfo) i.next();
+ String filterPattern = templateInfo.getFilterPattern();
+ String[] toolChains = templateInfo.getToolChainIds();
+
+ if (toolChain != null) {
+ for (int j=0; j < toolChains.length; j++) {
+ if (toolChains[j].equals(toolChain)) {
+ if (usageFilter != null && filterPattern.matches(usageFilter)) {
+ matchedTemplateInfoList.add(templateInfo);
+ } else if (usageFilter == null) {
+ matchedTemplateInfoList.add(templateInfo);
+ }
+ continue;
+ }
+ }
+ } else {
+ if (usageFilter != null && filterPattern.matches(usageFilter)) {
+ matchedTemplateInfoList.add(templateInfo);
+ } else if (usageFilter == null) {
+ matchedTemplateInfoList.add(templateInfo);
+ }
+ }
+ }
+ }
+ return (TemplateInfo[]) matchedTemplateInfoList.toArray(new TemplateInfo[matchedTemplateInfoList.size()]);
+ }
+
+ public TemplateInfo[] getTemplateInfos(String projectType, String toolChain) {
+ return getTemplateInfos(projectType, toolChain, null);
+ }
+
+ public TemplateInfo[] getTemplateInfos(String projectType) {
+ return getTemplateInfos(projectType, null, null);
+ }
+
+ public TemplateInfo[] getTemplateInfos() {
+ List/*<TemplateInfo>*/ infoList = new ArrayList/*<TemplateInfo>*/();
+ for (Iterator i = templateInfoMap.values().iterator(); i.hasNext();) {
+ infoList.addAll((List/*<TemplateInfo>*/)i.next());
+ }
+
+ return (TemplateInfo[]) infoList.toArray(new TemplateInfo[infoList.size()]);
+ }
+
+
+ /**
+ * Getter for templateInfoMap
+ *
+ * @return
+ */
+ public Map/*<String, List<TemplateInfo>>*/ getTemplateInfoMap() {
+ return templateInfoMap;
+ }
+
+ /**
+ * Returns the Template Schema URL
+ *
+ * @return URL of the Template Schema.
+ * @throws IOException
+ */
+ public URL getTemplateSchemaURL() throws IOException {
+ return FileLocator.toFileURL(Platform.getBundle(CCorePlugin.PLUGIN_ID).getEntry("schema/TemplateDescriptorSchema.xsd")); //$NON-NLS-1$
+ }
+
+ /**
+ * Returns the Children of the Element.
+ * @param element
+ * @return List of the child elelments
+ *
+ * @since 4.0
+ */
+ public static List/*<Element>*/ getChildrenOfElement(Element element) {
+ List/*<Element>*/ list = new ArrayList/*<Element>*/();
+ NodeList children = element.getChildNodes();
+ for (int i = 0, l = children.getLength(); i < l; i++) {
+ Node child = children.item(i);
+ if (child.getNodeType() == Node.ELEMENT_NODE) {
+ list.add((Element) child);
+ }
+ }
+ return list;
+ }
+
+ /**
+ * Returns the child elements by Tag
+ *
+ * @param element
+ * @param tag
+ * @return List of child elements
+ *
+ * @since 4.0
+ */
+ public static List/*<Element>*/ getChildrenOfElementByTag(Element element, String tag) {
+ List/*<Element>*/ list = new ArrayList/*<Element>*/();
+ NodeList children = element.getChildNodes();
+ for (int i = 0, l = children.getLength(); i < l; i++) {
+ Node child = children.item(i);
+ if (child.getNodeType() == Node.ELEMENT_NODE && child.getNodeName().equals(tag)) {
+ list.add((Element) child);
+ }
+ }
+ return list;
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngineHelper.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngineHelper.java
new file mode 100644
index 0000000000..1866acdba6
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngineHelper.java
@@ -0,0 +1,221 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine;
+
+import java.io.File;
+import java.io.IOException;
+import java.net.URL;
+
+import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.core.resources.IWorkspace;
+import org.eclipse.core.resources.IWorkspaceRoot;
+import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.FileLocator;
+import org.eclipse.core.runtime.IPath;
+import org.eclipse.core.runtime.Path;
+import org.eclipse.core.runtime.Platform;
+import org.eclipse.core.runtime.Plugin;
+
+/**
+ * Acts as an Helper class for Template Engine
+ *
+ * @since 4.0
+ */
+public class TemplateEngineHelper {
+
+ public static final String OPEN_MARKER = "$("; //$NON-NLS-1$
+ public static final String CLOSE_MARKER = ")"; //$NON-NLS-1$
+ public static final String LOGGER_FILE_NAME = "Process"; //$NON-NLS-1$
+ // This is used while getting the Plugin Path.
+ public static final String PROJRESOURCE = "plugin.xml"; //$NON-NLS-1$
+ public static final String BOOLTRUE = "true"; //$NON-NLS-1$
+ public static final String ID = "id"; //NON-NLS-1$
+ public static final String VALUE = "value"; //NON-NLS-1$
+ public static final String SDLOG_FILE_NAME = "sharedDefaults"; //$NON-NLS-1$
+ public static final String LOCATION = "location"; //NON-NLS-1$
+ public static final String WIZARD_ID = "wizardId"; //NON-NLS-1$
+ public static final String FILTER_PATTERN = "filterPattern"; //NON-NLS-1$
+ public static final String USAGE_DESCRIPTION = "usageDescription"; //NON-NLS-1$
+ public static final String PROJECT_TYPE = "projectType"; //NON-NLS-1$
+ public static final String TOOL_CHAIN = "toolChain"; //NON-NLS-1$
+ public static final String EXTRA_PAGES_PROVIDER = "pagesAfterTemplateSelectionProvider"; //NON-NLS-1$
+ public static final String IS_CATEGORY = "isCategory"; //NON-NLS-1$
+ public static final String CONFIGURATIONS = "Configurations"; //NON-NLS-1$
+
+ /**
+ * Gets the backup shareddefaults XML file. Presence of the file indicates
+ * that the template engine or the application underwent some crash or
+ * destruction.
+ *
+ * @param sharedLocation
+ * @return sharedXMLFile
+ *
+ * @since 4.0
+ */
+
+ public static File getSharedDefaultLocation(String sharedLocation) {
+
+ File sharedXMLFile = findLocation(sharedLocation);
+ return sharedXMLFile;
+ }
+
+ /**
+ * Finds the location of the shareddefaults backup and original xml file.
+ *
+ * @param fileLocation
+ * @return file
+ *
+ * @since 4.0
+ */
+
+ private static File findLocation(String fileLocation) {
+
+ Plugin plugin = CCorePlugin.getDefault();
+ IPath stateLoc = plugin.getStateLocation();
+ fileLocation = stateLoc.toString() + File.separator + fileLocation;
+ File file = new File(fileLocation);
+
+ return file;
+ }
+
+ /**
+ * Stores the shareddefaults xml file in
+ * "${workspace}/.metadata/.plugins/${plugin.name}/shareddefaults.xml" path.
+ *
+ * @param sharedLocation
+ * @return sharedXMLFile
+ *
+ * @since 4.0
+ */
+
+ public static File storeSharedDefaultLocation(String sharedLocation) {
+
+ File sharedXMLFile = findLocation(sharedLocation);
+
+ try {
+ createNewFile(sharedXMLFile.getPath());
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ return sharedXMLFile;
+ }
+
+ /**
+ * This creates a new File, in the Absolute Path given as argument. The File
+ * name will be part of the path argument.
+ *
+ * @param aFileName,
+ * absoulute File path(including File name) to be created.
+ *
+ * @since 4.0
+ */
+ public static void createNewFile(String fileName) throws IOException {
+
+ (new File(fileName)).createNewFile();
+ }
+
+ /**
+ * This method returns the workspace path present in the workspace
+ *
+ * @return String Example : file:/C:/eclipse/workspace/
+ *
+ * @since 4.0
+ */
+ public static IPath getWorkspacePath() {
+
+ IWorkspace workspace = ResourcesPlugin.getWorkspace();
+ IWorkspaceRoot root = workspace.getRoot();
+ IPath workSpacePath = new Path(root.getLocation().toString() + File.separator);
+ return workSpacePath;
+
+ }
+
+ /**
+ * given a String of the form $(ID), return ID.
+ *
+ * @param markerString
+ * @return
+ *
+ * @since 4.0
+ */
+ public static String getFirstMarkerID(String markerString) {
+ String key = null;
+ if (markerString.indexOf(OPEN_MARKER) != -1) {
+ key = markerString.substring(markerString.indexOf(OPEN_MARKER) + OPEN_MARKER.length(), markerString
+ .indexOf(CLOSE_MARKER));
+ }
+ return key;
+ }
+
+ /**
+ * Check whether there is a directory existing in present workspace, with
+ * the given name.
+ *
+ * @param directoryName
+ * @return true, if directory exists.
+ *
+ * @since 4.0
+ */
+ public static boolean checkDirectoryInWorkspace(String directoryName) {
+
+ boolean retVal = false;
+ File file = null;
+
+ try {
+ file = new File(getWorkspacePath() + directoryName);
+ } catch (Exception exp) {
+
+ }
+ if ((file != null) && (file.exists()) && (file.isDirectory())) {
+ retVal = true;
+ }
+ return retVal;
+ }
+ /**
+ * Return Template Source path as URL
+ * @param pluginId
+ * @param resourcePath
+ * @return URL, of the Template Resource
+ * @throws IOException
+ *
+ * @since 4.0
+ */
+
+ public static URL getTemplateResourceURL(String pluginId, String resourcePath) throws IOException {
+ return FileLocator.toFileURL(Platform.getBundle(pluginId).getEntry(resourcePath));
+ }
+
+ /**
+ *
+ * Returns the Template Resource Relative Path as URL
+ * @param template
+ * @param resourcePath
+ * @return URL, of the Template Resource
+ * @throws IOException
+ *
+ * @since 4.0
+ */
+ public static URL getTemplateResourceURLRelativeToTemplate(TemplateCore template, String resourcePath) throws IOException {
+ TemplateInfo templateInfo = template.getTemplateInfo();
+ String path = templateInfo.getTemplatePath();
+ int slash = path.lastIndexOf("/"); //$NON-NLS-1$
+ if (slash == -1) {
+ path = resourcePath;
+ } else {
+ path = path.substring(0, slash + 1) + resourcePath;
+ }
+ URL entry = Platform.getBundle(templateInfo.getPluginId()).getEntry(path);
+ if (entry == null) {
+ return null;
+ }
+ return FileLocator.toFileURL(entry);
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngineMessages.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngineMessages.java
new file mode 100644
index 0000000000..bba96d2734
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngineMessages.java
@@ -0,0 +1,32 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine;
+
+import java.util.MissingResourceException;
+import java.util.ResourceBundle;
+
+public class TemplateEngineMessages {
+ private static final String BUNDLE_NAME = "org.eclipse.cdt.core.templateengine.messages"; //$NON-NLS-1$
+
+ private static final ResourceBundle RESOURCE_BUNDLE = ResourceBundle
+ .getBundle(BUNDLE_NAME);
+
+ private TemplateEngineMessages() {
+ }
+
+ public static String getString(String key) {
+ try {
+ return RESOURCE_BUNDLE.getString(key);
+ } catch (MissingResourceException e) {
+ return '!' + key + '!';
+ }
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngineUtil.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngineUtil.java
new file mode 100644
index 0000000000..6802f70094
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateEngineUtil.java
@@ -0,0 +1,51 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.Iterator;
+import java.util.List;
+
+import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.Status;
+
+public class TemplateEngineUtil {
+
+ public static void log(Throwable t) {
+ if (t == null) {
+ return;
+ }
+ if (t instanceof InvocationTargetException) {
+ t = ((InvocationTargetException) t).getTargetException();
+ }
+ if (t instanceof CoreException) {
+ ResourcesPlugin.getPlugin().getLog().log(((CoreException) t).getStatus());
+ } if (t instanceof ProcessFailureException) {
+ do {
+ List/*<IStatus>*/ statuses = ((ProcessFailureException) t).getStatuses();
+ if (statuses != null) {
+ for(Iterator i = statuses.iterator(); i.hasNext(); ) {
+ IStatus status = (IStatus) i.next();
+ ResourcesPlugin.getPlugin().getLog().log(status);
+ }
+ }
+ t = t.getCause();
+ } while (t != null && t instanceof ProcessFailureException);
+ } else {
+ ResourcesPlugin.getPlugin().getLog().log(new Status(IStatus.ERROR, CCorePlugin.PLUGIN_ID, IStatus.OK, t.getMessage() == null ? t.toString() : t.getMessage() , t));
+ }
+ }
+
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateInfo.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateInfo.java
new file mode 100644
index 0000000000..169b708964
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/TemplateInfo.java
@@ -0,0 +1,129 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine;
+
+import java.util.Set;
+
+
+
+/**
+ * TemplateInfo class contains the template information like wizard ID, pattern, path and project type.
+ */
+public class TemplateInfo {
+ private String projectTypeId;
+ private String filterPattern;
+ private String usageDescription;
+ private String templatePath;
+ private String pluginId;
+ private Set toolChainIdSet;
+ private String pagesProvider;
+ private boolean isCategory;
+ private String icon;
+
+ public TemplateInfo(String projectTypeId, String filterPattern, String templatePath,
+ String pluginId, Set toolChainIdSet, String usageDescription,
+ String pagesProvider, boolean isCategory) {
+ this.filterPattern = filterPattern;
+ this.templatePath = templatePath;
+ this.pluginId = pluginId;
+ this.projectTypeId = projectTypeId;
+ this.toolChainIdSet = toolChainIdSet;
+ this.usageDescription = usageDescription != null ? usageDescription : ""; //$NON-NLS-1$
+ this.pagesProvider = pagesProvider;
+ this.isCategory = isCategory;
+ }
+
+ /**
+ * Returns the Plugin ID
+ * @return String contains the plugin id.
+ */
+ public String getPluginId() {
+ return pluginId;
+ }
+
+ /**
+ * Returns the Template path as String.
+ * @return String containing the path.
+ */
+ public String getTemplatePath() {
+ return templatePath;
+ }
+
+ /**
+ * Returns the Filter Pattern.
+ * @return String containing the Filter Pattern.
+ */
+ public String getFilterPattern() {
+ return filterPattern;
+ }
+
+ /**
+ * @return the usageDescription
+ */
+ public String getUsageDescription() {
+ return usageDescription;
+ }
+
+ public String getExtraPagesProvider() {
+ return pagesProvider;
+ }
+
+ /**
+ * @return the projectTypeIds
+ */
+ public String getProjectType() {
+ return projectTypeId;
+ }
+
+ /**
+ * @return the toolChainIds
+ */
+ public String[] getToolChainIds() {
+ return (String[]) toolChainIdSet.toArray(new String[toolChainIdSet.size()]);
+ }
+
+ /**
+ * @return the isCategory
+ */
+ public boolean isCategory() {
+ return isCategory;
+ }
+
+ /**
+ * @return the icon image file name
+ */
+ public String getIcon() {
+ return icon;
+ }
+
+ /**
+ * Checks whether two TemplateInfo object are equal.
+ */
+ public boolean equals(Object obj) {
+ if (obj instanceof TemplateInfo) {
+ TemplateInfo info = (TemplateInfo) obj;
+ return projectTypeId.equals(info.projectTypeId) && templatePath.equals(info.templatePath) && pluginId.equals(info.pluginId)
+ && (((filterPattern == null || info.filterPattern == null) && filterPattern == info.filterPattern)
+ || filterPattern.equals(info.filterPattern))
+ && ((toolChainIdSet.equals(info.toolChainIdSet)))
+ && ((isCategory == info.isCategory));
+ }
+ return false;
+ }
+
+ /**
+ * Return the hashcode of the object.
+ */
+ public int hashCode() {
+ return projectTypeId.hashCode() | templatePath.hashCode() | pluginId.hashCode();
+ }
+
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/messages.properties b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/messages.properties
new file mode 100644
index 0000000000..08fb3cac58
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/messages.properties
@@ -0,0 +1,31 @@
+###############################################################################
+# Copyright (c) 2007 Symbian Software Limited and others.
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Eclipse Public License v1.0
+# which accompanies this distribution, and is available at
+# http://www.eclipse.org/legal/epl-v10.html
+#
+# Contributors:
+# Bala Torati (Symbian) - Initial API and implementation
+###############################################################################
+
+TemplateEngine.internalError=Internal Error:
+TemplateEngine.templateEngine=Template Engine
+ProjectCreatedActions.InsufficientInformation=Insufficient information to create new project
+
+ConditionalProcessGroup.notExecuting=Condition block not executing:
+ConditionalProcessGroup.unexpandableMacro=Condition has an unexpandable macro:
+Process.argument=Argument
+Process.expandableMacro=\ has an unexpandable macro:
+Process.error=-->Error:
+Process.success=-->Success:
+Process.info=-->Info:
+Process.unknownProcess=Unknown process:
+Process.executedSuccessfully=Executed successfully with args:
+ProcessRunner.unexpectedArguments=Unexpected arguments found.
+ProcessRunner.missingArguments=Missing arguments.
+ProcessRunner.argumentsMismatch=Argument type mismatch:
+ProcessRunner.error=-->Error:
+ProcessRunner.success=-->Success:
+ProcessRunner.info=-->Info:
+ProcessHelper.fileNotFound=File not found:
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ConditionalProcessGroup.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ConditionalProcessGroup.java
new file mode 100644
index 0000000000..f3f59406f4
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ConditionalProcessGroup.java
@@ -0,0 +1,284 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateDescriptor;
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+import org.eclipse.cdt.core.templateengine.TemplateEngineMessages;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.Status;
+import org.w3c.dom.Element;
+
+
+/**
+ * ConditionalProcess encloses an &lt;if condition="..."&gt;&lt;/if&gt; block of the template.
+ * The currently supported conditions are equals and not equals operations performed on two
+ * Strings. The respective operators are == and !=. Any spaces will be treated as part of the
+ * operands. The two operands will be evaluated for simple String equals and not equals after
+ * performing a single pass replace of any replace markers with their values in the template's
+ * value store.
+ */
+public class ConditionalProcessGroup {
+
+ private TemplateCore template;
+ private Set/*<String>*/ macros;
+ private String conditionString;
+ private String lValue;
+ private String rValue;
+ private Operator op;
+ private List/*<Process>*/ processes;
+ private String id;
+
+ /**
+ * @author BalaT
+ */
+ private static class Operator {
+ final static Operator EQUALS = new Operator("="); //$NON-NLS-1$
+ final static Operator NOT_EQUALS = new Operator("!="); //$NON-NLS-1$
+
+ String id;
+ Operator(String id) {
+ this.id = id;
+ }
+ public boolean equals(Object arg0) {
+ if(arg0 instanceof Operator) {
+ return id.equals(((Operator)arg0).id);
+ }
+ return false;
+ }
+ }
+
+ /**
+ * Constructs a ConditionalProcess element from the supplied conditionElement (&lt;if&gt;) while building Process
+ * objects out of each of the element's &lt;process&gt; children.
+ * @throws ProcessFailureException
+ */
+ public ConditionalProcessGroup(TemplateCore template, Element conditionElement, int id) {
+ this.id = "Condition " + id; //$NON-NLS-1$
+ conditionString = conditionElement.getAttribute(ProcessHelper.CONDITION);
+ if (conditionString != null) {
+ if (conditionString.trim().equals("")) { //$NON-NLS-1$
+ conditionString = null;
+ } else {
+ int op = conditionString.indexOf(ProcessHelper.EQUALS);
+ if (op != -1) {
+ this.op = Operator.EQUALS;
+ lValue = conditionString.substring(0, op);
+ rValue = conditionString.substring(op + ProcessHelper.EQUALS.length());
+ } else {
+ op = conditionString.indexOf(ProcessHelper.NOT_EQUALS);
+ if (op != -1) {
+ this.op = Operator.NOT_EQUALS;
+ lValue = conditionString.substring(0, op);
+ rValue = conditionString.substring(op + ProcessHelper.NOT_EQUALS.length());
+ }//else an unsupported operation where this condition is ignored.
+ }
+ collectMacros(lValue);
+ collectMacros(rValue);
+ }
+ }
+ createProcessObjects(template, TemplateEngine.getChildrenOfElementByTag(conditionElement, TemplateDescriptor.PROCESS));
+ }
+
+ /**
+ * Adds values passed as parameter to the macros object
+ * @param value
+ */
+ private void collectMacros(String value) {
+ if (value != null) {
+ if (macros == null) {
+ macros = new HashSet/*<String>*/();
+ }
+ macros.addAll(ProcessHelper.getReplaceKeys(value));
+ }
+ }
+
+ /**
+ * Constructs a ConditionalProcess element from the supplied process elements while building Process
+ * objects out of each of the supplied process elements (&lt;process&gt;). The condition in this case is evaluated to true.
+ *
+ * This Constructor is expected to be used to evaluate all those process elements that are children of the template root element.
+ * @throws ProcessFailureException
+ */
+ public ConditionalProcessGroup(TemplateCore template, Element[] processElements) {
+ id = "No Condition"; //$NON-NLS-1$
+ createProcessObjects(template, Arrays.asList(processElements));
+ }
+
+ /**
+ * Creates the Proccess from the process Elements.
+ * @param template
+ * @param processElements
+ */
+ private void createProcessObjects(TemplateCore template, List/*<Element>*/ processElements) {
+ this.template = template;
+ this.processes = new ArrayList/*<Process>*/(processElements.size());
+ for (int j = 0, l = processElements.size(); j < l; j++) {
+ Element processElem = (Element) processElements.get(j);
+ if (processElem.getNodeName().equals(TemplateDescriptor.PROCESS)) {
+ String processId = id + "--> Process " + (j + 1) + " (" + processElem.getAttribute(Process.ELEM_TYPE) + ")"; //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
+ processes.add(new Process(template, processElem, processId));
+ }
+ }
+ }
+
+ /**
+ * Checks if this conditional process group is completely ready to be processed.
+ */
+ public boolean isReadyToProcess() {
+ return areMacrosForConditionEvaluationExpandable() && isConditionValueTrue() && areProcessesReady();
+ }
+
+ /**
+ *
+ * @return boolean, as true if the Processes are ready to process
+ */
+ private boolean areProcessesReady() {
+ for(Iterator i = processes.iterator(); i.hasNext(); ) {
+ Process process = (Process) i.next();
+ if (!process.isReadyToProcess()) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ /**
+ *
+ * @return boolean, true if Macros For Condition Evaluation Expandable.
+ */
+ private boolean areMacrosForConditionEvaluationExpandable() {
+ if (macros != null) {
+ Map/*<String, String>*/ valueStore = template.getValueStore();
+ for(Iterator i = macros.iterator(); i.hasNext(); ) {
+ String value = (String) i.next();
+ if (valueStore.get(value) == null) {
+ return false;
+ }
+ }
+ }
+ return true;
+ }
+
+ /**
+ *
+ * @return boolean, true if Condition Value is True.
+ */
+ public boolean isConditionValueTrue() {
+ if (conditionString == null) {
+ return true;
+ }
+ if (!areMacrosForConditionEvaluationExpandable()) {
+ return false;
+ }
+ Map/*<String, String>*/ valueStore = template.getValueStore();
+ String lValue = this.lValue;
+ String rValue = this.rValue;
+ for(Iterator i = macros.iterator(); i.hasNext(); ) {
+ String value = (String) i.next();
+ lValue = lValue.replaceAll(ProcessHelper.START_PATTERN + value + ProcessHelper.END_PATTERN, (String) valueStore.get(value));
+ rValue = rValue.replaceAll(ProcessHelper.START_PATTERN + value + ProcessHelper.END_PATTERN, (String) valueStore.get(value));
+ }
+ if(op.equals(Operator.EQUALS)) {
+ return lValue.equals(rValue);
+ } else if(op.equals(Operator.NOT_EQUALS)) {
+ return !lValue.equals(rValue);
+ } else {
+ return false;
+ }
+ }
+
+ /**
+ * Process and Returns the Status of the prosses as a List.
+ * @param monitor
+ * @return List contains the IStatus.
+ * @throws ProcessFailureException
+ */
+ public List/*<IStatus>*/ process(IProgressMonitor monitor) throws ProcessFailureException {
+ if (!areMacrosForConditionEvaluationExpandable()) {
+ throw new ProcessFailureException(getUnexpandableMacroMessage());
+ }
+ if (!isConditionValueTrue()) {
+ List/*<IStatus>*/ statuses = new ArrayList/*<IStatus>*/(1);
+ statuses.add(new Status(IStatus.ERROR, CCorePlugin.PLUGIN_ID, IStatus.INFO, TemplateEngineMessages.getString("ConditionalProcessGroup.notExecuting") + id, null)); //$NON-NLS-1$
+ return statuses;
+ }
+ List/*<IStatus>*/ statuses = new ArrayList/*<IStatus>*/(processes.size());
+ for(Iterator i = processes.iterator(); i.hasNext(); ) {
+ Process process = (Process) i.next();
+ try {
+ statuses.add(process.process(monitor));
+ } catch (ProcessFailureException e) {
+ throw new ProcessFailureException(e.getMessage(), e, statuses);
+ }
+ }
+ return statuses;
+ }
+
+ /**
+ * Return the Unexpandable Macro Message
+ * @return
+ */
+ private String getUnexpandableMacroMessage() {
+ if (macros != null) {
+ Map/*<String, String>*/ valueStore = template.getValueStore();
+ for(Iterator i = macros.iterator(); i.hasNext(); ) {
+ String value = (String) i.next();
+ if (valueStore.get(value) == null) {
+ return TemplateEngineMessages.getString("ConditionalProcessGroup.unexpandableMacro") + value; //$NON-NLS-1$
+ }
+ }
+ }
+ return null;
+ }
+
+ /**
+ * Returns the Macros as a Set.
+ * @return Set, contains macros
+ */
+ public Set/*<String>*/ getMacros() {
+ return macros;
+ }
+
+ /**
+ * Returns All Macros as a Set.
+ * @return Set, contains macros
+ */
+ public Set/*<String>*/ getAllMacros() {
+ Set/*<String>*/ set = null;
+ if (macros != null) {
+ set = new HashSet/*<String>*/();
+ set.addAll(macros);
+ }
+ for(Iterator i = processes.iterator(); i.hasNext(); ) {
+ Process process = (Process) i.next();
+ Set/*<String>*/ subSet = process.getMacros();
+ if (subSet != null) {
+ if (set == null) {
+ set = new HashSet/*<String>*/();
+ }
+ set.addAll(subSet);
+ }
+ }
+ return set;
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/Process.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/Process.java
new file mode 100644
index 0000000000..cad1c6e38a
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/Process.java
@@ -0,0 +1,201 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+
+import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+import org.eclipse.cdt.core.templateengine.TemplateEngineMessages;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.Status;
+import org.w3c.dom.Element;
+
+
+/**
+ * This class contains methods to get first process block element, next process
+ * block element and checks for next process block element.
+ */
+public class Process {
+ public static final String ELEM_TYPE = "type"; //$NON-NLS-1$
+
+ private ProcessRunner processRunner;
+ private ProcessArgument[] args;
+ private TemplateCore template;
+ private String id;
+ private String processType;
+
+ /**
+ * Constructor to create a process.
+ * @param template
+ * @param element
+ * @param id
+ */
+ public Process(TemplateCore template, Element element, String id) {
+ this.template = template;
+ this.id = id;
+ processType = element.getAttribute(ELEM_TYPE);
+ processRunner = ProcessRunnerFactory.getDefault().getProcessRunner(processType);
+ if (processRunner != null) {
+ buildArgs(template, element);
+ }
+ }
+
+ /**
+ * This method build the necessary Arguments for the process
+ * @param template
+ * @param element
+ */
+ private void buildArgs(TemplateCore template, Element element) {
+ List/*<Element>*/ children = TemplateEngine.getChildrenOfElement(element);
+ ProcessParameter[] params = processRunner.getProcessParameters();
+ List/*<ProcessArgument>*/ list = new ArrayList/*<ProcessArgument>*/(params.length);
+ int childIndex = 0;
+ for(int i=0; i<params.length; i++) {
+ ProcessParameter param = params[i];
+ boolean childrenRemain = childIndex < children.size();
+ Element child = (Element) (childrenRemain ? children.get(childIndex) : null);
+ if (param.isExternal() && (!childrenRemain || !param.getName().equals(child.getAttribute(ProcessArgument.ELEM_NAME)))) {
+ list.add(new ProcessArgument(template, param));
+ } else if (childrenRemain) {
+ list.add(new ProcessArgument(template, child));
+ childIndex++;
+ }
+ }
+ while (childIndex < children.size()) {
+ list.add(new ProcessArgument(template, (Element) children.get(childIndex++)));
+ }
+ args = (ProcessArgument[]) list.toArray(new ProcessArgument[list.size()]);
+ }
+
+ /**
+ *
+ * @return boolean, true if the Process is Ready.
+ */
+ public boolean isReadyToProcess() {
+ if (processRunner == null || !processRunner.areArgumentsMatchingRequiredParameters(args) || !areAllMacrosExpandable()) {
+ return false;
+ }
+ return true;
+ }
+
+ /**
+ *
+ * @return boolean, true if Macros are Exapandable.
+ */
+ private boolean areAllMacrosExpandable() {
+ if (args != null) {
+ for(int i=0; i<args.length; i++) {
+ ProcessArgument arg = args[i];
+ if (!arg.areAllMacrosExpandable()) {
+ return false;
+ }
+ }
+ }
+ return true;
+ }
+
+ /**
+ * Returns First NonExpandable Macro Message
+ */
+ private String getFirstNonExpandableMacroMessage(ProcessArgument[] args2) {
+ if (args != null) {
+ String macro;
+ for(int i=0; i<args.length; i++) {
+ ProcessArgument arg = args[i];
+ if ((macro = arg.getFirstNonExpandableMacro()) != null) {
+ return TemplateEngineMessages.getString("Process.argument") + arg.getName() + TemplateEngineMessages.getString("Process.expandableMacro") + macro; //$NON-NLS-1$ //$NON-NLS-2$
+ }
+ }
+ }
+ return null;
+ }
+
+ /**
+ * Returns the Process Message depending on the parameters.
+ * @param code
+ * @param msg
+ * @return
+ */
+ private String getProcessMessage(int code, String msg) {
+ switch (code) {
+ case IStatus.ERROR:
+ return id + TemplateEngineMessages.getString("Process.error") + msg; //$NON-NLS-1$
+ case IStatus.OK:
+ return id + TemplateEngineMessages.getString("Process.success") + msg; //$NON-NLS-1$
+ default:
+ return id + TemplateEngineMessages.getString("Process.info") + msg; //$NON-NLS-1$
+ }
+ }
+
+ /**
+ * Constructor
+ * @param monitor
+ * @return
+ * @throws ProcessFailureException
+ */
+ public IStatus process(IProgressMonitor monitor) throws ProcessFailureException {
+ if (processRunner == null) {
+ throw new ProcessFailureException(TemplateEngineMessages.getString("Process.unknownProcess") + processType); //$NON-NLS-1$
+ }
+ if (!processRunner.areArgumentsMatchingRequiredParameters(args)) {
+ throw new ProcessFailureException(processRunner.getArgumentsMismatchMessage(args));
+ }
+ if (!areAllMacrosExpandable()) {
+ throw new ProcessFailureException(getProcessMessage(IStatus.ERROR, getFirstNonExpandableMacroMessage(args)));
+ }
+ resolve();
+ processRunner.process(template, args, id, monitor);
+ return new Status(IStatus.INFO, CCorePlugin.PLUGIN_ID, IStatus.OK, getProcessMessage(IStatus.OK, TemplateEngineMessages.getString("Process.executedSuccessfully") + Arrays.asList(args)), null); //$NON-NLS-1$
+ }
+
+ private void resolve() {
+ if (args != null) {
+ for(int i=0; i<args.length; i++) {
+ ProcessArgument arg = args[i];
+ if (!arg.isResolved()) {
+ arg.resolve();
+ }
+ }
+ }
+ }
+
+ /**
+ * Returns the Macros.
+ * @return
+ */
+ public Set/*<String>*/ getMacros() {
+ Set/*<String>*/ set = null;
+ if (args != null) {
+ for(int i=0; i<args.length; i++) {
+ ProcessArgument arg = args[i];
+ Set/*<String>*/ subSet = arg.getMacros();
+ if (subSet != null) {
+ if (set == null) {
+ set = new HashSet/*<String>*/();
+ }
+ set.addAll(subSet);
+ }
+ }
+ }
+ return set;
+ }
+
+ public String toString() {
+ return id;
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessArgument.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessArgument.java
new file mode 100644
index 0000000000..b5abbba013
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessArgument.java
@@ -0,0 +1,435 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process;
+
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+import org.w3c.dom.Element;
+
+
+/**
+ * ProcessArgument class responsible for constructing process Arguments by taking info from Template.
+ */
+public class ProcessArgument {
+
+ static final String ELEM_NAME = "name"; //$NON-NLS-1$
+ private static final String ELEM_VALUE = "value"; //$NON-NLS-1$
+ private static final String ELEM_ELEMENT = "element"; //$NON-NLS-1$
+ private static final String ELEM_SIMPLE = "simple"; //$NON-NLS-1$
+ private static final String ELEM_SIMPLE_ARRAY = "simple-array"; //$NON-NLS-1$
+ private static final String ELEM_COMPLEX = "complex"; //$NON-NLS-1$
+ private static final String ELEM_COMPLEX_ARRAY = "complex-array"; //$NON-NLS-1$
+
+ private String name;
+ private byte type;
+
+ private String simpleValue;
+ private String[] simpleValueArray;
+ private ProcessArgument[] complexValue;
+ private ProcessArgument[][] complexValueArray;
+
+ private String resolvedSimpleValue;
+ private String[] resolvedSimpleValueArray;
+
+ private TemplateCore template;
+
+ private Set/*<String>*/ macros;
+ private boolean resolved;
+ private ProcessParameter externalParam;
+
+ /**
+ * constructor
+ * @param template
+ * @param elem
+ */
+ public ProcessArgument(TemplateCore template, Element elem) {
+ this.template = template;
+ this.name = elem.getAttribute(ELEM_NAME);
+ String elemName = elem.getNodeName();
+ if (elemName.equals(ELEM_SIMPLE)) {
+ type = ProcessParameter.SIMPLE;
+ simpleValue = elem.getAttribute(ELEM_VALUE);
+ collectMacros(simpleValue);
+ } else if (elemName.equals(ELEM_SIMPLE_ARRAY)) {
+ type = ProcessParameter.SIMPLE_ARRAY;
+ List/*<Element>*/ valueElements = TemplateEngine.getChildrenOfElementByTag(elem, ELEM_ELEMENT);
+ simpleValueArray = new String[valueElements.size()];
+ for (int i = 0, l = valueElements.size(); i < l; i++) {
+ simpleValueArray[i] = ((Element)valueElements.get(i)).getAttribute(ELEM_VALUE);
+ collectMacros(simpleValueArray[i]);
+ }
+ } else if (elemName.equals(ELEM_COMPLEX)) {
+ type = ProcessParameter.COMPLEX;
+ List/*<Element>*/ children = TemplateEngine.getChildrenOfElement(elem);
+ complexValue = new ProcessArgument[children.size()];
+ for (int i = 0, l = children.size(); i < l; i++) {
+ complexValue[i] = new ProcessArgument(template, (Element) children.get(i));
+ Set/*<String>*/ subMacros = complexValue[i].getMacros();
+ if (macros == null) {
+ macros = new HashSet/*<String>*/();
+ }
+ if (subMacros != null) {
+ macros.addAll(subMacros);
+ }
+ }
+ } else if (elemName.equals(ELEM_COMPLEX_ARRAY)) {
+ type = ProcessParameter.COMPLEX_ARRAY;
+ List/*<Element>*/ valueElements = TemplateEngine.getChildrenOfElementByTag(elem, ELEM_ELEMENT);
+ complexValueArray = new ProcessArgument[valueElements.size()][];
+
+ for (int i = 0, l = valueElements.size(); i < l; i++) {
+ List/*<Element>*/ children = TemplateEngine.getChildrenOfElement((Element)valueElements.get(i));
+ complexValueArray[i] = new ProcessArgument[children.size()];
+ for (int j = 0, l2 = children.size(); j < l2; j++) {
+ complexValueArray[i][j] = new ProcessArgument(template, (Element) children.get(j));
+ Set/*<String>*/ subMacros = complexValueArray[i][j].getMacros();
+ if (subMacros != null) {
+ if (macros == null) {
+ macros = new HashSet/*<String>*/();
+ }
+ macros.addAll(subMacros);
+ }
+ }
+ }
+ }
+ }
+
+ /**
+ * Creates an <i>external</i> argument. This is not read from the template descriptor.
+ * @param param The ProcessParameter whose replacement this argument is in the Process call
+ */
+ public ProcessArgument(TemplateCore template, ProcessParameter param) {
+ this.template = template;
+ name = param.getName();
+ type = param.getType();
+ macros = new HashSet/*<String>*/();
+ macros.add(name);
+ simpleValue = ProcessHelper.getReplaceMarker(name);
+ this.externalParam = param;
+ }
+
+ /**
+ * Adds the marcos based on the value.
+ * @param value
+ */
+ private void collectMacros(String value) {
+ if (value == null) {
+ return;
+ }
+ if (macros == null) {
+ macros = new HashSet/*<String>*/();
+ }
+ macros.addAll(ProcessHelper.getReplaceKeys(value));
+ }
+
+ /**
+ * Returns Parameter name.
+ * @return parameter name as String
+ */
+ public String getName() {
+ return name;
+ }
+
+ /**
+ * Returns the Parameter Type
+ * @return the Parmeter Type as String
+ */
+ public byte getParameterType() {
+ return type;
+ }
+
+ /**
+ * Returns the Simple Value.
+ * @return String,
+ */
+ public String getSimpleValue() {
+ return resolved ? resolvedSimpleValue : simpleValue;
+ }
+
+ /**
+ * Returns the Simple Array Values.
+ * @return String Array.
+ */
+ public String[] getSimpleArrayValue() {
+ return resolved ? resolvedSimpleValueArray : simpleValueArray;
+ }
+
+ /**
+ * Returns Process Arguments
+ */
+ public ProcessArgument[] getComplexValue() {
+ return complexValue;
+ }
+
+ /**
+ * Returns Process Arguments
+ */
+ public ProcessArgument[][] getComplexArrayValue() {
+ return complexValueArray;
+ }
+
+ /**
+ * Check for parameter type.
+ * @param param
+ * @return boolean
+ */
+ public boolean isOfParameterType(ProcessParameter param) {
+ if (param.getType() != type || !param.getName().equals(name)) {
+ return false;
+ }
+ switch (type) {
+ case ProcessParameter.SIMPLE:
+ return simpleValue != null || param.isNullable();
+ case ProcessParameter.SIMPLE_ARRAY:
+ return true;
+ case ProcessParameter.COMPLEX:
+ ProcessParameter[] params = param.getComplexChildren();
+ if (params.length != complexValue.length) {
+ return false;
+ }
+ for (int i = 0; i < complexValue.length; i++) {
+ if (!complexValue[i].isOfParameterType(params[i])) {
+ return false;
+ }
+ }
+ return true;
+ case ProcessParameter.COMPLEX_ARRAY:
+ params = param.getComplexChildren();
+ for(int i=0; i<complexValueArray.length; i++) {
+ ProcessArgument[] complexValue = complexValueArray[i];
+ if (params.length != complexValue.length) {
+ return false;
+ }
+ for (int j = 0; j < complexValue.length; j++) {
+ if (!complexValue[j].isOfParameterType(params[j])) {
+ return false;
+ }
+ }
+ }
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Returns true if All macros are Expandable.
+ * @return
+ */
+ public boolean areAllMacrosExpandable() {
+ switch (type) {
+ case ProcessParameter.SIMPLE:
+ if (externalParam != null) {
+ return externalParam.isNullable() || template.getValueStore().get(name) != null;
+ }
+ case ProcessParameter.SIMPLE_ARRAY:
+ if (macros == null || macros.size() == 0) {
+ return true;
+ }
+ Map/*<String, String>*/ valueStore = template.getValueStore();
+ for(Iterator i = macros.iterator(); i.hasNext(); ) {
+ String macro = (String) i.next();
+ if (valueStore.get(macro) == null) {
+ return false;
+ }
+ }
+ return true;
+ case ProcessParameter.COMPLEX:
+ for(int i=0; i<complexValue.length; i++) {
+ ProcessArgument arg = complexValue[i];
+ if (!arg.areAllMacrosExpandable()) {
+ return false;
+ }
+ }
+ return true;
+ case ProcessParameter.COMPLEX_ARRAY:
+ for(int i=0; i<complexValueArray.length; i++) {
+ ProcessArgument[] complexValue =complexValueArray[i];
+ for(int j=0; j<complexValue.length; j++) {
+ ProcessArgument arg = complexValue[j];
+ if (!arg.areAllMacrosExpandable()) {
+ return false;
+ }
+ }
+ }
+ return true;
+ }
+ return true;
+ }
+
+ /**
+ * Returns the First Non-expandable Macro.
+ */
+ public String getFirstNonExpandableMacro() {
+ switch (type) {
+ case ProcessParameter.SIMPLE:
+ case ProcessParameter.SIMPLE_ARRAY:
+ if (macros == null || macros.size() == 0) {
+ return null;
+ }
+ Map/*<String, String>*/ valueStore = template.getValueStore();
+ for(Iterator i = macros.iterator(); i.hasNext(); ) {
+ String macro = (String) i.next();
+ if (valueStore.get(macro) == null) {
+ return macro;
+ }
+ }
+ return null;
+ case ProcessParameter.COMPLEX:
+ String macro;
+ for(int i=0; i<complexValue.length; i++) {
+ ProcessArgument arg = complexValue[i];
+ if ((macro = arg.getFirstNonExpandableMacro()) != null) {
+ return macro;
+ }
+ }
+ return null;
+ case ProcessParameter.COMPLEX_ARRAY:
+ for(int i=0; i<complexValueArray.length; i++) {
+ ProcessArgument[] complexValue =complexValueArray[i];
+ for(int j=0; j<complexValue.length; j++) {
+ ProcessArgument arg = complexValue[j];
+ if ((macro = arg.getFirstNonExpandableMacro()) != null) {
+ return macro;
+ }
+ }
+ }
+ return null;
+ }
+ return null;
+ }
+
+ /**
+ * Returns the Macros as Set.
+ * @return Set, contains the Macros.
+ */
+ public Set/*<String>*/ getMacros() {
+ return macros;
+ }
+
+ /**
+ * resolve
+ *
+ */
+ public void resolve() {
+ Map/*<String, String>*/ valueStore = template.getValueStore();
+ switch (type) {
+ case ProcessParameter.SIMPLE:
+ if (externalParam != null) {
+ resolvedSimpleValue = (String) template.getValueStore().get(name);
+ } else {
+ resolvedSimpleValue = simpleValue;
+ if (macros != null && !macros.isEmpty()) {
+ resolvedSimpleValue = ProcessHelper.getValueAfterExpandingMacros(resolvedSimpleValue, macros, valueStore);
+ }
+ }
+ break;
+ case ProcessParameter.SIMPLE_ARRAY:
+ resolvedSimpleValueArray = simpleValueArray;
+ if (macros != null && !macros.isEmpty()) {
+ for (int i = 0; i < resolvedSimpleValueArray.length; i++) {
+ resolvedSimpleValueArray[i] = ProcessHelper.getValueAfterExpandingMacros(resolvedSimpleValueArray[i], macros, valueStore);
+ }
+ }
+ break;
+ case ProcessParameter.COMPLEX:
+ for(int i=0; i<complexValue.length; i++) {
+ ProcessArgument arg = complexValue[i];
+ arg.resolve();
+ }
+ break;
+ case ProcessParameter.COMPLEX_ARRAY:
+ for(int i=0; i<complexValueArray.length; i++) {
+ ProcessArgument[] complexValue =complexValueArray[i];
+ for(int j=0; j<complexValue.length; j++) {
+ ProcessArgument arg = complexValue[j];
+ arg.resolve();
+ }
+ }
+ break;
+ }
+ resolved = true;
+ }
+
+ /**
+ * Checks whether the process argument has resolved.
+ * @return boolean, true if resolved.
+ */
+ public boolean isResolved() {
+ return resolved;
+ }
+
+ /*
+ * (non-Javadoc)
+ * @see java.lang.Object#toString()
+ */
+ public String toString() {
+ StringBuffer b = new StringBuffer(name);
+ b.append(":"); //$NON-NLS-1$
+ switch (type) {
+ case ProcessParameter.SIMPLE:
+ return b.append(getSimpleValue()).toString();
+ case ProcessParameter.SIMPLE_ARRAY:
+ b.append("{"); //$NON-NLS-1$
+ String[] strings = getSimpleArrayValue();
+ for(int i=0; i<strings.length; i++) {
+ b.append(strings[i]).append(", "); //$NON-NLS-1$
+ }
+ if (b.charAt(b.length() - 1) == ' ') {
+ b.replace(b.length() - 2, b.length(), "}"); //$NON-NLS-1$
+ } else {
+ b.append("}"); //$NON-NLS-1$
+ }
+ return b.toString();
+ case ProcessParameter.COMPLEX:
+ b.append("{"); //$NON-NLS-1$
+ ProcessArgument[] args = getComplexValue();
+ for(int i=0; i<args.length; i++) {
+ ProcessArgument arg = args[i];
+ b.append(arg).append(", "); //$NON-NLS-1$
+ }
+ if (b.charAt(b.length() - 1) == ' ') {
+ b.replace(b.length() - 2, b.length(), "}"); //$NON-NLS-1$
+ } else {
+ b.append("}"); //$NON-NLS-1$
+ }
+ return b.toString();
+ case ProcessParameter.COMPLEX_ARRAY:
+ b.append("{"); //$NON-NLS-1$
+ ProcessArgument[][] argssCA = getComplexArrayValue();
+ for(int i=0; i<argssCA.length; i++) {
+ ProcessArgument[] argsCA = argssCA[i];
+ b.append("{"); //$NON-NLS-1$
+ for(int j=0; j<argsCA.length; j++) {
+ ProcessArgument arg = argsCA[j];
+ b.append(arg).append(", "); //$NON-NLS-1$
+ }
+ if (b.charAt(b.length() - 1) == ' ') {
+ b.replace(b.length() - 2, b.length(), "}, "); //$NON-NLS-1$
+ } else {
+ b.append("}, "); //$NON-NLS-1$
+ }
+ }
+ if (b.charAt(b.length() - 1) == ' ') {
+ b.replace(b.length() - 2, b.length(), "}"); //$NON-NLS-1$
+ } else {
+ b.append("}"); //$NON-NLS-1$
+ }
+ return b.toString();
+ }
+ return ""; //$NON-NLS-1$
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessFailureException.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessFailureException.java
new file mode 100644
index 0000000000..4c874d9e6e
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessFailureException.java
@@ -0,0 +1,66 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process;
+
+import java.util.List;
+
+public class ProcessFailureException extends Exception {
+ private static final long serialVersionUID = 1766239661286962870L;
+ private List/*<IStatus>*/ statuses;
+
+ /**
+ * Constructor based on the msg.
+ * @param msg
+ */
+ public ProcessFailureException(String msg) {
+ super(msg);
+ }
+
+ /**
+ * Constructor based on the msg and cause.
+ * @param cause
+ */
+ public ProcessFailureException(Throwable cause) {
+ super(cause);
+ }
+
+ /**
+ * Constructor based on the msg and cause.
+ * @param msg
+ * @param cause
+ */
+ public ProcessFailureException(String msg, Throwable cause) {
+ super(msg, cause);
+ }
+
+ /**
+ * Constructor based on the msg and causes.
+ * @param msg
+ * @param statuses
+ */
+ public ProcessFailureException(String msg, List/*<IStatus>*/ statuses) {
+ super(msg);
+ this.statuses = statuses;
+ }
+
+ public ProcessFailureException(String msg, Throwable cause, List/*<IStatus>*/ statuses) {
+ super(msg, cause);
+ this.statuses = statuses;
+ }
+
+ /**
+ * Returns the Statuses.
+ * @return List, contains the IStatus.
+ */
+ public List/*<IStatus>*/ getStatuses() {
+ return statuses;
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessHelper.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessHelper.java
new file mode 100644
index 0000000000..d8d7f0d14e
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessHelper.java
@@ -0,0 +1,232 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process;
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStreamReader;
+import java.io.RandomAccessFile;
+import java.net.URL;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.Set;
+
+import org.eclipse.cdt.core.templateengine.TemplateEngineMessages;
+import org.eclipse.core.resources.IFolder;
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.runtime.CoreException;
+
+/**
+ * Acts as Helper class for process the processes i.e., copy, replace and append
+ * files.
+ */
+public class ProcessHelper {
+ public static final String CONDITION = "condition"; //$NON-NLS-1$
+ public static final String START_PATTERN = "$("; //$NON-NLS-1$
+ public static final String END_PATTERN = ")"; //$NON-NLS-1$
+ public static final String EQUALS = "=="; //$NON-NLS-1$
+ public static final String NOT_EQUALS = "!="; //$NON-NLS-1$
+
+ /**
+ * This method is to append the given contents into a file.
+ *
+ * @param fileContents,
+ * contents which are appended to the file.
+ * @param toFile,
+ * a file to append contents.
+ * @throws IOException,
+ * exception while writing contents into a file
+ *
+ * @since 4.0
+ */
+ public static void appendFile(String fileContents, File toFile) throws IOException {
+ RandomAccessFile raf = null;
+ if (!toFile.exists()) {
+ throw new FileNotFoundException(" The specified destination file does not exists "); //$NON-NLS-1$
+ } else {
+ try {
+ raf = new RandomAccessFile(toFile, "rw"); //$NON-NLS-1$
+ raf.skipBytes((int) raf.length());
+ raf.writeBytes(fileContents);
+ } finally {
+ raf.close();
+ }
+ }
+ }
+
+ /**
+ * This method returns a vector of all replace marker strings. (e.g.,
+ * $(item), vector contains 'item' as one item. , ) is the end pattern.
+ *
+ * @param str,
+ * A given string may contains replace markers.
+ * @param pattern
+ * start pattern (e.g., $( is the start pattern)
+ * @param endPat
+ * end pattern (e.g., ) is the end pattern)
+ * @return a set of all replace marker strings.
+ *
+ * @since 4.0
+ */
+ public static Set/*<String>*/ getReplaceKeys(String str) {
+ int start = 0;
+ int end = 0;
+ Set/*<String>*/ replaceStrings = new HashSet/*<String>*/();
+ while ((start = str.indexOf(START_PATTERN, start)) >= 0) {
+ end = str.indexOf(END_PATTERN, start);
+ if (end != -1) {
+ replaceStrings.add(str.substring(start + START_PATTERN.length(), end));
+ start = end + START_PATTERN.length();
+ } else
+ start++;
+ }
+ return replaceStrings;
+ }
+
+ /**
+ * This method takes a URL as parameter to read the contents, and to add
+ * into a string buffer.
+ *
+ * @param source
+ * URL to read the contents.
+ * @return string, contents of a file specified in the URL source path.
+ * @throws IOException
+ *
+ * @since 4.0
+ */
+ public static String readFromFile(URL source) throws IOException {
+ char[] chars = new char[4092];
+ InputStreamReader contentsReader = null;
+ StringBuffer buffer = new StringBuffer();
+ if (!new java.io.File(source.getFile()).exists()) {
+ throw new FileNotFoundException(TemplateEngineMessages.getString("ProcessHelper.fileNotFound") + source.getFile()); //$NON-NLS-1$
+ } else {
+ contentsReader = new InputStreamReader(source.openStream());
+ int c;
+ do {
+ c = contentsReader.read(chars);
+ if (c == -1)
+ break;
+ buffer.append(chars, 0, c);
+ } while (c != -1);
+ contentsReader.close();
+ }
+ return buffer.toString();
+ }
+
+ /**
+ * This method reads contents from source, and writes the contents into
+ * destination file.
+ *
+ * @param source
+ * URL to read the contents.
+ * @param dest
+ * destination file to write the contents.
+ * @throws IOException
+ *
+ * @since 4.0
+ */
+ public static void copyBinaryFile(URL source, File dest) throws IOException {
+ byte[] bytes = new byte[4092];
+ if (source != null && dest != null) {
+ File file = new File(source.getFile());
+ if (file.isFile()) {
+ FileInputStream fis = new FileInputStream(file);
+ FileOutputStream fos = new FileOutputStream(dest);
+ int ch;
+ while (true) {
+ ch = fis.read(bytes);
+ if (ch == -1) {
+ break;
+ }
+ fos.write(bytes, 0, ch);
+ }
+ }
+ }
+ }
+
+ /**
+ * This method Creates the Directories in the parent Folder.
+ * @param projectHandle
+ * @param parentFolder
+ * @throws CoreException
+ *
+ * @since 4.0
+ */
+ public static void mkdirs(IProject projectHandle, IFolder parentFolder) throws CoreException {
+ if (parentFolder.getProjectRelativePath().equals(projectHandle.getProjectRelativePath())) {
+ return;
+ }
+ if (!parentFolder.getParent().exists()) {
+ mkdirs(projectHandle, projectHandle.getFolder(parentFolder.getParent().getProjectRelativePath()));
+ }
+ parentFolder.create(true, true, null);
+ }
+
+
+ /**
+ * Returns the Macro Value after Exanding the Macros.
+ * @param string
+ * @param macros
+ * @param valueStore
+ * @return
+ *
+ * @since 4.0
+ */
+ public static String getValueAfterExpandingMacros(String string, Set/*<String>*/ macros, Map/*<String, String>*/ valueStore) {
+ for (Iterator i = macros.iterator(); i.hasNext();) {
+ String key = (String) i.next();
+ String value = (String) valueStore.get(key);
+ if (value != null) {
+ string = replace(START_PATTERN + key + END_PATTERN, value, string);
+ }
+ }
+ return string;
+ }
+
+ /**
+ * This is equivalent to Java 5.0 version of
+ * String.replace(CharSequence target, CharSequence replacement) method.
+ * @since 4.0
+ */
+ private static String replace(String target, String replacement, String string) {
+ try {
+ StringBuffer stringBuffer = new StringBuffer(string);
+
+ int index = string.length();
+ int offset = target.length();
+
+ while ((index=string.lastIndexOf(target, index-1)) != -1) {
+ stringBuffer.replace(index, index+offset, replacement);
+ }
+
+ return stringBuffer.toString();
+ } catch (StringIndexOutOfBoundsException e) {
+ return string;
+ }
+ }
+
+ /**
+ * Consturct and Return the Replacment Markers
+ * after adding the patterns to the macro.
+ * @param macro
+ * @return
+ *
+ * @since 4.0
+ */
+ public static String getReplaceMarker(String macro) {
+ return START_PATTERN + macro + END_PATTERN;
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessParameter.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessParameter.java
new file mode 100644
index 0000000000..ce43a2bedd
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessParameter.java
@@ -0,0 +1,111 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process;
+
+import org.eclipse.core.runtime.IConfigurationElement;
+
+/**
+ * ProcessParameter is responsible for construting the Process Parameter the given configuration element.
+ */
+public class ProcessParameter {
+ public static final byte SIMPLE = 1;
+ public static final byte SIMPLE_ARRAY = 2;
+ public static final byte COMPLEX = 3;
+ public static final byte COMPLEX_ARRAY = 4;
+
+ private static final String ELEM_NAME = "name"; //$NON-NLS-1$
+ private static final String ELEM_BASE_TYPE = "baseType"; //$NON-NLS-1$
+ private static final String ELEM_SIMPLE = "simple"; //$NON-NLS-1$
+ private static final String ELEM_SIMPLE_ARRAY = "simpleArray"; //$NON-NLS-1$
+ private static final String ELEM_COMPLEX = "complex"; //$NON-NLS-1$
+ private static final String ELEM_COMPLEX_ARRAY = "complexArray"; //$NON-NLS-1$
+ private static final String ELEM_EXTERNAL = "external"; //$NON-NLS-1$
+ private static final String ELEM_NULLABLE = "nullable"; //$NON-NLS-1$
+
+ private String name;
+ private byte type;
+
+ private ProcessParameter[] complexChildren;
+ private boolean external;
+ private boolean nullable;
+
+ /**
+ * Constructor to extract the parameter info.
+ * @param element
+ */
+ public ProcessParameter(IConfigurationElement element) {
+ this.name = element.getAttribute(ELEM_NAME);
+ String elemName = element.getName();
+ if (elemName.equals(ELEM_SIMPLE)) {
+ type = SIMPLE;
+ } else if (elemName.equals(ELEM_SIMPLE_ARRAY)) {
+ type = SIMPLE_ARRAY;
+ } else if (elemName.equals(ELEM_COMPLEX)) {
+ type = COMPLEX;
+ IConfigurationElement[] children = element.getChildren();
+ complexChildren = new ProcessParameter[children.length];
+ for(int i=0; i<children.length; i++) {
+ complexChildren[i] = new ProcessParameter(children[i]);
+ }
+ } else if (elemName.equals(ELEM_COMPLEX_ARRAY)) {
+ type = COMPLEX_ARRAY;
+ IConfigurationElement baseType = element.getChildren(ELEM_BASE_TYPE)[0];
+ IConfigurationElement[] children = baseType.getChildren();
+ complexChildren = new ProcessParameter[children.length];
+ for(int i=0; i<children.length; i++) {
+ complexChildren[i] = new ProcessParameter(children[i]);
+ }
+ } else {
+ throw new IllegalArgumentException();
+ }
+
+ external = Boolean.valueOf(element.getAttribute(ELEM_EXTERNAL)).booleanValue();
+ nullable = Boolean.valueOf(element.getAttribute(ELEM_NULLABLE)).booleanValue();
+ }
+
+ /**
+ * Return the Element name.
+ * @return
+ */
+ public String getName() {
+ return name;
+ }
+
+ /**
+ * Returns the Element Type.
+ * @return
+ */
+ public byte getType() {
+ return type;
+ }
+
+ /**
+ * @return the complexChildren
+ */
+ public ProcessParameter[] getComplexChildren() {
+ return complexChildren;
+ }
+
+ /**
+ * Checks whether the element in external.
+ * @return
+ */
+ public boolean isExternal() {
+ return external;
+ }
+
+ /**
+ * @return the nullable
+ */
+ public boolean isNullable() {
+ return nullable;
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessRunner.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessRunner.java
new file mode 100644
index 0000000000..47c9cd9a72
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessRunner.java
@@ -0,0 +1,115 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateEngineMessages;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+
+
+/**
+ * Abstract ProcessRunner class provides the methods to implement for processes.
+ */
+public abstract class ProcessRunner {
+
+ private ProcessParameter[] params;
+
+ void setProcessParameters(ProcessParameter[] params) {
+ this.params = params;
+ }
+
+ /**
+ * Returns the Process Parameters.
+ * @return
+ */
+ public ProcessParameter[] getProcessParameters() {
+ return params;
+ }
+
+ /**
+ * Checks the whether the arguments are matching to Requied Parameters.
+ * @param args
+ * @return
+ */
+ protected final boolean areArgumentsMatchingRequiredParameters(ProcessArgument[] args) {
+ if ((params == null && args != null) || (params != null && args == null)) {
+ return false;
+ }
+ if (params == null && args == null) {
+ return true;
+ }
+ if (params.length != args.length) {
+ return false;
+ }
+ for (int i = 0; i < params.length; i++) {
+ if (!args[i].isOfParameterType(params[i])) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ /**
+ * Return the String containing the mismatching message
+ * if the arguments are not matching to Requied Parameters.
+ * @param args
+ * @return
+ */
+ public String getArgumentsMismatchMessage(ProcessArgument[] args) {
+ if (params == null && args != null) {
+ return TemplateEngineMessages.getString("ProcessRunner.unexpectedArguments"); //$NON-NLS-1$
+ }
+ if (params != null && args == null) {
+ return TemplateEngineMessages.getString("ProcessRunner.missingArguments"); //$NON-NLS-1$
+ }
+ if (params == null && args == null) {
+ return null;
+ }
+ if (params.length != args.length) {
+ return TemplateEngineMessages.getString("ProcessRunner.missingArguments"); //$NON-NLS-1$
+ }
+ for (int i = 0; i < params.length; i++) {
+ ProcessParameter param = params[i];
+ ProcessArgument arg = args[i];
+ if (!arg.isOfParameterType(param)) {
+ return TemplateEngineMessages.getString("ProcessRunner.argumentsMismatch") + arg.getName(); //$NON-NLS-1$
+ }
+ }
+ return null;
+ }
+
+ /**
+ * Returns the process message based on the pameters.
+ * @param processId
+ * @param code
+ * @param msg
+ * @return
+ */
+ protected final String getProcessMessage(String processId, int code, String msg) {
+ switch (code) {
+ case IStatus.ERROR:
+ return processId + TemplateEngineMessages.getString("ProcessRunner.error") + msg; //$NON-NLS-1$
+ case IStatus.OK:
+ return processId + TemplateEngineMessages.getString("ProcessRunner.success") + msg; //$NON-NLS-1$
+ default:
+ return processId + TemplateEngineMessages.getString("ProcessRunner.info") + msg; //$NON-NLS-1$
+ }
+ }
+
+ /**
+ * @param template
+ * @param args
+ * @param processId
+ * @throws ProcessFailureException
+ */
+ public abstract void process(TemplateCore template, ProcessArgument[] args, String processId, IProgressMonitor monitor) throws ProcessFailureException;
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessRunnerFactory.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessRunnerFactory.java
new file mode 100644
index 0000000000..fa9c2f4a62
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/ProcessRunnerFactory.java
@@ -0,0 +1,101 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.cdt.core.templateengine.TemplateEngineUtil;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IConfigurationElement;
+import org.eclipse.core.runtime.IExtension;
+import org.eclipse.core.runtime.IExtensionPoint;
+import org.eclipse.core.runtime.Platform;
+
+
+/**
+ * Factory class for creating the Process Runners.
+ */
+public class ProcessRunnerFactory {
+ private static final String EXTENSION_POINT_PROCESSES = CCorePlugin.PLUGIN_ID + ".templateProcessTypes"; //$NON-NLS-1$
+ private static final String ELEM_NAME = "name"; //$NON-NLS-1$
+ private static final String ELEM_PROCESS_RUNNER = "processRunner"; //$NON-NLS-1$
+ private static ProcessRunnerFactory instance;
+
+ static {
+ instance = new ProcessRunnerFactory();
+ }
+
+ private Map/*<String, ProcessRunner>*/ processRunnerMap;
+
+ private ProcessRunnerFactory() {
+ initializeProcessRunners();
+ }
+
+ /**
+ * initializes the process runners.
+ *
+ */
+ private synchronized void initializeProcessRunners() {
+ processRunnerMap = new HashMap/*<String, ProcessRunner>*/();
+ IExtensionPoint point = Platform.getExtensionRegistry().getExtensionPoint(EXTENSION_POINT_PROCESSES);
+ IExtension[] extensions = point.getExtensions();
+ for(int i=0; i<extensions.length; i++) {
+ IExtension extension = extensions[i];
+ String prefix = extension.getNamespaceIdentifier() + "."; //$NON-NLS-1$
+ IConfigurationElement[] configurationElements = extension.getConfigurationElements();
+ for(int j=0; j<configurationElements.length; j++) {
+ IConfigurationElement element = configurationElements[j];
+ String processType = element.getAttribute(ELEM_NAME);
+ if (processType != null) {
+ try {
+ ProcessRunner runner = (ProcessRunner) element.createExecutableExtension(ELEM_PROCESS_RUNNER);
+ List/*<ProcessParameter>*/ params = null;
+ IConfigurationElement[] elementChildren = element.getChildren();
+ for (int k=0; k<elementChildren.length; k++) {
+ if (params == null) {
+ params = new ArrayList/*<ProcessParameter>*/();
+ }
+ params.add(new ProcessParameter(elementChildren[k]));
+ }
+ if (params != null) {
+ runner.setProcessParameters((ProcessParameter[])params.toArray(new ProcessParameter[params.size()]));
+ }
+ processRunnerMap.put(prefix + processType, runner);
+ } catch (CoreException e) {
+ TemplateEngineUtil.log(e);
+// TemplateEngine.showError(e.getMessage(), e);
+ }
+ }
+ }
+ }
+ }
+
+ /**
+ * Process Runners Factory instace.
+ * @return
+ */
+ public static ProcessRunnerFactory getDefault() {
+ return instance;
+ }
+
+ /**
+ * Return the ProcessRunner based on the ProcessType.
+ * @param processType
+ * @return
+ */
+ public ProcessRunner getProcessRunner(String processType) {
+ return (ProcessRunner) processRunnerMap.get(processType);
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/TemplateProcessHandler.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/TemplateProcessHandler.java
new file mode 100644
index 0000000000..eab75afe3c
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/TemplateProcessHandler.java
@@ -0,0 +1,92 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process;
+
+import java.util.ArrayList;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Set;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateDescriptor;
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+import org.w3c.dom.Element;
+
+
+/**
+ * Class handles the Template processes
+ */
+public class TemplateProcessHandler {
+
+ private TemplateCore template;
+ private List/*<ConditionalProcessGroup>*/ conditionalProcessGroupList;
+
+ public TemplateProcessHandler(TemplateCore template) {
+ this.template = template;
+ initialize();
+ }
+
+ /**
+ * initializes the template descriptor and Root Elements.
+ *
+ */
+ private void initialize() {
+ TemplateDescriptor desc = template.getTemplateDescriptor();
+ Element root = desc.getRootElement();
+ conditionalProcessGroupList = new ArrayList/*<ConditionalProcessGroup>*/();
+ List/*<Element>*/ nodeList = TemplateEngine.getChildrenOfElementByTag(root, TemplateDescriptor.IF);
+ for (int j = 0, l = nodeList.size(); j < l; j++) {
+ conditionalProcessGroupList.add(new ConditionalProcessGroup(template, (Element) nodeList.get(j), j + 1));
+ }
+ //Collect all free-hanging processes in one ConditionalProcessGroup object with condition true.
+ nodeList = TemplateEngine.getChildrenOfElementByTag(root, TemplateDescriptor.PROCESS);
+ conditionalProcessGroupList.add(new ConditionalProcessGroup(template, (Element[]) nodeList.toArray(new Element[nodeList.size()])));
+ }
+
+ /**
+ *
+ * @param monitor
+ * @return IStatus, as an array of status info
+ * @throws ProcessFailureException
+ */
+ public IStatus[] processAll(IProgressMonitor monitor) throws ProcessFailureException {
+ List/*<IStatus>*/ allStatuses = new ArrayList/*<IStatus>*/();
+ for (Iterator i = conditionalProcessGroupList.iterator(); i.hasNext();) {
+ try {
+ allStatuses.addAll(((ConditionalProcessGroup)i.next()).process(monitor));
+ } catch (ProcessFailureException e) {
+ throw new ProcessFailureException(e.getMessage(), e, allStatuses);
+ }
+ }
+ return (IStatus[]) allStatuses.toArray(new IStatus[allStatuses.size()]);
+ }
+
+ /**
+ * Returns all macros
+ * @return
+ */
+ public Set/*<String>*/ getAllMacros() {
+ Set/*<String>*/ set = null;
+ for (Iterator i = conditionalProcessGroupList.iterator(); i.hasNext();) {
+ Set/*<String>*/ subSet = ((ConditionalProcessGroup)i.next()).getAllMacros();
+ if (subSet != null) {
+ if (set == null) {
+ set = new HashSet/*<String>*/();
+ }
+ set.addAll(subSet);
+ }
+ }
+ return set;
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AddFile.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AddFile.java
new file mode 100644
index 0000000000..245867027b
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AddFile.java
@@ -0,0 +1,90 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process.processes;
+
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.URL;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateEngineHelper;
+import org.eclipse.cdt.core.templateengine.process.ProcessArgument;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.core.templateengine.process.ProcessHelper;
+import org.eclipse.cdt.core.templateengine.process.ProcessRunner;
+import org.eclipse.core.resources.IFile;
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.resources.IResource;
+import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+
+
+/**
+ * Adds File to the project
+ */
+public class AddFile extends ProcessRunner {
+
+ /**
+ * This method Adds the File to the corresponding Project.
+ */
+ public void process(TemplateCore template, ProcessArgument[] args, String processId, IProgressMonitor monitor) throws ProcessFailureException {
+ String projectName = args[0].getSimpleValue();
+ ProcessArgument file = args[1];
+ ProcessArgument[] fileMembers = file.getComplexValue();
+ String fileSourcePath = fileMembers[0].getSimpleValue();
+ String fileTargetPath = fileMembers[1].getSimpleValue();
+ boolean replaceable = fileMembers[2].getSimpleValue().equals("true"); //$NON-NLS-1$
+
+ IProject projectHandle = ResourcesPlugin.getWorkspace().getRoot().getProject(projectName);
+ URL path;
+ try {
+ path = TemplateEngineHelper.getTemplateResourceURLRelativeToTemplate(template, fileSourcePath);
+ if (path == null) {
+ throw new ProcessFailureException(getProcessMessage(processId, IStatus.ERROR, Messages.getString("AddFile.0") + fileSourcePath)); //$NON-NLS-1$
+ }
+ } catch (IOException e1) {
+ throw new ProcessFailureException(getProcessMessage(processId, IStatus.ERROR, Messages.getString("AddFile.1") + fileSourcePath)); //$NON-NLS-1$
+ }
+
+ InputStream contents = null;
+ if (replaceable) {
+ String fileContents;
+ try {
+ fileContents = ProcessHelper.readFromFile(path);
+ } catch (IOException e) {
+ throw new ProcessFailureException(getProcessMessage(processId, IStatus.ERROR, Messages.getString("AddFile.2") + fileSourcePath)); //$NON-NLS-1$
+ }
+ fileContents = ProcessHelper.getValueAfterExpandingMacros(fileContents, ProcessHelper.getReplaceKeys(fileContents), template.getValueStore());
+ contents = new ByteArrayInputStream(fileContents.getBytes());
+ } else {
+ try {
+ contents = path.openStream();
+ } catch (IOException e) {
+ throw new ProcessFailureException(getProcessMessage(processId, IStatus.ERROR, Messages.getString("AddFile.3") + fileSourcePath)); //$NON-NLS-1$
+ }
+ }
+
+ try {
+ IFile iFile = projectHandle.getFile(fileTargetPath);
+ if (!iFile.getParent().exists()) {
+ ProcessHelper.mkdirs(projectHandle, projectHandle.getFolder(iFile.getParent().getProjectRelativePath()));
+ }
+ iFile.create(contents, true, null);
+ iFile.refreshLocal(IResource.DEPTH_ONE, null);
+ projectHandle.refreshLocal(IResource.DEPTH_INFINITE, null);
+ } catch (CoreException e) {
+ throw new ProcessFailureException(getProcessMessage(processId, IStatus.ERROR, Messages.getString("AddFile.4") + e.getMessage()), e); //$NON-NLS-1$
+ }
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AddFiles.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AddFiles.java
new file mode 100644
index 0000000000..bd11bf6026
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AddFiles.java
@@ -0,0 +1,107 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process.processes;
+
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.URL;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateEngineHelper;
+import org.eclipse.cdt.core.templateengine.process.ProcessArgument;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.core.templateengine.process.ProcessHelper;
+import org.eclipse.cdt.core.templateengine.process.ProcessRunner;
+import org.eclipse.core.resources.IFile;
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.resources.IResource;
+import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+
+
+/**
+ * Adds Files to the Project
+ */
+public class AddFiles extends ProcessRunner {
+
+ /**
+ * This method Adds the list of Files to the corresponding Project.
+ */
+ public void process(TemplateCore template, ProcessArgument[] args, String processId, IProgressMonitor monitor) throws ProcessFailureException {
+ String projectName = args[0].getSimpleValue();
+ IProject projectHandle = ResourcesPlugin.getWorkspace().getRoot().getProject(projectName);
+ ProcessArgument[][] files = args[1].getComplexArrayValue();
+ for(int i=0; i<files.length; i++) {
+ ProcessArgument[] file = files[i];
+ String fileSourcePath = file[0].getSimpleValue();
+ String fileTargetPath = file[1].getSimpleValue();
+ boolean replaceable = file[2].getSimpleValue().equals("true"); //$NON-NLS-1$
+
+ URL path;
+ try {
+ path = TemplateEngineHelper.getTemplateResourceURLRelativeToTemplate(template, fileSourcePath);
+ if (path == null) {
+ throw new ProcessFailureException(getProcessMessage(processId, IStatus.ERROR, Messages.getString("AddFiles.1") + fileSourcePath)); //$NON-NLS-1$
+ }
+ } catch (IOException e1) {
+ throw new ProcessFailureException(Messages.getString("AddFiles.2") + fileSourcePath); //$NON-NLS-1$
+ }
+
+ InputStream contents = null;
+ if (replaceable) {
+ String fileContents;
+ try {
+ fileContents = ProcessHelper.readFromFile(path);
+ } catch (IOException e) {
+ throw new ProcessFailureException(Messages.getString("AddFiles.3") + fileSourcePath); //$NON-NLS-1$
+ }
+ fileContents = ProcessHelper.getValueAfterExpandingMacros(fileContents, ProcessHelper.getReplaceKeys(fileContents), template.getValueStore());
+ contents = new ByteArrayInputStream(fileContents.getBytes());
+ } else {
+ try {
+ contents = path.openStream();
+ } catch (IOException e) {
+ throw new ProcessFailureException(getProcessMessage(processId, IStatus.ERROR, Messages.getString("AddFiles.4") + fileSourcePath)); //$NON-NLS-1$
+ }
+ }
+
+ try {
+ IFile iFile = projectHandle.getFile(fileTargetPath);
+ if (!iFile.getParent().exists()) {
+ ProcessHelper.mkdirs(projectHandle, projectHandle.getFolder(iFile.getParent().getProjectRelativePath()));
+ }
+
+ if (iFile.exists()) {
+ // honor the replaceable flag and replace the file contents if the file already exists.
+ if (replaceable) {
+ iFile.setContents(contents, true, true, null);
+ } else {
+ throw new ProcessFailureException(Messages.getString("AddFiles.5")); //$NON-NLS-1$
+ }
+
+ } else {
+ iFile.create(contents, true, null);
+ iFile.refreshLocal(IResource.DEPTH_ONE, null);
+ }
+ } catch (CoreException e) {
+ throw new ProcessFailureException(Messages.getString("AddFiles.6") + e.getMessage(), e); //$NON-NLS-1$
+ }
+ }
+ try {
+ projectHandle.refreshLocal(IResource.DEPTH_INFINITE, null);
+ } catch (CoreException e) {
+ throw new ProcessFailureException(Messages.getString("AddFiles.7") + e.getMessage(), e); //$NON-NLS-1$
+ }
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AddLink.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AddLink.java
new file mode 100644
index 0000000000..930bfe6545
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AddLink.java
@@ -0,0 +1,58 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process.processes;
+
+import java.io.File;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.process.ProcessArgument;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.core.templateengine.process.ProcessHelper;
+import org.eclipse.cdt.core.templateengine.process.ProcessRunner;
+import org.eclipse.core.resources.IFile;
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.resources.IResource;
+import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.Path;
+
+
+/**
+ * Adds a Link to the Project.
+ */
+public class AddLink extends ProcessRunner {
+
+ /**
+ * This method Adds a Link to the Project.
+ */
+ public void process(TemplateCore template, ProcessArgument[] args, String processId, IProgressMonitor monitor) throws ProcessFailureException {
+ String projectName = args[0].getSimpleValue();
+ String fileSourcePath = args[1].getSimpleValue();
+ String targetPath = args[2].getSimpleValue();
+
+ File sourceFile = new java.io.File(fileSourcePath);
+
+ IProject projectHandle = ResourcesPlugin.getWorkspace().getRoot().getProject(projectName);
+
+ try {
+ IFile file = projectHandle.getFile(targetPath);
+ if (!file.getParent().exists()) {
+ ProcessHelper.mkdirs(projectHandle, projectHandle.getFolder(file.getParent().getProjectRelativePath()));
+ }
+ file.createLink(Path.fromOSString(sourceFile.getAbsolutePath()), IResource.ALLOW_MISSING_LOCAL | IResource.BACKGROUND_REFRESH, null);
+ file.refreshLocal(IResource.DEPTH_ONE, null);
+ projectHandle.refreshLocal(IResource.DEPTH_INFINITE, null);
+ } catch (CoreException e) {
+ throw new ProcessFailureException(Messages.getString("AddLink.0") + e.getMessage(), e); //$NON-NLS-1$
+ }
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/Append.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/Append.java
new file mode 100644
index 0000000000..5577b702a2
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/Append.java
@@ -0,0 +1,67 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process.processes;
+
+import java.io.File;
+import java.io.IOException;
+import java.net.URL;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateEngineHelper;
+import org.eclipse.cdt.core.templateengine.process.ProcessArgument;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.core.templateengine.process.ProcessHelper;
+import org.eclipse.cdt.core.templateengine.process.ProcessRunner;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+
+
+/**
+ * Append the contents to the file.
+ */
+public class Append extends ProcessRunner {
+
+ /**
+ * This method Appends the contents to a file.
+ */
+ public void process(TemplateCore template, ProcessArgument[] args, String processId, IProgressMonitor monitor) throws ProcessFailureException {
+ ProcessArgument[][] files = args[0].getComplexArrayValue();
+ for(int i=0; i<files.length; i++) {
+ ProcessArgument[] file = files[i];
+ String sourcePath = file[0].getSimpleValue();
+ URL sourceURL;
+ try {
+ sourceURL = TemplateEngineHelper.getTemplateResourceURLRelativeToTemplate(template, sourcePath);
+ if (sourceURL == null) {
+ throw new ProcessFailureException(getProcessMessage(processId, IStatus.ERROR, Messages.getString("Append.0") + sourcePath)); //$NON-NLS-1$
+ }
+ } catch (IOException e1) {
+ throw new ProcessFailureException(Messages.getString("Append.1") + sourcePath); //$NON-NLS-1$
+ }
+ File targetFile = new File(file[1].getSimpleValue());
+ boolean replaceable = file[2].getSimpleValue().equals("true"); //$NON-NLS-1$
+ String fileContents;
+ try {
+ fileContents = ProcessHelper.readFromFile(sourceURL);
+ } catch (IOException e1) {
+ throw new ProcessFailureException(Messages.getString("Append.3") + sourcePath); //$NON-NLS-1$
+ }
+ if (replaceable) {
+ fileContents = ProcessHelper.getValueAfterExpandingMacros(fileContents, ProcessHelper.getReplaceKeys(fileContents), template.getValueStore());
+ }
+ try {
+ ProcessHelper.appendFile(fileContents, targetFile);
+ } catch (IOException e) {
+ throw new ProcessFailureException(Messages.getString("Append.4"), e); //$NON-NLS-1$
+ }
+ }
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AppendCreate.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AppendCreate.java
new file mode 100644
index 0000000000..63e49f1e95
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/AppendCreate.java
@@ -0,0 +1,89 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process.processes;
+
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.URL;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateEngineHelper;
+import org.eclipse.cdt.core.templateengine.process.ProcessArgument;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.core.templateengine.process.ProcessHelper;
+import org.eclipse.cdt.core.templateengine.process.ProcessRunner;
+import org.eclipse.core.resources.IFile;
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.resources.IResource;
+import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+
+
+/*
+ * Appends a file to an existing file if present. If not, create the file
+ */
+public class AppendCreate extends ProcessRunner {
+ public void process(TemplateCore template, ProcessArgument[] args, String processId, IProgressMonitor monitor) throws ProcessFailureException {
+ String projectName = args[0].getSimpleValue();
+ IProject projectHandle = ResourcesPlugin.getWorkspace().getRoot().getProject(projectName);
+ ProcessArgument[][] files = args[1].getComplexArrayValue();
+ for(int i=0; i<files.length; i++) {
+ ProcessArgument[] file = files[i];
+ String sourcePath = file[0].getSimpleValue();
+ String targetPath = file[1].getSimpleValue();
+ boolean replaceable = file[2].getSimpleValue().equals("true"); //$NON-NLS-1$
+
+ URL sourceURL;
+ try {
+ sourceURL = TemplateEngineHelper.getTemplateResourceURLRelativeToTemplate(template, sourcePath);
+ if (sourceURL == null) {
+ throw new ProcessFailureException(getProcessMessage(processId, IStatus.ERROR, Messages.getString("AppendCreate.1") + sourcePath)); //$NON-NLS-1$
+ }
+ } catch (IOException e1) {
+ throw new ProcessFailureException(Messages.getString("AppendCreate.2") + sourcePath); //$NON-NLS-1$
+ }
+ String fileContents;
+ try {
+ fileContents = ProcessHelper.readFromFile(sourceURL);
+ } catch (IOException e1) {
+ throw new ProcessFailureException(Messages.getString("AppendCreate.3") + sourcePath); //$NON-NLS-1$
+ }
+ if (replaceable) {
+ fileContents = ProcessHelper.getValueAfterExpandingMacros(fileContents, ProcessHelper.getReplaceKeys(fileContents), template.getValueStore());
+ }
+ try {
+ // Check whether the file exists
+ IFile iFile = projectHandle.getFile(targetPath);
+ if (!iFile.getParent().exists()) {
+ ProcessHelper.mkdirs(projectHandle, projectHandle.getFolder(iFile.getParent().getProjectRelativePath()));
+ }
+ InputStream contents = new ByteArrayInputStream(fileContents.getBytes());;
+ if (!iFile.exists()) {
+ // Create the file
+ iFile.create(contents, true, null);
+ iFile.refreshLocal(IResource.DEPTH_ONE, null);
+
+ } else {
+ // Append the file keeping the history
+ iFile.appendContents(contents, true, true, null);
+ }
+ // Update the project
+ projectHandle.refreshLocal(IResource.DEPTH_INFINITE, null);
+
+ } catch (CoreException e) {
+ throw new ProcessFailureException(Messages.getString("AppendCreate.4"), e); //$NON-NLS-1$
+ }
+ }
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/Copy.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/Copy.java
new file mode 100644
index 0000000000..be02c089a9
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/Copy.java
@@ -0,0 +1,86 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process.processes;
+
+import java.io.File;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.net.URL;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateEngineHelper;
+import org.eclipse.cdt.core.templateengine.process.ProcessArgument;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.core.templateengine.process.ProcessHelper;
+import org.eclipse.cdt.core.templateengine.process.ProcessRunner;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+
+
+/**
+ * Copies a File to the Project.
+ */
+public class Copy extends ProcessRunner {
+
+ /**
+ * This method Copies a File to the Project.
+ */
+ public void process(TemplateCore template, ProcessArgument[] args, String processId, IProgressMonitor monitor) throws ProcessFailureException {
+ ProcessArgument[][] files = args[0].getComplexArrayValue();
+ for(int i=0; i<files.length; i++) {
+ ProcessArgument[] file = files[i];
+ String sourcePath = file[0].getSimpleValue();
+ URL sourceURL;
+ try {
+ sourceURL = TemplateEngineHelper.getTemplateResourceURLRelativeToTemplate(template, sourcePath);
+ if (sourceURL == null) {
+ throw new ProcessFailureException(getProcessMessage(processId, IStatus.ERROR, Messages.getString("Copy.0") + sourcePath)); //$NON-NLS-1$
+ }
+ } catch (IOException e1) {
+ throw new ProcessFailureException(Messages.getString("Copy.1") + sourcePath); //$NON-NLS-1$
+ }
+ File targetFile = new File(file[1].getSimpleValue());
+ boolean replaceable = file[2].getSimpleValue().equals("true"); //$NON-NLS-1$
+ if (replaceable) {
+ String fileContents;
+ try {
+ fileContents = ProcessHelper.readFromFile(sourceURL);
+ } catch (IOException e1) {
+ throw new ProcessFailureException(Messages.getString("Copy.3") + sourcePath); //$NON-NLS-1$
+ }
+ fileContents = ProcessHelper.getValueAfterExpandingMacros(fileContents, ProcessHelper.getReplaceKeys(fileContents), template.getValueStore());
+ if (!targetFile.getParentFile().exists()) {
+ targetFile.getParentFile().mkdirs();
+ }
+ FileWriter writer = null;
+ try {
+ writer = new FileWriter(targetFile);
+ writer.write(fileContents);
+ } catch (IOException e) {
+ throw new ProcessFailureException(Messages.getString("Copy.4"), e); //$NON-NLS-1$
+ } finally {
+ if (writer != null) {
+ try {
+ writer.close();
+ } catch (IOException ioe) {// ignore
+ }
+ }
+ }
+ } else {
+ try {
+ ProcessHelper.copyBinaryFile(sourceURL, targetFile);
+ } catch (IOException e) {
+ throw new ProcessFailureException(Messages.getString("Copy.5"), e); //$NON-NLS-1$
+ }
+ }
+ }
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/CreateResourceIdentifier.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/CreateResourceIdentifier.java
new file mode 100644
index 0000000000..65046b5857
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/CreateResourceIdentifier.java
@@ -0,0 +1,42 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process.processes;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.process.ProcessArgument;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.core.templateengine.process.ProcessRunner;
+import org.eclipse.core.runtime.IProgressMonitor;
+
+
+/**
+ * Creates a template macro value that can be used as a pseudo-unique resource identifier.
+ * It is based on the name of the application and is in the form of four capital letters.
+ * e.g. Helloworld => HELL
+ */
+public class CreateResourceIdentifier extends ProcessRunner {
+
+ public void process(TemplateCore template, ProcessArgument[] args, String processId, IProgressMonitor monitor) throws ProcessFailureException {
+ String valueName = args[0].getSimpleValue();
+ String appName = args[1].getSimpleValue();
+
+ String value = ""; //$NON-NLS-1$
+ if (appName.length() >= 4) {
+ value = appName.substring(0, 4).toUpperCase();
+ } else {
+ value = appName.toUpperCase();
+ for (int i=0; i<4-appName.length(); i++) {
+ value = value + "X"; //$NON-NLS-1$
+ }
+ }
+ template.getValueStore().put(valueName, value);
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/CreateSourceFolder.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/CreateSourceFolder.java
new file mode 100644
index 0000000000..bda5d6b94b
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/CreateSourceFolder.java
@@ -0,0 +1,148 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process.processes;
+
+import java.util.ArrayList;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+
+import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.cdt.core.model.CModelException;
+import org.eclipse.cdt.core.model.CoreModel;
+import org.eclipse.cdt.core.model.ICProject;
+import org.eclipse.cdt.core.model.IPathEntry;
+import org.eclipse.cdt.core.settings.model.CSourceEntry;
+import org.eclipse.cdt.core.settings.model.ICConfigurationDescription;
+import org.eclipse.cdt.core.settings.model.ICProjectDescription;
+import org.eclipse.cdt.core.settings.model.ICSourceEntry;
+import org.eclipse.cdt.core.settings.model.WriteAccessException;
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.process.ProcessArgument;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.core.templateengine.process.ProcessRunner;
+import org.eclipse.core.resources.IFolder;
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IPath;
+import org.eclipse.core.runtime.IProgressMonitor;
+
+
+/**
+ * Creates a include Folder to the project.
+ */
+public class CreateSourceFolder extends ProcessRunner {
+
+ public void process(TemplateCore template, ProcessArgument[] args, String processId, IProgressMonitor monitor) throws ProcessFailureException {
+ createSourceFolder(args[0].getSimpleValue(), args[1].getSimpleValue(), monitor);
+ }
+
+ protected void createSourceFolder(String projectName, String targetPath, IProgressMonitor monitor) throws ProcessFailureException {
+ IProject projectHandle = ResourcesPlugin.getWorkspace().getRoot().getProject(projectName);
+
+ if (!projectHandle.exists()) {
+ throw new ProcessFailureException(Messages.getString("CreateSourceFolder.0") + projectName); //$NON-NLS-1$
+ }
+
+ IPath projPath = projectHandle.getFullPath();
+
+ IFolder folder = projectHandle.getFolder(targetPath);
+ if (!folder.exists()) {
+ try {
+ folder.create(true, true, monitor);
+ } catch (CoreException e) {
+ throw new ProcessFailureException(Messages.getString("CreateSourceFolder.1") + e.getMessage(), e); //$NON-NLS-1$
+ }
+ }
+
+ try {
+ ICProject cProject = CoreModel.getDefault().create(projectHandle);
+ if (cProject != null) {
+ if(CCorePlugin.getDefault().isNewStyleProject(cProject.getProject())){
+ //create source folder for new style project
+ createNewStyleProjectFolder(monitor, projectHandle, folder);
+ } else {
+ //create source folder for all other projects
+ createFolder(targetPath, monitor, projPath, cProject);
+ }
+ }
+ } catch (WriteAccessException e) {
+ throw new ProcessFailureException(Messages.getString("CreateSourceFolder.2") + e.getMessage(), e); //$NON-NLS-1$
+ } catch (CoreException e) {
+ throw new ProcessFailureException(Messages.getString("CreateSourceFolder.2") + e.getMessage(), e); //$NON-NLS-1$
+ }
+ }
+
+ /**
+ * @param monitor
+ * @param projectHandle
+ * @param folder
+ * @throws CoreException
+ * @throws WriteAccessException
+ */
+ private void createNewStyleProjectFolder(IProgressMonitor monitor, IProject projectHandle, IFolder folder) throws CoreException, WriteAccessException {
+ ICSourceEntry newEntry = new CSourceEntry(folder, null, 0);
+ ICProjectDescription description = CCorePlugin.getDefault().getProjectDescription(projectHandle);
+
+ ICConfigurationDescription configs[] = description.getConfigurations();
+ for(int i=0; i < configs.length; i++){
+ ICConfigurationDescription config = configs[i];
+ ICSourceEntry[] entries = config.getSourceEntries();
+ Set set = new HashSet();
+ for (int j=0; j < entries.length; j++) {
+ set.add(entries[j]);
+ }
+ set.add(newEntry);
+ config.setSourceEntries((ICSourceEntry[])set.toArray(new ICSourceEntry[set.size()]));
+ }
+
+ CCorePlugin.getDefault().setProjectDescription(projectHandle, description, false, monitor);
+ }
+
+ /**
+ * @param targetPath
+ * @param monitor
+ * @param projPath
+ * @param cProject
+ * @throws CModelException
+ */
+ private void createFolder(String targetPath, IProgressMonitor monitor, IPath projPath, ICProject cProject) throws CModelException {
+ IPathEntry[] entries = cProject.getRawPathEntries();
+ List/*<IPathEntry>*/ newEntries = new ArrayList/*<IPathEntry>*/(entries.length + 1);
+
+ int projectEntryIndex= -1;
+ IPath path = projPath.append(targetPath);
+
+ for (int i = 0; i < entries.length; i++) {
+ IPathEntry curr = entries[i];
+ if (path.equals(curr.getPath())) {
+ // just return if this folder exists already
+ return;
+ }
+ if (projPath.equals(curr.getPath())) {
+ projectEntryIndex = i;
+ }
+ newEntries.add(curr);
+ }
+
+ IPathEntry newEntry = CoreModel.newSourceEntry(path);
+
+ if (projectEntryIndex != -1) {
+ newEntries.set(projectEntryIndex, newEntry);
+ } else {
+ newEntries.add(CoreModel.newSourceEntry(path));
+ }
+
+ cProject.setRawPathEntries((IPathEntry[])newEntries.toArray(new IPathEntry[newEntries.size()]), monitor);
+ }
+
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/Messages.java b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/Messages.java
new file mode 100644
index 0000000000..863aaef9f1
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/Messages.java
@@ -0,0 +1,32 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.core.templateengine.process.processes;
+
+import java.util.MissingResourceException;
+import java.util.ResourceBundle;
+
+public class Messages {
+ private static final String BUNDLE_NAME = "org.eclipse.cdt.core.templateengine.process.processes.messages"; //$NON-NLS-1$
+
+ private static final ResourceBundle RESOURCE_BUNDLE = ResourceBundle
+ .getBundle(BUNDLE_NAME);
+
+ private Messages() {
+ }
+
+ public static String getString(String key) {
+ try {
+ return RESOURCE_BUNDLE.getString(key);
+ } catch (MissingResourceException e) {
+ return '!' + key + '!';
+ }
+ }
+}
diff --git a/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/messages.properties b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/messages.properties
new file mode 100644
index 0000000000..833b13cab3
--- /dev/null
+++ b/core/org.eclipse.cdt.core/templateengine/org/eclipse/cdt/core/templateengine/process/processes/messages.properties
@@ -0,0 +1,58 @@
+###############################################################################
+# Copyright (c) 2007 Symbian Software Limited and others.
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Eclipse Public License v1.0
+# which accompanies this distribution, and is available at
+# http://www.eclipse.org/legal/epl-v10.html
+#
+# Contributors:
+# Bala Torati (Symbian) - Initial API and implementation
+###############################################################################
+
+AddFiles.1=Add File failure: template source not found:
+AddFiles.2=Add Files failure: template source not found:
+AddFiles.3=Add Files failure: cannot read template source:
+AddFiles.4=Add File failure: cannot read template source:
+AddFiles.5=Add Files failure: File already exists.
+AddFiles.6=Add Files failure:
+AddFiles.7=Add Files failure:
+AddFile.0=Add File failure: template source not found:
+AddFile.1=Add File failure: template source not found:
+AddFile.2=Add File failure: cannot read template source:
+AddFile.3=Add File failure: cannot read template source:
+AddFile.4=Add File failure:
+AddLink.0=Add Link failure:
+SetMBSBooleanOptionValue.0=SetMBSBooleanOptionValue failure:
+SetMBSBooleanOptionValue.3=SetMBSBooleanOptionValue failure: No such file exists:
+SetMBSStringOptionValue.0=SetMBSStringOptionValue failure:
+SetMBSStringOptionValue.3=SetMBSStringOptionValue failure: No such file exists:
+SetMBSStringListOptionValues.0=SetMBSStringListOptionValues failure:
+SetMBSStringListOptionValues.3=SetMBSStringListOptionValues failure: No such file exists:
+NewManagedProject.3=New Project failure:
+NewManagedProject.4=New Project failure:
+NewManagedProject.5=New Project failure: project already existing in work space:
+AppendCreate.1=Add File failure: template source not found:
+AppendCreate.2=Append failure: template source not found:
+AppendCreate.3=Append failure: cannot read template source:
+AppendCreate.4=Append failure: failed while trying to append contents.
+AppendToMBSStringOptionValue.0=AppendToMBSStringOptionValue failure:
+AppendToMBSStringOptionValue.3=AppendToMBSStringOptionValue failure: No such file exists:
+AppendToMBSStringListOptionValues.0=AppendToMBSStringListOptionValues failure:
+AppendToMBSStringListOptionValues.3=AppendToMBSStringListOptionValues failure: No such file exists:
+CreateSourceFolder.0=Create Source Folder failure: project does not exist:
+CreateSourceFolder.1=Create Source Folder failure:
+CreateSourceFolder.2=Create Source Folder failure:
+CreateIncludeFolder.3=Create Include Folder failure: while setting include path:
+ExcludeResources.0=ExcludeResources can only process CDT Managed projects
+Copy.0=Add File failure: template source not found:
+Copy.1=Copy failure: template source not found:
+Copy.3=Copy failure: cannot read template source:
+Copy.4=Copy failure: failed while copying contents.
+Copy.5=Copy failure: failed while copying contents.
+NewProject.7=New Project failure:
+NewProject.8=New Project failure:
+NewProject.9=New Project failure: project already existing in work space:
+Append.0=Add File failure: template source not found:
+Append.1=Copy failure: template source not found:
+Append.3=Copy failure: cannot read template source:
+Append.4=Append failure: failed while trying to append contents.
diff --git a/core/org.eclipse.cdt.ui/.classpath b/core/org.eclipse.cdt.ui/.classpath
index fcd0420f98..07ee51f5d6 100644
--- a/core/org.eclipse.cdt.ui/.classpath
+++ b/core/org.eclipse.cdt.ui/.classpath
@@ -3,6 +3,7 @@
<classpathentry kind="src" path="src"/>
<classpathentry kind="src" path="utils.ui"/>
<classpathentry kind="src" path="browser"/>
+ <classpathentry kind="src" path="templateengine"/>
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/J2SE-1.4"/>
<classpathentry kind="con" path="org.eclipse.pde.core.requiredPlugins"/>
<classpathentry kind="output" path="bin"/>
diff --git a/core/org.eclipse.cdt.ui/META-INF/MANIFEST.MF b/core/org.eclipse.cdt.ui/META-INF/MANIFEST.MF
index 32dd343f44..700c693797 100644
--- a/core/org.eclipse.cdt.ui/META-INF/MANIFEST.MF
+++ b/core/org.eclipse.cdt.ui/META-INF/MANIFEST.MF
@@ -47,14 +47,19 @@ Export-Package: org.eclipse.cdt.internal.corext;x-internal:=true,
org.eclipse.cdt.ui.actions,
org.eclipse.cdt.ui.browser.typeinfo,
org.eclipse.cdt.ui.dialogs,
+ org.eclipse.cdt.ui.newui,
+ org.eclipse.cdt.ui.templateengine,
+ org.eclipse.cdt.ui.templateengine.event,
+ org.eclipse.cdt.ui.templateengine.pages,
+ org.eclipse.cdt.ui.templateengine.uitree,
+ org.eclipse.cdt.ui.templateengine.uitree.uiwidgets,
org.eclipse.cdt.ui.text,
org.eclipse.cdt.ui.text.c.hover,
org.eclipse.cdt.ui.text.contentassist,
org.eclipse.cdt.ui.text.folding,
org.eclipse.cdt.ui.wizards,
org.eclipse.cdt.ui.wizards.conversion,
- org.eclipse.cdt.utils.ui.controls,
- org.eclipse.cdt.ui.newui
+ org.eclipse.cdt.utils.ui.controls
Require-Bundle: org.eclipse.ui.ide;bundle-version="[3.3.0,4.0.0)",
org.eclipse.ui.views;bundle-version="[3.2.0,4.0.0)",
org.eclipse.jface.text;bundle-version="[3.3.0,4.0.0)",
diff --git a/core/org.eclipse.cdt.ui/build.properties b/core/org.eclipse.cdt.ui/build.properties
index 5330a7b67f..bbfa9e58c7 100644
--- a/core/org.eclipse.cdt.ui/build.properties
+++ b/core/org.eclipse.cdt.ui/build.properties
@@ -1,5 +1,5 @@
###############################################################################
-# Copyright (c) 2003, 2006 IBM Corporation and others.
+# Copyright (c) 2003, 2007 IBM Corporation and others.
# All rights reserved. This program and the accompanying materials
# are made available under the terms of the Eclipse Public License v1.0
# which accompanies this distribution, and is available at
@@ -24,7 +24,8 @@ javadoc.packages = org.eclipse.cdt.ui.*,\
source.. = src/,\
browser/,\
- utils.ui/
+ utils.ui/,\
+ templateengine/
jre.compilation.profile=J2SE-1.4
javacSource=1.4
diff --git a/core/org.eclipse.cdt.ui/icons/dlcl16/list-add.gif b/core/org.eclipse.cdt.ui/icons/dlcl16/list-add.gif
new file mode 100644
index 0000000000..5ee82b45c2
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/icons/dlcl16/list-add.gif
Binary files differ
diff --git a/core/org.eclipse.cdt.ui/icons/dlcl16/list-delete.gif b/core/org.eclipse.cdt.ui/icons/dlcl16/list-delete.gif
new file mode 100644
index 0000000000..5fd7e2d44e
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/icons/dlcl16/list-delete.gif
Binary files differ
diff --git a/core/org.eclipse.cdt.ui/icons/dlcl16/list-edit.gif b/core/org.eclipse.cdt.ui/icons/dlcl16/list-edit.gif
new file mode 100644
index 0000000000..3718972851
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/icons/dlcl16/list-edit.gif
Binary files differ
diff --git a/core/org.eclipse.cdt.ui/icons/dlcl16/list-movedown.gif b/core/org.eclipse.cdt.ui/icons/dlcl16/list-movedown.gif
new file mode 100644
index 0000000000..d2866389ea
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/icons/dlcl16/list-movedown.gif
Binary files differ
diff --git a/core/org.eclipse.cdt.ui/icons/dlcl16/list-moveup.gif b/core/org.eclipse.cdt.ui/icons/dlcl16/list-moveup.gif
new file mode 100644
index 0000000000..f8440c8161
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/icons/dlcl16/list-moveup.gif
Binary files differ
diff --git a/core/org.eclipse.cdt.ui/icons/elcl16/list-add.gif b/core/org.eclipse.cdt.ui/icons/elcl16/list-add.gif
new file mode 100644
index 0000000000..45c0e60778
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/icons/elcl16/list-add.gif
Binary files differ
diff --git a/core/org.eclipse.cdt.ui/icons/elcl16/list-delete.gif b/core/org.eclipse.cdt.ui/icons/elcl16/list-delete.gif
new file mode 100644
index 0000000000..af59a0b19a
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/icons/elcl16/list-delete.gif
Binary files differ
diff --git a/core/org.eclipse.cdt.ui/icons/elcl16/list-edit.gif b/core/org.eclipse.cdt.ui/icons/elcl16/list-edit.gif
new file mode 100644
index 0000000000..d1aa86cdf6
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/icons/elcl16/list-edit.gif
Binary files differ
diff --git a/core/org.eclipse.cdt.ui/icons/elcl16/list-movedown.gif b/core/org.eclipse.cdt.ui/icons/elcl16/list-movedown.gif
new file mode 100644
index 0000000000..572933eec5
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/icons/elcl16/list-movedown.gif
Binary files differ
diff --git a/core/org.eclipse.cdt.ui/icons/elcl16/list-moveup.gif b/core/org.eclipse.cdt.ui/icons/elcl16/list-moveup.gif
new file mode 100644
index 0000000000..768c5c1711
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/icons/elcl16/list-moveup.gif
Binary files differ
diff --git a/core/org.eclipse.cdt.ui/plugin.properties b/core/org.eclipse.cdt.ui/plugin.properties
index 18654b1448..193d2ddf88 100644
--- a/core/org.eclipse.cdt.ui/plugin.properties
+++ b/core/org.eclipse.cdt.ui/plugin.properties
@@ -411,3 +411,5 @@ CPPproject.desc=Create a new C++ project
Cproject=C project
Cproject.desc=Create a new C project
+TemplatePreferencePage.name=Template Default Values
+Template.Engine.Wizard=template entries contributor
diff --git a/core/org.eclipse.cdt.ui/plugin.xml b/core/org.eclipse.cdt.ui/plugin.xml
index d146dddb69..8a4f64bf81 100644
--- a/core/org.eclipse.cdt.ui/plugin.xml
+++ b/core/org.eclipse.cdt.ui/plugin.xml
@@ -2131,5 +2131,31 @@
name="%exportWizard.CDTCategory.name">
</category>
</extension>
+
+ <extension
+ point="org.eclipse.ui.perspectiveExtensions">
+ <perspectiveExtension
+ targetID="org.eclipse.ui.resourcePerspective">
+ </perspectiveExtension>
+ </extension>
+
+ <extension
+ point="org.eclipse.ui.preferencePages">
+ <page
+ class="org.eclipse.cdt.ui.templateengine.pages.TemplatePreferencePage"
+ name="%TemplatePreferencePage.name"
+ category="org.eclipse.cdt.ui.preferences.CPluginPreferencePage"
+ id="org.eclipse.cdt.core.templateengine.shareddefaults"/>
+ </extension>
+
+ <extension
+ id="TemplateEngineWizard"
+ name="%Template.Engine.Wizard"
+ point="org.eclipse.cdt.ui.CDTWizard">
+ <wizard
+ class="org.eclipse.cdt.ui.internal.templateengine.wizard.TemplateCNewWizard"
+ name="%Template.Wizard">
+ </wizard>
+ </extension>
</plugin>
diff --git a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/CDTUIImages.java b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/CDTUIImages.java
new file mode 100644
index 0000000000..b443627096
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/CDTUIImages.java
@@ -0,0 +1,84 @@
+/*******************************************************************************
+ * Copyright (c) 2002, 2007 Rational Software Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * IBM Rational Software - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui;
+
+
+import java.net.MalformedURLException;
+import java.net.URL;
+
+import org.eclipse.core.runtime.Platform;
+import org.eclipse.jface.resource.ImageDescriptor;
+import org.eclipse.jface.resource.ImageRegistry;
+import org.eclipse.swt.graphics.Image;
+
+
+/**
+ * Bundle of all images used by the C plugin.
+ */
+public class CDTUIImages {
+
+ // The plugin registry
+ private static ImageRegistry imageRegistry = new ImageRegistry();
+
+ // Subdirectory (under the package containing this class) where 16 color images are
+ private static URL iconBaseURL = null;
+ static {
+ iconBaseURL = Platform.getBundle(CUIPlugin.PLUGIN_ID).getEntry("icons/"); //$NON-NLS-1$
+ }
+
+ private static final String NAME_PREFIX= CUIPlugin.PLUGIN_ID + '.';
+ private static final int NAME_PREFIX_LENGTH= NAME_PREFIX.length();
+ public static final String T_LIST= "elcl16/"; //$NON-NLS-1$
+
+ // Image for file list control
+ public static final String IMG_FILELIST_ADD = NAME_PREFIX + "list-add.gif"; //$NON-NLS-1$
+ public static final ImageDescriptor DESC_FILELIST_ADD = createManaged(T_LIST, IMG_FILELIST_ADD);
+ public static final String IMG_FILELIST_DEL = NAME_PREFIX + "list-delete.gif"; //$NON-NLS-1$
+ public static final ImageDescriptor DESC_FILELIST_DEL = createManaged(T_LIST, IMG_FILELIST_DEL);
+ public static final String IMG_FILELIST_EDIT = NAME_PREFIX + "list-edit.gif"; //$NON-NLS-1$
+ public static final ImageDescriptor DESC_FILELIST_EDIT = createManaged(T_LIST, IMG_FILELIST_EDIT);
+ public static final String IMG_FILELIST_MOVEUP = NAME_PREFIX + "list-moveup.gif"; //$NON-NLS-1$
+ public static final ImageDescriptor DESC_FILELIST_MOVEUP = createManaged(T_LIST, IMG_FILELIST_MOVEUP);
+ public static final String IMG_FILELIST_MOVEDOWN = NAME_PREFIX + "list-movedown.gif"; //$NON-NLS-1$
+ public static final ImageDescriptor DESC_FILELIST_MOVEDOWN = createManaged(T_LIST, IMG_FILELIST_MOVEDOWN);
+
+ private static ImageDescriptor createManaged(String prefix, String name) {
+ return createManaged(imageRegistry, prefix, name);
+ }
+
+ private static ImageDescriptor createManaged(ImageRegistry registry, String prefix, String name) {
+ ImageDescriptor result= ImageDescriptor.createFromURL(makeIconFileURL(prefix, name.substring(NAME_PREFIX_LENGTH)));
+ registry.put(name, result);
+ return result;
+ }
+
+ public static Image get(String key) {
+ return imageRegistry.get(key);
+ }
+
+ private static URL makeIconFileURL(String prefix, String name) {
+ StringBuffer buffer= new StringBuffer(prefix);
+ buffer.append(name);
+ try {
+ return new URL(iconBaseURL, buffer.toString());
+ } catch (MalformedURLException e) {
+ CUIPlugin.getDefault().log(e);
+ return null;
+ }
+ }
+
+ /**
+ * Helper method to access the image registry from the JavaPlugin class.
+ */
+ static ImageRegistry getImageRegistry() {
+ return imageRegistry;
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/CUIPlugin.java b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/CUIPlugin.java
index 65da9f7cff..c91b4ab7c9 100644
--- a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/CUIPlugin.java
+++ b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/CUIPlugin.java
@@ -801,4 +801,17 @@ public class CUIPlugin extends AbstractUIPlugin {
return fASTProvider;
}
+ /**
+ * Answers the <code>Shell</code> associated with the active workbench, or
+ * one of the windows associated with the workbench.
+ */
+ public Shell getShell() {
+ if (getActiveWorkbenchShell() != null) {
+ return getActiveWorkbenchShell();
+ } else {
+ IWorkbenchWindow[] windows = getDefault().getWorkbench().getWorkbenchWindows();
+ return windows[0].getShell();
+ }
+ }
+
}
diff --git a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CDTCommonProjectWizard.java b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CDTCommonProjectWizard.java
index 0c79cc5ea9..caef8120e9 100644
--- a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CDTCommonProjectWizard.java
+++ b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CDTCommonProjectWizard.java
@@ -209,6 +209,8 @@ implements IExecutableExtension, IWizardWithMemory
public boolean canFinish() {
if (fMainPage.h_selected != null) {
+ if(!fMainPage.h_selected.canFinich())
+ return false;
String s = fMainPage.h_selected.getErrorMessage();
if (s != null) return false;
}
diff --git a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CDTMainWizardPage.java b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CDTMainWizardPage.java
index 0aa4ba0a8a..887a274c9b 100644
--- a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CDTMainWizardPage.java
+++ b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CDTMainWizardPage.java
@@ -113,7 +113,8 @@ import org.eclipse.cdt.internal.ui.CPluginImages;
createDynamicGroup(composite);
- switchTo(updateData(tree, right, show_sup, CDTMainWizardPage.this, getWizard()));
+ switchTo(updateData(tree, right, show_sup, CDTMainWizardPage.this, getWizard()),
+ getDescriptor());
setPageComplete(validatePage());
// Show description on opening
@@ -159,7 +160,8 @@ import org.eclipse.cdt.internal.ui.CPluginImages;
public void widgetSelected(SelectionEvent e) {
if (h_selected != null)
h_selected.setSupportedOnly(show_sup.getSelection());
- switchTo(updateData(tree, right, show_sup, CDTMainWizardPage.this, getWizard()));
+ switchTo(updateData(tree, right, show_sup, CDTMainWizardPage.this, getWizard()),
+ getDescriptor());
}} );
// restore settings from preferences
@@ -256,7 +258,11 @@ import org.eclipse.cdt.internal.ui.CPluginImages;
if (locationArea.isDefault()) return null;
return new Path(locationArea.getProjectLocation());
}
-
+
+ public String getProjectLocationPath() {
+ return locationArea.getProjectLocation();
+ }
+
/**
* Returns the value of the project name field
* with leading and trailing spaces removed.
@@ -509,24 +515,42 @@ import org.eclipse.cdt.internal.ui.CPluginImages;
}
private void switchTo(ICWizardHandler h, EntryDescriptor ed) {
+
if (h == null) h = ed.getHandler();
+
try {
- if (h != null) h.initialize(ed);
+
+ if (h != null && ed != null) h.initialize(ed);
+
} catch (CoreException e) { h = null; }
- switchTo(h);
- }
- /**
- * @param h - new handler
- */
- private void switchTo(ICWizardHandler h) {
if (h_selected != null) h_selected.handleUnSelection();
+
h_selected = h;
+
if (h == null) return;
+
right_label.setText(h_selected.getHeader());
+
h_selected.handleSelection();
+
h_selected.setSupportedOnly(show_sup.getSelection());
+
}
+
+
+ private EntryDescriptor getDescriptor() {
+
+ TreeItem[] sel = tree.getSelection();
+
+ if (sel == null || sel.length == 0)
+
+ return null;
+
+ return (EntryDescriptor)sel[0].getData(DESC);
+
+ }
+
public void toolChainListChanged(int count) {
setPageComplete(validatePage());
diff --git a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CWizardHandler.java b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CWizardHandler.java
index 9b060db7d7..30ddf1b001 100644
--- a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CWizardHandler.java
+++ b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/CWizardHandler.java
@@ -97,7 +97,8 @@ public class CWizardHandler implements ICWizardHandler {
public void postProcess(IProject proj) {}
public boolean isApplicable(EntryDescriptor data) { return true; }
public void initialize(EntryDescriptor data) throws CoreException {}
-
+ public boolean canFinich() {return true;}
+
public Object clone() {
try {
CWizardHandler clone = (CWizardHandler)super.clone();
diff --git a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/EntryDescriptor.java b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/EntryDescriptor.java
index 815d60e0ec..ef1b0cd515 100644
--- a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/EntryDescriptor.java
+++ b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/EntryDescriptor.java
@@ -12,6 +12,8 @@ package org.eclipse.cdt.ui.wizards;
import org.eclipse.swt.graphics.Image;
+import org.eclipse.cdt.core.settings.model.util.CDataUtil;
+
/**
* This class stores data for each tree item
* in "Project types" tree of New Project Wizard.
@@ -62,7 +64,11 @@ public class EntryDescriptor {
public String getPath() {
return path;
}
-
+
+ public String[] getPathArray() {
+ return CDataUtil.stringToArray(path, "/"); //$NON-NLS-1$
+ }
+
public void setParent(EntryDescriptor p) {
parent = p;
}
diff --git a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/ICWizardHandler.java b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/ICWizardHandler.java
index 9ad9e63a4a..cc55cb3fcf 100644
--- a/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/ICWizardHandler.java
+++ b/core/org.eclipse.cdt.ui/src/org/eclipse/cdt/ui/wizards/ICWizardHandler.java
@@ -103,5 +103,7 @@ public interface ICWizardHandler extends Cloneable {
*/
public void initialize(EntryDescriptor data) throws CoreException;
+ public boolean canFinich();
+
public Object clone();
}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/internal/templateengine/wizard/TemplateCNewWizard.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/internal/templateengine/wizard/TemplateCNewWizard.java
new file mode 100644
index 0000000000..29f4985441
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/internal/templateengine/wizard/TemplateCNewWizard.java
@@ -0,0 +1,54 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Intel Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Intel Corporation - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.internal.templateengine.wizard;
+
+import java.util.ArrayList;
+
+import org.eclipse.jface.wizard.IWizard;
+import org.eclipse.swt.widgets.Composite;
+
+import org.eclipse.cdt.core.templateengine.TemplateInfo;
+import org.eclipse.cdt.ui.templateengine.Template;
+import org.eclipse.cdt.ui.templateengine.TemplateEngineUI;
+import org.eclipse.cdt.ui.wizards.EntryDescriptor;
+import org.eclipse.cdt.ui.wizards.ICNewWizard;
+import org.eclipse.cdt.ui.wizards.IWizardItemsListListener;
+
+/**
+ *
+ */
+public class TemplateCNewWizard implements ICNewWizard {
+ /**
+ * Creates and returns an array of items to be displayed
+ */
+ public EntryDescriptor[] createItems(boolean supportedOnly, IWizard wizard) {
+ Template[] templates = TemplateEngineUI.getDefault().getTemplates();
+ ArrayList items = new ArrayList();
+
+ for (int k=0; k < templates.length; k++) {
+ TemplateInfo templateInfo = templates[k].getTemplateInfo();
+
+ items.add(new EntryDescriptor(templates[k].getTemplateId(),
+ templateInfo.getProjectType(),
+ templates[k].getLabel(),
+ templateInfo.isCategory(),
+ null,
+ null));
+ }
+ return (EntryDescriptor[])items.toArray(new EntryDescriptor[items.size()]);
+ }
+
+ public void setDependentControl(Composite parent,
+ IWizardItemsListListener page) {
+ //nothing to do?
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/FormBrowser.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/FormBrowser.java
new file mode 100644
index 0000000000..f9415e0049
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/FormBrowser.java
@@ -0,0 +1,80 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.events.DisposeEvent;
+import org.eclipse.swt.events.DisposeListener;
+import org.eclipse.swt.layout.FillLayout;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Control;
+import org.eclipse.ui.forms.widgets.FormText;
+import org.eclipse.ui.forms.widgets.FormToolkit;
+import org.eclipse.ui.forms.widgets.ScrolledFormText;
+
+/**
+ * FormBrowser.
+ */
+class FormBrowser {
+ private FormToolkit toolkit;
+ private Composite container;
+ private ScrolledFormText formText;
+ private String text;
+
+ public void createControl(Composite parent) {
+ toolkit = new FormToolkit(parent.getDisplay());
+ int borderStyle = toolkit.getBorderStyle() == SWT.BORDER ? SWT.NULL : SWT.BORDER;
+ container = new Composite(parent, borderStyle);
+ FillLayout flayout = new FillLayout();
+ flayout.marginWidth = 1;
+ flayout.marginHeight = 1;
+ container.setLayout(flayout);
+ formText = new ScrolledFormText(container, SWT.V_SCROLL | SWT.H_SCROLL, false);
+ if (borderStyle == SWT.NULL) {
+ formText.setData(FormToolkit.KEY_DRAW_BORDER, FormToolkit.TREE_BORDER);
+ toolkit.paintBordersFor(container);
+ }
+ FormText ftext = toolkit.createFormText(formText, false);
+ formText.setFormText(ftext);
+ formText.setExpandHorizontal(true);
+ formText.setExpandVertical(true);
+ formText.setBackground(toolkit.getColors().getBackground());
+ formText.setForeground(toolkit.getColors().getForeground());
+ ftext.marginWidth = 2;
+ ftext.marginHeight = 2;
+ ftext.setHyperlinkSettings(toolkit.getHyperlinkGroup());
+ formText.addDisposeListener(new DisposeListener() {
+ public void widgetDisposed(DisposeEvent e) {
+ if (toolkit != null) {
+ toolkit.dispose();
+ toolkit = null;
+ }
+ }
+ });
+ if (text != null) {
+ formText.setText(text);
+ }
+ }
+
+ public Control getControl() {
+ return container;
+ }
+
+ /**
+ * @param text the text to set
+ */
+ public void setText(String text) {
+ this.text = text;
+ if (formText != null) {
+ formText.setText(text);
+ }
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/IPagesAfterTemplateSelectionProvider.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/IPagesAfterTemplateSelectionProvider.java
new file mode 100644
index 0000000000..d43f40148f
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/IPagesAfterTemplateSelectionProvider.java
@@ -0,0 +1,40 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import org.eclipse.jface.viewers.IStructuredSelection;
+import org.eclipse.ui.IWorkbench;
+import org.eclipse.ui.IWorkbenchWizard;
+
+
+public interface IPagesAfterTemplateSelectionProvider {
+
+ /**
+ * Creates pages that will be appended to the pages returned from
+ * TemplatesChoiceWizard.getPagesAfterTemplateSelection()
+ * Parameters are those used to initialize the wizard.
+ * </p>
+ * @param wizard the wizard requesting the pages
+ * @param workbench the current workbench
+ * @param selection the current object selection
+ *
+ * @since 4.0
+ */
+ IWizardDataPage[] createAdditionalPages(IWorkbenchWizard wizard, IWorkbench workbench, IStructuredSelection selection);
+
+ /**
+ * Gets the previously created pages
+ * @param wizard the wizard that requested creation of the pages
+ *
+ * @since 4.0
+ */
+ IWizardDataPage[] getCreatedPages(IWorkbenchWizard wizard);
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/ITemplatesListProvider.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/ITemplatesListProvider.java
new file mode 100644
index 0000000000..8628d92bdc
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/ITemplatesListProvider.java
@@ -0,0 +1,28 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import org.eclipse.jface.viewers.ITreeContentProvider;
+
+/**
+ * ITemplatesListProvider
+ *
+ * @since 4.0
+ */
+public interface ITemplatesListProvider extends ITreeContentProvider {
+
+ Template[] getTemplates();
+
+ String getDescription(Object object);
+
+ boolean showTemplatesInTreeView();
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/IWizardDataPage.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/IWizardDataPage.java
new file mode 100644
index 0000000000..04aac5e5e3
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/IWizardDataPage.java
@@ -0,0 +1,24 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import java.util.Map;
+
+import org.eclipse.jface.wizard.IWizardPage;
+
+/**
+ * IWizardDataPage
+ *
+ * @since 4.0
+ */
+public interface IWizardDataPage extends IWizardPage {
+ Map/*<String, String>*/ getPageData();
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/Messages.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/Messages.java
new file mode 100644
index 0000000000..f79224e291
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/Messages.java
@@ -0,0 +1,32 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import java.util.MissingResourceException;
+import java.util.ResourceBundle;
+
+public class Messages {
+ private static final String BUNDLE_NAME = "org.eclipse.cdt.ui.templateengine.messages"; //$NON-NLS-1$
+
+ private static final ResourceBundle RESOURCE_BUNDLE = ResourceBundle
+ .getBundle(BUNDLE_NAME);
+
+ private Messages() {
+ }
+
+ public static String getString(String key) {
+ try {
+ return RESOURCE_BUNDLE.getString(key);
+ } catch (MissingResourceException e) {
+ return '!' + key + '!';
+ }
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/ProjectSelectionPage.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/ProjectSelectionPage.java
new file mode 100644
index 0000000000..ccab0d912c
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/ProjectSelectionPage.java
@@ -0,0 +1,330 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.resources.IResource;
+import org.eclipse.core.resources.IWorkspaceRoot;
+import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IPath;
+import org.eclipse.core.runtime.Path;
+import org.eclipse.jface.dialogs.Dialog;
+import org.eclipse.jface.viewers.ILabelProvider;
+import org.eclipse.jface.viewers.IStructuredSelection;
+import org.eclipse.jface.window.Window;
+import org.eclipse.jface.wizard.WizardPage;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.events.ModifyEvent;
+import org.eclipse.swt.events.ModifyListener;
+import org.eclipse.swt.events.SelectionEvent;
+import org.eclipse.swt.events.SelectionListener;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Button;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Label;
+import org.eclipse.swt.widgets.Text;
+import org.eclipse.ui.IEditorInput;
+import org.eclipse.ui.IEditorPart;
+import org.eclipse.ui.IWorkbenchPage;
+import org.eclipse.ui.PlatformUI;
+import org.eclipse.ui.dialogs.ElementListSelectionDialog;
+
+import org.eclipse.cdt.core.CCProjectNature;
+import org.eclipse.cdt.core.CProjectNature;
+import org.eclipse.cdt.core.model.CModelException;
+import org.eclipse.cdt.core.model.CoreModel;
+import org.eclipse.cdt.core.model.ICElement;
+import org.eclipse.cdt.core.model.ICProject;
+import org.eclipse.cdt.ui.CElementLabelProvider;
+import org.eclipse.cdt.ui.CUIPlugin;
+
+import org.eclipse.cdt.internal.ui.ICHelpContextIds;
+
+public class ProjectSelectionPage extends WizardPage implements IWizardDataPage {
+
+ private static final String PAGE_NAME= "NewProjectSelectionWizardPage"; //$NON-NLS-1$
+ private static final String PAGE_TITLE = Messages.getString("ProjectSelectionPage.0"); //$NON-NLS-1$
+ private static final String PAGE_DESCRIPTION = Messages.getString("ProjectSelectionPage.1"); //$NON-NLS-1$
+
+ private Label projectNameLabel;
+ private Button projectBrowseButton;
+ private Text projectNameText;
+ private String projectName = ""; //$NON-NLS-1$
+
+ private IWorkspaceRoot workspaceRoot;
+ private ICProject currentCProject;
+
+ public ProjectSelectionPage() {
+ super(PAGE_NAME);
+ setTitle(PAGE_TITLE);
+ setDescription(PAGE_DESCRIPTION);
+
+ workspaceRoot = ResourcesPlugin.getWorkspace().getRoot();
+
+ setPageComplete(false);
+ }
+
+ public void init(IStructuredSelection selection) {
+ if (selection == null || selection.isEmpty()) {
+ setDefaultAttributes();
+ return;
+ }
+
+ Object selectedElement= selection.getFirstElement();
+ if (selectedElement == null) {
+ selectedElement= getActiveEditorCInput();
+ }
+
+ String projPath= null;
+
+ if (selectedElement instanceof IResource) {
+ IProject project= ((IResource)selectedElement).getProject();
+ if (project != null) {
+ projPath= project.getFullPath().makeRelative().toString();
+ }
+ } else if (selectedElement instanceof ICElement) {
+ ICProject cProject= ((ICElement)selectedElement).getCProject();
+ if (cProject != null) {
+ projPath= cProject.getProject().getFullPath().makeRelative().toString();
+ }
+ }
+
+ if (projPath != null) {
+ projectName = projPath;
+ } else {
+ setDefaultAttributes();
+ }
+ }
+
+ /**
+ * If the current active editor edits a c element return it, else
+ * return null
+ */
+ private ICElement getActiveEditorCInput() {
+ IWorkbenchPage page= CUIPlugin.getActivePage();
+ if (page != null) {
+ IEditorPart part= page.getActiveEditor();
+ if (part != null) {
+ IEditorInput editorInput= part.getEditorInput();
+ if (editorInput != null) {
+ return (ICElement)editorInput.getAdapter(ICElement.class);
+ }
+ }
+ }
+ return null;
+ }
+
+ private void setDefaultAttributes() {
+
+ try {
+ // find the first C project
+ IProject[] projects= workspaceRoot.getProjects();
+ for (int i= 0; i < projects.length; i++) {
+ IProject project= projects[i];
+ if (project.hasNature(CProjectNature.C_NATURE_ID) || project.hasNature(CCProjectNature.CC_NATURE_ID)) {
+ projectName = project.getFullPath().makeRelative().toString();
+ break;
+ }
+ }
+ } catch (CoreException e) {
+ // ignore here
+ }
+ }
+
+ private Map data = new HashMap(2);
+
+ public Map getPageData() {
+ String cPojectName = currentCProject.getResource().getName().trim();
+ data.put("projectName", cPojectName); //$NON-NLS-1$
+ data.put("baseName", getBaseName(cPojectName)); //$NON-NLS-1$
+ return data;
+ }
+
+ private String getBaseName(String name) {
+ String baseName = name;
+ int dot = baseName.lastIndexOf('.');
+ if (dot != -1) {
+ baseName = baseName.substring(dot + 1);
+ }
+ dot = baseName.indexOf(' ');
+ if (dot != -1) {
+ baseName = baseName.substring(0, dot);
+ }
+ return baseName;
+ }
+
+ public void createControl(Composite parent) {
+ initializeDialogUnits(parent);
+
+ Composite composite= new Composite(parent, SWT.NONE);
+
+ GridLayout layout= new GridLayout();
+ layout.marginWidth= 0;
+ layout.marginHeight= 0;
+ layout.numColumns= 3;
+ composite.setLayout(layout);
+
+ createProjectFiled(composite);
+
+ setControl(composite);
+ Dialog.applyDialogFont(composite);
+ PlatformUI.getWorkbench().getHelpSystem().setHelp(composite, ICHelpContextIds.NEW_SRCFLDER_WIZARD_PAGE);
+
+ projectNameText.setFocus();
+ projectNameText.setSelection(0, projectNameText.getText().length());
+
+ setPageComplete(validatePage());
+ }
+
+ private void createProjectFiled(Composite parent) {
+ getLabelControl(parent);
+ GridData gdLabel = new GridData(GridData.HORIZONTAL_ALIGN_FILL);
+ gdLabel.horizontalSpan= 1;
+ projectNameLabel.setLayoutData(gdLabel);
+
+
+ getTextControl(parent);
+ GridData gdText = new GridData();
+ gdText.horizontalAlignment= GridData.FILL;
+ gdText.grabExcessHorizontalSpace= true;
+ gdText.horizontalSpan= 1;
+ gdText.widthHint = convertWidthInCharsToPixels(40);
+ projectNameText.setLayoutData(gdText);
+
+ getButtonControl(parent);
+ GridData gdButton = new GridData();
+ gdButton.horizontalAlignment= GridData.FILL;
+ gdButton.grabExcessHorizontalSpace= false;
+ gdButton.horizontalSpan= 1;
+ projectBrowseButton.setLayoutData(gdButton);
+ }
+
+ /**
+ * Creates or returns the created Label control.
+ * @param parent The parent composite
+ */
+ private void getLabelControl(Composite parent) {
+ projectNameLabel = new Label(parent, SWT.LEFT | SWT.WRAP);
+ projectNameLabel.setText(Messages.getString("ProjectSelectionPage.4")); //$NON-NLS-1$
+ projectNameLabel.setFont(parent.getFont());
+ projectNameLabel.setEnabled(true);
+ }
+
+ /**
+ * Creates or returns the created text control.
+ * @param parent The parent composite
+ */
+ private void getTextControl(Composite parent) {
+ projectNameText = new Text(parent, SWT.SINGLE | SWT.BORDER);
+ projectNameText.setText(projectName);
+ projectNameText.setFont(parent.getFont());
+ projectNameText.setEnabled(true);
+ projectNameText.addModifyListener(new ModifyListener() {
+ public void modifyText(ModifyEvent e) {
+ setPageComplete(validatePage());
+ }
+ });
+ }
+
+ /**
+ * Creates or returns the created buttom widget.
+ * @param parent The parent composite
+ */
+ private void getButtonControl(Composite parent) {
+ projectBrowseButton = new Button(parent, SWT.PUSH);
+ projectBrowseButton.setText(Messages.getString("ProjectSelectionPage.5")); //$NON-NLS-1$
+ projectBrowseButton.setFont(parent.getFont());
+ projectBrowseButton.setEnabled(true);
+ projectBrowseButton.addSelectionListener(new SelectionListener() {
+ public void widgetDefaultSelected(SelectionEvent e) {
+ packRootChangeControlPressed();
+ }
+ public void widgetSelected(SelectionEvent e) {
+ packRootChangeControlPressed();
+ }
+ });
+ }
+
+ public void setVisible(boolean visible) {
+ super.setVisible(visible);
+ }
+
+ protected void packRootChangeControlPressed() {
+ ICProject cProject= chooseProject();
+ if (cProject != null) {
+ IPath path= cProject.getProject().getFullPath().makeRelative();
+ projectName = path.toOSString();
+ projectNameText.setText(projectName);
+ }
+ }
+
+ private boolean validatePage() {
+ currentCProject= null;
+
+ String projectName = projectNameText.getText();
+ if (projectName.length() == 0) {
+ setErrorMessage(Messages.getString("ProjectSelectionPage.6")); //$NON-NLS-1$
+ return false;
+ }
+
+ IPath path= new Path(projectName);
+ if (path.segmentCount() != 1) {
+ setErrorMessage(Messages.getString("ProjectSelectionPage.7")); //$NON-NLS-1$
+ return false;
+ }
+
+ IProject project= workspaceRoot.getProject(path.toString());
+ if (!project.exists()) {
+ setErrorMessage(Messages.getString("ProjectSelectionPage.8")); //$NON-NLS-1$
+ return false;
+ }
+
+ try {
+ if (project.hasNature(CProjectNature.C_NATURE_ID) || project.hasNature(CCProjectNature.CC_NATURE_ID)) {
+ currentCProject= CoreModel.getDefault().create(project);
+ setErrorMessage(null);
+ return true;
+ }
+ } catch (CoreException e) {
+ CUIPlugin.getDefault().log(e);
+ currentCProject= null;
+ }
+
+ setErrorMessage(Messages.getString("ProjectSelectionPage.9")); //$NON-NLS-1$
+ return false;
+ }
+
+ private ICProject chooseProject() {
+ ICProject[] projects;
+ try {
+ projects= CoreModel.create(workspaceRoot).getCProjects();
+ } catch (CModelException e) {
+ CUIPlugin.getDefault().log(e);
+ projects= new ICProject[0];
+ }
+
+ ILabelProvider labelProvider= new CElementLabelProvider(CElementLabelProvider.SHOW_DEFAULT);
+ ElementListSelectionDialog dialog= new ElementListSelectionDialog(getShell(), labelProvider);
+ dialog.setTitle(Messages.getString("ProjectSelectionPage.10")); //$NON-NLS-1$
+ dialog.setMessage(Messages.getString("ProjectSelectionPage.11")); //$NON-NLS-1$
+ dialog.setElements(projects);
+ dialog.setInitialSelections(new Object[] { currentCProject });
+ if (dialog.open() == Window.OK) {
+ return (ICProject) dialog.getFirstResult();
+ }
+ return null;
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/SimpleElementException.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/SimpleElementException.java
new file mode 100644
index 0000000000..b13940adbb
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/SimpleElementException.java
@@ -0,0 +1,62 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+
+
+/**
+ * This Exception is thrown when, we execute getNextChild, addToChildList and
+ * getChildCount on an InputUIElement.
+ *
+ * @since 4.0
+ */
+
+public class SimpleElementException extends Exception {
+
+ private static final long serialVersionUID = 0000000000L;
+
+ /**
+ * The description of the exception.
+ */
+ String expDefinition;
+
+ private static final String EXCEPTION_STRING = Messages.getString("SimpleElementException.0"); //$NON-NLS-1$
+
+ /**
+ * Constructor receives description of this instance of event as parameter.
+ * The same is assigned to iExpDefinition.
+ */
+ public SimpleElementException() {
+ super(EXCEPTION_STRING);
+ expDefinition = EXCEPTION_STRING;
+ }
+
+ /**
+ * Constructor receives description of this instance of event as parameter.
+ * The same is assigned to iExpDefinition.
+ *
+ * @param def
+ */
+ public SimpleElementException(String def) {
+ super(def);
+ expDefinition = def;
+ }
+
+ /**
+ * The description of the SimpleElementException is returned.
+ *
+ * @return String
+ */
+ public String toString() {
+ return expDefinition;
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/Template.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/Template.java
new file mode 100644
index 0000000000..fb432e55ca
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/Template.java
@@ -0,0 +1,210 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import java.io.IOException;
+import java.lang.reflect.InvocationTargetException;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import javax.xml.parsers.ParserConfigurationException;
+
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.Status;
+import org.eclipse.jface.wizard.IWizard;
+import org.eclipse.jface.wizard.IWizardPage;
+import org.eclipse.ui.IWorkbenchWizard;
+import org.eclipse.ui.actions.WorkspaceModifyOperation;
+import org.w3c.dom.Element;
+import org.xml.sax.SAXException;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateDescriptor;
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+import org.eclipse.cdt.core.templateengine.TemplateInfo;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.ui.CUIPlugin;
+import org.eclipse.cdt.ui.templateengine.pages.UIPagesProvider;
+import org.eclipse.cdt.ui.templateengine.pages.UIWizardPage;
+import org.eclipse.cdt.ui.templateengine.uitree.UIElementTreeBuilderHelper;
+import org.eclipse.cdt.ui.templateengine.uitree.UIElementTreeBuilderManager;
+
+/**
+ * Template class is responsible for initiating GUI construction. Collecting data from GUI and
+ * initiating process part of Template Engine. This is created per TemplateDescriptor basis.
+ * Once The Template is created it creates a TemplateDescriptor for the XML file name given.
+ *
+ * @since 4.0
+ */
+
+public class Template extends TemplateCore {
+
+ private TemplateDescriptor templateDescriptor;
+ private UIElementTreeBuilderManager uiElementTreeBuilderManager;
+ private UIPagesProvider uiPagesProvider;
+ private Map/*<String, UIWizardPage>*/ pageMap;
+
+ public Template(TemplateInfo templateInfo) throws IOException, ProcessFailureException, SAXException, ParserConfigurationException {
+ super(templateInfo);
+ templateDescriptor = getTemplateDescriptor();
+ uiElementTreeBuilderManager = new UIElementTreeBuilderManager(new UIElementTreeBuilderHelper(templateDescriptor));
+ uiPagesProvider = new UIPagesProvider();
+ }
+
+ /**
+ * 1. get PropertyGroupList.
+ * 2. clear UIPage's display order Vector.
+ * 3. for each PropertyGroup create the UIElementTree.
+ * 4. Request the UIPagesProvider to generate UIPages for the Tree.
+ * 5. return the HashMap of UIPages.
+ */
+ public Map/*<String, UIWizardPage>*/ getUIPages() {
+ if (pageMap == null) {
+ pageMap = new HashMap/*<String, UIWizardPage>*/();
+ List rootPropertyGrouplist = templateDescriptor.getPropertyGroupList();
+
+ uiPagesProvider.clearOrderVector();
+
+ for (int i = 0; i < rootPropertyGrouplist.size(); i++) {
+ // since the tree is constructed for a list of PropertyGroup's tree
+ // root is set to null
+ // before invoking createUIElementTree(...).
+ uiElementTreeBuilderManager.setUIElementTreeRootNull();
+ uiElementTreeBuilderManager.createUIElementTree(null, (Element) rootPropertyGrouplist.get(i));
+ pageMap.putAll(uiPagesProvider.getWizardUIPages(uiElementTreeBuilderManager.getUIElementTreeRoot(), getValueStore()));
+ }
+ }
+
+ return pageMap;
+ }
+
+
+ public IWizardPage[] getTemplateWizardPages(IWizardPage predatingPage, IWizardPage followingPage, IWizard wizard) {
+ List pages= new ArrayList();
+// if (predatingPage != null) {
+// pages.add(predatingPage);
+// }
+
+ Map templatePages = getUIPages();
+ List templatePagesOrderVector = getPagesOrderVector();
+ if (templatePagesOrderVector.size() != 0) {
+ IWizardPage prevPage = predatingPage;
+
+ for (int i=0; i < templatePagesOrderVector.size(); i++) {
+ UIWizardPage page = (UIWizardPage) templatePages.get(templatePagesOrderVector.get(i));
+ pages.add(page);
+ page.setPreviousPage(prevPage);
+ if (i+1 < templatePagesOrderVector.size()) {
+ page.setNextPage((UIWizardPage) templatePages.get(templatePagesOrderVector.get(i+1)));
+ } else {
+ page.setNextPage(followingPage);
+ }
+ page.setWizard(wizard);
+ prevPage = page;
+ }
+
+ try {
+ IWizardDataPage[] extraPages = getExtraCreatedPages((IWorkbenchWizard)wizard);
+ for (int i=0; i < extraPages.length; i++) {
+ IWizardDataPage page = extraPages[i];
+ pages.add(page);
+ page.setPreviousPage(prevPage);
+ //TODO: set the next page for page
+ //page.setNextPage(extraPages[i+1]);
+ page.setWizard(wizard);
+ prevPage = page;
+ }
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+
+ followingPage.setPreviousPage(prevPage);
+ } else {
+ followingPage.setPreviousPage(predatingPage);
+ }
+
+// pages.add(followingPage);
+
+ return (IWizardPage[]) pages.toArray(new IWizardPage[pages.size()]);
+ }
+
+ IWizardDataPage[] getExtraCreatedPages(IWorkbenchWizard wizard) throws InstantiationException, IllegalAccessException, ClassNotFoundException {
+ TemplateInfo templateInfo = getTemplateInfo();
+ String pagesProvider = templateInfo.getExtraPagesProvider();
+ if (pagesProvider != null) {
+ IPagesAfterTemplateSelectionProvider extraPagesProvider = (IPagesAfterTemplateSelectionProvider) Class.forName(pagesProvider).newInstance();
+ if (extraPagesProvider != null) {
+ List/*<IWizardDataPage>*/ pageList = new ArrayList/*<IWizardDataPage>*/();
+ IWizardDataPage[] extraPages = extraPagesProvider.getCreatedPages(wizard);
+ pageList.addAll(Arrays.asList(extraPages));
+ return (IWizardDataPage[]) pageList.toArray(new IWizardDataPage[pageList.size()]);
+ }
+ }
+ return new IWizardDataPage[0];
+ }
+
+
+ /**
+ *
+ * @return List,which contains Page display order
+ */
+
+ public List/*<String>*/ getPagesOrderVector() {
+ return uiPagesProvider.getOrderVector();
+ }
+
+ /**
+ * this method is for JUnit Test case excecution. return the
+ * UIElementTreeBuilderManager instance used by this Template.
+ *
+ * @return UIElementTreeBuilderManager
+ */
+ public UIElementTreeBuilderManager getUIElementTreeBuilderManager() {
+ return uiElementTreeBuilderManager;
+ }
+
+ /**
+ * initializeProcessBlockList() will create the ProcessBlockList,
+ * processPorcessBlockList() will invoke each process execution by assigning
+ * resources to each process (Ref. ProcessResourceManager).
+ * @param monitor
+ */
+ public IStatus[] executeTemplateProcesses(IProgressMonitor monitor, final boolean showError) {
+ setDirty();
+ TemplateEngine.getDefault().updateSharedDefaults(this);
+ final IStatus[][] result = new IStatus[1][];
+ WorkspaceModifyOperation wmo = new WorkspaceModifyOperation() {
+ protected void execute(IProgressMonitor monitor) throws org.eclipse.core.runtime.CoreException ,java.lang.reflect.InvocationTargetException ,InterruptedException {
+ try {
+ result[0] = getProcessHandler().processAll(monitor);
+ } catch (ProcessFailureException e) {
+ if (showError) {
+ TemplateEngineUIUtil.showError(e.getMessage(), e.getCause());
+ }
+ result[0] = new IStatus[] {new Status(IStatus.ERROR, CUIPlugin.getPluginId(), IStatus.ERROR, e.getMessage(), e)};
+ }
+ }
+ };
+ try {
+ wmo.run(monitor); // TODO support progress monitors
+ } catch(InterruptedException ie) {
+ throw new RuntimeException(ie);
+ } catch(InvocationTargetException ite) {
+ throw new RuntimeException(ite.getTargetException());
+ }
+ return result[0];
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateClassWizard.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateClassWizard.java
new file mode 100644
index 0000000000..4428c6182c
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateClassWizard.java
@@ -0,0 +1,132 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Symbian - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import java.util.Arrays;
+import java.util.SortedSet;
+import java.util.TreeSet;
+
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IConfigurationElement;
+import org.eclipse.core.runtime.IExecutableExtension;
+import org.eclipse.jface.viewers.Viewer;
+import org.eclipse.ui.INewWizard;
+import org.eclipse.ui.wizards.newresource.BasicNewProjectResourceWizard;
+
+public class TemplateClassWizard extends TemplatesChoiceWizard implements INewWizard, IExecutableExtension {
+
+ public static final String WIZARD_ID = TemplateClassWizard.class.getName();
+
+ private IWizardDataPage[] pagesBeforeTemplatePages;
+ private IWizardDataPage[] pagesAfterTemplatePages;
+ private IWizardDataPage[] pagesAfterTemplateSelection;
+
+ private ProjectSelectionPage projectSelectionPage;
+
+ private IConfigurationElement configElement;
+
+ public TemplateClassWizard() {
+ super();
+ setWindowTitle(Messages.getString("TemplateClassWizard.0")); //$NON-NLS-1$
+ //TODO: Fix the imagedescriptor later.
+// setDefaultPageImageDescriptor(TemplateEnginePlugin.imageDescriptorFromPlugin(TemplateEnginePlugin.getDefault().getWizardIconPluginID(), TemplateEnginePlugin.getDefault().getWizardIconFile()));
+ }
+
+ public String getListSelectionTitle()
+ {
+ return Messages.getString("TemplateClassWizard.1"); //$NON-NLS-1$
+ }
+
+ public String getListSelectionDescription()
+ {
+ return Messages.getString("TemplateClassWizard.2"); //$NON-NLS-1$
+ }
+
+ public String getListSelectionLabel()
+ {
+ return Messages.getString("TemplateClassWizard.3"); //$NON-NLS-1$
+ }
+
+ protected IWizardDataPage[] getPagesBeforeTemplatePages() {
+ if (pagesBeforeTemplatePages == null) {
+ projectSelectionPage = new ProjectSelectionPage();
+ projectSelectionPage.setTitle(Messages.getString("TemplateClassWizard.4")); //$NON-NLS-1$
+ projectSelectionPage.setDescription(Messages.getString("TemplateClassWizard.5")); //$NON-NLS-1$
+ projectSelectionPage.init(selection);
+ pagesBeforeTemplatePages = new IWizardDataPage[] {projectSelectionPage};
+ }
+ return pagesBeforeTemplatePages;
+ }
+
+ protected IWizardDataPage[] getPagesAfterTemplatePages() {
+ if (pagesAfterTemplatePages == null) {
+ pagesAfterTemplatePages = new IWizardDataPage[] {};
+ }
+ return pagesAfterTemplatePages;
+ }
+
+ public Template[] getTemplates() {
+ SortedSet templateList = new TreeSet(Template.TEMPLATE_ID_CASE_INSENSITIVE_COMPARATOR);
+
+ templateList.addAll(Arrays.asList(TemplateEngineUI.getDefault().getTemplates()));
+
+ return (Template[]) templateList.toArray(new Template[templateList.size()]);
+ }
+
+ public void setInitializationData(IConfigurationElement config, String propertyName, Object data) throws CoreException {
+ configElement = config;
+ }
+
+ public boolean performFinish() {
+ boolean retVal = super.performFinish();
+ BasicNewProjectResourceWizard.updatePerspective(configElement);
+ return retVal;
+ }
+
+ protected IWizardDataPage[] getPagesAfterTemplateSelection() {
+ if (pagesAfterTemplateSelection == null) {
+ pagesAfterTemplateSelection = new IWizardDataPage[] {};
+ }
+ return pagesAfterTemplateSelection;
+ }
+
+ public String getDescription(Object object) {
+ if (object instanceof Template)
+ {
+ return ((Template)object).getDescription();
+ }
+ return ""; //$NON-NLS-1$
+ }
+
+ public boolean showTemplatesInTreeView() {
+ return false;
+ }
+
+ public Object[] getChildren(Object parentElement) {
+ return null;
+ }
+
+ public Object getParent(Object element) {
+ return null;
+ }
+
+ public boolean hasChildren(Object element) {
+ return false;
+ }
+
+ public Object[] getElements(Object inputElement) {
+ return getTemplates();
+ }
+
+ public void inputChanged(Viewer viewer, Object oldInput, Object newInput) {
+
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateDrivenWizard.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateDrivenWizard.java
new file mode 100644
index 0000000000..b41197a221
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateDrivenWizard.java
@@ -0,0 +1,184 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+
+package org.eclipse.cdt.ui.templateengine;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.MultiStatus;
+import org.eclipse.jface.operation.IRunnableWithProgress;
+import org.eclipse.jface.wizard.IWizardPage;
+import org.eclipse.jface.wizard.Wizard;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.ui.actions.WorkspaceModifyDelegatingOperation;
+
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.ui.CUIPlugin;
+
+
+/**
+ * Any wizard intending to use template (@see org.eclipse.cdt.core.templateenginee.Template) based pages
+ * can extend this wizard and use it. Alternatively, a wizard intending to show a choice of templates
+ * should use TemplatesChoiceWizard (@see org.eclipse.cdt.core.templateenginee.ui.TemplatesChoiceWizard)
+ *
+ */
+public abstract class TemplateDrivenWizard extends Wizard {
+ protected List/*<IWizardPage>*/ pagesBeforeTemplatePages = new ArrayList/*<IWizardPage>*/();
+ protected List/*<IWizardPage>*/ pagesAfterTemplatePages = new ArrayList/*<IWizardPage>*/();
+
+ protected Template template;
+ protected int pageIndex;
+ protected Map/*<String, UIWizardPage>*/ templatePages;
+ protected Composite pageContainer;
+ protected List/*<String>*/ templatePagesOrderVector;
+
+ public final void addPage(IWizardPage page) {
+ page.setWizard(this);
+ }
+
+ public final void addPages() {
+ IWizardPage[] pages = getPagesBeforeTemplatePages();
+ for(int i=0; i<pages.length; i++) {
+ addPageBeforeTemplatePages(pages[i]);
+ }
+
+ pages = getPagesAfterTemplatePages();
+ for(int i=0; i<pages.length; i++) {
+ addPageAfterTemplatePages(pages[i]);
+ }
+ }
+
+ private void addPageBeforeTemplatePages(IWizardPage page) {
+ addPage(page);
+ pagesBeforeTemplatePages.add(page);
+ }
+
+ private void addPageAfterTemplatePages(IWizardPage page) {
+ addPage(page);
+ pagesAfterTemplatePages.add(page);
+ }
+
+ protected abstract IWizardPage[] getPagesBeforeTemplatePages();
+
+ protected abstract IWizardPage[] getPagesAfterTemplatePages();
+
+ /**
+ * @return the template
+ */
+ protected abstract Template getTemplate();
+
+ public IWizardPage getPreviousPage(IWizardPage page) {
+ if (pageIndex > pagesBeforeTemplatePages.size() + templatePagesOrderVector.size()) {//current is some page after template pages other than the first post-template page
+ pageIndex--;
+ return (IWizardPage) pagesAfterTemplatePages.get(pageIndex - pagesBeforeTemplatePages.size() - templatePagesOrderVector.size());
+ } else if (pageIndex > pagesBeforeTemplatePages.size()) {//current is some template page other than the first
+ pageIndex--;
+ return (IWizardPage) templatePages.get(templatePagesOrderVector.get(pageIndex - pagesBeforeTemplatePages.size()));
+ } else if (pageIndex > 0) {
+ pageIndex--;
+ return (IWizardPage) pagesBeforeTemplatePages.get(pageIndex);
+ }
+ return null;
+ }
+
+ public IWizardPage getNextPage(IWizardPage page) {
+ if (pageIndex < pagesBeforeTemplatePages.size() - 1) {//current is a page before template pages that is not the final one
+ pageIndex++;
+ return (IWizardPage) pagesBeforeTemplatePages.get(pageIndex);
+ } else if (pageIndex < pagesBeforeTemplatePages.size() + templatePagesOrderVector.size() - 1) {
+ if(pageIndex == pagesBeforeTemplatePages.size() - 1) {//current is final page before template pages
+ Template template = getTemplate();
+ if (this.template != null && !this.template.equals(template)) {//template changed
+ this.template = template;
+ //TODO: dispose old template pages
+ templatePages = template.getUIPages();
+ templatePagesOrderVector = template.getPagesOrderVector();
+ }
+ }//else current is some template page other than the final one
+ pageIndex++;
+ IWizardPage nextPage = (IWizardPage) templatePages.get(templatePagesOrderVector.get(pageIndex - pagesBeforeTemplatePages.size()));
+ nextPage.setWizard(this);
+ if (nextPage.getControl() == null) {
+ nextPage.createControl(pageContainer);
+ }
+ return nextPage;
+ } else if (pageIndex < pagesBeforeTemplatePages.size() + templatePagesOrderVector.size() + pagesAfterTemplatePages.size() - 1) {//current is final template page or a page after the final template page
+ pageIndex++;
+ return (IWizardPage) pagesAfterTemplatePages.get(pageIndex - pagesBeforeTemplatePages.size() - templatePagesOrderVector.size());
+ }
+ return null;
+ }
+
+ public final boolean canFinish() {
+ for(Iterator i = pagesBeforeTemplatePages.iterator(); i.hasNext(); ) {
+ IWizardPage page = (IWizardPage) i.next();
+ if (!page.isPageComplete()) {
+ return false;
+ }
+ }
+ if (templatePages == null) {
+ return false;
+ }
+ for(Iterator i = templatePages.values().iterator(); i.hasNext(); ) {
+ IWizardPage page = (IWizardPage) i.next();
+ if (!page.isPageComplete()) {
+ return false;
+ }
+ }
+ for(Iterator i = pagesAfterTemplatePages.iterator(); i.hasNext(); ) {
+ IWizardPage page = (IWizardPage) i.next();
+ if (!page.isPageComplete()) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ public boolean performFinish() {
+ IRunnableWithProgress op= new WorkspaceModifyDelegatingOperation(new IRunnableWithProgress() {
+ public void run(IProgressMonitor monitor) throws InvocationTargetException, InterruptedException {
+ finishPage(monitor);
+ }
+ });
+
+ try {
+ getContainer().run(true, false, op);
+ } catch (InvocationTargetException e) {
+ return false;
+ } catch (InterruptedException e) {
+ return false;
+ }
+ return true;
+ }
+
+ private boolean finishPage(IProgressMonitor monitor) {
+ IStatus[] statuses = template.executeTemplateProcesses(monitor, false);
+ if (statuses.length == 1 && statuses[0].getException() instanceof ProcessFailureException) {
+ TemplateEngineUIUtil.showError(statuses[0].getMessage(), statuses[0].getException());
+ return false;
+ } else {
+ String msg = Messages.getString("TemplateDrivenWizard.0"); //$NON-NLS-1$
+ TemplateEngineUIUtil.showStatusDialog(msg, new MultiStatus(CUIPlugin.getPluginId(), IStatus.OK, statuses, msg, null));
+ return true;
+ }
+ }
+
+ public final void createPageControls(Composite pageContainer) {
+ super.createPageControls(pageContainer);
+ this.pageContainer = pageContainer;
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateEngineUI.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateEngineUI.java
new file mode 100644
index 0000000000..dbaab4cb63
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateEngineUI.java
@@ -0,0 +1,110 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.eclipse.cdt.core.templateengine.TemplateCore;
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+import org.eclipse.cdt.core.templateengine.TemplateInfo;
+
+
+/**
+ * TemplateEngine is implemented as a Singleton. TemplateEngine is responsible for
+ * creating SharedDefaults and initializing the SharedDefaults. Template instances
+ * are obtained from TemplateEngine.
+ *
+ * @since 4.0
+ */
+public class TemplateEngineUI {
+
+ /**
+ * static reference to the Singleton TemplateEngine instance.
+ */
+ private static TemplateEngineUI TEMPLATE_ENGINE_UI = new TemplateEngineUI();
+
+ private TemplateEngineUI() {
+ }
+
+ public static TemplateEngineUI getDefault() {
+ return TEMPLATE_ENGINE_UI;
+ }
+
+ /**
+ * This method will be called by Contianer UIs (Wizard, PropertyPage,
+ * PreferencePage). Create a Template instance, update the ValueStore, with
+ * SharedDefaults. This method calls the getTemplate(URL), after getting URL
+ * for the given String TemplateDescriptor.
+ */
+ public TemplateCore getFirstTemplate(String projectType) {
+ return getFirstTemplate(projectType, null, null);
+ }
+
+ public TemplateCore getFirstTemplate(String projectType, String toolChain, String usageFilter) {
+ try {
+ return new Template(TemplateEngine.getDefault().getTemplateInfos(projectType, toolChain, usageFilter)[0]);
+ } catch (Exception e) {
+ // ignore
+ }
+ return null;
+ }
+
+ public Template[] getTemplates(String projectType, String toolChain, String usageFilter) {
+ TemplateInfo[] templateInfoArray = TemplateEngine.getDefault().getTemplateInfos(projectType, toolChain, usageFilter);
+ List/*<Template>*/ templatesList = new ArrayList/*<Template>*/();
+ for (int i=0; i<templateInfoArray.length; i++) {
+ TemplateInfo info = templateInfoArray[i];
+ try {
+ templatesList.add(new Template(info));
+ } catch (Exception e) {
+ }
+ }
+ return (Template[]) templatesList.toArray(new Template[templatesList.size()]);
+ }
+
+ public Template[] getTemplates(String projectType, String toolChain) {
+ return getTemplates(projectType, toolChain, null);
+ }
+
+ public Template[] getTemplates(String projectType) {
+ return getTemplates(projectType, null, null);
+ }
+
+ /**
+ * get All the templates, no filtering is done.
+ */
+ public Template[] getTemplates() {
+ TemplateInfo[] templateInfoArray = TemplateEngine.getDefault().getTemplateInfos();
+ List/*<Template>*/ templatesList = new ArrayList/*<Template>*/();
+ for (int i=0; i<templateInfoArray.length; i++) {
+ try {
+ templatesList.add(new Template(templateInfoArray[i]));
+ } catch (Exception e) {
+ }
+ }
+
+ return (Template[]) templatesList.toArray(new Template[templatesList.size()]);
+ }
+
+ public Template getTemplateById(String templateId) {
+ Template[] templates = getTemplates();
+
+ for(int i=0; i<templates.length; i++) {
+ Template template = templates[i];
+ if (template.getTemplateId().equalsIgnoreCase(templateId)) {
+ return template;
+ }
+ }
+ return null;
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateEngineUIUtil.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateEngineUIUtil.java
new file mode 100644
index 0000000000..a5c47a02cb
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateEngineUIUtil.java
@@ -0,0 +1,93 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import java.util.List;
+
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.MultiStatus;
+import org.eclipse.core.runtime.Status;
+import org.eclipse.jface.dialogs.ErrorDialog;
+import org.eclipse.ui.IWorkbenchWindow;
+import org.eclipse.ui.PlatformUI;
+
+import org.eclipse.cdt.core.templateengine.TemplateEngineMessages;
+import org.eclipse.cdt.core.templateengine.TemplateEngineUtil;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.ui.CUIPlugin;
+
+public class TemplateEngineUIUtil {
+ /**
+ * Shows the error message in a Dialog Box.
+ * @param message
+ * @param t
+ *
+ * @since 4.0
+ */
+ public static void showError(String message, Throwable t) {
+ TemplateEngineUtil.log(t);
+ IStatus status;
+ if (t != null) {
+ if (t instanceof ProcessFailureException) {
+ List/*<IStatus>*/ statuses = ((ProcessFailureException) t).getStatuses();
+ if (statuses == null || statuses.isEmpty()) {
+ Throwable p = t;
+ do {
+ p = p.getCause();
+ if (p != null) {
+ statuses = ((ProcessFailureException) p).getStatuses();
+ }
+ } while ((statuses == null || statuses.isEmpty()) && p != null && p instanceof ProcessFailureException);
+ if (statuses == null || statuses.isEmpty()) {
+ status = new Status(IStatus.ERROR, CUIPlugin.getPluginId(), IStatus.ERROR, t.getMessage(), t);
+ } else {
+ status = new MultiStatus(CUIPlugin.getPluginId(), IStatus.ERROR, (IStatus[]) statuses.toArray(new IStatus[statuses.size()]), t.getMessage(), t);
+ }
+ } else {
+ status = new MultiStatus(CUIPlugin.getPluginId(), IStatus.ERROR, (IStatus[]) statuses.toArray(new IStatus[statuses.size()]), t.getMessage(), t);
+ }
+ } else if (t instanceof CoreException) {
+ status = ((CoreException) t).getStatus();
+ if (status != null && message.equals(status.getMessage())) {
+ message = null;
+ }
+ } else {
+ status = new Status(IStatus.ERROR, CUIPlugin.getPluginId(), -1, TemplateEngineMessages.getString("TemplateEngine.internalError") + message, t); //$NON-NLS-1$
+ }
+ } else {
+ status = new Status(IStatus.ERROR, CUIPlugin.getPluginId(), -1, TemplateEngineMessages.getString("TemplateEngine.internalError") + message, null); //$NON-NLS-1$
+ }
+ IWorkbenchWindow window = PlatformUI.getWorkbench().getActiveWorkbenchWindow();
+ if(window == null){
+ IWorkbenchWindow windows[] = PlatformUI.getWorkbench().getWorkbenchWindows();
+ window = windows[0];
+ }
+ ErrorDialog.openError(window.getShell(), TemplateEngineMessages.getString("TemplateEngine.templateEngine"), message, status); //$NON-NLS-1$
+ }
+
+ /**
+ * Shows the Status meassage in Dialog Box.
+ * @param message
+ * @param status
+ *
+ * @since 4.0
+ */
+ public static void showStatusDialog(String message, IStatus status) {
+ IWorkbenchWindow window = PlatformUI.getWorkbench().getActiveWorkbenchWindow();
+ if(window == null){
+ IWorkbenchWindow windows[] = PlatformUI.getWorkbench().getWorkbenchWindows();
+ window = windows[0];
+ }
+ ErrorDialog.openError(window.getShell(), TemplateEngineMessages.getString("TemplateEngine.templateEngine"), message, status); //$NON-NLS-1$
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateListSelectionPage.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateListSelectionPage.java
new file mode 100644
index 0000000000..1b8e89cc97
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplateListSelectionPage.java
@@ -0,0 +1,271 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import java.util.Iterator;
+import java.util.Map;
+
+import org.eclipse.jface.dialogs.Dialog;
+import org.eclipse.jface.viewers.DoubleClickEvent;
+import org.eclipse.jface.viewers.IDoubleClickListener;
+import org.eclipse.jface.viewers.ISelectionChangedListener;
+import org.eclipse.jface.viewers.IStructuredSelection;
+import org.eclipse.jface.viewers.SelectionChangedEvent;
+import org.eclipse.jface.viewers.StructuredSelection;
+import org.eclipse.jface.viewers.StructuredViewer;
+import org.eclipse.jface.viewers.TableViewer;
+import org.eclipse.jface.viewers.TreeViewer;
+import org.eclipse.jface.wizard.IWizard;
+import org.eclipse.jface.wizard.IWizardNode;
+import org.eclipse.jface.wizard.IWizardPage;
+import org.eclipse.jface.wizard.WizardSelectionPage;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.custom.SashForm;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Control;
+import org.eclipse.swt.widgets.Label;
+
+
+/**
+ * TemplateListSelectionPage
+ */
+class TemplateListSelectionPage extends WizardSelectionPage implements ISelectionChangedListener {
+
+ private String labelText;
+ private FormBrowser descriptionBrowser;
+ private TreeViewer wizardSelectionTreeViewer = null;
+ private TableViewer wizardSelectionTableViewer = null;
+ private StructuredViewer wizardSelectionViewer = null;
+ private TemplatesChoiceWizard parentWizard;
+ private Template[] templates;
+
+ public TemplateListSelectionPage(TemplatesChoiceWizard parentWizard) {
+ super("Template Selection"); //$NON-NLS-1$
+ setTitle(parentWizard.getListSelectionTitle());
+ setDescription(parentWizard.getListSelectionDescription());
+ this.labelText = parentWizard.getListSelectionLabel();
+ descriptionBrowser = new FormBrowser();
+ descriptionBrowser.setText(""); //$NON-NLS-1$
+ this.parentWizard = parentWizard;
+ }
+
+ public void createDescriptionIn(Composite composite) {
+ descriptionBrowser.createControl(composite);
+ Control c = descriptionBrowser.getControl();
+ GridData gd = new GridData(GridData.FILL_BOTH);
+ gd.widthHint = 200;
+ c.setLayoutData(gd);
+ }
+
+ public String getLabel() {
+ return labelText;
+ }
+
+ public void setDescriptionText(String text) {
+ descriptionBrowser.setText(text);
+ }
+
+ public void setDescriptionEnabled(boolean enabled) {
+ Control control = descriptionBrowser.getControl();
+ if (control != null) {
+ control.setEnabled(enabled);
+ }
+ }
+
+ public void moveToNextPage() {
+ getContainer().showPage(getNextPage());
+ }
+
+ public void createControl(Composite parent) {
+ Composite container = new Composite(parent, SWT.NONE);
+ GridLayout layout = new GridLayout();
+ layout.verticalSpacing = 10;
+ container.setLayout(layout);
+ container.setLayoutData(new GridData(GridData.FILL_BOTH));
+
+ Label label = new Label(container, SWT.NONE);
+ label.setText(getLabel());
+ GridData gd = new GridData();
+ label.setLayoutData(gd);
+
+ SashForm sashForm = new SashForm(container, SWT.VERTICAL);
+ gd = new GridData(GridData.FILL_BOTH);
+ gd.widthHint = 300;
+ gd.minimumHeight = 230;
+ sashForm.setLayoutData(gd);
+
+ boolean useTree = parentWizard.showTemplatesInTreeView();
+
+ if (useTree)
+ {
+ wizardSelectionTreeViewer = new TreeViewer(sashForm, SWT.BORDER);
+ wizardSelectionTreeViewer.setContentProvider(parentWizard);
+ wizardSelectionTreeViewer.addDoubleClickListener(new IDoubleClickListener() {
+ public void doubleClick(DoubleClickEvent event) {
+ selectionChanged(new SelectionChangedEvent(wizardSelectionTreeViewer, wizardSelectionTreeViewer.getSelection()));
+ moveToNextPage();
+ }
+ });
+ wizardSelectionTreeViewer.setInput(templates);
+ wizardSelectionTreeViewer.addSelectionChangedListener(this);
+ wizardSelectionTreeViewer.getTree().setData("name", "templates"); //$NON-NLS-1$ //$NON-NLS-2$
+ wizardSelectionViewer = wizardSelectionTreeViewer;
+
+ }
+ else
+ {
+ wizardSelectionTableViewer = new TableViewer(sashForm, SWT.BORDER);
+ wizardSelectionTableViewer.setContentProvider(parentWizard);
+ wizardSelectionTableViewer.addDoubleClickListener(new IDoubleClickListener() {
+ public void doubleClick(DoubleClickEvent event) {
+ selectionChanged(new SelectionChangedEvent(wizardSelectionTableViewer, wizardSelectionTableViewer.getSelection()));
+ moveToNextPage();
+ }
+ });
+ wizardSelectionTableViewer.setInput(templates);
+ wizardSelectionTableViewer.addSelectionChangedListener(this);
+ wizardSelectionTableViewer.getTable().setData("name", "templates"); //$NON-NLS-1$ //$NON-NLS-2$
+ wizardSelectionViewer = wizardSelectionTableViewer;
+
+ }
+ wizardSelectionViewer.getControl().setData(".uid", "wizardSelectionViewer"); //$NON-NLS-1$ //$NON-NLS-2$
+
+ createDescriptionIn(sashForm);
+ sashForm.setWeights(new int[] {75, 25});
+
+ Dialog.applyDialogFont(container);
+ setControl(container);
+ }
+
+ public void selectionChanged(SelectionChangedEvent event) {
+ setErrorMessage(null);
+ IStructuredSelection selection = (IStructuredSelection) event.getSelection();
+ Template currentWizardSelection = null;
+ Object selectedObject = null;
+ Iterator iter = selection.iterator();
+ if (iter.hasNext()) {
+ selectedObject = iter.next();
+ if (selectedObject instanceof Template)
+ currentWizardSelection = (Template) selectedObject;
+ }
+ if (currentWizardSelection == null) {
+ setDescriptionText(parentWizard.getDescription(selectedObject));
+ setSelectedNode(null);
+ return;
+ }
+ final Template finalSelection = currentWizardSelection;
+ setSelectedNode(new WizardNode(this, finalSelection));
+ setDescriptionText(parentWizard.getDescription(finalSelection));
+ getContainer().updateButtons();
+ }
+
+ public Template getTemplate() {
+ IWizardNode selectedNode = getSelectedNode();
+ if (selectedNode != null) {
+ return ((WizardNode)selectedNode).getTemplate();
+ }
+ return null;
+ }
+
+ public IWizardPage getNextPage(boolean shouldCreate) {
+ if (!shouldCreate) {
+ return super.getNextPage();
+ }
+ IWizardNode selectedNode = getSelectedNode();
+ selectedNode.dispose();
+ IWizard wizard = selectedNode.getWizard();
+ if (wizard == null) {
+ super.setSelectedNode(null);
+ return null;
+ }
+ if (shouldCreate) {
+ wizard.addPages();
+ }
+
+ return wizard.getStartingPage();
+ }
+
+ public boolean canFlipToNextPage() {
+ IStructuredSelection ssel = (IStructuredSelection)wizardSelectionViewer.getSelection();
+ return ssel != null && !ssel.isEmpty() && (ssel.getFirstElement() instanceof Template);
+ }
+
+ public void setVisible(boolean visible) {
+ if (visible) {
+ Template[] templates = parentWizard.getTemplates();
+ if (templatesHaveChanged(templates)) {
+ this.templates = templates;
+ wizardSelectionViewer.setInput(templates);
+ wizardSelectionViewer.refresh();
+ if (wizardSelectionTreeViewer != null) {
+ wizardSelectionTreeViewer.expandAll();
+ }
+
+ // select the first element by default
+ if (wizardSelectionTableViewer != null) {
+ wizardSelectionTableViewer.setSelection(new StructuredSelection(wizardSelectionTableViewer.getElementAt(0)), true);
+ }
+ if (wizardSelectionTreeViewer != null) {
+ wizardSelectionTreeViewer.setSelection(new StructuredSelection(wizardSelectionTreeViewer.getTree().getItem(0).getData()), true);
+ }
+ }
+ }
+ super.setVisible(visible);
+ if (visible) {
+ if (wizardSelectionTreeViewer != null) {
+ wizardSelectionTreeViewer.getTree().setFocus();
+ }
+ if (wizardSelectionTableViewer != null) {
+ wizardSelectionTableViewer.getTable().setFocus();
+ }
+ }
+ }
+
+ private boolean templatesHaveChanged(Template[] newTemplates) {
+ // doing this rather than an array compare because even when
+ // the templates are the same the objects are not. we really
+ // just need to compare the template info.
+ boolean changed = false;
+ if (newTemplates != null && templates != null && newTemplates.length == templates.length) {
+ for (int i=0; i<templates.length; i++) {
+ if (!newTemplates[i].getTemplateInfo().equals(templates[i].getTemplateInfo())) {
+ changed = true;
+ break;
+ }
+ }
+ } else {
+ changed = true;
+ }
+
+ return changed;
+ }
+
+ Map/*<String, String>*/ getDataInPreviousPages() {
+ return parentWizard.getAllDataInNonTemplatePages();
+ }
+
+ public IWizardDataPage[] getPagesAfterTemplatePages()
+ {
+ return parentWizard.getPagesAfterTemplatePages();
+ }
+
+ public IWizardDataPage[] getPagesAfterTemplateSelection() throws InstantiationException, IllegalAccessException, ClassNotFoundException
+ {
+ return parentWizard.getPagesAfterTemplateSelectionWithExtraPages(getTemplate());
+ }
+
+ public void adjustTemplateValues(Template template) {
+ parentWizard.adjustTemplateValues(template);
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplatesChoiceWizard.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplatesChoiceWizard.java
new file mode 100644
index 0000000000..0c1275e8b1
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/TemplatesChoiceWizard.java
@@ -0,0 +1,204 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.MultiStatus;
+import org.eclipse.jface.operation.IRunnableWithProgress;
+import org.eclipse.jface.viewers.IStructuredSelection;
+import org.eclipse.jface.wizard.IWizardPage;
+import org.eclipse.jface.wizard.Wizard;
+import org.eclipse.ui.IWorkbench;
+import org.eclipse.ui.IWorkbenchWizard;
+import org.eclipse.ui.actions.WorkspaceModifyDelegatingOperation;
+
+import org.eclipse.cdt.core.templateengine.TemplateInfo;
+import org.eclipse.cdt.core.templateengine.process.ProcessFailureException;
+import org.eclipse.cdt.ui.CUIPlugin;
+
+
+/**
+ * A wizard intending to show a choice of templates (@see org.eclipse.cdt.core.templateenginee.Template)
+ * before switching to the pages driven by the chosen template should extend from TemplatesChoiceWizard.
+ * Alternatively, when a choice of templates needn't be shown, TemplateDrivenWizard is a better fit.
+ * (@see org.eclipse.cdt.ui.templateengine.TemplateDrivenWizard)
+ *
+ */
+public abstract class TemplatesChoiceWizard extends Wizard implements ITemplatesListProvider, IWorkbenchWizard {
+ private static final boolean DEBUG = false;
+ private TemplateListSelectionPage templateListSelectionPage;
+ protected IWorkbench workbench;
+ protected IStructuredSelection selection;
+
+ public final void addPages() {
+ IWizardPage[] pages = getPagesBeforeTemplatePages();
+ for(int i=0; i<pages.length; i++) {
+ addPage(pages[i]);
+ }
+
+ templateListSelectionPage = new TemplateListSelectionPage(this);
+ addPage(templateListSelectionPage);
+
+ pages = getPagesAfterTemplatePages();
+ for(int i=0; i<pages.length; i++) {
+ addPage(pages[i]);
+ }
+ }
+
+ public String getListSelectionTitle()
+ {
+ return Messages.getString("TemplatesChoiceWizard.0"); //$NON-NLS-1$
+ }
+
+ public String getListSelectionDescription()
+ {
+ return Messages.getString("TemplatesChoiceWizard.1"); //$NON-NLS-1$
+ }
+
+ public String getListSelectionLabel()
+ {
+ return Messages.getString("TemplatesChoiceWizard.2"); //$NON-NLS-1$
+ }
+
+ protected abstract IWizardDataPage[] getPagesBeforeTemplatePages();
+
+ protected abstract IWizardDataPage[] getPagesAfterTemplatePages();
+
+ protected abstract IWizardDataPage[] getPagesAfterTemplateSelection();
+
+ IWizardDataPage[] getPagesAfterTemplateSelectionWithExtraPages(Template template) throws InstantiationException, IllegalAccessException, ClassNotFoundException {
+ IWizardDataPage[] pages = getPagesAfterTemplateSelection();
+ TemplateInfo templateInfo = template.getTemplateInfo();
+ String pagesProvider = templateInfo.getExtraPagesProvider();
+ if (pagesProvider != null) {
+ IPagesAfterTemplateSelectionProvider extraPagesProvider = (IPagesAfterTemplateSelectionProvider) Class.forName(pagesProvider).newInstance();
+ if (extraPagesProvider != null) {
+ List/*<IWizardDataPage>*/ pageList = new ArrayList/*<IWizardDataPage>*/(Arrays.asList(pages));
+ IWizardDataPage[] extraPages = extraPagesProvider.createAdditionalPages(this, workbench, selection);
+ pageList.addAll(Arrays.asList(extraPages));
+ pages = (IWizardDataPage[]) pageList.toArray(new IWizardDataPage[pageList.size()]);
+ }
+ }
+ return pages;
+ }
+
+ IWizardDataPage[] getExtraCreatedPages(Template template) throws InstantiationException, IllegalAccessException, ClassNotFoundException {
+ TemplateInfo templateInfo = template.getTemplateInfo();
+ String pagesProvider = templateInfo.getExtraPagesProvider();
+ if (pagesProvider != null) {
+ IPagesAfterTemplateSelectionProvider extraPagesProvider = (IPagesAfterTemplateSelectionProvider) Class.forName(pagesProvider).newInstance();
+ if (extraPagesProvider != null) {
+ List/*<IWizardDataPage>*/ pageList = new ArrayList/*<IWizardDataPage>*/();
+ IWizardDataPage[] extraPages = extraPagesProvider.getCreatedPages(this);
+ pageList.addAll(Arrays.asList(extraPages));
+ return (IWizardDataPage[]) pageList.toArray(new IWizardDataPage[pageList.size()]);
+ }
+ }
+ return new IWizardDataPage[0];
+ }
+
+ public boolean performFinish() {
+ IRunnableWithProgress op= new WorkspaceModifyDelegatingOperation(new IRunnableWithProgress() {
+ public void run(IProgressMonitor monitor) throws InvocationTargetException, InterruptedException {
+ finishPage(monitor);
+ }
+ });
+
+ try {
+ getContainer().run(true, false, op);
+ } catch (InvocationTargetException e) {
+ return false;
+ } catch (InterruptedException e) {
+ return false;
+ }
+ return true;
+
+ }
+
+ private boolean finishPage(IProgressMonitor monitor) {
+ IStatus[] statuses = templateListSelectionPage.getTemplate().executeTemplateProcesses(monitor, false);
+ if (statuses.length == 1 && statuses[0].getException() instanceof ProcessFailureException) {
+ TemplateEngineUIUtil.showError(statuses[0].getMessage(), statuses[0].getException());
+ return false;
+ } else {
+ if (DEBUG) {
+ String msg = Messages.getString("TemplatesChoiceWizard.3"); //$NON-NLS-1$
+ TemplateEngineUIUtil.showStatusDialog(msg, new MultiStatus(CUIPlugin.getPluginId(), IStatus.OK, statuses, msg, null));
+ }
+ return true;
+ }
+ }
+
+ /**
+ * Returns the Data in Non-Template Pages.
+ * @return Map,
+ */
+ public Map/*<String, String>*/ getAllDataInNonTemplatePages() {
+ Map/*<String, String>*/ map = new HashMap/*<String, String>*/();
+
+ IWizardDataPage[] pages = getPagesBeforeTemplatePages();
+ for(int i=0; i<pages.length; i++) {
+ map.putAll(pages[i].getPageData());
+ }
+
+ pages = getPagesAfterTemplateSelection();
+ for(int i=0; i<pages.length; i++) {
+ map.putAll(pages[i].getPageData());
+ }
+
+ try {
+ pages = getExtraCreatedPages(getSelectedTemplate());
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ for(int i=0; i<pages.length; i++) {
+ map.putAll(pages[i].getPageData());
+ }
+
+ pages = getPagesAfterTemplatePages();
+ for(int i=0; i<pages.length; i++) {
+ map.putAll(pages[i].getPageData());
+ }
+
+ return map;
+ }
+
+ /**
+ * initializes the workbench
+ */
+ public void init(IWorkbench workbench, IStructuredSelection currentSelection) {
+ this.workbench = workbench;
+ this.selection = currentSelection;
+ initializeDefaultPageImageDescriptor();
+ }
+
+ protected void initializeDefaultPageImageDescriptor() {
+// setDefaultPageImageDescriptor(descriptor);
+ }
+
+ public Template getSelectedTemplate() {
+ return templateListSelectionPage.getTemplate();
+ }
+
+ public void adjustTemplateValues(Template template) {
+ // Give the wizard a chance to adjust template values before they go into the page controls.
+ }
+
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/WizardNode.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/WizardNode.java
new file mode 100644
index 0000000000..40baa61218
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/WizardNode.java
@@ -0,0 +1,138 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine;
+
+import java.util.Iterator;
+import java.util.Map;
+
+import org.eclipse.jface.wizard.IWizard;
+import org.eclipse.jface.wizard.IWizardNode;
+import org.eclipse.jface.wizard.IWizardPage;
+import org.eclipse.jface.wizard.Wizard;
+import org.eclipse.swt.graphics.Image;
+import org.eclipse.swt.graphics.Point;
+import org.eclipse.swt.widgets.Composite;
+
+import org.eclipse.cdt.ui.templateengine.pages.UIWizardPage;
+
+
+/**
+ * Wizard Node
+ */
+class WizardNode implements IWizardNode {
+ private IWizard wizard;
+ private Template template;
+ private TemplateListSelectionPage parentPage;
+
+ /**
+ * Constructor.
+ * @param parentPage
+ * @param template
+ */
+ public WizardNode(TemplateListSelectionPage parentPage, Template template) {
+ this.parentPage = parentPage;
+ this.template = template;
+ }
+
+ public void dispose() {
+ if (wizard != null) {
+ wizard.dispose();
+ wizard = null;
+ }
+ }
+
+ /**
+ * Returns the Template
+ */
+ public Template getTemplate() {
+ return template;
+ }
+
+ public Point getExtent() {
+ return new Point(-1, -1);
+ }
+
+ /**
+ * Returns the Wizard.
+ */
+ public IWizard getWizard() {
+ if (wizard != null) {
+ return wizard;
+ }
+ wizard = new Wizard() {
+ {
+ setWindowTitle(template.getLabel());
+ }
+
+ private boolean finishPressed;
+
+ public void addPages() {
+ IWizardPage[] wpages = null;
+ try {
+ wpages = parentPage.getPagesAfterTemplateSelection();
+ } catch (Exception e) {
+ }
+ for(int i=0; i<wpages.length; i++) {
+ addPage(wpages[i]);
+ }
+
+ Map/*<String, UIWizardPage>*/ pages = template.getUIPages();
+ for(Iterator i = template.getPagesOrderVector().iterator(); i.hasNext(); ){
+ String id = (String) i.next();
+ addPage((UIWizardPage) pages.get(id));
+ }
+
+ wpages = parentPage.getPagesAfterTemplatePages();
+ for(int i=0; i<wpages.length; i++) {
+ addPage(wpages[i]);
+ }
+ }
+
+ public boolean performFinish() {
+ Map/*<String, String>*/ valueStore = template.getValueStore();
+ finishPressed = true;
+ getContainer().updateButtons();
+ IWizardPage[] wpages = getPages();
+ for(int i=0; i<wpages.length; i++) {
+ IWizardPage page = wpages[i];
+ if (page instanceof UIWizardPage)
+ valueStore.putAll(((UIWizardPage) page).getPageData());
+ }
+ template.getValueStore().putAll(parentPage.getDataInPreviousPages());
+ return true;
+ }
+
+ public boolean canFinish(){
+ return !finishPressed && super.canFinish();
+ }
+
+ public void createPageControls(Composite pageContainer) {
+ super.createPageControls(pageContainer);
+ parentPage.adjustTemplateValues(template);
+ IWizardPage[] wpages = getPages();
+ for(int i=0; i<wpages.length; i++) {
+ IWizardPage page = wpages[i];
+ if (page instanceof UIWizardPage)
+ ((UIWizardPage) page).getComposite().getUIElement().setValues(template.getValueStore());
+ }
+ }
+
+ public Image getDefaultPageImage() {
+ return parentPage.getImage();
+ }
+ };
+ return wizard;
+ }
+
+ public boolean isContentCreated() {
+ return wizard != null;
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/event/PatternEvent.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/event/PatternEvent.java
new file mode 100644
index 0000000000..1d79d21a68
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/event/PatternEvent.java
@@ -0,0 +1,83 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.event;
+
+import java.util.EventObject;
+
+/**
+ *
+ * PatternEvent class instances are created, when there is an unexpected input
+ * in the InputUIElement. Which results in a mismatch to the pattern of input
+ * data exptected. This has to be updated in the UIPage. To do this,
+ * PatternEvent is fired. For which, the UIPage will be the registered listener.
+ * Here UIPage stands for WizardPage.
+ *
+ * @since 4.0
+ */
+
+public class PatternEvent extends EventObject {
+
+ private static final long serialVersionUID = 0000000000L;
+
+ /**
+ * The description of this Event instance.
+ */
+ String eventMessage;
+
+ /**
+ * true indicates whether the user input is valid(according to pattern). This is useful, to update the UIPage with error messages. false otherwise.
+ */
+ private boolean valid;
+
+ /**
+ * The PatternEvent gets the Object source of this event, the same is passed
+ * to the EventObject.
+ *
+ * @param source
+ */
+ private PatternEvent(Object source) {
+ super(source);
+ }
+
+ /**
+ * Overloaded constructor, the Object source of this event and the String
+ * message is paramete. Object source is passed as parameter to EventObject,
+ * the event description is initialized to eventMessage.
+ *
+ * @param source
+ * @param eventMessage
+ */
+ public PatternEvent(Object source, String eventMessage, boolean valid) {
+ this(source);
+ this.eventMessage = eventMessage;
+ this.valid = valid;
+ }
+
+ /**
+ * return the String description of this Event instance.
+ *
+ * @return String
+ */
+ public String toString() {
+ return eventMessage;
+ }
+
+ /**
+ * returns the valid flag.
+ *
+ * @return boolean
+ */
+ public boolean getValid() {
+ return valid;
+ }
+
+}
+
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/event/PatternEventListener.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/event/PatternEventListener.java
new file mode 100644
index 0000000000..98a726a9d4
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/event/PatternEventListener.java
@@ -0,0 +1,35 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.event;
+
+import java.util.EventListener;
+
+/**
+ * PatternEventListener will be implemented by UIPage. When PatternEvent is
+ * fired by InputUIElement due to a mismatch of input entered by the user and
+ * the expected pattern of input.
+ *
+ * @since 4.0
+ */
+
+public interface PatternEventListener extends EventListener {
+
+ /**
+ * This methods is implemented by calsses handling PatternEvent.
+ * PatternEvent instance is the parameter to this method.
+ *
+ * @param aPet
+ *
+ * @since 4.0
+ */
+ public void patternPerformed(PatternEvent aPet);
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/messages.properties b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/messages.properties
new file mode 100644
index 0000000000..56ecdc5258
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/messages.properties
@@ -0,0 +1,40 @@
+###############################################################################
+# Copyright (c) 2007 Symbian Software Limited and others.
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Eclipse Public License v1.0
+# which accompanies this distribution, and is available at
+# http://www.eclipse.org/legal/epl-v10.html
+#
+# Contributors:
+# Symbian - Initial API and implementation
+###############################################################################
+
+TemplateDrivenWizard.0=Successful
+TemplateClassWizard.0=Templates Based Class Wizard
+TemplateClassWizard.1=Managed CDT projects class templates
+TemplateClassWizard.2=Select the type of class you would like to create.
+TemplateClassWizard.3=Select a class:
+TemplateClassWizard.4=Managed CDT Projects Class Wizard
+TemplateClassWizard.5=Add a new class to your existing project.
+TemplatesChoiceWizard.0=Template Selection
+TemplatesChoiceWizard.1=Select a template based upon the type of program you are creating.
+TemplatesChoiceWizard.2=Select a template:
+TemplatesChoiceWizard.3=Successful
+TemplateProjectWizard.1=New Managed CDT Project Wizard
+TemplateProjectWizard.2=New Managed CDT Project Wizard
+TemplateProjectWizard.3=Managed CDT Project
+TemplateProjectWizard.4=Managed CDT Project
+TemplateProjectWizard.5=Create a new managed CDT project.
+ProjectSelectionPage.0=Select a Managed CDT project
+ProjectSelectionPage.1=Select a Managed CDT project:
+ProjectSelectionPage.4=Project Name:
+ProjectSelectionPage.5=Browse...
+ProjectSelectionPage.6=Please enter a project name
+ProjectSelectionPage.7=Invalid Project Path
+ProjectSelectionPage.8=The project does not exist
+ProjectSelectionPage.9=Please select a CDT project
+ProjectSelectionPage.10=Project Selection
+ProjectSelectionPage.11=Choose a Project
+UITextWidget.0=\ Project already exists in workspace.
+SimpleElementException.0=This Operation not supported on InputUIElement
+
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/Messages.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/Messages.java
new file mode 100644
index 0000000000..0b53ce4fa7
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/Messages.java
@@ -0,0 +1,32 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.pages;
+
+import java.util.MissingResourceException;
+import java.util.ResourceBundle;
+
+public class Messages {
+ private static final String BUNDLE_NAME = "org.eclipse.cdt.ui.templateengine.pages.messages"; //$NON-NLS-1$
+
+ private static final ResourceBundle RESOURCE_BUNDLE = ResourceBundle
+ .getBundle(BUNDLE_NAME);
+
+ private Messages() {
+ }
+
+ public static String getString(String key) {
+ try {
+ return RESOURCE_BUNDLE.getString(key);
+ } catch (MissingResourceException e) {
+ return '!' + key + '!';
+ }
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/NewProjectCreationPage.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/NewProjectCreationPage.java
new file mode 100644
index 0000000000..3722597ad2
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/NewProjectCreationPage.java
@@ -0,0 +1,109 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Symbian - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.pages;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.Status;
+import org.eclipse.ui.dialogs.WizardNewProjectCreationPage;
+
+import org.eclipse.cdt.ui.CUIPlugin;
+import org.eclipse.cdt.ui.templateengine.IWizardDataPage;
+
+/**
+ * The first page in a NewProjectWizard. This is the wizard page that
+ * asks the user for the name and location of the new project.
+ */
+public class NewProjectCreationPage extends WizardNewProjectCreationPage implements IWizardDataPage {
+ private Map data = new HashMap(2);
+
+ private static final String ERROR_SUFFIX = Messages.getString("NewProjectCreationPage.0"); //$NON-NLS-1$
+ private static final String ERROR_SUFFIX_TOO_LONG = Messages.getString("NewProjectCreationPage.1"); //$NON-NLS-1$
+ private static final Status OK_STATUS = new Status(IStatus.OK, CUIPlugin.getPluginId(), 0, "", null); //$NON-NLS-1$
+
+ public NewProjectCreationPage(String name) {
+ super(name);
+ this.setDescription(Messages.getString("NewProjectCreationPage.3")); //$NON-NLS-1$
+ }
+
+ public Map getPageData() {
+ String projName = super.getProjectName().trim();
+ data.put("projectName", projName); //$NON-NLS-1$
+ data.put("baseName", getBaseName(projName)); //$NON-NLS-1$
+ data.put("baseNameUpper", getBaseName(projName).toUpperCase() ); //$NON-NLS-1$
+ data.put("baseNameLower", getBaseName(projName).toLowerCase() ); //$NON-NLS-1$
+ data.put("location", super.getLocationPath().toPortableString()); //$NON-NLS-1$
+ return data;
+ }
+
+ private String getBaseName(String projName) {
+ String baseName = projName;
+ int dot = baseName.lastIndexOf('.');
+ if (dot != -1) {
+ baseName = baseName.substring(dot + 1);
+ }
+ dot = baseName.indexOf(' ');
+ if (dot != -1) {
+ baseName = baseName.substring(0, dot);
+ }
+ return baseName;
+ }
+
+ protected boolean validatePage() {
+ if (super.validatePage() == true) {
+ IStatus validName = isValidName(getProjectName());
+ if (!validName.isOK()) {
+ setErrorMessage(validName.getMessage());
+ return false;
+ }
+ return true;
+ } else {
+ return false;
+ }
+ }
+
+ /**
+ * Projects names should only be alphanumeric and can contain ' ' and '_' chars.
+ * Names are limited to 31 chars. Names cannot end in a '.' char. Note that '.'
+ * characters currently not allowed as many of the command line generators get
+ * the name wrong for generated files. e.g. my.foo project name results in
+ * foo.rsc, foo.rsg, etc.. rather than the expected my.foo.rsc.
+ * @param projectName - The unmodified project name from the project wizard.
+ * @return an IStatus message on error.
+ *
+ * Note: Platform may have a different project name constraints. Please subclass this
+ * to add your own versions of validnames for template projects.
+ */
+ private IStatus isValidName(String projectName) {
+ //String baseName = getBaseName(projectName);
+ String baseName = projectName;
+
+ if (!Character.isLetter(baseName.charAt(0))) {
+ return new Status(IStatus.ERROR, CUIPlugin.getPluginId(), IStatus.ERROR, projectName + ERROR_SUFFIX, null);
+ }
+
+ if (baseName.length() > 31) {
+ return new Status(IStatus.ERROR, CUIPlugin.getPluginId(), IStatus.ERROR, projectName + ERROR_SUFFIX_TOO_LONG, null);
+ }
+
+ for (int i = 1, l = baseName.length(); i < l; i++) {
+ char c = baseName.charAt(i);
+ if (!Character.isLetterOrDigit(c) && c != '_' && c != ' ') {
+ return new Status(IStatus.ERROR, CUIPlugin.getPluginId(), IStatus.ERROR, projectName + ERROR_SUFFIX, null);
+ }
+ }
+
+ return OK_STATUS;
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/TemplateInputDialog.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/TemplateInputDialog.java
new file mode 100644
index 0000000000..3622f2472a
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/TemplateInputDialog.java
@@ -0,0 +1,328 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.pages;
+
+import org.eclipse.jface.dialogs.Dialog;
+import org.eclipse.jface.dialogs.IDialogConstants;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.events.ModifyEvent;
+import org.eclipse.swt.events.ModifyListener;
+import org.eclipse.swt.graphics.Color;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Button;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Control;
+import org.eclipse.swt.widgets.Display;
+import org.eclipse.swt.widgets.Label;
+import org.eclipse.swt.widgets.MessageBox;
+import org.eclipse.swt.widgets.Shell;
+import org.eclipse.swt.widgets.Text;
+
+import org.eclipse.cdt.core.templateengine.TemplateEngineUtil;
+
+
+/**
+ * Creates a JFace Dialog for the user to get name-value pair to perform
+ * SharedDefaults settings. The class takes care of user input validation.
+ */
+
+public class TemplateInputDialog extends Dialog {
+
+ /**
+ * Controls settings in the GUI
+ */
+ private static final String NAME = Messages.getString("TemplateInputDialog.0");// To be externalised //$NON-NLS-1$
+ private static final String VALUE = Messages.getString("TemplateInputDialog.1");// To be externalised //$NON-NLS-1$
+
+ /**
+ * Shell display messages for ADD and EDIT functionality
+ */
+
+ private static final String ADD_SHELL_MESSAGE = Messages.getString("TemplateInputDialog.2"); //$NON-NLS-1$
+ private static final String EDIT_SHELL_MESSAGE = Messages.getString("TemplateInputDialog.3"); //$NON-NLS-1$
+
+ /**
+ * Label Error Message
+ */
+ private Label errMessageLabel;
+ private String labelMessage = Messages.getString("TemplateInputDialog.4"); //$NON-NLS-1$
+
+ /**
+ * Text fields properties
+ */
+ private static final int TEXT_LIMIT = 100;
+
+ /**
+ * Dialog creation instances for display
+ */
+ private TemplatePreferencePage templatePreferencePage;
+ private TemplateInputDialog sharedDialog;
+ private Shell shell;
+ private Display display;
+
+ /**
+ * Dialog control instances
+ */
+ private Label valueLabel;
+ private Label nameLabel;
+ private Text valueText;
+ private Text nameText;
+ private Button oKButton;
+
+ /**
+ * Indentifies ADD/EDIT function
+ */
+ private int option;
+
+ /**
+ * Parent composite
+ */
+ private Composite parent;
+
+ /**
+ * JFace Dialog Constructor, constructs controls of the super class
+ *
+ * @param parentShell
+ */
+
+ protected TemplateInputDialog(Shell parentShell) {
+ super(parentShell);
+
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.jface.window.Window#configureShell(org.eclipse.swt.widgets.Shell)
+ */
+
+ protected void configureShell(Shell shell) {
+ super.configureShell(shell);
+ this.shell = shell;
+ shell.setBounds(420, 280, 300, 160);
+ display = shell.getDisplay();
+
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.jface.dialogs.Dialog#createDialogArea(org.eclipse.swt.widgets.Composite)
+ */
+
+ protected Control createDialogArea(Composite parent) {
+
+ this.parent = parent;
+ Composite composite = (Composite) super.createDialogArea(parent);
+ GridLayout gridLayout = new GridLayout(2, false);
+ composite.setLayout(gridLayout);
+ createControls(composite);
+ return composite;
+ }
+
+ /**
+ * Opens the Dialog to accept user input for shared values.
+ *
+ * @param myDialog
+ * @param dataOption
+ */
+
+ public void open(TemplateInputDialog myDialog, int dataOption) {
+ this.option = dataOption;
+ sharedDialog = myDialog;
+ sharedDialog.create();
+ Button oK = getButton(IDialogConstants.OK_ID);
+ oK.setEnabled(false);
+ if (option == TemplatePreferencePage.OPTION_ADD) {
+
+ shell.setText(ADD_SHELL_MESSAGE);
+ } else if (option == TemplatePreferencePage.OPTION_EDIT) {
+
+ shell.setText(EDIT_SHELL_MESSAGE);
+ }
+
+ sharedDialog.open();
+ }
+
+ /**
+ * Creates control under the parent composite
+ *
+ * @param composite
+ */
+
+ private void createControls(Composite composite) {
+
+ // Name Label
+ nameLabel = new Label(composite, SWT.NONE);
+ nameLabel.setText(NAME);
+
+ // Name Text Field
+ nameText = new Text(composite, SWT.BORDER | SWT.SINGLE);
+ nameText.setTextLimit(TEXT_LIMIT);
+ GridData textData = new GridData(GridData.FILL_HORIZONTAL);
+ textData.horizontalSpan = GridData.BEGINNING;
+ nameText.setLayoutData(textData);
+ addTextListener(nameText);
+
+ // Value Label
+ valueLabel = new Label(composite, SWT.NONE);
+ valueLabel.setText(VALUE);
+
+ // Value Text Field
+ valueText = new Text(composite, SWT.BORDER | SWT.SINGLE);
+ valueText.setTextLimit(TEXT_LIMIT);
+ GridData valueData = new GridData(GridData.FILL_HORIZONTAL);
+ valueData.horizontalSpan = GridData.BEGINNING;
+ valueData.verticalSpan = 5;
+ valueText.setLayoutData(valueData);
+ addTextListener(valueText);
+
+ // Label for Error Message
+ Color color = display.getSystemColor(SWT.COLOR_RED); // Get a red Color
+ Composite labelComposite = new Composite(parent, SWT.NONE);
+ labelComposite.setLayout(new GridLayout());
+ labelComposite.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
+ errMessageLabel = new Label(labelComposite, SWT.COLOR_DARK_RED);
+ errMessageLabel.setForeground(color);
+ errMessageLabel.setText(labelMessage);
+ errMessageLabel.setVisible(false);
+
+ if (option == TemplatePreferencePage.OPTION_EDIT) {
+ nameLabel.setEnabled(false);
+ nameText.setEnabled(false);
+
+ String name = TemplatePreferencePage.getSelectedItemNameFromTable();
+ if (name != null) {
+ nameText.setText(name);
+ }
+ }
+ }
+
+ /**
+ * Adds Modify listeners to the Text fields
+ *
+ * @param aText
+ */
+ public void addTextListener(final Text aText) {
+
+ ModifyListener mListener = new ModifyListener() {
+ public void modifyText(ModifyEvent e) {
+ String nameField = aText.getText();
+ textChanged(nameField);
+ }
+ };
+
+ aText.addModifyListener(mListener);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.jface.dialogs.Dialog#okPressed() This method is
+ * overridden to perform custom events on OK button.
+ */
+
+ protected void okPressed() {
+ if (option == TemplatePreferencePage.OPTION_ADD) {
+ String name = nameText.getText();
+ String value = valueText.getText();
+
+ if (name != TemplatePreferencePage.Blank && value != TemplatePreferencePage.Blank) {
+ templatePreferencePage = new TemplatePreferencePage(name, value);
+ templatePreferencePage.addNewDataIntoTable();
+
+ if (TemplatePreferencePage.isDup) {
+ nameText.setText(TemplatePreferencePage.Blank);
+ nameText.setFocus();
+ TemplatePreferencePage.isDup = false;
+ } else if (!TemplatePreferencePage.isDup) {
+ nameText.setFocus();
+ sharedDialog.close();
+ }
+ }
+ }
+
+ if (option == TemplatePreferencePage.OPTION_EDIT) {
+ String name = nameText.getText();
+ String value = valueText.getText();
+
+ if (!value.equals(TemplatePreferencePage.Blank)) {
+ templatePreferencePage = new TemplatePreferencePage(name, value);
+ templatePreferencePage.updateDataInTheTable();
+ }
+ sharedDialog.close();
+ }
+ }
+
+ /**
+ * Pops up Message dialog if duplicate entry is found and returns
+ * confirmation.
+ *
+ * @return result
+ */
+
+ public int popDuplicate() {
+
+ MessageBox mBox = new MessageBox(new Shell(), SWT.ICON_INFORMATION);
+ mBox.setText(TemplatePreferencePage.Message);
+ mBox.setMessage(TemplatePreferencePage.DuplicateEntry);
+ int result = mBox.open();
+ return result;
+
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.eclipse.jface.dialogs.Dialog#cancelPressed()
+ */
+ protected void cancelPressed() {
+
+ sharedDialog.close();
+ }
+
+ /**
+ *
+ * Implements the modify listener for the text field Name and Value fields.
+ *
+ * @param textField
+ */
+
+ private void textChanged(String textField) {
+
+ errMessageLabel.setVisible(false);
+ try {
+
+ // Diable OK button if special characters are entererd.
+ if (textField.matches(TemplatePreferencePage.Blank)) {
+
+ oKButton = getButton(IDialogConstants.OK_ID);
+ errMessageLabel.setText(labelMessage);
+ errMessageLabel.setVisible(true);
+ oKButton.setEnabled(false);
+
+ }
+
+ // Enable OK button if and only if data is entered.
+ else if (!nameText.getText().equals(TemplatePreferencePage.Blank)
+ && !valueText.getText().equals(TemplatePreferencePage.Blank)) {
+
+ oKButton = getButton(IDialogConstants.OK_ID);
+ oKButton.setEnabled(true);
+ }
+
+ } catch (Exception exp) {
+ TemplateEngineUtil.log(exp);
+ }
+
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/TemplatePreferencePage.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/TemplatePreferencePage.java
new file mode 100644
index 0000000000..730bea8e8a
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/TemplatePreferencePage.java
@@ -0,0 +1,589 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.pages;
+
+import java.util.List;
+
+import org.eclipse.jface.preference.PreferencePage;
+import org.eclipse.jface.viewers.ColumnLayoutData;
+import org.eclipse.jface.viewers.ColumnWeightData;
+import org.eclipse.jface.viewers.TableLayout;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.events.SelectionAdapter;
+import org.eclipse.swt.events.SelectionEvent;
+import org.eclipse.swt.events.SelectionListener;
+import org.eclipse.swt.layout.FillLayout;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Button;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Control;
+import org.eclipse.swt.widgets.Label;
+import org.eclipse.swt.widgets.MessageBox;
+import org.eclipse.swt.widgets.Shell;
+import org.eclipse.swt.widgets.Table;
+import org.eclipse.swt.widgets.TableColumn;
+import org.eclipse.swt.widgets.TableItem;
+import org.eclipse.ui.IWorkbench;
+import org.eclipse.ui.IWorkbenchPreferencePage;
+import org.eclipse.ui.PlatformUI;
+import org.w3c.dom.Element;
+
+import org.eclipse.cdt.core.templateengine.SharedDefaults;
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+import org.eclipse.cdt.core.templateengine.TemplateEngineHelper;
+import org.eclipse.cdt.core.templateengine.TemplateEngineUtil;
+import org.eclipse.cdt.ui.CUIPlugin;
+
+
+/**
+ * This class represents a preference page that is contributed to the
+ * Preferences dialog. By Provided GUI for SharedDefaults settings for the
+ * Templates present in the Template Engine
+ */
+
+public class TemplatePreferencePage extends PreferencePage implements IWorkbenchPreferencePage {
+
+ /**
+ * Preference Page buttons
+ */
+
+ private static final String EditButton = " Edit... "; //$NON-NLS-1$
+ private static final String DeleteButton = " Remove "; //$NON-NLS-1$
+ private static final String PageDescription = Messages.getString("TemplatePreferencePage.0");//$NON-NLS-1$
+ public static final String Blank = "";//$NON-NLS-1$
+
+ /**
+ * Validation Messages
+ */
+ public static final String Message = Messages.getString("TemplatePreferencePage.1");//$NON-NLS-1$
+ protected static final String DuplicateEntry = Messages.getString("TemplatePreferencePage.2");//$NON-NLS-1$
+ private static final String DeleteValidator = Messages.getString("TemplatePreferencePage.3");//$NON-NLS-1$
+ private static final String DeleteShellMessage = Messages.getString("TemplatePreferencePage.4");//$NON-NLS-1$
+
+ /**
+ * Button ToolTips
+ */
+ private static final String TableToolTip = Messages.getString("TemplatePreferencePage.5");//$NON-NLS-1$
+ private static final String EditToolTip = Messages.getString("TemplatePreferencePage.6");//$NON-NLS-1$
+ private static final String DeleteToolTip = Messages.getString("TemplatePreferencePage.7");//$NON-NLS-1$
+
+ /**
+ * Class instances
+ */
+ private static TemplateInputDialog inputDialog;
+ private static SharedDefaults sharedDefaults = SharedDefaults.getInstance();
+
+ /**
+ * Table Attributes
+ */
+ private int columnWidth = 100;
+ private int columnWeight = 50;
+ private String columnNames[];
+ private static List/*<Element>*/ sharedElementList;
+ private int attrListSize;
+
+ private ColumnLayoutData columnLayouts[] = { new ColumnWeightData(columnWeight, columnWidth),
+ new ColumnWeightData(columnWeight, columnWidth) };
+
+ /**
+ * InfoHelp for SharedDefault
+ */
+ private String pageID;
+ private String SharedContextHelpID = "shared_defaults_help";//$NON-NLS-1$
+
+ /**
+ * Button instance for ADD/EDIT/DELETE
+ */
+
+ private Button editButton;
+ private Button deleteButton;
+
+ /**
+ * Checks for row(s) deletion
+ */
+ private static boolean isDeleted;
+
+ /**
+ * Checks for redundant data
+ */
+ private boolean isRedundant;
+
+ /**
+ * Takes isRedundant reference to get reflected in different class scope See
+ * TemplateInputDialog class
+ */
+ public static boolean isDup;
+ private static String delItemNames[] = null;
+ private static Table table;
+
+ /**
+ * Add/Edit option values
+ */
+ protected static final int OPTION_ADD = 0;
+ protected static final int OPTION_EDIT = 1;
+
+ /**
+ * Dialog input values arriving from TemplateInputDialog class
+ */
+ private String name;
+ private String value;
+
+ /**
+ * Constructor to initialize defaults
+ */
+
+ public TemplatePreferencePage() {
+
+ noDefaultAndApplyButton();
+ initializeDefaults();
+ }
+
+ /**
+ * Sets the values of the Message Dialog
+ *
+ * @param aName
+ * @param aValue
+ */
+ public TemplatePreferencePage(String aName, String aValue) {
+ this.name = aName;
+ this.value = aValue;
+ }
+
+ /**
+ * Sets default settings and gathers attributes from the XML for Table
+ * properties
+ */
+
+ private void initializeDefaults() {
+ columnNames = new String[] { TemplateEngineHelper.ID, TemplateEngineHelper.VALUE };
+ // Setting InfoPop help (plugin-id+ContextID).
+ pageID = CUIPlugin.getPluginId() + "." + //$NON-NLS-1$
+ SharedContextHelpID;
+
+ setTableAttributes();
+
+ }
+
+ /**
+ * Creates controls on the Preference Page Adds the created Table and Button
+ * composite to the parent composite.
+ *
+ * @param parent
+ * @return subComposite
+ */
+
+ protected Control createContents(Composite parent) {
+
+ Composite composite = new Composite(parent, SWT.NONE);
+ GridLayout layout = new GridLayout();
+ layout.marginHeight = 0;
+ layout.marginWidth = 0;
+ composite.setLayout(layout);
+
+ Label pageLabel = new Label(composite, SWT.NONE);
+ pageLabel.setText(PageDescription);
+
+ Composite subComposite = new Composite(parent, SWT.NONE);
+ GridLayout subLayout = new GridLayout(2, false);
+ GridData gridData = new GridData(GridData.FILL_BOTH);
+ subComposite.setLayout(subLayout);
+ subComposite.setLayoutData(gridData);
+
+ addFirstSection(subComposite);
+ addSecondSection(subComposite);
+
+ // Info help for SharedDefault is displayed when Functional Key (F1) is
+ // triggered.
+ PlatformUI.getWorkbench().getHelpSystem().setHelp(super.getControl(), pageID);
+ return subComposite;
+
+ }
+
+ /**
+ * Adds table into the first composite present under parent Updates the
+ * Table with backend persistence data.
+ *
+ * @param parent
+ */
+
+ private void addFirstSection(Composite parent) {
+ createTable(parent);
+ setTableAttributes();
+ addXMLDataIntoTable();
+ }
+
+ /**
+ * Creates second composite for buttons present under the parent
+ *
+ * @param parent
+ */
+
+ private void addSecondSection(Composite parent) {
+ Composite composite = createDefaultComposite(parent);
+ addButtonControls(composite);
+ }
+
+ /**
+ * Creates default composite area for the Buttons
+ *
+ * @param parent
+ * @return composite
+ */
+
+ private Composite createDefaultComposite(Composite parent) {
+
+ Composite composite = new Composite(parent, SWT.NULL);
+ FillLayout layout = new FillLayout(SWT.VERTICAL);
+ layout.spacing = 5;
+ layout.marginWidth = 0;
+ layout.marginHeight = 0;
+ composite.setLayout(layout);
+
+ GridData gridData = new GridData();
+ gridData.verticalAlignment = GridData.BEGINNING;
+ composite.setLayoutData(gridData);
+
+ return composite;
+
+ }
+
+ /**
+ * Creates Table with XML properties as its settings
+ *
+ * @param composite
+ */
+
+ private void createTable(Composite composite) {
+
+ table = new Table(composite, SWT.H_SCROLL | SWT.V_SCROLL | SWT.MULTI | SWT.FULL_SELECTION | SWT.BORDER
+ | SWT.NO_REDRAW_RESIZE);
+
+ GridData gridData = new GridData(GridData.FILL_BOTH);
+ gridData.heightHint = convertHeightInCharsToPixels(10);
+ gridData.widthHint = convertWidthInCharsToPixels(10);
+
+ table.setLayoutData(gridData);
+ TableLayout layout = new TableLayout();
+ table.setLayout(layout);
+ table.setLinesVisible(true);
+ table.setHeaderVisible(true);
+ table.setToolTipText(TableToolTip);
+
+ // The attribute size becomes zero when no data
+ // remains in the table. To avoid fault creation of
+ // the table the attribute size to required columns
+ // in the table.
+ if (attrListSize == 0) {
+ attrListSize = 2;
+ }
+
+ for (int nCols = 0; nCols < attrListSize; nCols++) {
+ layout.addColumnData(columnLayouts[nCols]);
+ TableColumn tColumn = new TableColumn(table, SWT.LEFT, nCols);
+ tColumn.setWidth(columnWidth);
+ tColumn.setText(columnNames[nCols]);
+ }
+
+ addTableListener();
+ }
+
+ /**
+ * Table listener added to enable EDIT/DELETE functionality only when table
+ * listenes to an event.
+ */
+ private void addTableListener() {
+
+ SelectionListener sListener = new SelectionAdapter() {
+ public void widgetSelected(SelectionEvent e) {
+ boolean isSelected = table.isSelected(table.getSelectionIndex());
+ int selectionCount = table.getSelectionCount();
+
+ // Enable EDIT/DELETE button when row(s) get selected
+ if (isSelected) {
+ editButton.setEnabled(true);
+ deleteButton.setEnabled(true);
+ }
+
+ // disable EDIT button if more than one row is selected
+ if (selectionCount > 1)
+ editButton.setEnabled(false);
+ }
+ };
+ table.addSelectionListener(sListener);
+ }
+
+ /**
+ * Adds XML backend data into the table Supports for pesistency.
+ */
+
+ private void addXMLDataIntoTable() {
+ for (int i = 0, l = sharedElementList.size(); i < l; i++) {
+ Element xmlElement = (Element) sharedElementList.get(i);
+ String name = xmlElement.getAttribute(TemplateEngineHelper.ID);
+ String value = xmlElement.getAttribute(TemplateEngineHelper.VALUE);
+
+ if (name.equals(Blank) && value.equals(Blank))
+ return;
+
+ String backEndData[] = new String[] { name, value };
+ TableItem backEndItem = new TableItem(table, SWT.NONE);
+
+ for (int data = 0; data < backEndData.length; data++) {
+ if (backEndData[data] != null)
+ backEndItem.setText(data, backEndData[data]);
+ }
+ }
+ }
+
+ /**
+ * Creates button controls on the first composite present under parent
+ * composite. Its aligned at rightmost end of Table and top of the second
+ * composite.
+ *
+ * @param composite
+ */
+
+ private void addButtonControls(Composite composite) {
+
+ editButton = new Button(composite, SWT.PUSH);
+ editButton.setText(EditButton);
+ editButton.setEnabled(false);
+ editButton.setToolTipText(EditToolTip);
+ addButtonListener(editButton);
+
+ deleteButton = new Button(composite, SWT.PUSH);
+ deleteButton.setText(DeleteButton);
+ deleteButton.setEnabled(false);
+ deleteButton.setToolTipText(DeleteToolTip);
+ addButtonListener(deleteButton);
+
+ }
+
+ /**
+ * Constructs button listeners to trigger specific functionality
+ *
+ * @param button
+ */
+ public void addButtonListener(final Button button) {
+
+ inputDialog = new TemplateInputDialog(getShell());
+ SelectionListener listener = new SelectionAdapter() {
+
+ public void widgetSelected(SelectionEvent e) {
+ if (e.getSource().equals(editButton)) {
+ String editItemString = getSelectedItemNameFromTable();
+ if (editItemString != null) {
+ if (editItemString != Blank) {
+ inputDialog.open(inputDialog, OPTION_EDIT);
+ }
+ }
+ }
+
+ if (e.getSource().equals(deleteButton)) {
+ deleteRow();
+ editButton.setEnabled(false);
+ deleteButton.setEnabled(false);
+ }
+ }
+ };
+ button.addSelectionListener(listener);
+ }
+
+ /**
+ * Adding new data into the table and adds the same data to the backend XML
+ * Checks for duplicate entries and null values
+ */
+
+ public void addNewDataIntoTable() {
+
+ String addData[] = new String[] { name, value };
+ if (!isDeleted) {
+ TableItem duplicateItems[] = table.getItems();
+ TableItem duplicateItem = null;
+
+ for (int nItems = 0; nItems < duplicateItems.length; nItems++) {
+ duplicateItem = duplicateItems[nItems];
+ String duplicateString = duplicateItem.getText();
+
+ if (duplicateString.equals(name)) {
+ int result = inputDialog.popDuplicate();
+ if (result == SWT.OK) {
+ isRedundant = true;
+ isDup = isRedundant;
+ break;
+ }
+ }
+ }
+
+ // Check if not redundant
+ if (!isRedundant) {
+ TableItem tableItem = new TableItem(table, SWT.NONE);
+
+ for (int data = 0; data < addData.length; data++) {
+ tableItem.setText(data, addData[data]);
+ }
+
+ isRedundant = false;
+ }
+ }
+
+ sharedDefaults.addToBackEndStorage(name, value);
+ }
+
+ /**
+ * Gets the size of the Attributes of an Element of XML file
+ *
+ * @param sharedElementList
+ * @return attrListSize
+ */
+ private int getAttributeSize() {
+ try {
+ int listSize = sharedElementList.size();
+ int i = 0;
+ while (i < listSize) {
+ Element xmlElement = (Element) sharedElementList.get(i++);
+ attrListSize = xmlElement.getAttributes().getLength();
+ }
+ } catch (Exception exp) {
+ TemplateEngineUtil.log(exp);
+ }
+ return attrListSize;
+ }
+
+ /**
+ * Setting the table attributes with the XML properties Sets XML-document
+ * Element List as the number of table rows and XML-document Attribute List
+ * as the number of table columns
+ */
+
+ private void setTableAttributes() {
+
+ try {
+ SharedDefaults sharedTemp = new SharedDefaults();
+ sharedElementList = TemplateEngine.getChildrenOfElement(sharedTemp.document.getDocumentElement());
+ attrListSize = getAttributeSize();
+ sharedDefaults.putAll(sharedTemp.getSharedDefaultsMap());
+
+ } catch (Exception exp) {
+ TemplateEngineUtil.log(exp);
+ }
+ }
+
+ public void init(IWorkbench workbench) {
+
+ }
+
+ /**
+ * Updating data with the changed value for a given ID in the table.
+ */
+
+ public void updateDataInTheTable() {
+
+ try {
+ int selectedItemIndex = table.getSelectionIndex();
+ TableItem selectedItem = table.getItem(selectedItemIndex);
+ String updateString[] = new String[] { name, value };
+ selectedItem.setText(updateString);
+ sharedDefaults.updateToBackEndStorage(name, value);
+ } catch (Exception exp) {
+ TemplateEngineUtil.log(exp);
+ }
+ }
+
+ /**
+ * Gives the item for the selected row in the table
+ *
+ * @return selectedItemName
+ */
+
+ public static String getSelectedItemNameFromTable() {
+
+ String selectedItemName = null;
+ int selectedItemIndex = 0;
+
+ try {
+ selectedItemIndex = table.getSelectionIndex();
+ }
+
+ catch (Exception exp) {
+ TemplateEngineUtil.log(exp);
+ }
+
+ TableItem selectedItem = table.getItem(selectedItemIndex);
+ selectedItemName = selectedItem.getText();
+ return selectedItemName;
+
+ }
+
+ /**
+ * Deletes the data for the specified row Data also gets deleted at the
+ * backend with Key-name as an identifier.
+ */
+ private void deleteRow() {
+
+ int result = 0;
+ String nonEmptyItemString = getSelectedItemNameFromTable();
+
+ if (nonEmptyItemString != null)
+ result = confirmdeleteContents(nonEmptyItemString);
+
+ if (result == SWT.OK) {
+ int itemSelected[] = table.getSelectionIndices();
+ table.remove(itemSelected);
+ }
+
+ else if (result == SWT.CANCEL)
+ isDeleted = false;
+
+ if (delItemNames != null) {
+ sharedDefaults.deleteBackEndStorage(delItemNames);
+ }
+
+ }
+
+ /**
+ * Sets confirmation for the data deletion at the fronend and backend
+ *
+ * @param selectedItems
+ * @return result
+ */
+
+ private int confirmdeleteContents(String selectedItems) {
+
+ int result = 0;
+ TableItem deleteItems[] = null;
+
+ if (selectedItems != Blank) {
+
+ deleteItems = table.getSelection();
+ delItemNames = new String[deleteItems.length];
+
+ for (int nDel = 0; nDel < deleteItems.length; nDel++) {
+
+ TableItem item = deleteItems[nDel];
+ delItemNames[nDel] = item.getText();
+
+ }
+
+ MessageBox mBox = new MessageBox(new Shell(), SWT.ICON_QUESTION | SWT.OK | SWT.CANCEL);
+ mBox.setText(DeleteShellMessage);
+ mBox.setMessage(DeleteValidator);
+ result = mBox.open();
+
+ }
+
+ return result;
+
+ }
+
+}
+
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/UIPage.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/UIPage.java
new file mode 100644
index 0000000000..4bdc6540f1
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/UIPage.java
@@ -0,0 +1,158 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.pages;
+
+import java.net.URL;
+import java.util.Map;
+
+import org.eclipse.core.runtime.FileLocator;
+import org.eclipse.core.runtime.Path;
+import org.eclipse.jface.dialogs.DialogPage;
+import org.eclipse.jface.resource.ImageDescriptor;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Control;
+import org.eclipse.ui.PlatformUI;
+
+import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.cdt.core.templateengine.TemplateEngineUtil;
+import org.eclipse.cdt.ui.CUIPlugin;
+import org.eclipse.cdt.ui.templateengine.uitree.UIElement;
+import org.eclipse.cdt.ui.templateengine.uitree.uiwidgets.UIComposite;
+
+
+/**
+ *
+ * The UIPage extends DialogPage, it implements the createControl() abstract
+ * method. The UIPage is the base class for UIWizardPage. The UIPage contains a
+ * UIComposite, which extends a SWT composite. The SWT widgets are added to
+ * UIComposite.
+ */
+
+public abstract class UIPage extends DialogPage {
+
+ /**
+ * The Composite belonging to this page. The SWT widgets are added to this Composite. UIComposite instance is the top level control of this page. This top level control is initialized in createControl method.
+ */
+ private UIComposite uiComposite;
+
+ /**
+ * resources ID which will be displayed as F1 help in Title area.
+ */
+ protected static String RESOURCES_ID = CCorePlugin.PLUGIN_ID + ".resources"; //$NON-NLS-1$
+
+ /**
+ * The UIElement (group), to which this page corresponds. Every UIElement group corresponds to a UIPage. The children of this goup are UIElement's (SWT widgets). Which are added to the UIComposite.
+ */
+ private UIElement uiElement;
+
+ /**
+ * ValueStore for this instance of Template.
+ */
+ private Map/*<String, String>*/ valueStore;
+
+ /**
+ * Title set for this WizardPage.
+ */
+ protected String title;
+
+ /**
+ * Property Group Id corresponding this page
+ */
+ protected String pageId;
+
+ private ImageDescriptor imageDescriptor;
+
+ /**
+ *
+ * @param name
+ * Name of this UIPage.
+ * @param element
+ * The group UIElement.
+ */
+ protected UIPage(String name, UIElement element, Map/*<String, String>*/ valueStore) {
+ super(name);
+ setTitle(name);
+ setDescription((String) element.getAttributes().get(UIElement.DESCRIPTION));
+ try {
+ String imageLoc = (String) element.getAttributes().get(UIElement.IMAGELOCATION);
+ if (imageLoc != null) {
+ URL url = FileLocator.toFileURL(FileLocator.find(CCorePlugin.getDefault().getBundle(), new Path(imageLoc), null));
+ imageDescriptor = ImageDescriptor.createFromURL(url);
+ }
+ } catch (Exception e) {
+ TemplateEngineUtil.log(e);
+ }
+
+ super.setImageDescriptor(imageDescriptor);
+ //TODO: Fix the imagedescriptor later.
+// setImageDescriptor(TemplateEnginePlugin.imageDescriptorFromPlugin(TemplateEnginePlugin.getDefault().getWizardIconPluginID(), TemplateEnginePlugin.getDefault().getWizardIconFile()));
+
+ title = name;
+ uiElement = element;
+ this.valueStore = valueStore;
+ //TODO: Check the from which plugin the PLUGIN_ID comes from i.e. from CCorePlugin or CUIPlugin
+ pageId = CUIPlugin.getPluginId() + "." + //$NON-NLS-1$
+ (uiElement.getAttributes()).get(UIElement.ID);
+ }
+
+ /**
+ * Creates the top level control for this dialog page under the given parent
+ * composite.
+ *
+ * @param parent
+ * the parent composite
+ */
+ public void createControl(Composite parent) {
+ initializeDialogUnits(parent);
+ uiComposite = new UIComposite(parent, uiElement, valueStore);
+
+ // set the focus so that InfoPop is displayed when F1 is Pressed.
+ uiComposite.setFocus();
+
+ setControl(uiComposite);
+
+ // Setting InfoPop help context ID(plugin-id+ContextID).
+ PlatformUI.getWorkbench().getHelpSystem().setHelp(super.getControl(), pageId);
+
+ }
+
+ /**
+ * The data contained in the Input elements (SWT widgets), on this page is
+ * extracted and put into an HashMap. The same is returned.
+ *
+ * @return HashMap. The data contained in the widgets on this page.
+ */
+ public Map/*<String, String>*/ getPageData() {
+ return uiComposite.getPageData();
+ }
+
+ /**
+ * This is an overridden definition for the same method in DialogPage. The
+ * top level control is returned.
+ *
+ * @return Control.
+ */
+ public Control getControl() {
+ return uiComposite;
+ }
+
+ // This method is provided for unit tesing the UIComposite instance.
+ /**
+ *
+ * This returns UICompostie as UIComposite instance. Unlike the getControl.
+ *
+ * @return UIComposite, used in this page.
+ */
+ public UIComposite getComposite() {
+ return uiComposite;
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/UIPagesProvider.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/UIPagesProvider.java
new file mode 100644
index 0000000000..605c0b25c2
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/UIPagesProvider.java
@@ -0,0 +1,170 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.pages;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.eclipse.cdt.core.templateengine.TemplateEngineUtil;
+import org.eclipse.cdt.ui.templateengine.SimpleElementException;
+import org.eclipse.cdt.ui.templateengine.uitree.InputUIElement;
+import org.eclipse.cdt.ui.templateengine.uitree.SimpleUIElementGroup;
+import org.eclipse.cdt.ui.templateengine.uitree.UIElement;
+
+
+/**
+ * The UIPagesProvider creates a Map of UIPages. The Map will have ID as key,
+ * UIPage as value. The sequence of call to get Map of UIPages. 1.
+ * clearOrderVector() for all PropertyGroup Elements. 2. getUIPages(...)
+ *
+ */
+public class UIPagesProvider {
+
+ /**
+ * maintains the Page display order.
+ */
+ private List/*<String>*/ orderVector;
+
+
+ public UIPagesProvider() {
+ orderVector = new ArrayList();
+ }
+
+ /**
+ * after getting this clear the Vector.
+ *
+ * @return Vector
+ */
+ public List/*<String>*/ getOrderVector() {
+ return orderVector;
+ }
+
+ /**
+ * re-initialize the Vector.
+ */
+ public void clearOrderVector() {
+ orderVector = new ArrayList/*<String>*/();
+ }
+
+ /**
+ * This class has methods to return an HashMap of UIPages. The UIPages will
+ * correspond to UIElement group passed as parameter to this method. For a
+ * group UIElement, the children count is taken. An array of UIPage for the
+ * count is created. The same is initialized with UIPages.
+ *
+ * @param uiElement
+ * UIElement group root element. Which can be converted to a
+ * UIPage.
+ * @param valueStore
+ * @return HashMap, UIPages corresonding to param aUIElement.
+ */
+ public Map/*<String, UIWizardPage>*/ getWizardUIPages(UIElement uiElement, Map/*<String, String>*/ valueStore) {
+ int childCount = 0;
+
+ try {
+ childCount = uiElement.getChildCount();
+ } catch (SimpleElementException e) {
+ TemplateEngineUtil.log(e);
+ }
+
+ // HashMap of UIPages
+ HashMap/*<String, UIWizardPage>*/ pageMap = new HashMap/*<String, UIWizardPage>*/();
+
+ // If uiElement contains other group elements as children.
+ if (hasChildUIGroupElement(uiElement)) {
+
+ for (int i = 0; i < childCount; i++) {
+ try {
+ pageMap.putAll(getWizardUIPages(uiElement.getChild(i), valueStore)); // recursion
+ } catch (SimpleElementException e) {
+ TemplateEngineUtil.log(e);
+ }
+ }
+ }
+ else {
+ if ((hasChildUIElement(uiElement))) {
+ String title = (String) uiElement.getAttributes().get(UIElement.TITLE);
+ String description = (String) (uiElement.getAttributes()).get(UIElement.DESCRIPTION);
+ UIWizardPage uiPage = new UIWizardPage(title, description, uiElement, valueStore);
+
+ pageMap.put((uiElement.getAttributes()).get(UIElement.ID), uiPage);
+ addToOrderVector((String) (uiElement.getAttributes()).get(UIElement.ID));
+ }
+ }
+ return pageMap;
+ }
+
+ /**
+ * whether the given (node in UIElementTree) UIElement contains children of
+ * group type.
+ *
+ * @param parent
+ * @return boolean, true if it does, false otherwise.
+ */
+ public boolean hasChildUIGroupElement(UIElement parent) {
+ boolean retVal = false;
+ try {
+ if (parent.getChildCount() > 0) {
+ for (int i = 0; i < parent.getChildCount(); i++) {
+ if (parent.getChild(i) instanceof SimpleUIElementGroup) {
+ retVal = true;
+ break;
+ }
+ }
+ }
+ } catch (SimpleElementException see) {
+ retVal = false;
+ }
+ return retVal;
+ }
+
+ /**
+ * whether the given (node in UIElementTree) UIElement contains children of
+ * UIElement type.
+ *
+ * @param parent
+ * @return boolean, true if it does, false otherwise.
+ */
+ public boolean hasChildUIElement(UIElement parent) {
+ boolean retVal = false;
+ try {
+ if (parent.getChildCount() > 0) {
+ for (int i = 0; i < parent.getChildCount(); i++) {
+ if (parent.getChild(i) instanceof InputUIElement) {
+ retVal = true;
+ break;
+ }
+ }
+ }
+ } catch (SimpleElementException see) {
+ retVal = false;
+ }
+ return retVal;
+ }
+
+ /**
+ * If the order vector contains the page id return, do not add it to order
+ * vector. HashMap will not allow duplicate keys.
+ *
+ * @param pageId
+ */
+ private void addToOrderVector(String pageId) {
+ String containerIds = null;
+ for (int i = 0; i < orderVector.size(); i++) {
+ containerIds = (String) orderVector.get(i);
+ if (containerIds.equalsIgnoreCase(pageId))
+ return;
+ }
+ orderVector.add(pageId);
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/UIWizardPage.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/UIWizardPage.java
new file mode 100644
index 0000000000..6dd79be032
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/UIWizardPage.java
@@ -0,0 +1,330 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.pages;
+
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+
+import org.eclipse.jface.dialogs.IDialogSettings;
+import org.eclipse.jface.wizard.IWizard;
+import org.eclipse.jface.wizard.IWizardContainer;
+import org.eclipse.jface.wizard.IWizardPage;
+import org.eclipse.swt.graphics.Image;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Shell;
+import org.eclipse.ui.PlatformUI;
+
+import org.eclipse.cdt.ui.templateengine.event.PatternEvent;
+import org.eclipse.cdt.ui.templateengine.event.PatternEventListener;
+import org.eclipse.cdt.ui.templateengine.uitree.UIElement;
+
+
+/**
+ * UIWizardPage provides implementation IWizardPage. UIWizardPage is a
+ * WizardPage.
+ */
+
+public class UIWizardPage extends UIPage implements IWizardPage, PatternEventListener {
+
+ /**
+ * This map will contain reference to the source widgets, which has generated the
+ * SWT events. If this map contains an event source, the error message will not be cleared.
+ */
+ HashMap/*<Object, String>*/ validInvalid;
+
+ /**
+ * Page Name
+ */
+ private String name;
+
+ /**
+ * The Wizard to which the Page belongs. null, If this page is yet to be added to a Wizard.
+ */
+ private IWizard wizard = null;
+
+ /**
+ * Indicates whether this page is complete.
+ */
+ private boolean isPageComplete = true;
+
+ /**
+ * That page that was shown right before this page became visible. null if none.
+ */
+ private IWizardPage previousPage = null;
+
+ private IWizardPage nextPage = null;
+
+ private Map valueStore;
+
+ /**
+ * Title of the page, Page Name and UIElement group are the parameters.
+ *
+ * @param title
+ * Title of this page
+ * @param pageName
+ * Name of this page
+ * @param uiElement
+ * The UIElement group.
+ */
+ public UIWizardPage(String title, String pageName, UIElement uiElement, Map/*<String, String>*/ valueStore) {
+ super(title, uiElement, valueStore);
+ name = pageName;
+ validInvalid = new HashMap/*<Object, String>*/();
+ this.valueStore = valueStore;
+ }
+
+ /**
+ * returns true if the page is complete, and there is a next page to flip.
+ *
+ * @return boolean. true if can flip to next page, otherwise false.
+ */
+ public boolean canFlipToNextPage() {
+ boolean retVal = false;
+
+ if (isPageComplete() && (getNextPage() != null))
+ retVal = true;
+
+ return retVal;
+ }
+
+ /**
+ * Returns the wizard container for this wizard page. null, if wizard page
+ * is yet to be adedd to a wizard, or the wizard is yet to be added to a
+ * container.
+ */
+ protected IWizardContainer getContainer() {
+ if (wizard == null)
+ return null;
+
+ return wizard.getContainer();
+ }
+
+ /**
+ * Retruns the dialog setting for this wizard page. null, if none exists.
+ *
+ * @return IDialogSettings, if Wizard is not set null.
+ */
+
+ protected IDialogSettings getDialogSettings() {
+ if (wizard == null)
+ return null;
+
+ return wizard.getDialogSettings();
+ }
+
+ /**
+ * Overloaded from DialogPage get the Image from the super class,
+ * DialogPage. if not defined, then the default page Image is returned.
+ *
+ * @return Image.
+ */
+
+ public Image getImage() {
+ Image result = super.getImage();
+
+ if (result == null && wizard != null)
+ return wizard.getDefaultPageImage();
+
+ return result;
+ }
+
+ /**
+ * @return String, page Name.
+ */
+ public String getName() {
+ return name;
+ }
+
+ /**
+ * gets the Nextpage to be displayed, if set.
+ *
+ * @return IWizardPage.
+ */
+ public IWizardPage getNextPage() {
+ if (nextPage != null)
+ return nextPage;
+
+ if (wizard == null)
+ return null;
+
+ return wizard.getNextPage(this);
+ }
+
+ public void setNextPage(IWizardPage page) {
+ nextPage = page;
+ }
+
+ /**
+ * returns the PreviousPage, if Previous page is not initialized. Wizard is
+ * checked for previous page. if wizard for this page is not set null is
+ * returned.
+ *
+ * @return IWizardPage
+ */
+ public IWizardPage getPreviousPage() {
+ if (previousPage != null)
+ return previousPage;
+
+ if (wizard == null)
+ return null;
+
+ return wizard.getPreviousPage(this);
+
+ }
+
+ /**
+ * Overloaded from DialogPage
+ */
+ public Shell getShell() {
+ IWizardContainer container = getContainer();
+
+ if (container == null)
+ return null;
+
+ return container.getShell();
+ }
+
+ /**
+ * returns the Wizard instance to which this page is added.
+ *
+ * @return IWizard.
+ */
+ public IWizard getWizard() {
+ return wizard;
+ }
+
+ /**
+ * is this is the current page being displayed.
+ *
+ * @return boolean, true if this is the current page. otherwise false.
+ */
+ protected boolean isCurrentPage() {
+ boolean retVal = false;
+ if ((getContainer() != null) && (this == getContainer().getCurrentPage()))
+ retVal = true;
+
+ return retVal;
+ }
+
+ /**
+ * @return boolean, true if this page is complete, otherwise false.
+ */
+ public boolean isPageComplete() {
+ return isPageComplete && getComposite() != null;
+ }
+
+ /**
+ * Methods from IDialOogPage
+ */
+
+ public void setPageComplete(boolean complete) {
+ isPageComplete = complete;
+
+ if (isCurrentPage())
+ getContainer().updateButtons();
+ }
+
+ /**
+ * Method from IWizardPage
+ *
+ */
+ public void setPreviousPage(IWizardPage page) {
+ previousPage = page;
+ }
+
+ /**
+ * set the Wizard for this page, the wizard will contain this page. In the
+ * list of pages which will be displayed as part of this Wizard.
+ *
+ */
+ public void setWizard(IWizard newWizard) {
+ wizard = newWizard;
+ }
+
+ /**
+ * @return String, Page name of this page.
+ */
+ public String toString() {
+ return name;
+ }
+
+ /**
+ * Creates the top level control for this dialog page under the given parent
+ * composite. call the super createControl, get the Composite and set this
+ * page as PatternEventListener.
+ *
+ * @param parent
+ * the parent composite
+ */
+ public void createControl(Composite parent) {
+ super.createControl(parent);
+ (super.getComposite()).addPatternListener(this);
+ (super.getComposite()).getUIElement().setValues(valueStore);
+
+
+ // Page complete is set true of false, based on Mandatory attribute
+ // and Widgets contents.
+ setPageComplete(super.getComposite().isValid());
+ PlatformUI.getWorkbench().getHelpSystem().setHelp(super.getControl(), pageId);
+ }
+
+ /**
+ * This method is implemented to handle the PatternEvent's generated by SWT
+ * widges contained in this page. When the user enters data violating the
+ * pattern of data expected by this SWT widgets, a PatternEvent is fired to
+ * the Container. Which has to reflect the same as an ErrorMeesage. Get the
+ * source of the PatternEvent, and the error String causing the
+ * PatternEvent. Store this pair in validInvalid HashMap.
+ *
+ */
+ public void patternPerformed(PatternEvent patternEvent) {
+ if (!patternEvent.getValid()) {
+
+ validInvalid.put(patternEvent.getSource(), patternEvent.toString());
+ setErrorMessage(getErrorString());
+ setPageComplete(validInvalid.isEmpty() && super.getComposite().isValid());
+
+ } else {
+
+ validInvalid.remove(patternEvent.getSource());
+ setPageComplete(validInvalid.isEmpty() && super.getComposite().isValid());
+ if (validInvalid.isEmpty()) {
+ setErrorMessage(null);
+ } else {
+ setErrorMessage(getErrorString());
+ }
+ }
+
+ getContainer().updateMessage();
+ }
+
+ /**
+ * Iterate through the validInvalid HashMap, formulate the error string
+ * retrun the same. This will ensure that the proper error string is
+ * updated.
+ *
+ * @return
+ */
+ private String getErrorString() {
+ Iterator iterator = validInvalid.keySet().iterator();
+ String message = ""; //$NON-NLS-1$
+
+ // only display one error message at a time
+ if (iterator.hasNext()) {
+
+ message = (String) validInvalid.get(iterator.next());
+ }
+ return message;
+ }
+
+}
+
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/messages.properties b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/messages.properties
new file mode 100644
index 0000000000..78d3c8dc45
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/pages/messages.properties
@@ -0,0 +1,27 @@
+###############################################################################
+# Copyright (c) 2007 Symbian Software Limited and others.
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Eclipse Public License v1.0
+# which accompanies this distribution, and is available at
+# http://www.eclipse.org/legal/epl-v10.html
+#
+# Contributors:
+# Symbian - Initial API and implementation
+###############################################################################
+
+NewProjectCreationPage.0=\ is an invalid name on this platform.
+NewProjectCreationPage.1=\ is too long. Project names must be less than 32 chars.
+NewProjectCreationPage.3=Enter a name and location for the new CDT project.
+TemplateInputDialog.0=Name :
+TemplateInputDialog.1=Value :
+TemplateInputDialog.2=Add a shared default value
+TemplateInputDialog.3=Edit a shared default value
+TemplateInputDialog.4=Template data must not be empty
+TemplatePreferencePage.0=Default input values for all templates:
+TemplatePreferencePage.1=Message from Dialog Validator
+TemplatePreferencePage.2=Duplicate Entry\!
+TemplatePreferencePage.3=Are you sure want to delete ?
+TemplatePreferencePage.4=Delete a shared default value
+TemplatePreferencePage.5=Templates Global Values Table
+TemplatePreferencePage.6=Updates changed key-value pair
+TemplatePreferencePage.7=Deletes key-value pair
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/GenericUIElementGroup.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/GenericUIElementGroup.java
new file mode 100644
index 0000000000..56d14af1cf
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/GenericUIElementGroup.java
@@ -0,0 +1,174 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.eclipse.cdt.ui.templateengine.uitree.uiwidgets.UIComposite;
+
+
+/**
+ *
+ * The GenericUIElementGroup extends UIElement, implements the default behaviour
+ * expected from UIElementGroup. This gives behaviour expected for PAGES-ONLY
+ * type. Any other type of UIElement groups can override the definitions given
+ * to methods in this class.
+ *
+ */
+
+public class GenericUIElementGroup extends UIElement {
+
+ /**
+ * Type of UIElement group. The possible values are PAGES_ONLY, PAGES_TAB,
+ * PAGES_TREE, PAGES_TREE_TREE, PAGES_TAB_TREE.
+ */
+ public static String PAGES_ONLY = "PAGES-ONLY"; //$NON-NLS-1$
+ public static String PAGES_TAB = "PAGES-TAB"; //$NON-NLS-1$
+ public static String LOGTYPE = "UIElement"; //$NON-NLS-1$
+
+ UIGroupTypeEnum type = null;
+
+
+ /**
+ * child list for this UIElement
+ */
+ private List/*<UIElement>*/ childList;
+
+ /**
+ * Call UIElement constructor by passing Attributes as param.
+ *
+ * @param attribute
+ */
+ public GenericUIElementGroup(UIGroupTypeEnum type, UIAttributes/*<String, String>*/ attribute) {
+ super(attribute);
+ this.type = type;
+ this.childList = new ArrayList/*<UIElement>*/();
+ }
+
+ /**
+ * @see UIElement
+ */
+ public void setValues(Map/*<String, String>*/ valueMap) {
+ int childCount = getChildCount();
+
+ for (int i = 0; i < childCount; i++) {
+ getChild(i).setValues(valueMap);
+ }
+ }
+
+ /**
+ * @see UIElement
+ */
+ public Map/*<String, String>*/ getValues() {
+
+ HashMap/*<String, String>*/ valueMap = new HashMap/*<String, String>*/();
+ int childCount = getChildCount();
+
+ for (int i = 0; i < childCount; i++) {
+ valueMap.putAll(getChild(i).getValues());
+ }
+
+ return valueMap;
+ }
+
+ /**
+ * @see UIElement
+ */
+ public void createWidgets(UIComposite uiComposite) {
+ int childCount = getChildCount();
+
+ // call createWidgets on all the contained
+ // UI wigets.
+ if (uiComposite != null) {
+ for (int i = 0; i < childCount; i++) {
+ getChild(i).createWidgets(uiComposite);
+ }
+ uiComposite.setData(".uid", getAttributes().get(UIElement.ID)); //$NON-NLS-1$
+ }
+ }
+
+ /**
+ * dispose the Widget, releasing any resources occupied by this widget. The
+ * same is called on the child list.
+ *
+ * @see UIElement
+ */
+ public void disposeWidget() {
+ int childCount = getChildCount();
+
+ for (int i = 0; i < childCount; i++)
+ getChild(i).disposeWidget();
+ }
+
+ /**
+ * getThe child UIElement at the given index. This method throws
+ * SimpleElementException, if invoked on a InputUIElement.
+ *
+ * @see UIElement
+ * @param index
+ * @return child uiElement
+ */
+ public UIElement getChild(int index) {
+ return (UIElement) childList.get(index);
+ }
+
+ /**
+ * add the given UIElement to the childList. This method throws
+ * SimpleElementException, if invoked on a InputUIElement.
+ *
+ * @see UIElement
+ * @param aUIElement
+ */
+ public void addToChildList(UIElement aUIElement) {
+
+ childList.add(aUIElement);
+ }
+
+ /**
+ * returns the child count of UIElement. This method throws
+ * SimpleElementException, if invoked on a InputUIElement.
+ *
+ * @see UIElement
+ * @return the child count of UIElement
+ */
+ public int getChildCount() {
+
+ return childList.size();
+ }
+
+ /**
+ * gets the type of this group. This is not used as of now. but can be used
+ * during UIPage construction.
+ */
+ public UIGroupTypeEnum getType() {
+
+ return type;
+ }
+
+ // @see UIElement
+ public boolean isValid() {
+
+ boolean retVal = true;
+
+ int childCount = getChildCount();
+ for (int i = 0; i < childCount; i++)
+ if (!getChild(i).isValid()) {
+ retVal = false;
+ break;
+ }
+
+ return retVal;
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/IPatternMatchingTable.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/IPatternMatchingTable.java
new file mode 100644
index 0000000000..479d7018c3
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/IPatternMatchingTable.java
@@ -0,0 +1,26 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree;
+
+/**
+ * This class contains the patter strings for a text widget
+ *
+ * @since 4.0
+ */
+public class IPatternMatchingTable {
+
+ public static final String TEXT = new String("Text"); //$NON-NLS-1$
+ public static final String FREETEXT = new String("FreeText"); //$NON-NLS-1$
+ public static final String FILENAME = new String("FileName"); //$NON-NLS-1$
+ public static final String TEXTPATTERNVALUE = "[A-Za-z0-9\\!\\?\\.: ]*"; //$NON-NLS-1$
+ public static final String FREETEXTPATTERNVALUE = "[A-Za-z0-9() \\.\\s]*"; //$NON-NLS-1$
+ public static final String FILEPATTERNVALUE = "([A-Za-z][:])?[[\\|\\\\|/]?[_!@#\\$%\\^()\\-+{}\\[\\]=;',A-Za-z0-9\\. ]*]*"; //$NON-NLS-1$
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/IUIElementTreeBuilderHelper.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/IUIElementTreeBuilderHelper.java
new file mode 100644
index 0000000000..cac37eca00
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/IUIElementTreeBuilderHelper.java
@@ -0,0 +1,31 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree;
+
+import org.w3c.dom.Element;
+
+/**
+ * This interface has methods which returns a UIElement, given an Element.
+ * Method to return a List of Elements, given an Element.
+ *
+ * @since 4.0
+ */
+
+public interface IUIElementTreeBuilderHelper {
+ /**
+ * Returns the UIElement.
+ * @param element
+ * @return UIElement
+ *
+ * @since 4.0
+ */
+ public UIElement getUIElement(Element element);
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/IUIElementTreeBuilderManager.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/IUIElementTreeBuilderManager.java
new file mode 100644
index 0000000000..80917cdc47
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/IUIElementTreeBuilderManager.java
@@ -0,0 +1,32 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree;
+
+import org.w3c.dom.Element;
+
+/**
+ * This interface provides methods, which will be implemented by Tree builder
+ * class.
+ *
+ * @since 4.0
+ */
+
+public interface IUIElementTreeBuilderManager {
+ /**
+ * Creates the UIElement Tree
+ * @param ui
+ * @param parent
+ *
+ * @since 4.0
+ */
+ public void createUIElementTree(UIElement ui, Element parent);
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/InputUIElement.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/InputUIElement.java
new file mode 100644
index 0000000000..c2f9abc768
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/InputUIElement.java
@@ -0,0 +1,78 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree;
+
+import org.eclipse.cdt.ui.templateengine.SimpleElementException;
+
+/**
+ * InputUIElement, an abstract class extends UIElement. Provides implementation
+ * to some of the methods. It provides definitions to those methods which
+ * doesn't apply to InuputUIElement's. SimpleElementException is thrown from
+ * these methods.
+ *
+ */
+public abstract class InputUIElement extends UIElement {
+
+ public static final String INPUTTYPE = new String("input"); //$NON-NLS-1$
+ public static final String MULTILINETYPE = new String("multiline"); //$NON-NLS-1$
+ public static final String SELECTTYPE = new String("select"); //$NON-NLS-1$
+ public static final String BOOLEANTYPE = new String("boolean"); //$NON-NLS-1$
+ public static final String BROWSETYPE = new String("browse"); //$NON-NLS-1$
+ public static final String STRINGLISTTYPE = new String("stringlist"); //$NON-NLS-1$
+ public static final String SPECIALLISTTYPE = new String("speciallist"); //$NON-NLS-1$
+ public static final String MANDATORY = new String("mandatory"); //$NON-NLS-1$
+ public static final String INPUTPATTERN = new String("pattern"); //$NON-NLS-1$
+ public static final String DEFAULT = new String("default"); //$NON-NLS-1$
+ public static final String WIDGETLABEL = new String("label"); //$NON-NLS-1$
+ public static final String BROWSELABEL = new String(" Browse.. "); //$NON-NLS-1$
+ public static final String CONTENTS = new String(" contents"); //$NON-NLS-1$
+ public static final String ISINVALID = new String(" is Invalid. "); //$NON-NLS-1$
+ public static final String CHECKPROJECT = new String("checkproject"); //$NON-NLS-1$
+ public static final String NULL = new String("null"); //$NON-NLS-1$
+ public static final String SIZE = new String("size"); //$NON-NLS-1$
+ public static final String HIDDEN = new String("hidden"); //$NON-NLS-1$
+ public static final String NAME = new String("name"); //$NON-NLS-1$
+ public static final String SELECTED = new String("selected"); //$NON-NLS-1$
+
+
+ protected InputUIElement(UIAttributes/*<String, String>*/ uiAttribute) {
+ super(uiAttribute);
+ }
+
+ /**
+ * Overloaded from UIElement, It does not apply to InputUIElement
+ *
+ * @see UIElement
+ * @param uiElement
+ * @throws SimpleElementException
+ */
+ public void addToChildList(UIElement uiElement) throws SimpleElementException {
+ throw new SimpleElementException();
+ }
+
+ /**
+ * Overloaded from UIElement, It does not apply to InputUIElement
+ *
+ * @see UIElement
+ */
+ public int getChildCount() throws SimpleElementException {
+ throw new SimpleElementException();
+ }
+
+ /**
+ * Overloaded from UIElement, It does not apply to InputUIElement
+ *
+ * @see UIElement
+ */
+ public UIElement getChild(int index) throws SimpleElementException {
+ throw new SimpleElementException();
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/SimpleUIElementGroup.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/SimpleUIElementGroup.java
new file mode 100644
index 0000000000..b7132cf937
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/SimpleUIElementGroup.java
@@ -0,0 +1,64 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree;
+
+import java.util.Map;
+
+import org.eclipse.cdt.ui.templateengine.uitree.uiwidgets.UIComposite;
+
+
+/**
+ * This is a PAGES_ONLY implementation for UIElement group. It uses the method
+ * implementation for UIElement provided by GenericUIElementGroup.
+ */
+
+public class SimpleUIElementGroup extends GenericUIElementGroup {
+
+ public SimpleUIElementGroup(UIAttributes/*<String, String>*/ attribute) {
+ super(UIGroupTypeEnum.PAGES_ONLY, attribute);
+ }
+
+ /**
+ * @see UIElement
+ */
+ public void setValues(Map/*<String, String>*/ valueMap) {
+ super.setValues(valueMap);
+ }
+
+ /**
+ * @see UIElement
+ */
+ public Map/*<String, String>*/ getValues() {
+ return super.getValues();
+ }
+
+ /**
+ * @see UIElement
+ */
+ public void createWidgets(UIComposite uiComposite) {
+ super.createWidgets(uiComposite);
+ }
+
+ /**
+ * dispose the Widget, releasing any resources occupied by this widget. The
+ * same is called on the child list.
+ *
+ * @see UIElement
+ */
+ public void disposeWidget() {
+ super.disposeWidget();
+ }
+
+ // @see UIElement
+ public boolean isValid() {
+ return super.isValid();
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIAttributes.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIAttributes.java
new file mode 100644
index 0000000000..0e7fdc43d2
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIAttributes.java
@@ -0,0 +1,27 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree;
+
+import java.util.HashMap;
+
+/**
+ *
+ * Every UIElement will be associated with attributes. This class extends
+ * HashMap. It just provides a convenient way to store Key , value pairs. This
+ * class is for clarity in usage. We need not use HashMap for attributes,
+ * instead we can use UIAttributes for attributes.
+ *
+ */
+
+public class UIAttributes/*<K, V>*/ extends HashMap/*<String, String>*/ {
+
+ private static final long serialVersionUID = 0000000000L;
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIElement.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIElement.java
new file mode 100644
index 0000000000..524b2316e2
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIElement.java
@@ -0,0 +1,131 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree;
+
+import java.util.Map;
+
+import org.eclipse.cdt.ui.templateengine.SimpleElementException;
+import org.eclipse.cdt.ui.templateengine.uitree.uiwidgets.UIComposite;
+
+
+/**
+ * UIElement describes the abstract behaviour expected from GenericUIElementGroup and
+ * InputUIElement. Some of the methods are meaningful to group Element. They will throw
+ * SimpleElementException when invoked on InputUIElement.
+ */
+
+public abstract class UIElement {
+
+ /**
+ * Parent of this UIElement
+ */
+ private UIElement parent;
+
+ /**
+ * Attributes of this UIElement
+ */
+ protected UIAttributes/*<String, String>*/ attribute;
+ public static final String ID = "id"; //$NON-NLS-1$
+ public static final String TYPE = "type"; //$NON-NLS-1$
+ public static final String DESCRIPTION = "description"; //$NON-NLS-1$
+ public static final String TITLE = "label"; //$NON-NLS-1$
+ public static final String IMAGELOCATION = "image"; //$NON-NLS-1$
+
+
+ public UIElement(UIAttributes/*<String, String> */uiAttribute) {
+ attribute = uiAttribute;
+ }
+
+ /**
+ * set the Parent of this UIElement
+ */
+ public void setParent(UIElement parent) {
+ this.parent = parent;
+ }
+
+ /**
+ * get the Parent of this UIElement
+ */
+ public UIElement getParent() {
+ return parent;
+ }
+
+ /**
+ * get the attributes of this UIElement
+ */
+ public UIAttributes/*<String, String>*/ getAttributes() {
+ return attribute;
+ }
+
+ /**
+ * set the Values of UIElements from the given HashMap. This method is called recursively on all the childrens, if the UIElement instance on which this mehtod called is a GenericUIElementGroup. return void.
+ */
+ public abstract void setValues(Map/*<String, String>*/ valueMap);
+
+ /**
+ * get The values as a HashMap. This method is called recursively on all the childrens, if the UIElement instance on which this mehtod called is a GenericUIElementGroup.
+ * @return HashMap.
+ */
+ public abstract Map/*<String, String>*/ getValues();
+
+ /**
+ * This method adds UIWidets to UIComposite. This method is called
+ * recursively on all the childrens, if the UIElement instance on which this
+ * mehtod called is a GenericUIElementGroup.
+ *
+ * @param uiComposite
+ */
+ public abstract void createWidgets(UIComposite uiComposite);
+
+ /**
+ * disposes the widget. This method is called recursively on all the
+ * childrens, if the UIElement instance on which this mehtod is called, is a
+ * GenericUIElementGroup.
+ *
+ */
+ public abstract void disposeWidget();
+
+ /**
+ * getThe child UIElement at the given index. This method throws
+ * SimpleElementException, if invoked on a InputUIElement.
+ *
+ * @param index
+ * @return The child UIElement
+ * @throws SimpleElementException
+ */
+ public abstract UIElement getChild(int index) throws SimpleElementException;
+
+ /**
+ * add the given UIElement to the childList. This method throws
+ * SimpleElementException, if invoked on a InputUIElement.
+ *
+ * @param uiElement
+ * @throws SimpleElementException
+ */
+ public abstract void addToChildList(UIElement uiElement) throws SimpleElementException;
+
+ /**
+ * returns the child count of UIElement. This method throws
+ * SimpleElementException, if invoked on a InputUIElement.
+ *
+ * @return the child count of UIElement
+ * @throws SimpleElementException
+ */
+ public abstract int getChildCount() throws SimpleElementException;
+
+ /**
+ * The return value depends on the state of the UIElement. This information
+ * is used by UIPage to enable or disable the UIPage.
+ *
+ * @return boolean.
+ */
+ public abstract boolean isValid();
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIElementTreeBuilderHelper.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIElementTreeBuilderHelper.java
new file mode 100644
index 0000000000..5da6fb1fe5
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIElementTreeBuilderHelper.java
@@ -0,0 +1,183 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree;
+
+import java.util.HashMap;
+import java.util.List;
+
+import org.w3c.dom.Element;
+import org.w3c.dom.NamedNodeMap;
+import org.w3c.dom.Node;
+
+import org.eclipse.cdt.core.templateengine.TemplateDescriptor;
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+import org.eclipse.cdt.core.templateengine.TemplateEngineHelper;
+import org.eclipse.cdt.ui.templateengine.uitree.uiwidgets.UIBooleanWidget;
+import org.eclipse.cdt.ui.templateengine.uitree.uiwidgets.UIBrowseWidget;
+import org.eclipse.cdt.ui.templateengine.uitree.uiwidgets.UISelectWidget;
+import org.eclipse.cdt.ui.templateengine.uitree.uiwidgets.UISpecialListWidget;
+import org.eclipse.cdt.ui.templateengine.uitree.uiwidgets.UIStringListWidget;
+import org.eclipse.cdt.ui.templateengine.uitree.uiwidgets.UITextWidget;
+
+
+/**
+ * UIElementTreeBuilderHelper provides methods to convert an Element (XML) into
+ * UIElement. The UIElement can be a simple UI Widget or a group.
+ */
+
+public class UIElementTreeBuilderHelper implements IUIElementTreeBuilderHelper {
+
+ /**
+ * TemplateDescriptor representing the TemplaeDescriptor XML.
+ */
+ private TemplateDescriptor templateDescriptor = null;
+
+ private Element element;
+
+ /**
+ * Constructor, takes an TemplateDescriptor instance as parameter.
+ *
+ * @param templateDescriptor
+ */
+ public UIElementTreeBuilderHelper(TemplateDescriptor templateDescriptor) {
+ this.templateDescriptor = templateDescriptor;
+ }
+
+ /**
+ *
+ * @return List of child Elements for the given
+ */
+ public List getPropertyGroupList() {
+ return templateDescriptor.getPropertyGroupList();
+ }
+
+ /**
+ * Given an XML Element, representing a PropertyElement. A UIElement for the
+ * same is returned. The Type attribute is verified, based on Type
+ * approprioate UIWidget is instantiated. This calss the getUIWidget private
+ * method.
+ *
+ * @param element
+ * @return UIElement.
+ */
+ public UIElement getUIElement(Element element) {
+
+ this.element = element;
+ UIElement retUIElement = null;
+ UIAttributes/*<String, String>*/ uiAttributes = new UIAttributes/*<String, String>*/();
+
+ NamedNodeMap list = element.getAttributes();
+ for (int i = 0, s = list.getLength(); i < s; i++) {
+ Node attribute = list.item(i);
+ uiAttributes.put(attribute.getNodeName(), attribute.getNodeValue());
+ }
+
+ retUIElement = getUIWidget(uiAttributes);
+
+ return retUIElement;
+ }
+
+ /**
+ * Given an XML Element, representing a PropertyElement. A UIElement for the
+ * same is returned. The Type attribute is verified, based on Type
+ * approprioate UIWidget is instantiated.
+ *
+ * @param uiAttributes
+ * @return UIElement.
+ */
+ private UIElement getUIWidget(UIAttributes/*<String, String>*/ uiAttributes) {
+
+ String type = (String) uiAttributes.get(InputUIElement.TYPE);
+
+ UIElement widgetElement = null;
+ String itemName = null;
+ String itemValue = null;
+ String itemSelected = null;
+ String nameStr = null;
+ String valueStr = null;
+ String selected = null;
+
+ if (new Boolean((String)uiAttributes.get(InputUIElement.HIDDEN)).booleanValue())
+ return null;
+ if (type.equalsIgnoreCase("") || type == null) //$NON-NLS-1$
+ return null;
+
+ // UIWidgets
+ if (type.equalsIgnoreCase(InputUIElement.INPUTTYPE)) {
+ widgetElement = new UITextWidget(uiAttributes);
+ }
+
+ if (type.equalsIgnoreCase(InputUIElement.MULTILINETYPE)) {
+ widgetElement = new UITextWidget(uiAttributes);
+ }
+
+ if (type.equalsIgnoreCase(InputUIElement.SELECTTYPE)) {
+
+ HashMap/*<String, String>*/ itemMap = new HashMap/*<String, String>*/();
+ List/*<Element>*/ itemList = TemplateEngine.getChildrenOfElement(element);
+
+ for (int i = 0, l = itemList.size(); i < l; i++) {
+ Element itemElement = (Element) itemList.get(i);
+ NamedNodeMap itemAttrList = itemElement.getAttributes();
+
+ for (int j = 0, l1 = itemAttrList.getLength(); j < l1; j++) {
+ Node itemAttr = itemAttrList.item(j);
+ itemName = itemAttr.getNodeName();
+ itemValue = itemAttr.getNodeValue();
+
+ if (itemName.equals(InputUIElement.TITLE)) {
+
+ selected = itemValue;
+ nameStr = new String(itemValue);
+ } else if (itemName.equals(InputUIElement.NAME))
+ valueStr = new String(itemValue);
+
+ if (itemName.equals(InputUIElement.SELECTED))
+ if (itemValue.equals(TemplateEngineHelper.BOOLTRUE))
+ itemSelected = selected;
+
+ itemMap.put(nameStr, valueStr);
+ }
+ }
+
+ widgetElement = new UISelectWidget(uiAttributes, itemMap, itemSelected);
+ }
+
+ if (type.equalsIgnoreCase(InputUIElement.BOOLEANTYPE)) {
+ widgetElement = new UIBooleanWidget(uiAttributes);
+ }
+
+ if (type.equalsIgnoreCase(InputUIElement.BROWSETYPE)) {
+ widgetElement = new UIBrowseWidget(uiAttributes);
+ }
+
+ if (type.equalsIgnoreCase(InputUIElement.STRINGLISTTYPE)) {
+ widgetElement = new UIStringListWidget(uiAttributes);
+ }
+
+ if (type.equalsIgnoreCase(InputUIElement.SPECIALLISTTYPE)) {
+ widgetElement = new UISpecialListWidget(uiAttributes);
+ }
+
+ // PAGES(Groups).
+
+ if (type.equalsIgnoreCase(GenericUIElementGroup.PAGES_ONLY)) {
+ widgetElement = new SimpleUIElementGroup(uiAttributes);
+ }
+
+ if (type.equalsIgnoreCase(GenericUIElementGroup.PAGES_TAB)) {
+ // Note: This is not implemented now as we haven't found a use case
+ // for generating UI pages as TABS in a single page.
+ }
+
+ return widgetElement;
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIElementTreeBuilderManager.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIElementTreeBuilderManager.java
new file mode 100644
index 0000000000..7296f6a22c
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIElementTreeBuilderManager.java
@@ -0,0 +1,112 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree;
+
+import java.util.List;
+
+import org.w3c.dom.Element;
+
+import org.eclipse.cdt.core.templateengine.TemplateEngine;
+import org.eclipse.cdt.core.templateengine.TemplateEngineUtil;
+import org.eclipse.cdt.ui.templateengine.SimpleElementException;
+
+
+/**
+ *
+ * call setgetUIElementTreeRootNull(), before createUIElementTree(...).
+ * UIElementTreeBuilderManager builds a UIElementTree.
+ *
+ * --------------UITree creation algorithm----------------------------
+ * createUIElementTree(UITreeRoot, RootPropertyGroupElement) UITreeRoot is
+ * initially null. createUIElementTree(UIElement parent, XML_Element element)
+ * Step 1. if( parent == null ) parent =
+ * UIElementTreeBuilderHelper.getUIElement(element).
+ * Step 2. else {
+ * Step 3. List
+ * childList = getChildList(element);
+ * Step 4. Iterator I =
+ * getIterator(childList);
+ * Step 5. for every element belonging to childList
+ * {
+ * Step 6. uiElement = getUIElement (element from childList); advance I to next
+ * Element. uiElement .setParent(parent); parent.put(uiElement );
+ * createUIElementTree(uiElement, element from childList);
+ * }
+ * }
+ * ---------------------------------------------------------------------
+ *
+ */
+
+public class UIElementTreeBuilderManager implements IUIElementTreeBuilderManager {
+ /**
+ * referenc to iUIElementTreeBuilderHelper, which returns UIElement for Element.
+ */
+ private UIElementTreeBuilderHelper uiElementTreeBuilderHelper;
+
+ /**
+ * The root of the UIElementTree.
+ */
+ private UIElement uiTreeRoot = null;
+
+ /**
+ *
+ * @param uiElementTreeBuilderHelper
+ */
+ public UIElementTreeBuilderManager(UIElementTreeBuilderHelper uiElementTreeBuilderHelper) {
+ this.uiElementTreeBuilderHelper = uiElementTreeBuilderHelper;
+ }
+
+ /**
+ * This method create the UIElementTree, by following the algorithm given
+ * above.
+ */
+ public void createUIElementTree(UIElement uiParent, Element element) {
+ if (uiParent == null) {
+ uiTreeRoot = uiElementTreeBuilderHelper.getUIElement(element);
+ uiParent = uiTreeRoot;
+ }
+
+ if ((uiParent != null) && (uiParent instanceof GenericUIElementGroup)) {
+ List/*<Element>*/ childList = TemplateEngine.getChildrenOfElement(element);
+ for (int listIndex = 0, l = childList.size(); listIndex < l; listIndex++) {
+ UIElement uiElement = uiElementTreeBuilderHelper.getUIElement((Element) childList.get(listIndex));
+ if (uiElement != null) {
+ uiElement.setParent(uiParent);
+ } else {
+ continue;
+ }
+ try {
+ uiParent.addToChildList(uiElement);
+ } catch (SimpleElementException exp) {
+ TemplateEngineUtil.log(exp);
+ }
+ createUIElementTree(uiElement, (Element) childList.get(listIndex));
+ }
+ }
+ }
+
+ /**
+ *
+ * @return UIElement, root UIElement.
+ */
+ public UIElement getUIElementTreeRoot() {
+ return uiTreeRoot;
+ }
+
+ /**
+ * sets the UIElementTree root element to null. This method is invoked
+ * before creating UIElementTree.
+ */
+ public void setUIElementTreeRootNull() {
+ uiTreeRoot = null;
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIGroupTypeEnum.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIGroupTypeEnum.java
new file mode 100644
index 0000000000..179df093cf
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/UIGroupTypeEnum.java
@@ -0,0 +1,42 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree;
+
+
+/**
+ * This class defines various types of UIElement groups.
+ */
+
+public class UIGroupTypeEnum {
+ public static final UIGroupTypeEnum PAGES_ONLY = new UIGroupTypeEnum("PAGES_ONLY"); //$NON-NLS-1$
+ public static final UIGroupTypeEnum PAGES_TAB = new UIGroupTypeEnum("PAGES_TAB"); //$NON-NLS-1$
+
+ private String id;
+
+ private UIGroupTypeEnum(String id) {
+ this.id = id;
+ }
+
+ public boolean equals(Object other) {
+ if(other instanceof UIGroupTypeEnum) {
+ return id.equals(((UIGroupTypeEnum)other).id);
+ }
+ return false;
+ }
+
+ public int hashCode() {
+ return id.hashCode();
+ }
+
+ public String toString() {
+ return id;
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIBooleanWidget.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIBooleanWidget.java
new file mode 100644
index 0000000000..fdc9f5eeca
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIBooleanWidget.java
@@ -0,0 +1,148 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree.uiwidgets;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Button;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Label;
+
+import org.eclipse.cdt.core.templateengine.TemplateEngineHelper;
+import org.eclipse.cdt.ui.templateengine.uitree.InputUIElement;
+import org.eclipse.cdt.ui.templateengine.uitree.UIAttributes;
+import org.eclipse.cdt.ui.templateengine.uitree.UIElement;
+
+
+/**
+ * This gives a Label and Boolean widget.
+ */
+
+public class UIBooleanWidget extends InputUIElement {
+
+ /**
+ * Attributes associated with this widget.
+ */
+ UIAttributes/*<String, String>*/ uiAttribute;
+
+ /**
+ * Boolean widget.
+ */
+ Button button;
+
+ /**
+ * Label of this widget.
+ */
+ Label label;
+
+ /**
+ * Composite to which this widget control is added.
+ */
+ UIComposite uiComposite;
+
+ /**
+ * Constructor.
+ *
+ * @param uiAttribute
+ * attribute associated with this widget.
+ */
+ public UIBooleanWidget(UIAttributes/*<String, String>*/ uiAttribute) {
+ super(uiAttribute);
+ this.uiAttribute = uiAttribute;
+ }
+
+ /**
+ * @return HashMap which contains the values in the Boolean Widget.
+ */
+ public Map/*<String, String>*/ getValues() {
+
+ Map/*<String, String>*/ retMap = new HashMap/*<String, String>*/();
+ Boolean isCheck = new Boolean(button.getSelection());
+ retMap.put(uiAttribute.get(InputUIElement.ID), isCheck.toString());
+
+ return retMap;
+ }
+
+ /**
+ * Set the Boolean widget with new value.
+ *
+ * @param valueMap
+ */
+ public void setValues(Map/*<String, String>*/ valueMap) {
+ String val = (String) valueMap.get(uiAttribute.get(InputUIElement.ID));
+ Boolean bool = new Boolean(val);
+ if (val != null) {
+ button.setSelection(bool.booleanValue());
+ }
+ }
+
+ /**
+ * create a Label and Boolean widget, add it to UIComposite. set Layout for
+ * the widgets to be added to UIComposite. set required parameters to the
+ * Widgets.
+ *
+ * @param uiComposite
+ */
+ public void createWidgets(UIComposite uiComposite) {
+ GridData gridData = null;
+ this.uiComposite = uiComposite;
+
+ label = new Label(uiComposite, SWT.LEFT);
+ label.setText((String) uiAttribute.get(InputUIElement.WIDGETLABEL));
+
+ if (uiAttribute.get(InputUIElement.DESCRIPTION) != null){
+ String tipText = (String) uiAttribute.get(UIElement.DESCRIPTION);
+ tipText = tipText.replaceAll("\\\\r\\\\n", "\r\n"); //$NON-NLS-1$ //$NON-NLS-2$
+ label.setToolTipText(tipText);
+ }
+ gridData = new GridData();
+ gridData.horizontalAlignment = GridData.FILL;
+ gridData.grabExcessHorizontalSpace = true;
+ Composite booleanConatiner = new Composite(uiComposite, SWT.NONE);
+ GridData gridcData = new GridData(GridData.FILL_HORIZONTAL);
+ booleanConatiner.setLayout(new GridLayout());
+ booleanConatiner.setLayoutData(gridcData);
+ button = new Button(booleanConatiner, SWT.CHECK);
+ button.setData(".uid", uiAttribute.get(UIElement.ID)); //$NON-NLS-1$
+ }
+
+ /**
+ * Based on the stae of this Widget return true or false. This return value
+ * will be used by the UIPage to update its(UIPage) state. Return value
+ * depends on the value contained in Boolean Widget. If boolean value
+ * contained is false and Mandatory value from attributes.
+ *
+ * @return boolean.
+ */
+ public boolean isValid() {
+ boolean retVal = true;
+ String mandatory = (String) uiAttribute.get(InputUIElement.MANDATORY);
+
+ if ((button.getSelection() == false) && (mandatory.equalsIgnoreCase(TemplateEngineHelper.BOOLTRUE))) {
+ retVal = false;
+ }
+ return retVal;
+ }
+
+ /**
+ * call the dispose method on the widgets. This is to ensure that the
+ * widgets are properly disposed.
+ */
+ public void disposeWidget() {
+ label.dispose();
+ button.dispose();
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIBrowseWidget.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIBrowseWidget.java
new file mode 100644
index 0000000000..f3a1920826
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIBrowseWidget.java
@@ -0,0 +1,114 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree.uiwidgets;
+
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.events.ModifyListener;
+import org.eclipse.swt.events.SelectionAdapter;
+import org.eclipse.swt.events.SelectionEvent;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Button;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.FileDialog;
+import org.eclipse.swt.widgets.Label;
+import org.eclipse.swt.widgets.Text;
+
+import org.eclipse.cdt.ui.templateengine.uitree.InputUIElement;
+import org.eclipse.cdt.ui.templateengine.uitree.UIAttributes;
+import org.eclipse.cdt.ui.templateengine.uitree.UIElement;
+
+
+/**
+ * This gives a Label and Browse widget.
+ */
+
+public class UIBrowseWidget extends UITextWidget implements ModifyListener {
+ /**
+ * Attributes associated with this widget.
+ */
+ UIAttributes/*<String, String>*/ uiAttribute;
+
+ /**
+ * Browse Button of this widget.
+ */
+ Button button;
+
+ /**
+ * Constructor.
+ *
+ * @param uiAttribute
+ * attribute associated with this widget.
+ */
+ public UIBrowseWidget(UIAttributes/*<String, String>*/ uiAttribute) {
+ super(uiAttribute);
+ this.uiAttribute = uiAttribute;
+ }
+
+ /**
+ * create a Label and Browse widget, add it to UIComposite. set Layout for
+ * the widgets to be added to UIComposite. set required parameters to the
+ * Widgets.
+ *
+ * @param composite
+ */
+ public void createWidgets(UIComposite composite) {
+ uiComposite = composite;
+
+ label = new Label(uiComposite, SWT.NONE | SWT.LEFT);
+ label.setText((String) uiAttribute.get(InputUIElement.WIDGETLABEL));
+
+ // set the tool tip text
+ if (uiAttribute.get(UIElement.DESCRIPTION) != null){
+ String tipText = (String) uiAttribute.get(UIElement.DESCRIPTION);
+ tipText = tipText.replaceAll("\\\\r\\\\n", "\r\n"); //$NON-NLS-1$, //$NON-NLS-2$
+ label.setToolTipText(tipText);
+ }
+ GridData gridData = new GridData(GridData.FILL_HORIZONTAL);
+ gridData.widthHint = 70;
+
+ Composite textConatiner = new Composite(uiComposite, SWT.NONE);
+ textConatiner.setLayout(new GridLayout(2, false));
+
+ textConatiner.setLayoutData(gridData);
+
+ text = new Text(textConatiner, SWT.SINGLE | SWT.LEFT | SWT.BORDER);
+ text.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
+ text.addModifyListener(this);
+
+ // set Default values
+ if (uiAttribute.get(InputUIElement.DEFAULT) != null)
+ text.setText((String) uiAttribute.get(InputUIElement.DEFAULT));
+
+ button = new Button(textConatiner, SWT.PUSH | SWT.LEFT);
+ button.setText(InputUIElement.BROWSELABEL);
+
+ button.addSelectionListener(new SelectionAdapter() {
+ public void widgetSelected(SelectionEvent event) {
+ String fileName = new FileDialog(uiComposite.getShell()).open();
+ if (fileName != null) {
+ text.setText(fileName.toString());
+ }
+ }
+ });
+ }
+
+ /**
+ * call the dispose method on the widgets. This is to ensure that the
+ * widgets are properly disposed.
+ */
+ public void disposeWidget() {
+ label.dispose();
+ text.dispose();
+ button.dispose();
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIComposite.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIComposite.java
new file mode 100644
index 0000000000..03fb8f70c6
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIComposite.java
@@ -0,0 +1,120 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree.uiwidgets;
+
+import java.util.Map;
+import java.util.Vector;
+
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Composite;
+
+import org.eclipse.cdt.ui.templateengine.event.PatternEvent;
+import org.eclipse.cdt.ui.templateengine.event.PatternEventListener;
+import org.eclipse.cdt.ui.templateengine.uitree.UIElement;
+
+
+/**
+ * By extending Composite we can create our own Container. UIComposite can act
+ * as the brdige between the UIPage and the UIWidgets contained in that page.
+ * The PatternEvents generated by the UIWidgets will be fired to the UIPage
+ * which is a PatternEventListener.
+ */
+
+public class UIComposite extends Composite {
+
+ /**
+ * The gruop UIElement corresponding to this UIPage.
+ */
+ private UIElement uiElement;
+
+ /**
+ * The list of PatternEventListeners.
+ */
+ private Vector/*<PatternEventListener>*/ vector;
+
+ /**
+ * parent Composite, and The UIElement corresponding to this page.
+ *
+ * @param parent
+ * @param uiElement
+ */
+ public UIComposite(Composite parent, UIElement uiElement, Map/*<String, String>*/ valueStore) {
+ super(parent, SWT.NONE);
+
+ vector = new Vector/*<PatternEventListener>*/();
+ GridLayout layout = new GridLayout(2, false);
+ layout.marginWidth = 10;
+ layout.marginHeight = 5;
+ this.setLayout(layout);
+ this.setLayoutData(new GridData(GridData.FILL_BOTH));
+
+ this.uiElement = uiElement;
+ this.uiElement.createWidgets(this);
+ }
+
+ /**
+ * add a PatternListener to the list.
+ *
+ * @param patternListener
+ */
+ public void addPatternListener(PatternEventListener patternListener) {
+ vector.add(patternListener);
+ }
+
+ /**
+ * remove the PatternListener from the list.
+ *
+ * @param patternListener
+ */
+ public void removePatternListener(PatternEventListener patternListener) {
+ vector.remove(patternListener);
+ }
+
+ /**
+ * On occurance of PatternEvent this method is called to ivoke
+ * patternPerformed on all the registered listeners. In our application, we
+ * will have just one registered listener.
+ */
+
+ public void firePatternEvent(PatternEvent patternEvent) {
+ for (int i = 0; i < vector.size(); i++) {
+ ((PatternEventListener) vector.get(i)).patternPerformed(patternEvent);
+ }
+ }
+
+ /**
+ * This method will invoke the getValues on UIElement (group Element), which
+ * in turn will invoke the getValues on the UIElement (widgets). This
+ * returns an HashMap of Values.
+ */
+ public Map/*<String, String>*/ getPageData() {
+ return uiElement.getValues();
+ }
+
+ /**
+ * return the UIElement(group UI Element) represented by this UIComposite.
+ *
+ * @return UIElement.
+ */
+ public UIElement getUIElement() {
+ return uiElement;
+ }
+
+ /**
+ * This information is used by UIPages to enable or disable the next button.
+ */
+ public boolean isValid() {
+ return uiElement.isValid();
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UISelectWidget.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UISelectWidget.java
new file mode 100644
index 0000000000..cbfec1c967
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UISelectWidget.java
@@ -0,0 +1,183 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree.uiwidgets;
+
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.Set;
+
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Combo;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Label;
+
+import org.eclipse.cdt.core.templateengine.TemplateEngineHelper;
+import org.eclipse.cdt.ui.templateengine.uitree.InputUIElement;
+import org.eclipse.cdt.ui.templateengine.uitree.UIAttributes;
+import org.eclipse.cdt.ui.templateengine.uitree.UIElement;
+
+
+/**
+ * This gives a Label and Combo widget.
+ */
+public class UISelectWidget extends InputUIElement {
+ /**
+ * Attributes associated with this widget.
+ */
+ UIAttributes/*<String, String>*/ uiAttribute;
+
+ /**
+ * Select widget.
+ */
+ Combo combo;
+
+ /**
+ * Label of this widget.
+ */
+ Label label;
+
+ /**
+ * Composite to which this widget control is added.
+ */
+ UIComposite uiComposite;
+
+ /**
+ * Map contains the values of Select Widget
+ */
+ HashMap/*<String, String>*/ itemMap;
+
+ /**
+ * Default value of Select Widget
+ */
+ String itemSelected;
+
+ /**
+ * Constructor for Select Widget.
+ *
+ * @param attribute
+ * attribute associated with this widget.
+ */
+ public UISelectWidget(UIAttributes/*<String, String>*/ attribute, HashMap/*<String, String>*/ itemMap,
+ String itemSelected) {
+
+ super(attribute);
+ uiAttribute = attribute;
+ this.itemMap = itemMap;
+ this.itemSelected = itemSelected;
+ }
+
+ /**
+ * @return Boolean value contained in the Boolean Widget.
+ */
+ public Map/*<String, String>*/ getValues() {
+
+ Map/*<String, String>*/ retMap = new HashMap/*<String, String>*/();
+ retMap.put(uiAttribute.get(InputUIElement.ID), itemMap.get(combo.getItem(combo.getSelectionIndex())));
+
+ return retMap;
+ }
+
+ /**
+ * Set the Text widget with new value.
+ *
+ * @param valueMap
+ */
+ public void setValues(Map/*<String, String>*/ valueMap) {
+
+ String val = (String) valueMap.get(uiAttribute.get(InputUIElement.ID));
+ if (val != null)
+ val = val.trim();
+ String[] items = combo.getItems();
+ int index = 0;
+ for (int i = 0; i < items.length; i++)
+ if (itemMap.get(items[i]).equals(val))
+ index = i;
+
+ combo.select(index);
+ }
+
+ /**
+ * create a Label and Text widget, add it to UIComposite. set Layout for the
+ * widgets to be added to UIComposite. set required parameters to the
+ * Widgets.
+ *
+ * @param composite
+ */
+ public void createWidgets(UIComposite composite) {
+ GridData gridData = null;
+ uiComposite = composite;
+
+ label = new Label(composite, SWT.LEFT);
+ label.setText((String) uiAttribute.get(InputUIElement.WIDGETLABEL));
+
+ gridData = new GridData();
+ gridData.horizontalAlignment = GridData.FILL;
+ gridData.grabExcessHorizontalSpace = true;
+
+ Composite comboComposite = new Composite(composite, SWT.NONE);
+
+ gridData = new GridData(GridData.FILL_HORIZONTAL);
+ comboComposite.setLayout(new GridLayout());
+ comboComposite.setLayoutData(gridData);
+
+ combo = new Combo(comboComposite, SWT.DROP_DOWN | SWT.READ_ONLY);
+
+ Set keySet = itemMap.keySet();
+ Iterator mapIterator = keySet.iterator();
+
+ int index = 0;
+ int i = 0;
+ while (mapIterator.hasNext()) {
+
+ String key = (String) mapIterator.next();
+ combo.add(key);
+ if (itemSelected.equals(key))
+ index = i;
+ i++;
+ }
+
+ combo.select(index);
+ combo.setData(".uid", uiAttribute.get(UIElement.ID)); //$NON-NLS-1$
+ }
+
+ /**
+ * Based on the stae of this Widget return true or false. This return value
+ * will be used by the UIPage to update its(UIPage) state. Return value
+ * depends on the value contained in Select Widget. If value contained is
+ * null, "" and Mandatory value from attributes.
+ *
+ * @return boolean.
+ */
+ public boolean isValid() {
+ boolean retVal = true;
+ String mandatory = (String) uiAttribute.get(InputUIElement.MANDATORY);
+
+ if (((combo.getText() == null) || (combo.getText().equals("")) //$NON-NLS-1$
+ || (combo.getText().trim().length() < 1)) && (mandatory.equalsIgnoreCase(TemplateEngineHelper.BOOLTRUE))) {
+
+ retVal = false;
+ }
+ return retVal;
+ }
+
+ /**
+ * call the dispose method on the widgets. This is to ensure that the
+ * widgets are properly disposed.
+ */
+ public void disposeWidget() {
+ label.dispose();
+ combo.dispose();
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UISpecialListWidget.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UISpecialListWidget.java
new file mode 100644
index 0000000000..a0409d9531
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UISpecialListWidget.java
@@ -0,0 +1,82 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree.uiwidgets;
+
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Label;
+
+import org.eclipse.cdt.ui.templateengine.uitree.InputUIElement;
+import org.eclipse.cdt.ui.templateengine.uitree.UIAttributes;
+import org.eclipse.cdt.ui.templateengine.uitree.UIElement;
+import org.eclipse.cdt.utils.ui.controls.FileListControl;
+
+
+/**
+ * This gives a Label and UISpecialList Widget.
+ *
+ */
+public class UISpecialListWidget extends UIStringListWidget {
+
+ /**
+ * Constructor.
+ *
+ * @param attribute
+ * attribute associated with this widget.
+ */
+ public UISpecialListWidget(UIAttributes/*<String, String>*/ attribute) {
+ super(attribute);
+ uiAttribute = attribute;
+ }
+
+ /**
+ * create a Label and Text widget, add it to UIComposite. set Layout for the
+ * widgets to be added to UIComposite. set required parameters to the
+ * Widgets.
+ *
+ * @param composite
+ */
+ public void createWidgets(UIComposite composite) {
+ GridData gridData = null;
+ uiComposite = composite;
+
+ label = new Label(composite, SWT.LEFT);
+ label.setText((String) uiAttribute.get(InputUIElement.WIDGETLABEL));
+
+ GridData gd = new GridData();
+ gd.verticalAlignment = SWT.BEGINNING;
+ gd.verticalIndent = 5;
+ label.setLayoutData(gd);
+
+ if (uiAttribute.get(InputUIElement.DESCRIPTION) != null){
+ String tipText = (String) uiAttribute.get(UIElement.DESCRIPTION);
+ tipText = tipText.replaceAll("\\\\r\\\\n", "\r\n"); //$NON-NLS-1$, //$NON-NLS-2$
+ label.setToolTipText(tipText);
+ }
+ Composite flcComposite = new Composite(composite, SWT.NONE);
+ gridData = new GridData(GridData.FILL_HORIZONTAL);
+ flcComposite.setLayout(new GridLayout());
+ flcComposite.setLayoutData(gridData);
+
+ fileListControl = new FileListControl(flcComposite, (String) uiAttribute.get(InputUIElement.WIDGETLABEL), 1);
+ }
+
+ /**
+ * call the dispose method on the widgets. This is to ensure that the
+ * widgets are properly disposed.
+ */
+ public void disposeWidget() {
+ label.dispose();
+ fileListControl = null;
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIStringListWidget.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIStringListWidget.java
new file mode 100644
index 0000000000..4b87e1e500
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UIStringListWidget.java
@@ -0,0 +1,166 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree.uiwidgets;
+
+import java.util.HashMap;
+import java.util.Map;
+import java.util.StringTokenizer;
+
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Label;
+
+import org.eclipse.cdt.core.templateengine.TemplateEngineHelper;
+import org.eclipse.cdt.ui.templateengine.uitree.InputUIElement;
+import org.eclipse.cdt.ui.templateengine.uitree.UIAttributes;
+import org.eclipse.cdt.ui.templateengine.uitree.UIElement;
+import org.eclipse.cdt.utils.ui.controls.FileListControl;
+
+
+/**
+ * This gives a Label and StringList Widget.
+ *
+ */
+
+public class UIStringListWidget extends InputUIElement {
+
+ /**
+ * Attributes associated with this widget.
+ */
+ UIAttributes/*<String, String>*/ uiAttribute;
+
+ /**
+ * StringList widget.
+ */
+ FileListControl fileListControl;
+
+ /**
+ * Label of this widget.
+ */
+ Label label;
+
+ /**
+ * Composite to which this widget control is added.
+ */
+ UIComposite uiComposite;
+
+ /**
+ * Constructor.
+ *
+ * @param attribute
+ * attribute associated with this widget.
+ */
+ public UIStringListWidget(UIAttributes/*<String, String>*/ attribute) {
+ super(attribute);
+ uiAttribute = attribute;
+ }
+
+ /**
+ * @return String_List value contained in the String_List Widget.
+ */
+ public Map/*<String, String>*/ getValues() {
+ Map/*<String, String>*/ retMap = new HashMap/*<String, String>*/();
+ String[] items = fileListControl.getItems();
+ String itemString = new String();
+
+ for (int i = 0; i < items.length; i++)
+ itemString = itemString + items[i] + "|"; //$NON-NLS-1$
+
+ retMap.put(uiAttribute.get(InputUIElement.ID), itemString);
+
+ return retMap;
+ }
+
+ /**
+ * Set the Text widget with new value.
+ *
+ * @param valueMap
+ */
+ public void setValues(Map/*<String, String>*/ valueMap) {
+
+ String items = (String) valueMap.get(uiAttribute.get(InputUIElement.ID));
+
+ if (items != null) {
+ items = items.trim();
+ StringTokenizer st = new StringTokenizer(items, "|"); //$NON-NLS-1$
+ String[] itemList = new String[st.countTokens()];
+
+ for (int i = 0; st.hasMoreTokens(); i++)
+ itemList[i] = st.nextToken();
+
+ fileListControl.setList(itemList);
+ fileListControl.setSelection(0);
+ }
+ }
+
+ /**
+ * create a Label and StringList widget, add it to UIComposite. set Layout
+ * for the widgets to be added to UIComposite. set required parameters to
+ * the Widgets.
+ *
+ * @param composite
+ */
+ public void createWidgets(UIComposite composite) {
+ GridData gridData = null;
+ uiComposite = composite;
+
+ label = new Label(composite, SWT.LEFT);
+ label.setText((String) uiAttribute.get(InputUIElement.WIDGETLABEL));
+
+ GridData gd = new GridData();
+ gd.verticalAlignment = SWT.BEGINNING;
+ gd.verticalIndent = 5;
+ label.setLayoutData(gd);
+
+ if (uiAttribute.get(InputUIElement.DESCRIPTION) != null){
+ String tipText = (String) uiAttribute.get(UIElement.DESCRIPTION);
+ tipText = tipText.replaceAll("\\\\r\\\\n", "\r\n"); //$NON-NLS-1$ //$NON-NLS-2$, $NON-NLS-2$
+ label.setToolTipText(tipText);
+ }
+ Composite flcComposite = new Composite(uiComposite, SWT.NONE);
+ gridData = new GridData(GridData.FILL_HORIZONTAL);
+ flcComposite.setLayout(new GridLayout());
+ flcComposite.setLayoutData(gridData);
+
+ fileListControl = new FileListControl(flcComposite, (String) uiAttribute.get(InputUIElement.WIDGETLABEL), 0);
+ }
+
+ /**
+ * Based on the stae of this Widget return true or false. This return value
+ * will be used by the UIPage to update its(UIPage) state. Return value
+ * depends on the value contained in String List Widget. If value contained
+ * is null and Mandatory value from attributes.
+ *
+ * @return boolean.
+ */
+ public boolean isValid() {
+ boolean retVal = true;
+ String mandatory = (String) uiAttribute.get(InputUIElement.MANDATORY);
+
+ if ((fileListControl.getItems() == null) && (mandatory.equalsIgnoreCase(TemplateEngineHelper.BOOLTRUE))) {
+
+ retVal = false;
+ }
+ return retVal;
+ }
+
+ /**
+ * call the dispose method on the widgets. This is to ensure that the
+ * widgets are properly disposed.
+ */
+ public void disposeWidget() {
+ label.dispose();
+ fileListControl = null;
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UITextWidget.java b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UITextWidget.java
new file mode 100644
index 0000000000..3c55cb2e2f
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/templateengine/org/eclipse/cdt/ui/templateengine/uitree/uiwidgets/UITextWidget.java
@@ -0,0 +1,318 @@
+/*******************************************************************************
+ * Copyright (c) 2007 Symbian Software Limited and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Bala Torati (Symbian) - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.ui.templateengine.uitree.uiwidgets;
+
+import java.util.HashMap;
+import java.util.Map;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.events.ModifyEvent;
+import org.eclipse.swt.events.ModifyListener;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Label;
+import org.eclipse.swt.widgets.Text;
+
+import org.eclipse.cdt.core.templateengine.TemplateEngineHelper;
+import org.eclipse.cdt.ui.templateengine.Messages;
+import org.eclipse.cdt.ui.templateengine.event.PatternEvent;
+import org.eclipse.cdt.ui.templateengine.uitree.IPatternMatchingTable;
+import org.eclipse.cdt.ui.templateengine.uitree.InputUIElement;
+import org.eclipse.cdt.ui.templateengine.uitree.UIAttributes;
+import org.eclipse.cdt.ui.templateengine.uitree.UIElement;
+
+
+/**
+ * This gives a Label and Text widget. The Text widget can be SINGLE type of
+ * MULTI type. This depends on the input type in TemplateDescriptor. The data
+ * entered by the user is verified against an expected pattern. If the user
+ * entered data doesn't confirms to the expected pattern, a PatternEvent is
+ * fired to UIComposite.
+ *
+ * The UI***Widget classes which needs to handle patterns, can inherit the same
+ * from this class. The inheriting class need not catche UIComposite instance
+ * but should set the same for UITextWidget(super).
+ */
+
+public class UITextWidget extends InputUIElement implements ModifyListener {
+
+ /**
+ * Attributes associated with this widget.
+ */
+ private UIAttributes/*<String, String>*/ uiAttribute;
+
+ /**
+ * Text widget.
+ */
+ protected Text text;
+
+ /**
+ * Label of this widget.
+ */
+ protected Label label;
+ private String patternValue;
+
+ /**
+ * Composite to which this widget control is added. Classes extending this class, should make sure that they initialize this from the respective class createWidgets method.
+ */
+ protected UIComposite uiComposite;
+
+ /**
+ * Constructor.
+ *
+ * @param uiAttribute
+ * attribute associated with this widget.
+ */
+ public UITextWidget(UIAttributes/*<String, String>*/ uiAttribute) {
+ super(uiAttribute);
+ this.uiAttribute = uiAttribute;
+ }
+
+ /**
+ * @return String, value contained in the Text Widget.
+ */
+ public Map/*<String, String>*/ getValues() {
+ Map/*<String, String>*/ retMap = new HashMap/*<String, String>*/();
+ retMap.put(uiAttribute.get(InputUIElement.ID), text.getText());
+
+ return retMap;
+ }
+
+ /**
+ * Set the Text widget with new value.
+ *
+ * @param valueMap
+ */
+ public void setValues(Map/*<String, String>*/ valueMap) {
+ String val = (String) valueMap.get(uiAttribute.get(InputUIElement.ID));
+ String key = null;
+ String subString = null;
+ if (val != null) {
+ if (val.indexOf(TemplateEngineHelper.OPEN_MARKER) != -1) {
+ key = TemplateEngineHelper.getFirstMarkerID(val);
+ subString = val.substring(key.length() + 3, val.length());
+ if (valueMap.get(key) != null)
+ val = valueMap.get(key) + subString;
+ else
+ val = subString;
+ }
+ val = val.trim();
+ text.setText(val);
+ }
+ }
+
+ /**
+ * create a Label and Text widget, add it to UIComposite. set Layout for the
+ * widgets to be added to UIComposite. set required parameters to the
+ * Widgets.
+ *
+ * @param uiComposite
+ */
+ public void createWidgets(UIComposite uiComposite) {
+
+ GridData gd = new GridData();
+ this.uiComposite = uiComposite;
+ label = new Label(uiComposite, SWT.LEFT);
+
+ label.setText((String)uiAttribute.get(InputUIElement.WIDGETLABEL));
+ if (((String)uiAttribute.get(UIElement.TYPE)).equalsIgnoreCase(InputUIElement.MULTILINETYPE)) {
+ gd = new GridData();
+ gd.verticalAlignment = SWT.BEGINNING;
+ gd.verticalIndent = 5;
+ label.setLayoutData(gd);
+ }
+
+ if (uiAttribute.get(UIElement.DESCRIPTION) != null){
+ String tipText = (String) uiAttribute.get(UIElement.DESCRIPTION);
+ tipText = tipText.replaceAll("\\\\r\\\\n", "\r\n"); //$NON-NLS-1$ //$NON-NLS-2$
+ label.setToolTipText(tipText);
+ }
+ text = getTextWidget((String) uiAttribute.get(UIElement.TYPE));
+ text.addModifyListener(this);
+ text.setData(".uid", uiAttribute.get(UIElement.ID)); //$NON-NLS-1$
+ }
+
+ /**
+ * call the dispose method on the widgets. This is to ensure that the
+ * widgets are properly disposed.
+ */
+ public void disposeWidget() {
+ label.dispose();
+ text.dispose();
+ }
+
+ /**
+ * evaluate the text entered by the user against the pattern associated with
+ * this widget. checks the text entered. On violation of pattern associated
+ * for this widget, by the user entered text. A pattern event is fired to
+ * the container. If this widget has attribute 'checkproject' set to true,
+ * the value entered in this widget is treated as project name. The same is
+ * verified if there is a direcotry by the same name in workspace,
+ * PatternEvent is thrown to Container.
+ *
+ * @param pattern
+ */
+ public void evaluatePattern(String labelText, String userInputText, String pattern) {
+ String message = labelText + InputUIElement.CONTENTS;
+ Pattern pattern2 = Pattern.compile(pattern);
+ Matcher matcher = pattern2.matcher(userInputText);
+ if (!matcher.matches()) {
+ String[] failed = pattern2.split(userInputText);
+ for (int i = 1; i < failed.length; i++)
+ message = message + " " + failed[i]; //$NON-NLS-1$
+ message += InputUIElement.ISINVALID;
+ message += " Expected pattern is \"" + pattern + "\""; //$NON-NLS-1$ //$NON-NLS-2$
+ if (uiComposite != null)
+ uiComposite.firePatternEvent(new PatternEvent(this, message, false));
+
+ } else {
+ String checkproject = (String) attribute.get(InputUIElement.CHECKPROJECT);
+ if ((checkproject != null) && (checkproject.equalsIgnoreCase(TemplateEngineHelper.BOOLTRUE))
+ && TemplateEngineHelper.checkDirectoryInWorkspace(userInputText)) {
+
+ message = userInputText + Messages.getString("UITextWidget.0"); //$NON-NLS-1$
+ uiComposite.firePatternEvent(new PatternEvent(this, message, false));
+ } else {
+ if (uiComposite != null)
+ uiComposite.firePatternEvent(new PatternEvent(this, message, true));
+ }
+ }
+ }
+
+ /**
+ * Method from ModifyListener. Extracts the Text from the widget. calls
+ * evaluatePattern.
+ */
+ public void modifyText(ModifyEvent e) {
+ String patternName = (String) uiAttribute.get(InputUIElement.INPUTPATTERN);
+
+ if (patternName == null) {
+ patternValue = null;
+ } else if (patternName.equals(IPatternMatchingTable.FREETEXT) ||
+ patternName.equals(IPatternMatchingTable.TEXT) ||
+ patternName.equals(IPatternMatchingTable.FILENAME)) {
+
+ patternValue = getPatternValue(patternName);
+ } else {
+ patternValue = patternName;
+ }
+
+ // Get the source from event. This is done because this class can be
+ // extended by
+ // other classes, having Text widget. They can just make use of
+ // modifyText,
+ // evaluatePattern and isValid.
+ String inputText = text.getText();
+
+ if ((patternValue == null) || (inputText == null))
+ return;
+
+ String mandatory = (String) attribute.get(InputUIElement.MANDATORY);
+ if ((mandatory == null || !mandatory.equalsIgnoreCase("true")) && inputText.equals("")) { //$NON-NLS-1$ //$NON-NLS-2$
+ return;
+ }
+
+ evaluatePattern(label.getText(), inputText, patternValue);
+ }
+
+ /**
+ * Returns the Pattern Value for the widget.
+ * @param patternName
+ * @return
+ */
+ private String getPatternValue(String patternName) {
+
+ if (patternName.equals(IPatternMatchingTable.TEXT)) {
+ patternValue = IPatternMatchingTable.TEXTPATTERNVALUE;
+ }
+
+ if (patternName.equals(IPatternMatchingTable.FREETEXT)) {
+ patternValue = IPatternMatchingTable.FREETEXTPATTERNVALUE;
+ }
+
+ if (patternName.equals(IPatternMatchingTable.FILENAME)) {
+ patternValue = IPatternMatchingTable.FILEPATTERNVALUE;
+ }
+ return patternValue;
+
+ }
+
+ /**
+ * Based on the sate of this Widget return true or false. This return value
+ * will be used by the UIPage to update its(UIPage) state. Return value
+ * depends on the value contained in TextWidget. If value contained is null, ""
+ * and Mandatory value from attributes.
+ *
+ * @return boolean.
+ */
+ public boolean isValid() {
+ boolean retVal = true;
+ String mandatory = (String) uiAttribute.get(InputUIElement.MANDATORY);
+
+ if (((mandatory != null) && (mandatory.equalsIgnoreCase(TemplateEngineHelper.BOOLTRUE)))
+ && ((text.getText() == null) || (text.getText().equals("")) || //$NON-NLS-1$
+ (text.getText().trim().length() < 1))) {
+
+ retVal = false;
+ }
+ return retVal;
+ }
+
+ /**
+ * Based on Input Type Text widget is created. The Text widget created can
+ * be of Type SINGLE or MULTI.
+ *
+ * @param type
+ * of Text widget required.
+ * @return Text.
+ */
+ private Text getTextWidget(String type) {
+ Text retTextWidget = null;
+
+ Composite textConatiner = new Composite(uiComposite, SWT.NONE | SWT.NO_REDRAW_RESIZE);
+
+ textConatiner.setLayout(new GridLayout());
+
+ if (type.equalsIgnoreCase(InputUIElement.INPUTTYPE)) {
+ GridData gridData = new GridData(GridData.FILL_HORIZONTAL);
+ gridData.widthHint = 70;
+ textConatiner.setLayoutData(gridData);
+ retTextWidget = new Text(textConatiner, SWT.SINGLE | SWT.BORDER);
+ retTextWidget.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
+ }
+ if (type.equalsIgnoreCase(InputUIElement.MULTILINETYPE)) {
+
+ GridData multiTextData = new GridData(GridData.FILL_HORIZONTAL);
+ multiTextData.widthHint = 70;
+ String line = (String) uiAttribute.get(InputUIElement.SIZE);
+ int cnt = 1;
+ if (line != null) {
+ cnt = Integer.parseInt(line);
+ if (cnt <= 0)
+ cnt = 1;
+
+ }
+ multiTextData.heightHint = 30 + 12 * cnt;
+ textConatiner.setLayoutData(multiTextData);
+
+ retTextWidget = new Text(textConatiner, SWT.WRAP | SWT.MULTI | SWT.V_SCROLL | SWT.BORDER);
+ GridData textData = new GridData(SWT.FILL, SWT.FILL, true, true);
+ retTextWidget.setLayoutData(textData);
+
+ }
+
+ return retTextWidget;
+ }
+
+}
diff --git a/core/org.eclipse.cdt.ui/utils.ui/org/eclipse/cdt/utils/ui/controls/FileListControl.java b/core/org.eclipse.cdt.ui/utils.ui/org/eclipse/cdt/utils/ui/controls/FileListControl.java
new file mode 100644
index 0000000000..1c3af39e7f
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/utils.ui/org/eclipse/cdt/utils/ui/controls/FileListControl.java
@@ -0,0 +1,832 @@
+/*******************************************************************************
+ * Copyright (c) 2004, 2007 BitMethods Inc and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * BitMethods Inc - initial API and implementation
+ * Sascha Radike <sradike@ejectlag.com> - Support for workspace browsing and small improvements
+ *******************************************************************************/
+package org.eclipse.cdt.utils.ui.controls;
+
+
+import java.util.ArrayList;
+import java.util.Iterator;
+
+import org.eclipse.core.resources.IContainer;
+import org.eclipse.core.resources.IFile;
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.resources.IResource;
+import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.IPath;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.Path;
+import org.eclipse.core.variables.IStringVariableManager;
+import org.eclipse.core.variables.VariablesPlugin;
+import org.eclipse.jface.dialogs.IDialogConstants;
+import org.eclipse.jface.dialogs.IInputValidator;
+import org.eclipse.jface.dialogs.InputDialog;
+import org.eclipse.jface.dialogs.MessageDialog;
+import org.eclipse.jface.window.Window;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.events.KeyAdapter;
+import org.eclipse.swt.events.KeyEvent;
+import org.eclipse.swt.events.MouseAdapter;
+import org.eclipse.swt.events.MouseEvent;
+import org.eclipse.swt.events.SelectionAdapter;
+import org.eclipse.swt.events.SelectionEvent;
+import org.eclipse.swt.events.SelectionListener;
+import org.eclipse.swt.graphics.Image;
+import org.eclipse.swt.graphics.Point;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Button;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.DirectoryDialog;
+import org.eclipse.swt.widgets.FileDialog;
+import org.eclipse.swt.widgets.Label;
+import org.eclipse.swt.widgets.List;
+import org.eclipse.swt.widgets.Shell;
+import org.eclipse.swt.widgets.ToolBar;
+import org.eclipse.swt.widgets.ToolItem;
+import org.eclipse.swt.widgets.Widget;
+import org.eclipse.ui.dialogs.ElementTreeSelectionDialog;
+import org.eclipse.ui.dialogs.ISelectionStatusValidator;
+import org.eclipse.ui.model.WorkbenchContentProvider;
+import org.eclipse.ui.model.WorkbenchLabelProvider;
+import org.eclipse.ui.views.navigator.ResourceComparator;
+
+import org.eclipse.cdt.ui.CDTUIImages;
+import org.eclipse.cdt.ui.newui.CDTStatusInfo;
+import org.eclipse.cdt.ui.newui.TypedCDTViewerFilter;
+import org.eclipse.cdt.ui.newui.UIMessages;
+import org.eclipse.cdt.utils.cdtvariables.IVariableContextInfo;
+
+/**
+ * Instances of this class allow the user to add,remove, delete, moveup and movedown
+ * the items in the list control.
+ */
+
+public class FileListControl {
+
+ // Browse type values
+ // (copied from IOption to fix the dependency on MBS ui plugins issue)
+ private static final int BROWSE_NONE = 0;
+ private static final int BROWSE_FILE = 1;
+ private static final int BROWSE_DIR = 2;
+
+ /**
+ * Multi-purpose dialog to prompt the user for a value, path, or file.
+ *
+ * @since 2.0
+ */
+ class SelectPathInputDialog extends InputDialog {
+ private int type;
+ /* True if user sucessfully set the text value by a browse dialog */
+ private boolean fSetByBrowseDialog = false;
+
+
+ /**
+ * @param parentShell
+ * @param dialogTitle
+ * @param dialogMessage
+ * @param initialValue
+ * @param validator
+ * @param browseType
+ */
+ public SelectPathInputDialog(Shell parentShell, String dialogTitle, String dialogMessage, String initialValue, IInputValidator validator, int browseType) {
+ super(parentShell, dialogTitle, dialogMessage, initialValue, validator);
+ this.type = browseType;
+ }
+
+ /**
+ * Returns true if the value has been set by a browse dialog.
+ */
+ public boolean isValueSetByBrowse() {
+ return fSetByBrowseDialog;
+ }
+
+
+ /* (non-Javadoc)
+ * @see org.eclipse.jface.dialogs.Dialog#createButtonsForButtonBar(org.eclipse.swt.widgets.Composite)
+ */
+ protected void createButtonsForButtonBar(Composite parent) {
+ super.createButtonsForButtonBar(parent);
+
+ if (((type == BROWSE_DIR) || (type == BROWSE_FILE)
+ ) && (fWorkspaceSupport)) {
+
+ /* Browse button for workspace folders/files */
+ final Button workspaceButton = createButton(parent, 3, WORKSPACEBUTTON_NAME, false);
+ workspaceButton.addSelectionListener(new SelectionAdapter() {
+ public void widgetSelected(SelectionEvent ev) {
+ /* Before opening the browse dialog we try to convert the current
+ * path text to a valid workspace resource, so we can set it
+ * as initial selection in the dialog.
+ *
+ * First we remove all double-quotes. Then the build macro provider
+ * will resolve all macros/variables (like workspace_loc, ...).
+ *
+ * If the workspace location path is a prefix of our resolved path,
+ * we will remove that part and finally get a full path relative to the
+ * workspace. We can use that path to set the initially selected resource.
+ */
+
+ String currentPathText;
+ IPath path;
+
+ currentPathText = getText().getText();
+ if(contextInfo != null){
+ /*
+ try {
+ currentPathText =
+ MacroResolver.resolveToString(currentPathText,
+ new DefaultMacroSubstitutor(contextInfo ,
+ "", //$NON-NLS-1$
+ " ")); //$NON-NLS-1$
+ } catch (BuildMacroException e) {
+ }
+ */
+ }
+
+ /* Remove double quotes */
+ currentPathText = currentPathText.replaceAll("\"", ""); //$NON-NLS-1$ //$NON-NLS-2$
+
+ /* Resolve variables */
+ IStringVariableManager variableManager =
+ VariablesPlugin.getDefault().getStringVariableManager();
+
+ /* Remove workspace location prefix (if any) */
+ path = new Path(currentPathText);
+
+ /* Create workspace folder/file selection dialog and
+ * set initial selection */
+ ElementTreeSelectionDialog dialog = new ElementTreeSelectionDialog(getShell(),
+ new WorkbenchLabelProvider(), new WorkbenchContentProvider());
+
+ dialog.setInput(ResourcesPlugin.getWorkspace().getRoot());
+ dialog.setComparator(new ResourceComparator(ResourceComparator.NAME));
+
+ if (type == BROWSE_DIR) {
+ IResource container = null;
+ if(path.isAbsolute()){
+ IContainer cs[] = ResourcesPlugin.getWorkspace().getRoot().findContainersForLocation(path);
+ if(cs != null && cs.length > 0)
+ container = cs[0];
+ }
+ if(container == null && rc instanceof IContainer)
+ container = rc;
+
+
+ dialog.setInitialSelection(container);
+
+ Class[] filteredResources = {IContainer.class, IProject.class};
+ dialog.addFilter(new TypedCDTViewerFilter(filteredResources));
+ dialog.setTitle(WORKSPACE_DIR_DIALOG_TITLE);
+ dialog.setMessage(WORKSPACE_DIR_DIALOG_MSG);
+ } else {
+ IResource resource = null;
+ if(path.isAbsolute()){
+ IFile fs[] = ResourcesPlugin.getWorkspace().getRoot().findFilesForLocation(path);
+ if(fs != null && fs.length > 0)
+ resource = fs[0];
+ }
+ if(resource == null) resource = rc;
+
+ dialog.setInitialSelection(resource);
+ dialog.setValidator(new ISelectionStatusValidator() {
+ public IStatus validate(Object[] selection) {
+ if (selection != null)
+ if (selection.length > 0)
+ if (!(selection[0] instanceof IFile))
+ return new CDTStatusInfo(IStatus.ERROR, WORKSPACE_FILE_DIALOG_ERR);
+ return new CDTStatusInfo();
+ }
+ });
+ dialog.setTitle(WORKSPACE_FILE_DIALOG_TITLE);
+ dialog.setMessage(WORKSPACE_FILE_DIALOG_MSG);
+ }
+
+ /* Open dialog and process result. If a resource has
+ * been selected we create an absolute file system
+ * path for it based on the workspace_loc variable */
+ if (dialog.open() == Window.OK) {
+ fSetByBrowseDialog = true;
+
+ IResource resource = (IResource) dialog.getFirstResult();
+
+ if (resource != null) {
+ getText().setText(variableManager.generateVariableExpression(WORKSPACELOC_VAR,
+ resource.getFullPath().toString()));
+ }
+ }
+
+
+ }
+ });
+ }
+
+ if (type != BROWSE_NONE) {
+ /* Browse button for external directories/files */
+ final Button externalButton = createButton(parent, 4, FILESYSTEMBUTTON_NAME, false);
+ externalButton.addSelectionListener(new SelectionAdapter() {
+ public void widgetSelected(SelectionEvent ev) {
+ String currentName;
+ String result;
+ switch (type) {
+ case BROWSE_DIR :
+ DirectoryDialog dialog = new DirectoryDialog(getParentShell(),
+ SWT.OPEN|SWT.APPLICATION_MODAL);
+ currentName = getText().getText();
+ if(currentName != null && currentName.trim().length() != 0) {
+ dialog.setFilterPath(currentName);
+ }
+ dialog.setMessage(FILESYSTEM_DIR_DIALOG_MSG);
+ result = dialog.open();
+ if(result != null) {
+ fSetByBrowseDialog = true;
+ getText().setText(result);
+ }
+ break;
+ case BROWSE_FILE:
+ FileDialog browseDialog = new FileDialog(getParentShell());
+ currentName = getText().getText();
+ if (currentName != null && currentName.trim().length() != 0) {
+ browseDialog.setFilterPath(currentName);
+ }
+ result = browseDialog.open();
+ if (result != null) {
+ fSetByBrowseDialog = true;
+ getText().setText(result);
+ }
+ break;
+ }
+ }
+ });
+ }
+ }
+
+ }
+
+ /* Variable names */
+ private static final String WORKSPACELOC_VAR = "workspace_loc"; //$NON-NLS-1$
+
+ /* Names, messages and titles */
+ private static final String WORKSPACEBUTTON_NAME = UIMessages.getString("FileListControl.button.workspace"); //$NON-NLS-1$
+ private static final String FILESYSTEMBUTTON_NAME = UIMessages.getString("FileListControl.button.fs"); //$NON-NLS-1$
+
+ private static final String ADD_STR = UIMessages.getString("FileListControl.add"); //$NON-NLS-1$
+ private static final String DEL_STR = UIMessages.getString("FileListControl.delete"); //$NON-NLS-1$
+ private static final String EDIT_STR = UIMessages.getString("FileListControl.edit"); //$NON-NLS-1$
+ private static final String MOVEUP_STR = UIMessages.getString("FileListControl.moveup"); //$NON-NLS-1$
+ private static final String MOVEDOWN_STR = UIMessages.getString("FileListControl.movedown"); //$NON-NLS-1$
+ private static final String FILE_TITLE_ADD = UIMessages.getString("BrowseEntryDialog.file.title.add"); //$NON-NLS-1$
+ private static final String DIR_TITLE_ADD = UIMessages.getString("BrowseEntryDialog.dir.title.add"); //$NON-NLS-1$
+ private static final String FILE_TITLE_EDIT = UIMessages.getString("BrowseEntryDialog.file.title.edit"); //$NON-NLS-1$
+ private static final String DIR_TITLE_EDIT = UIMessages.getString("BrowseEntryDialog.dir.title.edit"); //$NON-NLS-1$
+ private static final String WORKSPACE_DIR_DIALOG_TITLE = UIMessages.getString("BrowseEntryDialog.wsp.dir.dlg.title"); //$NON-NLS-1$
+ private static final String WORKSPACE_FILE_DIALOG_TITLE = UIMessages.getString("BrowseEntryDialog.wsp.file.dlg.title"); //$NON-NLS-1$
+ private static final String WORKSPACE_DIR_DIALOG_MSG = UIMessages.getString("BrowseEntryDialog.wsp.dir.dlg.msg"); //$NON-NLS-1$
+ private static final String WORKSPACE_FILE_DIALOG_MSG = UIMessages.getString("BrowseEntryDialog.wsp.file.dlg.msg"); //$NON-NLS-1$
+ private static final String WORKSPACE_FILE_DIALOG_ERR = UIMessages.getString("BrowseEntryDialog.wsp.file.dlg.err"); //$NON-NLS-1$
+ private static final String FILESYSTEM_DIR_DIALOG_MSG = UIMessages.getString("BrowseEntryDialog.fs.dir.dlg.msg"); //$NON-NLS-1$
+ private static final String FILE_MSG = UIMessages.getString("BrowseEntryDialog.message.file"); //$NON-NLS-1$
+ private static final String DIR_MSG = UIMessages.getString("BrowseEntryDialog.message.directory"); //$NON-NLS-1$
+ private static final String TITLE = UIMessages.getString("BuildPropertyCommon.label.title"); //$NON-NLS-1$
+
+ //toolbar
+ private ToolBar toolBar;
+ // toolbar items
+ private ToolItem addItem, deleteItem, editItem, moveUpItem,
+ moveDownItem;
+ // title label
+ private Label title;
+ // images
+// private Image addImage, deleteImage, editImage, moveUpImage, moveDownImage;
+// private Composite composite;
+ // list control
+ private List list;
+ private String compTitle;
+ private SelectionListener selectionListener;
+ private GridData tgdata, grid3, grid4, grid2;
+
+ // The type of browse support that is required
+ private int browseType;
+ private IPath path;
+
+ /* Workspace support */
+ private boolean fWorkspaceSupport = false;
+ private IVariableContextInfo contextInfo;
+ private IResource rc;
+
+ private java.util.List listeners = new ArrayList();
+ private String oldValue[];
+
+ //images
+ private final Image IMG_ADD = CDTUIImages
+ .get(CDTUIImages.IMG_FILELIST_ADD);
+ private final Image IMG_DEL = CDTUIImages
+ .get(CDTUIImages.IMG_FILELIST_DEL);
+ private final Image IMG_EDIT = CDTUIImages
+ .get(CDTUIImages.IMG_FILELIST_EDIT);
+ private final Image IMG_MOVEUP = CDTUIImages
+ .get(CDTUIImages.IMG_FILELIST_MOVEUP);
+ private final Image IMG_MOVEDOWN = CDTUIImages
+ .get(CDTUIImages.IMG_FILELIST_MOVEDOWN);
+
+ /**
+ * Constructor
+ *
+ * @param parent
+ * @param compTitle
+ * @param type
+ */
+ public FileListControl(Composite parent, String compTitle, int type) {
+ // Default to no browsing
+ browseType = type;
+
+ //file panel
+ Composite filePanel = new Composite(parent, SWT.NONE);
+ GridLayout form1 = new GridLayout();
+ form1.numColumns = 1;
+ form1.horizontalSpacing = 0;
+ form1.verticalSpacing = 0;
+ form1.marginHeight = 0;
+ form1.marginWidth = 0;
+ filePanel.setLayout(form1);
+ filePanel.setLayoutData(new GridData(GridData.FILL_BOTH));
+
+ // title panel
+ Composite titlePanel = new Composite(filePanel, SWT.BORDER);
+ GridLayout titleform = new GridLayout(2, false);
+ titleform.horizontalSpacing = 0;
+ titleform.verticalSpacing = 0;
+ titleform.marginHeight = 0;
+ titleform.marginWidth = 0;
+ titlePanel.setLayout(titleform);
+ tgdata = new GridData(GridData.FILL_HORIZONTAL);
+ tgdata.heightHint = IDialogConstants.BUTTON_BAR_HEIGHT;
+ titlePanel.setLayoutData(tgdata);
+ title = new Label(titlePanel, SWT.NONE | SWT.BOLD);
+ this.compTitle = " " + compTitle; //$NON-NLS-1$
+ title.setText(this.compTitle);
+ grid2 = new GridData(GridData.FILL_HORIZONTAL);
+ title.setLayoutData(grid2);
+ //button panel
+ Composite buttonPanel = new Composite(titlePanel, SWT.NONE);
+ GridLayout form2 = new GridLayout();
+ form2.numColumns = 5;
+ form2.horizontalSpacing = 0;
+ form2.verticalSpacing = 0;
+ form2.marginWidth = 0;
+ form2.marginHeight = 0;
+ buttonPanel.setLayout(form2);
+ // toolbar
+ toolBar = new ToolBar(buttonPanel, SWT.HORIZONTAL | SWT.RIGHT
+ | SWT.FLAT);
+ // add toolbar item
+ addItem = new ToolItem(toolBar, SWT.PUSH);
+ addItem.setImage(IMG_ADD);
+ addItem.setToolTipText(ADD_STR);
+ addItem.addSelectionListener(getSelectionListener());
+ // delete toolbar item
+ deleteItem = new ToolItem(toolBar, SWT.PUSH);
+ deleteItem.setImage(IMG_DEL);
+ deleteItem.setToolTipText(DEL_STR);
+ deleteItem.addSelectionListener(getSelectionListener());
+ // edit toolbar item
+ editItem = new ToolItem(toolBar, SWT.PUSH);
+ editItem.setImage(IMG_EDIT);
+ editItem.setToolTipText(EDIT_STR);
+ editItem.addSelectionListener(getSelectionListener());
+ // moveup toolbar item
+ moveUpItem = new ToolItem(toolBar, SWT.PUSH);
+ moveUpItem.setImage(IMG_MOVEUP);
+ moveUpItem.setToolTipText(MOVEUP_STR);
+ moveUpItem.addSelectionListener(getSelectionListener());
+ // movedown toolbar item
+ moveDownItem = new ToolItem(toolBar, SWT.PUSH);
+ moveDownItem.setImage(IMG_MOVEDOWN);
+ moveDownItem.setToolTipText(MOVEDOWN_STR);
+ moveDownItem.addSelectionListener(getSelectionListener());
+ grid3 = new GridData(GridData.FILL_HORIZONTAL
+ | GridData.HORIZONTAL_ALIGN_END);
+ buttonPanel.setLayoutData(grid3);
+ // list control
+ list = new List(filePanel, SWT.V_SCROLL | SWT.H_SCROLL | SWT.BORDER);
+ grid4 = new GridData(GridData.FILL_BOTH);
+ // force the list to be no wider than the title bar
+ Point preferredSize = titlePanel.computeSize(SWT.DEFAULT, SWT.DEFAULT);
+ grid4.widthHint = preferredSize.x;
+ grid4.heightHint = preferredSize.y * 3;
+ grid4.horizontalSpan = 2;
+ list.setLayoutData(grid4);
+ list.addSelectionListener(getSelectionListener());
+ //Add a double-click event handler
+ list.addMouseListener(new MouseAdapter() {
+ public void mouseDoubleClick(MouseEvent e) {
+ // Popup the editor on the selected item from the list
+ editSelection();
+ }
+ });
+ // Add a delete event handler
+ list.addKeyListener(new KeyAdapter() {
+ /* (non-Javadoc)
+ * @see org.eclipse.swt.events.KeyAdapter#keyPressed(org.eclipse.swt.events.KeyEvent)
+ */
+ public void keyPressed(KeyEvent e) {
+ // Is this the delete key
+ if (e.keyCode == SWT.DEL) {
+ removePressed();
+ } else {
+ super.keyPressed(e);
+ }
+ }
+ });
+
+ selectionChanged();
+ }
+ /**
+ * Set list values
+ *
+ * @param listVal
+ */
+ public void setList(String[] listVal) {
+ if (list != null) {
+ list.removeAll();
+ }
+ for (int i = 0; i < listVal.length; i++) {
+ list.add(listVal[i]);
+ }
+ checkNotificationNeeded();
+ }
+
+ public void addChangeListener(IFileListChangeListener listener){
+ listeners.add(listener);
+ }
+
+ public void removeChangeListener(IFileListChangeListener listener){
+ listeners.remove(listener);
+ }
+
+ public void checkNotificationNeeded(){
+ String items[] = getItems();
+ if(oldValue != null){
+ if(oldValue.length == items.length){
+ int i;
+ for(i = 0; i < oldValue.length; i++){
+ if(!oldValue[i].equals(items[i]))
+ break;
+ }
+ if(i == oldValue.length)
+ return;
+ }
+ String old[] = oldValue;
+ System.arraycopy(items,0,oldValue = new String[items.length],0,items.length);
+ notifyListeners(old,oldValue);
+ } else{
+ System.arraycopy(items,0,oldValue = new String[items.length],0,items.length);
+ }
+ }
+
+ public void notifyListeners(String oldVal[], String newVal[]){
+ Iterator iter = listeners.iterator();
+ while(iter.hasNext()){
+ ((IFileListChangeListener)iter.next()).fileListChanged(this,oldVal,newVal);
+ }
+ }
+
+ /**
+ * Set selection
+ *
+ * @param sel
+ */
+ public void setSelection(int sel) {
+ if (list.getItemCount() > 0)
+ list.setSelection(sel);
+ selectionChanged();
+ }
+ /**
+ * Set default selection
+ */
+ public void setSelection() {
+ if (list.getItemCount() > 0)
+ list.setSelection(0);
+ }
+ /**
+ * removes all items from list control
+ */
+ public void removeAll() {
+ if (list != null){
+ list.removeAll();
+ checkNotificationNeeded();
+ }
+ }
+ /**
+ * get list items
+ */
+ public String[] getItems() {
+ return list.getItems();
+ }
+ /**
+ * Create selection listener for buttons
+ */
+ private void createSelectionListener() {
+ selectionListener = new SelectionAdapter() {
+ public void widgetSelected(SelectionEvent event) {
+ Widget widget = event.widget;
+ if (widget == addItem) {
+ addPressed();
+ } else if (widget == deleteItem) {
+ removePressed();
+ } else if (widget == moveUpItem) {
+ upPressed();
+ } else if (widget == moveDownItem) {
+ downPressed();
+ } else if (widget == list) {
+ selectionChanged();
+ } else if (widget == editItem) {
+ editSelection();
+ }
+ }
+ };
+ }
+ /**
+ * Returns selection listener
+ *
+ * @return
+ */
+ private SelectionListener getSelectionListener() {
+ if (selectionListener == null)
+ createSelectionListener();
+ return selectionListener;
+ }
+ /**
+ * This method will be called when the add button is pressed
+ */
+ private void addPressed() {
+ // Prompt user for a new item
+ String input = getNewInputObject();
+
+ // Add it to the list
+ if (input != null && input.length() > 0) {
+ int index = list.getSelectionIndex();
+ if (index >= 0) {
+ list.add(input, index + 1);
+ list.setSelection(index + 1);
+ }
+ else {
+ list.add(input, 0);
+ list.setSelection(0);
+ }
+ checkNotificationNeeded();
+ }
+
+ selectionChanged();
+ }
+ /**
+ * This method will be called when the remove button is pressed
+ */
+ private void removePressed() {
+ int index = list.getSelectionIndex();
+ if (browseType == BROWSE_DIR || browseType == BROWSE_FILE) {
+ String quest = UIMessages.getString("FileListControl.deletedialog.message"); //$NON-NLS-1$
+ String title = UIMessages.getString("FileListControl.deletedialog.title"); //$NON-NLS-1$
+ boolean delDir = MessageDialog.openQuestion(list.getShell(), title,
+ quest);
+ if (delDir && index != -1){
+ list.remove(index);
+ checkNotificationNeeded();
+ }
+ } else if (index != -1){
+ list.remove(index);
+ checkNotificationNeeded();
+ }
+ selectionChanged();
+ }
+ /**
+ * This method will be called when the move up button is pressed
+ */
+ private void upPressed() {
+ int index = list.getSelectionIndex();
+ String curSelList = list.getItem(index);
+ String preList = list.getItem(index - 1);
+ list.setItem(index - 1, curSelList);
+ list.setItem(index, preList);
+ list.setSelection(index - 1);
+ checkNotificationNeeded();
+ selectionChanged();
+ }
+ /**
+ * This method will be called when the move down button is pressed
+ */
+ private void downPressed() {
+ int index = list.getSelectionIndex();
+ String curSelList = list.getItem(index);
+ String nextList = list.getItem(index + 1);
+ list.setItem(index + 1, curSelList);
+ list.setItem(index, nextList);
+ list.setSelection(index + 1);
+ checkNotificationNeeded();
+ selectionChanged();
+ }
+ /**
+ * This method will be called when the edit button is pressed
+ */
+ private void editSelection() {
+ int index = list.getSelectionIndex();
+ if (index != -1) {
+ String selItem = list.getItem(index);
+ if (selItem != null) {
+ /* Use SelectPathInputDialog for IOption.BROWSE_DIR and
+ * IOption.BROWSE_FILE. Use simple input dialog otherwise.
+ */
+ InputDialog dialog;
+ if ((browseType == BROWSE_DIR) ||
+ (browseType == BROWSE_FILE)) {
+
+ String title;
+ String message;
+ if (browseType == BROWSE_DIR) {
+ title = DIR_TITLE_EDIT;
+ message = DIR_MSG;
+ } else {
+ title = FILE_TITLE_EDIT;
+ message = FILE_MSG;
+ }
+ dialog = new SelectPathInputDialog(getListControl().getShell(), title,
+ message, selItem, null, browseType);
+
+ } else {
+ String title = UIMessages.getString("FileListControl.editdialog.title"); //$NON-NLS-1$
+ dialog = new InputDialog(null, title, compTitle,
+ selItem, null);
+ }
+
+
+ String newItem = null;
+ if (dialog.open() == InputDialog.OK) {
+ newItem = dialog.getValue();
+
+ /* If newItem is a directory or file path we need to
+ * double-quote it if required. We only do this if the user
+ * selected a new path using a browse button. If he/she simply
+ * edited the text, we skip this so the user can remove quotes if he/she
+ * wants to.
+ */
+ if (dialog instanceof SelectPathInputDialog) {
+ if (((SelectPathInputDialog) dialog).isValueSetByBrowse())
+ newItem = doubleQuotePath(newItem);
+ }
+
+ if (newItem != null && !newItem.equals(selItem)) {
+ list.setItem(index, newItem);
+ checkNotificationNeeded();
+ selectionChanged();
+ }
+ }
+ }
+ }
+ }
+ /**
+ * This method will be called when the list selection changed
+ */
+ public void selectionChanged() {
+ int index = list.getSelectionIndex();
+ int size = list.getItemCount();
+ deleteItem.setEnabled(size > 0);
+ moveUpItem.setEnabled(size > 1 && index > 0);
+ moveDownItem.setEnabled(size > 1 && index >= 0 && index < size - 1);
+ editItem.setEnabled(size > 0);
+ }
+ /**
+ * Returns List control
+ */
+ public List getListControl() {
+ return list;
+ }
+
+ /**
+ * Sets the IPath of the project the field editor was
+ * created for.
+ *
+ * @param path The path to the
+ */
+ public void setPath(IPath path) {
+ this.path = path;
+ }
+
+ /**
+ * Set browseType
+ */
+ public void setType(int type) {
+ browseType = type;
+ }
+
+ /**
+ * Enable/Disable workspace support. If enabled, the workspace browse button
+ * will be visible in the SelectPathInputDialog.
+ * @param enable
+ */
+ public void setWorkspaceSupport(boolean enable) {
+ fWorkspaceSupport = enable;
+ }
+
+ /**
+ * Set the field editor context.
+ */
+ public void setContext(IVariableContextInfo info) {
+ contextInfo = info;
+ for(;info != null;info = info.getNext()){
+ /*
+ if(info.getContextType() == IBuildMacroProvider.CONTEXT_PROJECT){
+ IManagedProject mngProj = (IManagedProject)info.getContextData();
+ this.rc = mngProj.getOwner();
+ break;
+ }
+ */
+ }
+ }
+
+ /**
+ * Returns the input dialog string
+ */
+ private String getNewInputObject() {
+ // Create a dialog to prompt for a new list item
+ String input = null;
+ String title = new String();
+ String message = new String();
+ String initVal = new String();
+
+ if (browseType == BROWSE_DIR) {
+ title = DIR_TITLE_ADD;
+ message = DIR_MSG;
+ initVal = (path == null ? initVal : path.toString());
+ } else if (browseType == BROWSE_FILE) {
+ title = FILE_TITLE_ADD;
+ message = FILE_MSG;
+ initVal = (path == null ? initVal : path.toString());
+ } else {
+ title = TITLE;
+ message = compTitle;
+ }
+
+ // Prompt for value
+ SelectPathInputDialog dialog = new SelectPathInputDialog(getListControl().getShell(), title, message, initVal, null, browseType);
+ if (dialog.open() == SelectPathInputDialog.OK) {
+ input = dialog.getValue();
+ }
+
+ /* Double-quote (if required) the text if it is a directory or file */
+ if (input != null && input.length() > 0) {
+ if (browseType == BROWSE_DIR ||
+ browseType == BROWSE_FILE) {
+ input = doubleQuotePath(input);
+ }
+ }
+
+ return input;
+ }
+
+ public Label getLabelControl(){
+ return title;
+ }
+
+ public void setEnabled(boolean enabled){
+ title.setEnabled(enabled);
+ toolBar.setEnabled(enabled);
+ list.setEnabled(enabled);
+ }
+
+ /**
+ * Double-quotes a path name if it contains white spaces, backslahes
+ * or a macro/variable (We don't know if a macro will contain spaces, so we
+ * have to be on the safe side).
+ * @param pathName The path name to double-quote.
+ * @return
+ */
+ private String doubleQuotePath(String pathName) {
+ /* Trim */
+ pathName = pathName.trim();
+
+ /* Check if path is already double-quoted */
+ boolean bStartsWithQuote = pathName.startsWith("\""); //$NON-NLS-1$
+ boolean bEndsWithQuote = pathName.endsWith("\""); //$NON-NLS-1$
+
+ /* Check for spaces, backslashes or macros */
+ int i = pathName.indexOf(" ") + pathName.indexOf("\\") //$NON-NLS-1$ //$NON-NLS-2$
+ + pathName.indexOf("${"); //$NON-NLS-1$
+
+ /* If indexof didn't fail all three times, double-quote path */
+ if (i != -3) {
+ if (!bStartsWithQuote)
+ pathName = "\"" + pathName; //$NON-NLS-1$
+ if (!bEndsWithQuote)
+ pathName = pathName + "\""; //$NON-NLS-1$
+ }
+
+ return pathName;
+ }
+}
diff --git a/core/org.eclipse.cdt.ui/utils.ui/org/eclipse/cdt/utils/ui/controls/IFileListChangeListener.java b/core/org.eclipse.cdt.ui/utils.ui/org/eclipse/cdt/utils/ui/controls/IFileListChangeListener.java
new file mode 100644
index 0000000000..0ffa47b156
--- /dev/null
+++ b/core/org.eclipse.cdt.ui/utils.ui/org/eclipse/cdt/utils/ui/controls/IFileListChangeListener.java
@@ -0,0 +1,15 @@
+/*******************************************************************************
+ * Copyright (c) 2005, 2007 Intel Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Intel Corporation - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.cdt.utils.ui.controls;
+
+public interface IFileListChangeListener {
+ void fileListChanged(FileListControl fileList, String oldValue[], String newValue[]);
+}

Back to the top