IDEA-54393 (type element tree generation reworked)

Fixes: marking of generated elements, annotated types
This commit is contained in:
Roman Shevchenko
2013-03-14 21:04:02 +01:00
parent 238483108b
commit 75f112bc0d
18 changed files with 240 additions and 128 deletions
@@ -1,5 +1,5 @@
/*
* Copyright 2000-2012 JetBrains s.r.o.
* Copyright 2000-2013 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -13,31 +13,24 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.intellij.psi.impl.source.tree;
import com.intellij.lang.ASTFactory;
import com.intellij.lang.ASTNode;
import com.intellij.lang.PsiBuilder;
import com.intellij.lang.java.parser.JavaParser;
import com.intellij.lang.java.parser.JavaParserUtil;
import com.intellij.lexer.JavaLexer;
import com.intellij.lexer.Lexer;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.Key;
import com.intellij.pom.java.LanguageLevel;
import com.intellij.psi.*;
import com.intellij.psi.impl.GeneratedMarkerVisitor;
import com.intellij.psi.impl.light.LightTypeElement;
import com.intellij.psi.impl.source.*;
import com.intellij.psi.impl.source.codeStyle.CodeEditUtil;
import com.intellij.psi.impl.source.parsing.ParseUtilBase;
import com.intellij.psi.search.GlobalSearchScope;
import com.intellij.psi.tree.IElementType;
import com.intellij.psi.util.PsiUtil;
import com.intellij.util.CharTable;
import org.jetbrains.annotations.NonNls;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -61,15 +54,16 @@ public class JavaTreeGenerator implements TreeGenerator {
final String text = original.getText();
return createLeafFromText(text, table, manager, original, ((PsiJavaToken)original).getTokenType());
}
if (original instanceof PsiModifierList) {
final String text = original.getText();
assert text != null : "Text is null for " + original + "; " + original.getClass();
final LanguageLevel level = PsiUtil.getLanguageLevel(original);
final DummyHolder holder = DummyHolderFactory.createHolder(original.getManager(), new JavaDummyElement(text, MOD_LIST, level), null);
final TreeElement modifierListElement = holder.getTreeElement().getFirstChildNode();
if (CodeEditUtil.isNodeGenerated(original.getNode())) modifierListElement.acceptTree(new GeneratedMarkerVisitor());
return modifierListElement;
return markGeneratedIfNeeded(original, modifierListElement);
}
if (original instanceof PsiReferenceExpression) {
TreeElement element = createReferenceExpression(original.getProject(), original.getText(), original);
PsiElement refElement = ((PsiJavaCodeReferenceElement)original).resolve();
@@ -78,6 +72,7 @@ public class JavaTreeGenerator implements TreeGenerator {
}
return element;
}
if (original instanceof PsiJavaCodeReferenceElement) {
PsiElement refElement = ((PsiJavaCodeReferenceElement)original).resolve();
final boolean generated = refElement != null && CodeEditUtil.isNodeGenerated(refElement.getNode());
@@ -115,6 +110,7 @@ public class JavaTreeGenerator implements TreeGenerator {
}
return createReference(original.getProject(), original.getText(), generated);
}
if (original instanceof PsiCompiledElement) {
PsiElement sourceVersion = original.getNavigationElement();
if (sourceVersion != original) {
@@ -123,84 +119,44 @@ public class JavaTreeGenerator implements TreeGenerator {
ASTNode mirror = SourceTreeToPsiMap.psiElementToTree(((PsiCompiledElement)original).getMirror());
return ChangeUtil.generateTreeElement(SourceTreeToPsiMap.treeElementToPsi(mirror), table,manager);
}
if (original instanceof PsiTypeElement) {
final boolean generated = CodeEditUtil.isNodeGenerated(original.getNode());
PsiTypeElement typeElement = (PsiTypeElement)original;
PsiType type = typeElement.getType();
if (type instanceof PsiEllipsisType) {
TreeElement componentTypeCopy = ChangeUtil.generateTreeElement(
new LightTypeElement(original.getManager(), ((PsiEllipsisType)type).getComponentType()),
table,
manager);
if (componentTypeCopy == null) return null;
CompositeElement element = ASTFactory.composite(JavaElementType.TYPE);
CodeEditUtil.setNodeGenerated(element, generated);
element.rawAddChildren(componentTypeCopy);
element.rawAddChildren(createLeafFromText("...", table, manager, original, JavaTokenType.ELLIPSIS));
return element;
}
if (type instanceof PsiArrayType) {
TreeElement componentTypeCopy = ChangeUtil.generateTreeElement(
new LightTypeElement(original.getManager(), ((PsiArrayType)type).getComponentType()),
table,
manager);
if (componentTypeCopy == null) return null;
CompositeElement element = ASTFactory.composite(JavaElementType.TYPE);
CodeEditUtil.setNodeGenerated(element, generated);
element.rawAddChildren(componentTypeCopy);
element.rawAddChildren(createLeafFromText("[", table, manager, original, JavaTokenType.LBRACKET));
element.rawAddChildren(createLeafFromText("]", table, manager, original, JavaTokenType.RBRACKET));
return element;
}
if (type instanceof PsiPrimitiveType) {
@NonNls String text = typeElement.getText();
if (text.equals("null")) return null;
Lexer lexer = new JavaLexer(LanguageLevel.JDK_1_3);
lexer.start(text);
TreeElement keyword = ParseUtilBase.createTokenElement(lexer, table);
CodeEditUtil.setNodeGenerated(keyword, generated);
CompositeElement element = ASTFactory.composite(JavaElementType.TYPE);
CodeEditUtil.setNodeGenerated(element, generated);
element.rawAddChildren(keyword);
return element;
}
if (type instanceof PsiWildcardType || type instanceof PsiCapturedWildcardType || type instanceof PsiDisjunctionType) {
final String originalText = original.getText();
return createType(original.getProject(), originalText, null, generated);
}
if (type instanceof PsiIntersectionType) {
LightTypeElement te = new LightTypeElement(original.getManager(), ((PsiIntersectionType)type).getRepresentative());
return ChangeUtil.generateTreeElement(te, table, manager);
type = ((PsiIntersectionType)type).getRepresentative();
}
if (type instanceof PsiMethodReferenceType || type instanceof PsiLambdaExpressionType) {
else if (type instanceof PsiMethodReferenceType || type instanceof PsiLambdaExpressionType) {
type = PsiType.getJavaLangObject(manager, GlobalSearchScope.projectScope(manager.getProject()));
}
PsiClassType classType = (PsiClassType)type;
String text = type.getPresentableText();
PsiJavaParserFacade parserFacade = JavaPsiFacade.getInstance(original.getProject()).getParserFacade();
TreeElement element = (TreeElement)parserFacade.createTypeElementFromText(text, original).getNode();
String text = classType.getPresentableText();
final TreeElement element = createType(original.getProject(), text, original, false);
PsiTypeElementImpl result = SourceTreeToPsiMap.treeToPsiNotNull(element);
CodeEditUtil.setNodeGenerated(result, generated);
if (generated) {
PsiJavaCodeReferenceElement ref = result.getInnermostComponentReferenceElement();
if (ref != null) ((CompositeElement)ref.getNode()).acceptTree(new GeneratedMarkerVisitor());
PsiTypeElementImpl result = (PsiTypeElementImpl)element.getPsi();
markGeneratedIfNeeded(original, result);
if (type instanceof PsiClassType) {
encodeInfoInTypeElement(result, type);
}
encodeInfoInTypeElement(result, classType);
return result;
}
return null;
}
private static LeafElement createLeafFromText(final String text,
final CharTable table,
final PsiManager manager,
final PsiElement original,
final IElementType type) {
private static LeafElement createLeafFromText(String text, CharTable table, PsiManager manager, PsiElement original, IElementType type) {
return Factory.createSingleLeafElement(type, text, 0, text.length(), table, manager, CodeEditUtil.isNodeGenerated(original.getNode()));
}
private static TreeElement markGeneratedIfNeeded(PsiElement original, TreeElement copy) {
if (CodeEditUtil.isNodeGenerated(original.getNode())) {
copy.acceptTree(new GeneratedMarkerVisitor());
}
return copy;
}
private static TreeElement createReference(final Project project, final String text, boolean mark) {
final PsiJavaParserFacade parserFacade = JavaPsiFacade.getInstance(project).getParserFacade();
final TreeElement element = (TreeElement)parserFacade.createReferenceFromText(text, null).getNode();
@@ -214,13 +170,6 @@ public class JavaTreeGenerator implements TreeGenerator {
return (TreeElement)expression.getNode();
}
private static TreeElement createType(final Project project, final String text, final PsiElement context, final boolean mark) {
final PsiJavaParserFacade parserFacade = JavaPsiFacade.getInstance(project).getParserFacade();
final TreeElement element = (TreeElement)parserFacade.createTypeElementFromText(text, context).getNode();
if (mark) element.acceptTree(new GeneratedMarkerVisitor());
return element;
}
private static void encodeInfoInTypeElement(ASTNode typeElement, PsiType type) {
if (type instanceof PsiPrimitiveType) return;
LOG.assertTrue(typeElement.getElementType() == JavaElementType.TYPE);
@@ -1,5 +1,5 @@
/*
* Copyright 2000-2009 JetBrains s.r.o.
* Copyright 2000-2013 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -36,14 +36,14 @@ public class PsiArrayType extends PsiType {
this(componentType, PsiAnnotation.EMPTY_ARRAY);
}
public PsiArrayType(@NotNull PsiType componentType, PsiAnnotation[] annotations) {
public PsiArrayType(@NotNull PsiType componentType, @NotNull PsiAnnotation[] annotations) {
super(annotations);
myComponentType = componentType;
}
@Override
public String getPresentableText() {
return StringUtil.joinOrNull(myComponentType.getPresentableText(), "[]");
return StringUtil.joinOrNull(myComponentType.getPresentableText(), getAnnotationsTextPrefix(true, true), "[]");
}
@Override
@@ -53,7 +53,7 @@ public class PsiArrayType extends PsiType {
@Override
public String getInternalCanonicalText() {
return StringUtil.joinOrNull(myComponentType.getInternalCanonicalText(), "[]");
return StringUtil.joinOrNull(myComponentType.getInternalCanonicalText(), getAnnotationsTextPrefix(true, true), "[]");
}
@Override
@@ -1,5 +1,5 @@
/*
* Copyright 2000-2009 JetBrains s.r.o.
* Copyright 2000-2013 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -36,7 +36,7 @@ public class PsiEllipsisType extends PsiArrayType {
@Override
public String getPresentableText() {
return StringUtil.joinOrNull(getComponentType().getPresentableText(), "...");
return StringUtil.joinOrNull(getComponentType().getPresentableText(), getAnnotationsTextPrefix(true, true), "...");
}
@Override
@@ -46,13 +46,13 @@ public class PsiEllipsisType extends PsiArrayType {
@Override
public String getInternalCanonicalText() {
return StringUtil.joinOrNull(getComponentType().getInternalCanonicalText(), "...");
return StringUtil.joinOrNull(getComponentType().getInternalCanonicalText(), getAnnotationsTextPrefix(true, true), "...");
}
@Override
public boolean equalsToText(String text) {
return text.endsWith("...") && getComponentType().equalsToText(text.substring(0, text.length() - 3))
|| super.equalsToText(text);
return text.endsWith("...") && getComponentType().equalsToText(text.substring(0, text.length() - 3)) ||
super.equalsToText(text);
}
/**
@@ -1,5 +1,5 @@
/*
* Copyright 2000-2009 JetBrains s.r.o.
* Copyright 2000-2013 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -169,10 +169,11 @@ public class PsiIntersectionType extends PsiType {
@Override
public String toString() {
String s = "PsiIntersectionType: ";
for (PsiType conjunct : myConjuncts) {
s += conjunct.getPresentableText() +", ";
StringBuilder sb = new StringBuilder("PsiIntersectionType: ");
for (int i = 0; i < myConjuncts.length; i++) {
if (i > 0) sb.append(", ");
sb.append(myConjuncts[i].getPresentableText());
}
return s;
return sb.toString();
}
}
@@ -1,5 +1,5 @@
/*
* Copyright 2000-2012 JetBrains s.r.o.
* Copyright 2000-2013 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -53,7 +53,7 @@ public class PsiPrimitiveType extends PsiType {
@Override
public String getPresentableText() {
return myName;
return getAnnotationsTextPrefix() + myName;
}
@Override
@@ -63,7 +63,7 @@ public class PsiPrimitiveType extends PsiType {
@Override
public String getInternalCanonicalText() {
return getAnnotationsTextPrefix() + getCanonicalText();
return getAnnotationsTextPrefix() + myName;
}
/**
@@ -1,5 +1,5 @@
/*
* Copyright 2000-2012 JetBrains s.r.o.
* Copyright 2000-2013 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -17,8 +17,6 @@ package com.intellij.psi;
import com.intellij.psi.search.GlobalSearchScope;
import com.intellij.psi.util.TypeConversionUtil;
import com.intellij.openapi.util.text.StringUtil;
import com.intellij.util.Function;
import org.jetbrains.annotations.NonNls;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -41,6 +39,7 @@ public abstract class PsiType implements PsiAnnotationOwner {
public static final PsiType[] EMPTY_ARRAY = new PsiType[0];
private final PsiAnnotation[] myAnnotations;
protected PsiType(@NotNull PsiAnnotation[] annotations) {
myAnnotations = annotations;
}
@@ -52,22 +51,31 @@ public abstract class PsiType implements PsiAnnotationOwner {
public PsiArrayType createArrayType() {
return new PsiArrayType(this);
}
/**
* Creates array type with this type as a component.
*/
@NotNull
public PsiArrayType createArrayType(PsiAnnotation... annotations) {
return new PsiArrayType(this,annotations);
return new PsiArrayType(this, annotations);
}
/**
* @return text of this type that can be presented to user.
* @return text of the type that can be presented to a user (non-qualified references, with annotations).
*/
@NonNls
public abstract String getPresentableText();
/**
* @return text of the type (fully-qualified references, no annotations).
*/
@NonNls
public abstract String getCanonicalText();
/**
* @return text of the type (fully-qualified references, with annotations).
*/
@NonNls
public abstract String getInternalCanonicalText();
/**
@@ -109,7 +117,8 @@ public abstract class PsiType implements PsiAnnotationOwner {
*/
@NotNull
public static PsiClassType getJavaLangObject(@NotNull PsiManager manager, @NotNull GlobalSearchScope resolveScope) {
return JavaPsiFacade.getInstance(manager.getProject()).getElementFactory().createTypeByFQClassName(CommonClassNames.JAVA_LANG_OBJECT, resolveScope);
PsiElementFactory factory = JavaPsiFacade.getInstance(manager.getProject()).getElementFactory();
return factory.createTypeByFQClassName(CommonClassNames.JAVA_LANG_OBJECT, resolveScope);
}
/**
@@ -120,7 +129,8 @@ public abstract class PsiType implements PsiAnnotationOwner {
* @return the class instance.
*/
public static PsiClassType getJavaLangClass(PsiManager manager, GlobalSearchScope resolveScope) {
return JavaPsiFacade.getInstance(manager.getProject()).getElementFactory().createTypeByFQClassName(CommonClassNames.JAVA_LANG_CLASS, resolveScope);
PsiElementFactory factory = JavaPsiFacade.getInstance(manager.getProject()).getElementFactory();
return factory.createTypeByFQClassName(CommonClassNames.JAVA_LANG_CLASS, resolveScope);
}
/**
@@ -131,7 +141,8 @@ public abstract class PsiType implements PsiAnnotationOwner {
* @return the class instance.
*/
public static PsiClassType getJavaLangThrowable(PsiManager manager, GlobalSearchScope resolveScope) {
return JavaPsiFacade.getInstance(manager.getProject()).getElementFactory().createTypeByFQClassName(CommonClassNames.JAVA_LANG_THROWABLE, resolveScope);
PsiElementFactory factory = JavaPsiFacade.getInstance(manager.getProject()).getElementFactory();
return factory.createTypeByFQClassName(CommonClassNames.JAVA_LANG_THROWABLE, resolveScope);
}
/**
@@ -143,7 +154,8 @@ public abstract class PsiType implements PsiAnnotationOwner {
*/
@NotNull
public static PsiClassType getJavaLangString(PsiManager manager, GlobalSearchScope resolveScope) {
return JavaPsiFacade.getInstance(manager.getProject()).getElementFactory().createTypeByFQClassName(CommonClassNames.JAVA_LANG_STRING, resolveScope);
PsiElementFactory factory = JavaPsiFacade.getInstance(manager.getProject()).getElementFactory();
return factory.createTypeByFQClassName(CommonClassNames.JAVA_LANG_STRING, resolveScope);
}
/**
@@ -154,7 +166,8 @@ public abstract class PsiType implements PsiAnnotationOwner {
* @return the class instance.
*/
public static PsiClassType getJavaLangError(PsiManager manager, GlobalSearchScope resolveScope) {
return JavaPsiFacade.getInstance(manager.getProject()).getElementFactory().createTypeByFQClassName(CommonClassNames.JAVA_LANG_ERROR, resolveScope);
PsiElementFactory factory = JavaPsiFacade.getInstance(manager.getProject()).getElementFactory();
return factory.createTypeByFQClassName(CommonClassNames.JAVA_LANG_ERROR, resolveScope);
}
/**
@@ -165,7 +178,8 @@ public abstract class PsiType implements PsiAnnotationOwner {
* @return the class instance.
*/
public static PsiClassType getJavaLangRuntimeException(PsiManager manager, GlobalSearchScope resolveScope) {
return JavaPsiFacade.getInstance(manager.getProject()).getElementFactory().createTypeByFQClassName(CommonClassNames.JAVA_LANG_RUNTIME_EXCEPTION, resolveScope);
PsiElementFactory factory = JavaPsiFacade.getInstance(manager.getProject()).getElementFactory();
return factory.createTypeByFQClassName(CommonClassNames.JAVA_LANG_RUNTIME_EXCEPTION, resolveScope);
}
/**
@@ -195,7 +209,7 @@ public abstract class PsiType implements PsiAnnotationOwner {
* Returns the innermost component type for an array type.
*
* @return the innermost (non-array) component of the type, or <code>this</code> if the type is not
* an array type.
* an array type.
*/
@NotNull
public final PsiType getDeepComponentType() {
@@ -214,11 +228,6 @@ public abstract class PsiType implements PsiAnnotationOwner {
@Nullable
public abstract GlobalSearchScope getResolveScope();
public String toString() {
//noinspection HardCodedStringLiteral
return "PsiType:" + getPresentableText();
}
/**
* Returns the list of superclass types for a class type.
*
@@ -251,13 +260,27 @@ public abstract class PsiType implements PsiAnnotationOwner {
}
protected String getAnnotationsTextPrefix() {
PsiAnnotation[] annotations = getAnnotations();
return StringUtil.join(annotations, new Function<PsiAnnotation, String>() {
@Override
public String fun(PsiAnnotation annotation) {
return "@"+annotation.getQualifiedName();
}
}, " ") + (annotations.length == 0 ? "" : " ");
return getAnnotationsTextPrefix(false, true);
}
@NotNull
protected String getAnnotationsTextPrefix(boolean leadingSpace, boolean trailingSpace) {
PsiAnnotation[] annotations = getAnnotations();
if (annotations.length == 0) return "";
StringBuilder sb = new StringBuilder();
if (leadingSpace) sb.append(' ');
for (int i = 0; i < annotations.length; i++) {
if (i > 0) sb.append(' ');
sb.append('@').append(annotations[i].getQualifiedName());
}
if (trailingSpace) sb.append(' ');
return sb.toString();
}
@Override
public String toString() {
//noinspection HardCodedStringLiteral
return "PsiType:" + getPresentableText();
}
}
@@ -1,5 +1,5 @@
/*
* Copyright 2000-2009 JetBrains s.r.o.
* Copyright 2000-2013 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -180,7 +180,9 @@ public class PsiImmediateClassType extends PsiClassType {
enclosingClass = (PsiClass)parent;
}
}
buffer.append(getAnnotationsTextPrefix());
if (canonical == internal) {
buffer.append(getAnnotationsTextPrefix());
}
if (enclosingClass != null) {
buildText(enclosingClass, substitutor, buffer, canonical, false);
buffer.append('.');
@@ -203,7 +205,7 @@ public class PsiImmediateClassType extends PsiClassType {
buffer.append(name);
}
final PsiTypeParameter[] typeParameters = aClass.getTypeParameters();
PsiTypeParameter[] typeParameters = aClass.getTypeParameters();
if (typeParameters.length > 0) {
StringBuilder pineBuffer = new StringBuilder();
pineBuffer.append('<');
@@ -0,0 +1,12 @@
// "Cast to 'int[]'" "true"
import java.lang.annotation.*;
import static java.lang.annotation.ElementType.*;
@Target({TYPE_USE}) @interface TA { }
class C {
{
Object o = null;
@TA <caret>int @TA [] a = (@TA int[]) o;
}
}
@@ -0,0 +1,12 @@
// "Cast to 'int'" "true"
import java.lang.annotation.*;
import static java.lang.annotation.ElementType.*;
@Target({TYPE_USE}) @interface TA { }
class C {
{
Object o = null;
@TA <caret>int i = (@TA int) o;
}
}
@@ -0,0 +1,12 @@
// "Cast to 'java.lang.Integer'" "true"
import java.lang.annotation.*;
import static java.lang.annotation.ElementType.*;
@Target({TYPE_USE}) @interface TA { }
class C {
{
Object o = null;
@TA <caret>Integer i = (@TA Integer) o;
}
}
@@ -0,0 +1,13 @@
// "Cast to 'java.util.List<java.lang.String>'" "true"
import java.lang.annotation.*;
import java.util.List;
import static java.lang.annotation.ElementType.*;
@Target({TYPE_USE}) @interface TA { }
class C {
{
Object o = null;
@TA <caret>List<@TA String> l = (@TA List<@TA String>) o;
}
}
@@ -0,0 +1,13 @@
// "Cast to 'java.util.List<? extends java.lang.String>'" "true"
import java.lang.annotation.*;
import java.util.List;
import static java.lang.annotation.ElementType.*;
@Target({TYPE_USE}) @interface TA { }
class C {
{
Object o = null;
@TA <caret>List<@TA ? extends @TA String> l = (@TA List<? extends @TA String>) o;
}
}
@@ -0,0 +1,12 @@
// "Cast to 'int[]'" "true"
import java.lang.annotation.*;
import static java.lang.annotation.ElementType.*;
@Target({TYPE_USE}) @interface TA { }
class C {
{
Object o = null;
@TA <caret>int @TA [] a = o;
}
}
@@ -0,0 +1,12 @@
// "Cast to 'int'" "true"
import java.lang.annotation.*;
import static java.lang.annotation.ElementType.*;
@Target({TYPE_USE}) @interface TA { }
class C {
{
Object o = null;
@TA <caret>int i = o;
}
}
@@ -0,0 +1,12 @@
// "Cast to 'java.lang.Integer'" "true"
import java.lang.annotation.*;
import static java.lang.annotation.ElementType.*;
@Target({TYPE_USE}) @interface TA { }
class C {
{
Object o = null;
@TA <caret>Integer i = o;
}
}
@@ -0,0 +1,13 @@
// "Cast to 'java.util.List<java.lang.String>'" "true"
import java.lang.annotation.*;
import java.util.List;
import static java.lang.annotation.ElementType.*;
@Target({TYPE_USE}) @interface TA { }
class C {
{
Object o = null;
@TA <caret>List<@TA String> l = o;
}
}
@@ -0,0 +1,13 @@
// "Cast to 'java.util.List<? extends java.lang.String>'" "true"
import java.lang.annotation.*;
import java.util.List;
import static java.lang.annotation.ElementType.*;
@Target({TYPE_USE}) @interface TA { }
class C {
{
Object o = null;
@TA <caret>List<@TA ? extends @TA String> l = o;
}
}
@@ -1,16 +1,29 @@
/*
* Copyright 2000-2013 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.intellij.codeInsight.daemon.quickFix;
public class AddTypeCastTest extends LightQuickFixTestCase {
public void test() {
doAllTests();
public class AddTypeCastTest extends LightQuickFix15TestCase {
public void test() throws Exception { doAllTests(); }
Object o = null;
}
@Override
protected String getBasePath() {
return "/codeInsight/daemonCodeAnalyzer/quickFix/addTypeCast";
}
}