Bug 52028 - Add variable expansion for Main Class and Project in launch configurations
diff --git a/org.eclipse.jdt.debug.ui/plugin.properties b/org.eclipse.jdt.debug.ui/plugin.properties
index 9c0dde4..9b4c985 100644
--- a/org.eclipse.jdt.debug.ui/plugin.properties
+++ b/org.eclipse.jdt.debug.ui/plugin.properties
@@ -233,4 +233,4 @@
 appletTabGroupDescription.debug=Create a configuration that will launch a Java applet in debug mode.
 appletTabGroupDescription.run=Create a configuration that will launch a Java applet.
 
-
+java_type_name.description=Fully qualified Java type name of the primary type in the selected resource
diff --git a/org.eclipse.jdt.debug.ui/plugin.xml b/org.eclipse.jdt.debug.ui/plugin.xml
index df2492d..62f0197 100644
--- a/org.eclipse.jdt.debug.ui/plugin.xml
+++ b/org.eclipse.jdt.debug.ui/plugin.xml
@@ -2410,5 +2410,15 @@
             id="org.eclipse.jdt.debug.ui.sourceContainerPresentation.classpathContainer">
       </sourceContainerPresentation>
    </extension>
+   
+   <!-- Dynamic (String Substitution) Variables -->
+   <extension
+         point="org.eclipse.core.variables.dynamicVariables">
+      <variable
+            name="java_type_name"
+            description="%java_type_name.description"
+            resolver="org.eclipse.jdt.internal.debug.ui.TypeNameResolver">
+      </variable>
+   </extension>   	
       
 </plugin>
diff --git a/org.eclipse.jdt.debug.ui/ui/org/eclipse/jdt/internal/debug/ui/DebugUIMessages.properties b/org.eclipse.jdt.debug.ui/ui/org/eclipse/jdt/internal/debug/ui/DebugUIMessages.properties
index 0f4849c..ee323b9 100644
--- a/org.eclipse.jdt.debug.ui/ui/org/eclipse/jdt/internal/debug/ui/DebugUIMessages.properties
+++ b/org.eclipse.jdt.debug.ui/ui/org/eclipse/jdt/internal/debug/ui/DebugUIMessages.properties
@@ -203,3 +203,4 @@
 CreateStepFilterDialog.3=&Pattern to filter:
 CreateStepFilterDialog.4=Step Filter must be a valid Java identifier.
 CreateStepFilterDialog.5=Step Filter already exists.
+TypeNameResolver.0=The selected resource does not resolve to a Java element
diff --git a/org.eclipse.jdt.debug.ui/ui/org/eclipse/jdt/internal/debug/ui/TypeNameResolver.java b/org.eclipse.jdt.debug.ui/ui/org/eclipse/jdt/internal/debug/ui/TypeNameResolver.java
new file mode 100644
index 0000000..0570fad
--- /dev/null
+++ b/org.eclipse.jdt.debug.ui/ui/org/eclipse/jdt/internal/debug/ui/TypeNameResolver.java
@@ -0,0 +1,69 @@
+/*******************************************************************************
+ * Copyright (c) 2000, 2004 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials 
+ * are made available under the terms of the Common Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/cpl-v10.html
+ * 
+ * Contributors:
+ *     IBM Corporation - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.jdt.internal.debug.ui;
+
+import org.eclipse.core.resources.IResource;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.variables.IDynamicVariable;
+import org.eclipse.debug.internal.ui.stringsubstitution.ResourceResolver;
+import org.eclipse.jdt.core.IClassFile;
+import org.eclipse.jdt.core.ICompilationUnit;
+import org.eclipse.jdt.core.IJavaElement;
+import org.eclipse.jdt.core.IType;
+import org.eclipse.jdt.core.JavaCore;
+import org.eclipse.jdt.core.JavaModelException;
+
+/**
+ * Variable resolver which returns the fully qualified name of the
+ * primary type in the selected resource.
+ */
+public class TypeNameResolver extends ResourceResolver {
+	/* (non-Javadoc)
+	 * @see org.eclipse.core.variables.IDynamicVariableResolver#resolveValue(org.eclipse.core.variables.IDynamicVariable, java.lang.String)
+	 */
+	public String resolveValue(IDynamicVariable variable, String argument) throws CoreException {
+		IResource resource = getSelectedResource(variable);
+		IJavaElement javaElement = JavaCore.create(resource);
+		if (javaElement != null) {
+			IType type= getType(javaElement);
+			if (type != null) {
+				return type.getFullyQualifiedName();
+			}	
+		}
+		abort(DebugUIMessages.getString("TypeNameResolver.0"), null); //$NON-NLS-1$
+		return null;
+	}
+	
+	/**
+	 * Returns the primary type in the given Java element
+	 * or <code>null</code> if none.
+	 * 
+	 * @param element the Java element
+	 * @return the primary type in the given Java element
+	 */
+	public static IType getType(IJavaElement element) {
+		IType type= null;
+		int elementType= element.getElementType();
+		switch (elementType) {
+			case IJavaElement.CLASS_FILE :
+				try {
+					type= ((IClassFile) element).getType();
+				} catch (JavaModelException e) {
+					// Ignore
+				}
+				break;
+			case IJavaElement.COMPILATION_UNIT :
+				type= ((ICompilationUnit) element).findPrimaryType();
+				break;
+		};
+		return type;
+	}
+}
diff --git a/org.eclipse.jdt.launching/launching/org/eclipse/jdt/launching/AbstractJavaLaunchConfigurationDelegate.java b/org.eclipse.jdt.launching/launching/org/eclipse/jdt/launching/AbstractJavaLaunchConfigurationDelegate.java
index bfe479e..bae5dba 100644
--- a/org.eclipse.jdt.launching/launching/org/eclipse/jdt/launching/AbstractJavaLaunchConfigurationDelegate.java
+++ b/org.eclipse.jdt.launching/launching/org/eclipse/jdt/launching/AbstractJavaLaunchConfigurationDelegate.java
@@ -369,7 +369,8 @@
 	 * @exception CoreException if unable to retrieve the attribute
 	 */
 	public String getMainTypeName(ILaunchConfiguration configuration) throws CoreException {
-		return configuration.getAttribute(IJavaLaunchConfigurationConstants.ATTR_MAIN_TYPE_NAME, (String)null);
+		String mainType= configuration.getAttribute(IJavaLaunchConfigurationConstants.ATTR_MAIN_TYPE_NAME, (String)null); 
+		return VariablesPlugin.getDefault().getStringVariableManager().performStringSubstitution(mainType);
 	}
 
 	/**