mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-05-06 05:10:22 +07:00
(on-the-fly) static import of constant
This commit is contained in:
@@ -39,6 +39,7 @@ public class DefaultQuickFixProvider extends UnresolvedReferenceQuickFixProvider
|
||||
public void registerFixes(@NotNull PsiJavaCodeReferenceElement ref, @NotNull QuickFixActionRegistrar registrar) {
|
||||
QuickFixFactory factory = QuickFixFactory.getInstance();
|
||||
registrar.register(new ImportClassFix(ref));
|
||||
registrar.register(new StaticImportConstantFix(ref));
|
||||
registrar.register(factory.createSetupJDKFix());
|
||||
|
||||
OrderEntryFix.registerFixes(registrar, ref);
|
||||
|
||||
@@ -0,0 +1,194 @@
|
||||
/*
|
||||
* Copyright 2000-2016 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.impl.quickfix;
|
||||
|
||||
import com.intellij.codeInsight.completion.JavaCompletionUtil;
|
||||
import com.intellij.openapi.progress.ProgressManager;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.util.PsiTreeUtil;
|
||||
import com.intellij.psi.util.PsiUtil;
|
||||
import com.intellij.psi.util.proximity.PsiProximityComparator;
|
||||
import com.intellij.util.ArrayUtilRt;
|
||||
import com.intellij.util.Processor;
|
||||
import com.intellij.util.containers.LinkedMultiMap;
|
||||
import com.intellij.util.containers.MultiMap;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.*;
|
||||
|
||||
abstract class MyStaticMembersProcessor<T extends PsiMember> implements Processor<T> {
|
||||
private final MultiMap<PsiClass, T> myDeprecated = new LinkedMultiMap<PsiClass, T>();
|
||||
private final MultiMap<PsiClass, T> mySuggestions = new LinkedMultiMap<PsiClass, T>();
|
||||
|
||||
private final Map<PsiClass, Boolean> myPossibleClasses = new HashMap<PsiClass, Boolean>();
|
||||
|
||||
private final PsiElement myPlace;
|
||||
private PsiType myExpectedType;
|
||||
|
||||
protected MyStaticMembersProcessor(PsiElement place) {
|
||||
myPlace = place;
|
||||
myExpectedType = PsiType.NULL;
|
||||
}
|
||||
|
||||
protected abstract boolean isApplicable(T member, PsiElement place);
|
||||
|
||||
@NotNull
|
||||
public List<T> getMembersToImport() {
|
||||
final List<T> list = new ArrayList<T>();
|
||||
final List<T> applicableList = new ArrayList<T>();
|
||||
for (Map.Entry<PsiClass, Collection<T>> methodEntry : mySuggestions.entrySet()) {
|
||||
registerMember(methodEntry.getKey(), methodEntry.getValue(), list, applicableList);
|
||||
}
|
||||
|
||||
for (Map.Entry<PsiClass, Collection<T>> deprecatedMethod : myDeprecated.entrySet()) {
|
||||
registerMember(deprecatedMethod.getKey(), deprecatedMethod.getValue(), list, applicableList);
|
||||
}
|
||||
|
||||
List<T> result = applicableList.isEmpty() ? list : applicableList;
|
||||
for (int i = result.size() - 1; i >= 0; i--) {
|
||||
ProgressManager.checkCanceled();
|
||||
T method = result.get(i);
|
||||
// check for manually excluded
|
||||
if (StaticImportMethodFix.isExcluded(method)) {
|
||||
result.remove(i);
|
||||
}
|
||||
}
|
||||
Collections.sort(result, new PsiProximityComparator(myPlace));
|
||||
return result;
|
||||
}
|
||||
|
||||
public PsiType getExpectedType() {
|
||||
if (myExpectedType == PsiType.NULL) {
|
||||
myExpectedType = getExpectedTypeInternal();
|
||||
}
|
||||
return myExpectedType;
|
||||
}
|
||||
|
||||
private PsiType getExpectedTypeInternal() {
|
||||
if (myPlace == null) return null;
|
||||
final PsiElement parent = PsiUtil.skipParenthesizedExprUp(myPlace.getParent());
|
||||
|
||||
if (parent instanceof PsiVariable) {
|
||||
if (myPlace.equals(PsiUtil.skipParenthesizedExprDown(((PsiVariable)parent).getInitializer()))) {
|
||||
return ((PsiVariable)parent).getType();
|
||||
}
|
||||
}
|
||||
else if (parent instanceof PsiAssignmentExpression) {
|
||||
if (myPlace.equals(PsiUtil.skipParenthesizedExprDown(((PsiAssignmentExpression)parent).getRExpression()))) {
|
||||
return ((PsiAssignmentExpression)parent).getLExpression().getType();
|
||||
}
|
||||
}
|
||||
else if (parent instanceof PsiReturnStatement) {
|
||||
final PsiElement psiElement = PsiTreeUtil.getParentOfType(parent, PsiLambdaExpression.class, PsiMethod.class);
|
||||
if (psiElement instanceof PsiLambdaExpression) {
|
||||
return LambdaUtil.getFunctionalInterfaceReturnType(((PsiLambdaExpression)psiElement).getFunctionalInterfaceType());
|
||||
}
|
||||
else if (psiElement instanceof PsiMethod) {
|
||||
return ((PsiMethod)psiElement).getReturnType();
|
||||
}
|
||||
}
|
||||
else if (parent instanceof PsiExpressionList) {
|
||||
final PsiElement pParent = parent.getParent();
|
||||
if (pParent instanceof PsiCallExpression && parent.equals(((PsiCallExpression)pParent).getArgumentList())) {
|
||||
final JavaResolveResult resolveResult = ((PsiCallExpression)pParent).resolveMethodGenerics();
|
||||
final PsiElement psiElement = resolveResult.getElement();
|
||||
if (psiElement instanceof PsiMethod) {
|
||||
final PsiMethod psiMethod = (PsiMethod)psiElement;
|
||||
final PsiParameter[] parameters = psiMethod.getParameterList().getParameters();
|
||||
final int idx = ArrayUtilRt.find(((PsiExpressionList)parent).getExpressions(), PsiUtil.skipParenthesizedExprUp(myPlace));
|
||||
if (idx > -1 && parameters.length > 0) {
|
||||
PsiType parameterType = parameters[Math.min(idx, parameters.length - 1)].getType();
|
||||
if (idx >= parameters.length - 1) {
|
||||
final PsiParameter lastParameter = parameters[parameters.length - 1];
|
||||
if (lastParameter.isVarArgs()) {
|
||||
parameterType = ((PsiEllipsisType)lastParameter.getType()).getComponentType();
|
||||
}
|
||||
}
|
||||
return resolveResult.getSubstitutor().substitute(parameterType);
|
||||
}
|
||||
else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (parent instanceof PsiLambdaExpression) {
|
||||
return LambdaUtil.getFunctionalInterfaceReturnType(((PsiLambdaExpression)parent).getFunctionalInterfaceType());
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean process(T member) {
|
||||
ProgressManager.checkCanceled();
|
||||
if (JavaCompletionUtil.isInExcludedPackage(member, false) || !member.hasModifierProperty(PsiModifier.STATIC)) return true;
|
||||
PsiFile file = member.getContainingFile();
|
||||
final PsiClass containingClass = member.getContainingClass();
|
||||
if (file instanceof PsiJavaFile
|
||||
//do not show methods from default package
|
||||
&& !((PsiJavaFile)file).getPackageName().isEmpty()) {
|
||||
if (isEffectivelyDeprecated(member)) {
|
||||
myDeprecated.putValue(containingClass, member);
|
||||
return processCondition();
|
||||
}
|
||||
mySuggestions.putValue(containingClass, member);
|
||||
}
|
||||
return processCondition();
|
||||
}
|
||||
|
||||
private boolean isEffectivelyDeprecated(T member) {
|
||||
if (((PsiDocCommentOwner)member).isDeprecated()) {
|
||||
return true;
|
||||
}
|
||||
|
||||
PsiClass aClass = member.getContainingClass();
|
||||
while (aClass != null) {
|
||||
if (aClass.isDeprecated()) {
|
||||
return true;
|
||||
}
|
||||
aClass = aClass.getContainingClass();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private boolean processCondition() {
|
||||
return mySuggestions.size() + myDeprecated.size() < 50;
|
||||
}
|
||||
|
||||
private void registerMember(PsiClass containingClass,
|
||||
Collection<T> members,
|
||||
List<T> list,
|
||||
List<T> applicableList) {
|
||||
final Boolean alreadyMentioned = myPossibleClasses.get(containingClass);
|
||||
if (alreadyMentioned == Boolean.TRUE) return;
|
||||
if (alreadyMentioned == null) {
|
||||
if (!members.isEmpty()) {
|
||||
list.add(members.iterator().next());
|
||||
}
|
||||
myPossibleClasses.put(containingClass, false);
|
||||
}
|
||||
for (T member : members) {
|
||||
if (!PsiUtil.isAccessible(myPlace.getProject(), member, myPlace, containingClass)) {
|
||||
continue;
|
||||
}
|
||||
if (isApplicable(member, myPlace)) {
|
||||
applicableList.add(member);
|
||||
myPossibleClasses.put(containingClass, true);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,102 @@
|
||||
/*
|
||||
* Copyright 2000-2016 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.impl.quickfix;
|
||||
|
||||
import com.intellij.codeInsight.daemon.QuickFixBundle;
|
||||
import com.intellij.openapi.editor.Editor;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.search.PsiShortNamesCache;
|
||||
import com.intellij.psi.util.PsiFormatUtil;
|
||||
import com.intellij.psi.util.PsiFormatUtilBase;
|
||||
import com.intellij.psi.util.TypeConversionUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
public class StaticImportConstantFix extends StaticImportMemberFix<PsiField> {
|
||||
private final SmartPsiElementPointer<PsiJavaCodeReferenceElement> myRef;
|
||||
|
||||
public StaticImportConstantFix(@NotNull PsiJavaCodeReferenceElement referenceElement) {
|
||||
myRef = SmartPointerManager.getInstance(referenceElement.getProject()).createSmartPsiElementPointer(referenceElement);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
protected String getBaseText() {
|
||||
return "Static import constant";
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
protected String getMemberPresentableText(PsiField field) {
|
||||
return PsiFormatUtil.formatVariable(field, PsiFormatUtilBase.SHOW_NAME |
|
||||
PsiFormatUtilBase.SHOW_CONTAINING_CLASS |
|
||||
PsiFormatUtilBase.SHOW_FQ_NAME, PsiSubstitutor.EMPTY);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
protected List<PsiField> getMembersToImport() {
|
||||
final Project project = myRef.getProject();
|
||||
PsiShortNamesCache cache = PsiShortNamesCache.getInstance(project);
|
||||
final PsiJavaCodeReferenceElement element = myRef.getElement();
|
||||
String name = element != null ? element.getReferenceName() : null;
|
||||
if (name == null) return Collections.emptyList();
|
||||
final MyStaticMembersProcessor<PsiField> processor = new MyStaticMembersProcessor<PsiField>(element) {
|
||||
@Override
|
||||
protected boolean isApplicable(PsiField field, PsiElement place) {
|
||||
final PsiType expectedType = getExpectedType();
|
||||
return expectedType == null || TypeConversionUtil.isAssignable(expectedType, field.getType());
|
||||
}
|
||||
};
|
||||
cache.processFieldsWithName(name, processor, element.getResolveScope(), null);
|
||||
return processor.getMembersToImport();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected StaticImportMethodQuestionAction<PsiField> createQuestionAction(List<PsiField> methodsToImport, @NotNull Project project, Editor editor) {
|
||||
return new StaticImportMethodQuestionAction<PsiField>(project, editor, methodsToImport, myRef) {
|
||||
@NotNull
|
||||
@Override
|
||||
protected String getPopupTitle() {
|
||||
return QuickFixBundle.message("field.to.import.chooser.title");
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
protected PsiElement getElement() {
|
||||
return myRef.getElement();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
protected PsiElement getQualifierExpression() {
|
||||
final PsiJavaCodeReferenceElement element = myRef.getElement();
|
||||
return element != null ? element.getQualifier() : null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
protected PsiElement resolveRef() {
|
||||
final PsiJavaCodeReferenceElement referenceElement = (PsiJavaCodeReferenceElement)getElement();
|
||||
return referenceElement != null ? referenceElement.resolve() : null;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,146 @@
|
||||
/*
|
||||
* Copyright 2000-2016 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.impl.quickfix;
|
||||
|
||||
import com.intellij.codeInsight.FileModificationService;
|
||||
import com.intellij.codeInsight.daemon.impl.ShowAutoImportPass;
|
||||
import com.intellij.codeInsight.hint.HintManager;
|
||||
import com.intellij.codeInsight.hint.QuestionAction;
|
||||
import com.intellij.codeInsight.intention.IntentionAction;
|
||||
import com.intellij.codeInspection.HintAction;
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.command.CommandProcessor;
|
||||
import com.intellij.openapi.editor.Editor;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiFile;
|
||||
import com.intellij.psi.PsiJavaFile;
|
||||
import com.intellij.psi.PsiMember;
|
||||
import com.intellij.psi.util.PsiUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public abstract class StaticImportMemberFix<T extends PsiMember> implements IntentionAction, HintAction {
|
||||
private List<T> candidates;
|
||||
|
||||
@NotNull protected abstract String getBaseText();
|
||||
@NotNull protected abstract String getMemberPresentableText(T t);
|
||||
|
||||
@Override
|
||||
@NotNull
|
||||
public String getText() {
|
||||
String text = getBaseText();
|
||||
if (candidates != null && candidates.size() == 1) {
|
||||
text += " '" + getMemberPresentableText(candidates.get(0)) + "'";
|
||||
}
|
||||
else {
|
||||
text += "...";
|
||||
}
|
||||
return text;
|
||||
}
|
||||
|
||||
@Override
|
||||
@NotNull
|
||||
public String getFamilyName() {
|
||||
return getText();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isAvailable(@NotNull Project project, Editor editor, PsiFile file) {
|
||||
return PsiUtil.isLanguageLevel5OrHigher(file)
|
||||
&& file instanceof PsiJavaFile
|
||||
&& getElement() != null
|
||||
&& getElement().isValid()
|
||||
&& getQualifierExpression() == null
|
||||
&& resolveRef() == null
|
||||
&& file.getManager().isInProject(file)
|
||||
&& !(candidates == null ? candidates = getMembersToImport() : candidates).isEmpty()
|
||||
;
|
||||
}
|
||||
|
||||
@NotNull protected abstract List<T> getMembersToImport();
|
||||
@NotNull protected abstract QuestionAction createQuestionAction(List<T> methodsToImport, @NotNull Project project, Editor editor);
|
||||
|
||||
@Nullable protected abstract PsiElement getElement();
|
||||
@Nullable protected abstract PsiElement getQualifierExpression();
|
||||
@Nullable protected abstract PsiElement resolveRef();
|
||||
|
||||
@Override
|
||||
public void invoke(@NotNull final Project project, final Editor editor, PsiFile file) {
|
||||
if (!FileModificationService.getInstance().prepareFileForWrite(file)) return;
|
||||
ApplicationManager.getApplication().runWriteAction(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
final List<T> methodsToImport = getMembersToImport();
|
||||
if (methodsToImport.isEmpty()) return;
|
||||
createQuestionAction(methodsToImport, project, editor).execute();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private ImportClassFixBase.Result doFix(Editor editor) {
|
||||
if (candidates.isEmpty()) {
|
||||
return ImportClassFixBase.Result.POPUP_NOT_SHOWN;
|
||||
}
|
||||
|
||||
final PsiElement element = getElement();
|
||||
if (element == null) {
|
||||
return ImportClassFixBase.Result.POPUP_NOT_SHOWN;
|
||||
}
|
||||
|
||||
final QuestionAction action = createQuestionAction(candidates, element.getProject(), editor);
|
||||
if (candidates.size() == 1 && ImportClassFixBase.canAddUnambiguousImport(element.getContainingFile())) {
|
||||
CommandProcessor.getInstance().runUndoTransparentAction(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
action.execute();
|
||||
}
|
||||
});
|
||||
return ImportClassFixBase.Result.CLASS_AUTO_IMPORTED;
|
||||
}
|
||||
|
||||
String hintText = ShowAutoImportPass.getMessage(candidates.size() > 1, getMemberPresentableText(candidates.get(0)));
|
||||
if (!ApplicationManager.getApplication().isUnitTestMode() && !HintManager.getInstance().hasShownHintsThatWillHideByOtherHint(true)) {
|
||||
final TextRange textRange = element.getTextRange();
|
||||
HintManager.getInstance().showQuestionHint(editor, hintText,
|
||||
textRange.getStartOffset(),
|
||||
textRange.getEndOffset(), action);
|
||||
}
|
||||
return ImportClassFixBase.Result.POPUP_SHOWN;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@Override
|
||||
public boolean startInWriteAction() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean showHint(@NotNull Editor editor) {
|
||||
final PsiElement callExpression = getElement();
|
||||
if (callExpression == null ||
|
||||
getQualifierExpression() != null) {
|
||||
return false;
|
||||
}
|
||||
ImportClassFixBase.Result result = doFix(editor);
|
||||
return result == ImportClassFixBase.Result.POPUP_SHOWN || result == ImportClassFixBase.Result.CLASS_AUTO_IMPORTED;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -15,245 +15,56 @@
|
||||
*/
|
||||
package com.intellij.codeInsight.daemon.impl.quickfix;
|
||||
|
||||
import com.intellij.codeInsight.FileModificationService;
|
||||
import com.intellij.codeInsight.JavaProjectCodeInsightSettings;
|
||||
import com.intellij.codeInsight.completion.JavaCompletionUtil;
|
||||
import com.intellij.codeInsight.daemon.QuickFixBundle;
|
||||
import com.intellij.codeInsight.daemon.impl.ShowAutoImportPass;
|
||||
import com.intellij.codeInsight.hint.HintManager;
|
||||
import com.intellij.codeInsight.intention.IntentionAction;
|
||||
import com.intellij.codeInspection.HintAction;
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.command.CommandProcessor;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.editor.Editor;
|
||||
import com.intellij.openapi.progress.ProgressManager;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.impl.source.resolve.DefaultParameterTypeInferencePolicy;
|
||||
import com.intellij.psi.search.GlobalSearchScope;
|
||||
import com.intellij.psi.search.PsiShortNamesCache;
|
||||
import com.intellij.psi.util.*;
|
||||
import com.intellij.psi.util.proximity.PsiProximityComparator;
|
||||
import com.intellij.util.ArrayUtilRt;
|
||||
import com.intellij.util.Processor;
|
||||
import com.intellij.util.containers.LinkedMultiMap;
|
||||
import com.intellij.util.containers.MultiMap;
|
||||
import com.intellij.psi.util.PsiFormatUtil;
|
||||
import com.intellij.psi.util.PsiFormatUtilBase;
|
||||
import com.intellij.psi.util.PsiUtil;
|
||||
import com.intellij.psi.util.TypeConversionUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.*;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
public class StaticImportMethodFix implements IntentionAction, HintAction {
|
||||
private static final Logger LOG = Logger.getInstance("#com.intellij.codeInsight.daemon.impl.quickfix.StaticImportMethodFix");
|
||||
public class StaticImportMethodFix extends StaticImportMemberFix<PsiMethod> {
|
||||
private final SmartPsiElementPointer<PsiMethodCallExpression> myMethodCall;
|
||||
private List<PsiMethod> candidates;
|
||||
|
||||
public StaticImportMethodFix(@NotNull PsiMethodCallExpression methodCallExpression) {
|
||||
myMethodCall = SmartPointerManager.getInstance(methodCallExpression.getProject()).createSmartPsiElementPointer(methodCallExpression);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
@NotNull
|
||||
public String getText() {
|
||||
String text = QuickFixBundle.message("static.import.method.text");
|
||||
if (candidates != null && candidates.size() == 1) {
|
||||
text += " '" + getMethodPresentableText() + "'";
|
||||
}
|
||||
else {
|
||||
text += "...";
|
||||
}
|
||||
return text;
|
||||
protected String getBaseText() {
|
||||
return QuickFixBundle.message("static.import.method.text");
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private String getMethodPresentableText() {
|
||||
return PsiFormatUtil.formatMethod(candidates.get(0), PsiSubstitutor.EMPTY, PsiFormatUtilBase.SHOW_NAME |
|
||||
PsiFormatUtilBase.SHOW_CONTAINING_CLASS |
|
||||
PsiFormatUtilBase.SHOW_FQ_NAME, 0);
|
||||
}
|
||||
|
||||
@Override
|
||||
@NotNull
|
||||
public String getFamilyName() {
|
||||
return getText();
|
||||
protected String getMemberPresentableText(PsiMethod method) {
|
||||
return PsiFormatUtil.formatMethod(method, PsiSubstitutor.EMPTY, PsiFormatUtilBase.SHOW_NAME |
|
||||
PsiFormatUtilBase.SHOW_CONTAINING_CLASS |
|
||||
PsiFormatUtilBase.SHOW_FQ_NAME, 0);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public boolean isAvailable(@NotNull Project project, Editor editor, PsiFile file) {
|
||||
return PsiUtil.isLanguageLevel5OrHigher(file)
|
||||
&& file instanceof PsiJavaFile
|
||||
&& myMethodCall.getElement() != null
|
||||
&& myMethodCall.getElement().isValid()
|
||||
&& myMethodCall.getElement().getMethodExpression().getQualifierExpression() == null
|
||||
&& myMethodCall.getElement().resolveMethod() == null
|
||||
&& file.getManager().isInProject(file)
|
||||
&& !(candidates == null ? candidates = getMethodsToImport() : candidates).isEmpty()
|
||||
;
|
||||
}
|
||||
|
||||
private PsiType getExpectedType() {
|
||||
final PsiMethodCallExpression methodCall = myMethodCall.getElement();
|
||||
if (methodCall == null) return null;
|
||||
final PsiElement parent = PsiUtil.skipParenthesizedExprUp(methodCall.getParent());
|
||||
|
||||
if (parent instanceof PsiVariable) {
|
||||
if (methodCall.equals(PsiUtil.skipParenthesizedExprDown(((PsiVariable)parent).getInitializer()))) {
|
||||
return ((PsiVariable)parent).getType();
|
||||
}
|
||||
}
|
||||
else if (parent instanceof PsiAssignmentExpression) {
|
||||
if (methodCall.equals(PsiUtil.skipParenthesizedExprDown(((PsiAssignmentExpression)parent).getRExpression()))) {
|
||||
return ((PsiAssignmentExpression)parent).getLExpression().getType();
|
||||
}
|
||||
}
|
||||
else if (parent instanceof PsiReturnStatement) {
|
||||
final PsiElement psiElement = PsiTreeUtil.getParentOfType(parent, PsiLambdaExpression.class, PsiMethod.class);
|
||||
if (psiElement instanceof PsiLambdaExpression) {
|
||||
return LambdaUtil.getFunctionalInterfaceReturnType(((PsiLambdaExpression)psiElement).getFunctionalInterfaceType());
|
||||
}
|
||||
else if (psiElement instanceof PsiMethod) {
|
||||
return ((PsiMethod)psiElement).getReturnType();
|
||||
}
|
||||
}
|
||||
else if (parent instanceof PsiExpressionList) {
|
||||
final PsiElement pParent = parent.getParent();
|
||||
if (pParent instanceof PsiCallExpression && parent.equals(((PsiCallExpression)pParent).getArgumentList())) {
|
||||
final JavaResolveResult resolveResult = ((PsiCallExpression)pParent).resolveMethodGenerics();
|
||||
final PsiElement psiElement = resolveResult.getElement();
|
||||
if (psiElement instanceof PsiMethod) {
|
||||
final PsiMethod psiMethod = (PsiMethod)psiElement;
|
||||
final PsiParameter[] parameters = psiMethod.getParameterList().getParameters();
|
||||
final int idx = ArrayUtilRt.find(((PsiExpressionList)parent).getExpressions(), PsiUtil.skipParenthesizedExprUp(methodCall));
|
||||
if (idx > -1 && parameters.length > 0) {
|
||||
PsiType parameterType = parameters[Math.min(idx, parameters.length - 1)].getType();
|
||||
if (idx >= parameters.length - 1) {
|
||||
final PsiParameter lastParameter = parameters[parameters.length - 1];
|
||||
if (lastParameter.isVarArgs()) {
|
||||
parameterType = ((PsiEllipsisType)lastParameter.getType()).getComponentType();
|
||||
}
|
||||
}
|
||||
return resolveResult.getSubstitutor().substitute(parameterType);
|
||||
}
|
||||
else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (parent instanceof PsiLambdaExpression) {
|
||||
return LambdaUtil.getFunctionalInterfaceReturnType(((PsiLambdaExpression)parent).getFunctionalInterfaceType());
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private List<PsiMethod> getMethodsToImport() {
|
||||
protected List<PsiMethod> getMembersToImport() {
|
||||
final Project project = myMethodCall.getProject();
|
||||
PsiShortNamesCache cache = PsiShortNamesCache.getInstance(project);
|
||||
final PsiMethodCallExpression element = myMethodCall.getElement();
|
||||
PsiReferenceExpression reference = element.getMethodExpression();
|
||||
final PsiExpressionList argumentList = element.getArgumentList();
|
||||
String name = reference.getReferenceName();
|
||||
final List<PsiMethod> list = new ArrayList<PsiMethod>();
|
||||
if (name == null) return list;
|
||||
GlobalSearchScope scope = element.getResolveScope();
|
||||
final Map<PsiClass, Boolean> possibleClasses = new HashMap<PsiClass, Boolean>();
|
||||
final PsiType expectedType = getExpectedType();
|
||||
final List<PsiMethod> applicableList = new ArrayList<PsiMethod>();
|
||||
final PsiResolveHelper resolveHelper = JavaPsiFacade.getInstance(project).getResolveHelper();
|
||||
|
||||
final MultiMap<PsiClass, PsiMethod> deprecated = new LinkedMultiMap<PsiClass, PsiMethod>();
|
||||
final MultiMap<PsiClass, PsiMethod> suggestions = new LinkedMultiMap<PsiClass, PsiMethod>();
|
||||
class RegisterMethodsProcessor {
|
||||
private void registerMethod(PsiClass containingClass, Collection<PsiMethod> methods) {
|
||||
final Boolean alreadyMentioned = possibleClasses.get(containingClass);
|
||||
if (alreadyMentioned == Boolean.TRUE) return;
|
||||
if (alreadyMentioned == null) {
|
||||
if (!methods.isEmpty()) {
|
||||
list.add(methods.iterator().next());
|
||||
}
|
||||
possibleClasses.put(containingClass, false);
|
||||
}
|
||||
for (PsiMethod method : methods) {
|
||||
if (!PsiUtil.isAccessible(project, method, element, containingClass)) {
|
||||
continue;
|
||||
}
|
||||
PsiSubstitutor substitutorForMethod = resolveHelper
|
||||
.inferTypeArguments(method.getTypeParameters(), method.getParameterList().getParameters(),
|
||||
argumentList.getExpressions(),
|
||||
PsiSubstitutor.EMPTY, element.getParent(), DefaultParameterTypeInferencePolicy.INSTANCE);
|
||||
if (PsiUtil.isApplicable(method, substitutorForMethod, argumentList)) {
|
||||
final PsiType returnType = substitutorForMethod.substitute(method.getReturnType());
|
||||
if (expectedType == null || returnType == null || TypeConversionUtil.isAssignable(expectedType, returnType)) {
|
||||
applicableList.add(method);
|
||||
possibleClasses.put(containingClass, true);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
final RegisterMethodsProcessor registrar = new RegisterMethodsProcessor();
|
||||
cache.processMethodsWithName(name, scope, new Processor<PsiMethod>() {
|
||||
@Override
|
||||
public boolean process(PsiMethod method) {
|
||||
ProgressManager.checkCanceled();
|
||||
if (JavaCompletionUtil.isInExcludedPackage(method, false)
|
||||
|| !method.hasModifierProperty(PsiModifier.STATIC)) return true;
|
||||
PsiFile file = method.getContainingFile();
|
||||
final PsiClass containingClass = method.getContainingClass();
|
||||
if (file instanceof PsiJavaFile
|
||||
//do not show methods from default package
|
||||
&& !((PsiJavaFile)file).getPackageName().isEmpty()) {
|
||||
if (isEffectivelyDeprecated(method)) {
|
||||
deprecated.putValue(containingClass, method);
|
||||
return processCondition();
|
||||
}
|
||||
suggestions.putValue(containingClass, method);
|
||||
}
|
||||
return processCondition();
|
||||
}
|
||||
|
||||
private boolean isEffectivelyDeprecated(PsiMethod method) {
|
||||
if (method.isDeprecated()) {
|
||||
return true;
|
||||
}
|
||||
PsiClass aClass = method.getContainingClass();
|
||||
while (aClass != null) {
|
||||
if (aClass.isDeprecated()) {
|
||||
return true;
|
||||
}
|
||||
aClass = aClass.getContainingClass();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private boolean processCondition() {
|
||||
return suggestions.size() + deprecated.size() < 50;
|
||||
}
|
||||
});
|
||||
|
||||
for (Map.Entry<PsiClass, Collection<PsiMethod>> methodEntry : suggestions.entrySet()) {
|
||||
registrar.registerMethod(methodEntry.getKey(), methodEntry.getValue());
|
||||
}
|
||||
|
||||
for (Map.Entry<PsiClass, Collection<PsiMethod>> deprecatedMethod : deprecated.entrySet()) {
|
||||
registrar.registerMethod(deprecatedMethod.getKey(), deprecatedMethod.getValue());
|
||||
}
|
||||
|
||||
List<PsiMethod> result = applicableList.isEmpty() ? list : applicableList;
|
||||
for (int i = result.size() - 1; i >= 0; i--) {
|
||||
ProgressManager.checkCanceled();
|
||||
PsiMethod method = result.get(i);
|
||||
// check for manually excluded
|
||||
if (isExcluded(method)) {
|
||||
result.remove(i);
|
||||
}
|
||||
}
|
||||
Collections.sort(result, new PsiProximityComparator(argumentList));
|
||||
return result;
|
||||
PsiReferenceExpression reference = element == null ? null : element.getMethodExpression();
|
||||
String name = reference == null ? null : reference.getReferenceName();
|
||||
if (name == null) return Collections.emptyList();
|
||||
final MyStaticMembersProcessor<PsiMethod> processor = new MyStaticMethodProcessor(project, element);
|
||||
cache.processMethodsWithName(name, element.getResolveScope(), processor);
|
||||
return processor.getMembersToImport();
|
||||
}
|
||||
|
||||
public static boolean isExcluded(PsiMember method) {
|
||||
@@ -261,68 +72,51 @@ public class StaticImportMethodFix implements IntentionAction, HintAction {
|
||||
return name != null && JavaProjectCodeInsightSettings.getSettings(method.getProject()).isExcluded(name);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void invoke(@NotNull final Project project, final Editor editor, PsiFile file) {
|
||||
if (!FileModificationService.getInstance().prepareFileForWrite(file)) return;
|
||||
ApplicationManager.getApplication().runWriteAction(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
final List<PsiMethod> methodsToImport = getMethodsToImport();
|
||||
if (methodsToImport.isEmpty()) return;
|
||||
createQuestionAction(methodsToImport, project, editor).execute();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private StaticImportMethodQuestionAction createQuestionAction(List<PsiMethod> methodsToImport, @NotNull Project project, Editor editor) {
|
||||
return new StaticImportMethodQuestionAction(project, editor, methodsToImport, myMethodCall);
|
||||
protected StaticImportMethodQuestionAction<PsiMethod> createQuestionAction(List<PsiMethod> methodsToImport, @NotNull Project project, Editor editor) {
|
||||
return new StaticImportMethodQuestionAction<PsiMethod>(project, editor, methodsToImport, myMethodCall);
|
||||
}
|
||||
|
||||
private ImportClassFixBase.Result doFix(Editor editor) {
|
||||
if (candidates.isEmpty()) {
|
||||
return ImportClassFixBase.Result.POPUP_NOT_SHOWN;
|
||||
}
|
||||
|
||||
final StaticImportMethodQuestionAction action = createQuestionAction(candidates, myMethodCall.getProject(), editor);
|
||||
@Nullable
|
||||
@Override
|
||||
protected PsiElement getElement() {
|
||||
return myMethodCall.getElement();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
protected PsiElement getQualifierExpression() {
|
||||
final PsiMethodCallExpression element = myMethodCall.getElement();
|
||||
if (element == null) {
|
||||
return ImportClassFixBase.Result.POPUP_NOT_SHOWN;
|
||||
}
|
||||
|
||||
if (candidates.size() == 1 && ImportClassFixBase.canAddUnambiguousImport(element.getContainingFile())) {
|
||||
CommandProcessor.getInstance().runUndoTransparentAction(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
action.execute();
|
||||
}
|
||||
});
|
||||
return ImportClassFixBase.Result.CLASS_AUTO_IMPORTED;
|
||||
}
|
||||
|
||||
String hintText = ShowAutoImportPass.getMessage(candidates.size() > 1, getMethodPresentableText());
|
||||
if (!ApplicationManager.getApplication().isUnitTestMode() && !HintManager.getInstance().hasShownHintsThatWillHideByOtherHint(true)) {
|
||||
final TextRange textRange = element.getTextRange();
|
||||
HintManager.getInstance().showQuestionHint(editor, hintText,
|
||||
textRange.getStartOffset(),
|
||||
textRange.getEndOffset(), action);
|
||||
}
|
||||
return ImportClassFixBase.Result.POPUP_SHOWN;
|
||||
return element != null ? element.getMethodExpression().getQualifierExpression() : null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public boolean startInWriteAction() {
|
||||
return false;
|
||||
protected PsiElement resolveRef() {
|
||||
final PsiMethodCallExpression methodCallExpression = (PsiMethodCallExpression)getElement();
|
||||
return methodCallExpression != null ? methodCallExpression.resolveMethod() : null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean showHint(@NotNull Editor editor) {
|
||||
final PsiMethodCallExpression callExpression = myMethodCall.getElement();
|
||||
if (callExpression == null || callExpression.getMethodExpression().getQualifierExpression() != null) {
|
||||
private static class MyStaticMethodProcessor extends MyStaticMembersProcessor<PsiMethod> {
|
||||
|
||||
private MyStaticMethodProcessor(Project project, PsiMethodCallExpression place) {
|
||||
super(place);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected boolean isApplicable(PsiMethod method, PsiElement place) {
|
||||
final PsiResolveHelper resolveHelper = JavaPsiFacade.getInstance(place.getProject()).getResolveHelper();
|
||||
final PsiExpressionList argumentList = ((PsiMethodCallExpression)place).getArgumentList();
|
||||
PsiSubstitutor substitutorForMethod = resolveHelper
|
||||
.inferTypeArguments(method.getTypeParameters(), method.getParameterList().getParameters(),
|
||||
argumentList.getExpressions(),
|
||||
PsiSubstitutor.EMPTY, place.getParent(), DefaultParameterTypeInferencePolicy.INSTANCE);
|
||||
if (PsiUtil.isApplicable(method, substitutorForMethod, argumentList)) {
|
||||
final PsiType returnType = substitutorForMethod.substitute(method.getReturnType());
|
||||
final PsiType expectedType = getExpectedType();
|
||||
return expectedType == null || returnType == null || TypeConversionUtil.isAssignable(expectedType, returnType);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
ImportClassFixBase.Result result = doFix(editor);
|
||||
return result == ImportClassFixBase.Result.POPUP_SHOWN || result == ImportClassFixBase.Result.CLASS_AUTO_IMPORTED;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,7 +19,8 @@ import com.intellij.codeInsight.daemon.QuickFixBundle;
|
||||
import com.intellij.codeInsight.daemon.impl.actions.AddImportAction;
|
||||
import com.intellij.codeInsight.hint.QuestionAction;
|
||||
import com.intellij.codeInsight.intention.impl.AddSingleMemberStaticImportAction;
|
||||
import com.intellij.ide.util.MethodCellRenderer;
|
||||
import com.intellij.ide.util.PsiClassListCellRenderer;
|
||||
import com.intellij.ide.util.PsiElementListCellRenderer;
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.command.CommandProcessor;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
@@ -29,7 +30,7 @@ import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.ui.popup.PopupStep;
|
||||
import com.intellij.openapi.ui.popup.util.BaseListPopupStep;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.util.PsiFormatUtilBase;
|
||||
import com.intellij.psi.presentation.java.ClassPresentationUtil;
|
||||
import com.intellij.psi.util.PsiUtil;
|
||||
import com.intellij.ui.popup.list.ListPopupImpl;
|
||||
import com.intellij.ui.popup.list.PopupListElementRenderer;
|
||||
@@ -42,33 +43,38 @@ import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.util.List;
|
||||
|
||||
public class StaticImportMethodQuestionAction implements QuestionAction {
|
||||
public class StaticImportMethodQuestionAction<T extends PsiMember> implements QuestionAction {
|
||||
private static final Logger LOG = Logger.getInstance("#" + StaticImportMethodQuestionAction.class.getName());
|
||||
private final Project myProject;
|
||||
private final Editor myEditor;
|
||||
private List<PsiMethod> myCandidates;
|
||||
private final SmartPsiElementPointer<PsiMethodCallExpression> myMethodCall;
|
||||
private List<T> myCandidates;
|
||||
private final SmartPsiElementPointer<? extends PsiElement> myRef;
|
||||
|
||||
public StaticImportMethodQuestionAction(Project project,
|
||||
Editor editor,
|
||||
List<PsiMethod> candidates,
|
||||
SmartPsiElementPointer<PsiMethodCallExpression> methodCall) {
|
||||
List<T> candidates,
|
||||
SmartPsiElementPointer<? extends PsiElement> ref) {
|
||||
myProject = project;
|
||||
myEditor = editor;
|
||||
myCandidates = candidates;
|
||||
myMethodCall = methodCall;
|
||||
myRef = ref;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected String getPopupTitle() {
|
||||
return QuickFixBundle.message("method.to.import.chooser.title");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean execute() {
|
||||
PsiDocumentManager.getInstance(myProject).commitAllDocuments();
|
||||
|
||||
final PsiMethodCallExpression element = myMethodCall.getElement();
|
||||
final PsiElement element = myRef.getElement();
|
||||
if (element == null || !element.isValid()){
|
||||
return false;
|
||||
}
|
||||
|
||||
for (PsiMethod targetMethod : myCandidates) {
|
||||
for (T targetMethod : myCandidates) {
|
||||
if (!targetMethod.isValid()) {
|
||||
return false;
|
||||
}
|
||||
@@ -83,7 +89,7 @@ public class StaticImportMethodQuestionAction implements QuestionAction {
|
||||
return true;
|
||||
}
|
||||
|
||||
private void doImport(final PsiMethod toImport) {
|
||||
private void doImport(final T toImport) {
|
||||
final Project project = toImport.getProject();
|
||||
CommandProcessor.getInstance().executeCommand(project, new Runnable(){
|
||||
@Override
|
||||
@@ -92,7 +98,7 @@ public class StaticImportMethodQuestionAction implements QuestionAction {
|
||||
@Override
|
||||
public void run() {
|
||||
try {
|
||||
PsiMethodCallExpression element = myMethodCall.getElement();
|
||||
PsiElement element = myRef.getElement();
|
||||
if (element != null) {
|
||||
AddSingleMemberStaticImportAction.bindAllClassRefs(element.getContainingFile(), toImport, toImport.getName(), toImport.getContainingClass());
|
||||
}
|
||||
@@ -113,11 +119,11 @@ public class StaticImportMethodQuestionAction implements QuestionAction {
|
||||
doImport(myCandidates.get(0));
|
||||
return;
|
||||
}
|
||||
final BaseListPopupStep<PsiMethod> step =
|
||||
new BaseListPopupStep<PsiMethod>(QuickFixBundle.message("method.to.import.chooser.title"), myCandidates) {
|
||||
final BaseListPopupStep<T> step =
|
||||
new BaseListPopupStep<T>(getPopupTitle(), myCandidates) {
|
||||
|
||||
@Override
|
||||
public PopupStep onChosen(PsiMethod selectedValue, boolean finalChoice) {
|
||||
public PopupStep onChosen(T selectedValue, boolean finalChoice) {
|
||||
if (selectedValue == null) {
|
||||
return FINAL_CHOICE;
|
||||
}
|
||||
@@ -151,18 +157,18 @@ public class StaticImportMethodQuestionAction implements QuestionAction {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasSubstep(PsiMethod selectedValue) {
|
||||
public boolean hasSubstep(T selectedValue) {
|
||||
return true;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public String getTextFor(PsiMethod value) {
|
||||
public String getTextFor(T value) {
|
||||
return ObjectUtils.assertNotNull(value.getName());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Icon getIconFor(PsiMethod aValue) {
|
||||
public Icon getIconFor(T aValue) {
|
||||
return aValue.getIcon(0);
|
||||
}
|
||||
};
|
||||
@@ -171,14 +177,27 @@ public class StaticImportMethodQuestionAction implements QuestionAction {
|
||||
final PopupListElementRenderer rightArrow = new PopupListElementRenderer(this);
|
||||
@Override
|
||||
protected ListCellRenderer getListElementRenderer() {
|
||||
return new MethodCellRenderer(true, PsiFormatUtilBase.SHOW_NAME){
|
||||
return new PsiElementListCellRenderer<T>() {
|
||||
public String getElementText(T element) {
|
||||
final PsiClass aClass = element.getContainingClass();
|
||||
LOG.assertTrue(aClass != null);
|
||||
return ClassPresentationUtil.getNameForClass(aClass, false) + "." + element.getName();
|
||||
}
|
||||
|
||||
public String getContainerText(final T element, final String name) {
|
||||
return PsiClassListCellRenderer.getContainerTextStatic(element);
|
||||
}
|
||||
|
||||
public int getIconFlags() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
protected TextAttributes getNavigationItemAttributes(Object value) {
|
||||
TextAttributes attrs = super.getNavigationItemAttributes(value);
|
||||
if (value instanceof PsiMethod && !((PsiMethod)value).isDeprecated()) {
|
||||
PsiClass psiClass = ((PsiMethod)value).getContainingClass();
|
||||
if (value instanceof PsiDocCommentOwner && !((PsiDocCommentOwner)value).isDeprecated()) {
|
||||
PsiClass psiClass = ((T)value).getContainingClass();
|
||||
if (psiClass != null && psiClass.isDeprecated()) {
|
||||
return TextAttributes.merge(attrs, super.getNavigationItemAttributes(psiClass));
|
||||
}
|
||||
|
||||
@@ -0,0 +1,17 @@
|
||||
// "Static import constant..." "true"
|
||||
package foo;
|
||||
|
||||
import static foo.B.aaaaaaa;
|
||||
|
||||
public class X {
|
||||
{
|
||||
aaaaaaa;
|
||||
}
|
||||
}
|
||||
|
||||
class B {
|
||||
public static Integer aaaaaaa = 1;
|
||||
}
|
||||
class B1 {
|
||||
public static String aaaaaaa = "";
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
// "Static import constant 'foo.B.aaaaaaa'" "true"
|
||||
package foo;
|
||||
|
||||
import static foo.B.aaaaaaa;
|
||||
|
||||
public class X {
|
||||
{
|
||||
int i = aaaaaaa;
|
||||
}
|
||||
}
|
||||
|
||||
class B {
|
||||
public static Integer aaaaaaa = 1;
|
||||
}
|
||||
class B1 {
|
||||
public static String aaaaaaa = "";
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
// "Static import constant..." "true"
|
||||
package foo;
|
||||
|
||||
public class X {
|
||||
{
|
||||
<caret>aaaaaaa;
|
||||
}
|
||||
}
|
||||
|
||||
class B {
|
||||
public static Integer aaaaaaa = 1;
|
||||
}
|
||||
class B1 {
|
||||
public static String aaaaaaa = "";
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
// "Static import constant 'foo.B.aaaaaaa'" "true"
|
||||
package foo;
|
||||
|
||||
public class X {
|
||||
{
|
||||
int i = <caret>aaaaaaa;
|
||||
}
|
||||
}
|
||||
|
||||
class B {
|
||||
public static Integer aaaaaaa = 1;
|
||||
}
|
||||
class B1 {
|
||||
public static String aaaaaaa = "";
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
/*
|
||||
* Copyright 2000-2016 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 StaticImportConstantTest extends LightQuickFixParameterizedTestCase {
|
||||
@Override
|
||||
protected String getBasePath() {
|
||||
return "/codeInsight/daemonCodeAnalyzer/quickFix/staticImportConstant";
|
||||
}
|
||||
}
|
||||
@@ -1,6 +1,7 @@
|
||||
add.import=Add Import
|
||||
class.to.import.chooser.title=Class to Import
|
||||
method.to.import.chooser.title=Method to Import
|
||||
field.to.import.chooser.title=Field to Import
|
||||
access.static.via.class.reference.family=Access static via class reference
|
||||
access.static.via.class.reference.text=Access static ''{1}.{0}'' via class ''{2}'' reference
|
||||
add.default.constructor.family=Add Default Constructor
|
||||
|
||||
Reference in New Issue
Block a user