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:
@@ -17,7 +17,6 @@ package com.intellij.debugger.ui;
|
||||
|
||||
import com.intellij.debugger.DebuggerBundle;
|
||||
import com.intellij.util.PlatformIcons;
|
||||
import com.intellij.xdebugger.XDebuggerBundle;
|
||||
import com.intellij.xdebugger.breakpoints.ui.XBreakpointGroup;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
@@ -26,13 +25,6 @@ import javax.swing.*;
|
||||
|
||||
public class XBreakpointClassGroup extends XBreakpointGroup {
|
||||
private static final String DEFAULT_PACKAGE_NAME = DebuggerBundle.message("default.package.name");
|
||||
public static final XBreakpointClassGroup UNKNOWN = new XBreakpointClassGroup("", "") {
|
||||
@NotNull
|
||||
@Override
|
||||
public String getName() {
|
||||
return XDebuggerBundle.message("xbreakpoint.group.unknown");
|
||||
}
|
||||
};
|
||||
|
||||
private String myPackageName;
|
||||
private String myClassName;
|
||||
|
||||
@@ -42,18 +42,17 @@ class XBreakpointGroupingByClassRule<B> extends XBreakpointGroupingRule<B, XBrea
|
||||
return XBreakpointsGroupingPriorities.BY_CLASS;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public XBreakpointClassGroup getGroup(@NotNull B b, @NotNull Collection<XBreakpointClassGroup> groups) {
|
||||
if (b instanceof XBreakpoint) {
|
||||
Breakpoint javaBreakpoint = BreakpointManager.findBreakpoint((XBreakpoint)b);
|
||||
if (javaBreakpoint == null) {
|
||||
return XBreakpointClassGroup.UNKNOWN;
|
||||
return null;
|
||||
}
|
||||
String className = javaBreakpoint.getShortClassName();
|
||||
String packageName = javaBreakpoint.getPackageName();
|
||||
if (className == null) {
|
||||
return XBreakpointClassGroup.UNKNOWN;
|
||||
return null;
|
||||
}
|
||||
for (XBreakpointClassGroup group : groups) {
|
||||
if (group.getClassName().equals(className) && group.getPackageName().equals(packageName)) {
|
||||
@@ -62,7 +61,7 @@ class XBreakpointGroupingByClassRule<B> extends XBreakpointGroupingRule<B, XBrea
|
||||
}
|
||||
return new XBreakpointClassGroup(packageName, className);
|
||||
}
|
||||
return XBreakpointClassGroup.UNKNOWN;
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
|
||||
+1
-2
@@ -39,7 +39,6 @@ public class XBreakpointGroupingByPackageRule<B> extends XBreakpointGroupingRule
|
||||
return XBreakpointsGroupingPriorities.BY_PACKAGE;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public XBreakpointPackageGroup getGroup(@NotNull B breakpoint, @NotNull Collection<XBreakpointPackageGroup> groups) {
|
||||
String packageName = null;
|
||||
@@ -50,7 +49,7 @@ public class XBreakpointGroupingByPackageRule<B> extends XBreakpointGroupingRule
|
||||
}
|
||||
}
|
||||
if (packageName == null) {
|
||||
return XBreakpointPackageGroup.UNKNOWN;
|
||||
return null;
|
||||
}
|
||||
for (XBreakpointPackageGroup group : groups) {
|
||||
if (StringUtil.equals(group.getPackageName(), packageName)) {
|
||||
|
||||
@@ -18,30 +18,17 @@ package com.intellij.debugger.ui;
|
||||
import com.intellij.debugger.DebuggerBundle;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.util.PlatformIcons;
|
||||
import com.intellij.xdebugger.XDebuggerBundle;
|
||||
import com.intellij.xdebugger.breakpoints.ui.XBreakpointGroup;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
|
||||
public class XBreakpointPackageGroup extends XBreakpointGroup {
|
||||
private static final String DEFAULT_PACKAGE_NAME = DebuggerBundle.message("default.package.name");
|
||||
public static final XBreakpointPackageGroup UNKNOWN = new XBreakpointPackageGroup() {
|
||||
@NotNull
|
||||
@Override
|
||||
public String getName() {
|
||||
return XDebuggerBundle.message("xbreakpoint.group.unknown");
|
||||
}
|
||||
};
|
||||
|
||||
private String myPackageName;
|
||||
|
||||
private XBreakpointPackageGroup() {
|
||||
myPackageName = null;
|
||||
}
|
||||
|
||||
public XBreakpointPackageGroup(@NotNull String packageName) {
|
||||
public XBreakpointPackageGroup(String packageName) {
|
||||
myPackageName = packageName;
|
||||
}
|
||||
|
||||
@@ -57,7 +44,7 @@ public class XBreakpointPackageGroup extends XBreakpointGroup {
|
||||
return StringUtil.isEmpty(packageName) ? DEFAULT_PACKAGE_NAME : packageName;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@NotNull
|
||||
public String getPackageName() {
|
||||
return myPackageName;
|
||||
}
|
||||
|
||||
@@ -133,6 +133,16 @@ public class BreakpointManager {
|
||||
|
||||
@Override
|
||||
public void changeEvent(@NotNull DebuggerContextImpl newContext, int event) {
|
||||
if (event == DebuggerSession.EVENT_ATTACHED) {
|
||||
// notify about possibly slow method breakpoints
|
||||
for (XLineBreakpoint breakpoint : getXBreakpointManager().getBreakpoints(JavaMethodBreakpointType.class)) {
|
||||
if (breakpoint.isEnabled()) {
|
||||
XDebugSessionImpl.NOTIFICATION_GROUP.createNotification("Method breakpoints may dramatically slow down debugging", MessageType.WARNING).notify(
|
||||
myProject);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (newContext.getDebuggerSession() != myPreviousSession || event == DebuggerSession.EVENT_DETACHED) {
|
||||
updateBreakpointsUI();
|
||||
myPreviousSession = newContext.getDebuggerSession();
|
||||
|
||||
+27
-7
@@ -18,7 +18,12 @@ package com.intellij.codeInspection.varScopeCanBeNarrowed;
|
||||
import com.intellij.codeInsight.AnnotationUtil;
|
||||
import com.intellij.codeInsight.daemon.GroupNames;
|
||||
import com.intellij.codeInsight.daemon.ImplicitUsageProvider;
|
||||
import com.intellij.codeInspection.*;
|
||||
import com.intellij.codeInsight.daemon.QuickFixBundle;
|
||||
import com.intellij.codeInspection.BaseJavaBatchLocalInspectionTool;
|
||||
import com.intellij.codeInspection.InspectionsBundle;
|
||||
import com.intellij.codeInspection.LocalQuickFix;
|
||||
import com.intellij.codeInspection.ProblemsHolder;
|
||||
import com.intellij.codeInspection.util.SpecialAnnotationsUtilBase;
|
||||
import com.intellij.openapi.extensions.Extensions;
|
||||
import com.intellij.openapi.util.Comparing;
|
||||
import com.intellij.openapi.util.JDOMExternalizableStringList;
|
||||
@@ -28,15 +33,14 @@ import com.intellij.psi.*;
|
||||
import com.intellij.psi.controlFlow.*;
|
||||
import com.intellij.psi.util.PsiTreeUtil;
|
||||
import com.intellij.psi.util.PsiUtil;
|
||||
import com.intellij.util.Processor;
|
||||
import com.siyeh.InspectionGadgetsBundle;
|
||||
import gnu.trove.THashSet;
|
||||
import org.jdom.Element;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import java.util.*;
|
||||
|
||||
public class FieldCanBeLocalInspectionBase extends BaseJavaBatchLocalInspectionTool {
|
||||
@NonNls public static final String SHORT_NAME = "FieldCanBeLocal";
|
||||
@@ -69,10 +73,26 @@ public class FieldCanBeLocalInspectionBase extends BaseJavaBatchLocalInspectionT
|
||||
if (candidates.isEmpty()) return;
|
||||
final ImplicitUsageProvider[] implicitUsageProviders = Extensions.getExtensions(ImplicitUsageProvider.EP_NAME);
|
||||
|
||||
for (PsiField field : candidates) {
|
||||
for (final PsiField field : candidates) {
|
||||
if (usedFields.contains(field) && !hasImplicitReadOrWriteUsage(field, implicitUsageProviders)) {
|
||||
final String message = InspectionsBundle.message("inspection.field.can.be.local.problem.descriptor");
|
||||
holder.registerProblem(field.getNameIdentifier(), message, createFix());
|
||||
final ArrayList<LocalQuickFix> fixes = new ArrayList<LocalQuickFix>();
|
||||
SpecialAnnotationsUtilBase.createAddToSpecialAnnotationFixes(field, new Processor<String>() {
|
||||
@Override
|
||||
public boolean process(String qualifiedName) {
|
||||
final LocalQuickFix quickFix = SpecialAnnotationsUtilBase.createAddToSpecialAnnotationsListQuickFix(
|
||||
InspectionGadgetsBundle.message("add.0.to.ignore.if.annotated.by.list.quickfix", qualifiedName),
|
||||
QuickFixBundle.message("fix.add.special.annotation.family"),
|
||||
EXCLUDE_ANNOS, qualifiedName, field);
|
||||
fixes.add(quickFix);
|
||||
return true;
|
||||
}
|
||||
});
|
||||
final LocalQuickFix fix = createFix();
|
||||
if (fix != null) {
|
||||
fixes.add(fix);
|
||||
}
|
||||
holder.registerProblem(field.getNameIdentifier(), message, fixes.toArray(new LocalQuickFix[fixes.size()]));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+12
-6
@@ -16,6 +16,7 @@
|
||||
package com.intellij.application.options;
|
||||
|
||||
import com.intellij.codeInsight.daemon.DaemonCodeAnalyzer;
|
||||
import com.intellij.lang.java.JavaLanguage;
|
||||
import com.intellij.openapi.application.ApplicationBundle;
|
||||
import com.intellij.openapi.options.Configurable;
|
||||
import com.intellij.openapi.options.ConfigurationException;
|
||||
@@ -23,6 +24,7 @@ import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.project.ProjectManager;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.psi.codeStyle.CodeStyleSettings;
|
||||
import com.intellij.psi.codeStyle.CommonCodeStyleSettings;
|
||||
import com.intellij.ui.IdeBorderFactory;
|
||||
import com.intellij.ui.ToolbarDecorator;
|
||||
import com.intellij.ui.components.JBList;
|
||||
@@ -204,6 +206,7 @@ public class CodeStyleGenerationConfigurable implements Configurable {
|
||||
}*/
|
||||
|
||||
public void reset(CodeStyleSettings settings) {
|
||||
CommonCodeStyleSettings javaCommonSettings = settings.getCommonSettings(JavaLanguage.INSTANCE);
|
||||
myCbPreferLongerNames.setSelected(settings.PREFER_LONGER_NAMES);
|
||||
|
||||
myFieldPrefixField.setText(settings.FIELD_NAME_PREFIX);
|
||||
@@ -216,8 +219,8 @@ public class CodeStyleGenerationConfigurable implements Configurable {
|
||||
myParameterSuffixField.setText(settings.PARAMETER_NAME_SUFFIX);
|
||||
myLocalVariableSuffixField.setText(settings.LOCAL_VARIABLE_NAME_SUFFIX);
|
||||
|
||||
myCbLineCommentAtFirstColumn.setSelected(settings.LINE_COMMENT_AT_FIRST_COLUMN);
|
||||
myCbBlockCommentAtFirstColumn.setSelected(settings.BLOCK_COMMENT_AT_FIRST_COLUMN);
|
||||
myCbLineCommentAtFirstColumn.setSelected(javaCommonSettings.LINE_COMMENT_AT_FIRST_COLUMN);
|
||||
myCbBlockCommentAtFirstColumn.setSelected(javaCommonSettings.BLOCK_COMMENT_AT_FIRST_COLUMN);
|
||||
|
||||
myCbGenerateFinalLocals.setSelected(settings.GENERATE_FINAL_LOCALS);
|
||||
myCbGenerateFinalParameters.setSelected(settings.GENERATE_FINAL_PARAMETERS);
|
||||
@@ -233,6 +236,7 @@ public class CodeStyleGenerationConfigurable implements Configurable {
|
||||
}
|
||||
|
||||
public void apply(CodeStyleSettings settings) throws ConfigurationException {
|
||||
CommonCodeStyleSettings javaCommonSettings = settings.getCommonSettings(JavaLanguage.INSTANCE);
|
||||
settings.PREFER_LONGER_NAMES = myCbPreferLongerNames.isSelected();
|
||||
|
||||
settings.FIELD_NAME_PREFIX = setPrefixSuffix(myFieldPrefixField.getText(), true);
|
||||
@@ -245,8 +249,8 @@ public class CodeStyleGenerationConfigurable implements Configurable {
|
||||
settings.PARAMETER_NAME_SUFFIX = setPrefixSuffix(myParameterSuffixField.getText(), false);
|
||||
settings.LOCAL_VARIABLE_NAME_SUFFIX = setPrefixSuffix(myLocalVariableSuffixField.getText(), false);
|
||||
|
||||
settings.LINE_COMMENT_AT_FIRST_COLUMN = myCbLineCommentAtFirstColumn.isSelected();
|
||||
settings.BLOCK_COMMENT_AT_FIRST_COLUMN = myCbBlockCommentAtFirstColumn.isSelected();
|
||||
javaCommonSettings.LINE_COMMENT_AT_FIRST_COLUMN = myCbLineCommentAtFirstColumn.isSelected();
|
||||
javaCommonSettings.BLOCK_COMMENT_AT_FIRST_COLUMN = myCbBlockCommentAtFirstColumn.isSelected();
|
||||
|
||||
settings.GENERATE_FINAL_LOCALS = myCbGenerateFinalLocals.isSelected();
|
||||
settings.GENERATE_FINAL_PARAMETERS = myCbGenerateFinalParameters.isSelected();
|
||||
@@ -276,6 +280,8 @@ public class CodeStyleGenerationConfigurable implements Configurable {
|
||||
}
|
||||
|
||||
public boolean isModified(CodeStyleSettings settings) {
|
||||
CommonCodeStyleSettings javaCommonSettings = settings.getCommonSettings(JavaLanguage.INSTANCE);
|
||||
|
||||
boolean isModified = isModified(myCbPreferLongerNames, settings.PREFER_LONGER_NAMES);
|
||||
|
||||
isModified |= isModified(myFieldPrefixField, settings.FIELD_NAME_PREFIX);
|
||||
@@ -288,8 +294,8 @@ public class CodeStyleGenerationConfigurable implements Configurable {
|
||||
isModified |= isModified(myParameterSuffixField, settings.PARAMETER_NAME_SUFFIX);
|
||||
isModified |= isModified(myLocalVariableSuffixField, settings.LOCAL_VARIABLE_NAME_SUFFIX);
|
||||
|
||||
isModified |= isModified(myCbLineCommentAtFirstColumn, settings.LINE_COMMENT_AT_FIRST_COLUMN);
|
||||
isModified |= isModified(myCbBlockCommentAtFirstColumn, settings.BLOCK_COMMENT_AT_FIRST_COLUMN);
|
||||
isModified |= isModified(myCbLineCommentAtFirstColumn, javaCommonSettings.LINE_COMMENT_AT_FIRST_COLUMN);
|
||||
isModified |= isModified(myCbBlockCommentAtFirstColumn, javaCommonSettings.BLOCK_COMMENT_AT_FIRST_COLUMN);
|
||||
|
||||
|
||||
isModified |= isModified(myCbGenerateFinalLocals, settings.GENERATE_FINAL_LOCALS);
|
||||
|
||||
+4
-2
@@ -109,7 +109,9 @@ public class JavaMemberNameCompletionContributor extends CompletionContributor {
|
||||
String propertyName = null;
|
||||
if (variableKind == VariableKind.PARAMETER) {
|
||||
final PsiMethod method = PsiTreeUtil.getParentOfType(var, PsiMethod.class);
|
||||
propertyName = PropertyUtil.getPropertyName(method);
|
||||
if (method != null) {
|
||||
propertyName = PropertyUtil.getPropertyName(method);
|
||||
}
|
||||
if (method != null && method.getName().startsWith("with")) {
|
||||
propertyName = StringUtil.decapitalize(method.getName().substring(4));
|
||||
}
|
||||
@@ -133,7 +135,7 @@ public class JavaMemberNameCompletionContributor extends CompletionContributor {
|
||||
addLookupItems(set, null, matcher, project, getOverlappedNameVersions(matcher.getPrefix(), suggestedNames, ""));
|
||||
}
|
||||
PsiElement parent = PsiTreeUtil.getParentOfType(var, PsiCodeBlock.class);
|
||||
if(parent == null) parent = PsiTreeUtil.getParentOfType(var, PsiMethod.class);
|
||||
if(parent == null) parent = PsiTreeUtil.getParentOfType(var, PsiMethod.class, PsiLambdaExpression.class);
|
||||
addLookupItems(set, suggestedNameInfo, matcher, project, getUnresolvedReferences(parent, false));
|
||||
if (var instanceof PsiParameter && parent instanceof PsiMethod) {
|
||||
addSuggestionsInspiredByFieldNames(set, matcher, var, project, codeStyleManager);
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2009 JetBrains s.r.o.
|
||||
* Copyright 2000-2014 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,7 +20,6 @@ import com.intellij.codeInsight.CodeInsightSettings;
|
||||
import com.intellij.codeInsight.completion.JavaClassReferenceCompletionContributor;
|
||||
import com.intellij.openapi.editor.Editor;
|
||||
import com.intellij.openapi.editor.EditorModificationUtil;
|
||||
import com.intellij.openapi.editor.ScrollType;
|
||||
import com.intellij.openapi.editor.ex.EditorEx;
|
||||
import com.intellij.openapi.editor.highlighter.HighlighterIterator;
|
||||
import com.intellij.openapi.fileTypes.FileType;
|
||||
@@ -132,7 +131,7 @@ public class JavaTypedHandler extends TypedHandlerDelegate {
|
||||
return Result.CONTINUE;
|
||||
}
|
||||
if (PsiTreeUtil.getParentOfType(leaf, PsiCodeBlock.class, false, PsiMember.class) != null) {
|
||||
EditorModificationUtil.insertStringAtCaret(editor, "{", false, true);
|
||||
EditorModificationUtil.typeInStringAtCaretHonorMultipleCarets(editor, "{");
|
||||
TypedHandler.indentOpenedBrace(project, editor);
|
||||
return Result.STOP;
|
||||
}
|
||||
@@ -170,8 +169,7 @@ public class JavaTypedHandler extends TypedHandlerDelegate {
|
||||
char charAt = editor.getDocument().getCharsSequence().charAt(offset);
|
||||
if (charAt != ';') return false;
|
||||
|
||||
editor.getCaretModel().moveToOffset(offset + 1);
|
||||
editor.getScrollingModel().scrollToCaret(ScrollType.RELATIVE);
|
||||
EditorModificationUtil.moveAllCaretsRelatively(editor, 1);
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -211,8 +209,7 @@ public class JavaTypedHandler extends TypedHandlerDelegate {
|
||||
}
|
||||
|
||||
if (balance == 0) {
|
||||
editor.getCaretModel().moveToOffset(offset + 1);
|
||||
editor.getScrollingModel().scrollToCaret(ScrollType.RELATIVE);
|
||||
EditorModificationUtil.moveAllCaretsRelatively(editor, 1);
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -251,7 +248,12 @@ public class JavaTypedHandler extends TypedHandlerDelegate {
|
||||
}
|
||||
|
||||
if (balance == 1) {
|
||||
editor.getDocument().insertString(offset, ">");
|
||||
if (editor.getCaretModel().supportsMultipleCarets()) {
|
||||
EditorModificationUtil.typeInStringAtCaretHonorMultipleCarets(editor, ">", 0);
|
||||
}
|
||||
else {
|
||||
editor.getDocument().insertString(offset, ">");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -103,7 +103,7 @@ public class PropertyUtil {
|
||||
return Comparing.equal(PsiUtil.resolveClassInType(TypeConversionUtil.erasure(returnType)), method.getContainingClass());
|
||||
}
|
||||
|
||||
@Nullable public static String getPropertyName(PsiMethod method) {
|
||||
@Nullable public static String getPropertyName(@NotNull PsiMethod method) {
|
||||
if (isSimplePropertyGetter(method)) {
|
||||
return getPropertyNameByGetter(method);
|
||||
}
|
||||
|
||||
+1
-1
@@ -163,7 +163,7 @@ public class PsiMethodReferenceExpressionImpl extends PsiReferenceExpressionBase
|
||||
if (containingClass != null) {
|
||||
PsiMethod[] methods = null;
|
||||
if (element instanceof PsiIdentifier) {
|
||||
methods = containingClass.findMethodsByName(element.getText(), true);
|
||||
methods = containingClass.findMethodsByName(element.getText(), !qualifierResolveResult.isReferenceTypeQualified());
|
||||
}
|
||||
else if (isConstructor()) {
|
||||
final PsiElementFactory factory = JavaPsiFacade.getElementFactory(getProject());
|
||||
|
||||
+15
@@ -0,0 +1,15 @@
|
||||
import java.util.function.ToIntFunction;
|
||||
class Test {
|
||||
{
|
||||
fooBar(String::length);
|
||||
}
|
||||
|
||||
class Foo<K> {
|
||||
Foo<K> then() {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
static <T> Foo<T> fooBar(ToIntFunction<? super T> keyExtractor) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
if (true)
|
||||
{<caret>
|
||||
if (true)
|
||||
{<caret>
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
if (true)
|
||||
<caret>
|
||||
if (true)
|
||||
<caret>
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
if (true) {
|
||||
System.out.println();
|
||||
}<caret>
|
||||
if (true) {
|
||||
System.out.println();
|
||||
}<caret>
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
if (true) {
|
||||
System.out.println();
|
||||
<caret>
|
||||
if (true) {
|
||||
System.out.println();
|
||||
<caret>
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
if (true) {
|
||||
List<<caret>>
|
||||
}
|
||||
if (true) {
|
||||
List<<caret>>
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
if (true) {
|
||||
List<caret>
|
||||
}
|
||||
if (true) {
|
||||
List<caret>
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
System.out.println("<caret>");
|
||||
System.out.println("<caret>");
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
System.out.println(<caret>);
|
||||
System.out.println(<caret>);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
System.exit(<caret>)
|
||||
System.exit(<caret>)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
System.exit<caret>
|
||||
System.exit<caret>
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
java.util.List<String> l1 = new java.util.ArrayList<><caret>();
|
||||
java.util.List<String> l2 = new java.util.ArrayList<><caret>();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
java.util.List<String> l1 = new java.util.ArrayList<<caret>>();
|
||||
java.util.List<String> l2 = new java.util.ArrayList<<caret>>();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
System.out.println(""<caret>);
|
||||
System.out.println(""<caret>);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
System.out.println("<caret>");
|
||||
System.out.println("<caret>");
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
System.exit()<caret>
|
||||
System.exit()<caret>
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
System.exit(<caret>)
|
||||
System.exit(<caret>)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
System.out.println();<caret>
|
||||
System.out.println();<caret>
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
class Foo {
|
||||
void m() {
|
||||
System.out.println()<caret>;
|
||||
System.out.println()<caret>;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,70 @@
|
||||
/*
|
||||
* Copyright 2000-2014 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;
|
||||
|
||||
import com.intellij.testFramework.PlatformTestUtil;
|
||||
import com.intellij.testFramework.fixtures.LightPlatformCodeInsightFixtureTestCase;
|
||||
|
||||
import java.io.File;
|
||||
|
||||
public class JavaTypingTest extends LightPlatformCodeInsightFixtureTestCase {
|
||||
public void testMulticaretIndentLBrace() {
|
||||
doTest('{');
|
||||
}
|
||||
|
||||
public void testMulticaretIndentRBrace() {
|
||||
doTest('}');
|
||||
}
|
||||
|
||||
public void testMulticaretSkipSemicolon() {
|
||||
doTest(';');
|
||||
}
|
||||
|
||||
public void testMulticaretSkipGt() {
|
||||
doTest('>');
|
||||
}
|
||||
|
||||
public void testMulticaretInsertGt() {
|
||||
doTest('<');
|
||||
}
|
||||
|
||||
public void testMulticaretSkipRParen() {
|
||||
doTest(')');
|
||||
}
|
||||
|
||||
public void testMulticaretInsertRParen() {
|
||||
doTest('(');
|
||||
}
|
||||
|
||||
public void testMulticaretSkipQuote() {
|
||||
doTest('"');
|
||||
}
|
||||
|
||||
public void testMulticaretInsertQuote() {
|
||||
doTest('"');
|
||||
}
|
||||
|
||||
private void doTest(char c) {
|
||||
myFixture.configureByFile(getTestName(true) + "_before.java");
|
||||
myFixture.type(c);
|
||||
myFixture.checkResultByFile(getTestName(true) + "_after.java");
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String getTestDataPath() {
|
||||
return PlatformTestUtil.getCommunityPath().replace(File.separatorChar, '/') + "/java/java-tests/testData/codeInsight/typing";
|
||||
}
|
||||
}
|
||||
+4
@@ -209,6 +209,10 @@ public class NewMethodRefHighlightingTest extends LightDaemonAnalyzerTestCase {
|
||||
doTest();
|
||||
}
|
||||
|
||||
public void testIDEA112191() throws Exception {
|
||||
doTest();
|
||||
}
|
||||
|
||||
private void doTest() {
|
||||
doTest(false);
|
||||
}
|
||||
|
||||
Binary file not shown.
|
After Width: | Height: | Size: 2.9 KiB |
Binary file not shown.
|
After Width: | Height: | Size: 7.5 KiB |
@@ -31,6 +31,7 @@
|
||||
<orderEntry type="module" module-name="jps-model-impl" />
|
||||
<orderEntry type="module" module-name="analysis-impl" exported="" />
|
||||
<orderEntry type="module" module-name="structure-view-impl" exported="" />
|
||||
<orderEntry type="module" module-name="RegExpSupport" />
|
||||
</component>
|
||||
</module>
|
||||
|
||||
|
||||
@@ -191,7 +191,7 @@ public class TypedHandler extends TypedActionHandlerBase {
|
||||
}
|
||||
}
|
||||
|
||||
if (!editor.getSelectionModel().hasBlockSelection() && editor.getCaretModel().getCaretCount() == 1) {
|
||||
if (!editor.getSelectionModel().hasBlockSelection()) {
|
||||
if (')' == charTyped || ']' == charTyped || '}' == charTyped) {
|
||||
if (FileTypes.PLAIN_TEXT != fileType) {
|
||||
if (handleRParen(editor, fileType, charTyped)) return;
|
||||
@@ -210,7 +210,7 @@ public class TypedHandler extends TypedActionHandlerBase {
|
||||
|
||||
if (('(' == charTyped || '[' == charTyped || '{' == charTyped) &&
|
||||
CodeInsightSettings.getInstance().AUTOINSERT_PAIR_BRACKET &&
|
||||
!editor.getSelectionModel().hasBlockSelection() && editor.getCaretModel().getCaretCount() == 1 && fileType != FileTypes.PLAIN_TEXT) {
|
||||
!editor.getSelectionModel().hasBlockSelection() && fileType != FileTypes.PLAIN_TEXT) {
|
||||
handleAfterLParen(editor, fileType, charTyped);
|
||||
}
|
||||
else if ('}' == charTyped) {
|
||||
@@ -361,7 +361,12 @@ public class TypedHandler extends TypedActionHandlerBase {
|
||||
else {
|
||||
throw new AssertionError("Unknown char "+lparenChar);
|
||||
}
|
||||
editor.getDocument().insertString(offset, text);
|
||||
if (editor.getCaretModel().supportsMultipleCarets()) {
|
||||
EditorModificationUtil.typeInStringAtCaretHonorMultipleCarets(editor, text, 0);
|
||||
}
|
||||
else {
|
||||
editor.getDocument().insertString(offset, text);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -417,8 +422,7 @@ public class TypedHandler extends TypedActionHandlerBase {
|
||||
|
||||
if (!matched) return false;
|
||||
|
||||
editor.getCaretModel().moveToOffset(offset + 1);
|
||||
editor.getScrollingModel().scrollToCaret(ScrollType.RELATIVE);
|
||||
EditorModificationUtil.moveAllCaretsRelatively(editor, 1);
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -436,8 +440,7 @@ public class TypedHandler extends TypedActionHandlerBase {
|
||||
|
||||
if (offset < length && chars.charAt(offset) == quote){
|
||||
if (isClosingQuote(editor, quoteHandler, offset)){
|
||||
editor.getCaretModel().moveToOffset(offset + 1);
|
||||
editor.getScrollingModel().scrollToCaret(ScrollType.RELATIVE);
|
||||
EditorModificationUtil.moveAllCaretsRelatively(editor, 1);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@@ -456,7 +459,9 @@ public class TypedHandler extends TypedActionHandlerBase {
|
||||
}
|
||||
}
|
||||
|
||||
myOriginalHandler.execute(editor, quote, dataContext);
|
||||
if (myOriginalHandler != null) {
|
||||
myOriginalHandler.execute(editor, quote, dataContext);
|
||||
}
|
||||
offset = editor.getCaretModel().getOffset();
|
||||
|
||||
if (quoteHandler instanceof MultiCharQuoteHandler) {
|
||||
@@ -464,7 +469,12 @@ public class TypedHandler extends TypedActionHandlerBase {
|
||||
if (closingQuote != null && hasNonClosedLiterals(editor, quoteHandler, offset - 1)) {
|
||||
if (offset == document.getTextLength() ||
|
||||
!Character.isUnicodeIdentifierPart(document.getCharsSequence().charAt(offset))) { //any better heuristic or an API?
|
||||
document.insertString(offset, closingQuote);
|
||||
if (editor.getCaretModel().supportsMultipleCarets()) {
|
||||
EditorModificationUtil.typeInStringAtCaretHonorMultipleCarets(editor, closingQuote.toString(), 0);
|
||||
}
|
||||
else {
|
||||
document.insertString(offset, closingQuote);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@@ -473,7 +483,12 @@ public class TypedHandler extends TypedActionHandlerBase {
|
||||
if (isOpeningQuote(editor, quoteHandler, offset - 1) && hasNonClosedLiterals(editor, quoteHandler, offset - 1)) {
|
||||
if (offset == document.getTextLength() ||
|
||||
!Character.isUnicodeIdentifierPart(document.getCharsSequence().charAt(offset))) { //any better heuristic or an API?
|
||||
document.insertString(offset, String.valueOf(quote));
|
||||
if (editor.getCaretModel().supportsMultipleCarets()) {
|
||||
EditorModificationUtil.typeInStringAtCaretHonorMultipleCarets(editor, String.valueOf(quote), 0);
|
||||
}
|
||||
else {
|
||||
document.insertString(offset, String.valueOf(quote));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -558,67 +573,72 @@ public class TypedHandler extends TypedActionHandlerBase {
|
||||
}
|
||||
|
||||
private static void indentBrace(@NotNull final Project project, @NotNull final Editor editor, final char braceChar) {
|
||||
final int offset = editor.getCaretModel().getOffset() - 1;
|
||||
final Document document = editor.getDocument();
|
||||
CharSequence chars = document.getCharsSequence();
|
||||
if (offset < 0 || chars.charAt(offset) != braceChar) return;
|
||||
editor.getCaretModel().runForEachCaret(new CaretAction() {
|
||||
@Override
|
||||
public void perform(Caret caret) {
|
||||
final int offset = editor.getCaretModel().getOffset() - 1;
|
||||
final Document document = editor.getDocument();
|
||||
CharSequence chars = document.getCharsSequence();
|
||||
if (offset < 0 || chars.charAt(offset) != braceChar) return;
|
||||
|
||||
int spaceStart = CharArrayUtil.shiftBackward(chars, offset - 1, " \t");
|
||||
if (spaceStart < 0 || chars.charAt(spaceStart) == '\n' || chars.charAt(spaceStart) == '\r'){
|
||||
PsiDocumentManager documentManager = PsiDocumentManager.getInstance(project);
|
||||
documentManager.commitDocument(document);
|
||||
int spaceStart = CharArrayUtil.shiftBackward(chars, offset - 1, " \t");
|
||||
if (spaceStart < 0 || chars.charAt(spaceStart) == '\n' || chars.charAt(spaceStart) == '\r'){
|
||||
PsiDocumentManager documentManager = PsiDocumentManager.getInstance(project);
|
||||
documentManager.commitDocument(document);
|
||||
|
||||
final PsiFile file = documentManager.getPsiFile(document);
|
||||
if (file == null || !file.isWritable()) return;
|
||||
PsiElement element = file.findElementAt(offset);
|
||||
if (element == null) return;
|
||||
final PsiFile file = documentManager.getPsiFile(document);
|
||||
if (file == null || !file.isWritable()) return;
|
||||
PsiElement element = file.findElementAt(offset);
|
||||
if (element == null) return;
|
||||
|
||||
EditorHighlighter highlighter = ((EditorEx)editor).getHighlighter();
|
||||
HighlighterIterator iterator = highlighter.createIterator(offset);
|
||||
EditorHighlighter highlighter = ((EditorEx)editor).getHighlighter();
|
||||
HighlighterIterator iterator = highlighter.createIterator(offset);
|
||||
|
||||
final FileType fileType = file.getFileType();
|
||||
BraceMatcher braceMatcher = BraceMatchingUtil.getBraceMatcher(fileType, iterator);
|
||||
boolean rBraceToken = braceMatcher.isRBraceToken(iterator, chars, fileType);
|
||||
final boolean isBrace = braceMatcher.isLBraceToken(iterator, chars, fileType) || rBraceToken;
|
||||
int lBraceOffset = -1;
|
||||
final FileType fileType = file.getFileType();
|
||||
BraceMatcher braceMatcher = BraceMatchingUtil.getBraceMatcher(fileType, iterator);
|
||||
boolean rBraceToken = braceMatcher.isRBraceToken(iterator, chars, fileType);
|
||||
final boolean isBrace = braceMatcher.isLBraceToken(iterator, chars, fileType) || rBraceToken;
|
||||
int lBraceOffset = -1;
|
||||
|
||||
if (CodeInsightSettings.getInstance().REFORMAT_BLOCK_ON_RBRACE &&
|
||||
rBraceToken &&
|
||||
braceMatcher.isStructuralBrace(iterator, chars, fileType) && offset > 0) {
|
||||
lBraceOffset = BraceMatchingUtil.findLeftLParen(
|
||||
highlighter.createIterator(offset - 1),
|
||||
braceMatcher.getOppositeBraceTokenType(iterator.getTokenType()),
|
||||
editor.getDocument().getCharsSequence(),
|
||||
fileType
|
||||
);
|
||||
}
|
||||
if (element.getNode() != null && isBrace) {
|
||||
final int finalLBraceOffset = lBraceOffset;
|
||||
ApplicationManager.getApplication().runWriteAction(new Runnable() {
|
||||
@Override
|
||||
public void run(){
|
||||
try{
|
||||
int newOffset;
|
||||
if (finalLBraceOffset != -1) {
|
||||
RangeMarker marker = document.createRangeMarker(offset, offset + 1);
|
||||
CodeStyleManager.getInstance(project).reformatRange(file, finalLBraceOffset, offset, true);
|
||||
newOffset = marker.getStartOffset();
|
||||
marker.dispose();
|
||||
} else {
|
||||
newOffset = CodeStyleManager.getInstance(project).adjustLineIndent(file, offset);
|
||||
}
|
||||
|
||||
editor.getCaretModel().moveToOffset(newOffset + 1);
|
||||
editor.getScrollingModel().scrollToCaret(ScrollType.RELATIVE);
|
||||
editor.getSelectionModel().removeSelection();
|
||||
}
|
||||
catch(IncorrectOperationException e){
|
||||
LOG.error(e);
|
||||
}
|
||||
if (CodeInsightSettings.getInstance().REFORMAT_BLOCK_ON_RBRACE &&
|
||||
rBraceToken &&
|
||||
braceMatcher.isStructuralBrace(iterator, chars, fileType) && offset > 0) {
|
||||
lBraceOffset = BraceMatchingUtil.findLeftLParen(
|
||||
highlighter.createIterator(offset - 1),
|
||||
braceMatcher.getOppositeBraceTokenType(iterator.getTokenType()),
|
||||
editor.getDocument().getCharsSequence(),
|
||||
fileType
|
||||
);
|
||||
}
|
||||
});
|
||||
if (element.getNode() != null && isBrace) {
|
||||
final int finalLBraceOffset = lBraceOffset;
|
||||
ApplicationManager.getApplication().runWriteAction(new Runnable() {
|
||||
@Override
|
||||
public void run(){
|
||||
try{
|
||||
int newOffset;
|
||||
if (finalLBraceOffset != -1) {
|
||||
RangeMarker marker = document.createRangeMarker(offset, offset + 1);
|
||||
CodeStyleManager.getInstance(project).reformatRange(file, finalLBraceOffset, offset, true);
|
||||
newOffset = marker.getStartOffset();
|
||||
marker.dispose();
|
||||
} else {
|
||||
newOffset = CodeStyleManager.getInstance(project).adjustLineIndent(file, offset);
|
||||
}
|
||||
|
||||
editor.getCaretModel().moveToOffset(newOffset + 1);
|
||||
editor.getScrollingModel().scrollToCaret(ScrollType.RELATIVE);
|
||||
editor.getSelectionModel().removeSelection();
|
||||
}
|
||||
catch(IncorrectOperationException e){
|
||||
LOG.error(e);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+3
-3
@@ -36,8 +36,8 @@ import com.intellij.openapi.util.Pair;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.codeStyle.CodeStyleManager;
|
||||
import com.intellij.psi.codeStyle.CodeStyleSettings;
|
||||
import com.intellij.psi.codeStyle.CodeStyleSettingsManager;
|
||||
import com.intellij.psi.codeStyle.CommonCodeStyleSettings;
|
||||
import com.intellij.psi.codeStyle.Indent;
|
||||
import com.intellij.psi.templateLanguages.MultipleLangCommentProvider;
|
||||
import com.intellij.psi.templateLanguages.OuterLanguageElement;
|
||||
@@ -55,7 +55,7 @@ import java.util.List;
|
||||
public class CommentByBlockCommentHandler implements CodeInsightActionHandler {
|
||||
private Project myProject;
|
||||
private Editor myEditor;
|
||||
private PsiFile myFile;
|
||||
private @NotNull PsiFile myFile;
|
||||
private Document myDocument;
|
||||
private CommenterDataHolder mySelfManagedCommenterData;
|
||||
|
||||
@@ -402,7 +402,7 @@ public class CommentByBlockCommentHandler implements CodeInsightActionHandler {
|
||||
if (startOffset == 0 || chars.charAt(startOffset - 1) == '\n') {
|
||||
if (endOffset == myDocument.getTextLength() || endOffset > 0 && chars.charAt(endOffset - 1) == '\n') {
|
||||
CodeStyleManager codeStyleManager = CodeStyleManager.getInstance(myProject);
|
||||
CodeStyleSettings settings = CodeStyleSettingsManager.getSettings(myProject);
|
||||
CommonCodeStyleSettings settings = CodeStyleSettingsManager.getSettings(myProject).getCommonSettings(myFile.getLanguage());
|
||||
String space;
|
||||
if (!settings.BLOCK_COMMENT_AT_FIRST_COLUMN) {
|
||||
final FileType fileType = myFile.getFileType();
|
||||
|
||||
+2
-1
@@ -260,7 +260,8 @@ public class CommentByLineCommentHandler implements CodeInsightActionHandler {
|
||||
}
|
||||
|
||||
boolean allLineCommented = true;
|
||||
boolean commentWithIndent = !CodeStyleSettingsManager.getSettings(myProject).LINE_COMMENT_AT_FIRST_COLUMN;
|
||||
boolean commentWithIndent =
|
||||
!CodeStyleSettingsManager.getSettings(myProject).getCommonSettings(myFile.getLanguage()).LINE_COMMENT_AT_FIRST_COLUMN;
|
||||
|
||||
for (int line = myStartLine; line <= myEndLine; line++) {
|
||||
Commenter commenter = blockSuitableCommenter != null ? blockSuitableCommenter : findCommenter(line);
|
||||
|
||||
-9
@@ -60,15 +60,6 @@ public abstract class BaseConsoleExecuteActionHandler extends ConsoleExecuteActi
|
||||
throw new AbstractMethodError();
|
||||
}
|
||||
|
||||
@Deprecated
|
||||
/**
|
||||
* @deprecated to remove in IDEA 14
|
||||
*
|
||||
* Never used. It is Python specific implementation.
|
||||
*/
|
||||
public void finishExecution() {
|
||||
}
|
||||
|
||||
public String getEmptyExecuteAction() {
|
||||
return ConsoleExecuteAction.CONSOLE_EXECUTE_ACTION_ID;
|
||||
}
|
||||
|
||||
@@ -152,11 +152,16 @@ public class ConsoleExecuteAction extends DumbAwareAction {
|
||||
return true;
|
||||
}
|
||||
|
||||
public void setAddCurrentToHistory(boolean addCurrentToHistory) {
|
||||
public final void setAddCurrentToHistory(boolean addCurrentToHistory) {
|
||||
myAddToHistory = addCurrentToHistory;
|
||||
}
|
||||
|
||||
protected void beforeExecution(@NotNull LanguageConsoleImpl console) {
|
||||
}
|
||||
|
||||
final void runExecuteAction(@NotNull LanguageConsoleImpl console, @Nullable LanguageConsoleView consoleView) {
|
||||
beforeExecution(console);
|
||||
|
||||
String text = console.prepareExecuteAction(myAddToHistory, myPreserveMarkup, true);
|
||||
((UndoManagerImpl)UndoManager.getInstance(console.getProject())).invalidateActionsFor(DocumentReferenceManager.getInstance().create(console.getCurrentEditor().getDocument()));
|
||||
addToCommandHistoryAndExecute(console, consoleView, text);
|
||||
|
||||
@@ -92,6 +92,8 @@ public class LanguageConsoleImpl implements Disposable, TypeSafeDataProvider {
|
||||
private String myTitle;
|
||||
@Nullable
|
||||
private String myPrompt = "> ";
|
||||
private TextAttributes myPromptAttributes = ConsoleViewContentType.USER_INPUT.getAttributes();
|
||||
|
||||
private final LightVirtualFile myHistoryFile;
|
||||
private Editor myCurrentEditor;
|
||||
|
||||
@@ -332,6 +334,10 @@ public class LanguageConsoleImpl implements Disposable, TypeSafeDataProvider {
|
||||
return myPrompt;
|
||||
}
|
||||
|
||||
public void setPromptAttributes(@NotNull TextAttributes textAttributes) {
|
||||
myPromptAttributes = textAttributes;
|
||||
}
|
||||
|
||||
public void setPrompt(@Nullable String prompt) {
|
||||
// always add space to the prompt otherwise it may look ugly
|
||||
myPrompt = prompt != null && !prompt.endsWith(" ") ? prompt + " " : prompt;
|
||||
@@ -344,7 +350,7 @@ public class LanguageConsoleImpl implements Disposable, TypeSafeDataProvider {
|
||||
UIUtil.invokeAndWaitIfNeeded(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
myConsoleEditor.setPrefixTextAndAttributes(prompt, ConsoleViewContentType.USER_INPUT.getAttributes());
|
||||
myConsoleEditor.setPrefixTextAndAttributes(prompt, myPromptAttributes);
|
||||
if (myPanel.isVisible()) {
|
||||
queueUiUpdate(false);
|
||||
}
|
||||
@@ -540,7 +546,7 @@ public class LanguageConsoleImpl implements Disposable, TypeSafeDataProvider {
|
||||
}
|
||||
|
||||
protected void doAddPromptToHistory() {
|
||||
addTextToHistory(myPrompt, ConsoleViewContentType.USER_INPUT.getAttributes());
|
||||
addTextToHistory(myPrompt, myPromptAttributes);
|
||||
}
|
||||
|
||||
// returns the real (cyclic-buffer-aware) start offset of the inserted text
|
||||
|
||||
@@ -28,8 +28,7 @@ import com.intellij.openapi.fileChooser.FileChooser;
|
||||
import com.intellij.openapi.fileChooser.FileChooserDescriptor;
|
||||
import com.intellij.openapi.fileChooser.FileChooserDescriptorFactory;
|
||||
import com.intellij.openapi.fileTypes.FileType;
|
||||
import com.intellij.openapi.fileTypes.FileTypeManager;
|
||||
import com.intellij.openapi.fileTypes.FileTypes;
|
||||
import com.intellij.openapi.fileTypes.PlainTextFileType;
|
||||
import com.intellij.openapi.help.HelpManager;
|
||||
import com.intellij.openapi.module.Module;
|
||||
import com.intellij.openapi.module.ModuleManager;
|
||||
@@ -56,7 +55,7 @@ import com.intellij.ui.components.labels.LinkListener;
|
||||
import com.intellij.util.ArrayUtil;
|
||||
import com.intellij.util.Consumer;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
import org.intellij.lang.regexp.RegExpFileType;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@@ -668,15 +667,10 @@ public class FindDialog extends DialogWrapper {
|
||||
final Component editorComponent = inputComboBox.getEditor().getEditorComponent();
|
||||
|
||||
if (editorComponent instanceof EditorTextField) {
|
||||
boolean selected = myCbRegularExpressions.isSelectedWhenSelectable();
|
||||
@NonNls final String s = selected ? "*.regexp" : "*.txt";
|
||||
FileType fileType = FileTypeManager.getInstance().getFileTypeByFileName(s);
|
||||
|
||||
if (selected && fileType == FileTypes.UNKNOWN) {
|
||||
fileType = FileTypeManager.getInstance().getFileTypeByFileName("*.txt"); // RegExp plugin is not installed
|
||||
}
|
||||
|
||||
final PsiFile file = PsiFileFactory.getInstance(myProject).createFileFromText(s, fileType, ((EditorTextField)editorComponent).getText(), -1, true);
|
||||
boolean isRegexp = myCbRegularExpressions.isSelectedWhenSelectable();
|
||||
FileType fileType = isRegexp ? RegExpFileType.INSTANCE : PlainTextFileType.INSTANCE;
|
||||
String fileName = isRegexp ? "a.regexp" : "a.txt";
|
||||
final PsiFile file = PsiFileFactory.getInstance(myProject).createFileFromText(fileName, fileType, ((EditorTextField)editorComponent).getText(), -1, true);
|
||||
|
||||
((EditorTextField)editorComponent).setNewDocumentAndFileType(fileType, PsiDocumentManager.getInstance(myProject).getDocument(file));
|
||||
}
|
||||
|
||||
@@ -34,6 +34,7 @@ import com.intellij.openapi.progress.ProgressIndicator;
|
||||
import com.intellij.openapi.progress.ProgressManager;
|
||||
import com.intellij.openapi.progress.util.ProgressWrapper;
|
||||
import com.intellij.openapi.progress.util.TooManyUsagesStatus;
|
||||
import com.intellij.openapi.project.DumbServiceImpl;
|
||||
import com.intellij.openapi.project.IndexNotReadyException;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.util.Computable;
|
||||
@@ -71,14 +72,16 @@ public class FindInProjectUtil {
|
||||
private FindInProjectUtil() {}
|
||||
|
||||
public static void setDirectoryName(@NotNull FindModel model, @NotNull DataContext dataContext) {
|
||||
PsiElement psiElement;
|
||||
try {
|
||||
psiElement = CommonDataKeys.PSI_ELEMENT.getData(dataContext);
|
||||
}
|
||||
catch (IndexNotReadyException e) {
|
||||
psiElement = null;
|
||||
PsiElement psiElement = null;
|
||||
Project project = CommonDataKeys.PROJECT.getData(dataContext);
|
||||
|
||||
if (project != null && !DumbServiceImpl.getInstance(project).isDumb()) {
|
||||
try {
|
||||
psiElement = CommonDataKeys.PSI_ELEMENT.getData(dataContext);
|
||||
} catch (IndexNotReadyException ignore) {}
|
||||
}
|
||||
|
||||
|
||||
String directoryName = null;
|
||||
|
||||
if (psiElement instanceof PsiDirectory) {
|
||||
|
||||
@@ -994,8 +994,8 @@ public class SearchEverywhereAction extends AnAction implements CustomComponentA
|
||||
}
|
||||
|
||||
Color bg = cmp.getBackground();
|
||||
cmp.setBackground(UIUtil.getListBackground(isSelected));
|
||||
if (bg == null) {
|
||||
cmp.setBackground(UIUtil.getListBackground(isSelected));
|
||||
bg = cmp.getBackground();
|
||||
}
|
||||
myMainPanel.setBorder(new CustomLineBorder(bg, 0, 0, 2, 0));
|
||||
|
||||
@@ -56,21 +56,24 @@ class RootIndex {
|
||||
private final Map<VirtualFile, DirectoryInfo> myInfoCache = ContainerUtil.newConcurrentMap();
|
||||
private final List<JpsModuleSourceRootType<?>> myRootTypes = ContainerUtil.newArrayList();
|
||||
private final TObjectIntHashMap<JpsModuleSourceRootType<?>> myRootTypeId = new TObjectIntHashMap<JpsModuleSourceRootType<?>>();
|
||||
@NotNull private final Project myProject;
|
||||
private volatile Map<VirtualFile, OrderEntry[]> myOrderEntries;
|
||||
|
||||
RootIndex(@NotNull final Project project) {
|
||||
myProject = project;
|
||||
final RootInfo info = buildRootInfo(project);
|
||||
|
||||
Set<VirtualFile> allRoots = info.getAllRoots();
|
||||
for (VirtualFile root : allRoots) {
|
||||
List<VirtualFile> hierarchy = getHierarchy(root, allRoots, info);
|
||||
Pair<DirectoryInfo, String> pair = hierarchy == null ? new Pair<DirectoryInfo, String>(null, null) : info.calcDirectoryInfo(root, hierarchy);
|
||||
Pair<DirectoryInfo, String> pair = hierarchy == null ? new Pair<DirectoryInfo, String>(null, null) : calcDirectoryInfo(root, hierarchy, info);
|
||||
cacheInfos(root, root, pair.first);
|
||||
myPackagePrefixRoots.putValue(pair.second, root);
|
||||
if (info.shouldMarkAsProjectExcluded(root, hierarchy)) {
|
||||
myProjectExcludedRoots.add(root);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
myModuleExcludedRoots = info.excludedFromModule.keySet();
|
||||
}
|
||||
|
||||
@@ -78,17 +81,14 @@ class RootIndex {
|
||||
final RootInfo info = new RootInfo();
|
||||
for (final Module module : ModuleManager.getInstance(project).getModules()) {
|
||||
final ModuleRootManager moduleRootManager = ModuleRootManager.getInstance(module);
|
||||
final OrderEntry[] orderEntries = moduleRootManager.getOrderEntries();
|
||||
final ContentEntry[] contentEntries = moduleRootManager.getContentEntries();
|
||||
final VirtualFile[] contentRoots = moduleRootManager.getContentRoots();
|
||||
|
||||
for (final VirtualFile contentRoot : contentRoots) {
|
||||
for (final VirtualFile contentRoot : moduleRootManager.getContentRoots()) {
|
||||
if (!info.contentRootOf.containsKey(contentRoot)) {
|
||||
info.contentRootOf.put(contentRoot, module);
|
||||
}
|
||||
}
|
||||
|
||||
for (ContentEntry contentEntry : contentEntries) {
|
||||
for (ContentEntry contentEntry : moduleRootManager.getContentEntries()) {
|
||||
for (VirtualFile excludeRoot : contentEntry.getExcludeFolderFiles()) {
|
||||
info.excludedFromModule.put(excludeRoot, module);
|
||||
}
|
||||
@@ -105,21 +105,8 @@ class RootIndex {
|
||||
}
|
||||
}
|
||||
|
||||
for (OrderEntry orderEntry : orderEntries) {
|
||||
// init ordered entries
|
||||
if (orderEntry instanceof ModuleOrderEntry) {
|
||||
final Module depModule = ((ModuleOrderEntry)orderEntry).getModule();
|
||||
if (depModule != null) {
|
||||
VirtualFile[] importedClassRoots = OrderEnumerator.orderEntries(depModule).exportedOnly().recursively().classes().usingCache().getRoots();
|
||||
for (VirtualFile importedClassRoot : importedClassRoots) {
|
||||
info.depEntries.putValue(importedClassRoot, orderEntry);
|
||||
}
|
||||
}
|
||||
for (VirtualFile sourceRoot : orderEntry.getFiles(OrderRootType.SOURCES)) {
|
||||
info.depEntries.putValue(sourceRoot, orderEntry);
|
||||
}
|
||||
}
|
||||
else if (orderEntry instanceof LibraryOrSdkOrderEntry) {
|
||||
for (OrderEntry orderEntry : moduleRootManager.getOrderEntries()) {
|
||||
if (orderEntry instanceof LibraryOrSdkOrderEntry) {
|
||||
final LibraryOrSdkOrderEntry entry = (LibraryOrSdkOrderEntry)orderEntry;
|
||||
final VirtualFile[] sourceRoots = entry.getRootFiles(OrderRootType.SOURCES);
|
||||
final VirtualFile[] classRoots = entry.getRootFiles(OrderRootType.CLASSES);
|
||||
@@ -127,14 +114,14 @@ class RootIndex {
|
||||
// Init library sources
|
||||
for (final VirtualFile sourceRoot : sourceRoots) {
|
||||
info.classAndSourceRoots.add(sourceRoot);
|
||||
info.libSourceRootEntries.putValue(sourceRoot, orderEntry);
|
||||
info.libraryOrSdkSources.add(sourceRoot);
|
||||
info.packagePrefix.put(sourceRoot, "");
|
||||
}
|
||||
|
||||
// init library classes
|
||||
for (final VirtualFile classRoot : classRoots) {
|
||||
info.classAndSourceRoots.add(classRoot);
|
||||
info.libClassRootEntries.putValue(classRoot, orderEntry);
|
||||
info.libraryOrSdkClasses.add(classRoot);
|
||||
info.packagePrefix.put(classRoot, "");
|
||||
}
|
||||
|
||||
@@ -163,6 +150,77 @@ class RootIndex {
|
||||
return info;
|
||||
}
|
||||
|
||||
private Map<VirtualFile, OrderEntry[]> getOrderEntries() {
|
||||
Map<VirtualFile, OrderEntry[]> result = myOrderEntries;
|
||||
if (result != null) return result;
|
||||
|
||||
MultiMap<VirtualFile, OrderEntry> libClassRootEntries = MultiMap.createSmartList();
|
||||
MultiMap<VirtualFile, OrderEntry> libSourceRootEntries = MultiMap.createSmartList();
|
||||
MultiMap<VirtualFile, OrderEntry> depEntries = MultiMap.createSmartList();
|
||||
|
||||
for (final Module module : ModuleManager.getInstance(myProject).getModules()) {
|
||||
final ModuleRootManager moduleRootManager = ModuleRootManager.getInstance(module);
|
||||
for (OrderEntry orderEntry : moduleRootManager.getOrderEntries()) {
|
||||
if (orderEntry instanceof ModuleOrderEntry) {
|
||||
final Module depModule = ((ModuleOrderEntry)orderEntry).getModule();
|
||||
if (depModule != null) {
|
||||
VirtualFile[] importedClassRoots = OrderEnumerator.orderEntries(depModule).exportedOnly().recursively().classes().usingCache().getRoots();
|
||||
for (VirtualFile importedClassRoot : importedClassRoots) {
|
||||
depEntries.putValue(importedClassRoot, orderEntry);
|
||||
}
|
||||
}
|
||||
for (VirtualFile sourceRoot : orderEntry.getFiles(OrderRootType.SOURCES)) {
|
||||
depEntries.putValue(sourceRoot, orderEntry);
|
||||
}
|
||||
}
|
||||
else if (orderEntry instanceof LibraryOrSdkOrderEntry) {
|
||||
final LibraryOrSdkOrderEntry entry = (LibraryOrSdkOrderEntry)orderEntry;
|
||||
for (final VirtualFile sourceRoot : entry.getRootFiles(OrderRootType.SOURCES)) {
|
||||
libSourceRootEntries.putValue(sourceRoot, orderEntry);
|
||||
}
|
||||
for (final VirtualFile classRoot : entry.getRootFiles(OrderRootType.CLASSES)) {
|
||||
libClassRootEntries.putValue(classRoot, orderEntry);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
RootInfo rootInfo = buildRootInfo(myProject);
|
||||
result = ContainerUtil.newHashMap();
|
||||
Set<VirtualFile> allRoots = rootInfo.getAllRoots();
|
||||
for (VirtualFile file : allRoots) {
|
||||
List<VirtualFile> hierarchy = getHierarchy(file, allRoots, rootInfo);
|
||||
result.put(file, hierarchy == null ? OrderEntry.EMPTY_ARRAY : calcOrderEntries(rootInfo, depEntries, libClassRootEntries, libSourceRootEntries, hierarchy));
|
||||
}
|
||||
myOrderEntries = result;
|
||||
return result;
|
||||
}
|
||||
|
||||
private static OrderEntry[] calcOrderEntries(RootInfo info,
|
||||
MultiMap<VirtualFile, OrderEntry> depEntries,
|
||||
MultiMap<VirtualFile, OrderEntry> libClassRootEntries,
|
||||
MultiMap<VirtualFile, OrderEntry> libSourceRootEntries, List<VirtualFile> hierarchy) {
|
||||
@Nullable VirtualFile libraryClassRoot = info.findLibraryRootInfo(hierarchy, false);
|
||||
@Nullable VirtualFile librarySourceRoot = info.findLibraryRootInfo(hierarchy, true);
|
||||
Set<OrderEntry> orderEntries = ContainerUtil.newLinkedHashSet();
|
||||
orderEntries.addAll(info.getLibraryOrderEntries(hierarchy, libraryClassRoot, librarySourceRoot, libClassRootEntries, libSourceRootEntries));
|
||||
for (VirtualFile root : hierarchy) {
|
||||
orderEntries.addAll(depEntries.get(root));
|
||||
}
|
||||
VirtualFile moduleContentRoot = info.findModuleRootInfo(hierarchy);
|
||||
if (moduleContentRoot != null) {
|
||||
ContainerUtil.addIfNotNull(orderEntries, info.getModuleSourceEntry(hierarchy, moduleContentRoot, libClassRootEntries));
|
||||
}
|
||||
if (orderEntries.isEmpty()) {
|
||||
return null;
|
||||
}
|
||||
|
||||
OrderEntry[] array = orderEntries.toArray(new OrderEntry[orderEntries.size()]);
|
||||
Arrays.sort(array, DirectoryInfo.BY_OWNER_MODULE);
|
||||
return array;
|
||||
}
|
||||
|
||||
|
||||
public void checkConsistency() {
|
||||
for (VirtualFile file : myProjectExcludedRoots) {
|
||||
assert file.exists() : file.getPath() + " does not exist";
|
||||
@@ -338,19 +396,18 @@ class RootIndex {
|
||||
// getDirectoriesByPackageName used to be in this order, some clients might rely on that
|
||||
@NotNull final LinkedHashSet<VirtualFile> classAndSourceRoots = ContainerUtil.newLinkedHashSet();
|
||||
|
||||
@NotNull final Set<VirtualFile> libraryOrSdkSources = ContainerUtil.newHashSet();
|
||||
@NotNull final Set<VirtualFile> libraryOrSdkClasses = ContainerUtil.newHashSet();
|
||||
@NotNull final Map<VirtualFile, Module> contentRootOf = ContainerUtil.newHashMap();
|
||||
@NotNull final MultiMap<VirtualFile, Module> sourceRootOf = MultiMap.createSet();
|
||||
@NotNull final TObjectIntHashMap<VirtualFile> rootTypeId = new TObjectIntHashMap<VirtualFile>();
|
||||
@NotNull final MultiMap<VirtualFile, OrderEntry> libClassRootEntries = MultiMap.createSmartList();
|
||||
@NotNull final MultiMap<VirtualFile, OrderEntry> libSourceRootEntries = MultiMap.createSmartList();
|
||||
@NotNull final MultiMap<VirtualFile, OrderEntry> depEntries = MultiMap.createSmartList();
|
||||
@NotNull final MultiMap<VirtualFile, Library> excludedFromLibraries = MultiMap.createSmartList();
|
||||
@NotNull final MultiMap<VirtualFile, Library> classOfLibraries = MultiMap.createSmartList();
|
||||
@NotNull final MultiMap<VirtualFile, Library> sourceOfLibraries = MultiMap.createSmartList();
|
||||
@NotNull final Set<VirtualFile> excludedFromProject = ContainerUtil.newHashSet();
|
||||
@NotNull final Map<VirtualFile, Module> excludedFromModule = ContainerUtil.newHashMap();
|
||||
@NotNull final Map<VirtualFile, String> packagePrefix = ContainerUtil.newHashMap();
|
||||
|
||||
|
||||
Set<VirtualFile> getAllRoots() {
|
||||
LinkedHashSet<VirtualFile> result = ContainerUtil.newLinkedHashSet();
|
||||
result.addAll(classAndSourceRoots);
|
||||
@@ -371,7 +428,7 @@ class RootIndex {
|
||||
}
|
||||
}) == null;
|
||||
}
|
||||
|
||||
|
||||
@Nullable
|
||||
private VirtualFile findModuleRootInfo(List<VirtualFile> hierarchy) {
|
||||
for (VirtualFile root : hierarchy) {
|
||||
@@ -392,10 +449,10 @@ class RootIndex {
|
||||
Set<Library> librariesToIgnore = ContainerUtil.newHashSet();
|
||||
for (VirtualFile root : hierarchy) {
|
||||
librariesToIgnore.addAll(excludedFromLibraries.get(root));
|
||||
if (source && libSourceRootEntries.containsKey(root) &&
|
||||
if (source && libraryOrSdkSources.contains(root) &&
|
||||
(!sourceOfLibraries.containsKey(root) || !librariesToIgnore.containsAll(sourceOfLibraries.get(root)))) {
|
||||
return root;
|
||||
} else if (!source && libClassRootEntries.containsKey(root) &&
|
||||
} else if (!source && libraryOrSdkClasses.contains(root) &&
|
||||
(!classOfLibraries.containsKey(root) || !librariesToIgnore.containsAll(classOfLibraries.get(root)))) {
|
||||
return root;
|
||||
}
|
||||
@@ -403,35 +460,6 @@ class RootIndex {
|
||||
return null;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private Pair<DirectoryInfo, String> calcDirectoryInfo(VirtualFile root, @NotNull final List<VirtualFile> hierarchy) {
|
||||
VirtualFile moduleContentRoot = findModuleRootInfo(hierarchy);
|
||||
VirtualFile libraryClassRoot = findLibraryRootInfo(hierarchy, false);
|
||||
VirtualFile librarySourceRoot = findLibraryRootInfo(hierarchy, true);
|
||||
if (moduleContentRoot == null && libraryClassRoot == null && librarySourceRoot == null) {
|
||||
return new Pair<DirectoryInfo, String>(null, null);
|
||||
}
|
||||
|
||||
VirtualFile sourceRoot = findPackageRootInfo(hierarchy, moduleContentRoot, null, librarySourceRoot);
|
||||
|
||||
VirtualFile moduleSourceRoot = findPackageRootInfo(hierarchy, moduleContentRoot, null, null);
|
||||
boolean inModuleSources = moduleSourceRoot != null;
|
||||
boolean inLibrarySource = librarySourceRoot != null;
|
||||
int typeId = moduleSourceRoot != null ? rootTypeId.get(moduleSourceRoot) : 0;
|
||||
|
||||
OrderEntry[] entries = getOrderEntries(hierarchy, moduleContentRoot, libraryClassRoot, librarySourceRoot);
|
||||
DirectoryInfo directoryInfo = new DirectoryInfo(contentRootOf.get(moduleContentRoot),
|
||||
moduleContentRoot,
|
||||
sourceRoot,
|
||||
libraryClassRoot,
|
||||
(byte)DirectoryInfo.createSourceRootTypeData(inModuleSources, inLibrarySource, typeId),
|
||||
entries);
|
||||
|
||||
String packagePrefix = calcPackagePrefix(root, hierarchy, moduleContentRoot, libraryClassRoot, librarySourceRoot);
|
||||
|
||||
return Pair.create(directoryInfo, packagePrefix);
|
||||
}
|
||||
|
||||
private String calcPackagePrefix(VirtualFile root,
|
||||
List<VirtualFile> hierarchy,
|
||||
VirtualFile moduleContentRoot,
|
||||
@@ -467,31 +495,28 @@ class RootIndex {
|
||||
return null;
|
||||
}
|
||||
|
||||
private void collectDependencyOrderEntries(List<VirtualFile> hierarchy, Set<OrderEntry> result) {
|
||||
for (VirtualFile root : hierarchy) {
|
||||
result.addAll(depEntries.get(root));
|
||||
}
|
||||
}
|
||||
|
||||
private void collectLibraryOrderEntries(List<VirtualFile> hierarchy,
|
||||
@Nullable VirtualFile libraryClassRoot,
|
||||
@Nullable VirtualFile librarySourceRoot,
|
||||
Set<OrderEntry> result) {
|
||||
private LinkedHashSet<OrderEntry> getLibraryOrderEntries(List<VirtualFile> hierarchy,
|
||||
@Nullable VirtualFile libraryClassRoot,
|
||||
@Nullable VirtualFile librarySourceRoot,
|
||||
MultiMap<VirtualFile, OrderEntry> libClassRootEntries,
|
||||
MultiMap<VirtualFile, OrderEntry> libSourceRootEntries) {
|
||||
LinkedHashSet<OrderEntry> orderEntries = ContainerUtil.newLinkedHashSet();
|
||||
for (VirtualFile root : hierarchy) {
|
||||
if (root == libraryClassRoot && !sourceRootOf.containsKey(root)) {
|
||||
result.addAll(libClassRootEntries.get(root));
|
||||
orderEntries.addAll(libClassRootEntries.get(root));
|
||||
}
|
||||
if (root == librarySourceRoot && libraryClassRoot == null) {
|
||||
result.addAll(libSourceRootEntries.get(root));
|
||||
orderEntries.addAll(libSourceRootEntries.get(root));
|
||||
}
|
||||
if (libClassRootEntries.containsKey(root) || sourceRootOf.containsKey(root) && librarySourceRoot == null) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
return orderEntries;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private ModuleSourceOrderEntry getModuleSourceEntry(List<VirtualFile> hierarchy, @NotNull VirtualFile moduleContentRoot) {
|
||||
private ModuleSourceOrderEntry getModuleSourceEntry(List<VirtualFile> hierarchy, @NotNull VirtualFile moduleContentRoot, MultiMap<VirtualFile, OrderEntry> libClassRootEntries) {
|
||||
Module module = contentRootOf.get(moduleContentRoot);
|
||||
for (VirtualFile root : hierarchy) {
|
||||
if (sourceRootOf.get(root).contains(module)) {
|
||||
@@ -504,24 +529,42 @@ class RootIndex {
|
||||
return null;
|
||||
}
|
||||
|
||||
private OrderEntry[] getOrderEntries(List<VirtualFile> hierarchy,
|
||||
@Nullable VirtualFile moduleContentRoot,
|
||||
@Nullable VirtualFile libraryClassRoot,
|
||||
@Nullable VirtualFile librarySourceRoot) {
|
||||
LinkedHashSet<OrderEntry> orderEntries = ContainerUtil.newLinkedHashSet();
|
||||
collectLibraryOrderEntries(hierarchy, libraryClassRoot, librarySourceRoot, orderEntries);
|
||||
collectDependencyOrderEntries(hierarchy, orderEntries);
|
||||
if (moduleContentRoot != null) {
|
||||
ContainerUtil.addIfNotNull(orderEntries, getModuleSourceEntry(hierarchy, moduleContentRoot));
|
||||
}
|
||||
if (orderEntries.isEmpty()) {
|
||||
return null;
|
||||
}
|
||||
|
||||
OrderEntry[] array = orderEntries.toArray(new OrderEntry[orderEntries.size()]);
|
||||
Arrays.sort(array, DirectoryInfo.BY_OWNER_MODULE);
|
||||
return array;
|
||||
}
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private Pair<DirectoryInfo, String> calcDirectoryInfo(final VirtualFile root, @NotNull final List<VirtualFile> hierarchy, RootInfo info) {
|
||||
VirtualFile moduleContentRoot = info.findModuleRootInfo(hierarchy);
|
||||
VirtualFile libraryClassRoot = info.findLibraryRootInfo(hierarchy, false);
|
||||
VirtualFile librarySourceRoot = info.findLibraryRootInfo(hierarchy, true);
|
||||
if (moduleContentRoot == null && libraryClassRoot == null && librarySourceRoot == null) {
|
||||
return new Pair<DirectoryInfo, String>(null, null);
|
||||
}
|
||||
|
||||
VirtualFile sourceRoot = info.findPackageRootInfo(hierarchy, moduleContentRoot, null, librarySourceRoot);
|
||||
|
||||
VirtualFile moduleSourceRoot = info.findPackageRootInfo(hierarchy, moduleContentRoot, null, null);
|
||||
boolean inModuleSources = moduleSourceRoot != null;
|
||||
boolean inLibrarySource = librarySourceRoot != null;
|
||||
int typeId = moduleSourceRoot != null ? info.rootTypeId.get(moduleSourceRoot) : 0;
|
||||
|
||||
DirectoryInfo directoryInfo = new DirectoryInfo(info.contentRootOf.get(moduleContentRoot),
|
||||
moduleContentRoot,
|
||||
sourceRoot,
|
||||
libraryClassRoot,
|
||||
(byte)DirectoryInfo.createSourceRootTypeData(inModuleSources, inLibrarySource, typeId),
|
||||
null) {
|
||||
@NotNull
|
||||
@Override
|
||||
public OrderEntry[] getOrderEntries() {
|
||||
OrderEntry[] entries = RootIndex.this.getOrderEntries().get(root);
|
||||
return entries == null ? OrderEntry.EMPTY_ARRAY : entries;
|
||||
}
|
||||
};
|
||||
|
||||
String packagePrefix = info.calcPackagePrefix(root, hierarchy, moduleContentRoot, libraryClassRoot, librarySourceRoot);
|
||||
|
||||
return Pair.create(directoryInfo, packagePrefix);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -218,7 +218,7 @@ public class DeferredIconImpl<T> implements DeferredIcon {
|
||||
|
||||
private void setDone(@NotNull Icon result) {
|
||||
if (myEvalListener != null) {
|
||||
myEvalListener.evalDone(myParam, result);
|
||||
myEvalListener.evalDone(this, myParam, result);
|
||||
}
|
||||
|
||||
myDone = true;
|
||||
@@ -334,6 +334,6 @@ public class DeferredIconImpl<T> implements DeferredIcon {
|
||||
}
|
||||
|
||||
public interface IconListener<T> {
|
||||
void evalDone(T key, @NotNull Icon result);
|
||||
void evalDone(DeferredIconImpl<T> source, T key, @NotNull Icon result);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -82,7 +82,7 @@ public class IconDeferrerImpl extends IconDeferrer {
|
||||
return deferImpl(base, param, f, true);
|
||||
}
|
||||
|
||||
private <T> Icon deferImpl(Icon base, T param, @NotNull Function<T, Icon> f, boolean autoupdatable) {
|
||||
private <T> Icon deferImpl(Icon base, T param, @NotNull Function<T, Icon> f, final boolean autoupdatable) {
|
||||
if (myEvaluationIsInProgress.get().booleanValue()) {
|
||||
return f.fun(param);
|
||||
}
|
||||
@@ -93,11 +93,11 @@ public class IconDeferrerImpl extends IconDeferrer {
|
||||
final long started = myLastClearTimestamp;
|
||||
result = new DeferredIconImpl<T>(base, param, f, new DeferredIconImpl.IconListener<T>() {
|
||||
@Override
|
||||
public void evalDone(T key, @NotNull Icon r) {
|
||||
public void evalDone(DeferredIconImpl<T> source, T key, @NotNull Icon r) {
|
||||
synchronized (LOCK) {
|
||||
// check if our results is not outdated yet
|
||||
if (started == myLastClearTimestamp) {
|
||||
myIconsCache.put(key, r);
|
||||
myIconsCache.put(key, autoupdatable ? source: r);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -49,7 +49,11 @@ import java.util.concurrent.ConcurrentMap;
|
||||
* and set its indexed state to unindexed
|
||||
* if we get other event we set indexed state to outdated
|
||||
*
|
||||
* Index stamp is file timestamp of the index directory, we assume that index stamps are monotonically increasing
|
||||
* Index stamp is file timestamp of the index directory, it is assumed that index stamps are monotonically increasing, but
|
||||
* still << Long.MAX_VALUE: there are two negative special timestamps used for marking outdated / unindexed index state.
|
||||
* The code doesn't take overflow of real file timestaps (or their coincidence to negative special timestamps) into account because
|
||||
* it will happen (if time will go as forward as it does today) near year 292277094 (=new java.util.Date(Long.MAX_VALUE).getYear()).
|
||||
* At that time (if this code will be still actual) we can use positive small timestamps for special cases.
|
||||
*/
|
||||
public class IndexingStamp {
|
||||
private static final long UNINDEXED_STAMP = -1L; // we don't store trivial "absent" state
|
||||
|
||||
+8
-9
@@ -16,20 +16,19 @@
|
||||
|
||||
package com.intellij.history.integration.ui.actions;
|
||||
|
||||
import com.intellij.ide.actions.NonTrivialActionGroup;
|
||||
import com.intellij.openapi.actionSystem.AnActionEvent;
|
||||
import com.intellij.openapi.actionSystem.CommonDataKeys;
|
||||
import com.intellij.openapi.actionSystem.DefaultActionGroup;
|
||||
import com.intellij.openapi.actionSystem.PlatformDataKeys;
|
||||
import com.intellij.openapi.actionSystem.Presentation;
|
||||
import com.intellij.openapi.project.DumbAware;
|
||||
|
||||
public class LocalHistoryGroup extends DefaultActionGroup implements DumbAware {
|
||||
public class LocalHistoryGroup extends NonTrivialActionGroup implements DumbAware {
|
||||
public void update(AnActionEvent event) {
|
||||
Presentation p = event.getPresentation();
|
||||
boolean hasProject = event.getData(CommonDataKeys.PROJECT) != null;
|
||||
|
||||
p.setVisible(hasProject);
|
||||
p.setEnabled(hasProject);
|
||||
if (event.getData(CommonDataKeys.PROJECT) == null) {
|
||||
event.getPresentation().setEnabledAndVisible(false);
|
||||
}
|
||||
else {
|
||||
super.update(event);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -17,6 +17,7 @@
|
||||
package com.intellij.history.integration.ui.actions;
|
||||
|
||||
import com.intellij.history.LocalHistory;
|
||||
import com.intellij.history.core.LocalHistoryFacade;
|
||||
import com.intellij.history.integration.IdeaGateway;
|
||||
import com.intellij.openapi.actionSystem.AnActionEvent;
|
||||
import com.intellij.openapi.project.Project;
|
||||
@@ -34,4 +35,9 @@ public class PutLabelAction extends LocalHistoryActionWithDialog {
|
||||
if (labelName == null) return;
|
||||
LocalHistory.getInstance().putUserLabel(p, labelName);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected boolean isEnabled(LocalHistoryFacade vcs, IdeaGateway gw, VirtualFile f, AnActionEvent e) {
|
||||
return f != null && gw.isVersioned(f);
|
||||
}
|
||||
}
|
||||
@@ -178,6 +178,18 @@ public class EditorModificationUtil {
|
||||
|
||||
if (editor.getCaretModel().supportsMultipleCarets()) {
|
||||
int caretCount = editor.getCaretModel().getCaretCount();
|
||||
if (caretCount == 1 && editor.isColumnMode()) {
|
||||
int pastedLineCount = LineTokenizer.calcLineCount(text, true);
|
||||
deleteSelectedText(editor);
|
||||
Caret caret = editor.getCaretModel().getPrimaryCaret();
|
||||
for (int i = 0; i < pastedLineCount - 1; i++) {
|
||||
caret = caret.clone(false);
|
||||
if (caret == null) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
caretCount = editor.getCaretModel().getCaretCount();
|
||||
}
|
||||
final Iterator<String> segments = new ClipboardTextPerCaretSplitter().split(text, caretCount).iterator();
|
||||
editor.getCaretModel().runForEachCaret(new CaretAction() {
|
||||
@Override
|
||||
@@ -403,6 +415,14 @@ public class EditorModificationUtil {
|
||||
}
|
||||
}
|
||||
|
||||
public static void typeInStringAtCaretHonorMultipleCarets(final Editor editor, @NotNull final String str) {
|
||||
typeInStringAtCaretHonorMultipleCarets(editor, str, true, str.length());
|
||||
}
|
||||
|
||||
public static void typeInStringAtCaretHonorMultipleCarets(final Editor editor, @NotNull final String str, final int caretShift) {
|
||||
typeInStringAtCaretHonorMultipleCarets(editor, str, true, caretShift);
|
||||
}
|
||||
|
||||
public static void typeInStringAtCaretHonorMultipleCarets(final Editor editor, @NotNull final String str, final boolean toProcessOverwriteMode) {
|
||||
typeInStringAtCaretHonorMultipleCarets(editor, str, toProcessOverwriteMode, str.length());
|
||||
}
|
||||
|
||||
@@ -35,7 +35,7 @@ public class TextBrowseFolderListener extends ComponentWithBrowseButton.BrowseFo
|
||||
myTextComponent = component;
|
||||
}
|
||||
|
||||
FileChooserDescriptor gFileChooserDescriptor() {
|
||||
FileChooserDescriptor getFileChooserDescriptor() {
|
||||
return myFileChooserDescriptor;
|
||||
}
|
||||
}
|
||||
@@ -59,7 +59,7 @@ public class TextFieldWithBrowseButton extends ComponentWithBrowseButton<JTextFi
|
||||
public void addBrowseFolderListener(@NotNull TextBrowseFolderListener listener) {
|
||||
listener.setOwnerComponent(this);
|
||||
addBrowseFolderListener(null, listener, true);
|
||||
installPathCompletion(listener.gFileChooserDescriptor());
|
||||
installPathCompletion(listener.getFileChooserDescriptor());
|
||||
}
|
||||
|
||||
protected void installPathCompletion(final FileChooserDescriptor fileChooserDescriptor) {
|
||||
|
||||
@@ -182,8 +182,10 @@ public abstract class FocusCommand extends ActiveRunnable implements Expirable {
|
||||
// This change seems reasonable to me. But as far as some implementations
|
||||
// can ignore the "forced" parameter we can get bad focus behaviour.
|
||||
// So let's start from mac.
|
||||
if (!myToFocus.requestFocusInWindow() && (isForced() && SystemInfo.isMac)) {
|
||||
myToFocus.requestFocus();
|
||||
if (!(myToFocus.requestFocusInWindow())) {
|
||||
if (!SystemInfo.isMac || isForced() ) {
|
||||
myToFocus.requestFocus();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -123,10 +123,20 @@ public interface ToolWindow extends BusyObject {
|
||||
|
||||
/**
|
||||
* Sets new window title.
|
||||
* @exception IllegalStateException if tool window isn't installed.
|
||||
*/
|
||||
void setTitle(String title);
|
||||
|
||||
/**
|
||||
* @return window stripe button text.
|
||||
*/
|
||||
@NotNull
|
||||
String getStripeTitle();
|
||||
|
||||
/**
|
||||
* Sets new window stripe button text.
|
||||
*/
|
||||
void setStripeTitle(@NotNull String title);
|
||||
|
||||
/**
|
||||
* @return whether the window is available or not.
|
||||
*/
|
||||
|
||||
@@ -21,8 +21,8 @@ public class ToolWindowContentUiType {
|
||||
|
||||
private static final Logger LOG = Logger.getInstance("#com.intellij.openapi.wm.ToolWindowContentUiType");
|
||||
|
||||
public static ToolWindowContentUiType TABBED = new ToolWindowContentUiType("tabs");
|
||||
public static ToolWindowContentUiType COMBO = new ToolWindowContentUiType("combo");
|
||||
public static final ToolWindowContentUiType TABBED = new ToolWindowContentUiType("tabs");
|
||||
public static final ToolWindowContentUiType COMBO = new ToolWindowContentUiType("combo");
|
||||
|
||||
private final String myName;
|
||||
|
||||
|
||||
@@ -40,9 +40,10 @@ public class ColorPanel extends JComponent {
|
||||
addMouseListener(new MouseAdapter() {
|
||||
@Override
|
||||
public void mousePressed(MouseEvent e) {
|
||||
if (!isEnabled() || !isEditable) return;
|
||||
Color color = ColorChooser.chooseColor(ColorPanel.this, UIBundle.message("color.panel.select.color.dialog.description"), myColor);
|
||||
if (color != null) {
|
||||
myColor = color;
|
||||
setSelectedColor(color);
|
||||
fireActionEvent();
|
||||
}
|
||||
}
|
||||
@@ -87,7 +88,7 @@ public class ColorPanel extends JComponent {
|
||||
return null;
|
||||
}
|
||||
StringBuilder buffer = new StringBuilder("0x").append(ColorUtil.toHex(myColor).toUpperCase());
|
||||
if (isEnabled()) {
|
||||
if (isEnabled() && isEditable) {
|
||||
buffer.append(" (Click to customize)");
|
||||
}
|
||||
return buffer.toString();
|
||||
|
||||
@@ -16,6 +16,7 @@
|
||||
package com.intellij.util.ui;
|
||||
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
@@ -34,7 +35,7 @@ public class FadeInFadeOut extends JComponent {
|
||||
private final BufferedImage myComponentImage;
|
||||
private Rectangle myComponentBounds;
|
||||
|
||||
@NotNull
|
||||
@Nullable
|
||||
private final Component myIcon;
|
||||
private Rectangle myIconBounds;
|
||||
|
||||
@@ -46,7 +47,7 @@ public class FadeInFadeOut extends JComponent {
|
||||
private Runnable myOnDone = null;
|
||||
|
||||
|
||||
public FadeInFadeOut(@NotNull Component component, int timeToComplete, boolean fadeIn, @NotNull Component icon) {
|
||||
public FadeInFadeOut(@NotNull Component component, int timeToComplete, boolean fadeIn, @Nullable Component icon) {
|
||||
setFocusable(false);
|
||||
myComponent = component;
|
||||
myFadeIn = fadeIn;
|
||||
@@ -81,7 +82,11 @@ public class FadeInFadeOut extends JComponent {
|
||||
super.reshape(x, y, w, h);
|
||||
if (!myTriggered) {
|
||||
myComponentBounds = SwingUtilities.convertRectangle(myComponent.getParent(), myComponent.getBounds(), this);
|
||||
myIconBounds = SwingUtilities.convertRectangle(myIcon.getParent(), myIcon.getBounds(), this);
|
||||
if (myIcon == null) {
|
||||
myIconBounds = myComponentBounds;
|
||||
} else {
|
||||
myIconBounds = SwingUtilities.convertRectangle(myIcon.getParent(), myIcon.getBounds(), this);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -16,12 +16,14 @@
|
||||
*/
|
||||
package com.intellij.ide.actions;
|
||||
|
||||
import com.intellij.icons.AllIcons;
|
||||
import com.intellij.ide.IdeBundle;
|
||||
import com.intellij.notification.EventLog;
|
||||
import com.intellij.openapi.actionSystem.*;
|
||||
import com.intellij.openapi.keymap.Keymap;
|
||||
import com.intellij.openapi.keymap.KeymapManager;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.project.DumbAware;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.wm.ToolWindow;
|
||||
import com.intellij.openapi.wm.ToolWindowManager;
|
||||
import com.intellij.ui.SizedIcon;
|
||||
@@ -55,6 +57,9 @@ public class ActivateToolWindowAction extends AnAction implements DumbAware {
|
||||
presentation.setVisible(toolWindow!=null);
|
||||
if (toolWindow != null) {
|
||||
Icon icon = toolWindow.getIcon();
|
||||
if (EventLog.LOG_TOOL_WINDOW_ID.equals(myToolWindowId)) {
|
||||
icon = AllIcons.Ide.Info_notifications;
|
||||
}
|
||||
presentation.setIcon(icon == null ? null : new SizedIcon(icon, icon.getIconHeight(), icon.getIconHeight()));
|
||||
}
|
||||
}
|
||||
|
||||
+2
-2
@@ -15,7 +15,7 @@
|
||||
*/
|
||||
package com.intellij.ide.passwordSafe.impl.providers.masterKey;
|
||||
|
||||
import com.intellij.openapi.ui.Messages;
|
||||
import com.intellij.icons.AllIcons;
|
||||
import com.intellij.openapi.ui.ValidationInfo;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -47,7 +47,7 @@ public abstract class PasswordComponentBase {
|
||||
mySafe = safe;
|
||||
myTitle = title;
|
||||
myIconLabel.setText("");
|
||||
myIconLabel.setIcon(Messages.getQuestionIcon()); // todo add some lock icon
|
||||
myIconLabel.setIcon(AllIcons.General.PasswordLock);
|
||||
//myPromptLabel.setUI(new MultiLineLabelUI());
|
||||
myPromptLabel.setFont(UIUtil.getLabelFont(UIUtil.FontSize.SMALL));
|
||||
|
||||
|
||||
@@ -15,6 +15,7 @@
|
||||
*/
|
||||
package com.intellij.openapi.actionSystem.impl;
|
||||
|
||||
import com.intellij.featureStatistics.FeatureUsageTracker;
|
||||
import com.intellij.ide.ui.UISettings;
|
||||
import com.intellij.openapi.Disposable;
|
||||
import com.intellij.openapi.actionSystem.*;
|
||||
@@ -227,6 +228,10 @@ public class ActionMenuItem extends JCheckBoxMenuItem {
|
||||
public void actionPerformed(final ActionEvent e) {
|
||||
final IdeFocusManager fm = IdeFocusManager.findInstanceByContext(myContext);
|
||||
final ActionCallback typeAhead = new ActionCallback();
|
||||
final String id = ActionManager.getInstance().getId(myAction.getAction());
|
||||
if (id != null) {
|
||||
FeatureUsageTracker.getInstance().triggerFeatureUsed("context.menu.click.stats." + id.replace(' ', '.'));
|
||||
}
|
||||
fm.typeAheadUntil(typeAhead);
|
||||
fm.runOnOwnContext(myContext, new Runnable() {
|
||||
@Override
|
||||
|
||||
@@ -17,12 +17,14 @@
|
||||
package com.intellij.openapi.editor.actions;
|
||||
|
||||
import com.intellij.openapi.actionSystem.DataContext;
|
||||
import com.intellij.openapi.editor.Caret;
|
||||
import com.intellij.openapi.editor.CaretModel;
|
||||
import com.intellij.openapi.editor.Editor;
|
||||
import com.intellij.openapi.editor.SelectionModel;
|
||||
import com.intellij.openapi.editor.actionSystem.EditorAction;
|
||||
import com.intellij.openapi.editor.actionSystem.EditorActionHandler;
|
||||
import com.intellij.openapi.editor.ex.EditorEx;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
/**
|
||||
* @author max
|
||||
@@ -35,17 +37,23 @@ public class EscapeAction extends EditorAction {
|
||||
|
||||
private static class Handler extends EditorActionHandler {
|
||||
@Override
|
||||
public void execute(Editor editor, DataContext dataContext) {
|
||||
public void doExecute(Editor editor, @Nullable Caret caret, DataContext dataContext) {
|
||||
if (editor instanceof EditorEx) {
|
||||
EditorEx editorEx = (EditorEx)editor;
|
||||
if (editorEx.isStickySelection()) {
|
||||
editorEx.setStickySelection(false);
|
||||
}
|
||||
}
|
||||
editor.getCaretModel().removeSecondaryCarets();
|
||||
retainOldestCaret(editor.getCaretModel());
|
||||
editor.getSelectionModel().removeSelection();
|
||||
}
|
||||
|
||||
private static void retainOldestCaret(CaretModel caretModel) {
|
||||
while(caretModel.getCaretCount() > 1) {
|
||||
caretModel.removeCaret(caretModel.getPrimaryCaret());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled(Editor editor, DataContext dataContext) {
|
||||
SelectionModel selectionModel = editor.getSelectionModel();
|
||||
|
||||
@@ -1445,7 +1445,19 @@ public class CaretImpl extends UserDataHolderBase implements Caret {
|
||||
CharSequence text = myEditor.getDocument().getCharsSequence();
|
||||
int selectionStart = getSelectionStart();
|
||||
int selectionEnd = getSelectionEnd();
|
||||
return text.subSequence(selectionStart, selectionEnd).toString();
|
||||
String selectedText = text.subSequence(selectionStart, selectionEnd).toString();
|
||||
if (isVirtualSelectionEnabled() && myEndVirtualOffset > myStartVirtualOffset) {
|
||||
int padding = myEndVirtualOffset - myStartVirtualOffset;
|
||||
StringBuilder builder = new StringBuilder(selectedText.length() + padding);
|
||||
builder.append(selectedText);
|
||||
for (int i = 0; i < padding; i++) {
|
||||
builder.append(' ');
|
||||
}
|
||||
return builder.toString();
|
||||
}
|
||||
else {
|
||||
return selectedText;
|
||||
}
|
||||
}
|
||||
|
||||
private void validateContext(boolean isWrite) {
|
||||
|
||||
@@ -306,6 +306,7 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi
|
||||
private LogicalPosition myLastMousePressedLocation;
|
||||
private VisualPosition myTargetMultiSelectionPosition;
|
||||
private boolean myMultiSelectionInProgress;
|
||||
private boolean myLastPressCreatedCaret;
|
||||
|
||||
private CaretImpl myPrimaryCaret;
|
||||
|
||||
@@ -5670,22 +5671,31 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi
|
||||
final int oldStart = mySelectionModel.getSelectionStart();
|
||||
final int oldEnd = mySelectionModel.getSelectionEnd();
|
||||
|
||||
boolean toggleCaret = myCaretModel.supportsMultipleCarets() && e.getSource() != myGutterComponent && isToggleCaretEvent(e);
|
||||
boolean lastPressCreatedCaret = myLastPressCreatedCaret;
|
||||
if (e.getClickCount() == 1) {
|
||||
myLastPressCreatedCaret = false;
|
||||
}
|
||||
// Don't move caret on mouse press above gutter line markers area (a place where break points, 'override', 'implements' etc icons
|
||||
// are drawn) and annotations area. E.g. we don't want to change caret position if a user sets new break point (clicks
|
||||
// at 'line markers' area).
|
||||
if (e.getSource() != myGutterComponent
|
||||
|| (eventArea != EditorMouseEventArea.LINE_MARKERS_AREA && eventArea != EditorMouseEventArea.ANNOTATIONS_AREA))
|
||||
{
|
||||
boolean toggleCaret = myCaretModel.supportsMultipleCarets() && e.getSource() != myGutterComponent && isToggleCaretEvent(e);
|
||||
LogicalPosition pos = getLogicalPositionForScreenPos(x, y, true);
|
||||
if (toggleCaret) {
|
||||
VisualPosition visualPosition = logicalToVisualPosition(pos);
|
||||
Caret caret = getCaretModel().getCaretAt(visualPosition);
|
||||
if (caret == null) {
|
||||
getCaretModel().addCaret(visualPosition);
|
||||
if (e.getClickCount() == 1) {
|
||||
if (caret == null) {
|
||||
myLastPressCreatedCaret = getCaretModel().addCaret(visualPosition) != null;
|
||||
}
|
||||
else {
|
||||
getCaretModel().removeCaret(caret);
|
||||
}
|
||||
}
|
||||
else {
|
||||
getCaretModel().removeCaret(caret);
|
||||
else if (e.getClickCount() == 3 && lastPressCreatedCaret) {
|
||||
getCaretModel().moveToLogicalPosition(pos);
|
||||
}
|
||||
}
|
||||
else {
|
||||
@@ -5755,7 +5765,8 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi
|
||||
}
|
||||
else {
|
||||
if (!e.isPopupTrigger()
|
||||
&& (eventArea == EditorMouseEventArea.EDITING_AREA || eventArea == EditorMouseEventArea.LINE_NUMBERS_AREA))
|
||||
&& (eventArea == EditorMouseEventArea.EDITING_AREA || eventArea == EditorMouseEventArea.LINE_NUMBERS_AREA)
|
||||
&& (!toggleCaret || lastPressCreatedCaret))
|
||||
{
|
||||
switch (e.getClickCount()) {
|
||||
case 2:
|
||||
|
||||
+18
-4
@@ -482,8 +482,8 @@ public class SelectionModelImpl implements SelectionModel, PrioritizedDocumentLi
|
||||
public String getSelectedText(boolean allCarets) {
|
||||
validateContext(false);
|
||||
|
||||
CharSequence text = myEditor.getDocument().getCharsSequence();
|
||||
if (hasBlockSelection() || (myEditor.getCaretModel().supportsMultipleCarets() && allCarets)) {
|
||||
if (hasBlockSelection()) {
|
||||
CharSequence text = myEditor.getDocument().getCharsSequence();
|
||||
int[] starts = getBlockSelectionStarts();
|
||||
int[] ends = getBlockSelectionEnds();
|
||||
int width = myEditor.getCaretModel().supportsMultipleCarets() ? 0 : Math.abs(myBlockEnd.column - myBlockStart.column);
|
||||
@@ -496,8 +496,22 @@ public class SelectionModelImpl implements SelectionModel, PrioritizedDocumentLi
|
||||
}
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
return myEditor.getCaretModel().getCurrentCaret().getSelectedText();
|
||||
else if (myEditor.getCaretModel().supportsMultipleCarets() && allCarets) {
|
||||
final StringBuilder buf = new StringBuilder();
|
||||
String separator = "";
|
||||
for (Caret caret : myEditor.getCaretModel().getAllCarets()) {
|
||||
buf.append(separator);
|
||||
String caretSelectedText = caret.getSelectedText();
|
||||
if (caretSelectedText != null) {
|
||||
buf.append(caretSelectedText);
|
||||
}
|
||||
separator = "\n";
|
||||
}
|
||||
return buf.toString();
|
||||
}
|
||||
else {
|
||||
return myEditor.getCaretModel().getCurrentCaret().getSelectedText();
|
||||
}
|
||||
}
|
||||
|
||||
private static void appendCharSequence(@NotNull StringBuilder buf, @NotNull CharSequence s, int srcOffset, int len) {
|
||||
|
||||
+7
-8
@@ -148,7 +148,7 @@ public final class UpdateChecker {
|
||||
|
||||
private static void doUpdateAndShowResult(final @Nullable Project project,
|
||||
final boolean enableLink,
|
||||
final boolean showDialog,
|
||||
final boolean manualCheck,
|
||||
final @Nullable PluginHostsConfigurable hostsConfigurable,
|
||||
final UpdateSettings updateSettings,
|
||||
final @Nullable ProgressIndicator indicator,
|
||||
@@ -161,17 +161,17 @@ public final class UpdateChecker {
|
||||
settings.setKnownChannelIds(result.getAllChannelsIds());
|
||||
}
|
||||
else if (result.getState() == UpdateStrategy.State.CONNECTION_ERROR) {
|
||||
showErrorMessage(showDialog, project, IdeBundle.message("updates.error.connection.failed"));
|
||||
showErrorMessage(manualCheck, project, IdeBundle.message("updates.error.connection.failed"));
|
||||
return;
|
||||
}
|
||||
|
||||
boolean platformUpdate = newChannelReady(result.getChannelToPropose()) || result.getUpdatedChannel() != null;
|
||||
final List<PluginDownloader> updatedPlugins = platformUpdate ? null : updatePlugins(showDialog, project, hostsConfigurable, indicator);
|
||||
final List<PluginDownloader> updatedPlugins = platformUpdate ? null : updatePlugins(manualCheck, project, hostsConfigurable, indicator);
|
||||
|
||||
ApplicationManager.getApplication().invokeLater(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
showUpdateResult(project, result, updatedPlugins, enableLink, showDialog);
|
||||
showUpdateResult(project, result, updatedPlugins, enableLink, manualCheck);
|
||||
if (callback != null) {
|
||||
callback.setDone();
|
||||
}
|
||||
@@ -179,7 +179,7 @@ public final class UpdateChecker {
|
||||
});
|
||||
}
|
||||
|
||||
private static List<PluginDownloader> updatePlugins(boolean showDialog,
|
||||
private static List<PluginDownloader> updatePlugins(boolean manualCheck,
|
||||
@Nullable Project project,
|
||||
@Nullable PluginHostsConfigurable hostsConfigurable,
|
||||
@Nullable ProgressIndicator indicator) {
|
||||
@@ -250,12 +250,12 @@ public final class UpdateChecker {
|
||||
return null;
|
||||
}
|
||||
catch (Exception e) {
|
||||
showErrorMessage(showDialog, project, e.getMessage());
|
||||
showErrorMessage(manualCheck, project, e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
if (!failed.isEmpty()) {
|
||||
showErrorMessage(showDialog, project, IdeBundle.message("updates.error.plugin.description.failed", StringUtil.join(failed, ",")));
|
||||
showErrorMessage(manualCheck, project, IdeBundle.message("updates.error.plugin.description.failed", StringUtil.join(failed, ",")));
|
||||
}
|
||||
|
||||
return downloaded.isEmpty() ? null : downloaded;
|
||||
@@ -278,7 +278,6 @@ public final class UpdateChecker {
|
||||
});
|
||||
}
|
||||
else {
|
||||
showNotification(project, message, true, null);
|
||||
LOG.warn(message);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,6 +29,7 @@ public interface ToolWindowEx extends ToolWindow {
|
||||
@NonNls String PROP_AVAILABLE = "available";
|
||||
@NonNls String PROP_ICON = "icon";
|
||||
@NonNls String PROP_TITLE = "title";
|
||||
@NonNls String PROP_STRIPE_TITLE = "stripe-title";
|
||||
|
||||
/**
|
||||
* Removes specified property change listener.
|
||||
|
||||
@@ -15,6 +15,7 @@
|
||||
*/
|
||||
package com.intellij.openapi.wm.impl;
|
||||
|
||||
import com.intellij.featureStatistics.FeatureUsageTracker;
|
||||
import com.intellij.ide.actions.ActivateToolWindowAction;
|
||||
import com.intellij.ide.ui.UISettings;
|
||||
import com.intellij.openapi.actionSystem.ActionGroup;
|
||||
@@ -289,6 +290,7 @@ public final class StripeButton extends AnchoredButton implements ActionListener
|
||||
myDecorator.fireActivated();
|
||||
}
|
||||
myPressedWhenSelected = false;
|
||||
FeatureUsageTracker.getInstance().triggerFeatureUsed("toolwindow.clickstat." + myDecorator.getToolWindow().getId());
|
||||
}
|
||||
|
||||
public void apply(@NotNull WindowInfoImpl info) {
|
||||
@@ -323,7 +325,7 @@ public final class StripeButton extends AnchoredButton implements ActionListener
|
||||
* and short cut registered in the key map.
|
||||
*/
|
||||
void updateText() {
|
||||
String toolWindowId = myDecorator.getToolWindow().getTitle();
|
||||
String toolWindowId = myDecorator.getToolWindow().getStripeTitle();
|
||||
String text = toolWindowId;
|
||||
if (UISettings.getInstance().SHOW_TOOL_WINDOW_NUMBERS) {
|
||||
final int mnemonic = ActivateToolWindowAction.getMnemonicForToolWindow(toolWindowId);
|
||||
@@ -364,7 +366,7 @@ public final class StripeButton extends AnchoredButton implements ActionListener
|
||||
if (ToolWindowEx.PROP_AVAILABLE.equals(name)) {
|
||||
updateState();
|
||||
}
|
||||
else if (ToolWindowEx.PROP_TITLE.equals(name)) {
|
||||
else if (ToolWindowEx.PROP_STRIPE_TITLE.equals(name)) {
|
||||
updateText();
|
||||
}
|
||||
else if (ToolWindowEx.PROP_ICON.equals(name)) {
|
||||
|
||||
@@ -266,7 +266,7 @@ public final class TestWindowManager extends WindowManagerEx implements Applicat
|
||||
|
||||
@Override
|
||||
public IdeFrame findFrameFor(@Nullable Project project) {
|
||||
throw new UnsupportedOperationException();
|
||||
return null;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
|
||||
+10
@@ -163,6 +163,16 @@ public class ToolWindowHeadlessManagerImpl extends ToolWindowManagerEx {
|
||||
public void setTitle(String title) {
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public String getStripeTitle() {
|
||||
return "";
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setStripeTitle(@NotNull String title) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isAvailable() {
|
||||
return false;
|
||||
|
||||
@@ -61,7 +61,7 @@ public final class ToolWindowImpl implements ToolWindowEx {
|
||||
private boolean myAvailable;
|
||||
private final ContentManager myContentManager;
|
||||
private Icon myIcon;
|
||||
private String myTitle;
|
||||
private String myStripeTitle;
|
||||
|
||||
private static final Content EMPTY_CONTENT = new ContentImpl(new JLabel(), "", false);
|
||||
private final ToolWindowContentUi myContentUI;
|
||||
@@ -344,7 +344,13 @@ public final class ToolWindowImpl implements ToolWindowEx {
|
||||
|
||||
public final String getTitle() {
|
||||
ApplicationManager.getApplication().assertIsDispatchThread();
|
||||
return ObjectUtils.notNull(myTitle, myId);
|
||||
return getSelectedContent().getDisplayName();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public final String getStripeTitle() {
|
||||
ApplicationManager.getApplication().assertIsDispatchThread();
|
||||
return ObjectUtils.notNull(myStripeTitle, myId);
|
||||
}
|
||||
|
||||
public final void setIcon(final Icon icon) {
|
||||
@@ -360,11 +366,18 @@ public final class ToolWindowImpl implements ToolWindowEx {
|
||||
|
||||
public final void setTitle(String title) {
|
||||
ApplicationManager.getApplication().assertIsDispatchThread();
|
||||
final String oldTitle = getTitle();
|
||||
myTitle = title;
|
||||
String oldTitle = getTitle();
|
||||
getSelectedContent().setDisplayName(title);
|
||||
myChangeSupport.firePropertyChange(PROP_TITLE, oldTitle, title);
|
||||
}
|
||||
|
||||
public final void setStripeTitle(@NotNull String stripeTitle) {
|
||||
ApplicationManager.getApplication().assertIsDispatchThread();
|
||||
String oldTitle = myStripeTitle;
|
||||
myStripeTitle = stripeTitle;
|
||||
myChangeSupport.firePropertyChange(PROP_STRIPE_TITLE, oldTitle, stripeTitle);
|
||||
}
|
||||
|
||||
private Content getSelectedContent() {
|
||||
final Content selected = getContentManager().getSelectedContent();
|
||||
return selected != null ? selected : EMPTY_CONTENT;
|
||||
|
||||
@@ -575,7 +575,7 @@ public final class ToolWindowManagerImpl extends ToolWindowManagerEx implements
|
||||
|
||||
@Override
|
||||
public void removeToolWindowManagerListener(@NotNull ToolWindowManagerListener l) {
|
||||
myDispatcher.addListener(l);
|
||||
myDispatcher.removeListener(l);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -71,7 +71,7 @@ abstract class ContentLayout {
|
||||
public abstract boolean shouldDrawDecorations();
|
||||
|
||||
protected void updateIdLabel(BaseLabel label) {
|
||||
label.setText(myUi.myWindow.getTitle() + (shouldDrawDecorations() ? ":" : ""));
|
||||
label.setText(myUi.myWindow.getStripeTitle() + (shouldDrawDecorations() ? ":" : ""));
|
||||
label.setBorder(new EmptyBorder(0, 2, 0, 8));
|
||||
|
||||
if (myUi.myManager.getContentCount() == 1) {
|
||||
|
||||
+1
-2
@@ -30,7 +30,6 @@ import com.intellij.openapi.util.SystemInfo;
|
||||
import com.intellij.openapi.util.registry.Registry;
|
||||
import com.intellij.openapi.wm.*;
|
||||
import com.intellij.openapi.wm.impl.IdeFrameImpl;
|
||||
import com.intellij.openapi.wm.impl.ToolWindowImpl;
|
||||
import com.intellij.ui.GotItMessage;
|
||||
import com.intellij.ui.IdeBorderFactory;
|
||||
import com.intellij.ui.UIBundle;
|
||||
@@ -146,7 +145,7 @@ class ToolWindowsWidget extends JLabel implements CustomStatusBarWidget, StatusB
|
||||
@Override
|
||||
public Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) {
|
||||
final ToolWindow toolWindow = (ToolWindow)value;
|
||||
label.setText(toolWindow instanceof ToolWindowImpl ? ((ToolWindowImpl)toolWindow).getId() : toolWindow.getTitle());
|
||||
label.setText(toolWindow.getStripeTitle());
|
||||
label.setIcon(toolWindow.getIcon());
|
||||
label.setBorder(IdeBorderFactory.createEmptyBorder(4, 10, 4, 10));
|
||||
label.setForeground(UIUtil.getListForeground(isSelected));
|
||||
|
||||
@@ -111,7 +111,7 @@ public class PlatformProjectOpenProcessor extends ProjectOpenProcessor {
|
||||
if (baseDir == null) { // no reasonable directory -> create new temp one or use parent
|
||||
if (Registry.is("ide.open.file.in.temp.project.dir")) {
|
||||
try {
|
||||
dummyProjectName = virtualFile.getPath();
|
||||
dummyProjectName = virtualFile.getName();
|
||||
File directory = FileUtil.createTempDirectory(dummyProjectName, null, true);
|
||||
baseDir = LocalFileSystem.getInstance().refreshAndFindFileByIoFile(directory);
|
||||
dummyProject = true;
|
||||
|
||||
@@ -48,6 +48,8 @@ public class SheetController {
|
||||
private JButton myDefaultButton;
|
||||
private JButton myFocusedButton;
|
||||
|
||||
private static int RIGHT_OFFSET = 15;
|
||||
|
||||
public int SHADOW_BORDER = 10;
|
||||
|
||||
// SHEET
|
||||
@@ -132,13 +134,17 @@ public class SheetController {
|
||||
|
||||
private void handleMnemonics(int i, String buttonTitle) {
|
||||
buttons[i].setName(buttonTitle);
|
||||
|
||||
if (buttonTitle.indexOf('&') != -1) {
|
||||
buttons[i].setMnemonic(buttonTitle.charAt(buttonTitle.indexOf('&') + 1));
|
||||
buttonTitle = buttonTitle.replace("&","");
|
||||
}
|
||||
|
||||
buttons[i].setText(buttonTitle);
|
||||
setMnemonicsFromChar('&', buttons[i]);
|
||||
setMnemonicsFromChar('_', buttons[i]);
|
||||
}
|
||||
|
||||
private static void setMnemonicsFromChar(char mnemonicChar, JButton button) {
|
||||
String buttonTitle = button.getText();
|
||||
if (buttonTitle.indexOf(mnemonicChar) != -1) {
|
||||
button.setMnemonic(buttonTitle.charAt(buttonTitle.indexOf(mnemonicChar) + 1));
|
||||
button.setText(buttonTitle.replace(Character.toString(mnemonicChar), ""));
|
||||
}
|
||||
}
|
||||
|
||||
void requestFocus() {
|
||||
@@ -172,9 +178,7 @@ public class SheetController {
|
||||
}
|
||||
|
||||
private final static int TOP_SHEET_PADDING = 15;
|
||||
private final static int GAP_BETWEEN_TITLE_AND_MESSAGE = 10;
|
||||
private final static int GAP_BETWEEN_MESSAGE_AND_BUTTONS = 10;
|
||||
private final static int BUTTONS_PLUS_CHECKBOX = 70;
|
||||
private final static int GAP_BETWEEN_LINES = 10;
|
||||
|
||||
private final static int LEFT_SHEET_PADDING = 35;
|
||||
private final static int LEFT_SHEET_OFFSET = 120;
|
||||
@@ -242,9 +246,22 @@ public class SheetController {
|
||||
messageTextPane.setEditable(false);
|
||||
|
||||
messageTextPane.setContentType("text/html");
|
||||
messageTextPane.setSize(250, Short.MAX_VALUE);
|
||||
|
||||
FontMetrics fontMetrics = mySheetMessage.getFontMetrics(regularFont);
|
||||
|
||||
int widestWordWidth = 250;
|
||||
|
||||
String [] words = message.split(" ");
|
||||
|
||||
for (String word : words) {
|
||||
widestWordWidth = Math.max(fontMetrics.stringWidth(word), widestWordWidth);
|
||||
}
|
||||
|
||||
messageTextPane.setSize(widestWordWidth, Short.MAX_VALUE);
|
||||
messageTextPane.setText(message);
|
||||
messageArea.setSize(250, messageTextPane.getPreferredSize().height);
|
||||
messageArea.setSize(widestWordWidth, messageTextPane.getPreferredSize().height);
|
||||
|
||||
SHEET_WIDTH = Math.max(LEFT_SHEET_OFFSET + widestWordWidth + RIGHT_OFFSET, SHEET_WIDTH);
|
||||
messageTextPane.setSize(messageArea);
|
||||
|
||||
messageTextPane.setOpaque(false);
|
||||
@@ -254,15 +271,23 @@ public class SheetController {
|
||||
|
||||
messageTextPane.repaint();
|
||||
|
||||
SHEET_HEIGHT = TOP_SHEET_PADDING + headerLabel.getPreferredSize().height + GAP_BETWEEN_TITLE_AND_MESSAGE + messageArea.height
|
||||
+ GAP_BETWEEN_MESSAGE_AND_BUTTONS + BUTTONS_PLUS_CHECKBOX;
|
||||
|
||||
|
||||
ico.setOpaque(false);
|
||||
ico.setSize(new Dimension(AllIcons.Logo_welcomeScreen.getIconWidth(), AllIcons.Logo_welcomeScreen.getIconHeight()));
|
||||
ico.setLocation(LEFT_SHEET_PADDING, TOP_SHEET_PADDING);
|
||||
sheetPanel.add(ico);
|
||||
headerLabel.setLocation(LEFT_SHEET_OFFSET, TOP_SHEET_PADDING);
|
||||
messageTextPane.setLocation(LEFT_SHEET_OFFSET, TOP_SHEET_PADDING + headerLabel.getPreferredSize().height + GAP_BETWEEN_TITLE_AND_MESSAGE);
|
||||
messageTextPane.setLocation(LEFT_SHEET_OFFSET, TOP_SHEET_PADDING + headerLabel.getPreferredSize().height + GAP_BETWEEN_LINES);
|
||||
|
||||
SHEET_HEIGHT = TOP_SHEET_PADDING + headerLabel.getPreferredSize().height + GAP_BETWEEN_LINES + messageArea.height
|
||||
+ GAP_BETWEEN_LINES;
|
||||
|
||||
|
||||
if (myDoNotAskOption != null) {
|
||||
layoutDoNotAskCheckbox(sheetPanel);
|
||||
}
|
||||
|
||||
layoutWithAbsoluteLayout(buttons, sheetPanel);
|
||||
|
||||
sheetPanel.setFocusCycleRoot(true);
|
||||
@@ -281,11 +306,6 @@ public class SheetController {
|
||||
|
||||
private void layoutWithAbsoluteLayout(JButton[] buttons, JPanel sheetPanel) {
|
||||
layoutButtons(buttons, sheetPanel);
|
||||
|
||||
if (myDoNotAskOption != null) {
|
||||
layoutDoNotAskCheckbox();
|
||||
sheetPanel.add(doNotAskCheckBox);
|
||||
}
|
||||
}
|
||||
|
||||
private void paintShadow(Graphics2D g2d) {
|
||||
@@ -297,7 +317,9 @@ public class SheetController {
|
||||
|
||||
private void layoutButtons(final JButton[] buttons, JPanel panel) {
|
||||
|
||||
int buttonsWidth = 15;
|
||||
int buttonsWidth = RIGHT_OFFSET;
|
||||
|
||||
|
||||
|
||||
for (JButton button : buttons) {
|
||||
panel.add(button);
|
||||
@@ -313,14 +335,16 @@ public class SheetController {
|
||||
Dimension size = button.getPreferredSize();
|
||||
buttonShift += size.width;
|
||||
button.setBounds(SHEET_WIDTH - buttonShift,
|
||||
SHEET_HEIGHT - 40,
|
||||
SHEET_HEIGHT,
|
||||
size.width, size.height);
|
||||
buttonShift += 10;
|
||||
}
|
||||
|
||||
SHEET_HEIGHT += buttons[0].getHeight() + GAP_BETWEEN_LINES;
|
||||
}
|
||||
|
||||
private void layoutDoNotAskCheckbox() {
|
||||
doNotAskCheckBox = new JCheckBox(myDoNotAskOption.getDoNotShowMessage());
|
||||
private void layoutDoNotAskCheckbox(JPanel sheetPanel) {
|
||||
doNotAskCheckBox = new JCheckBox(myDoNotAskOption.getDoNotShowMessage(), !myDoNotAskOption.isToBeShown());
|
||||
doNotAskCheckBox.addItemListener(new ItemListener() {
|
||||
@Override
|
||||
public void itemStateChanged(ItemEvent e) {
|
||||
@@ -329,7 +353,12 @@ public class SheetController {
|
||||
});
|
||||
doNotAskCheckBox.repaint();
|
||||
doNotAskCheckBox.setSize(doNotAskCheckBox.getPreferredSize());
|
||||
doNotAskCheckBox.setLocation(LEFT_SHEET_OFFSET, SHEET_HEIGHT - BUTTONS_PLUS_CHECKBOX);
|
||||
|
||||
|
||||
doNotAskCheckBox.setLocation(LEFT_SHEET_OFFSET, SHEET_HEIGHT);
|
||||
sheetPanel.add(doNotAskCheckBox);
|
||||
|
||||
SHEET_HEIGHT += doNotAskCheckBox.getHeight() + GAP_BETWEEN_LINES;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -17,7 +17,9 @@ package com.intellij.ui.messages;
|
||||
|
||||
import com.apple.eawt.FullScreenUtilities;
|
||||
import com.intellij.openapi.application.impl.LaterInvocator;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.ui.DialogWrapper;
|
||||
import com.intellij.openapi.util.SystemInfo;
|
||||
import com.intellij.ui.JBColor;
|
||||
import com.intellij.ui.mac.MacMainFrameDecorator;
|
||||
import com.intellij.util.ui.Animator;
|
||||
@@ -28,12 +30,17 @@ import java.awt.event.ComponentAdapter;
|
||||
import java.awt.event.ComponentEvent;
|
||||
import java.awt.event.WindowAdapter;
|
||||
import java.awt.event.WindowEvent;
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
|
||||
/**
|
||||
* Created by Denis Fokin
|
||||
*/
|
||||
public class SheetMessage {
|
||||
|
||||
private static final Logger LOG = Logger.getInstance("#com.intellij.ui.messages.SheetMessage");
|
||||
|
||||
private JDialog myWindow;
|
||||
private Window myParent;
|
||||
private SheetController myController;
|
||||
@@ -73,19 +80,51 @@ public class SheetMessage {
|
||||
registerMoveResizeHandler();
|
||||
myWindow.setFocusable(true);
|
||||
myWindow.setFocusableWindowState(true);
|
||||
if (SystemInfo.isJavaVersionAtLeast("1.7")) {
|
||||
myWindow.setSize(myController.SHEET_NC_WIDTH, 0);
|
||||
|
||||
setWindowOpacity(0.0f);
|
||||
|
||||
myWindow.addComponentListener(new ComponentAdapter() {
|
||||
@Override
|
||||
public void componentShown(ComponentEvent e) {
|
||||
super.componentShown(e);
|
||||
setWindowOpacity(1.0f);
|
||||
myWindow.setSize(myController.SHEET_NC_WIDTH, myController.SHEET_NC_HEIGHT);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
myWindow.setModal(true);
|
||||
myWindow.setSize(myController.SHEET_NC_WIDTH, myController.SHEET_NC_HEIGHT);
|
||||
setPositionRelativeToParent();
|
||||
}
|
||||
startAnimation(true);
|
||||
myWindow.setSize(myController.SHEET_NC_WIDTH, myController.SHEET_NC_HEIGHT);
|
||||
restoreFullscreenButton = couldBeInFullScreen();
|
||||
if (restoreFullscreenButton) {
|
||||
FullScreenUtilities.setWindowCanFullScreen(myParent, false);
|
||||
}
|
||||
setPositionRelativeToParent();
|
||||
|
||||
LaterInvocator.enterModal(myWindow);
|
||||
myWindow.setVisible(true);
|
||||
LaterInvocator.leaveModal(myWindow);
|
||||
}
|
||||
|
||||
private void setWindowOpacity(float opacity) {
|
||||
try {
|
||||
Method setOpacityMethod = myWindow.getClass().getMethod("setOpacity", Float.TYPE);
|
||||
setOpacityMethod.invoke(myWindow, opacity);
|
||||
}
|
||||
catch (NoSuchMethodException e) {
|
||||
LOG.error(e);
|
||||
}
|
||||
catch (InvocationTargetException e) {
|
||||
LOG.error(e);
|
||||
}
|
||||
catch (IllegalAccessException e) {
|
||||
LOG.error(e);
|
||||
}
|
||||
}
|
||||
|
||||
private boolean couldBeInFullScreen() {
|
||||
if (myParent instanceof JFrame) {
|
||||
JRootPane rootPane = ((JFrame)myParent).getRootPane();
|
||||
@@ -189,6 +228,11 @@ public class SheetMessage {
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
FontMetrics getFontMetrics(Font f) {
|
||||
return myParent.getGraphics().getFontMetrics(f);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -44,7 +44,6 @@ xbreakpoint.master.breakpoint.none=<None>
|
||||
xbreakpoint.master.breakpoint.description=Disabled until selected breakpoint is hit:
|
||||
rule.name.group.by.file=Group by file
|
||||
xbreakpoint.default.display.text=Line {0} in {1}
|
||||
xbreakpoint.group.unknown=Unknown
|
||||
|
||||
xbreakpoint.reached.text=Breakpoint reached:
|
||||
|
||||
|
||||
@@ -1,2 +1,2 @@
|
||||
some text
|
||||
some other t<caret>ext
|
||||
so<caret>me text
|
||||
some other text
|
||||
+26
@@ -271,6 +271,32 @@ public class EditorMultiCaretColumnModeTest extends AbstractEditorTest {
|
||||
"ccS<caret>cc");
|
||||
}
|
||||
|
||||
public void testCopyPasteOfShortLines() throws Exception {
|
||||
init("a\n" +
|
||||
"bbb\n" +
|
||||
"ccccc");
|
||||
mouse().clickAt(0, 2).dragTo(2, 4).release();
|
||||
executeAction("EditorCopy");
|
||||
executeAction("EditorLineStart");
|
||||
executeAction("EditorPaste");
|
||||
checkResultByText(" <caret>a\n" +
|
||||
"b <caret>bbb\n" +
|
||||
"cc<caret>ccccc");
|
||||
}
|
||||
|
||||
public void testPasteOfBlockToASingleCaret() throws Exception {
|
||||
init("a\n" +
|
||||
"bbb\n" +
|
||||
"ccccc");
|
||||
mouse().clickAt(1, 2).dragTo(2, 4).release();
|
||||
executeAction("EditorCopy");
|
||||
mouse().clickAt(0, 2);
|
||||
executeAction("EditorPaste");
|
||||
checkResultByText("a b <caret>\n" +
|
||||
"bbcc<caret>b\n" +
|
||||
"ccccc");
|
||||
}
|
||||
|
||||
private void init(String text) throws IOException {
|
||||
configureFromFileText(getTestName(false) + ".txt", text);
|
||||
setEditorVisibleSize(1000, 1000);
|
||||
|
||||
+64
-1
@@ -233,7 +233,8 @@ public class EditorMultiCaretTest extends AbstractEditorTest {
|
||||
"three<caret></selection> four \n" +
|
||||
"five <selection>six \n" +
|
||||
"seven<caret></selection> eight",
|
||||
TestFileType.TEXT);
|
||||
TestFileType.TEXT
|
||||
);
|
||||
executeAction("EditorCut");
|
||||
executeAction("EditorLineEnd");
|
||||
executeAction("EditorPaste");
|
||||
@@ -242,4 +243,66 @@ public class EditorMultiCaretTest extends AbstractEditorTest {
|
||||
"five eightsix \n" +
|
||||
"seven<caret>");
|
||||
}
|
||||
|
||||
public void testEscapeAfterDragDown() throws Exception {
|
||||
init("line1\n" +
|
||||
"line2",
|
||||
TestFileType.TEXT
|
||||
);
|
||||
setEditorVisibleSize(1000, 1000);
|
||||
|
||||
mouse().alt().clickAt(0, 1).dragTo(1, 2).release();
|
||||
executeAction("EditorEscape");
|
||||
checkResultByText("li<caret>ne1\n" +
|
||||
"line2");
|
||||
}
|
||||
|
||||
public void testEscapeAfterDragUp() throws Exception {
|
||||
init("line1\n" +
|
||||
"line2",
|
||||
TestFileType.TEXT);
|
||||
setEditorVisibleSize(1000, 1000);
|
||||
|
||||
mouse().alt().clickAt(1, 1).dragTo(0, 2).release();
|
||||
executeAction("EditorEscape");
|
||||
checkResultByText("line1\n" +
|
||||
"li<caret>ne2");
|
||||
}
|
||||
|
||||
public void testAltShiftDoubleClick() throws Exception {
|
||||
init("q<caret>uick brown fox",
|
||||
TestFileType.TEXT);
|
||||
mouse().alt().shift().doubleClickAt(0, 8);
|
||||
checkResultByText("q<caret>uick <selection>brown<caret></selection> fox");
|
||||
}
|
||||
|
||||
public void testAltShiftDoubleClickAtExistingCaret() throws Exception {
|
||||
init("q<caret>uick br<caret>own fox",
|
||||
TestFileType.TEXT);
|
||||
mouse().alt().shift().doubleClickAt(0, 8);
|
||||
checkResultByText("q<caret>uick brown fox");
|
||||
}
|
||||
|
||||
public void testAltShiftTripleClick() throws Exception {
|
||||
init("q<caret>uick\n" +
|
||||
"brown\n" +
|
||||
"fox",
|
||||
TestFileType.TEXT
|
||||
);
|
||||
mouse().alt().shift().tripleClickAt(1, 2);
|
||||
checkResultByText("q<caret>uick\n" +
|
||||
"<selection>br<caret>own\n" +
|
||||
"</selection>fox");
|
||||
}
|
||||
|
||||
public void testAltShiftTripleClickAtExistingCaret() throws Exception {
|
||||
init("q<caret>uick\n" +
|
||||
"br<caret>own\n" +
|
||||
"fox",
|
||||
TestFileType.TEXT);
|
||||
mouse().alt().shift().tripleClickAt(1, 2);
|
||||
checkResultByText("q<caret>uick\n" +
|
||||
"brown\n" +
|
||||
"fox");
|
||||
}
|
||||
}
|
||||
|
||||
+9
@@ -185,6 +185,15 @@ public class SelectUnselectOccurrenceActionsTest extends LightPlatformCodeInsigh
|
||||
checkResult("text <selection><caret>text</selection> <selection><caret>text</selection>");
|
||||
}
|
||||
|
||||
public void testEscapeReturnsToInitialPosition() throws Exception {
|
||||
init("l<caret>ine\n" +
|
||||
"another line");
|
||||
executeAction();
|
||||
myFixture.performEditorAction("EditorEscape");
|
||||
checkResult("l<caret>ine\n" +
|
||||
"another line");
|
||||
}
|
||||
|
||||
private void init(String text) {
|
||||
myFixture.configureByText(FileTypes.PLAIN_TEXT, text);
|
||||
}
|
||||
|
||||
@@ -35,7 +35,7 @@ import java.util.Collections;
|
||||
import java.util.Comparator;
|
||||
import java.util.List;
|
||||
|
||||
public final class DirectoryInfo {
|
||||
public class DirectoryInfo {
|
||||
public static final int MAX_ROOT_TYPE_ID = (1 << (Byte.SIZE - 2)) - 1;
|
||||
private final Module module; // module to which content it belongs or null
|
||||
private final VirtualFile libraryClassRoot; // class root in library
|
||||
@@ -81,7 +81,7 @@ public final class DirectoryInfo {
|
||||
Comparing.equal(contentRoot, info.contentRoot) &&
|
||||
Comparing.equal(libraryClassRoot, info.libraryClassRoot) &&
|
||||
Comparing.equal(module, info.module) &&
|
||||
Arrays.equals(orderEntries, info.orderEntries) &&
|
||||
Arrays.equals(getOrderEntries(), info.getOrderEntries()) &&
|
||||
Comparing.equal(sourceRoot, info.sourceRoot);
|
||||
}
|
||||
|
||||
@@ -105,7 +105,7 @@ public final class DirectoryInfo {
|
||||
", libraryClassRoot=" + getLibraryClassRoot() +
|
||||
", contentRoot=" + getContentRoot() +
|
||||
", sourceRoot=" + getSourceRoot() +
|
||||
", orderEntries=" + Arrays.toString(orderEntries) +
|
||||
", orderEntries=" + Arrays.toString(getOrderEntries()) +
|
||||
"}";
|
||||
}
|
||||
|
||||
@@ -117,10 +117,7 @@ public final class DirectoryInfo {
|
||||
|
||||
@Nullable
|
||||
OrderEntry findOrderEntryWithOwnerModule(@NotNull Module ownerModule) {
|
||||
OrderEntry[] entries = orderEntries;
|
||||
if (entries == null) {
|
||||
return null;
|
||||
}
|
||||
OrderEntry[] entries = getOrderEntries();
|
||||
if (entries.length < 10) {
|
||||
for (OrderEntry entry : entries) {
|
||||
if (entry.getOwnerModule() == ownerModule) return entry;
|
||||
@@ -133,10 +130,7 @@ public final class DirectoryInfo {
|
||||
|
||||
@NotNull
|
||||
List<OrderEntry> findAllOrderEntriesWithOwnerModule(@NotNull Module ownerModule) {
|
||||
OrderEntry[] entries = orderEntries;
|
||||
if (entries == null) {
|
||||
return Collections.emptyList();
|
||||
}
|
||||
OrderEntry[] entries = getOrderEntries();
|
||||
if (entries.length == 1) {
|
||||
OrderEntry entry = entries[0];
|
||||
return entry.getOwnerModule() == ownerModule ? Arrays.asList(entries) : Collections.<OrderEntry>emptyList();
|
||||
@@ -271,10 +265,6 @@ public final class DirectoryInfo {
|
||||
return sourceRoot;
|
||||
}
|
||||
|
||||
public boolean hasSourceRoot() {
|
||||
return getSourceRoot() != null;
|
||||
}
|
||||
|
||||
public VirtualFile getLibraryClassRoot() {
|
||||
return libraryClassRoot;
|
||||
}
|
||||
|
||||
+19
-3
@@ -37,6 +37,10 @@ public class EditorMouseFixture {
|
||||
}
|
||||
|
||||
public EditorMouseFixture pressAt(int visualLine, int visualColumn) {
|
||||
return pressAt(1, visualLine, visualColumn);
|
||||
}
|
||||
|
||||
private EditorMouseFixture pressAt(int clickCount, int visualLine, int visualColumn) {
|
||||
JComponent component = myEditor.getContentComponent();
|
||||
Point p = getPoint(visualLine, visualColumn);
|
||||
component.dispatchEvent(new MouseEvent(component,
|
||||
@@ -45,13 +49,17 @@ public class EditorMouseFixture {
|
||||
getModifiers(),
|
||||
myX = p.x,
|
||||
myY = p.y,
|
||||
1,
|
||||
clickCount,
|
||||
false,
|
||||
myButton));
|
||||
return this;
|
||||
}
|
||||
|
||||
public EditorMouseFixture release() {
|
||||
return release(1);
|
||||
}
|
||||
|
||||
private EditorMouseFixture release(int clickCount) {
|
||||
int oldLastId = myLastId;
|
||||
JComponent component = myEditor.getContentComponent();
|
||||
component.dispatchEvent(new MouseEvent(component,
|
||||
@@ -60,7 +68,7 @@ public class EditorMouseFixture {
|
||||
getModifiers(),
|
||||
myX,
|
||||
myY,
|
||||
1,
|
||||
clickCount,
|
||||
false,
|
||||
myButton));
|
||||
if (oldLastId == MouseEvent.MOUSE_PRESSED) {
|
||||
@@ -70,7 +78,7 @@ public class EditorMouseFixture {
|
||||
getModifiers(),
|
||||
myX,
|
||||
myY,
|
||||
1,
|
||||
clickCount,
|
||||
false,
|
||||
myButton));
|
||||
}
|
||||
@@ -81,6 +89,14 @@ public class EditorMouseFixture {
|
||||
return pressAt(visualLine, visualColumn).release();
|
||||
}
|
||||
|
||||
public EditorMouseFixture doubleClickAt(int visualLine, int visualColumn) {
|
||||
return clickAt(visualLine, visualColumn).pressAt(2, visualLine, visualColumn).release(2);
|
||||
}
|
||||
|
||||
public EditorMouseFixture tripleClickAt(int visualLine, int visualColumn) {
|
||||
return doubleClickAt(visualLine, visualColumn).pressAt(3, visualLine, visualColumn).release(3);
|
||||
}
|
||||
|
||||
public EditorMouseFixture dragTo(int visualLine, int visualColumn) {
|
||||
JComponent component = myEditor.getContentComponent();
|
||||
Point p = getPoint(visualLine, visualColumn);
|
||||
|
||||
@@ -437,6 +437,7 @@ public class AllIcons {
|
||||
public static final Icon OverridenMethod = IconLoader.getIcon("/general/overridenMethod.png"); // 10x14
|
||||
public static final Icon OverridingMethod = IconLoader.getIcon("/general/overridingMethod.png"); // 10x14
|
||||
public static final Icon PackagesTab = IconLoader.getIcon("/general/packagesTab.png"); // 16x16
|
||||
public static final Icon PasswordLock = IconLoader.getIcon("/general/passwordLock.png"); // 64x64
|
||||
public static final Icon PathVariables = IconLoader.getIcon("/general/pathVariables.png"); // 32x32
|
||||
public static final Icon Pin_tab = IconLoader.getIcon("/general/pin_tab.png"); // 16x16
|
||||
public static final Icon PluginManager = IconLoader.getIcon("/general/pluginManager.png"); // 32x32
|
||||
|
||||
+1
-1
@@ -53,7 +53,7 @@ public abstract class XBreakpointGroupingRule<B, G extends XBreakpointGroup> {
|
||||
return XBreakpointsGroupingPriorities.DEFAULT;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Nullable
|
||||
public abstract G getGroup(@NotNull B breakpoint, @NotNull Collection<G> groups);
|
||||
|
||||
@Nullable
|
||||
|
||||
+1
-22
@@ -15,11 +15,9 @@
|
||||
*/
|
||||
package com.intellij.xdebugger.impl.breakpoints.ui.grouping;
|
||||
|
||||
import com.intellij.icons.AllIcons;
|
||||
import com.intellij.ide.presentation.VirtualFilePresentation;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.xdebugger.XDebuggerBundle;
|
||||
import com.intellij.xdebugger.breakpoints.ui.XBreakpointGroup;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@@ -29,26 +27,8 @@ import javax.swing.*;
|
||||
* @author nik
|
||||
*/
|
||||
public class XBreakpointFileGroup extends XBreakpointGroup {
|
||||
public static final XBreakpointFileGroup UNKNOWN = new XBreakpointFileGroup() {
|
||||
@NotNull
|
||||
@Override
|
||||
public String getName() {
|
||||
return XDebuggerBundle.message("xbreakpoint.group.unknown");
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Icon getIcon(boolean isOpen) {
|
||||
return AllIcons.FileTypes.Text;
|
||||
}
|
||||
};
|
||||
|
||||
private final VirtualFile myFile;
|
||||
|
||||
private XBreakpointFileGroup() {
|
||||
myFile = null;
|
||||
}
|
||||
|
||||
public XBreakpointFileGroup(@NotNull VirtualFile file) {
|
||||
myFile = file;
|
||||
}
|
||||
@@ -63,7 +43,6 @@ public class XBreakpointFileGroup extends XBreakpointGroup {
|
||||
return myFile.getPresentableUrl();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public VirtualFile getFile() {
|
||||
return myFile;
|
||||
}
|
||||
|
||||
+3
-7
@@ -16,7 +16,6 @@
|
||||
package com.intellij.xdebugger.impl.breakpoints.ui.grouping;
|
||||
|
||||
import com.intellij.icons.AllIcons;
|
||||
import com.intellij.openapi.util.Comparing;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.xdebugger.XDebuggerBundle;
|
||||
import com.intellij.xdebugger.XSourcePosition;
|
||||
@@ -42,20 +41,17 @@ public class XBreakpointFileGroupingRule<B> extends XBreakpointGroupingRule<B, X
|
||||
return XBreakpointsGroupingPriorities.BY_FILE;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public XBreakpointFileGroup getGroup(@NotNull final B breakpoint, @NotNull final Collection<XBreakpointFileGroup> groups) {
|
||||
if (!(breakpoint instanceof XLineBreakpoint)) {
|
||||
return XBreakpointFileGroup.UNKNOWN;
|
||||
return null;
|
||||
}
|
||||
XSourcePosition position = ((XLineBreakpoint)breakpoint).getSourcePosition();
|
||||
|
||||
if (position == null) {
|
||||
return XBreakpointFileGroup.UNKNOWN;
|
||||
}
|
||||
if (position == null) return null;
|
||||
|
||||
VirtualFile file = position.getFile();
|
||||
for (XBreakpointFileGroup group : groups) {
|
||||
if (Comparing.equal(group.getFile(), file)) {
|
||||
if (group.getFile().equals(file)) {
|
||||
return group;
|
||||
}
|
||||
}
|
||||
|
||||
+1
-2
@@ -45,7 +45,6 @@ public class XBreakpointGroupingByTypeRule<B> extends XBreakpointGroupingRule<B,
|
||||
return XBreakpointsGroupingPriorities.BY_TYPE;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public XBreakpointTypeGroup getGroup(@NotNull B b, @NotNull Collection<XBreakpointTypeGroup> groups) {
|
||||
if (b instanceof XBreakpoint) {
|
||||
@@ -57,6 +56,6 @@ public class XBreakpointGroupingByTypeRule<B> extends XBreakpointGroupingRule<B,
|
||||
}
|
||||
return new XBreakpointTypeGroup(breakpoint.getType());
|
||||
}
|
||||
return XBreakpointTypeGroup.UNKNOWN;
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
+1
-16
@@ -15,31 +15,17 @@
|
||||
*/
|
||||
package com.intellij.xdebugger.impl.breakpoints.ui.grouping;
|
||||
|
||||
import com.intellij.icons.AllIcons;
|
||||
import com.intellij.util.ArrayUtil;
|
||||
import com.intellij.xdebugger.XDebuggerBundle;
|
||||
import com.intellij.xdebugger.breakpoints.XBreakpointType;
|
||||
import com.intellij.xdebugger.breakpoints.XLineBreakpoint;
|
||||
import com.intellij.xdebugger.breakpoints.XLineBreakpointType;
|
||||
import com.intellij.xdebugger.breakpoints.ui.XBreakpointGroup;
|
||||
import com.intellij.xdebugger.impl.breakpoints.XBreakpointUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
|
||||
public class XBreakpointTypeGroup extends XBreakpointGroup {
|
||||
public static final XBreakpointTypeGroup UNKNOWN = new XBreakpointTypeGroup(null) {
|
||||
@NotNull
|
||||
@Override
|
||||
public String getName() {
|
||||
return XDebuggerBundle.message("xbreakpoint.group.unknown");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Icon getIcon(boolean isOpen) {
|
||||
return AllIcons.Debugger.Db_set_breakpoint;
|
||||
}
|
||||
};
|
||||
|
||||
private XBreakpointType myBreakpointType;
|
||||
|
||||
@@ -53,7 +39,6 @@ public class XBreakpointTypeGroup extends XBreakpointGroup {
|
||||
return myBreakpointType.getTitle();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public XBreakpointType getBreakpointType() {
|
||||
return myBreakpointType;
|
||||
}
|
||||
|
||||
+1
-2
@@ -129,8 +129,7 @@ public class BreakpointItemsTreeController implements BreakpointsCheckboxTree.De
|
||||
private CheckedTreeNode getParentNode(final BreakpointItem breakpoint) {
|
||||
CheckedTreeNode parent = myRoot;
|
||||
for (int i = 0; i < myGroupingRules.size(); i++) {
|
||||
Collection<XBreakpointGroup> existingGroups = getGroupNodes(parent);
|
||||
XBreakpointGroup group = myGroupingRules.get(i).getGroup(breakpoint.getBreakpoint(), existingGroups);
|
||||
XBreakpointGroup group = myGroupingRules.get(i).getGroup(breakpoint.getBreakpoint(), Collections.emptyList());
|
||||
if (group != null) {
|
||||
parent = getOrCreateGroupNode(parent, group, i);
|
||||
}
|
||||
|
||||
+1
@@ -1877,6 +1877,7 @@ if.can.be.switch.quickfix=Replace with 'switch'
|
||||
if.can.be.switch.minimum.branch.option=Minimum number of branches:
|
||||
if.can.be.switch.int.option=Suggest switch on numbers
|
||||
if.can.be.switch.enum.option=Suggest switch on enums
|
||||
if.can.be.switch.null.safe.option=Only suggest on null-safe expressions
|
||||
unnecessarily.qualified.inner.class.access.option=Ignore references for which an import is needed
|
||||
unqualified.inner.class.access.option=Ignore references to local inner classes
|
||||
try.with.identical.catches.quickfix=Collapse 'catch' blocks
|
||||
|
||||
+2
-2
@@ -16,6 +16,7 @@
|
||||
package com.siyeh.ig.maturity;
|
||||
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.util.InheritanceUtil;
|
||||
import com.siyeh.HardcodedMethodConstants;
|
||||
import com.siyeh.InspectionGadgetsBundle;
|
||||
import com.siyeh.ig.BaseInspection;
|
||||
@@ -69,8 +70,7 @@ public class ThrowablePrintStackTraceInspectionBase extends BaseInspection {
|
||||
if (containingClass == null) {
|
||||
return;
|
||||
}
|
||||
final String name = containingClass.getQualifiedName();
|
||||
if (!CommonClassNames.JAVA_LANG_THROWABLE.equals(name)) {
|
||||
if (!InheritanceUtil.isInheritor(containingClass, false, CommonClassNames.JAVA_LANG_THROWABLE)) {
|
||||
return;
|
||||
}
|
||||
registerMethodCallError(expression, expression);
|
||||
|
||||
+13
-31
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2011-2013 Bas Leijdekkers
|
||||
* Copyright 2011-2014 Bas Leijdekkers
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -15,20 +15,19 @@
|
||||
*/
|
||||
package com.siyeh.ig.migration;
|
||||
|
||||
import com.intellij.codeInsight.NullableNotNullManager;
|
||||
import com.intellij.codeInspection.ProblemDescriptor;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
import com.intellij.psi.util.PsiTreeUtil;
|
||||
import com.intellij.ui.DocumentAdapter;
|
||||
import com.intellij.util.ui.CheckBox;
|
||||
import com.siyeh.InspectionGadgetsBundle;
|
||||
import com.siyeh.ig.BaseInspection;
|
||||
import com.siyeh.ig.BaseInspectionVisitor;
|
||||
import com.siyeh.ig.InspectionGadgetsFix;
|
||||
import com.siyeh.ig.psiutils.ControlFlowUtils;
|
||||
import com.siyeh.ig.psiutils.EquivalenceChecker;
|
||||
import com.siyeh.ig.psiutils.ParenthesesUtils;
|
||||
import com.siyeh.ig.psiutils.SwitchUtils;
|
||||
import com.siyeh.ig.psiutils.SwitchUtils.IfStatementBranch;
|
||||
import org.jetbrains.annotations.Nls;
|
||||
@@ -37,8 +36,6 @@ import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import javax.swing.event.ChangeEvent;
|
||||
import javax.swing.event.ChangeListener;
|
||||
import javax.swing.event.DocumentEvent;
|
||||
import javax.swing.text.Document;
|
||||
import java.awt.*;
|
||||
@@ -58,6 +55,9 @@ public class IfCanBeSwitchInspection extends BaseInspection {
|
||||
@SuppressWarnings({"PublicField"})
|
||||
public boolean suggestEnumSwitches = false;
|
||||
|
||||
@SuppressWarnings("PublicField")
|
||||
public boolean onlySuggestNullSafe = true;
|
||||
|
||||
@Override
|
||||
public boolean isEnabledByDefault() {
|
||||
return true;
|
||||
@@ -121,26 +121,16 @@ public class IfCanBeSwitchInspection extends BaseInspection {
|
||||
constraints.gridx = 0;
|
||||
constraints.gridy = 1;
|
||||
constraints.gridwidth = 2;
|
||||
final JCheckBox checkBox1 = new JCheckBox(InspectionGadgetsBundle.message("if.can.be.switch.int.option"), suggestIntSwitches);
|
||||
final ButtonModel model1 = checkBox1.getModel();
|
||||
model1.addChangeListener(new ChangeListener() {
|
||||
@Override
|
||||
public void stateChanged(ChangeEvent e) {
|
||||
suggestIntSwitches = model1.isSelected();
|
||||
}
|
||||
});
|
||||
final CheckBox checkBox1 = new CheckBox(InspectionGadgetsBundle.message("if.can.be.switch.int.option"), this, "suggestIntSwitches");
|
||||
panel.add(checkBox1, constraints);
|
||||
constraints.gridy = 2;
|
||||
constraints.weighty = 1.0;
|
||||
final JCheckBox checkBox2 = new JCheckBox(InspectionGadgetsBundle.message("if.can.be.switch.enum.option"), suggestEnumSwitches);
|
||||
final ButtonModel model2 = checkBox2.getModel();
|
||||
model2.addChangeListener(new ChangeListener() {
|
||||
@Override
|
||||
public void stateChanged(ChangeEvent e) {
|
||||
suggestEnumSwitches = model2.isSelected();
|
||||
}
|
||||
});
|
||||
final CheckBox checkBox2 = new CheckBox(InspectionGadgetsBundle.message("if.can.be.switch.enum.option"), this, "suggestEnumSwitches");
|
||||
panel.add(checkBox2, constraints);
|
||||
constraints.gridy = 3;
|
||||
constraints.weighty = 1.0;
|
||||
final CheckBox checkBox3 =
|
||||
new CheckBox(InspectionGadgetsBundle.message("if.can.be.switch.null.safe.option"), this, "onlySuggestNullSafe");
|
||||
panel.add(checkBox3, constraints);
|
||||
return panel;
|
||||
}
|
||||
|
||||
@@ -508,18 +498,10 @@ public class IfCanBeSwitchInspection extends BaseInspection {
|
||||
if (parent instanceof PsiIfStatement) {
|
||||
return;
|
||||
}
|
||||
final PsiExpression switchExpression = SwitchUtils.getSwitchExpression(statement, minimumBranches);
|
||||
final PsiExpression switchExpression = SwitchUtils.getSwitchExpression(statement, minimumBranches, onlySuggestNullSafe);
|
||||
if (switchExpression == null) {
|
||||
return;
|
||||
}
|
||||
final PsiExpression unwrappedExpression = ParenthesesUtils.stripParentheses(switchExpression);
|
||||
if (unwrappedExpression instanceof PsiReferenceExpression) {
|
||||
final PsiReferenceExpression referenceExpression = (PsiReferenceExpression)unwrappedExpression;
|
||||
final PsiElement target = referenceExpression.resolve();
|
||||
if (target instanceof PsiModifierListOwner && NullableNotNullManager.isNullable((PsiModifierListOwner)target)) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
final PsiType type = switchExpression.getType();
|
||||
if (!suggestIntSwitches) {
|
||||
if (type instanceof PsiClassType) {
|
||||
|
||||
+51
-10
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2003-2013 Dave Griffith, Bas Leijdekkers
|
||||
* Copyright 2003-2014 Dave Griffith, Bas Leijdekkers
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -15,6 +15,7 @@
|
||||
*/
|
||||
package com.siyeh.ig.psiutils;
|
||||
|
||||
import com.intellij.codeInsight.NullableNotNullManager;
|
||||
import com.intellij.pom.java.LanguageLevel;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
@@ -47,16 +48,21 @@ public class SwitchUtils {
|
||||
|
||||
@Nullable
|
||||
public static PsiExpression getSwitchExpression(PsiIfStatement statement, int minimumBranches) {
|
||||
return getSwitchExpression(statement, minimumBranches, false);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static PsiExpression getSwitchExpression(PsiIfStatement statement, int minimumBranches, boolean nullSafe) {
|
||||
final PsiExpression condition = statement.getCondition();
|
||||
final LanguageLevel languageLevel = PsiUtil.getLanguageLevel(statement);
|
||||
final PsiExpression possibleSwitchExpression = determinePossibleSwitchExpressions(condition, languageLevel);
|
||||
final PsiExpression possibleSwitchExpression = determinePossibleSwitchExpressions(condition, languageLevel, nullSafe);
|
||||
if (!canBeSwitchExpression(possibleSwitchExpression, languageLevel)) {
|
||||
return null;
|
||||
}
|
||||
int branchCount = 0;
|
||||
while (true) {
|
||||
branchCount++;
|
||||
if (!canBeMadeIntoCase(statement.getCondition(), possibleSwitchExpression, languageLevel)) {
|
||||
if (!canBeMadeIntoCase(statement.getCondition(), possibleSwitchExpression, languageLevel, false)) {
|
||||
break;
|
||||
}
|
||||
final PsiStatement elseBranch = statement.getElseBranch();
|
||||
@@ -74,10 +80,11 @@ public class SwitchUtils {
|
||||
return null;
|
||||
}
|
||||
|
||||
private static boolean canBeMadeIntoCase(PsiExpression expression, PsiExpression switchExpression, LanguageLevel languageLevel) {
|
||||
private static boolean canBeMadeIntoCase(PsiExpression expression, PsiExpression switchExpression, LanguageLevel languageLevel,
|
||||
boolean nullSafe) {
|
||||
expression = ParenthesesUtils.stripParentheses(expression);
|
||||
if (languageLevel.isAtLeast(LanguageLevel.JDK_1_7)) {
|
||||
final PsiExpression stringSwitchExpression = determinePossibleStringSwitchExpression(expression);
|
||||
final PsiExpression stringSwitchExpression = determinePossibleStringSwitchExpression(expression, nullSafe);
|
||||
if (EquivalenceChecker.expressionsAreEquivalent(switchExpression, stringSwitchExpression)) {
|
||||
return true;
|
||||
}
|
||||
@@ -90,7 +97,7 @@ public class SwitchUtils {
|
||||
final PsiExpression[] operands = polyadicExpression.getOperands();
|
||||
if (operation.equals(JavaTokenType.OROR)) {
|
||||
for (PsiExpression operand : operands) {
|
||||
if (!canBeMadeIntoCase(operand, switchExpression, languageLevel)) {
|
||||
if (!canBeMadeIntoCase(operand, switchExpression, languageLevel, nullSafe)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@@ -114,6 +121,9 @@ public class SwitchUtils {
|
||||
return true;
|
||||
}
|
||||
else if (type instanceof PsiClassType) {
|
||||
if (isAnnotatedNullable(expression)) {
|
||||
return false;
|
||||
}
|
||||
if (type.equalsToText(CommonClassNames.JAVA_LANG_CHARACTER) || type.equalsToText(CommonClassNames.JAVA_LANG_BYTE) ||
|
||||
type.equalsToText(CommonClassNames.JAVA_LANG_SHORT) || type.equalsToText(CommonClassNames.JAVA_LANG_INTEGER)) {
|
||||
return true;
|
||||
@@ -132,13 +142,13 @@ public class SwitchUtils {
|
||||
return false;
|
||||
}
|
||||
|
||||
private static PsiExpression determinePossibleSwitchExpressions(PsiExpression expression, LanguageLevel languageLevel) {
|
||||
private static PsiExpression determinePossibleSwitchExpressions(PsiExpression expression, LanguageLevel languageLevel, boolean nullSafe) {
|
||||
expression = ParenthesesUtils.stripParentheses(expression);
|
||||
if (expression == null) {
|
||||
return null;
|
||||
}
|
||||
if (languageLevel.isAtLeast(LanguageLevel.JDK_1_7)) {
|
||||
final PsiExpression jdk17Expression = determinePossibleStringSwitchExpression(expression);
|
||||
final PsiExpression jdk17Expression = determinePossibleStringSwitchExpression(expression, nullSafe);
|
||||
if (jdk17Expression != null) {
|
||||
return jdk17Expression;
|
||||
}
|
||||
@@ -150,7 +160,7 @@ public class SwitchUtils {
|
||||
final IElementType operation = polyadicExpression.getOperationTokenType();
|
||||
final PsiExpression[] operands = polyadicExpression.getOperands();
|
||||
if (operation.equals(JavaTokenType.OROR) && operands.length > 0) {
|
||||
return determinePossibleSwitchExpressions(operands[0], languageLevel);
|
||||
return determinePossibleSwitchExpressions(operands[0], languageLevel, nullSafe);
|
||||
}
|
||||
else if (operation.equals(JavaTokenType.EQEQ) && operands.length == 2) {
|
||||
final PsiExpression lhs = operands[0];
|
||||
@@ -165,7 +175,7 @@ public class SwitchUtils {
|
||||
return null;
|
||||
}
|
||||
|
||||
private static PsiExpression determinePossibleStringSwitchExpression(PsiExpression expression) {
|
||||
private static PsiExpression determinePossibleStringSwitchExpression(PsiExpression expression, boolean nullSafe) {
|
||||
if (!(expression instanceof PsiMethodCallExpression)) {
|
||||
return null;
|
||||
}
|
||||
@@ -194,6 +204,9 @@ public class SwitchUtils {
|
||||
return null;
|
||||
}
|
||||
if (PsiUtil.isConstantExpression(qualifierExpression)) {
|
||||
if (nullSafe && !isAnnotatedNotNull(argument)) {
|
||||
return null;
|
||||
}
|
||||
return argument;
|
||||
}
|
||||
else if (PsiUtil.isConstantExpression(argument)) {
|
||||
@@ -202,6 +215,34 @@ public class SwitchUtils {
|
||||
return null;
|
||||
}
|
||||
|
||||
private static boolean isAnnotatedNotNull(PsiExpression expression) {
|
||||
expression = ParenthesesUtils.stripParentheses(expression);
|
||||
if (!(expression instanceof PsiReferenceExpression)) {
|
||||
return false;
|
||||
}
|
||||
final PsiReferenceExpression referenceExpression = (PsiReferenceExpression)expression;
|
||||
final PsiElement target = referenceExpression.resolve();
|
||||
if (!(target instanceof PsiModifierListOwner)) {
|
||||
return false;
|
||||
}
|
||||
final PsiModifierListOwner modifierListOwner = (PsiModifierListOwner)target;
|
||||
return NullableNotNullManager.isNotNull(modifierListOwner);
|
||||
}
|
||||
|
||||
private static boolean isAnnotatedNullable(PsiExpression expression) {
|
||||
expression = ParenthesesUtils.stripParentheses(expression);
|
||||
if (!(expression instanceof PsiReferenceExpression)) {
|
||||
return false;
|
||||
}
|
||||
final PsiReferenceExpression referenceExpression = (PsiReferenceExpression)expression;
|
||||
final PsiElement target = referenceExpression.resolve();
|
||||
if (!(target instanceof PsiModifierListOwner)) {
|
||||
return false;
|
||||
}
|
||||
final PsiModifierListOwner modifierListOwner = (PsiModifierListOwner)target;
|
||||
return NullableNotNullManager.isNullable(modifierListOwner);
|
||||
}
|
||||
|
||||
private static boolean canBeCaseLabel(PsiExpression expression, LanguageLevel languageLevel) {
|
||||
if (expression == null) {
|
||||
return false;
|
||||
|
||||
@@ -14,6 +14,8 @@ primitive and boxed numbers and characters.
|
||||
Use the second checkbox below to have this inspection suggest switch statements on
|
||||
enum constants.
|
||||
<p>
|
||||
Use the third checkbox below to only suggest switch statements which can't introduce a <b>NullPointerException</b>
|
||||
<p>
|
||||
<small>New in 10.5</small>
|
||||
</body>
|
||||
</html>
|
||||
+34
-4
@@ -1,5 +1,5 @@
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
class IfCanBeSwitch {
|
||||
void m1(int i) { // ok
|
||||
if (i == 0) System.out.println("zero"); else if (i == 1) System.out.println("one"); else System.out.println("many");
|
||||
@@ -23,10 +23,10 @@ class IfCanBeSwitch {
|
||||
|
||||
void polyadic() {
|
||||
String s = null;
|
||||
if ("asdf".equals(s) || "addd".equals(s) || "lkjh".equals(s)) {
|
||||
if (s.equals("asdf") || s.equals("addd") || s.equals("lkjh")) {
|
||||
System.out.println("asdf");
|
||||
|
||||
} else if ("null".equals(s)) {
|
||||
} else if (s.equals("null")) {
|
||||
System.out.println("null");
|
||||
|
||||
} else {
|
||||
@@ -35,7 +35,7 @@ class IfCanBeSwitch {
|
||||
}
|
||||
|
||||
void nullable(@Nullable String s) {
|
||||
if ("a".equals(s)) {
|
||||
if ("a".equals((s))) {
|
||||
System.out.println(1);
|
||||
} else if ("b".equals(s)) {
|
||||
System.out.println(2);
|
||||
@@ -45,4 +45,34 @@ class IfCanBeSwitch {
|
||||
System.out.println(4);
|
||||
}
|
||||
}
|
||||
|
||||
void notNullSafe() {
|
||||
String narf = null;
|
||||
if ("foo".equals(narf)) {
|
||||
// do this
|
||||
} else if ("bar".equals(narf)){
|
||||
// do that
|
||||
}
|
||||
else {
|
||||
// do something else.
|
||||
}
|
||||
}
|
||||
|
||||
void nullSafe(String earth) {
|
||||
if (earth.equals("foo")) {
|
||||
} else if ("bar".equals(earth)) {
|
||||
} else {
|
||||
}
|
||||
}
|
||||
|
||||
void nullSafe2(@NotNull String narf) {
|
||||
if ("foo".equals((narf))) {
|
||||
// do this
|
||||
} else if ("bar".equals(narf)){
|
||||
// do that
|
||||
}
|
||||
else {
|
||||
// do something else.
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -27,4 +27,18 @@
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">'if' replaceable with 'switch'</problem_class>
|
||||
<description><code>if</code> statement replaceable with 'switch' statement #loc</description>
|
||||
</problem>
|
||||
|
||||
<problem>
|
||||
<file>IfCanBeSwitch.java</file>
|
||||
<line>62</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">'if' replaceable with 'switch'</problem_class>
|
||||
<description><code>if</code> statement replaceable with 'switch' statement #loc</description>
|
||||
</problem>
|
||||
|
||||
<problem>
|
||||
<file>IfCanBeSwitch.java</file>
|
||||
<line>69</line>
|
||||
<problem_class severity="WARNING" attribute_key="WARNING_ATTRIBUTES">'if' replaceable with 'switch'</problem_class>
|
||||
<description><code>if</code> statement replaceable with 'switch' statement #loc</description>
|
||||
</problem>
|
||||
</problems>
|
||||
+10
@@ -37,6 +37,16 @@ public class ThrowablePrintStackTraceInspectionTest extends LightInspectionTestC
|
||||
"}");
|
||||
}
|
||||
|
||||
public void testPrintStacktraceOverridden() throws Exception {
|
||||
addEnvironmentClass("public class FException extends Exception {\n" +
|
||||
" @Override\n" +
|
||||
" public void printStackTrace() {\n" +
|
||||
" super.printStackTrace();\n" +
|
||||
" }\n" +
|
||||
"}\n");
|
||||
doStatementTest("new FException()./*Call to 'printStackTrace()' should probably be replaced with more robust logging*/printStackTrace/**/();");
|
||||
}
|
||||
|
||||
@Override
|
||||
protected InspectionProfileEntry getInspection() {
|
||||
return new ThrowablePrintStackTraceInspection();
|
||||
|
||||
+3
-2
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2011 JetBrains s.r.o.
|
||||
* Copyright 2000-2014 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.
|
||||
@@ -33,6 +33,7 @@ public class IfCanBeSwitchInspectionTest extends IGInspectionTestCase {
|
||||
public void test() throws Exception {
|
||||
final IfCanBeSwitchInspection inspection = new IfCanBeSwitchInspection();
|
||||
inspection.suggestIntSwitches = true;
|
||||
doTest("com/siyeh/igtest/migration/if_switch", new LocalInspectionToolWrapper(inspection));
|
||||
inspection.onlySuggestNullSafe = true;
|
||||
doTest("com/siyeh/igtest/migration/if_switch", new LocalInspectionToolWrapper(inspection));
|
||||
}
|
||||
}
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user