From 9387f10fc2b208366d0a148f960ad4cc52d8d04e Mon Sep 17 00:00:00 2001 From: Roman Shevchenko Date: Thu, 9 Jun 2011 11:45:45 +0400 Subject: [PATCH] IDEA-70089 (inherited methods should shadow statically imported ones) --- .../processor/MethodCandidatesProcessor.java | 44 ++++++++++++------- .../staticImports/P1/MethodShadowing.java | 31 +++++++++++++ .../daemon/AdvHighlightingJdk7Test.java | 4 ++ 3 files changed, 62 insertions(+), 17 deletions(-) create mode 100644 java/java-tests/testData/codeInsight/daemonCodeAnalyzer/advHighlighting7/staticImports/P1/MethodShadowing.java diff --git a/java/java-impl/src/com/intellij/psi/scope/processor/MethodCandidatesProcessor.java b/java/java-impl/src/com/intellij/psi/scope/processor/MethodCandidatesProcessor.java index d633b2178146..a81921a5cc17 100644 --- a/java/java-impl/src/com/intellij/psi/scope/processor/MethodCandidatesProcessor.java +++ b/java/java-impl/src/com/intellij/psi/scope/processor/MethodCandidatesProcessor.java @@ -1,5 +1,5 @@ /* - * Copyright 2000-2009 JetBrains s.r.o. + * Copyright 2000-2011 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. @@ -24,64 +24,74 @@ import com.intellij.psi.scope.conflictResolvers.DuplicateConflictResolver; import com.intellij.util.SmartList; /** - * Created by IntelliJ IDEA. - * User: ik + * @author ik * Date: 31.01.2003 - * Time: 19:31:12 - * To change this template use Options | File Templates. */ public class MethodCandidatesProcessor extends MethodsProcessor{ protected boolean myHasAccessibleStaticCorrectCandidate = false; - public MethodCandidatesProcessor(PsiElement place, PsiConflictResolver[] resolvers, SmartList container){ + public MethodCandidatesProcessor(PsiElement place, PsiConflictResolver[] resolvers, SmartList container) { super(resolvers, container, place); } - public MethodCandidatesProcessor(PsiElement place){ + public MethodCandidatesProcessor(PsiElement place) { super(new PsiConflictResolver[]{DuplicateConflictResolver.INSTANCE}, new SmartList(), place); } public void add(PsiElement element, PsiSubstitutor substitutor) { - if (element instanceof PsiMethod){ + if (element instanceof PsiMethod) { final PsiMethod method = (PsiMethod)element; addMethod(method, substitutor, isInStaticScope() && !method.hasModifierProperty(PsiModifier.STATIC)); } } public void addMethod(final PsiMethod method, final PsiSubstitutor substitutor, final boolean staticProblem) { - boolean isAccessible = JavaResolveUtil.isAccessible(method, method.getContainingClass(), method.getModifierList(), - myPlace, myAccessClass, myCurrentFileContext, myPlaceFile); - myHasAccessibleStaticCorrectCandidate |= isAccessible && !staticProblem; - + final boolean isAccessible = JavaResolveUtil.isAccessible(method, method.getContainingClass(), method.getModifierList(), + myPlace, myAccessClass, myCurrentFileContext, myPlaceFile) && + !isShadowed(method); if (isAccepted(method)) { add(createCandidateInfo(method, substitutor, staticProblem, isAccessible)); + myHasAccessibleStaticCorrectCandidate |= isAccessible && !staticProblem; } } protected MethodCandidateInfo createCandidateInfo(final PsiMethod method, final PsiSubstitutor substitutor, - final boolean staticProblem, - final boolean accessible) { + final boolean staticProblem, final boolean accessible) { return new MethodCandidateInfo(method, substitutor, !accessible, staticProblem, getArgumentList(), myCurrentFileContext, getArgumentList().getExpressionTypes(), getTypeArguments(), getLanguageLevel()); } protected boolean isAccepted(final PsiMethod candidate) { if (!isConstructor()) { - return !candidate.isConstructor() && getName(ResolveState.initial()).equals(candidate.getName()); + return !candidate.isConstructor() && candidate.getName().equals(getName(ResolveState.initial())); } else { if (!candidate.isConstructor()) return false; if (myAccessClass == null) return true; if (myAccessClass instanceof PsiAnonymousClass) { - return candidate.getContainingClass().equals(myAccessClass.getSuperClass()); + final PsiClass containingClass = candidate.getContainingClass(); + return containingClass != null && containingClass.equals(myAccessClass.getSuperClass()); } return myAccessClass.equals(candidate.getContainingClass()); } } + protected boolean isShadowed(final PsiMethod candidate) { + if (myCurrentFileContext instanceof PsiImportStaticStatement) { + for (JavaResolveResult result : getResult()) { + if (result.getElement() != candidate && + result.isAccessible() && + !(result.getCurrentFileResolveScope() instanceof PsiImportStaticStatement)) return true; + } + } + return false; + } + public CandidateInfo[] getCandidates() { final JavaResolveResult[] resolveResult = getResult(); - CandidateInfo[] infos = new CandidateInfo[resolveResult.length]; + if (resolveResult.length == 0) return CandidateInfo.EMPTY_ARRAY; + final CandidateInfo[] infos = new CandidateInfo[resolveResult.length]; + //noinspection SuspiciousSystemArraycopy System.arraycopy(resolveResult, 0, infos, 0, resolveResult.length); return infos; } diff --git a/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/advHighlighting7/staticImports/P1/MethodShadowing.java b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/advHighlighting7/staticImports/P1/MethodShadowing.java new file mode 100644 index 000000000000..694ceda3ce36 --- /dev/null +++ b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/advHighlighting7/staticImports/P1/MethodShadowing.java @@ -0,0 +1,31 @@ +/* + * Copyright 2000-2011 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 P1; + +import static P1.Outside.getObject; + +class Outside { + static Object getObject(Object dummy) { return "Static"; } +} + +class Base { + Object getObject() { return "Instance"; } +} + +class Derived extends Base { + final static Object o1 = getObject(null); + final Object o2 = getObject(null); +} diff --git a/java/java-tests/testSrc/com/intellij/codeInsight/daemon/AdvHighlightingJdk7Test.java b/java/java-tests/testSrc/com/intellij/codeInsight/daemon/AdvHighlightingJdk7Test.java index 71ce3c297525..4cdb0d4c29cc 100644 --- a/java/java-tests/testSrc/com/intellij/codeInsight/daemon/AdvHighlightingJdk7Test.java +++ b/java/java-tests/testSrc/com/intellij/codeInsight/daemon/AdvHighlightingJdk7Test.java @@ -52,4 +52,8 @@ public class AdvHighlightingJdk7Test extends DaemonAnalyzerTestCase { public void testStaticOnDemandImportConflict() throws Exception { doTest(BASE_PATH + "staticImportConflict/UsageOnDemand.java", BASE_PATH + "/staticImportConflict", false, false); } + + public void testStaticImportMethodShadowing() throws Exception { + doTest(BASE_PATH + "staticImports/P1/MethodShadowing.java", BASE_PATH + "/staticImports", false, false); + } }