mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
Merge remote-tracking branch 'origin/master'
This commit is contained in:
+5
-2
@@ -80,9 +80,12 @@ sun.java2d.noddraw=true
|
||||
sun.java2d.d3d=false
|
||||
|
||||
#---------------------------------------------------------------------
|
||||
# Workaround for slow scrolling in JDK6
|
||||
# Set swing.bufferPerWindow=false to workaround a slow scrolling in JDK6 (see IDEA-35883),
|
||||
# But this may lead to performance degradation, because it disables a double buffering,
|
||||
# which is needed to eliminate tearing on blit-accelerated scrolling and to restore
|
||||
# a frame buffer content without the usual repainting, even when the EDT is blocked.
|
||||
#---------------------------------------------------------------------
|
||||
swing.bufferPerWindow=false
|
||||
swing.bufferPerWindow=true
|
||||
|
||||
#---------------------------------------------------------------------
|
||||
# Removing this property may lead to editor performance degradation under X Window.
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -383,14 +383,15 @@ public class VirtualMachineProxyImpl implements JdiTimer, VirtualMachineProxy {
|
||||
catch (UnsupportedOperationException e) {
|
||||
LOG.info(e);
|
||||
}
|
||||
|
||||
if (Patches.JDK_BUG_EVENT_CONTROLLER_LEAK) {
|
||||
// Memory leak workaround, see IDEA-163334
|
||||
TargetVM target = ReflectionUtil.getField(myVirtualMachine.getClass(), myVirtualMachine, TargetVM.class, "target");
|
||||
if (target != null) {
|
||||
Thread controller = ReflectionUtil.getField(target.getClass(), target, Thread.class, "eventController");
|
||||
if (controller != null) {
|
||||
controller.stop();
|
||||
finally {
|
||||
if (Patches.JDK_BUG_EVENT_CONTROLLER_LEAK) {
|
||||
// Memory leak workaround, see IDEA-163334
|
||||
TargetVM target = ReflectionUtil.getField(myVirtualMachine.getClass(), myVirtualMachine, TargetVM.class, "target");
|
||||
if (target != null) {
|
||||
Thread controller = ReflectionUtil.getField(target.getClass(), target, Thread.class, "eventController");
|
||||
if (controller != null) {
|
||||
controller.stop();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -173,7 +173,7 @@ public class CaptureConfigurable implements SearchableConfigurable {
|
||||
}
|
||||
});
|
||||
try {
|
||||
JDOMUtil.writeDocument(new Document(rootElement), wrapper.getFile(), "\n");
|
||||
JDOMUtil.write(rootElement, wrapper.getFile());
|
||||
}
|
||||
catch (Exception ex) {
|
||||
final String msg = ex.getLocalizedMessage();
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -23,7 +23,6 @@ import com.intellij.openapi.extensions.PluginId;
|
||||
import com.intellij.openapi.module.ModuleType;
|
||||
import com.intellij.openapi.module.ModuleTypeManager;
|
||||
import com.intellij.openapi.util.ClearableLazyValue;
|
||||
import com.intellij.openapi.util.JDOMUtil;
|
||||
import com.intellij.platform.ProjectTemplate;
|
||||
import com.intellij.platform.ProjectTemplatesFactory;
|
||||
import com.intellij.util.ArrayUtil;
|
||||
@@ -95,7 +94,7 @@ public class RemoteTemplatesFactory extends ProjectTemplatesFactory {
|
||||
@NotNull
|
||||
@TestOnly
|
||||
public static MultiMap<String, ArchivedProjectTemplate> createFromText(@NotNull String value) throws IOException, JDOMException {
|
||||
return create(JDOMUtil.loadDocument(value).getRootElement());
|
||||
return create(JdomKt.loadElement(value));
|
||||
}
|
||||
|
||||
@NotNull
|
||||
|
||||
+23
-5
@@ -49,6 +49,9 @@ public class DataFlowRunner {
|
||||
|
||||
private Instruction[] myInstructions;
|
||||
private final MultiMap<PsiElement, DfaMemoryState> myNestedClosures = new MultiMap<>();
|
||||
// Closures which were registered for previous instruction and can be queried by visitor
|
||||
// to adjust them somehow
|
||||
private final List<DfaMemoryState> myStackTopClosures = new ArrayList<>();
|
||||
@NotNull
|
||||
private final DfaValueFactory myValueFactory;
|
||||
private final boolean myShouldCheckLimitTime;
|
||||
@@ -90,6 +93,10 @@ public class DataFlowRunner {
|
||||
return Collections.singletonList(createMemoryState());
|
||||
}
|
||||
|
||||
List<DfaMemoryState> getStackTopClosures() {
|
||||
return new ArrayList<>(myStackTopClosures);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public final RunnerResult analyzeMethod(@NotNull PsiElement psiBlock, @NotNull InstructionVisitor visitor) {
|
||||
Collection<DfaMemoryState> initialStates = createInitialStates(psiBlock, visitor);
|
||||
@@ -109,6 +116,7 @@ public class DataFlowRunner {
|
||||
int endOffset = flow.getInstructionCount();
|
||||
myInstructions = flow.getInstructions();
|
||||
myNestedClosures.clear();
|
||||
myStackTopClosures.clear();
|
||||
|
||||
Set<Instruction> joinInstructions = ContainerUtil.newHashSet();
|
||||
for (int index = 0; index < myInstructions.length; index++) {
|
||||
@@ -270,6 +278,9 @@ public class DataFlowRunner {
|
||||
@NotNull
|
||||
protected DfaInstructionState[] acceptInstruction(@NotNull InstructionVisitor visitor, @NotNull DfaInstructionState instructionState) {
|
||||
Instruction instruction = instructionState.getInstruction();
|
||||
DfaInstructionState[] states = instruction.accept(this, instructionState.getMemoryState(), visitor);
|
||||
|
||||
myStackTopClosures.clear();
|
||||
PsiElement closure = DfaUtil.getClosureInside(instruction);
|
||||
if (closure instanceof PsiClass) {
|
||||
registerNestedClosures(instructionState, (PsiClass)closure);
|
||||
@@ -277,7 +288,7 @@ public class DataFlowRunner {
|
||||
registerNestedClosures(instructionState, (PsiLambdaExpression)closure);
|
||||
}
|
||||
|
||||
return instruction.accept(this, instructionState.getMemoryState(), visitor);
|
||||
return states;
|
||||
}
|
||||
|
||||
private void registerNestedClosures(@NotNull DfaInstructionState instructionState, @NotNull PsiClass nestedClass) {
|
||||
@@ -285,14 +296,14 @@ public class DataFlowRunner {
|
||||
for (PsiMethod method : nestedClass.getMethods()) {
|
||||
PsiCodeBlock body = method.getBody();
|
||||
if (body != null) {
|
||||
myNestedClosures.putValue(body, state.createClosureState());
|
||||
myNestedClosures.putValue(body, createClosureState(state));
|
||||
}
|
||||
}
|
||||
for (PsiClassInitializer initializer : nestedClass.getInitializers()) {
|
||||
myNestedClosures.putValue(initializer.getBody(), state.createClosureState());
|
||||
myNestedClosures.putValue(initializer.getBody(), createClosureState(state));
|
||||
}
|
||||
for (PsiField field : nestedClass.getFields()) {
|
||||
myNestedClosures.putValue(field, state.createClosureState());
|
||||
myNestedClosures.putValue(field, createClosureState(state));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -300,10 +311,17 @@ public class DataFlowRunner {
|
||||
DfaMemoryState state = instructionState.getMemoryState();
|
||||
PsiElement body = expr.getBody();
|
||||
if (body != null) {
|
||||
myNestedClosures.putValue(body, state.createClosureState());
|
||||
myNestedClosures.putValue(body, createClosureState(state));
|
||||
}
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private DfaMemoryState createClosureState(DfaMemoryState state) {
|
||||
DfaMemoryState closureState = state.createClosureState();
|
||||
myStackTopClosures.add(closureState);
|
||||
return closureState;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected DfaMemoryState createMemoryState() {
|
||||
return new DfaMemoryStateImpl(myValueFactory);
|
||||
|
||||
-10
@@ -53,8 +53,6 @@ public class DfaMemoryStateImpl implements DfaMemoryState {
|
||||
// dfa value id -> indices in myEqClasses list of the classes which contain the id (or wrapped)
|
||||
private final TIntObjectHashMap<int[]> myIdToEqClassesIndices;
|
||||
private final Stack<DfaValue> myStack;
|
||||
// Closures which correspond to the stack top (do not track other closures for now)
|
||||
private final List<DfaMemoryState> myStackTopClosures = new ArrayList<>();
|
||||
private final TLongHashSet myDistinctClasses;
|
||||
private final LinkedHashMap<DfaVariableValue,DfaVariableState> myVariableStates;
|
||||
private final Map<DfaVariableValue,DfaVariableState> myDefaultVariableStates;
|
||||
@@ -118,14 +116,9 @@ public class DfaMemoryStateImpl implements DfaMemoryState {
|
||||
copy.flushDependencies(value);
|
||||
}
|
||||
copy.emptyStack();
|
||||
myStackTopClosures.add(copy);
|
||||
return copy;
|
||||
}
|
||||
|
||||
List<DfaMemoryState> getStackTopClosures() {
|
||||
return new ArrayList<>(myStackTopClosures);
|
||||
}
|
||||
|
||||
public boolean equals(Object obj) {
|
||||
if (obj == this) return true;
|
||||
if (!(obj instanceof DfaMemoryStateImpl)) return false;
|
||||
@@ -241,7 +234,6 @@ public class DfaMemoryStateImpl implements DfaMemoryState {
|
||||
@Override
|
||||
public DfaValue pop() {
|
||||
myCachedHash = null;
|
||||
myStackTopClosures.clear();
|
||||
return myStack.pop();
|
||||
}
|
||||
|
||||
@@ -253,14 +245,12 @@ public class DfaMemoryStateImpl implements DfaMemoryState {
|
||||
@Override
|
||||
public void push(@NotNull DfaValue value) {
|
||||
myCachedHash = null;
|
||||
myStackTopClosures.clear();
|
||||
myStack.push(value);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void emptyStack() {
|
||||
myCachedHash = null;
|
||||
myStackTopClosures.clear();
|
||||
while (!myStack.isEmpty() && !(myStack.peek() instanceof DfaControlTransferValue)) {
|
||||
myStack.pop();
|
||||
}
|
||||
|
||||
+1
-1
@@ -229,7 +229,7 @@ public class StandardInstructionVisitor extends InstructionVisitor {
|
||||
if (methodName == null || !OPTIONAL_METHOD_NAMES.contains(methodName)) return Collections.emptyList();
|
||||
PsiMethod method = call.resolveMethod();
|
||||
if (method == null || !TypeUtils.isOptional(method.getContainingClass())) return Collections.emptyList();
|
||||
List<DfaMemoryState> closures = ((DfaMemoryStateImpl)memState).getStackTopClosures();
|
||||
List<DfaMemoryState> closures = runner.getStackTopClosures();
|
||||
DfaValue[] argValues = popCallArguments(instruction, runner, memState);
|
||||
final DfaValue qualifier = popQualifier(instruction, runner, memState);
|
||||
switch (methodName) {
|
||||
|
||||
+48
-11
@@ -890,6 +890,10 @@ public class SimplifyStreamApiCallChainsInspection extends BaseJavaBatchLocalIns
|
||||
.parameterCount(1);
|
||||
private static final CallMatcher INT_STREAM_RANGE =
|
||||
CallMatcher.staticCall(CommonClassNames.JAVA_UTIL_STREAM_INT_STREAM, "range").parameterTypes("int", "int");
|
||||
private static final CallMatcher MIN_INT =
|
||||
CallMatcher.anyOf(
|
||||
CallMatcher.staticCall(CommonClassNames.JAVA_LANG_MATH, "min").parameterTypes("int", "int"),
|
||||
CallMatcher.staticCall(CommonClassNames.JAVA_LANG_INTEGER, "min").parameterTypes("int", "int"));
|
||||
|
||||
private final String myName;
|
||||
|
||||
@@ -913,8 +917,10 @@ public class SimplifyStreamApiCallChainsInspection extends BaseJavaBatchLocalIns
|
||||
public PsiElement simplify(PsiMethodCallExpression mapToObjCall) {
|
||||
Project project = mapToObjCall.getProject();
|
||||
PsiExpression mapper = ArrayUtil.getFirstElement(mapToObjCall.getArgumentList().getExpressions());
|
||||
IndexedContainer container = extractContainer(getQualifierMethodCall(mapToObjCall), mapper);
|
||||
if (container == null) return null;
|
||||
LimitedContainer limitedContainer = extractContainer(getQualifierMethodCall(mapToObjCall), mapper);
|
||||
if (limitedContainer == null) return null;
|
||||
IndexedContainer container = limitedContainer.myContainer;
|
||||
PsiExpression limit = limitedContainer.myLimit;
|
||||
PsiExpression containerQualifier = container.getQualifier();
|
||||
PsiType type = containerQualifier.getType();
|
||||
PsiType elementType = container.getElementType();
|
||||
@@ -929,6 +935,9 @@ public class SimplifyStreamApiCallChainsInspection extends BaseJavaBatchLocalIns
|
||||
}
|
||||
PsiElementFactory factory = JavaPsiFacade.getElementFactory(project);
|
||||
CommentTracker ct = new CommentTracker();
|
||||
if (limit != null) {
|
||||
replacement += ".limit(" + ct.text(limit) + ")";
|
||||
}
|
||||
if (mapper instanceof PsiMethodReferenceExpression) {
|
||||
mapper = LambdaRefactoringUtil.convertMethodReferenceToLambda((PsiMethodReferenceExpression)mapper, false, true);
|
||||
}
|
||||
@@ -975,22 +984,39 @@ public class SimplifyStreamApiCallChainsInspection extends BaseJavaBatchLocalIns
|
||||
static CallHandler<CallChainSimplification> handler() {
|
||||
return CallHandler.of(INT_STREAM_MAP, call -> {
|
||||
PsiExpression mapper = call.getArgumentList().getExpressions()[0];
|
||||
IndexedContainer container = extractContainer(getQualifierMethodCall(call), mapper);
|
||||
if (container == null) return null;
|
||||
return new ReplaceWithElementIterationFix(container, call.getMethodExpression().getReferenceName());
|
||||
LimitedContainer limitedContainer = extractContainer(getQualifierMethodCall(call), mapper);
|
||||
if (limitedContainer == null) return null;
|
||||
return new ReplaceWithElementIterationFix(limitedContainer.myContainer, call.getMethodExpression().getReferenceName());
|
||||
});
|
||||
}
|
||||
|
||||
@Contract("null, _ -> null")
|
||||
private static IndexedContainer extractContainer(PsiMethodCallExpression qualifierCall, PsiExpression mapper) {
|
||||
private static LimitedContainer extractContainer(PsiMethodCallExpression qualifierCall, PsiExpression mapper) {
|
||||
if (!INT_STREAM_RANGE.test(qualifierCall)) return null;
|
||||
PsiExpression[] rangeArgs = qualifierCall.getArgumentList().getExpressions();
|
||||
if (!ExpressionUtils.isZero(rangeArgs[0])) return null;
|
||||
PsiExpression bound = rangeArgs[1];
|
||||
PsiExpression bound = ExpressionUtils.resolveExpression(rangeArgs[1]);
|
||||
IndexedContainer container = IndexedContainer.fromLengthExpression(bound);
|
||||
if (container == null || !StreamApiUtil.isSupportedStreamElement(container.getElementType())) return null;
|
||||
PsiExpression limit = null;
|
||||
if (container == null) {
|
||||
if(bound instanceof PsiMethodCallExpression && MIN_INT.test((PsiMethodCallExpression)bound)) {
|
||||
PsiExpression[] args = ((PsiMethodCallExpression)bound).getArgumentList().getExpressions();
|
||||
container = IndexedContainer.fromLengthExpression(args[0]);
|
||||
if(container != null) {
|
||||
limit = args[1];
|
||||
} else {
|
||||
container = IndexedContainer.fromLengthExpression(args[1]);
|
||||
if(container != null) {
|
||||
limit = args[0];
|
||||
}
|
||||
}
|
||||
}
|
||||
if(container == null) return null;
|
||||
}
|
||||
if (!StreamApiUtil.isSupportedStreamElement(container.getElementType())) return null;
|
||||
LimitedContainer limitedContainer = new LimitedContainer(container, limit);
|
||||
if (mapper instanceof PsiMethodReferenceExpression && container.isGetMethodReference((PsiMethodReferenceExpression)mapper)) {
|
||||
return container;
|
||||
return limitedContainer;
|
||||
}
|
||||
if (mapper instanceof PsiLambdaExpression) {
|
||||
PsiLambdaExpression lambda = (PsiLambdaExpression)mapper;
|
||||
@@ -1001,12 +1027,23 @@ public class SimplifyStreamApiCallChainsInspection extends BaseJavaBatchLocalIns
|
||||
if (body == null) return null;
|
||||
Collection<PsiReference> refs = ReferencesSearch.search(indexParameter, new LocalSearchScope(body)).findAll();
|
||||
if (!refs.isEmpty() &&
|
||||
refs.stream().allMatch(ref -> container.extractGetExpressionFromIndex(tryCast(ref, PsiExpression.class)) != null)) {
|
||||
return container;
|
||||
refs.stream()
|
||||
.allMatch(ref -> limitedContainer.myContainer.extractGetExpressionFromIndex(tryCast(ref, PsiExpression.class)) != null)) {
|
||||
return limitedContainer;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
static class LimitedContainer {
|
||||
@NotNull final IndexedContainer myContainer;
|
||||
@Nullable final PsiExpression myLimit;
|
||||
|
||||
LimitedContainer(@NotNull IndexedContainer container, @Nullable PsiExpression limit) {
|
||||
myContainer = container;
|
||||
myLimit = limit;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static class RemoveBooleanIdentityFix implements CallChainSimplification {
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -46,9 +46,7 @@ import com.intellij.psi.util.PsiTreeUtil
|
||||
import com.sun.tools.doclint.DocLint
|
||||
import java.io.File
|
||||
|
||||
class JavadocHtmlLintAnnotator() :
|
||||
ExternalAnnotator<JavadocHtmlLintAnnotator.Info, JavadocHtmlLintAnnotator.Result>() {
|
||||
|
||||
class JavadocHtmlLintAnnotator : ExternalAnnotator<JavadocHtmlLintAnnotator.Info, JavadocHtmlLintAnnotator.Result>() {
|
||||
data class Info(val file: PsiFile)
|
||||
data class Anno(val row: Int, val col: Int, val error: Boolean, val message: String)
|
||||
data class Result(val annotations: List<Anno>)
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -25,5 +25,5 @@ class JavadocHtmlLintInspection : LocalInspectionTool(), ExternalAnnotatorBatchI
|
||||
val SHORT_NAME = "JavadocHtmlLint"
|
||||
}
|
||||
|
||||
override fun getBatchSuppressActions(element: PsiElement?) = SuppressQuickFix.EMPTY_ARRAY
|
||||
override fun getBatchSuppressActions(element: PsiElement?): Array<out SuppressQuickFix> = SuppressQuickFix.EMPTY_ARRAY
|
||||
}
|
||||
+42
-22
@@ -45,6 +45,8 @@ import com.intellij.psi.search.LocalSearchScope;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
import com.intellij.psi.util.*;
|
||||
import com.intellij.slicer.*;
|
||||
import com.intellij.util.ArrayUtil;
|
||||
import com.intellij.util.IncorrectOperationException;
|
||||
import com.intellij.util.Processor;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import com.intellij.util.indexing.FileBasedIndex;
|
||||
@@ -325,42 +327,60 @@ public class MagicConstantInspection extends BaseJavaLocalInspectionTool {
|
||||
private static AllowedValues getAllowedValuesFromMagic(@NotNull PsiType type,
|
||||
@NotNull PsiAnnotation magic,
|
||||
@NotNull PsiManager manager) {
|
||||
PsiAnnotationMemberValue[] allowedValues;
|
||||
final boolean canBeOred;
|
||||
PsiAnnotationMemberValue[] allowedValues = PsiAnnotationMemberValue.EMPTY_ARRAY;
|
||||
boolean values = false, flags = false;
|
||||
if (TypeConversionUtil.getTypeRank(type) <= TypeConversionUtil.LONG_RANK) {
|
||||
PsiAnnotationMemberValue intValues = magic.findAttributeValue("intValues");
|
||||
allowedValues = intValues instanceof PsiArrayInitializerMemberValue ? ((PsiArrayInitializerMemberValue)intValues).getInitializers() : PsiAnnotationMemberValue.EMPTY_ARRAY;
|
||||
if (allowedValues.length == 0) {
|
||||
PsiAnnotationMemberValue orValue = magic.findAttributeValue("flags");
|
||||
allowedValues = orValue instanceof PsiArrayInitializerMemberValue ? ((PsiArrayInitializerMemberValue)orValue).getInitializers() : PsiAnnotationMemberValue.EMPTY_ARRAY;
|
||||
canBeOred = true;
|
||||
if (intValues instanceof PsiArrayInitializerMemberValue) {
|
||||
final PsiAnnotationMemberValue[] initializers = ((PsiArrayInitializerMemberValue)intValues).getInitializers();
|
||||
if (initializers.length != 0) {
|
||||
allowedValues = initializers;
|
||||
values = true;
|
||||
}
|
||||
}
|
||||
else {
|
||||
canBeOred = false;
|
||||
if (!values) {
|
||||
PsiAnnotationMemberValue orValue = magic.findAttributeValue("flags");
|
||||
if (orValue instanceof PsiArrayInitializerMemberValue) {
|
||||
final PsiAnnotationMemberValue[] initializers = ((PsiArrayInitializerMemberValue)orValue).getInitializers();
|
||||
if (initializers.length != 0) {
|
||||
allowedValues = initializers;
|
||||
flags = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (type.equals(PsiType.getJavaLangString(manager, GlobalSearchScope.allScope(manager.getProject())))) {
|
||||
PsiAnnotationMemberValue strValuesAttr = magic.findAttributeValue("stringValues");
|
||||
allowedValues = strValuesAttr instanceof PsiArrayInitializerMemberValue ? ((PsiArrayInitializerMemberValue)strValuesAttr).getInitializers() : PsiAnnotationMemberValue.EMPTY_ARRAY;
|
||||
canBeOred = false;
|
||||
if (strValuesAttr instanceof PsiArrayInitializerMemberValue) {
|
||||
final PsiAnnotationMemberValue[] initializers = ((PsiArrayInitializerMemberValue)strValuesAttr).getInitializers();
|
||||
if (initializers.length != 0) {
|
||||
allowedValues = initializers;
|
||||
values = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
return null; //other types not supported
|
||||
}
|
||||
|
||||
if (allowedValues.length != 0) {
|
||||
return new AllowedValues(allowedValues, canBeOred);
|
||||
PsiAnnotationMemberValue[] valuesFromClass = readFromClass("valuesFromClass", magic, type, manager);
|
||||
if (valuesFromClass != null) {
|
||||
allowedValues = ArrayUtil.mergeArrays(allowedValues, valuesFromClass, PsiAnnotationMemberValue.ARRAY_FACTORY);
|
||||
values = true;
|
||||
}
|
||||
|
||||
// last resort: try valuesFromClass
|
||||
PsiAnnotationMemberValue[] values = readFromClass("valuesFromClass", magic, type, manager);
|
||||
boolean ored = false;
|
||||
if (values == null) {
|
||||
values = readFromClass("flagsFromClass", magic, type, manager);
|
||||
ored = true;
|
||||
PsiAnnotationMemberValue[] flagsFromClass = readFromClass("flagsFromClass", magic, type, manager);
|
||||
if (flagsFromClass != null) {
|
||||
allowedValues = ArrayUtil.mergeArrays(allowedValues, flagsFromClass, PsiAnnotationMemberValue.ARRAY_FACTORY);
|
||||
flags = true;
|
||||
}
|
||||
if (values == null) return null;
|
||||
return new AllowedValues(values, ored);
|
||||
if (allowedValues.length == 0) {
|
||||
return null;
|
||||
}
|
||||
if (values && flags) {
|
||||
throw new IncorrectOperationException(
|
||||
"Misconfiguration of @MagicConstant annotation: 'flags' and 'values' shouldn't be used at the same time");
|
||||
}
|
||||
return new AllowedValues(allowedValues, flags);
|
||||
}
|
||||
|
||||
private static PsiAnnotationMemberValue[] readFromClass(@NonNls @NotNull String attributeName,
|
||||
|
||||
+7
-5
@@ -106,7 +106,8 @@ class CollectMigration extends BaseStreamApiMigration {
|
||||
return initializerClass != null &&
|
||||
varClass != null &&
|
||||
CommonClassNames.JAVA_UTIL_HASH_MAP.equals(initializerClass.getQualifiedName()) &&
|
||||
CommonClassNames.JAVA_UTIL_MAP.equals(varClass.getQualifiedName());
|
||||
CommonClassNames.JAVA_UTIL_MAP.equals(varClass.getQualifiedName()) &&
|
||||
!ConstructionUtils.isCustomizedEmptyCollectionInitializer(initializer);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@@ -315,13 +316,14 @@ class CollectMigration extends BaseStreamApiMigration {
|
||||
PsiClassType rawVarType = type instanceof PsiClassType ? ((PsiClassType)type).rawType() : null;
|
||||
if (rawType != null && rawVarType != null &&
|
||||
rawType.equalsToText(CommonClassNames.JAVA_UTIL_ARRAY_LIST) &&
|
||||
(rawVarType.equalsToText(CommonClassNames.JAVA_UTIL_LIST) || rawVarType.equalsToText(CommonClassNames.JAVA_UTIL_COLLECTION))) {
|
||||
(rawVarType.equalsToText(CommonClassNames.JAVA_UTIL_LIST) || rawVarType.equalsToText(CommonClassNames.JAVA_UTIL_COLLECTION)) &&
|
||||
!ConstructionUtils.isCustomizedEmptyCollectionInitializer(initializer)) {
|
||||
collector = "toList()";
|
||||
}
|
||||
else if (rawType != null && rawVarType != null &&
|
||||
rawType.equalsToText(CommonClassNames.JAVA_UTIL_HASH_SET) &&
|
||||
(rawVarType.equalsToText(CommonClassNames.JAVA_UTIL_SET) ||
|
||||
rawVarType.equalsToText(CommonClassNames.JAVA_UTIL_COLLECTION))) {
|
||||
(rawVarType.equalsToText(CommonClassNames.JAVA_UTIL_SET) || rawVarType.equalsToText(CommonClassNames.JAVA_UTIL_COLLECTION)) &&
|
||||
!ConstructionUtils.isCustomizedEmptyCollectionInitializer(initializer)) {
|
||||
collector = "toSet()";
|
||||
}
|
||||
else {
|
||||
@@ -331,7 +333,7 @@ class CollectMigration extends BaseStreamApiMigration {
|
||||
PsiExpressionList argumentList = ((PsiNewExpression)copy).getArgumentList();
|
||||
if (argumentList != null) {
|
||||
PsiExpression arg = ArrayUtil.getFirstElement(argumentList.getExpressions());
|
||||
if (arg != null) {
|
||||
if (arg != null && !(arg.getType() instanceof PsiPrimitiveType)) {
|
||||
arg.delete();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,13 +1,27 @@
|
||||
/*
|
||||
* Copyright 2000-2017 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.jarFinder;
|
||||
|
||||
import com.intellij.openapi.progress.ProgressIndicator;
|
||||
import com.intellij.openapi.util.JDOMUtil;
|
||||
import com.intellij.openapi.util.io.StreamUtil;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.openapi.vfs.VfsUtilCore;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.util.JdomKt;
|
||||
import com.intellij.util.io.HttpRequests;
|
||||
import org.jdom.Document;
|
||||
import org.jdom.Element;
|
||||
import org.jdom.JDOMException;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
@@ -52,14 +66,14 @@ public abstract class SourceSearcher {
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected static Document readDocumentCancelable(final ProgressIndicator indicator, String url) throws IOException {
|
||||
protected static Element readDocumentCancelable(final ProgressIndicator indicator, String url) throws IOException {
|
||||
return HttpRequests.request(url)
|
||||
.accept("application/xml")
|
||||
.connect(new HttpRequests.RequestProcessor<Document>() {
|
||||
.connect(new HttpRequests.RequestProcessor<Element>() {
|
||||
@Override
|
||||
public Document process(@NotNull HttpRequests.Request request) throws IOException {
|
||||
public Element process(@NotNull HttpRequests.Request request) throws IOException {
|
||||
try {
|
||||
return JDOMUtil.loadDocument(request.getReader(indicator));
|
||||
return JdomKt.loadElement(request.getReader(indicator));
|
||||
}
|
||||
catch (JDOMException e) {
|
||||
throw new IOException(e);
|
||||
|
||||
+28
-9
@@ -18,8 +18,8 @@ package com.intellij.psi.impl.source.resolve.reference.impl;
|
||||
import com.intellij.codeInsight.completion.InsertHandler;
|
||||
import com.intellij.codeInsight.completion.InsertionContext;
|
||||
import com.intellij.codeInsight.completion.JavaLookupElementBuilder;
|
||||
import com.intellij.codeInsight.completion.PrioritizedLookupElement;
|
||||
import com.intellij.codeInsight.lookup.LookupElement;
|
||||
import com.intellij.codeInsight.lookup.LookupElementBuilder;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.util.PsiTreeUtil;
|
||||
import com.intellij.psi.util.PsiUtilCore;
|
||||
@@ -29,6 +29,7 @@ import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Comparator;
|
||||
|
||||
import static com.intellij.psi.impl.source.resolve.reference.impl.JavaReflectionReferenceUtil.*;
|
||||
|
||||
@@ -71,7 +72,7 @@ public class JavaLangClassMemberReference extends PsiReferenceBase<PsiLiteralExp
|
||||
|
||||
case DECLARED_FIELD: {
|
||||
PsiField field = psiClass.findFieldByName(name, false);
|
||||
return isReachable(field, psiClass) ? field : null;
|
||||
return isPotentiallyAccessible(field, psiClass) ? field : null;
|
||||
}
|
||||
|
||||
case METHOD: {
|
||||
@@ -85,7 +86,7 @@ public class JavaLangClassMemberReference extends PsiReferenceBase<PsiLiteralExp
|
||||
|
||||
case DECLARED_METHOD: {
|
||||
final PsiMethod[] methods = psiClass.findMethodsByName(name, false);
|
||||
return ContainerUtil.find(methods, method -> isRegularMethod(method) && isReachable(method, psiClass));
|
||||
return ContainerUtil.find(methods, method -> isRegularMethod(method) && isPotentiallyAccessible(method, psiClass));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -115,21 +116,30 @@ public class JavaLangClassMemberReference extends PsiReferenceBase<PsiLiteralExp
|
||||
switch (type) {
|
||||
|
||||
case DECLARED_FIELD:
|
||||
return psiClass.getFields();
|
||||
return Arrays.stream(psiClass.getFields())
|
||||
.sorted(Comparator.comparing(PsiField::getName))
|
||||
.map(field -> lookupField(field))
|
||||
.toArray();
|
||||
|
||||
case FIELD:
|
||||
return ContainerUtil.filter(psiClass.getAllFields(), field -> isReachable(field, psiClass)).toArray();
|
||||
return Arrays.stream(psiClass.getAllFields())
|
||||
.filter(field -> isPotentiallyAccessible(field, psiClass))
|
||||
.sorted(Comparator.comparingInt((PsiField field) -> isPublic(field) ? 0 : 1).thenComparing(PsiField::getName))
|
||||
.map(field -> withPriority(lookupField(field), isPublic(field)))
|
||||
.toArray();
|
||||
|
||||
case DECLARED_METHOD:
|
||||
return Arrays.stream(psiClass.getMethods())
|
||||
.filter(method -> isRegularMethod(method))
|
||||
.map(this::lookupMethod)
|
||||
.sorted(Comparator.comparing(PsiMethod::getName))
|
||||
.map(method -> lookupMethod(method))
|
||||
.toArray();
|
||||
|
||||
case METHOD:
|
||||
return Arrays.stream(psiClass.getAllMethods())
|
||||
.filter(method -> isRegularMethod(method) && isReachable(method, psiClass) && !isJavaLangObject(method.getContainingClass()))
|
||||
.map(this::lookupMethod)
|
||||
.filter(method -> isRegularMethod(method) && isPotentiallyAccessible(method, psiClass))
|
||||
.sorted(Comparator.comparingInt((PsiMethod method) -> getMethodSortOrder(method)).thenComparing(PsiMethod::getName))
|
||||
.map(method -> PrioritizedLookupElement.withPriority(lookupMethod(method), -getMethodSortOrder(method)))
|
||||
.toArray();
|
||||
}
|
||||
}
|
||||
@@ -137,8 +147,17 @@ public class JavaLangClassMemberReference extends PsiReferenceBase<PsiLiteralExp
|
||||
return EMPTY_ARRAY;
|
||||
}
|
||||
|
||||
private static int getMethodSortOrder(PsiMethod method) {
|
||||
return isJavaLangObject(method.getContainingClass()) ? 1 : isPublic(method) ? -1 : 0;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private LookupElementBuilder lookupMethod(PsiMethod method) {
|
||||
private static LookupElement lookupField(PsiField field) {
|
||||
return JavaLookupElementBuilder.forField(field);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private LookupElement lookupMethod(PsiMethod method) {
|
||||
return JavaLookupElementBuilder.forMethod(method, PsiSubstitutor.EMPTY).withInsertHandler(this);
|
||||
}
|
||||
|
||||
|
||||
+44
-32
@@ -27,11 +27,11 @@ import com.intellij.psi.util.InheritanceUtil;
|
||||
import com.intellij.psi.util.PsiTreeUtil;
|
||||
import com.intellij.psi.util.PsiUtilCore;
|
||||
import com.intellij.util.ProcessingContext;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.Set;
|
||||
import java.util.function.BiConsumer;
|
||||
|
||||
import static com.intellij.codeInsight.completion.JavaCompletionContributor.isInJavaContext;
|
||||
import static com.intellij.patterns.PsiJavaPatterns.*;
|
||||
@@ -42,18 +42,27 @@ import static com.intellij.psi.impl.source.resolve.reference.impl.JavaReflection
|
||||
* @author Pavel.Dolgov
|
||||
*/
|
||||
public class JavaReflectionCompletionContributor extends CompletionContributor {
|
||||
private static final String CONSTRUCTOR = "getConstructor";
|
||||
private static final String DECLARED_CONSTRUCTOR = "getDeclaredConstructor";
|
||||
private static final String ANNOTATION = "getAnnotation";
|
||||
private static final String DECLARED_ANNOTATION = "getDeclaredAnnotation";
|
||||
private static final String ANNOTATIONS_BY_TYPE = "getAnnotationsByType";
|
||||
private static final String DECLARED_ANNOTATIONS_BY_TYPE = "getDeclaredAnnotationsByType";
|
||||
private static final String ANNOTATED_ELEMENT = "java.lang.reflect.AnnotatedElement";
|
||||
|
||||
private static final Set<String> DECLARED_NAMES =
|
||||
ContainerUtil.immutableSet(DECLARED_CONSTRUCTOR, DECLARED_ANNOTATION, DECLARED_ANNOTATIONS_BY_TYPE);
|
||||
private static final ElementPattern<? extends PsiElement> CONSTRUCTOR_ARGUMENTS = psiElement(PsiExpressionList.class)
|
||||
.withParent(psiExpression().methodCall(
|
||||
psiMethod()
|
||||
.withName("getConstructor", "getDeclaredConstructor")
|
||||
.withName(CONSTRUCTOR, DECLARED_CONSTRUCTOR)
|
||||
.definedInClass(CommonClassNames.JAVA_LANG_CLASS)));
|
||||
|
||||
private static final ElementPattern<? extends PsiElement> ANNOTATION_ARGUMENTS = psiElement(PsiExpressionList.class)
|
||||
.withParent(psiExpression().methodCall(
|
||||
psiMethod()
|
||||
.withName("getAnnotation", "getDeclaredAnnotation", "getAnnotationsByType", "getDeclaredAnnotationsByType")
|
||||
.with(new MethodDefinedInInterfacePatternCondition("java.lang.reflect.AnnotatedElement"))));
|
||||
.withName(ANNOTATION, DECLARED_ANNOTATION, ANNOTATIONS_BY_TYPE, DECLARED_ANNOTATIONS_BY_TYPE)
|
||||
.with(new MethodDefinedInInterfacePatternCondition(ANNOTATED_ELEMENT))));
|
||||
|
||||
private static final ElementPattern<PsiElement> BEGINNING_OF_CONSTRUCTOR_ARGUMENTS = beginningOfArguments(CONSTRUCTOR_ARGUMENTS);
|
||||
|
||||
@@ -79,28 +88,32 @@ public class JavaReflectionCompletionContributor extends CompletionContributor {
|
||||
}
|
||||
|
||||
if (BEGINNING_OF_ANNOTATION_ARGUMENTS.accepts(position)) {
|
||||
PsiClass psiClass = getQualifierClass(position);
|
||||
if (psiClass != null) {
|
||||
addAnnotationClasses(psiClass, result);
|
||||
}
|
||||
addVariants(position, (psiClass, isDeclared) -> addAnnotationClasses(psiClass, isDeclared, result));
|
||||
//TODO handle annotations on fields and methods
|
||||
}
|
||||
if (BEGINNING_OF_CONSTRUCTOR_ARGUMENTS.accepts(position)) {
|
||||
PsiClass psiClass = getQualifierClass(position);
|
||||
else if (BEGINNING_OF_CONSTRUCTOR_ARGUMENTS.accepts(position)) {
|
||||
addVariants(position, (psiClass, isDeclared) -> addConstructorParameterTypes(psiClass, isDeclared, result));
|
||||
}
|
||||
}
|
||||
|
||||
private static void addVariants(PsiElement position, BiConsumer<PsiClass, Boolean> variantAdder) {
|
||||
PsiMethodCallExpression methodCall = PsiTreeUtil.getParentOfType(position, PsiMethodCallExpression.class);
|
||||
if (methodCall != null) {
|
||||
PsiClass psiClass = getReflectiveClass(methodCall.getMethodExpression().getQualifierExpression());
|
||||
if (psiClass != null) {
|
||||
addConstructorParameterTypes(psiClass, result);
|
||||
String methodName = methodCall.getMethodExpression().getReferenceName();
|
||||
if (methodName != null) {
|
||||
variantAdder.accept(psiClass, DECLARED_NAMES.contains(methodName));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private static PsiClass getQualifierClass(@Nullable PsiElement position) {
|
||||
PsiMethodCallExpression methodCall = PsiTreeUtil.getParentOfType(position, PsiMethodCallExpression.class);
|
||||
return methodCall != null ? getReflectiveClass(methodCall.getMethodExpression().getQualifierExpression()) : null;
|
||||
}
|
||||
private static void addAnnotationClasses(@NotNull PsiClass psiClass, boolean isDeclared, @NotNull CompletionResultSet result) {
|
||||
Set<PsiAnnotation> declaredAnnotations =
|
||||
isDeclared ? ContainerUtil.set(AnnotationUtil.getAllAnnotations(psiClass, false, null, false)) : null;
|
||||
|
||||
private static void addAnnotationClasses(@NotNull PsiModifierListOwner annotationsOwner, @NotNull CompletionResultSet result) {
|
||||
PsiAnnotation[] annotations = AnnotationUtil.getAllAnnotations(annotationsOwner, true, null);
|
||||
PsiAnnotation[] annotations = AnnotationUtil.getAllAnnotations(psiClass, true, null, false);
|
||||
for (PsiAnnotation annotation : annotations) {
|
||||
PsiJavaCodeReferenceElement referenceElement = annotation.getNameReferenceElement();
|
||||
if (referenceElement != null) {
|
||||
@@ -112,6 +125,9 @@ public class JavaReflectionCompletionContributor extends CompletionContributor {
|
||||
LookupElement lookupElement = LookupElementBuilder.createWithIcon(annotationClass)
|
||||
.withPresentableText(className + ".class")
|
||||
.withInsertHandler(JavaReflectionCompletionContributor::handleAnnotationClassInsertion);
|
||||
if (isDeclared) {
|
||||
lookupElement = withPriority(lookupElement, declaredAnnotations.contains(annotation));
|
||||
}
|
||||
result.addElement(lookupElement);
|
||||
}
|
||||
}
|
||||
@@ -119,26 +135,22 @@ public class JavaReflectionCompletionContributor extends CompletionContributor {
|
||||
}
|
||||
}
|
||||
|
||||
private static void addConstructorParameterTypes(@NotNull PsiClass psiClass, @NotNull CompletionResultSet result) {
|
||||
private static void addConstructorParameterTypes(@NotNull PsiClass psiClass, boolean isDeclared, @NotNull CompletionResultSet result) {
|
||||
PsiMethod[] constructors = psiClass.getConstructors();
|
||||
if (constructors.length != 0) {
|
||||
for (PsiMethod constructor : constructors) {
|
||||
String parameterTypesText = Arrays.stream(constructor.getParameterList().getParameters())
|
||||
.map(p -> p.getType().getCanonicalText())
|
||||
.collect(Collectors.joining(",", constructor.getName() + "(", ")"));
|
||||
|
||||
LookupElement lookupElement = LookupElementBuilder.createWithIcon(constructor)
|
||||
.withPresentableText(parameterTypesText)
|
||||
.withInsertHandler(JavaReflectionCompletionContributor::handleConstructorSignatureInsertion);
|
||||
result.addElement(lookupElement);
|
||||
for (PsiMethod constructor : constructors) {
|
||||
LookupElement lookupElement = JavaLookupElementBuilder.forMethod(constructor, PsiSubstitutor.EMPTY)
|
||||
.withInsertHandler(JavaReflectionCompletionContributor::handleConstructorSignatureInsertion);
|
||||
if (isDeclared) {
|
||||
lookupElement = withPriority(lookupElement, isPublic(constructor));
|
||||
}
|
||||
result.addElement(lookupElement);
|
||||
}
|
||||
}
|
||||
|
||||
private static void handleAnnotationClassInsertion(@NotNull InsertionContext context, @NotNull LookupElement item) {
|
||||
Object object = item.getObject();
|
||||
if (object instanceof PsiClass) {
|
||||
String className = ((PsiClass)object).getName();
|
||||
String className = ((PsiClass)object).getQualifiedName();
|
||||
if (className != null) {
|
||||
handleParametersInsertion(context, className + ".class");
|
||||
}
|
||||
|
||||
+8
-1
@@ -16,6 +16,8 @@
|
||||
package com.intellij.psi.impl.source.resolve.reference.impl;
|
||||
|
||||
import com.intellij.codeInsight.completion.InsertionContext;
|
||||
import com.intellij.codeInsight.completion.PrioritizedLookupElement;
|
||||
import com.intellij.codeInsight.lookup.LookupElement;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.util.RecursionGuard;
|
||||
import com.intellij.openapi.util.RecursionManager;
|
||||
@@ -151,7 +153,7 @@ class JavaReflectionReferenceUtil {
|
||||
* Non-public members of superclass/superinterface can't be obtained via reflection, they need to be filtered out.
|
||||
*/
|
||||
@Contract("null, _ -> false")
|
||||
static boolean isReachable(PsiMember member, PsiClass psiClass) {
|
||||
static boolean isPotentiallyAccessible(PsiMember member, PsiClass psiClass) {
|
||||
return member != null && (member.getContainingClass() == psiClass || isPublic(member));
|
||||
}
|
||||
|
||||
@@ -175,4 +177,9 @@ class JavaReflectionReferenceUtil {
|
||||
JavaCodeStyleManager.getInstance(context.getProject()).shortenClassReferences(methodCall.getArgumentList());
|
||||
}
|
||||
}
|
||||
|
||||
@NotNull
|
||||
static LookupElement withPriority(LookupElement lookupElement, boolean hasPriority) {
|
||||
return PrioritizedLookupElement.withPriority(lookupElement, hasPriority ? 1 : -1);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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,12 +24,10 @@ import com.intellij.psi.impl.source.SourceTreeToPsiMap;
|
||||
import com.intellij.psi.impl.source.tree.JavaElementType;
|
||||
import com.intellij.psi.impl.source.tree.TreeElement;
|
||||
import com.intellij.util.IncorrectOperationException;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
@SuppressWarnings("ForLoopReplaceableByForEach")
|
||||
public class ClsModifierListImpl extends ClsRepositoryPsiElement<PsiModifierListStub> implements PsiModifierList {
|
||||
public ClsModifierListImpl(final PsiModifierListStub stub) {
|
||||
public ClsModifierListImpl(PsiModifierListStub stub) {
|
||||
super(stub);
|
||||
}
|
||||
|
||||
@@ -78,29 +76,29 @@ public class ClsModifierListImpl extends ClsRepositoryPsiElement<PsiModifierList
|
||||
|
||||
@Override
|
||||
@NotNull
|
||||
public PsiAnnotation addAnnotation(@NotNull @NonNls String qualifiedName) {
|
||||
public PsiAnnotation addAnnotation(@NotNull String qualifiedName) {
|
||||
throw cannotModifyException(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void appendMirrorText(int indentLevel, @NotNull StringBuilder buffer) {
|
||||
final PsiElement parent = getParent();
|
||||
final PsiAnnotation[] annotations = getAnnotations();
|
||||
final boolean separateAnnotations = parent instanceof PsiClass || parent instanceof PsiMethod || parent instanceof PsiField;
|
||||
PsiElement parent = getParent();
|
||||
PsiAnnotation[] annotations = getAnnotations();
|
||||
boolean separateAnnotations = parent instanceof PsiClass || parent instanceof PsiMethod || parent instanceof PsiField;
|
||||
|
||||
for (int i = 0; i < annotations.length; i++) {
|
||||
appendText(annotations[i], indentLevel, buffer, separateAnnotations ? NEXT_LINE : " ");
|
||||
for (PsiAnnotation annotation : annotations) {
|
||||
appendText(annotation, indentLevel, buffer, separateAnnotations ? NEXT_LINE : " ");
|
||||
}
|
||||
|
||||
final boolean isClass = parent instanceof PsiClass;
|
||||
final boolean isInterface = isClass && ((PsiClass)parent).isInterface();
|
||||
final boolean isEnum = isClass && ((PsiClass)parent).isEnum();
|
||||
final boolean isInterfaceClass = isClass && parent.getParent() instanceof PsiClass && ((PsiClass)parent.getParent()).isInterface();
|
||||
final boolean isMethod = parent instanceof PsiMethod;
|
||||
final boolean isInterfaceMethod = isMethod && parent.getParent() instanceof PsiClass && ((PsiClass)parent.getParent()).isInterface();
|
||||
final boolean isField = parent instanceof PsiField;
|
||||
final boolean isInterfaceField = isField && parent.getParent() instanceof PsiClass && ((PsiClass)parent.getParent()).isInterface();
|
||||
final boolean isEnumConstant = parent instanceof PsiEnumConstant;
|
||||
boolean isClass = parent instanceof PsiClass;
|
||||
boolean isInterface = isClass && ((PsiClass)parent).isInterface();
|
||||
boolean isEnum = isClass && ((PsiClass)parent).isEnum();
|
||||
boolean isInterfaceClass = isClass && parent.getParent() instanceof PsiClass && ((PsiClass)parent.getParent()).isInterface();
|
||||
boolean isMethod = parent instanceof PsiMethod;
|
||||
boolean isInterfaceMethod = isMethod && parent.getParent() instanceof PsiClass && ((PsiClass)parent.getParent()).isInterface();
|
||||
boolean isField = parent instanceof PsiField;
|
||||
boolean isInterfaceField = isField && parent.getParent() instanceof PsiClass && ((PsiClass)parent.getParent()).isInterface();
|
||||
boolean isEnumConstant = parent instanceof PsiEnumConstant;
|
||||
|
||||
if (hasModifierProperty(PsiModifier.PUBLIC) && !isInterfaceMethod && !isInterfaceField && !isInterfaceClass && !isEnumConstant) {
|
||||
buffer.append(PsiModifier.PUBLIC).append(' ');
|
||||
@@ -160,4 +158,4 @@ public class ClsModifierListImpl extends ClsRepositoryPsiElement<PsiModifierList
|
||||
public String toString() {
|
||||
return "PsiModifierList";
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -18,7 +18,7 @@ package com.intellij.psi.impl.java.stubs;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.impl.compiled.*;
|
||||
|
||||
/*
|
||||
/**
|
||||
* @author max
|
||||
*/
|
||||
public class ClsStubPsiFactory extends StubPsiFactory {
|
||||
|
||||
@@ -13,16 +13,15 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
/*
|
||||
* @author max
|
||||
*/
|
||||
package com.intellij.psi.impl.java.stubs;
|
||||
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.impl.source.*;
|
||||
import com.intellij.psi.impl.source.tree.java.*;
|
||||
|
||||
/**
|
||||
* @author max
|
||||
*/
|
||||
public class SourceStubPsiFactory extends StubPsiFactory {
|
||||
public static final SourceStubPsiFactory INSTANCE = new SourceStubPsiFactory();
|
||||
|
||||
|
||||
@@ -17,7 +17,7 @@ package com.intellij.psi.impl.java.stubs;
|
||||
|
||||
import com.intellij.psi.*;
|
||||
|
||||
/*
|
||||
/**
|
||||
* @author max
|
||||
*/
|
||||
public abstract class StubPsiFactory {
|
||||
|
||||
@@ -22,5 +22,5 @@ class DeclaredField {
|
||||
class Test {
|
||||
public int num;
|
||||
public int num2;
|
||||
int num3;
|
||||
int num1;
|
||||
}
|
||||
@@ -22,5 +22,5 @@ class DeclaredField {
|
||||
class Test {
|
||||
public int num;
|
||||
public int num2;
|
||||
int num3;
|
||||
int num1;
|
||||
}
|
||||
@@ -22,7 +22,7 @@ class DecalredMethod {
|
||||
class Test {
|
||||
public void method(){}
|
||||
public void method2(A a, B b){}
|
||||
public void method3(){}
|
||||
void method1(){}
|
||||
}
|
||||
|
||||
class A {}
|
||||
|
||||
@@ -22,7 +22,7 @@ class DecalredMethod2 {
|
||||
class Test {
|
||||
void method(){}
|
||||
void method2(A a, B b){}
|
||||
void method3(){}
|
||||
void method1(){}
|
||||
}
|
||||
|
||||
class A {}
|
||||
|
||||
+2
-2
@@ -15,14 +15,14 @@
|
||||
*/
|
||||
class DecalredMethod2 {
|
||||
void foo() {
|
||||
Test.class.getDeclaredMethod("method3");
|
||||
Test.class.getDeclaredMethod("method1");
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
void method(){}
|
||||
void method2(A a, B b){}
|
||||
void method3(){}
|
||||
void method1(){}
|
||||
}
|
||||
|
||||
class A {}
|
||||
|
||||
+1
-1
@@ -22,7 +22,7 @@ class DecalredMethod {
|
||||
class Test {
|
||||
public void method(){}
|
||||
public void method2(A a, B b){}
|
||||
public void method3(){}
|
||||
void method1(){}
|
||||
}
|
||||
|
||||
class A {}
|
||||
|
||||
+1
-1
@@ -22,5 +22,5 @@ class ForNameDeclaredField {
|
||||
class Test {
|
||||
public int num;
|
||||
public int num2;
|
||||
int num3;
|
||||
int num1;
|
||||
}
|
||||
+2
-2
@@ -15,12 +15,12 @@
|
||||
*/
|
||||
class ForNameDeclaredField {
|
||||
void foo() {
|
||||
Class.forName("Test").getDeclaredField("num3");
|
||||
Class.forName("Test").getDeclaredField("num1");
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
public int num;
|
||||
public int num2;
|
||||
int num3;
|
||||
int num1;
|
||||
}
|
||||
+1
-1
@@ -22,7 +22,7 @@ class ForNameDeclaredMethod {
|
||||
class Test {
|
||||
public void method(){}
|
||||
public void method2(A a, B b){}
|
||||
void method3(){}
|
||||
void method1(){}
|
||||
}
|
||||
|
||||
class A {}
|
||||
|
||||
+1
-1
@@ -22,7 +22,7 @@ class ForNameDeclaredMethod {
|
||||
class Test {
|
||||
public void method(){}
|
||||
public void method2(A a, B b){}
|
||||
void method3(){}
|
||||
void method1(){}
|
||||
}
|
||||
|
||||
class A {}
|
||||
|
||||
@@ -0,0 +1,17 @@
|
||||
class HasConstructor {
|
||||
void foo() {
|
||||
Test.class.getMethod("<caret>");
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
public Test() {}
|
||||
Test(int n) {}
|
||||
public void method(){}
|
||||
public void method2(A a, B b){}
|
||||
void method1(){}
|
||||
}
|
||||
|
||||
class A {}
|
||||
class B {}
|
||||
class C {}
|
||||
@@ -0,0 +1,17 @@
|
||||
class HasConstructor {
|
||||
void foo() {
|
||||
Test.class.getMethod("method1");
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
public Test() {}
|
||||
Test(int n) {}
|
||||
public void method(){}
|
||||
public void method2(A a, B b){}
|
||||
void method1(){}
|
||||
}
|
||||
|
||||
class A {}
|
||||
class B {}
|
||||
class C {}
|
||||
+9
@@ -0,0 +1,9 @@
|
||||
class Main {
|
||||
void foo() {
|
||||
Test.class.getMethod("<caret>");
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
public void method(){}
|
||||
}
|
||||
+9
@@ -0,0 +1,9 @@
|
||||
class Main {
|
||||
void foo() {
|
||||
Test.class.getMethod("notifyAll");
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
public void method(){}
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
class Main {
|
||||
void foo() {
|
||||
Object.class.getMethod("<caret>");
|
||||
}
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
class Main {
|
||||
void foo() {
|
||||
Object.class.getMethod("wait", long.class);
|
||||
}
|
||||
}
|
||||
+17
@@ -0,0 +1,17 @@
|
||||
class Main {
|
||||
void foo() {
|
||||
Test.class.getMethod("<caret>");
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
public Test() {}
|
||||
Test(int n) {}
|
||||
public void method(){}
|
||||
void method(A a, B b){}
|
||||
public void method(C c){}
|
||||
}
|
||||
|
||||
class A {}
|
||||
class B {}
|
||||
class C {}
|
||||
+17
@@ -0,0 +1,17 @@
|
||||
class Main {
|
||||
void foo() {
|
||||
Test.class.getMethod("method", A.class, B.class);
|
||||
}
|
||||
}
|
||||
|
||||
class Test {
|
||||
public Test() {}
|
||||
Test(int n) {}
|
||||
public void method(){}
|
||||
void method(A a, B b){}
|
||||
public void method(C c){}
|
||||
}
|
||||
|
||||
class A {}
|
||||
class B {}
|
||||
class C {}
|
||||
@@ -1,7 +1,6 @@
|
||||
import foo.bar.*;
|
||||
class Main {
|
||||
void foo() throws ReflectiveOperationException {
|
||||
Class<Annotation> aType = Baz.class;
|
||||
Test.class.getAnnotation(<caret>);
|
||||
}
|
||||
}
|
||||
-1
@@ -1,7 +1,6 @@
|
||||
import foo.bar.*;
|
||||
class Main {
|
||||
void foo() throws ReflectiveOperationException {
|
||||
Class<Annotation> aType = Baz.class;
|
||||
Test.class.getAnnotation(Bar.class);
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
import foo.bar.*;
|
||||
class Main {
|
||||
void foo() throws ReflectiveOperationException {
|
||||
Test.class.getDeclaredAnnotation(Bar.class);
|
||||
Test.class.getDeclaredAnnotation(Foo.class);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
import foo.bar.*;
|
||||
class Main {
|
||||
void foo() throws ReflectiveOperationException {
|
||||
More.class.getAnnotation(<caret>);
|
||||
}
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
import foo.bar.*;
|
||||
import foo.baz.Baz;
|
||||
|
||||
class Main {
|
||||
void foo() throws ReflectiveOperationException {
|
||||
More.class.getAnnotation(Baz.class);
|
||||
}
|
||||
}
|
||||
-1
@@ -1,7 +1,6 @@
|
||||
import foo.bar.*;
|
||||
class Main {
|
||||
void foo() throws ReflectiveOperationException {
|
||||
Class<Annotation> aType = Baz.class;
|
||||
Test.class.getAnnotation(<caret>);
|
||||
}
|
||||
}
|
||||
-1
@@ -1,7 +1,6 @@
|
||||
import foo.bar.*;
|
||||
class Main {
|
||||
void foo() throws ReflectiveOperationException {
|
||||
Class<Annotation> aType = Baz.class;
|
||||
Test.class.getAnnotation(Foo.class);
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
import foo.bar.*;
|
||||
class Main {
|
||||
void foo() throws ReflectiveOperationException {
|
||||
Test.class.getDeclaredAnnotation(Foo.class);
|
||||
Test.class.getDeclaredAnnotation(Bar.class);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
import foo.bar.*;
|
||||
import foo.baz.Baz;
|
||||
class Main {
|
||||
void foo() throws ReflectiveOperationException {
|
||||
Class<Annotation> aType = Baz.class;
|
||||
Test.class.getAnnotation(<caret>);
|
||||
}
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
import foo.bar.*;
|
||||
import foo.baz.Baz;
|
||||
class Main {
|
||||
void foo() throws ReflectiveOperationException {
|
||||
Class<Annotation> aType = Baz.class;
|
||||
Test.class.getAnnotation(aType);
|
||||
}
|
||||
}
|
||||
+52
@@ -0,0 +1,52 @@
|
||||
// "Fix all 'Loop can be collapsed with Stream API' problems in file" "true"
|
||||
|
||||
import java.util.*;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
public class Test {
|
||||
void testList(List<String> input) {
|
||||
List<String> result = input.stream().filter(s -> !s.isEmpty()).collect(Collectors.toCollection(() -> new ArrayList<>(10)));
|
||||
System.out.println(result);
|
||||
|
||||
ArrayList<String> result2 = input.stream().filter(s -> !s.isEmpty()).collect(Collectors.toCollection(() -> new ArrayList<>(20)));
|
||||
System.out.println(result2);
|
||||
|
||||
// Non-empty
|
||||
ArrayList<String> result3 = new ArrayList<>(input);
|
||||
input.stream().filter(s -> !s.isEmpty()).forEach(result3::add);
|
||||
System.out.println(result3);
|
||||
}
|
||||
|
||||
void testSet(List<String> input) {
|
||||
Set<String> result = input.stream().filter(s -> !s.isEmpty()).collect(Collectors.toCollection(() -> new HashSet<>(10)));
|
||||
System.out.println(result);
|
||||
|
||||
Collection<String> result2 = input.stream().filter(s -> !s.isEmpty()).collect(Collectors.toCollection(() -> new LinkedHashSet<>(20, 0.8f)));
|
||||
System.out.println(result2);
|
||||
|
||||
// Non-empty
|
||||
AbstractSet<String> result3 = new HashSet<>(input);
|
||||
input.stream().filter(s -> !s.isEmpty()).forEach(result3::add);
|
||||
System.out.println(result3);
|
||||
|
||||
Collection<TimeUnit> result4 = input.stream().filter(s -> !s.isEmpty()).map(TimeUnit::valueOf).collect(Collectors.toCollection(() -> EnumSet.noneOf(TimeUnit.class)));
|
||||
System.out.println(result4);
|
||||
}
|
||||
|
||||
void testMap(List<String> input) {
|
||||
Map<Integer, String> result = input.stream().filter(s -> !s.isEmpty()).collect(Collectors.toMap(String::length, s -> s, (a, b) -> b, () -> new HashMap<>(10)));
|
||||
System.out.println(result);
|
||||
|
||||
Map<Integer, String> result2 = input.stream().filter(s -> !s.isEmpty()).collect(Collectors.toMap(String::length, s -> s, (a, b) -> b, () -> new HashMap<>(10, 0.8f)));
|
||||
System.out.println(result2);
|
||||
|
||||
EnumMap<TimeUnit, String> result3 = input.stream().filter(s -> !s.isEmpty()).collect(Collectors.toMap(TimeUnit::valueOf, s -> s, (a, b) -> b, () -> new EnumMap<>(TimeUnit.class)));
|
||||
System.out.println(result3);
|
||||
|
||||
// Non-empty
|
||||
EnumMap<TimeUnit, String> result4 = new EnumMap<>(result3);
|
||||
input.stream().filter(s -> !s.isEmpty()).forEach(s -> result4.put(TimeUnit.valueOf(s), s));
|
||||
System.out.println(result4);
|
||||
}
|
||||
}
|
||||
+14
@@ -0,0 +1,14 @@
|
||||
// "Replace with collect" "true"
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
public class Test {
|
||||
public List<String> test(String[] data) {
|
||||
int top = Math.min(10, data.length);
|
||||
List<String> result = Arrays.stream(data).limit(10).map(String::trim).filter(item -> !item.isEmpty()).collect(Collectors.toList());
|
||||
return result;
|
||||
}
|
||||
}
|
||||
+103
@@ -0,0 +1,103 @@
|
||||
// "Fix all 'Loop can be collapsed with Stream API' problems in file" "true"
|
||||
|
||||
import java.util.*;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
public class Test {
|
||||
void testList(List<String> input) {
|
||||
List<String> result = new ArrayList<>(10);
|
||||
for (String s : in<caret>put) {
|
||||
if (!s.isEmpty()) {
|
||||
result.add(s);
|
||||
}
|
||||
}
|
||||
System.out.println(result);
|
||||
|
||||
ArrayList<String> result2 = new ArrayList<>(20);
|
||||
for (String s : input) {
|
||||
if (!s.isEmpty()) {
|
||||
result2.add(s);
|
||||
}
|
||||
}
|
||||
System.out.println(result2);
|
||||
|
||||
// Non-empty
|
||||
ArrayList<String> result3 = new ArrayList<>(input);
|
||||
for (String s : input) {
|
||||
if (!s.isEmpty()) {
|
||||
result3.add(s);
|
||||
}
|
||||
}
|
||||
System.out.println(result3);
|
||||
}
|
||||
|
||||
void testSet(List<String> input) {
|
||||
Set<String> result = new HashSet<>(10);
|
||||
for (String s : input) {
|
||||
if (!s.isEmpty()) {
|
||||
result.add(s);
|
||||
}
|
||||
}
|
||||
System.out.println(result);
|
||||
|
||||
Collection<String> result2 = new LinkedHashSet<>(20, 0.8f);
|
||||
for (String s : input) {
|
||||
if (!s.isEmpty()) {
|
||||
result2.add(s);
|
||||
}
|
||||
}
|
||||
System.out.println(result2);
|
||||
|
||||
// Non-empty
|
||||
AbstractSet<String> result3 = new HashSet<>(input);
|
||||
for (String s : input) {
|
||||
if (!s.isEmpty()) {
|
||||
result3.add(s);
|
||||
}
|
||||
}
|
||||
System.out.println(result3);
|
||||
|
||||
Collection<TimeUnit> result4 = EnumSet.noneOf(TimeUnit.class);
|
||||
for (String s : input) {
|
||||
if (!s.isEmpty()) {
|
||||
result4.add(TimeUnit.valueOf(s));
|
||||
}
|
||||
}
|
||||
System.out.println(result4);
|
||||
}
|
||||
|
||||
void testMap(List<String> input) {
|
||||
Map<Integer, String> result = new HashMap<>(10);
|
||||
for (String s : input) {
|
||||
if (!s.isEmpty()) {
|
||||
result.put(s.length(), s);
|
||||
}
|
||||
}
|
||||
System.out.println(result);
|
||||
|
||||
Map<Integer, String> result2 = new HashMap<>(10, 0.8f);
|
||||
for (String s : input) {
|
||||
if (!s.isEmpty()) {
|
||||
result2.put(s.length(), s);
|
||||
}
|
||||
}
|
||||
System.out.println(result2);
|
||||
|
||||
EnumMap<TimeUnit, String> result3 = new EnumMap<>(TimeUnit.class);
|
||||
for (String s : input) {
|
||||
if (!s.isEmpty()) {
|
||||
result3.put(TimeUnit.valueOf(s), s);
|
||||
}
|
||||
}
|
||||
System.out.println(result3);
|
||||
|
||||
// Non-empty
|
||||
EnumMap<TimeUnit, String> result4 = new EnumMap<>(result3);
|
||||
for (String s : input) {
|
||||
if (!s.isEmpty()) {
|
||||
result4.put(TimeUnit.valueOf(s), s);
|
||||
}
|
||||
}
|
||||
System.out.println(result4);
|
||||
}
|
||||
}
|
||||
+18
@@ -0,0 +1,18 @@
|
||||
// "Replace with collect" "true"
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public class Test {
|
||||
public List<String> test(String[] data) {
|
||||
int top = Math.min(10, data.length);
|
||||
List<String> result = new ArrayList<>();
|
||||
for(int<caret> i=0; i<top; i++) {
|
||||
String item = data[i].trim();
|
||||
if(!item.isEmpty()) {
|
||||
result.add(item);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,79 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<problems>
|
||||
<problem>
|
||||
<file>X.java</file>
|
||||
<line>31</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">magic constant</problem_class>
|
||||
<description>Should be one of: Const1.X, Const2.I</description>
|
||||
</problem>
|
||||
<problem>
|
||||
<file>X.java</file>
|
||||
<line>32</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">magic constant</problem_class>
|
||||
<description>Should be one of: Const1.X, Const2.I</description>
|
||||
</problem>
|
||||
<problem>
|
||||
<file>X.java</file>
|
||||
<line>33</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">magic constant</problem_class>
|
||||
<description>Should be one of: Const1.X, Const2.I</description>
|
||||
</problem>
|
||||
|
||||
<problem>
|
||||
<file>X.java</file>
|
||||
<line>44</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">magic constant</problem_class>
|
||||
<description>Should be one of: Const2.I, Const1.X</description>
|
||||
</problem>
|
||||
<problem>
|
||||
<file>X.java</file>
|
||||
<line>45</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">magic constant</problem_class>
|
||||
<description>Should be one of: Const2.I, Const1.X</description>
|
||||
</problem>
|
||||
<problem>
|
||||
<file>X.java</file>
|
||||
<line>46</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">magic constant</problem_class>
|
||||
<description>Should be one of: Const2.I, Const1.X</description>
|
||||
</problem>
|
||||
|
||||
<problem>
|
||||
<file>X.java</file>
|
||||
<line>57</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">magic constant</problem_class>
|
||||
<description>Should be one of: Const1.X, Const2.I or their combination</description>
|
||||
</problem>
|
||||
<problem>
|
||||
<file>X.java</file>
|
||||
<line>58</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">magic constant</problem_class>
|
||||
<description>Should be one of: Const1.X, Const2.I or their combination</description>
|
||||
</problem>
|
||||
<problem>
|
||||
<file>X.java</file>
|
||||
<line>59</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">magic constant</problem_class>
|
||||
<description>Should be one of: Const1.X, Const2.I</description>
|
||||
</problem>
|
||||
<problem>
|
||||
<file>X.java</file>
|
||||
<line>61</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">magic constant</problem_class>
|
||||
<description>Should be one of: Const1.X, Const2.I or their combination</description>
|
||||
</problem>
|
||||
|
||||
<problem>
|
||||
<file>X.java</file>
|
||||
<line>72</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">magic constant</problem_class>
|
||||
<description>Should be one of: Const2.I, Const1.X or their combination</description>
|
||||
</problem>
|
||||
<problem>
|
||||
<file>X.java</file>
|
||||
<line>73</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">magic constant</problem_class>
|
||||
<description>Should be one of: Const2.I, Const1.X or their combination</description>
|
||||
</problem>
|
||||
|
||||
</problems>
|
||||
@@ -0,0 +1,82 @@
|
||||
/*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
import org.intellij.lang.annotations.MagicConstant;
|
||||
|
||||
class Const1 {
|
||||
public static final int X = 1;
|
||||
}
|
||||
|
||||
class Const2 {
|
||||
public static final int I = 4;
|
||||
}
|
||||
|
||||
public class X {
|
||||
|
||||
void f(@MagicConstant(intValues = {Const1.X, Const2.I}) int x) {
|
||||
/////////// BAD
|
||||
f(0);
|
||||
f(1);
|
||||
f(Const1.X | Const2.I);
|
||||
|
||||
////////////// GOOD
|
||||
f(Const1.X);
|
||||
f(Const2.I);
|
||||
|
||||
f2(x);
|
||||
}
|
||||
|
||||
void f2(@MagicConstant(valuesFromClass = Const1.class, intValues = {Const2.I}) int x) {
|
||||
/////////// BAD
|
||||
f2(0);
|
||||
f2(1);
|
||||
f2(Const1.X | Const2.I);
|
||||
|
||||
////////////// GOOD
|
||||
f2(Const1.X);
|
||||
f2(Const2.I);
|
||||
|
||||
f(x);
|
||||
}
|
||||
|
||||
void f3(@MagicConstant(flags = {Const1.X, Const2.I}) int x) {
|
||||
/////////// BAD
|
||||
f3(2);
|
||||
f3(1);
|
||||
f(Const1.X | Const2.I);
|
||||
int i = Const1.X | 4;
|
||||
f3(i);
|
||||
|
||||
////////////// GOOD
|
||||
f3(Const1.X);
|
||||
f3(Const2.I);
|
||||
|
||||
f4(x);
|
||||
}
|
||||
|
||||
void f4(@MagicConstant(flagsFromClass = Const1.class, flags = {Const2.I}) int x) {
|
||||
/////////// BAD
|
||||
f4(-3);
|
||||
f4(1);
|
||||
|
||||
////////////// GOOD
|
||||
f4(Const1.X);
|
||||
f4(Const2.I);
|
||||
f4(Const1.X | Const2.I);
|
||||
|
||||
f3(x);
|
||||
}
|
||||
}
|
||||
+53
@@ -0,0 +1,53 @@
|
||||
/*
|
||||
* Copyright 2000-2017 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.completion
|
||||
|
||||
import com.intellij.JavaTestUtil
|
||||
|
||||
/**
|
||||
* @author Pavel.Dolgov
|
||||
*/
|
||||
class JavaReflectionCompletionOverloadTest : LightFixtureCompletionTestCase() {
|
||||
|
||||
override fun getBasePath() = JavaTestUtil.getRelativeJavaTestDataPath() + "/codeInsight/completion/reflectionOverload/"
|
||||
|
||||
fun testOverloadMethods() = doTest(2, "method()", "method(C c)", "method(A a,B b)")
|
||||
|
||||
fun testJavaLangObjectMethods() = doTest(6,
|
||||
"method()",
|
||||
"equals(java.lang.Object obj)", "hashCode()", "toString()",
|
||||
"getClass()", "notify()", "notifyAll()",
|
||||
"wait()", "wait(long timeout)", "wait(long timeout,int nanos)"
|
||||
)
|
||||
|
||||
fun testJavaLangObjectOwnMethods() = doTest(9,
|
||||
"clone()", "equals(java.lang.Object obj)", "hashCode()",
|
||||
"toString()", "finalize()", "getClass()",
|
||||
"notify()", "notifyAll()",
|
||||
"wait()", "wait(long timeout)", "wait(long timeout,int nanos)",
|
||||
"registerNatives()")
|
||||
|
||||
|
||||
private fun doTest(index: Int, vararg expected: String) {
|
||||
configureByFile(getTestName(false) + ".java")
|
||||
|
||||
val lookupItems = lookup.items
|
||||
val texts = lookupItemTexts(lookupItems, expected.size)
|
||||
assertOrderedEquals(texts, *expected)
|
||||
if (index >= 0) selectItem(lookupItems[index])
|
||||
myFixture.checkResultByFile(getTestName(false) + "_after.java")
|
||||
}
|
||||
}
|
||||
+12
-7
@@ -34,15 +34,15 @@ public class JavaReflectionCompletionTest extends LightFixtureCompletionTestCase
|
||||
}
|
||||
|
||||
public void testDeclaredField() throws Exception {
|
||||
doTest(1, "num", "num2", "num3");
|
||||
doTest(2, "num", "num1", "num2");
|
||||
}
|
||||
|
||||
public void testDeclaredMethod() throws Exception {
|
||||
doTest(1, "method", "method2", "method3");
|
||||
doTest(2, "method", "method1", "method2");
|
||||
}
|
||||
|
||||
public void testDeclaredMethod2() throws Exception {
|
||||
doTest(2, "method", "method2", "method3");
|
||||
doTest(1, "method", "method1", "method2");
|
||||
}
|
||||
|
||||
public void testMethod() throws Exception {
|
||||
@@ -50,7 +50,7 @@ public class JavaReflectionCompletionTest extends LightFixtureCompletionTestCase
|
||||
}
|
||||
|
||||
public void testForNameDeclaredMethod() throws Exception {
|
||||
doTest(1, "method", "method2", "method3");
|
||||
doTest(2, "method", "method1", "method2");
|
||||
}
|
||||
|
||||
public void testForNameMethod() throws Exception {
|
||||
@@ -62,7 +62,7 @@ public class JavaReflectionCompletionTest extends LightFixtureCompletionTestCase
|
||||
}
|
||||
|
||||
public void testForNameDeclaredField() throws Exception {
|
||||
doTest(2, "num", "num2", "num3");
|
||||
doTest(1, "num", "num1", "num2");
|
||||
}
|
||||
|
||||
public void testVarargMethod() throws Exception {
|
||||
@@ -135,7 +135,7 @@ public class JavaReflectionCompletionTest extends LightFixtureCompletionTestCase
|
||||
}
|
||||
|
||||
public void testConstantGetClassField() throws Exception {
|
||||
doTest(1, "num", "num2", "num3");
|
||||
doTest(2, "num", "num3", "num2");
|
||||
}
|
||||
|
||||
public void testExpressionGetClassField() throws Exception {
|
||||
@@ -165,9 +165,14 @@ public class JavaReflectionCompletionTest extends LightFixtureCompletionTestCase
|
||||
doTest(0, "PublicClass");
|
||||
}
|
||||
|
||||
public void testHasConstructor() {
|
||||
doTest(2, "method", "method2", "method1");
|
||||
}
|
||||
|
||||
|
||||
private void doTest(int index, String... expected) {
|
||||
configureByFile(getTestName(false) + ".java");
|
||||
assertStringItems(expected);
|
||||
assertFirstStringItems(expected);
|
||||
if (index >= 0) selectItem(getLookup().getItems().get(index));
|
||||
myFixture.checkResultByFile(getTestName(false) + "_after.java");
|
||||
}
|
||||
|
||||
+43
-15
@@ -31,7 +31,9 @@
|
||||
package com.intellij.codeInsight.completion
|
||||
|
||||
import com.intellij.JavaTestUtil
|
||||
import com.intellij.codeInsight.lookup.LookupElement
|
||||
import com.intellij.codeInsight.lookup.LookupElementPresentation
|
||||
import com.intellij.psi.PsiMethod
|
||||
import com.intellij.testFramework.LightProjectDescriptor
|
||||
|
||||
/**
|
||||
@@ -42,26 +44,36 @@ class JavaReflectionParametersCompletionTest : LightFixtureCompletionTestCase()
|
||||
|
||||
override fun getProjectDescriptor(): LightProjectDescriptor = com.intellij.testFramework.fixtures.LightCodeInsightFixtureTestCase.JAVA_8
|
||||
|
||||
fun testAnnotation() = doTest(0, "Bar.class", "Foo.class", "aType")
|
||||
fun testAnnotation() = doTest(0, "Bar.class", "Foo.class")
|
||||
|
||||
fun testInheritedAnnotation() = doTest(1, "Bar.class", "Foo.class", "aType")
|
||||
fun testInheritedAnnotation() = doTest(1, "Bar.class", "Foo.class")
|
||||
|
||||
fun testDeclaredAnnotation() = doTest(0, "Bar.class", "Foo.class")
|
||||
fun testDeclaredAnnotation() = doTest(0, "Foo.class", "Bar.class")
|
||||
|
||||
fun testInheritedDeclaredAnnotation() = doTest(1, "Bar.class", "Foo.class")
|
||||
fun testInheritedDeclaredAnnotation() = doTest(1, "Foo.class", "Bar.class")
|
||||
|
||||
fun testAnnotationsByType() = doTest(0, "Bar.class", "Foo.class")
|
||||
|
||||
fun testDeclaredAnnotationsByType() = doTest(1, "Bar.class", "Foo.class")
|
||||
fun testDeclaredAnnotationsByType() = doTest(0, "Foo.class", "Bar.class")
|
||||
|
||||
fun testConstructor() {
|
||||
addConstructors()
|
||||
doTest(2, "Construct()", "Construct(int)", "Construct(int,java.lang.String)", "Construct(java.lang.String)")
|
||||
doTest(3, "Construct()", "Construct(int n)", "Construct(java.lang.String s)", "Construct(int n,java.lang.String s)")
|
||||
}
|
||||
|
||||
fun testDeclaredConstructor() {
|
||||
addConstructors()
|
||||
doTest(0, "Construct()", "Construct(int)", "Construct(int,java.lang.String)", "Construct(java.lang.String)")
|
||||
doTest(0, "Construct()", "Construct(int n,java.lang.String s)", "Construct(int n)", "Construct(java.lang.String s)")
|
||||
}
|
||||
|
||||
fun testImports() {
|
||||
addMoreClasses()
|
||||
doTest(1, "Bar.class", "Baz.class")
|
||||
}
|
||||
|
||||
fun testVariable() {
|
||||
addMoreClasses()
|
||||
doTest(2, "Bar.class", "Foo.class", "aType")
|
||||
}
|
||||
|
||||
private fun doTest(index: Int, vararg expected: String) {
|
||||
@@ -69,11 +81,7 @@ class JavaReflectionParametersCompletionTest : LightFixtureCompletionTestCase()
|
||||
configureByFile(getTestName(false) + ".java")
|
||||
|
||||
val lookupItems = lookup.items
|
||||
val texts = lookupItems.subList(0, Math.min(lookupItems.size, expected.size)).map {
|
||||
val presentation = LookupElementPresentation()
|
||||
it?.renderElement(presentation)
|
||||
presentation.itemText ?: ""
|
||||
}
|
||||
val texts = lookupItemTexts(lookupItems, expected.size)
|
||||
assertOrderedEquals(texts, *expected)
|
||||
selectItem(lookupItems[index])
|
||||
myFixture.checkResultByFile(getTestName(false) + "_after.java")
|
||||
@@ -82,9 +90,13 @@ class JavaReflectionParametersCompletionTest : LightFixtureCompletionTestCase()
|
||||
private fun addClasses() {
|
||||
myFixture.addClass("package foo.bar; public @interface Foo {}")
|
||||
myFixture.addClass("package foo.bar; public @interface Bar {}")
|
||||
myFixture.addClass("package foo.bar; public @interface Baz {}")
|
||||
myFixture.addClass("package foo.bar; @Foo class Parent {}")
|
||||
myFixture.addClass("package foo.bar; @Bar class Test extends Parent {}")
|
||||
myFixture.addClass("package foo.bar; @Bar class Parent {}")
|
||||
myFixture.addClass("package foo.bar; @Foo class Test extends Parent {}")
|
||||
}
|
||||
|
||||
private fun addMoreClasses() {
|
||||
myFixture.addClass("package foo.baz; public @interface Baz {}")
|
||||
myFixture.addClass("package foo.bar; @foo.baz.Baz class More extends Parent {}")
|
||||
}
|
||||
|
||||
private fun addConstructors() {
|
||||
@@ -96,4 +108,20 @@ public class Construct {
|
||||
public Construct() {}
|
||||
}""")
|
||||
}
|
||||
|
||||
}
|
||||
fun lookupItemTexts(lookupItems: List<LookupElement?>, maxSize: Int): List<String> =
|
||||
lookupItems.subList(0, Math.min(lookupItems.size, maxSize)).map {
|
||||
val obj = it?.`object`
|
||||
when (obj) {
|
||||
is PsiMethod -> {
|
||||
obj.name + obj.parameterList.parameters.map { it.type.canonicalText + " " + it.name }
|
||||
.joinToString(",", prefix = "(", postfix = ")")
|
||||
}
|
||||
else -> {
|
||||
val presentation = LookupElementPresentation()
|
||||
it?.renderElement(presentation)
|
||||
presentation.itemText ?: ""
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+4
-4
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -15,11 +15,11 @@
|
||||
*/
|
||||
package com.intellij.codeInsight.javadoc
|
||||
|
||||
import com.intellij.openapi.util.JDOMUtil
|
||||
import com.intellij.psi.PsiJavaFile
|
||||
import com.intellij.testFramework.assertions.Assertions.assertThat
|
||||
import com.intellij.testFramework.LightProjectDescriptor
|
||||
import com.intellij.testFramework.assertions.Assertions.assertThat
|
||||
import com.intellij.testFramework.fixtures.LightCodeInsightFixtureTestCase
|
||||
import com.intellij.util.loadElement
|
||||
|
||||
class LightJavadocGeneratorTest : LightCodeInsightFixtureTestCase() {
|
||||
override fun getProjectDescriptor(): LightProjectDescriptor = JAVA_9
|
||||
@@ -45,7 +45,7 @@ class LightJavadocGeneratorTest : LightCodeInsightFixtureTestCase() {
|
||||
val file = myFixture.configureByText("module-info.java", text)
|
||||
val module = (file as PsiJavaFile).moduleDeclaration!!
|
||||
val docInfo = JavaDocInfoGeneratorFactory.create(project, module).generateDocInfo(null)!!
|
||||
val body = JDOMUtil.loadDocument(docInfo).rootElement.getChild("body")
|
||||
val body = loadElement(docInfo).getChild("body")
|
||||
assertThat(body).isEqualTo(expected)
|
||||
}
|
||||
}
|
||||
@@ -35,6 +35,7 @@ import com.intellij.psi.codeStyle.CommonCodeStyleSettings
|
||||
import com.intellij.testFramework.LightPlatformCodeInsightTestCase
|
||||
import com.intellij.testFramework.fixtures.CodeInsightTestUtil
|
||||
import com.intellij.testFramework.fixtures.LightCodeInsightFixtureTestCase
|
||||
import com.intellij.util.JdomKt
|
||||
import com.intellij.util.containers.ContainerUtil
|
||||
import com.intellij.util.ui.UIUtil
|
||||
import org.jdom.Element
|
||||
@@ -658,11 +659,11 @@ class Outer {
|
||||
}
|
||||
|
||||
void testDontSaveDefaultContexts() {
|
||||
def defElement = JDOMUtil.loadDocument('''\
|
||||
def defElement = JdomKt.loadElement('''\
|
||||
<context>
|
||||
<option name="JAVA_STATEMENT" value="false"/>
|
||||
<option name="JAVA_CODE" value="true"/>
|
||||
</context>''').rootElement
|
||||
</context>''')
|
||||
def defContext = new TemplateContext()
|
||||
defContext.readTemplateContext(defElement)
|
||||
|
||||
@@ -695,10 +696,10 @@ class Outer {
|
||||
}
|
||||
|
||||
void "test adding new context to Other"() {
|
||||
def defElement = JDOMUtil.loadDocument('''\
|
||||
def defElement = JdomKt.loadElement('''\
|
||||
<context>
|
||||
<option name="OTHER" value="true"/>
|
||||
</context>''').rootElement
|
||||
</context>''')
|
||||
def context = new TemplateContext()
|
||||
context.readTemplateContext(defElement)
|
||||
|
||||
|
||||
@@ -92,6 +92,8 @@ public class MagicConstantInspectionTest extends InspectionTestCase {
|
||||
}
|
||||
|
||||
public void testSimple() throws Exception { doTest(); }
|
||||
|
||||
public void testManyConstantSources() throws Exception { doTest(); }
|
||||
// test that the optimisation for not loading AST works
|
||||
public void testWithLibrary() throws Exception { doTest(); }
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -117,7 +117,7 @@ public class InspectionProfileTest extends LightIdeaTestCase {
|
||||
}
|
||||
|
||||
public void testConvertOldProfile() throws Exception {
|
||||
Element element = JDOMUtil.loadDocument("<inspections version=\"1.0\">\n" +
|
||||
Element element = JdomKt.loadElement("<inspections version=\"1.0\">\n" +
|
||||
" <option name=\"myName\" value=\"ToConvert\" />\n" +
|
||||
" <inspection_tool class=\"JavaDoc\" enabled=\"false\" level=\"WARNING\" enabled_by_default=\"false\">\n" +
|
||||
" <option name=\"TOP_LEVEL_CLASS_OPTIONS\">\n" +
|
||||
@@ -149,7 +149,7 @@ public class InspectionProfileTest extends LightIdeaTestCase {
|
||||
" <option name=\"IGNORE_POINT_TO_ITSELF\" value=\"false\" />\n" +
|
||||
" <option name=\"myAdditionalJavadocTags\" value=\"tag1,tag2 \" />\n" +
|
||||
" </inspection_tool>\n" +
|
||||
"</inspections>").getRootElement();
|
||||
"</inspections>");
|
||||
InspectionProfileImpl profile = createProfile();
|
||||
profile.readExternal(element);
|
||||
profile.getModifiableModel().commit();
|
||||
@@ -296,7 +296,7 @@ public class InspectionProfileTest extends LightIdeaTestCase {
|
||||
InspectionToolsConfigurable.importInspectionProfile(toImportElement, getApplicationProfileManager(), getProject(), null);
|
||||
|
||||
//check merged
|
||||
Element mergedElement = JDOMUtil.loadDocument(mergedText).getRootElement();
|
||||
Element mergedElement = JdomKt.loadElement(mergedText);
|
||||
profile = createProfile(new InspectionProfileImpl("foo"));
|
||||
profile.readExternal(mergedElement);
|
||||
profile.getModifiableModel().commit();
|
||||
@@ -307,7 +307,7 @@ public class InspectionProfileTest extends LightIdeaTestCase {
|
||||
|
||||
public void testStoredMemberVisibility() throws Exception {
|
||||
InspectionProfileImpl profile = createProfile(new InspectionProfileImpl("foo"));
|
||||
profile.readExternal(JDOMUtil.loadDocument("<profile version=\"1.0\">\n" +
|
||||
profile.readExternal(JdomKt.loadElement("<profile version=\"1.0\">\n" +
|
||||
" <inspection_tool class=\"unused\" enabled=\"true\" level=\"WARNING\" enabled_by_default=\"true\">\n" +
|
||||
" <option name=\"LOCAL_VARIABLE\" value=\"true\" />\n" +
|
||||
" <option name=\"FIELD\" value=\"true\" />\n" +
|
||||
@@ -320,7 +320,7 @@ public class InspectionProfileTest extends LightIdeaTestCase {
|
||||
" <option name=\"ADD_SERVLET_TO_ENTRIES\" value=\"true\" />\n" +
|
||||
" <option name=\"ADD_NONJAVA_TO_ENTRIES\" value=\"false\" />\n" +
|
||||
" </inspection_tool>\n" +
|
||||
"</profile>").getRootElement());
|
||||
"</profile>"));
|
||||
profile.modifyProfile(it -> {
|
||||
InspectionToolWrapper toolWrapper = it.getInspectionTool("unused", getProject());
|
||||
UnusedDeclarationInspectionBase tool = (UnusedDeclarationInspectionBase)toolWrapper.getTool();
|
||||
@@ -481,7 +481,7 @@ public class InspectionProfileTest extends LightIdeaTestCase {
|
||||
}
|
||||
|
||||
private static void checkMergedNoChanges(String initialText) throws Exception {
|
||||
final Element element = JDOMUtil.loadDocument(initialText).getRootElement();
|
||||
final Element element = JdomKt.loadElement(initialText);
|
||||
InspectionProfileImpl profile = createProfile(new InspectionProfileImpl("foo"));
|
||||
profile.readExternal(element);
|
||||
profile.getModifiableModel().commit();
|
||||
@@ -615,13 +615,13 @@ public class InspectionProfileTest extends LightIdeaTestCase {
|
||||
|
||||
public void testInspectionInitializationForSerialization() throws Exception {
|
||||
InspectionProfileImpl foo = new InspectionProfileImpl("foo");
|
||||
foo.readExternal(JDOMUtil.loadDocument("<profile version=\"1.0\">\n" +
|
||||
foo.readExternal(JdomKt.loadElement("<profile version=\"1.0\">\n" +
|
||||
" <option name=\"myName\" value=\"idea.default\" />\n" +
|
||||
" <inspection_tool class=\"AbstractMethodCallInConstructor\" enabled=\"true\" level=\"WARNING\" enabled_by_default=\"true\" />\n" +
|
||||
" <inspection_tool class=\"AssignmentToForLoopParameter\" enabled=\"true\" level=\"WARNING\" enabled_by_default=\"true\">\n" +
|
||||
" <option name=\"m_checkForeachParameters\" value=\"false\" />\n" +
|
||||
" </inspection_tool>\n" +
|
||||
"</profile>").getRootElement());
|
||||
"</profile>"));
|
||||
foo.initInspectionTools(getProject());
|
||||
assertEquals(1, countInitializedTools(foo));
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -21,11 +21,11 @@ import com.intellij.execution.configurations.UnknownConfigurationType;
|
||||
import com.intellij.execution.junit.JUnitConfigurationType;
|
||||
import com.intellij.ide.util.PropertiesComponent;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.util.JDOMUtil;
|
||||
import com.intellij.openapi.util.Trinity;
|
||||
import com.intellij.testFramework.LightIdeaTestCase;
|
||||
import com.intellij.ui.RowsDnDSupport;
|
||||
import com.intellij.ui.treeStructure.Tree;
|
||||
import com.intellij.util.JdomKt;
|
||||
import org.jdom.Element;
|
||||
|
||||
import javax.swing.tree.DefaultMutableTreeNode;
|
||||
@@ -66,7 +66,7 @@ public class RunConfigurableTest extends LightIdeaTestCase {
|
||||
@Override
|
||||
protected void setUp() throws Exception {
|
||||
super.setUp();
|
||||
myConfigurable = new MockRunConfigurable(createRunManager(JDOMUtil.loadDocument(FOLDERS_CONFIGURATION).getRootElement()));
|
||||
myConfigurable = new MockRunConfigurable(createRunManager(JdomKt.loadElement(FOLDERS_CONFIGURATION)));
|
||||
myTree = myConfigurable.myTree;
|
||||
myRoot = myConfigurable.myRoot;
|
||||
myModel = myConfigurable.myTreeModel;
|
||||
|
||||
@@ -282,6 +282,18 @@ public class GotoImplementationHandlerTest extends JavaCodeInsightFixtureTestCas
|
||||
assertEquals(1, impls.length);
|
||||
}
|
||||
|
||||
public void testPrivateClassInheritors() {
|
||||
PsiFile file = myFixture.addFileToProject("Foo.java",
|
||||
"class C {\n" +
|
||||
" private static class Pr<caret>ivate {}\n" +
|
||||
" public static class Public extends Private {}" +
|
||||
"}");
|
||||
myFixture.addClass("class Inheritor extends C.Public {}");
|
||||
myFixture.configureFromExistingVirtualFile(file.getVirtualFile());
|
||||
|
||||
assertSize(2, getTargets(file));
|
||||
}
|
||||
|
||||
private PsiElement[] getTargets(PsiFile file) {
|
||||
GotoTargetHandler.GotoData gotoData = CodeInsightTestUtil.gotoImplementation(myFixture.getEditor(), file);
|
||||
assertNotNull(gotoData);
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -16,10 +16,10 @@
|
||||
package com.intellij.openapi.wm.impl;
|
||||
|
||||
import com.intellij.openapi.extensions.Extensions;
|
||||
import com.intellij.openapi.util.JDOMUtil;
|
||||
import com.intellij.openapi.wm.ToolWindowEP;
|
||||
import com.intellij.openapi.wm.ToolWindowId;
|
||||
import com.intellij.usageView.impl.UsageViewManagerImpl;
|
||||
import com.intellij.util.JdomKt;
|
||||
|
||||
import java.util.Arrays;
|
||||
|
||||
@@ -41,7 +41,7 @@ public class HiddenSidebarButtonTest extends ToolWindowManagerTestCase {
|
||||
|
||||
public void testHiddenButton() throws Exception {
|
||||
DesktopLayout layout = myManager.getLayout();
|
||||
layout.readExternal(JDOMUtil.loadDocument(LAYOUT).getRootElement());
|
||||
layout.readExternal(JdomKt.loadElement(LAYOUT));
|
||||
for (String ID : IDS) {
|
||||
assertFalse(layout.isToolWindowRegistered(ID));
|
||||
assertTrue(layout.isToolWindowUnregistered(ID));
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -16,8 +16,8 @@
|
||||
package com.intellij.run
|
||||
|
||||
import com.intellij.application.options.PathMacrosCollector
|
||||
import com.intellij.openapi.util.JDOMUtil
|
||||
import com.intellij.testFramework.fixtures.LightCodeInsightFixtureTestCase
|
||||
import com.intellij.util.JdomKt
|
||||
|
||||
class JavaPathMacroCollectorTest extends LightCodeInsightFixtureTestCase {
|
||||
void testJunitConfiguration() {
|
||||
@@ -56,8 +56,7 @@ class JavaPathMacroCollectorTest extends LightCodeInsightFixtureTestCase {
|
||||
</recent_temporary>
|
||||
</component>
|
||||
'''
|
||||
def element = JDOMUtil.loadDocument(text).rootElement
|
||||
assert PathMacrosCollector.getMacroNames(element).empty
|
||||
assert PathMacrosCollector.getMacroNames(JdomKt.loadElement(text)).empty
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -1,9 +1,11 @@
|
||||
package com.jetbrains.jsonSchema;
|
||||
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.application.ModalityState;
|
||||
import com.intellij.openapi.components.*;
|
||||
import com.intellij.openapi.fileTypes.ex.FileTypeManagerEx;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.util.Condition;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.util.xmlb.annotations.Transient;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -74,7 +76,7 @@ public class JsonSchemaMappingsProjectConfiguration extends JsonSchemaMappingsCo
|
||||
private void recalculateSchemaFiles() {
|
||||
ApplicationManager.getApplication().invokeLater(() -> {
|
||||
ApplicationManager.getApplication().runWriteAction(() -> FileTypeManagerEx.getInstanceEx().fireFileTypesChanged());
|
||||
}, o -> !myProject.isDisposed());
|
||||
}, ModalityState.NON_MODAL, myProject == null ? Condition.FALSE : myProject.getDisposed());
|
||||
mySchemaFiles.clear();
|
||||
if (myProject == null || myProject.getBaseDir() == null) return;
|
||||
|
||||
|
||||
+10
-9
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -20,17 +20,19 @@ import com.intellij.codeInspection.ex.InspectionProfileImpl;
|
||||
import com.intellij.lang.annotation.HighlightSeverity;
|
||||
import com.intellij.openapi.application.PathManager;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.util.JDOMUtil;
|
||||
import com.intellij.openapi.util.io.FileUtil;
|
||||
import com.intellij.profile.codeInspection.InspectionProfileManager;
|
||||
import com.intellij.util.JdomKt;
|
||||
import com.intellij.util.io.PathKt;
|
||||
import org.jdom.Element;
|
||||
import org.jdom.JDOMException;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.FileOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Path;
|
||||
import java.nio.file.Paths;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
@@ -93,20 +95,19 @@ public class InspectionProfileConvertor {
|
||||
}
|
||||
|
||||
private static void renameOldDefaultsProfile() {
|
||||
String directoryPath = PathManager.getConfigPath() + File.separator + InspectionProfileManager.INSPECTION_DIR;
|
||||
File profileDirectory = new File(directoryPath);
|
||||
if (!profileDirectory.exists()) {
|
||||
Path directoryPath = Paths.get(PathManager.getConfigPath(), InspectionProfileManager.INSPECTION_DIR);
|
||||
if (!PathKt.exists(directoryPath)) {
|
||||
return;
|
||||
}
|
||||
|
||||
File[] files = profileDirectory.listFiles(pathname -> pathname.getPath().endsWith(File.separator + DEFAULT_XML));
|
||||
File[] files = directoryPath.toFile().listFiles(pathname -> pathname.getPath().endsWith(File.separator + DEFAULT_XML));
|
||||
if (files == null || files.length != 1 || !files[0].isFile() || files[0].length() == 0) {
|
||||
return;
|
||||
}
|
||||
try {
|
||||
Element root = JDOMUtil.load(files[0]);
|
||||
Element root = JdomKt.loadElement(files[0].toPath());
|
||||
if (root.getAttributeValue(VERSION_ATT) == null){
|
||||
JDOMUtil.writeParent(root, new FileOutputStream(new File(profileDirectory, OLD_DEFAUL_PROFILE + XML_EXTENSION)), "\n");
|
||||
JdomKt.write(root, directoryPath.resolve(OLD_DEFAUL_PROFILE + XML_EXTENSION));
|
||||
FileUtil.delete(files[0]);
|
||||
}
|
||||
}
|
||||
|
||||
+3
-3
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -18,8 +18,8 @@ package com.intellij.profile.codeInspection;
|
||||
import com.intellij.codeInspection.ex.InspectionProfileImpl;
|
||||
import com.intellij.codeInspection.ex.InspectionToolRegistrar;
|
||||
import com.intellij.openapi.util.InvalidDataException;
|
||||
import com.intellij.openapi.util.JDOMUtil;
|
||||
import com.intellij.openapi.util.io.FileUtil;
|
||||
import com.intellij.util.JdomKt;
|
||||
import org.jdom.Element;
|
||||
import org.jdom.JDOMException;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -46,7 +46,7 @@ public class InspectionProfileLoadUtil {
|
||||
public static InspectionProfileImpl load(@NotNull File file,
|
||||
@NotNull InspectionToolRegistrar registrar,
|
||||
@NotNull InspectionProfileManager profileManager) throws JDOMException, IOException, InvalidDataException {
|
||||
Element element = JDOMUtil.load(file);
|
||||
Element element = JdomKt.loadElement(file.getPath());
|
||||
InspectionProfileImpl profile = new InspectionProfileImpl(getProfileName(file, element), registrar,
|
||||
(BaseInspectionProfileManager)profileManager);
|
||||
final Element profileElement = element.getChild("profile");
|
||||
|
||||
@@ -50,7 +50,6 @@ public class BootstrapClassLoaderUtil extends ClassUtilCore {
|
||||
@NotNull
|
||||
public static ClassLoader initClassLoader(boolean updatePlugins) throws MalformedURLException {
|
||||
PathManager.loadProperties();
|
||||
PathManager.patchProperties();
|
||||
|
||||
Collection<URL> classpath = new LinkedHashSet<URL>();
|
||||
addParentClasspath(classpath, false);
|
||||
|
||||
+21
-12
@@ -18,6 +18,7 @@ package org.jetbrains.intellij.build.impl
|
||||
import com.intellij.openapi.util.MultiValuesMap
|
||||
import com.intellij.openapi.util.io.FileUtil
|
||||
import org.apache.tools.ant.types.FileSet
|
||||
import org.apache.tools.ant.types.resources.FileProvider
|
||||
import org.jetbrains.intellij.build.BuildContext
|
||||
import org.jetbrains.intellij.build.BuildOptions
|
||||
import org.jetbrains.intellij.build.BuildTasks
|
||||
@@ -32,7 +33,7 @@ import org.jetbrains.jps.util.JpsPathUtil
|
||||
|
||||
/**
|
||||
* Assembles output of modules to platform JARs (in {@link org.jetbrains.intellij.build.BuildPaths#distAll distAll}/lib directory),
|
||||
* bunlded plugins' JARs (in {@link org.jetbrains.intellij.build.BuildPaths#distAll distAll}/plugins directory) and zip archives with
|
||||
* bundled plugins' JARs (in {@link org.jetbrains.intellij.build.BuildPaths#distAll distAll}/plugins directory) and zip archives with
|
||||
* non-bundled plugins (in {@link org.jetbrains.intellij.build.BuildPaths#artifacts artifacts}/plugins directory).
|
||||
*
|
||||
* @author nik
|
||||
@@ -293,27 +294,31 @@ class DistributionJARsBuilder {
|
||||
def enabledModulesSet = buildContext.productProperties.productLayout.enabledPluginModules
|
||||
pluginsToInclude.each { plugin ->
|
||||
def actualModuleJars = plugin.getActualModules(enabledModulesSet)
|
||||
checkOutputOfPluginModules(plugin.mainModule, actualModuleJars.values())
|
||||
checkOutputOfPluginModules(plugin.mainModule, actualModuleJars.values(), plugin.moduleExcludes)
|
||||
buildByLayout(layoutBuilder, plugin, "$targetDirectory/$plugin.directoryName", actualModuleJars)
|
||||
}
|
||||
}
|
||||
|
||||
private void checkOutputOfPluginModules(String mainPluginModule, Collection<String> moduleNames) {
|
||||
def modulesWithPluginXml = moduleNames.findAll { containsFileInOutput(it, "META-INF/plugin.xml") }
|
||||
private void checkOutputOfPluginModules(String mainPluginModule, Collection<String> moduleNames, MultiValuesMap<String, String> moduleExcludes) {
|
||||
def modulesWithPluginXml = moduleNames.findAll { containsFileInOutput(it, "META-INF/plugin.xml", moduleExcludes.get(it)) }
|
||||
if (modulesWithPluginXml.size() > 1) {
|
||||
buildContext.messages.error("Multiple modules (${modulesWithPluginXml.join(", ")}) from '$mainPluginModule' plugin contain plugin.xml files so the plugin won't work properly")
|
||||
}
|
||||
|
||||
moduleNames.each {
|
||||
if (containsFileInOutput(it, "com/intellij/uiDesigner/core/GridLayoutManager.class")) {
|
||||
if (containsFileInOutput(it, "com/intellij/uiDesigner/core/GridLayoutManager.class", moduleExcludes.get(it))) {
|
||||
buildContext.messages.error("Runtime classes of GUI designer must not be packaged to '$mainPluginModule' plugin, because they are included into a platform JAR. " +
|
||||
"Make sure that 'Automatically copy form runtime classes to the output directory' is disabled in Settings | Editor | GUI Designer.")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private boolean containsFileInOutput(String moduleName, String filePath) {
|
||||
return new File(buildContext.projectBuilder.getModuleOutput(buildContext.findRequiredModule(moduleName), false), filePath).exists()
|
||||
private boolean containsFileInOutput(String moduleName, String filePath, Collection<String> excludes) {
|
||||
def moduleOutput = new File(buildContext.projectBuilder.getModuleOutput(buildContext.findRequiredModule(moduleName), false))
|
||||
def fileInOutput = new File(moduleOutput, filePath)
|
||||
return fileInOutput.exists() && (excludes == null || excludes.every {
|
||||
createFileSet(it, moduleOutput).iterator().every { !(it instanceof FileProvider && FileUtil.filesEqual(it.file, fileInOutput))}
|
||||
})
|
||||
}
|
||||
|
||||
private void buildByLayout(LayoutBuilder layoutBuilder, BaseLayout layout, String targetDirectory, MultiValuesMap<String, String> moduleJars) {
|
||||
@@ -419,22 +424,26 @@ class DistributionJARsBuilder {
|
||||
moduleExcludes.entrySet().each { entry ->
|
||||
String module = entry.key
|
||||
entry.value.each { pattern ->
|
||||
def fileSet = new FileSet()
|
||||
fileSet.setProject(buildContext.ant.antProject)
|
||||
def moduleOutput = new File(buildContext.projectBuilder.getModuleOutput(buildContext.findRequiredModule(module), false))
|
||||
if (!moduleOutput.exists()) {
|
||||
buildContext.messages.error("There are excludes defined for module '$module', but the module wasn't compiled; " +
|
||||
"most probably it means that '$module' isn't include into the product distribution so it makes no sense to define excludes for it.")
|
||||
}
|
||||
fileSet.setDir(moduleOutput)
|
||||
fileSet.createInclude().setName(pattern)
|
||||
if (fileSet.size() == 0) {
|
||||
if (createFileSet(pattern, moduleOutput).size() == 0) {
|
||||
buildContext.messages.error("Incorrect exludes for module '$module': nothing matches to $pattern in the module output")
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private FileSet createFileSet(String pattern, File baseDir) {
|
||||
def fileSet = new FileSet()
|
||||
fileSet.setProject(buildContext.ant.antProject)
|
||||
fileSet.setDir(baseDir)
|
||||
fileSet.createInclude().setName(pattern)
|
||||
return fileSet
|
||||
}
|
||||
|
||||
static String basePath(BuildContext buildContext, String moduleName) {
|
||||
JpsPathUtil.urlToPath(buildContext.findRequiredModule(moduleName).contentRootsList.urls.first())
|
||||
}
|
||||
|
||||
@@ -132,7 +132,8 @@ open class FileBasedStorage(file: Path,
|
||||
else {
|
||||
val charBuffer = StandardCharsets.UTF_8.decode(ByteBuffer.wrap(file.contentsToByteArray()))
|
||||
lineSeparator = detectLineSeparators(charBuffer, if (isUseXmlProlog) null else LineSeparator.LF)
|
||||
return JDOMUtil.loadDocument(charBuffer).detachRootElement()
|
||||
@Suppress("DEPRECATION")
|
||||
return loadElement(charBuffer)
|
||||
}
|
||||
return null
|
||||
}
|
||||
@@ -242,7 +243,7 @@ private fun doWrite(requestor: Any, file: VirtualFile, content: Any, lineSeparat
|
||||
out.write(lineSeparator.separatorBytes)
|
||||
}
|
||||
if (content is Element) {
|
||||
JDOMUtil.writeParent(content, out, lineSeparator.separatorString)
|
||||
JDOMUtil.write(content, out, lineSeparator.separatorString)
|
||||
}
|
||||
else {
|
||||
(content as BufferExposingByteArrayOutputStream).writeTo(out)
|
||||
@@ -253,7 +254,7 @@ private fun doWrite(requestor: Any, file: VirtualFile, content: Any, lineSeparat
|
||||
|
||||
internal fun Parent.toBufferExposingByteArray(lineSeparator: String = "\n"): BufferExposingByteArrayOutputStream {
|
||||
val out = BufferExposingByteArrayOutputStream(512)
|
||||
JDOMUtil.writeParent(this, out, lineSeparator)
|
||||
JDOMUtil.write(this, out, lineSeparator)
|
||||
return out
|
||||
}
|
||||
|
||||
|
||||
@@ -129,7 +129,7 @@ abstract class ProjectStoreBase(override final val project: ProjectImpl) : Compo
|
||||
wrapper.addContent(profile)
|
||||
val path = Paths.get(storageManager.expandMacro(PROJECT_CONFIG_DIR), if (isInspection) "inspectionProfiles" else "copyright",
|
||||
"${FileUtil.sanitizeFileName(schemeName, true)}.xml")
|
||||
JDOMUtil.writeParent(wrapper, path.outputStream(), "\n")
|
||||
JDOMUtil.write(wrapper, path.outputStream(), "\n")
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -58,7 +58,7 @@ fun getNewByteIfDiffers(key: String, newState: Any, oldState: ByteArray): ByteAr
|
||||
|
||||
val logChangedComponents = SystemProperties.getBooleanProperty("idea.log.changed.components", false)
|
||||
if (ApplicationManager.getApplication().isUnitTestMode || logChangedComponents ) {
|
||||
fun stateToString(state: Any) = JDOMUtil.writeParent(state as? Element ?: unarchiveState(state as ByteArray), "\n")
|
||||
fun stateToString(state: Any) = JDOMUtil.write(state as? Element ?: unarchiveState(state as ByteArray), "\n")
|
||||
|
||||
val before = stateToString(oldState)
|
||||
val after = stateToString(newState)
|
||||
|
||||
@@ -634,7 +634,7 @@ internal class XmlSerializerTest {
|
||||
|
||||
private fun checkSmartSerialization(bean: Bean2, serialized: String) {
|
||||
val serializer = SmartSerializer()
|
||||
serializer.readExternal(bean, JDOMUtil.loadDocument(serialized).rootElement)
|
||||
serializer.readExternal(bean, JDOMUtil.load(serialized))
|
||||
val serializedState = Element("Bean2")
|
||||
serializer.writeExternal(bean, serializedState)
|
||||
assertThat(JDOMUtil.writeElement(serializedState)).isEqualTo(serialized)
|
||||
|
||||
@@ -204,6 +204,7 @@ public class TextMergeViewer implements MergeTool.MergeViewer {
|
||||
|
||||
myTextDiffProvider = new TextDiffProviderBase(getTextSettings(),
|
||||
myInnerDiffWorker::onSettingsChanged,
|
||||
this,
|
||||
ar(IgnorePolicy.DEFAULT),
|
||||
ar(HighlightPolicy.BY_LINE, HighlightPolicy.BY_WORD));
|
||||
|
||||
|
||||
@@ -122,7 +122,7 @@ public class UnifiedDiffViewer extends ListenerDiffViewerBase {
|
||||
myEditorSettingsAction = new SetEditorSettingsAction(getTextSettings(), getEditors());
|
||||
myEditorSettingsAction.applyDefaults();
|
||||
|
||||
myTextDiffProvider = DiffUtil.createNoIgnoreTextDiffProvider(getProject(), getRequest(), getTextSettings(), this::rediff);
|
||||
myTextDiffProvider = DiffUtil.createNoIgnoreTextDiffProvider(getProject(), getRequest(), getTextSettings(), this::rediff, this);
|
||||
|
||||
new MyOpenInEditorWithMouseAction().install(getEditors());
|
||||
|
||||
|
||||
@@ -80,7 +80,7 @@ public class SimpleDiffViewer extends TwosideTextDiffViewer {
|
||||
|
||||
myModifierProvider = new ModifierProvider();
|
||||
|
||||
myTextDiffProvider = DiffUtil.createTextDiffProvider(getProject(), getRequest(), getTextSettings(), this::rediff);
|
||||
myTextDiffProvider = DiffUtil.createTextDiffProvider(getProject(), getRequest(), getTextSettings(), this::rediff, this);
|
||||
|
||||
DiffUtil.registerAction(new ReplaceSelectedChangesAction(Side.LEFT, true), myPanel);
|
||||
DiffUtil.registerAction(new AppendSelectedChangesAction(Side.LEFT, true), myPanel);
|
||||
|
||||
@@ -56,7 +56,7 @@ public class SimpleOnesideDiffViewer extends OnesideTextDiffViewer {
|
||||
public SimpleOnesideDiffViewer(@NotNull DiffContext context, @NotNull DiffRequest request) {
|
||||
super(context, (ContentDiffRequest)request);
|
||||
|
||||
myTextDiffProvider = DiffUtil.createTextDiffProvider(getProject(), getRequest(), getTextSettings(), this::rediff);
|
||||
myTextDiffProvider = DiffUtil.createTextDiffProvider(getProject(), getRequest(), getTextSettings(), this::rediff, this);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
+1
-1
@@ -49,7 +49,7 @@ public class SimpleThreesideDiffViewer extends ThreesideTextDiffViewerEx {
|
||||
public SimpleThreesideDiffViewer(@NotNull DiffContext context, @NotNull DiffRequest request) {
|
||||
super(context, (ContentDiffRequest)request);
|
||||
|
||||
myTextDiffProvider = new SimpleThreesideTextDiffProvider(getTextSettings(), this::rediff);
|
||||
myTextDiffProvider = new SimpleThreesideTextDiffProvider(getTextSettings(), this::rediff, this);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
|
||||
@@ -17,12 +17,15 @@ package com.intellij.diff.tools.util.base
|
||||
|
||||
import com.intellij.diff.util.DiffPlaces
|
||||
import com.intellij.diff.util.DiffUtil
|
||||
import com.intellij.openapi.Disposable
|
||||
import com.intellij.openapi.components.PersistentStateComponent
|
||||
import com.intellij.openapi.components.State
|
||||
import com.intellij.openapi.components.Storage
|
||||
import com.intellij.openapi.components.service
|
||||
import com.intellij.openapi.util.Key
|
||||
import com.intellij.util.EventDispatcher
|
||||
import com.intellij.util.xmlb.annotations.MapAnnotation
|
||||
import com.intellij.util.xmlb.annotations.Transient
|
||||
import java.util.*
|
||||
|
||||
@State(
|
||||
@@ -61,12 +64,19 @@ class TextDiffSettingsHolder : PersistentStateComponent<TextDiffSettingsHolder.S
|
||||
|
||||
// Fragments settings
|
||||
var EXPAND_BY_DEFAULT: Boolean = true
|
||||
)
|
||||
) {
|
||||
@Transient
|
||||
val eventDispatcher: EventDispatcher<TextDiffSettings.Listener> = EventDispatcher.create(TextDiffSettings.Listener::class.java)
|
||||
}
|
||||
|
||||
class TextDiffSettings internal constructor(private val SHARED_SETTINGS: SharedSettings,
|
||||
private val PLACE_SETTINGS: PlaceSettings) {
|
||||
constructor() : this(SharedSettings(), PlaceSettings())
|
||||
|
||||
fun addListener(listener: Listener, disposable: Disposable) {
|
||||
PLACE_SETTINGS.eventDispatcher.addListener(listener, disposable)
|
||||
}
|
||||
|
||||
// Presentation settings
|
||||
|
||||
var isEnableSyncScroll: Boolean
|
||||
@@ -77,11 +87,13 @@ class TextDiffSettingsHolder : PersistentStateComponent<TextDiffSettingsHolder.S
|
||||
|
||||
var highlightPolicy: HighlightPolicy
|
||||
get() = PLACE_SETTINGS.HIGHLIGHT_POLICY
|
||||
set(value) { PLACE_SETTINGS.HIGHLIGHT_POLICY = value }
|
||||
set(value) { PLACE_SETTINGS.HIGHLIGHT_POLICY = value
|
||||
PLACE_SETTINGS.eventDispatcher.multicaster.highlightPolicyChanged() }
|
||||
|
||||
var ignorePolicy: IgnorePolicy
|
||||
get() = PLACE_SETTINGS.IGNORE_POLICY
|
||||
set(value) { PLACE_SETTINGS.IGNORE_POLICY = value }
|
||||
set(value) { PLACE_SETTINGS.IGNORE_POLICY = value
|
||||
PLACE_SETTINGS.eventDispatcher.multicaster.ignorePolicyChanged() }
|
||||
|
||||
//
|
||||
// Merge
|
||||
@@ -139,6 +151,11 @@ class TextDiffSettingsHolder : PersistentStateComponent<TextDiffSettingsHolder.S
|
||||
@JvmStatic fun getSettings(): TextDiffSettings = getSettings(null)
|
||||
@JvmStatic fun getSettings(place: String?): TextDiffSettings = service<TextDiffSettingsHolder>().getSettings(place)
|
||||
}
|
||||
|
||||
interface Listener : EventListener {
|
||||
fun highlightPolicyChanged() {}
|
||||
fun ignorePolicyChanged() {}
|
||||
}
|
||||
}
|
||||
|
||||
fun getSettings(place: String?): TextDiffSettings {
|
||||
|
||||
@@ -261,14 +261,11 @@ public class TextDiffViewerUtil {
|
||||
|
||||
public static class HighlightPolicySettingAction extends EnumPolicySettingAction<HighlightPolicy> {
|
||||
@NotNull protected final TextDiffSettings mySettings;
|
||||
@NotNull private final Runnable myRediffRunnable;
|
||||
|
||||
public HighlightPolicySettingAction(@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull HighlightPolicy... policies) {
|
||||
super(policies);
|
||||
mySettings = settings;
|
||||
myRediffRunnable = rediff;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -276,7 +273,6 @@ public class TextDiffViewerUtil {
|
||||
if (getValue() == option) return;
|
||||
UsageTrigger.trigger("diff.TextDiffSettings.HighlightPolicy." + option.name());
|
||||
mySettings.setHighlightPolicy(option);
|
||||
myRediffRunnable.run();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@@ -306,14 +302,11 @@ public class TextDiffViewerUtil {
|
||||
|
||||
public static class IgnorePolicySettingAction extends EnumPolicySettingAction<IgnorePolicy> {
|
||||
@NotNull protected final TextDiffSettings mySettings;
|
||||
@NotNull private final Runnable myRediffRunnable;
|
||||
|
||||
public IgnorePolicySettingAction(@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull IgnorePolicy... policies) {
|
||||
super(policies);
|
||||
mySettings = settings;
|
||||
myRediffRunnable = rediff;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -321,7 +314,6 @@ public class TextDiffViewerUtil {
|
||||
if (getValue() == option) return;
|
||||
UsageTrigger.trigger("diff.TextDiffSettings.IgnorePolicy." + option.name());
|
||||
mySettings.setIgnorePolicy(option);
|
||||
myRediffRunnable.run();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
|
||||
+17
-13
@@ -21,7 +21,8 @@ import com.intellij.diff.fragments.LineFragment;
|
||||
import com.intellij.diff.tools.util.base.HighlightPolicy;
|
||||
import com.intellij.diff.tools.util.base.IgnorePolicy;
|
||||
import com.intellij.diff.tools.util.base.TextDiffSettingsHolder.TextDiffSettings;
|
||||
import com.intellij.diff.util.DiffUserDataKeysEx;
|
||||
import com.intellij.diff.util.DiffUserDataKeysEx.DiffComputer;
|
||||
import com.intellij.openapi.Disposable;
|
||||
import com.intellij.openapi.progress.ProgressIndicator;
|
||||
import com.intellij.util.ArrayUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -32,7 +33,7 @@ import static com.intellij.diff.tools.util.base.HighlightPolicy.*;
|
||||
import static com.intellij.diff.tools.util.base.IgnorePolicy.*;
|
||||
|
||||
public class SimpleTextDiffProvider extends TwosideTextDiffProviderBase implements TwosideTextDiffProvider {
|
||||
static final DiffUserDataKeysEx.DiffComputer DEFAULT_COMPUTER = (text1, text2, policy, innerChanges, indicator) -> {
|
||||
static final DiffComputer DEFAULT_COMPUTER = (text1, text2, policy, innerChanges, indicator) -> {
|
||||
if (innerChanges) {
|
||||
return ComparisonManager.getInstance().compareLinesInner(text1, text2, policy, indicator);
|
||||
}
|
||||
@@ -44,25 +45,28 @@ public class SimpleTextDiffProvider extends TwosideTextDiffProviderBase implemen
|
||||
private static final IgnorePolicy[] IGNORE_POLICIES = {DEFAULT, TRIM_WHITESPACES, IGNORE_WHITESPACES, IGNORE_WHITESPACES_CHUNKS};
|
||||
private static final HighlightPolicy[] HIGHLIGHT_POLICIES = {BY_LINE, BY_WORD, BY_WORD_SPLIT, DO_NOT_HIGHLIGHT};
|
||||
|
||||
@NotNull private final DiffUserDataKeysEx.DiffComputer myDiffComputer;
|
||||
@NotNull private final DiffComputer myDiffComputer;
|
||||
|
||||
public SimpleTextDiffProvider(@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff) {
|
||||
this(settings, rediff, DEFAULT_COMPUTER);
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull Disposable disposable) {
|
||||
this(settings, rediff, disposable, DEFAULT_COMPUTER);
|
||||
}
|
||||
|
||||
public SimpleTextDiffProvider(@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull DiffUserDataKeysEx.DiffComputer diffComputer) {
|
||||
this(settings, rediff, diffComputer, IGNORE_POLICIES, HIGHLIGHT_POLICIES);
|
||||
@NotNull Disposable disposable,
|
||||
@NotNull DiffComputer diffComputer) {
|
||||
this(settings, rediff, disposable, diffComputer, IGNORE_POLICIES, HIGHLIGHT_POLICIES);
|
||||
}
|
||||
|
||||
private SimpleTextDiffProvider(@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull DiffUserDataKeysEx.DiffComputer diffComputer,
|
||||
@NotNull Disposable disposable,
|
||||
@NotNull DiffComputer diffComputer,
|
||||
@NotNull IgnorePolicy[] ignorePolicies,
|
||||
@NotNull HighlightPolicy[] highlightPolicies) {
|
||||
super(settings, rediff, ignorePolicies, highlightPolicies);
|
||||
super(settings, rediff, disposable, ignorePolicies, highlightPolicies);
|
||||
myDiffComputer = diffComputer;
|
||||
}
|
||||
|
||||
@@ -79,12 +83,12 @@ public class SimpleTextDiffProvider extends TwosideTextDiffProviderBase implemen
|
||||
|
||||
|
||||
public static class NoIgnore extends SimpleTextDiffProvider implements TwosideTextDiffProvider.NoIgnore {
|
||||
public NoIgnore(@NotNull TextDiffSettings settings, @NotNull Runnable rediff) {
|
||||
this(settings, rediff, DEFAULT_COMPUTER);
|
||||
public NoIgnore(@NotNull TextDiffSettings settings, @NotNull Runnable rediff, @NotNull Disposable disposable) {
|
||||
this(settings, rediff, disposable, DEFAULT_COMPUTER);
|
||||
}
|
||||
|
||||
public NoIgnore(@NotNull TextDiffSettings settings, @NotNull Runnable rediff, @NotNull DiffUserDataKeysEx.DiffComputer diffComputer) {
|
||||
super(settings, rediff, diffComputer, IGNORE_POLICIES, ArrayUtil.remove(HIGHLIGHT_POLICIES, DO_NOT_HIGHLIGHT));
|
||||
public NoIgnore(@NotNull TextDiffSettings settings, @NotNull Runnable rediff, @NotNull Disposable disposable, @NotNull DiffComputer diffComputer) {
|
||||
super(settings, rediff, disposable, diffComputer, IGNORE_POLICIES, ArrayUtil.remove(HIGHLIGHT_POLICIES, DO_NOT_HIGHLIGHT));
|
||||
}
|
||||
|
||||
@NotNull
|
||||
|
||||
+4
-2
@@ -24,6 +24,7 @@ import com.intellij.diff.tools.util.base.TextDiffSettingsHolder.TextDiffSettings
|
||||
import com.intellij.diff.util.DiffUtil;
|
||||
import com.intellij.diff.util.MergeConflictType;
|
||||
import com.intellij.diff.util.ThreeSide;
|
||||
import com.intellij.openapi.Disposable;
|
||||
import com.intellij.openapi.progress.ProgressIndicator;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -40,8 +41,9 @@ public class SimpleThreesideTextDiffProvider extends TextDiffProviderBase {
|
||||
private static final HighlightPolicy[] HIGHLIGHT_POLICIES = {BY_LINE, BY_WORD};
|
||||
|
||||
public SimpleThreesideTextDiffProvider(@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff) {
|
||||
super(settings, rediff, IGNORE_POLICIES, HIGHLIGHT_POLICIES);
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull Disposable disposable) {
|
||||
super(settings, rediff, disposable, IGNORE_POLICIES, HIGHLIGHT_POLICIES);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
|
||||
+13
-7
@@ -25,6 +25,7 @@ import com.intellij.diff.tools.util.base.HighlightPolicy;
|
||||
import com.intellij.diff.tools.util.base.IgnorePolicy;
|
||||
import com.intellij.diff.tools.util.base.TextDiffSettingsHolder.TextDiffSettings;
|
||||
import com.intellij.diff.util.Side;
|
||||
import com.intellij.openapi.Disposable;
|
||||
import com.intellij.openapi.progress.ProgressIndicator;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
@@ -51,24 +52,26 @@ public class SmartTextDiffProvider extends TwosideTextDiffProviderBase implement
|
||||
public static TwosideTextDiffProvider create(@Nullable Project project,
|
||||
@NotNull ContentDiffRequest request,
|
||||
@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff) {
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull Disposable disposable) {
|
||||
DiffContent content1 = Side.LEFT.select(request.getContents());
|
||||
DiffContent content2 = Side.RIGHT.select(request.getContents());
|
||||
DiffIgnoredRangeProvider ignoredRangeProvider = getIgnoredRangeProvider(project, content1, content2);
|
||||
if (ignoredRangeProvider == null) return null;
|
||||
return new SmartTextDiffProvider(project, content1, content2, settings, rediff, ignoredRangeProvider);
|
||||
return new SmartTextDiffProvider(project, content1, content2, settings, rediff, disposable, ignoredRangeProvider);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static TwosideTextDiffProvider.NoIgnore createNoIgnore(@Nullable Project project,
|
||||
@NotNull ContentDiffRequest request,
|
||||
@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff) {
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull Disposable disposable) {
|
||||
DiffContent content1 = Side.LEFT.select(request.getContents());
|
||||
DiffContent content2 = Side.RIGHT.select(request.getContents());
|
||||
DiffIgnoredRangeProvider ignoredRangeProvider = getIgnoredRangeProvider(project, content1, content2);
|
||||
if (ignoredRangeProvider == null) return null;
|
||||
return new SmartTextDiffProvider.NoIgnore(project, content1, content2, settings, rediff, ignoredRangeProvider);
|
||||
return new SmartTextDiffProvider.NoIgnore(project, content1, content2, settings, rediff, disposable, ignoredRangeProvider);
|
||||
}
|
||||
|
||||
private SmartTextDiffProvider(@Nullable Project project,
|
||||
@@ -76,8 +79,9 @@ public class SmartTextDiffProvider extends TwosideTextDiffProviderBase implement
|
||||
@NotNull DiffContent content2,
|
||||
@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull Disposable disposable,
|
||||
@NotNull DiffIgnoredRangeProvider ignoredRangeProvider) {
|
||||
this(project, content1, content2, settings, rediff, ignoredRangeProvider, IGNORE_POLICIES, HIGHLIGHT_POLICIES);
|
||||
this(project, content1, content2, settings, rediff, disposable, ignoredRangeProvider, IGNORE_POLICIES, HIGHLIGHT_POLICIES);
|
||||
}
|
||||
|
||||
private SmartTextDiffProvider(@Nullable Project project,
|
||||
@@ -85,10 +89,11 @@ public class SmartTextDiffProvider extends TwosideTextDiffProviderBase implement
|
||||
@NotNull DiffContent content2,
|
||||
@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull Disposable disposable,
|
||||
@NotNull DiffIgnoredRangeProvider ignoredRangeProvider,
|
||||
@NotNull IgnorePolicy[] ignorePolicies,
|
||||
@NotNull HighlightPolicy[] highlightPolicies) {
|
||||
super(settings, rediff, ignorePolicies, highlightPolicies);
|
||||
super(settings, rediff, disposable, ignorePolicies, highlightPolicies);
|
||||
myProject = project;
|
||||
myContent1 = content1;
|
||||
myContent2 = content2;
|
||||
@@ -151,8 +156,9 @@ public class SmartTextDiffProvider extends TwosideTextDiffProviderBase implement
|
||||
@NotNull DiffContent content2,
|
||||
@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull Disposable disposable,
|
||||
@NotNull DiffIgnoredRangeProvider ignoredRangeProvider) {
|
||||
super(project, content1, content2, settings, rediff, ignoredRangeProvider,
|
||||
super(project, content1, content2, settings, rediff, disposable, ignoredRangeProvider,
|
||||
IGNORE_POLICIES, ArrayUtil.remove(HIGHLIGHT_POLICIES, DO_NOT_HIGHLIGHT));
|
||||
}
|
||||
|
||||
|
||||
@@ -20,6 +20,7 @@ import com.intellij.diff.tools.util.base.IgnorePolicy;
|
||||
import com.intellij.diff.tools.util.base.TextDiffSettingsHolder.TextDiffSettings;
|
||||
import com.intellij.diff.tools.util.base.TextDiffViewerUtil.HighlightPolicySettingAction;
|
||||
import com.intellij.diff.tools.util.base.TextDiffViewerUtil.IgnorePolicySettingAction;
|
||||
import com.intellij.openapi.Disposable;
|
||||
import com.intellij.openapi.actionSystem.AnAction;
|
||||
import com.intellij.openapi.actionSystem.Separator;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -36,10 +37,12 @@ public class TextDiffProviderBase implements TextDiffProvider {
|
||||
|
||||
public TextDiffProviderBase(@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull Disposable disposable,
|
||||
@NotNull IgnorePolicy[] ignorePolicies,
|
||||
@NotNull HighlightPolicy[] highlightPolicies) {
|
||||
myIgnorePolicySettingAction = new MyIgnorePolicySettingAction(settings, rediff, ignorePolicies);
|
||||
myHighlightPolicySettingAction = new MyHighlightPolicySettingAction(settings, rediff, highlightPolicies);
|
||||
myIgnorePolicySettingAction = new MyIgnorePolicySettingAction(settings, ignorePolicies);
|
||||
myHighlightPolicySettingAction = new MyHighlightPolicySettingAction(settings, highlightPolicies);
|
||||
settings.addListener(new MyListener(rediff), disposable);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@@ -86,9 +89,8 @@ public class TextDiffProviderBase implements TextDiffProvider {
|
||||
|
||||
private class MyIgnorePolicySettingAction extends IgnorePolicySettingAction {
|
||||
public MyIgnorePolicySettingAction(@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull IgnorePolicy[] ignorePolicies) {
|
||||
super(settings, rediff, ignorePolicies);
|
||||
super(settings, ignorePolicies);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@@ -100,9 +102,8 @@ public class TextDiffProviderBase implements TextDiffProvider {
|
||||
|
||||
private class MyHighlightPolicySettingAction extends HighlightPolicySettingAction {
|
||||
public MyHighlightPolicySettingAction(@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull HighlightPolicy[] highlightPolicies) {
|
||||
super(settings, rediff, highlightPolicies);
|
||||
super(settings, highlightPolicies);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@@ -111,4 +112,22 @@ public class TextDiffProviderBase implements TextDiffProvider {
|
||||
return notNullize(TextDiffProviderBase.this.getText(option), super.getText(option));
|
||||
}
|
||||
}
|
||||
|
||||
private static class MyListener implements TextDiffSettings.Listener {
|
||||
@NotNull private final Runnable myRediff;
|
||||
|
||||
public MyListener(@NotNull Runnable rediff) {
|
||||
myRediff = rediff;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void highlightPolicyChanged() {
|
||||
myRediff.run();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void ignorePolicyChanged() {
|
||||
myRediff.run();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+3
-1
@@ -21,6 +21,7 @@ import com.intellij.diff.fragments.LineFragment;
|
||||
import com.intellij.diff.tools.util.base.HighlightPolicy;
|
||||
import com.intellij.diff.tools.util.base.IgnorePolicy;
|
||||
import com.intellij.diff.tools.util.base.TextDiffSettingsHolder.TextDiffSettings;
|
||||
import com.intellij.openapi.Disposable;
|
||||
import com.intellij.openapi.progress.ProgressIndicator;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
@@ -30,9 +31,10 @@ import java.util.List;
|
||||
abstract class TwosideTextDiffProviderBase extends TextDiffProviderBase implements TwosideTextDiffProvider {
|
||||
protected TwosideTextDiffProviderBase(@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull Disposable disposable,
|
||||
@NotNull IgnorePolicy[] ignorePolicies,
|
||||
@NotNull HighlightPolicy[] highlightPolicies) {
|
||||
super(settings, rediff, ignorePolicies, highlightPolicies);
|
||||
super(settings, rediff, disposable, ignorePolicies, highlightPolicies);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
|
||||
@@ -600,28 +600,30 @@ public class DiffUtil {
|
||||
public static TwosideTextDiffProvider createTextDiffProvider(@Nullable Project project,
|
||||
@NotNull ContentDiffRequest request,
|
||||
@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff) {
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull Disposable disposable) {
|
||||
DiffUserDataKeysEx.DiffComputer diffComputer = request.getUserData(DiffUserDataKeysEx.CUSTOM_DIFF_COMPUTER);
|
||||
if (diffComputer != null) return new SimpleTextDiffProvider(settings, rediff, diffComputer);
|
||||
if (diffComputer != null) return new SimpleTextDiffProvider(settings, rediff, disposable, diffComputer);
|
||||
|
||||
TwosideTextDiffProvider smartProvider = SmartTextDiffProvider.create(project, request, settings, rediff);
|
||||
TwosideTextDiffProvider smartProvider = SmartTextDiffProvider.create(project, request, settings, rediff, disposable);
|
||||
if (smartProvider != null) return smartProvider;
|
||||
|
||||
return new SimpleTextDiffProvider(settings, rediff);
|
||||
return new SimpleTextDiffProvider(settings, rediff, disposable);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static TwosideTextDiffProvider.NoIgnore createNoIgnoreTextDiffProvider(@Nullable Project project,
|
||||
@NotNull ContentDiffRequest request,
|
||||
@NotNull TextDiffSettings settings,
|
||||
@NotNull Runnable rediff) {
|
||||
@NotNull Runnable rediff,
|
||||
@NotNull Disposable disposable) {
|
||||
DiffUserDataKeysEx.DiffComputer diffComputer = request.getUserData(DiffUserDataKeysEx.CUSTOM_DIFF_COMPUTER);
|
||||
if (diffComputer != null) return new SimpleTextDiffProvider.NoIgnore(settings, rediff, diffComputer);
|
||||
if (diffComputer != null) return new SimpleTextDiffProvider.NoIgnore(settings, rediff, disposable, diffComputer);
|
||||
|
||||
TwosideTextDiffProvider.NoIgnore smartProvider = SmartTextDiffProvider.createNoIgnore(project, request, settings, rediff);
|
||||
TwosideTextDiffProvider.NoIgnore smartProvider = SmartTextDiffProvider.createNoIgnore(project, request, settings, rediff, disposable);
|
||||
if (smartProvider != null) return smartProvider;
|
||||
|
||||
return new SimpleTextDiffProvider.NoIgnore(settings, rediff);
|
||||
return new SimpleTextDiffProvider.NoIgnore(settings, rediff, disposable);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
|
||||
+342
-60
@@ -17,83 +17,365 @@ package com.intellij.diff.tools.fragmented
|
||||
|
||||
import com.intellij.diff.DiffTestCase
|
||||
import com.intellij.diff.comparison.ComparisonPolicy
|
||||
import com.intellij.diff.comparison.iterables.DiffIterable
|
||||
import com.intellij.diff.comparison.iterables.DiffIterableUtil
|
||||
import com.intellij.diff.fragments.LineFragment
|
||||
import com.intellij.diff.fragments.LineFragmentImpl
|
||||
import com.intellij.diff.util.LineRange
|
||||
import com.intellij.diff.util.Range
|
||||
import com.intellij.diff.util.Side
|
||||
import com.intellij.openapi.editor.impl.DocumentImpl
|
||||
import com.intellij.openapi.progress.DumbProgressIndicator
|
||||
import junit.framework.TestCase
|
||||
import java.util.*
|
||||
|
||||
class UnifiedFragmentBuilderTest : DiffTestCase() {
|
||||
fun testEquals() {
|
||||
val builder = createBuilder("A\nB\nC", "A\nB\nC", Side.LEFT)
|
||||
fun testSimple() {
|
||||
Test("", "",
|
||||
".",
|
||||
" ")
|
||||
.run()
|
||||
|
||||
assertTrue(builder.isEqual)
|
||||
assertEquals(builder.text.toString(), "A\nB\nC\n")
|
||||
assertEmpty(builder.changedLines)
|
||||
assertEmpty(builder.blocks)
|
||||
Test("A_B_C", "A_B_C",
|
||||
"A_B_C",
|
||||
" _ _ ")
|
||||
.run()
|
||||
|
||||
// empty document has one line, so it's "modified" case (and not "deleted")
|
||||
Test("A", "",
|
||||
"A_.",
|
||||
"L_R")
|
||||
.run()
|
||||
|
||||
Test("", "A",
|
||||
"._A",
|
||||
"L_R")
|
||||
.run()
|
||||
|
||||
Test("A_", "",
|
||||
"A_.",
|
||||
"L_ ")
|
||||
.run()
|
||||
|
||||
Test("A_", "B",
|
||||
"A_._B",
|
||||
"L_L_R")
|
||||
.run()
|
||||
|
||||
Test("B_", "B",
|
||||
"B_.",
|
||||
" _L")
|
||||
.run()
|
||||
|
||||
Test("_B", "B",
|
||||
"._B",
|
||||
"L_ ")
|
||||
.run()
|
||||
|
||||
Test("A_A", "B",
|
||||
"A_A_B",
|
||||
"L_L_R")
|
||||
.run()
|
||||
|
||||
Test("A_B_C_D", "A_D",
|
||||
"A_B_C_D",
|
||||
" _L_L_ ")
|
||||
.run()
|
||||
|
||||
Test("X_B_C", "A_B_C",
|
||||
"X_A_B_C",
|
||||
"L_R_ _ ")
|
||||
.run()
|
||||
|
||||
Test("A_B_C", "A_B_Y",
|
||||
"A_B_C_Y",
|
||||
" _ _L_R")
|
||||
.run()
|
||||
|
||||
Test("A_B_C_D_E_F", "A_X_C_D_Y_F",
|
||||
"A_B_X_C_D_E_Y_F",
|
||||
" _L_R_ _ _L_R_ ")
|
||||
.run()
|
||||
|
||||
Test("A_B_C_D_E_F", "A_B_X_C_D_F",
|
||||
"A_B_X_C_D_E_F",
|
||||
" _ _R_ _ _L_ ")
|
||||
.run()
|
||||
|
||||
Test("A_B_C_D_E_F", "A_B_X_Y_E_F",
|
||||
"A_B_C_D_X_Y_E_F",
|
||||
" _ _L_L_R_R_ _ ")
|
||||
.run()
|
||||
|
||||
Test("", "",
|
||||
".",
|
||||
" ")
|
||||
.changes()
|
||||
.run()
|
||||
|
||||
Test("A", "B",
|
||||
"A_B",
|
||||
"L_R")
|
||||
.changes(mod(0, 0, 1, 1))
|
||||
.runLeft()
|
||||
|
||||
Test("A", "B",
|
||||
"A",
|
||||
" ")
|
||||
.changes()
|
||||
.runLeft()
|
||||
|
||||
Test("A", "B",
|
||||
"B",
|
||||
" ")
|
||||
.changes()
|
||||
.runRight()
|
||||
}
|
||||
|
||||
fun testWrongEndLineTypoBug() {
|
||||
val builder = createBuilder("A\nB\nC\nD", "A\nD", Side.RIGHT)
|
||||
fun testNonFair() {
|
||||
Test("A_B", "",
|
||||
"A_B",
|
||||
" _ ")
|
||||
.changes()
|
||||
.runLeft()
|
||||
|
||||
assertFalse(builder.isEqual)
|
||||
assertEquals(builder.text.toString(), "A\nB\nC\nD\n")
|
||||
assertEquals(builder.changedLines, listOf(LineRange(1, 3)))
|
||||
Test("A_B", "",
|
||||
".",
|
||||
" ")
|
||||
.changes()
|
||||
.runRight()
|
||||
|
||||
assertEquals(builder.blocks.size, 1)
|
||||
val block = builder.blocks[0]
|
||||
assertEquals(block.line1, 1)
|
||||
assertEquals(block.line2, 3)
|
||||
assertEquals(block.range1.start, 1)
|
||||
assertEquals(block.range1.end, 3)
|
||||
assertEquals(block.range2.start, 3)
|
||||
assertEquals(block.range2.end, 3)
|
||||
Test("A_B", "A_._B",
|
||||
"A_B",
|
||||
" _ ")
|
||||
.changes()
|
||||
.runLeft()
|
||||
|
||||
Test("A_B", "A_._B",
|
||||
"A_._B",
|
||||
" _ _ ")
|
||||
.changes()
|
||||
.runRight()
|
||||
|
||||
Test("_._A_._", "X",
|
||||
"._._A_X_._.",
|
||||
" _ _L_R_ _ ")
|
||||
.changes(mod(2, 0, 1, 1))
|
||||
.runLeft()
|
||||
|
||||
Test("_._A_._", "X",
|
||||
"A_X",
|
||||
"L_R")
|
||||
.changes(mod(2, 0, 1, 1))
|
||||
.runRight()
|
||||
|
||||
Test("A_B_C_D", "X_BC_Y",
|
||||
"A_X_BC_D_Y",
|
||||
"L_R_ _L_R")
|
||||
.changes(mod(0, 0, 1, 1), mod(3, 2, 1, 1))
|
||||
.runRight()
|
||||
|
||||
Test("A_B_C_D", "A_BC_Y",
|
||||
"A_BC_D_Y",
|
||||
" _ _L_R")
|
||||
.changes(mod(3, 2, 1, 1))
|
||||
.runRight()
|
||||
|
||||
Test("AB_C_DE", "A_B_D_E",
|
||||
"AB_C_DE",
|
||||
" _L_ ")
|
||||
.changes(del(1, 2, 1))
|
||||
.runLeft()
|
||||
|
||||
Test("AB_C_DE", "A_B_D_E",
|
||||
"A_B_C_D_E",
|
||||
" _ _L_ _ ")
|
||||
.changes(del(1, 2, 1))
|
||||
.runRight()
|
||||
|
||||
Test("AB_DE", "A_B_C_D_E",
|
||||
"AB_C_DE",
|
||||
" _R_ ")
|
||||
.changes(ins(1, 2, 1))
|
||||
.runLeft()
|
||||
|
||||
Test("AB_DE", "A_B_C_D_E",
|
||||
"A_B_C_D_E",
|
||||
" _ _R_ _ ")
|
||||
.changes(ins(1, 2, 1))
|
||||
.runRight()
|
||||
}
|
||||
|
||||
fun testFirstLineChange() {
|
||||
val builder = createBuilder("X\nB\nC", "A\nB\nC", Side.RIGHT)
|
||||
private inner class Test(val input1: String, val input2: String,
|
||||
val result: String,
|
||||
val lineMapping: String) {
|
||||
private var customFragments: List<LineFragment>? = null
|
||||
|
||||
assertFalse(builder.isEqual)
|
||||
assertEquals(builder.text.toString(), "X\nA\nB\nC\n")
|
||||
assertEquals(builder.changedLines, listOf(LineRange(0, 1), LineRange(1, 2)))
|
||||
fun runLeft() {
|
||||
doRun(Side.LEFT)
|
||||
}
|
||||
|
||||
assertEquals(builder.blocks.size, 1)
|
||||
val block = builder.blocks[0]
|
||||
assertEquals(block.line1, 0)
|
||||
assertEquals(block.line2, 2)
|
||||
assertEquals(block.range1.start, 0)
|
||||
assertEquals(block.range1.end, 1)
|
||||
assertEquals(block.range2.start, 1)
|
||||
assertEquals(block.range2.end, 2)
|
||||
fun runRight() {
|
||||
doRun(Side.RIGHT)
|
||||
}
|
||||
|
||||
fun run() {
|
||||
doRun(Side.LEFT, Side.RIGHT)
|
||||
}
|
||||
|
||||
private fun doRun(vararg sides: Side) {
|
||||
sides.forEach { side ->
|
||||
assert(result.length == lineMapping.length)
|
||||
|
||||
val text1 = processText(input1)
|
||||
val text2 = processText(input2)
|
||||
|
||||
val fragments = if (customFragments != null) customFragments!!
|
||||
else MANAGER.compareLines(text1, text2, ComparisonPolicy.DEFAULT, INDICATOR)
|
||||
|
||||
val builder = UnifiedFragmentBuilder(fragments, DocumentImpl(text1), DocumentImpl(text2), side)
|
||||
builder.exec()
|
||||
|
||||
|
||||
val lineCount1 = input1.count({ it == '_' }) + 1
|
||||
val lineCount2 = input2.count({ it == '_' }) + 1
|
||||
val resultLineCount = result.count({ it == '_' }) + 1
|
||||
val lineIterable = DiffIterableUtil.create(fragments.map { Range(it.startLine1, it.endLine1, it.startLine2, it.endLine2) },
|
||||
lineCount1, lineCount2)
|
||||
|
||||
val expectedText = processText(result)
|
||||
val actualText = processActualText(builder)
|
||||
|
||||
val expectedMapping = processExpectedLineMapping(lineMapping)
|
||||
val actualMapping = processActualLineMapping(builder.blocks, resultLineCount)
|
||||
|
||||
val expectedChangedLines = processExpectedChangedLines(lineMapping)
|
||||
val actualChangedLines = processActualChangedLines(builder.changedLines)
|
||||
|
||||
val expectedMappedLines1 = processExpectedMappedLines(lineIterable, Side.LEFT)
|
||||
val expectedMappedLines2 = processExpectedMappedLines(lineIterable, Side.RIGHT)
|
||||
val actualMappedLines1 = processActualMappedLines(builder.convertor1, resultLineCount)
|
||||
val actualMappedLines2 = processActualMappedLines(builder.convertor2, resultLineCount)
|
||||
|
||||
assertEquals(expectedText, actualText)
|
||||
assertEquals(expectedMapping, actualMapping)
|
||||
assertEquals(expectedChangedLines, actualChangedLines)
|
||||
|
||||
if (customFragments == null) {
|
||||
assertEquals(expectedMappedLines1, actualMappedLines1)
|
||||
assertEquals(expectedMappedLines2, actualMappedLines2)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun changes(vararg ranges: Range): Test {
|
||||
customFragments = ranges.map {
|
||||
LineFragmentImpl(it.start1, it.end1, it.start2, it.end2,
|
||||
-1, -1, -1, -1)
|
||||
}
|
||||
return this
|
||||
}
|
||||
|
||||
private fun processText(text: String): String {
|
||||
return text.filterNot { it == '.' }.replace('_', '\n')
|
||||
}
|
||||
|
||||
private fun processActualText(builder: UnifiedFragmentBuilder): String {
|
||||
return builder.text.toString().removeSuffix("\n")
|
||||
}
|
||||
|
||||
private fun processExpectedLineMapping(lineMapping: String): LineMapping {
|
||||
val leftSet = BitSet()
|
||||
val rightSet = BitSet()
|
||||
val unchangedSet = BitSet()
|
||||
|
||||
lineMapping.split('_').forEachIndexed { index, line ->
|
||||
if (!line.isEmpty()) {
|
||||
val left = line.all { it == 'L' }
|
||||
val right = line.all { it == 'R' }
|
||||
val unchanged = line.all { it == ' ' }
|
||||
|
||||
if (left) leftSet.set(index)
|
||||
else if (right) rightSet.set(index)
|
||||
else if (unchanged) unchangedSet.set(index)
|
||||
else TestCase.fail()
|
||||
}
|
||||
}
|
||||
|
||||
return LineMapping(leftSet, rightSet, unchangedSet)
|
||||
}
|
||||
|
||||
private fun processActualLineMapping(blocks: List<ChangedBlock>, lineCount: Int): LineMapping {
|
||||
val leftSet = BitSet()
|
||||
val rightSet = BitSet()
|
||||
val unchangedSet = BitSet()
|
||||
|
||||
blocks.forEach {
|
||||
leftSet.set(it.range1.start, it.range1.end)
|
||||
rightSet.set(it.range2.start, it.range2.end)
|
||||
}
|
||||
|
||||
unchangedSet.set(0, lineCount)
|
||||
unchangedSet.andNot(leftSet)
|
||||
unchangedSet.andNot(rightSet)
|
||||
|
||||
return LineMapping(leftSet, rightSet, unchangedSet)
|
||||
}
|
||||
|
||||
private fun processExpectedChangedLines(lineMapping: String): BitSet {
|
||||
val expectedMapping = processExpectedLineMapping(lineMapping)
|
||||
val result = BitSet()
|
||||
result.or(expectedMapping.left)
|
||||
result.or(expectedMapping.right)
|
||||
return result
|
||||
}
|
||||
|
||||
private fun processActualChangedLines(changedRanges: List<LineRange>): BitSet {
|
||||
val result = BitSet()
|
||||
changedRanges.forEach {
|
||||
result.set(it.start, it.end)
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
private fun processExpectedMappedLines(iterable: DiffIterable, side: Side): BitSet {
|
||||
val result = BitSet()
|
||||
DiffIterableUtil.iterateAll(iterable).forEach { pair ->
|
||||
val range = pair.first
|
||||
val start = side.select(range.start1, range.start2)
|
||||
val end = side.select(range.end1, range.end2)
|
||||
result.set(start, end)
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
private fun processActualMappedLines(convertor: LineNumberConvertor, lineCount: Int): BitSet {
|
||||
val result = BitSet()
|
||||
for (i in -5..lineCount + 5) {
|
||||
val line = convertor.convert(i)
|
||||
if (line != -1) {
|
||||
if (result[line]) TestCase.fail()
|
||||
result.set(line)
|
||||
}
|
||||
}
|
||||
return result
|
||||
}
|
||||
}
|
||||
|
||||
fun testDeletion() {
|
||||
val builder = createBuilder("A\n", "", Side.LEFT)
|
||||
|
||||
assertFalse(builder.isEqual)
|
||||
assertEquals(builder.text.toString(), "A\n\n")
|
||||
assertEquals(builder.changedLines, listOf(LineRange(0, 1)))
|
||||
|
||||
assertEquals(builder.blocks.size, 1)
|
||||
val block = builder.blocks[0]
|
||||
assertEquals(block.line1, 0)
|
||||
assertEquals(block.line2, 1)
|
||||
assertEquals(block.range1.start, 0)
|
||||
assertEquals(block.range1.end, 1)
|
||||
assertEquals(block.range2.start, 1)
|
||||
assertEquals(block.range2.end, 1)
|
||||
private fun mod(line1: Int, line2: Int, count1: Int, count2: Int): Range {
|
||||
assert(count1 != 0)
|
||||
assert(count2 != 0)
|
||||
return Range(line1, line1 + count1, line2, line2 + count2)
|
||||
}
|
||||
|
||||
|
||||
private fun createBuilder(text1: String, text2: String, side: Side): UnifiedFragmentBuilder {
|
||||
val document1 = DocumentImpl(text1)
|
||||
val document2 = DocumentImpl(text2)
|
||||
|
||||
val fragments = MANAGER.compareLinesInner(document1.charsSequence, document2.charsSequence,
|
||||
ComparisonPolicy.DEFAULT, DumbProgressIndicator.INSTANCE)
|
||||
|
||||
val builder = UnifiedFragmentBuilder(fragments, document1, document2, side)
|
||||
builder.exec()
|
||||
|
||||
return builder
|
||||
private fun del(line1: Int, line2: Int, count1: Int): Range {
|
||||
assert(count1 != 0)
|
||||
return Range(line1, line1 + count1, line2, line2)
|
||||
}
|
||||
|
||||
private fun ins(line1: Int, line2: Int, count2: Int): Range {
|
||||
assert(count2 != 0)
|
||||
return Range(line1, line1, line2, line2 + count2)
|
||||
}
|
||||
|
||||
private data class LineMapping(val left: BitSet, val right: BitSet, val unchanged: BitSet)
|
||||
}
|
||||
|
||||
@@ -59,7 +59,7 @@ public interface PrePushHandler {
|
||||
String getPresentableName();
|
||||
|
||||
/**
|
||||
* Check synchronously if the push operation should be performed or canceled for specified {@link PushDetail}s
|
||||
* Check synchronously if the push operation should be performed or canceled for specified {@link PushInfo}s
|
||||
* <p>
|
||||
* Note: it is permissible for a handler to show it's own modal dialogs with specifying
|
||||
* the supplied {@code indicator}'s {@link ProgressIndicator#getModalityState() modality} state.
|
||||
@@ -70,6 +70,6 @@ public interface PrePushHandler {
|
||||
*/
|
||||
@CalledInAny
|
||||
@NotNull
|
||||
Result handle(@NotNull List<PushDetail> pushDetails, @NotNull ProgressIndicator indicator);
|
||||
Result handle(@NotNull List<PushInfo> pushDetails, @NotNull ProgressIndicator indicator);
|
||||
|
||||
}
|
||||
|
||||
@@ -524,7 +524,7 @@ public class PushController implements Disposable {
|
||||
@CalledInAny
|
||||
public PrePushHandler.Result executeHandlers(@NotNull ProgressIndicator indicator) throws ProcessCanceledException, HandlerException {
|
||||
if (myHandlers.isEmpty()) return PrePushHandler.Result.OK;
|
||||
List<PushDetail> pushDetails = preparePushDetails();
|
||||
List<PushInfo> pushDetails = preparePushDetails();
|
||||
StepsProgressIndicator stepsIndicator = new StepsProgressIndicator(indicator, myHandlers.size());
|
||||
stepsIndicator.setIndeterminate(false);
|
||||
stepsIndicator.setFraction(0);
|
||||
@@ -588,8 +588,8 @@ public class PushController implements Disposable {
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private List<PushDetail> preparePushDetails() {
|
||||
List<PushDetail> allDetails = ContainerUtil.newArrayList();
|
||||
private List<PushInfo> preparePushDetails() {
|
||||
List<PushInfo> allDetails = ContainerUtil.newArrayList();
|
||||
Collection<MyRepoModel<?, ?, ?>> repoModels = getSelectedRepoNode();
|
||||
|
||||
for (MyRepoModel<?, ?, ?> model : repoModels) {
|
||||
@@ -608,7 +608,7 @@ public class PushController implements Disposable {
|
||||
|
||||
//sort commits in the time-ascending order
|
||||
Collections.reverse(loadedCommits);
|
||||
allDetails.add(new PushDetailImpl(model.getRepository(), pushSpec, loadedCommits));
|
||||
allDetails.add(new PushInfoImpl(model.getRepository(), pushSpec, loadedCommits));
|
||||
}
|
||||
return Collections.unmodifiableList(allDetails);
|
||||
}
|
||||
@@ -736,15 +736,15 @@ public class PushController implements Disposable {
|
||||
}) ? commonTarget : null;
|
||||
}
|
||||
|
||||
private static class PushDetailImpl implements PushDetail {
|
||||
private static class PushInfoImpl implements PushInfo {
|
||||
|
||||
private final Repository myRepository;
|
||||
private final PushSpec<PushSource, PushTarget> myPushSpec;
|
||||
private final List<VcsFullCommitDetails> myCommits;
|
||||
|
||||
private PushDetailImpl(@NotNull Repository repository,
|
||||
@NotNull PushSpec<PushSource, PushTarget> spec,
|
||||
@NotNull List<VcsFullCommitDetails> commits) {
|
||||
private PushInfoImpl(@NotNull Repository repository,
|
||||
@NotNull PushSpec<PushSource, PushTarget> spec,
|
||||
@NotNull List<VcsFullCommitDetails> commits) {
|
||||
myRepository = repository;
|
||||
myPushSpec = spec;
|
||||
myCommits = commits;
|
||||
@@ -752,19 +752,19 @@ public class PushController implements Disposable {
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Repository repository() {
|
||||
public Repository getRepository() {
|
||||
return myRepository;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public PushSpec<PushSource, PushTarget> pushSpec() {
|
||||
public PushSpec<PushSource, PushTarget> getPushSpec() {
|
||||
return myPushSpec;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public List<VcsFullCommitDetails> commits() {
|
||||
public List<VcsFullCommitDetails> getCommits() {
|
||||
return myCommits;
|
||||
}
|
||||
}
|
||||
|
||||
+7
-8
@@ -22,28 +22,27 @@ import org.jetbrains.annotations.NotNull;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Upcoming push information holder
|
||||
* Upcoming push information holder for one repository
|
||||
*/
|
||||
public interface PushDetail {
|
||||
public interface PushInfo {
|
||||
/**
|
||||
* Repository of the push source
|
||||
*/
|
||||
@NotNull
|
||||
Repository repository();
|
||||
Repository getRepository();
|
||||
|
||||
/**
|
||||
* For a {@link #repository()} specifies what would be pushed and where
|
||||
* Specifies what would be pushed and where for this repository
|
||||
*
|
||||
* @return push specification
|
||||
*/
|
||||
@NotNull
|
||||
PushSpec<PushSource, PushTarget> pushSpec();
|
||||
PushSpec<PushSource, PushTarget> getPushSpec();
|
||||
|
||||
/**
|
||||
* Returns list of commits to be pushed.
|
||||
* a.e. result of `git log source..target` for updated git branches; empty list for newly created branches.
|
||||
* Commits should be ordered by commit time (ex: committer time for git);
|
||||
* Commits are ordered so that the most recent come last, e.g. as in the output of git log source..target but in reverse order
|
||||
*/
|
||||
@NotNull
|
||||
List<VcsFullCommitDetails> commits();
|
||||
List<VcsFullCommitDetails> getCommits();
|
||||
}
|
||||
@@ -393,14 +393,18 @@ public class BranchActionGroupPopup extends FlatSpeedSearchPopup {
|
||||
@NotNull private final String myToCollapseText;
|
||||
@NotNull private final String myToExpandText;
|
||||
|
||||
public MoreAction(@NotNull Project project, int numberOfHiddenNodes, @Nullable String settingName, boolean defaultExpandValue) {
|
||||
public MoreAction(@NotNull Project project,
|
||||
int numberOfHiddenNodes,
|
||||
@Nullable String settingName,
|
||||
boolean defaultExpandValue,
|
||||
boolean hasFavorites) {
|
||||
super();
|
||||
myProject = project;
|
||||
mySettingName = settingName;
|
||||
myDefaultExpandValue = defaultExpandValue;
|
||||
assert numberOfHiddenNodes > 0;
|
||||
myToExpandText = "Show " + numberOfHiddenNodes + " More...";
|
||||
myToCollapseText = "Show Only Favorites";
|
||||
myToCollapseText = "Show " + (hasFavorites ? "Only Favorites" : "Less");
|
||||
setExpanded(
|
||||
settingName != null ? PropertiesComponent.getInstance(project).getBoolean(settingName, defaultExpandValue) : defaultExpandValue);
|
||||
}
|
||||
@@ -466,7 +470,9 @@ public class BranchActionGroupPopup extends FlatSpeedSearchPopup {
|
||||
@NotNull DefaultActionGroup parentGroup, @NotNull List<? extends ActionGroup> actionList,
|
||||
int maxIndex, @Nullable String settingName, boolean defaultExpandValue) {
|
||||
if (actionList.size() > maxIndex) {
|
||||
MoreAction moreAction = new MoreAction(project, actionList.size() - maxIndex, settingName, defaultExpandValue);
|
||||
boolean hasFavorites =
|
||||
actionList.stream().anyMatch(action -> action instanceof BranchActionGroup && ((BranchActionGroup)action).isFavorite());
|
||||
MoreAction moreAction = new MoreAction(project, actionList.size() - maxIndex, settingName, defaultExpandValue, hasFavorites);
|
||||
for (int i = 0; i < actionList.size(); i++) {
|
||||
parentGroup.add(i < maxIndex ? actionList.get(i) : new HideableActionGroup(actionList.get(i), moreAction));
|
||||
}
|
||||
|
||||
+6
-5
@@ -17,9 +17,11 @@
|
||||
package com.intellij.psi.search.searches;
|
||||
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.application.ReadAction;
|
||||
import com.intellij.openapi.extensions.ExtensionPointName;
|
||||
import com.intellij.openapi.util.Computable;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiFile;
|
||||
import com.intellij.psi.search.PsiSearchHelper;
|
||||
import com.intellij.psi.search.SearchScope;
|
||||
import com.intellij.util.Processor;
|
||||
@@ -98,11 +100,10 @@ public class DefinitionsScopedSearch extends ExtensibleQueryFactory<PsiElement,
|
||||
|
||||
@NotNull
|
||||
public SearchScope getScope() {
|
||||
return ApplicationManager.getApplication().runReadAction(new Computable<SearchScope>() {
|
||||
@Override
|
||||
public SearchScope compute() {
|
||||
return myScope.intersectWith(PsiSearchHelper.SERVICE.getInstance(myElement.getProject()).getUseScope(myElement));
|
||||
}
|
||||
return ReadAction.compute(() -> {
|
||||
PsiFile file = myElement.getContainingFile();
|
||||
return myScope.intersectWith(
|
||||
PsiSearchHelper.SERVICE.getInstance(myElement.getProject()).getUseScope(file != null ? file : myElement));
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -88,6 +88,10 @@ public abstract class TargetElementEvaluatorEx2 implements TargetElementEvaluato
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return a scope where element's implementations (Goto/Show Implementations) should be searched.
|
||||
* If null is returned, default (module-with-dependents) scope will be used.
|
||||
*/
|
||||
@Nullable
|
||||
public SearchScope getSearchScope(Editor editor, @NotNull PsiElement element) {
|
||||
return null;
|
||||
|
||||
@@ -457,7 +457,10 @@ public class TargetElementUtil extends TargetElementUtilBase {
|
||||
public SearchScope getSearchScope(Editor editor, @NotNull PsiElement element) {
|
||||
TargetElementEvaluatorEx2 evaluator = getElementEvaluatorsEx2(element.getLanguage());
|
||||
SearchScope result = evaluator != null ? evaluator.getSearchScope(editor, element) : null;
|
||||
return result != null ? result : PsiSearchHelper.SERVICE.getInstance(element.getProject()).getUseScope(element);
|
||||
if (result != null) return result;
|
||||
|
||||
PsiFile file = element.getContainingFile();
|
||||
return PsiSearchHelper.SERVICE.getInstance(element.getProject()).getUseScope(file != null ? file : element);
|
||||
}
|
||||
|
||||
protected final LanguageExtension<TargetElementEvaluator> targetElementEvaluator =
|
||||
|
||||
@@ -96,6 +96,9 @@ public abstract class TargetElementUtilBase {
|
||||
|
||||
public abstract boolean acceptImplementationForReference(@Nullable PsiReference reference, @Nullable PsiElement element);
|
||||
|
||||
/**
|
||||
* @return a scope where element's implementations (Goto/Show Implementations) should be searched
|
||||
*/
|
||||
@NotNull
|
||||
public abstract SearchScope getSearchScope(Editor editor, @NotNull PsiElement element);
|
||||
}
|
||||
|
||||
@@ -18,7 +18,6 @@ package com.intellij.codeInsight.daemon.impl;
|
||||
|
||||
import com.intellij.codeInsight.hint.TooltipController;
|
||||
import com.intellij.codeInsight.hint.TooltipGroup;
|
||||
import com.intellij.lang.annotation.HighlightSeverity;
|
||||
import com.intellij.openapi.editor.Editor;
|
||||
import com.intellij.ui.HintHint;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -46,7 +45,6 @@ public class DaemonTooltipUtil {
|
||||
|
||||
public static void showInfoTooltip(@NotNull final HighlightInfo info, @NotNull Editor editor, final int defaultOffset, final int currentWidth, final boolean requestFocus) {
|
||||
if (info.getToolTip() == null) return;
|
||||
if (HighlightSeverity.INFORMATION.equals(info.getSeverity())) return;
|
||||
Rectangle visibleArea = editor.getScrollingModel().getVisibleArea();
|
||||
|
||||
Point bestPoint = editor.logicalPositionToXY(editor.offsetToLogicalPosition(defaultOffset));
|
||||
|
||||
+11
-2
@@ -355,13 +355,22 @@ public class LocalInspectionsPass extends ProgressableTextEditorHighlightingPass
|
||||
.range(psiElement, textRange.getStartOffset(), textRange.getEndOffset())
|
||||
.description(message)
|
||||
.severity(severity);
|
||||
if (toolTip != null) b.escapedToolTip(toolTip);
|
||||
boolean invisible = HighlightSeverity.INFORMATION.equals(severity);
|
||||
if (toolTip != null && !invisible) b.escapedToolTip(toolTip);
|
||||
if (attributes != null) b.textAttributes(attributes);
|
||||
if (problemDescriptor.isAfterEndOfLine()) b.endOfLine();
|
||||
if (isFileLevel) b.fileLevelAnnotation();
|
||||
if (problemDescriptor.getProblemGroup() != null) b.problemGroup(problemDescriptor.getProblemGroup());
|
||||
if (!invisible) return b.create();
|
||||
|
||||
return b.create();
|
||||
HighlightInfo info = b.createUnconditionally();
|
||||
for (HighlightInfoFilter filter : HighlightInfoFilter.EXTENSION_POINT_NAME.getExtensions()) {
|
||||
if (!(filter instanceof HighlightInfoFilterImpl) && !filter.accept(info, myFile)) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
info.psiElement = psiElement;
|
||||
return info;
|
||||
}
|
||||
|
||||
private final Map<TextRange, RangeMarker> ranges2markersCache = new THashMap<>();
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2014 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -142,6 +142,8 @@ public class JoinLinesHandler extends EditorActionHandler {
|
||||
@NotNull PsiFile psiFile,
|
||||
int startLine,
|
||||
Ref<Integer> caretRestoreOffset) {
|
||||
if (startLine >= doc.getLineCount() - 1) return;
|
||||
|
||||
docManager.doPostponedOperationsAndUnblockDocument(doc);
|
||||
docManager.commitDocument(doc);
|
||||
CharSequence text = doc.getCharsSequence();
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2016 JetBrains s.r.o.
|
||||
* Copyright 2000-2017 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.
|
||||
@@ -172,9 +172,9 @@ public class ExportHTMLAction extends AnAction implements DumbAware {
|
||||
if (profileName != null) {
|
||||
element.setAttribute(InspectionApplication.PROFILE, profileName);
|
||||
}
|
||||
JDOMUtil.writeParent(element,
|
||||
new File(outputDirectoryName, InspectionApplication.DESCRIPTIONS + InspectionApplication.XML_EXTENSION),
|
||||
CodeStyleSettingsManager.getSettings(null).getLineSeparator());
|
||||
JDOMUtil.write(element,
|
||||
new File(outputDirectoryName, InspectionApplication.DESCRIPTIONS + InspectionApplication.XML_EXTENSION),
|
||||
CodeStyleSettingsManager.getSettings(null).getLineSeparator());
|
||||
}
|
||||
catch (IOException e) {
|
||||
ApplicationManager.getApplication().invokeLater(() -> Messages.showErrorDialog(myView, e.getMessage()));
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user