--- /dev/null
+/*******************************************************************************
+ * Copyright (c) 2000, 2012 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
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Renaud Waldura <renaud+eclipse@waldura.com>
+ * IBM Corporation - updates
+ *******************************************************************************/
+package org.eclipse.jdt.internal.ui.text.correction.proposals;
+
+import java.util.Collection;
+
+import org.eclipse.core.runtime.Assert;
+import org.eclipse.core.runtime.IProgressMonitor;
+
+import org.eclipse.jface.viewers.StructuredSelection;
+import org.eclipse.jface.wizard.IWizardPage;
+
+import org.eclipse.jface.text.IDocument;
+
+import org.eclipse.jdt.core.ICompilationUnit;
+import org.eclipse.jdt.core.IJavaElement;
+import org.eclipse.jdt.core.IType;
+import org.eclipse.jdt.core.dom.AST;
+import org.eclipse.jdt.core.dom.ASTNode;
+import org.eclipse.jdt.core.dom.CatchClause;
+import org.eclipse.jdt.core.dom.ITypeBinding;
+import org.eclipse.jdt.core.dom.MethodDeclaration;
+import org.eclipse.jdt.core.dom.Name;
+import org.eclipse.jdt.core.dom.ParameterizedType;
+
+import org.eclipse.jdt.internal.corext.dom.ASTNodes;
+import org.eclipse.jdt.internal.corext.dom.Bindings;
+import org.eclipse.jdt.internal.corext.util.Messages;
+
+import org.eclipse.jdt.ui.JavaElementLabels;
+import org.eclipse.jdt.ui.text.java.IInvocationContext;
+import org.eclipse.jdt.ui.text.java.IProblemLocation;
+import org.eclipse.jdt.ui.text.java.correction.ChangeCorrectionProposal;
+import org.eclipse.jdt.ui.wizards.NewAnnotationWizardPage;
+import org.eclipse.jdt.ui.wizards.NewClassWizardPage;
+import org.eclipse.jdt.ui.wizards.NewEnumWizardPage;
+import org.eclipse.jdt.ui.wizards.NewInterfaceWizardPage;
+import org.eclipse.jdt.ui.wizards.NewTypeWizardPage;
+
+import org.eclipse.jdt.internal.ui.JavaPluginImages;
+import org.eclipse.jdt.internal.ui.text.correction.ASTResolving;
+import org.eclipse.jdt.internal.ui.text.correction.CorrectionMessages;
+import org.eclipse.jdt.internal.ui.text.correction.UnresolvedElementsSubProcessor;
+import org.eclipse.jdt.internal.ui.viewsupport.BasicElementLabels;
+import org.eclipse.jdt.internal.ui.viewsupport.BindingLabelProvider;
+import org.eclipse.jdt.internal.ui.wizards.NewAnnotationCreationWizard;
+import org.eclipse.jdt.internal.ui.wizards.NewClassCreationWizard;
+import org.eclipse.jdt.internal.ui.wizards.NewElementWizard;
+import org.eclipse.jdt.internal.ui.wizards.NewEnumCreationWizard;
+import org.eclipse.jdt.internal.ui.wizards.NewInterfaceCreationWizard;
+
+
+/**
+ * This proposal is listed in the corrections list for a "type not found" problem.
+ * It offers to create a new type by running the class/interface wizard.
+ * If selected, this proposal will open a {@link NewClassCreationWizard},
+ * {@link NewInterfaceCreationWizard}, {@link NewEnumCreationWizard} or {@link NewAnnotationCreationWizard}.
+ *
+ * @see UnresolvedElementsSubProcessor#getTypeProposals(IInvocationContext, IProblemLocation, Collection)
+ */
+public class NewCUUsingWizardProposal extends ChangeCorrectionProposal {
+
+ public static final int K_CLASS= 1;
+ public static final int K_INTERFACE= 2;
+ public static final int K_ENUM= 3;
+ public static final int K_ANNOTATION= 4;
+
+ private Name fNode;
+ public ICompilationUnit fCompilationUnit;
+ public int fTypeKind;
+ public IJavaElement fTypeContainer; // IType or IPackageFragment
+ public String fTypeNameWithParameters;
+ public IType fCreatedType;
+
+ public boolean fShowDialog;
+
+ public NewCUUsingWizardProposal(ICompilationUnit cu, Name node, int typeKind, IJavaElement typeContainer, int severity) {
+ super("", null, severity, null); //$NON-NLS-1$
+
+ fCompilationUnit= cu;
+ fNode= node;
+ fTypeKind= typeKind;
+ fTypeContainer= typeContainer;
+ fTypeNameWithParameters= getTypeName(typeKind, node);
+
+ fCreatedType= null;
+
+ String containerName= ASTNodes.getQualifier(node);
+ String typeName= fTypeNameWithParameters;
+ String containerLabel= BasicElementLabels.getJavaElementName(containerName);
+ String typeLabel= BasicElementLabels.getJavaElementName(typeName);
+ boolean isInnerType= typeContainer instanceof IType;
+ switch (typeKind) {
+ case K_CLASS:
+ setImage(JavaPluginImages.get(JavaPluginImages.IMG_OBJS_CLASS));
+ if (isInnerType) {
+ if (containerName.length() == 0) {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createinnerclass_description, typeLabel));
+ } else {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createinnerclass_intype_description, new String[] { typeLabel, containerLabel }));
+ }
+ } else {
+ if (containerName.length() == 0) {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createclass_description, typeLabel));
+ } else {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createclass_inpackage_description, new String[] { typeLabel, containerLabel }));
+ }
+ }
+ break;
+ case K_INTERFACE:
+ setImage(JavaPluginImages.get(JavaPluginImages.IMG_OBJS_INTERFACE));
+ if (isInnerType) {
+ if (containerName.length() == 0) {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createinnerinterface_description, typeLabel));
+ } else {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createinnerinterface_intype_description, new String[] { typeLabel, containerLabel }));
+ }
+ } else {
+ if (containerName.length() == 0) {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createinterface_description, typeLabel));
+ } else {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createinterface_inpackage_description, new String[] { typeLabel, containerLabel }));
+ }
+ }
+ break;
+ case K_ENUM:
+ setImage(JavaPluginImages.get(JavaPluginImages.IMG_OBJS_ENUM));
+ if (isInnerType) {
+ if (containerName.length() == 0) {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createinnerenum_description, typeLabel));
+ } else {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createinnerenum_intype_description, new String[] { typeLabel, containerLabel }));
+ }
+ } else {
+ if (containerName.length() == 0) {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createenum_description, typeLabel));
+ } else {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createenum_inpackage_description, new String[] { typeLabel, containerLabel }));
+ }
+ }
+ break;
+ case K_ANNOTATION:
+ setImage(JavaPluginImages.get(JavaPluginImages.IMG_OBJS_ANNOTATION));
+ if (isInnerType) {
+ if (containerName.length() == 0) {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createinnerannotation_description, typeLabel));
+ } else {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createinnerannotation_intype_description, new String[] { typeLabel, containerLabel }));
+ }
+ } else {
+ if (containerName.length() == 0) {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createannotation_description, typeLabel));
+ } else {
+ setDisplayName(Messages.format(CorrectionMessages.NewCUCompletionUsingWizardProposal_createannotation_inpackage_description, new String[] { typeLabel, containerLabel }));
+ }
+ }
+ break;
+ default:
+ throw new IllegalArgumentException("Unknown type kind"); //$NON-NLS-1$
+ }
+ fShowDialog= true;
+ }
+
+ private static String getTypeName(int typeKind, Name node) {
+ String name= ASTNodes.getSimpleNameIdentifier(node);
+
+ if (typeKind == K_CLASS || typeKind == K_INTERFACE) {
+ ASTNode parent= node.getParent();
+ if (parent.getLocationInParent() == ParameterizedType.TYPE_PROPERTY) {
+ String typeArgBaseName= name.startsWith(String.valueOf('T')) ? String.valueOf('S') : String.valueOf('T'); // use 'S' or 'T'
+
+ int nTypeArgs= ((ParameterizedType) parent.getParent()).typeArguments().size();
+ StringBuffer buf= new StringBuffer(name);
+ buf.append('<');
+ if (nTypeArgs == 1) {
+ buf.append(typeArgBaseName);
+ } else {
+ for (int i= 0; i < nTypeArgs; i++) {
+ if (i != 0)
+ buf.append(", "); //$NON-NLS-1$
+ buf.append(typeArgBaseName).append(i + 1);
+ }
+ }
+ buf.append('>');
+ return buf.toString();
+ }
+ }
+ return name;
+ }
+
+
+ @Override
+ public void apply(IDocument document) {
+ StructuredSelection selection= new StructuredSelection(fCompilationUnit);
+ NewElementWizard wizard= createWizard(selection);
+ wizard.generated_904266101912896755(selection, this);
+
+ }
+
+ public NewTypeWizardPage getPage(NewElementWizard wizard) {
+ IWizardPage[] pages= wizard.getPages();
+ Assert.isTrue(pages.length > 0 && pages[0] instanceof NewTypeWizardPage);
+ return (NewTypeWizardPage) pages[0];
+ }
+
+ private NewElementWizard createWizard(StructuredSelection selection) {
+ switch (fTypeKind) {
+ case K_CLASS: {
+ NewClassWizardPage page= new NewClassWizardPage();
+ page.init(selection);
+ return page.generated_1485325614336726374(this);
+ }
+ case K_INTERFACE: {
+ NewInterfaceWizardPage page= new NewInterfaceWizardPage();
+ page.init(selection);
+ configureWizardPage(page);
+ return new NewInterfaceCreationWizard(page, true);
+ }
+ case K_ENUM: {
+ NewEnumWizardPage page= new NewEnumWizardPage();
+ page.init(selection);
+ configureWizardPage(page);
+ return new NewEnumCreationWizard(page, true);
+ }
+ case K_ANNOTATION: {
+ NewAnnotationWizardPage page= new NewAnnotationWizardPage();
+ page.init(selection);
+ configureWizardPage(page);
+ return new NewAnnotationCreationWizard(page, true);
+ }
+ }
+ throw new IllegalArgumentException();
+ }
+
+ public void configureWizardPage(NewTypeWizardPage page) {
+ page.generated_9162701838499014517(this);
+ }
+
+ /**
+ * Fill-in the "Package" and "Name" fields.
+ * @param page the wizard page.
+ */
+ public void fillInWizardPageName(NewTypeWizardPage page) {
+ // allow to edit when there are type parameters
+ page.generated_7046135698741273911(this);
+ }
+
+ /**
+ * Fill-in the "Super Class" and "Super Interfaces" fields.
+ * @param page the wizard page.
+ */
+ public void fillInWizardPageSuperTypes(NewTypeWizardPage page) {
+ ITypeBinding type= getPossibleSuperTypeBinding(fNode);
+ type= Bindings.normalizeTypeBinding(type);
+ page.generated_8611962565835975360(this, type);
+ }
+
+ private ITypeBinding getPossibleSuperTypeBinding(ASTNode node) {
+ if (fTypeKind == K_ANNOTATION) {
+ return null;
+ }
+
+ AST ast= node.getAST();
+ node= ASTNodes.getNormalizedNode(node);
+ ASTNode parent= node.getParent();
+ switch (parent.getNodeType()) {
+ case ASTNode.METHOD_DECLARATION:
+ if (node.getLocationInParent() == MethodDeclaration.THROWN_EXCEPTIONS_PROPERTY) {
+ return ast.resolveWellKnownType("java.lang.Exception"); //$NON-NLS-1$
+ }
+ break;
+ case ASTNode.THROW_STATEMENT :
+ return ast.resolveWellKnownType("java.lang.Exception"); //$NON-NLS-1$
+ case ASTNode.SINGLE_VARIABLE_DECLARATION:
+ if (parent.getLocationInParent() == CatchClause.EXCEPTION_PROPERTY) {
+ return ast.resolveWellKnownType("java.lang.Exception"); //$NON-NLS-1$
+ }
+ break;
+ case ASTNode.VARIABLE_DECLARATION_STATEMENT:
+ case ASTNode.FIELD_DECLARATION:
+ return null; // no guessing for LHS types, cannot be a supertype of a known type
+ case ASTNode.PARAMETERIZED_TYPE:
+ return null; // Inheritance doesn't help: A<X> z= new A<String>(); ->
+ }
+ ITypeBinding binding= ASTResolving.guessBindingForTypeReference(node);
+ if (binding != null && !binding.isRecovered()) {
+ return binding;
+ }
+ return null;
+ }
+
+ /*
+ * @see org.eclipse.jface.text.contentassist.ICompletionProposalExtension5#getAdditionalProposalInfo(org.eclipse.core.runtime.IProgressMonitor)
+ * @since 3.5
+ */
+ @Override
+ public Object getAdditionalProposalInfo(IProgressMonitor monitor) {
+ StringBuffer buf= new StringBuffer();
+ switch (fTypeKind) {
+ case K_CLASS:
+ buf.append(CorrectionMessages.NewCUCompletionUsingWizardProposal_createclass_info);
+ break;
+ case K_INTERFACE:
+ buf.append(CorrectionMessages.NewCUCompletionUsingWizardProposal_createinterface_info);
+ break;
+ case K_ENUM:
+ buf.append(CorrectionMessages.NewCUCompletionUsingWizardProposal_createenum_info);
+ break;
+ case K_ANNOTATION:
+ buf.append(CorrectionMessages.NewCUCompletionUsingWizardProposal_createannotation_info);
+ break;
+ }
+ buf.append("<br>"); //$NON-NLS-1$
+ buf.append("<br>"); //$NON-NLS-1$
+ if (fTypeContainer instanceof IType) {
+ buf.append(CorrectionMessages.NewCUCompletionUsingWizardProposal_tooltip_enclosingtype);
+ } else {
+ buf.append(CorrectionMessages.NewCUCompletionUsingWizardProposal_tooltip_package);
+ }
+ buf.append(" <b>"); //$NON-NLS-1$
+ buf.append(JavaElementLabels.getElementLabel(fTypeContainer, JavaElementLabels.T_FULLY_QUALIFIED));
+ buf.append("</b><br>"); //$NON-NLS-1$
+ buf.append("public "); //$NON-NLS-1$
+
+
+ switch (fTypeKind) {
+ case K_CLASS:
+ buf.append("class <b>"); //$NON-NLS-1$
+ break;
+ case K_INTERFACE:
+ buf.append("interface <b>"); //$NON-NLS-1$
+ break;
+ case K_ENUM:
+ buf.append("enum <b>"); //$NON-NLS-1$
+ break;
+ case K_ANNOTATION:
+ buf.append("@interface <b>"); //$NON-NLS-1$
+ break;
+ }
+ nameToHTML(fTypeNameWithParameters, buf);
+
+ ITypeBinding superclass= getPossibleSuperTypeBinding(fNode);
+ if (superclass != null) {
+ if (superclass.isClass()) {
+ if (fTypeKind == K_CLASS) {
+ buf.append("</b> extends <b>"); //$NON-NLS-1$
+ nameToHTML(BindingLabelProvider.getBindingLabel(superclass, BindingLabelProvider.DEFAULT_TEXTFLAGS), buf);
+ }
+ } else {
+ if (fTypeKind == K_INTERFACE) {
+ buf.append("</b> extends <b>"); //$NON-NLS-1$
+ } else {
+ buf.append("</b> implements <b>"); //$NON-NLS-1$
+ }
+ nameToHTML(BindingLabelProvider.getBindingLabel(superclass, BindingLabelProvider.DEFAULT_TEXTFLAGS), buf);
+ }
+ }
+ buf.append("</b> {<br>}<br>"); //$NON-NLS-1$
+ return buf.toString();
+ }
+
+ private void nameToHTML(String name, StringBuffer buf) {
+ for (int i= 0; i < name.length(); i++) {
+ char ch= name.charAt(i);
+ if (ch == '>') {
+ buf.append(">"); //$NON-NLS-1$
+ } else if (ch == '<') {
+ buf.append("<"); //$NON-NLS-1$
+ } else {
+ buf.append(ch);
+ }
+ }
+ }
+
+ /**
+ * Returns the showDialog.
+ * @return boolean
+ */
+ public boolean isShowDialog() {
+ return fShowDialog;
+ }
+
+ /**
+ * Sets the showDialog.
+ * @param showDialog The showDialog to set
+ */
+ public void setShowDialog(boolean showDialog) {
+ fShowDialog= showDialog;
+ }
+
+ public IType getCreatedType() {
+ return fCreatedType;
+ }
+
+
+ public int getTypeKind() {
+ return fTypeKind;
+ }
+
+}