mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
IDEA-102405 Arrangement: Refactor the API in accordance with design problems discovered during non-java arrangement implementations
1. Old settings enum (ArrangementEntryType, ArrangementModifier etc) are replaced by ArrangementSettingsToken; 2. All existing arrangement codebase is switched to the new api;
This commit is contained in:
+40
-36
@@ -18,12 +18,12 @@ package com.intellij.psi.codeStyle.arrangement;
|
||||
import com.intellij.openapi.editor.Document;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.psi.*;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens;
|
||||
import com.intellij.psi.search.searches.SuperMethodsSearch;
|
||||
import com.intellij.psi.util.MethodSignatureBackedByPsiMethod;
|
||||
import com.intellij.psi.util.PropertyUtil;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import com.intellij.util.containers.Stack;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
@@ -33,37 +33,41 @@ import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.EntryType.*;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Modifier.*;
|
||||
|
||||
public class JavaArrangementVisitor extends JavaElementVisitor {
|
||||
|
||||
|
||||
private static final String NULL_CONTENT = "no content";
|
||||
|
||||
private static final Map<String, ArrangementModifier> MODIFIERS = new HashMap<String, ArrangementModifier>();
|
||||
|
||||
private static final Map<String, ArrangementSettingsToken> MODIFIERS = ContainerUtilRt.newHashMap();
|
||||
|
||||
static {
|
||||
MODIFIERS.put(PsiModifier.PUBLIC, ArrangementModifier.PUBLIC);
|
||||
MODIFIERS.put(PsiModifier.PROTECTED, ArrangementModifier.PROTECTED);
|
||||
MODIFIERS.put(PsiModifier.PRIVATE, ArrangementModifier.PRIVATE);
|
||||
MODIFIERS.put(PsiModifier.PACKAGE_LOCAL, ArrangementModifier.PACKAGE_PRIVATE);
|
||||
MODIFIERS.put(PsiModifier.STATIC, ArrangementModifier.STATIC);
|
||||
MODIFIERS.put(PsiModifier.FINAL, ArrangementModifier.FINAL);
|
||||
MODIFIERS.put(PsiModifier.TRANSIENT, ArrangementModifier.TRANSIENT);
|
||||
MODIFIERS.put(PsiModifier.VOLATILE, ArrangementModifier.VOLATILE);
|
||||
MODIFIERS.put(PsiModifier.SYNCHRONIZED, ArrangementModifier.SYNCHRONIZED);
|
||||
MODIFIERS.put(PsiModifier.ABSTRACT, ArrangementModifier.ABSTRACT);
|
||||
MODIFIERS.put(PsiModifier.PUBLIC, PUBLIC);
|
||||
MODIFIERS.put(PsiModifier.PROTECTED, PROTECTED);
|
||||
MODIFIERS.put(PsiModifier.PRIVATE, PRIVATE);
|
||||
MODIFIERS.put(PsiModifier.PACKAGE_LOCAL, PACKAGE_PRIVATE);
|
||||
MODIFIERS.put(PsiModifier.STATIC, STATIC);
|
||||
MODIFIERS.put(PsiModifier.FINAL, FINAL);
|
||||
MODIFIERS.put(PsiModifier.TRANSIENT, TRANSIENT);
|
||||
MODIFIERS.put(PsiModifier.VOLATILE, VOLATILE);
|
||||
MODIFIERS.put(PsiModifier.SYNCHRONIZED, SYNCHRONIZED);
|
||||
MODIFIERS.put(PsiModifier.ABSTRACT, ABSTRACT);
|
||||
}
|
||||
|
||||
@NotNull private final Stack<JavaElementArrangementEntry> myStack = new Stack<JavaElementArrangementEntry>();
|
||||
@NotNull private final Map<PsiElement, JavaElementArrangementEntry> myEntries = new HashMap<PsiElement, JavaElementArrangementEntry>();
|
||||
|
||||
@NotNull private final JavaArrangementParseInfo myInfo;
|
||||
@NotNull private final Collection<TextRange> myRanges;
|
||||
@NotNull private final Set<ArrangementGroupingType> myGroupingRules;
|
||||
@NotNull private final MethodBodyProcessor myMethodBodyProcessor;
|
||||
@Nullable private final Document myDocument;
|
||||
@NotNull private final JavaArrangementParseInfo myInfo;
|
||||
@NotNull private final Collection<TextRange> myRanges;
|
||||
@NotNull private final Set<ArrangementSettingsToken> myGroupingRules;
|
||||
@NotNull private final MethodBodyProcessor myMethodBodyProcessor;
|
||||
@Nullable private final Document myDocument;
|
||||
|
||||
public JavaArrangementVisitor(@NotNull JavaArrangementParseInfo infoHolder,
|
||||
@Nullable Document document,
|
||||
@NotNull Collection<TextRange> ranges,
|
||||
@NotNull Set<ArrangementGroupingType> groupingRules)
|
||||
@NotNull Set<ArrangementSettingsToken> groupingRules)
|
||||
{
|
||||
myInfo = infoHolder;
|
||||
myDocument = document;
|
||||
@@ -74,12 +78,12 @@ public class JavaArrangementVisitor extends JavaElementVisitor {
|
||||
|
||||
@Override
|
||||
public void visitClass(PsiClass aClass) {
|
||||
ArrangementEntryType type = ArrangementEntryType.CLASS;
|
||||
ArrangementSettingsToken type = CLASS;
|
||||
if (aClass.isEnum()) {
|
||||
type = ArrangementEntryType.ENUM;
|
||||
type = ENUM;
|
||||
}
|
||||
else if (aClass.isInterface()) {
|
||||
type = ArrangementEntryType.INTERFACE;
|
||||
type = INTERFACE;
|
||||
}
|
||||
JavaElementArrangementEntry entry = createNewEntry(aClass, aClass.getTextRange(), type, aClass.getName(), true);
|
||||
processEntry(entry, aClass, aClass);
|
||||
@@ -88,7 +92,7 @@ public class JavaArrangementVisitor extends JavaElementVisitor {
|
||||
@Override
|
||||
public void visitAnonymousClass(PsiAnonymousClass aClass) {
|
||||
JavaElementArrangementEntry entry = createNewEntry(
|
||||
aClass, aClass.getTextRange(), ArrangementEntryType.ANONYMOUS_CLASS, aClass.getName(), false
|
||||
aClass, aClass.getTextRange(), ANONYMOUS_CLASS, aClass.getName(), false
|
||||
);
|
||||
processEntry(entry, null, aClass);
|
||||
}
|
||||
@@ -107,8 +111,8 @@ public class JavaArrangementVisitor extends JavaElementVisitor {
|
||||
PsiElement fieldPrev = getPreviousNonWsComment(field.getPrevSibling(), 0);
|
||||
if (fieldPrev instanceof PsiJavaToken && ((PsiJavaToken)fieldPrev).getTokenType() == JavaTokenType.COMMA) {
|
||||
return;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// There is a possible case that fields which share the same type declaration are located on different document lines, e.g.:
|
||||
// int i1,
|
||||
// i2;
|
||||
@@ -158,7 +162,7 @@ public class JavaArrangementVisitor extends JavaElementVisitor {
|
||||
break;
|
||||
}
|
||||
}
|
||||
JavaElementArrangementEntry entry = createNewEntry(field, range, ArrangementEntryType.FIELD, field.getName(), true);
|
||||
JavaElementArrangementEntry entry = createNewEntry(field, range, FIELD, field.getName(), true);
|
||||
processEntry(entry, field, field.getInitializer());
|
||||
}
|
||||
|
||||
@@ -182,7 +186,7 @@ public class JavaArrangementVisitor extends JavaElementVisitor {
|
||||
|
||||
@Override
|
||||
public void visitClassInitializer(PsiClassInitializer initializer) {
|
||||
JavaElementArrangementEntry entry = createNewEntry(initializer, initializer.getTextRange(), ArrangementEntryType.FIELD, null, true);
|
||||
JavaElementArrangementEntry entry = createNewEntry(initializer, initializer.getTextRange(), FIELD, null, true);
|
||||
if (entry == null) {
|
||||
return;
|
||||
}
|
||||
@@ -211,7 +215,7 @@ public class JavaArrangementVisitor extends JavaElementVisitor {
|
||||
|
||||
@Override
|
||||
public void visitMethod(PsiMethod method) {
|
||||
ArrangementEntryType type = method.isConstructor() ? ArrangementEntryType.CONSTRUCTOR : ArrangementEntryType.METHOD;
|
||||
ArrangementSettingsToken type = method.isConstructor() ? CONSTRUCTOR : METHOD;
|
||||
JavaElementArrangementEntry entry = createNewEntry(method, method.getTextRange(), type, method.getName(), true);
|
||||
if (entry == null) {
|
||||
return;
|
||||
@@ -236,7 +240,7 @@ public class JavaArrangementVisitor extends JavaElementVisitor {
|
||||
}
|
||||
|
||||
private void parseProperties(PsiMethod method, JavaElementArrangementEntry entry) {
|
||||
if (!myGroupingRules.contains(ArrangementGroupingType.GETTERS_AND_SETTERS)) {
|
||||
if (!myGroupingRules.contains(StdArrangementTokens.Grouping.GETTERS_AND_SETTERS)) {
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -283,7 +287,7 @@ public class JavaArrangementVisitor extends JavaElementVisitor {
|
||||
return;
|
||||
}
|
||||
JavaElementArrangementEntry entry =
|
||||
createNewEntry(anonymousClass, anonymousClass.getTextRange(), ArrangementEntryType.CLASS, anonymousClass.getName(), false);
|
||||
createNewEntry(anonymousClass, anonymousClass.getTextRange(), CLASS, anonymousClass.getName(), false);
|
||||
processEntry(entry, null, anonymousClass);
|
||||
}
|
||||
|
||||
@@ -326,7 +330,7 @@ public class JavaArrangementVisitor extends JavaElementVisitor {
|
||||
@Nullable
|
||||
private JavaElementArrangementEntry createNewEntry(@NotNull PsiElement element,
|
||||
@NotNull TextRange range,
|
||||
@NotNull ArrangementEntryType type,
|
||||
@NotNull ArrangementSettingsToken type,
|
||||
@Nullable String name,
|
||||
boolean canArrange)
|
||||
{
|
||||
@@ -375,14 +379,14 @@ public class JavaArrangementVisitor extends JavaElementVisitor {
|
||||
}
|
||||
for (String modifier : PsiModifier.MODIFIERS) {
|
||||
if (modifierList.hasModifierProperty(modifier)) {
|
||||
ArrangementModifier arrangementModifier = MODIFIERS.get(modifier);
|
||||
ArrangementSettingsToken arrangementModifier = MODIFIERS.get(modifier);
|
||||
if (arrangementModifier != null) {
|
||||
entry.addModifier(arrangementModifier);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (modifierList.hasModifierProperty(PsiModifier.PACKAGE_LOCAL)) {
|
||||
entry.addModifier(ArrangementModifier.PACKAGE_PRIVATE);
|
||||
entry.addModifier(PACKAGE_PRIVATE);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+13
-17
@@ -17,12 +17,11 @@ package com.intellij.psi.codeStyle.arrangement;
|
||||
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.EnumSet;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
@@ -35,15 +34,15 @@ public class JavaElementArrangementEntry extends DefaultArrangementEntry
|
||||
implements TypeAwareArrangementEntry, NameAwareArrangementEntry,ModifierAwareArrangementEntry
|
||||
{
|
||||
|
||||
private final Set<ArrangementModifier> myModifiers = EnumSet.noneOf(ArrangementModifier.class);
|
||||
@NotNull private final Set<ArrangementSettingsToken> myModifiers = ContainerUtilRt.newHashSet();
|
||||
@NotNull private final Set<ArrangementSettingsToken> myTypes = ContainerUtilRt.newHashSet();
|
||||
|
||||
@NotNull private final Set<ArrangementEntryType> myTypes;
|
||||
@NotNull private final ArrangementEntryType myType;
|
||||
@Nullable private final String myName;
|
||||
@NotNull private final ArrangementSettingsToken myType;
|
||||
@Nullable private final String myName;
|
||||
|
||||
public JavaElementArrangementEntry(@Nullable ArrangementEntry parent,
|
||||
@NotNull TextRange range,
|
||||
@NotNull ArrangementEntryType type,
|
||||
@NotNull ArrangementSettingsToken type,
|
||||
@Nullable String name,
|
||||
boolean canBeMatched)
|
||||
{
|
||||
@@ -53,26 +52,23 @@ public class JavaElementArrangementEntry extends DefaultArrangementEntry
|
||||
public JavaElementArrangementEntry(@Nullable ArrangementEntry parent,
|
||||
int startOffset,
|
||||
int endOffset,
|
||||
@NotNull ArrangementEntryType type,
|
||||
@NotNull ArrangementSettingsToken type,
|
||||
@Nullable String name,
|
||||
boolean canBeArranged)
|
||||
{
|
||||
super(parent, startOffset, endOffset, canBeArranged);
|
||||
myType = type;
|
||||
myTypes = EnumSet.of(type);
|
||||
if (myType == ArrangementEntryType.CONSTRUCTOR) {
|
||||
myTypes.add(ArrangementEntryType.METHOD);
|
||||
}
|
||||
myTypes.add(type);
|
||||
myName = name;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Set<ArrangementModifier> getModifiers() {
|
||||
public Set<ArrangementSettingsToken> getModifiers() {
|
||||
return myModifiers;
|
||||
}
|
||||
|
||||
public void addModifier(@NotNull ArrangementModifier modifier) {
|
||||
public void addModifier(@NotNull ArrangementSettingsToken modifier) {
|
||||
myModifiers.add(modifier);
|
||||
}
|
||||
|
||||
@@ -84,12 +80,12 @@ public class JavaElementArrangementEntry extends DefaultArrangementEntry
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Set<ArrangementEntryType> getTypes() {
|
||||
public Set<ArrangementSettingsToken> getTypes() {
|
||||
return myTypes;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public ArrangementEntryType getType() {
|
||||
public ArrangementSettingsToken getType() {
|
||||
return myType;
|
||||
}
|
||||
|
||||
|
||||
@@ -18,31 +18,25 @@ package com.intellij.psi.codeStyle.arrangement;
|
||||
import com.intellij.ide.highlighter.JavaHighlightingColors;
|
||||
import com.intellij.lang.java.JavaLanguage;
|
||||
import com.intellij.openapi.editor.Document;
|
||||
import com.intellij.openapi.editor.SyntaxHighlighterColors;
|
||||
import com.intellij.openapi.editor.colors.CodeInsightColors;
|
||||
import com.intellij.openapi.editor.colors.EditorColors;
|
||||
import com.intellij.openapi.editor.colors.EditorColorsScheme;
|
||||
import com.intellij.openapi.editor.colors.TextAttributesKey;
|
||||
import com.intellij.openapi.editor.markup.TextAttributes;
|
||||
import com.intellij.openapi.util.Pair;
|
||||
import com.intellij.openapi.util.Ref;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.codeStyle.CodeStyleSettings;
|
||||
import com.intellij.psi.codeStyle.CommonCodeStyleSettings;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryMatcher;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementEntryMatcher;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.*;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementColorsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementConditionsGrouper;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsAware;
|
||||
import com.intellij.util.Function;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementCompositeMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementColorsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.*;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
@@ -51,36 +45,38 @@ import java.awt.*;
|
||||
import java.util.*;
|
||||
import java.util.List;
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType.*;
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier.*;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.EntryType.*;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Grouping.*;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Modifier.*;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Order.*;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.General.*;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 7/20/12 2:31 PM
|
||||
*/
|
||||
public class JavaRearranger implements Rearranger<JavaElementArrangementEntry>, ArrangementStandardSettingsAware,
|
||||
ArrangementConditionsGrouper, ArrangementColorsAware
|
||||
{
|
||||
public class JavaRearranger implements Rearranger<JavaElementArrangementEntry>, ArrangementStandardSettingsAware, ArrangementColorsAware {
|
||||
|
||||
// Type
|
||||
@NotNull private static final Set<ArrangementEntryType> SUPPORTED_TYPES = EnumSet.of(INTERFACE, CLASS, ENUM, FIELD, METHOD, CONSTRUCTOR);
|
||||
|
||||
// Modifier
|
||||
@NotNull private static final Set<ArrangementModifier> SUPPORTED_MODIFIERS = EnumSet.of(
|
||||
PUBLIC, PROTECTED, PACKAGE_PRIVATE, PRIVATE, STATIC, FINAL, VOLATILE, TRANSIENT, SYNCHRONIZED, ABSTRACT
|
||||
@NotNull private static final Set<ArrangementSettingsToken> SUPPORTED_TYPES = ContainerUtilRt.newLinkedHashSet(
|
||||
FIELD, CONSTRUCTOR, METHOD, CLASS, INTERFACE, ENUM
|
||||
);
|
||||
|
||||
@NotNull private static final Object NO_TYPE = new Object();
|
||||
@NotNull private static final Map<Object, Set<ArrangementModifier>> MODIFIERS_BY_TYPE = new HashMap<Object, Set<ArrangementModifier>>();
|
||||
@NotNull private static final Collection<Set<?>> MUTEXES = new ArrayList<Set<?>>();
|
||||
|
||||
// Modifier
|
||||
@NotNull private static final Set<ArrangementSettingsToken> SUPPORTED_MODIFIERS = ContainerUtilRt.newLinkedHashSet(
|
||||
PUBLIC, PROTECTED, PACKAGE_PRIVATE, PRIVATE, STATIC, FINAL, ABSTRACT, SYNCHRONIZED, TRANSIENT, VOLATILE
|
||||
);
|
||||
@NotNull private static final List<ArrangementSettingsToken> SUPPORTED_ORDERS = ContainerUtilRt.newArrayList(KEEP, BY_NAME);
|
||||
@NotNull private static final ArrangementSettingsToken NO_TYPE = new ArrangementSettingsToken("NO_TYPE", "NO_TYPE");
|
||||
@NotNull
|
||||
private static final Map<ArrangementSettingsToken, Set<ArrangementSettingsToken>> MODIFIERS_BY_TYPE = ContainerUtilRt.newHashMap();
|
||||
@NotNull private static final Collection<Set<ArrangementSettingsToken>> MUTEXES = ContainerUtilRt.newArrayList();
|
||||
static {
|
||||
EnumSet<ArrangementModifier> visibilityModifiers = EnumSet.of(PUBLIC, PROTECTED, PACKAGE_PRIVATE, PRIVATE);
|
||||
Set<ArrangementSettingsToken> visibilityModifiers = ContainerUtilRt.newHashSet(PUBLIC, PROTECTED, PACKAGE_PRIVATE, PRIVATE);
|
||||
MUTEXES.add(visibilityModifiers);
|
||||
MUTEXES.add(SUPPORTED_TYPES);
|
||||
|
||||
Set<ArrangementModifier> commonModifiers = concat(visibilityModifiers, STATIC, FINAL);
|
||||
|
||||
Set<ArrangementSettingsToken> commonModifiers = concat(visibilityModifiers, STATIC, FINAL);
|
||||
|
||||
MODIFIERS_BY_TYPE.put(NO_TYPE, commonModifiers);
|
||||
MODIFIERS_BY_TYPE.put(ENUM, visibilityModifiers);
|
||||
MODIFIERS_BY_TYPE.put(INTERFACE, visibilityModifiers);
|
||||
@@ -89,135 +85,20 @@ public class JavaRearranger implements Rearranger<JavaElementArrangementEntry>,
|
||||
MODIFIERS_BY_TYPE.put(CONSTRUCTOR, concat(commonModifiers, SYNCHRONIZED));
|
||||
MODIFIERS_BY_TYPE.put(FIELD, concat(commonModifiers, TRANSIENT, VOLATILE));
|
||||
}
|
||||
|
||||
@NotNull private static final List<Set<ArrangementMatchCondition>> UI_GROUPING_RULES = ContainerUtilRt.newArrayList();
|
||||
private static final Map<ArrangementSettingsToken, List<ArrangementSettingsToken>> GROUPING_RULES = ContainerUtilRt.newLinkedHashMap();
|
||||
static {
|
||||
UI_GROUPING_RULES.add(new HashSet<ArrangementMatchCondition>(
|
||||
ContainerUtil.map(
|
||||
SUPPORTED_TYPES,
|
||||
new Function<ArrangementEntryType, ArrangementMatchCondition>() {
|
||||
@Override
|
||||
public ArrangementMatchCondition fun(ArrangementEntryType type) {
|
||||
return new ArrangementAtomMatchCondition(ArrangementSettingType.TYPE, type);
|
||||
}
|
||||
}
|
||||
)
|
||||
));
|
||||
}
|
||||
|
||||
private static final Map<ArrangementGroupingType, Set<ArrangementEntryOrderType>> GROUPING_RULES = ContainerUtilRt.newHashMap();
|
||||
static {
|
||||
GROUPING_RULES.put(ArrangementGroupingType.GETTERS_AND_SETTERS, EnumSet.noneOf(ArrangementEntryOrderType.class));
|
||||
GROUPING_RULES.put(ArrangementGroupingType.OVERRIDDEN_METHODS,
|
||||
EnumSet.of(ArrangementEntryOrderType.BY_NAME, ArrangementEntryOrderType.KEEP));
|
||||
GROUPING_RULES.put(ArrangementGroupingType.DEPENDENT_METHODS,
|
||||
EnumSet.of(ArrangementEntryOrderType.BREADTH_FIRST, ArrangementEntryOrderType.DEPTH_FIRST));
|
||||
}
|
||||
|
||||
private static final List<ArrangementGroupingRule> DEFAULT_GROUPING_RULES = new ArrayList<ArrangementGroupingRule>();
|
||||
static {
|
||||
DEFAULT_GROUPING_RULES.add(new ArrangementGroupingRule(ArrangementGroupingType.GETTERS_AND_SETTERS));
|
||||
}
|
||||
|
||||
private static final List<StdArrangementMatchRule> DEFAULT_MATCH_RULES = new ArrayList<StdArrangementMatchRule>();
|
||||
|
||||
static {
|
||||
ArrangementModifier[] visibility = {PUBLIC, PROTECTED, PACKAGE_PRIVATE, PRIVATE};
|
||||
for (ArrangementModifier modifier : visibility) {
|
||||
and(FIELD, STATIC, FINAL, modifier);
|
||||
}
|
||||
for (ArrangementModifier modifier : visibility) {
|
||||
and(FIELD, STATIC, modifier);
|
||||
}
|
||||
for (ArrangementModifier modifier : visibility) {
|
||||
and(FIELD, FINAL, modifier);
|
||||
}
|
||||
for (ArrangementModifier modifier : visibility) {
|
||||
and(FIELD, modifier);
|
||||
}
|
||||
and(FIELD);
|
||||
and(CONSTRUCTOR);
|
||||
and(METHOD, STATIC);
|
||||
and(METHOD);
|
||||
and(ENUM);
|
||||
and(INTERFACE);
|
||||
and(CLASS, STATIC);
|
||||
and(CLASS);
|
||||
}
|
||||
|
||||
private static final StdArrangementSettings DEFAULT_SETTINGS = new StdArrangementSettings(DEFAULT_GROUPING_RULES, DEFAULT_MATCH_RULES);
|
||||
|
||||
private static void and(@NotNull Object... conditions) {
|
||||
if (conditions.length == 1) {
|
||||
DEFAULT_MATCH_RULES.add(new StdArrangementMatchRule(new StdArrangementEntryMatcher(new ArrangementAtomMatchCondition(
|
||||
ArrangementUtil.parseType(conditions[0]), conditions[0]
|
||||
))));
|
||||
return;
|
||||
}
|
||||
|
||||
ArrangementCompositeMatchCondition composite = new ArrangementCompositeMatchCondition();
|
||||
for (Object condition : conditions) {
|
||||
composite.addOperand(new ArrangementAtomMatchCondition(ArrangementUtil.parseType(condition), condition));
|
||||
}
|
||||
DEFAULT_MATCH_RULES.add(new StdArrangementMatchRule(new StdArrangementEntryMatcher(composite)));
|
||||
GROUPING_RULES.put(GETTERS_AND_SETTERS, Collections.<ArrangementSettingsToken>emptyList());
|
||||
GROUPING_RULES.put(OVERRIDDEN_METHODS, ContainerUtilRt.newArrayList(BY_NAME, KEEP));
|
||||
GROUPING_RULES.put(DEPENDENT_METHODS, ContainerUtilRt.newArrayList(BREADTH_FIRST, DEPTH_FIRST));
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private static Set<ArrangementModifier> concat(@NotNull Set<ArrangementModifier> base, ArrangementModifier... modifiers) {
|
||||
EnumSet<ArrangementModifier> result = EnumSet.copyOf(base);
|
||||
private static Set<ArrangementSettingsToken> concat(@NotNull Set<ArrangementSettingsToken> base, ArrangementSettingsToken... modifiers) {
|
||||
Set<ArrangementSettingsToken> result = ContainerUtilRt.newHashSet(base);
|
||||
Collections.addAll(result, modifiers);
|
||||
return result;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Pair<JavaElementArrangementEntry, List<JavaElementArrangementEntry>> parseWithNew(
|
||||
@NotNull PsiElement root,
|
||||
@Nullable Document document,
|
||||
@NotNull Collection<TextRange> ranges,
|
||||
@NotNull PsiElement element,
|
||||
@Nullable ArrangementSettings settings)
|
||||
{
|
||||
Set<ArrangementGroupingType> groupingRules = getGroupingRules(settings);
|
||||
JavaArrangementParseInfo existingEntriesInfo = new JavaArrangementParseInfo();
|
||||
root.accept(new JavaArrangementVisitor(existingEntriesInfo, document, ranges, groupingRules));
|
||||
|
||||
JavaArrangementParseInfo newEntryInfo = new JavaArrangementParseInfo();
|
||||
element.accept(new JavaArrangementVisitor(newEntryInfo, document, Collections.singleton(element.getTextRange()), groupingRules));
|
||||
if (newEntryInfo.getEntries().size() != 1) {
|
||||
return null;
|
||||
}
|
||||
return Pair.create(newEntryInfo.getEntries().get(0), existingEntriesInfo.getEntries());
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public List<JavaElementArrangementEntry> parse(@NotNull PsiElement root,
|
||||
@Nullable Document document,
|
||||
@NotNull Collection<TextRange> ranges,
|
||||
@Nullable ArrangementSettings settings)
|
||||
{
|
||||
// Following entries are subject to arrangement: class, interface, field, method.
|
||||
JavaArrangementParseInfo parseInfo = new JavaArrangementParseInfo();
|
||||
root.accept(new JavaArrangementVisitor(parseInfo, document, ranges, getGroupingRules(settings)));
|
||||
if (settings != null) {
|
||||
for (ArrangementGroupingRule rule : settings.getGroupings()) {
|
||||
switch (rule.getGroupingType()) {
|
||||
case GETTERS_AND_SETTERS:
|
||||
setupGettersAndSetters(parseInfo);
|
||||
break;
|
||||
case DEPENDENT_METHODS:
|
||||
setupUtilityMethods(parseInfo, rule.getOrderType());
|
||||
break;
|
||||
case OVERRIDDEN_METHODS:
|
||||
setupOverriddenMethods(parseInfo);
|
||||
default: // Do nothing
|
||||
}
|
||||
}
|
||||
}
|
||||
return parseInfo.getEntries();
|
||||
}
|
||||
|
||||
private static void setupGettersAndSetters(@NotNull JavaArrangementParseInfo info) {
|
||||
Collection<JavaArrangementPropertyInfo> properties = info.getProperties();
|
||||
for (JavaArrangementPropertyInfo propertyInfo : properties) {
|
||||
@@ -229,18 +110,19 @@ public class JavaRearranger implements Rearranger<JavaElementArrangementEntry>,
|
||||
}
|
||||
}
|
||||
|
||||
private static void setupUtilityMethods(@NotNull JavaArrangementParseInfo info, @NotNull ArrangementEntryOrderType orderType) {
|
||||
switch (orderType) {
|
||||
case DEPTH_FIRST:
|
||||
for (JavaArrangementMethodDependencyInfo rootInfo : info.getMethodDependencyRoots()) {
|
||||
setupDepthFirstDependency(rootInfo);
|
||||
}
|
||||
break;
|
||||
case BREADTH_FIRST:
|
||||
for (JavaArrangementMethodDependencyInfo rootInfo : info.getMethodDependencyRoots()) {
|
||||
setupBreadthFirstDependency(rootInfo);
|
||||
}
|
||||
default: // Unexpected type, do nothing
|
||||
private static void setupUtilityMethods(@NotNull JavaArrangementParseInfo info, @NotNull ArrangementSettingsToken orderType) {
|
||||
if (DEPTH_FIRST.equals(orderType)) {
|
||||
for (JavaArrangementMethodDependencyInfo rootInfo : info.getMethodDependencyRoots()) {
|
||||
setupDepthFirstDependency(rootInfo);
|
||||
}
|
||||
}
|
||||
else if (BREADTH_FIRST.equals(orderType)) {
|
||||
for (JavaArrangementMethodDependencyInfo rootInfo : info.getMethodDependencyRoots()) {
|
||||
setupBreadthFirstDependency(rootInfo);
|
||||
}
|
||||
}
|
||||
else {
|
||||
assert false : orderType;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -280,16 +162,52 @@ public class JavaRearranger implements Rearranger<JavaElementArrangementEntry>,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Pair<JavaElementArrangementEntry, List<JavaElementArrangementEntry>> parseWithNew(
|
||||
@NotNull PsiElement root,
|
||||
@Nullable Document document,
|
||||
@NotNull Collection<TextRange> ranges,
|
||||
@NotNull PsiElement element,
|
||||
@Nullable ArrangementSettings settings)
|
||||
{
|
||||
Set<ArrangementSettingsToken> groupingRules = getGroupingRules(settings);
|
||||
JavaArrangementParseInfo existingEntriesInfo = new JavaArrangementParseInfo();
|
||||
root.accept(new JavaArrangementVisitor(existingEntriesInfo, document, ranges, groupingRules));
|
||||
|
||||
JavaArrangementParseInfo newEntryInfo = new JavaArrangementParseInfo();
|
||||
element.accept(new JavaArrangementVisitor(newEntryInfo, document, Collections.singleton(element.getTextRange()), groupingRules));
|
||||
if (newEntryInfo.getEntries().size() != 1) {
|
||||
return null;
|
||||
}
|
||||
return Pair.create(newEntryInfo.getEntries().get(0), existingEntriesInfo.getEntries());
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private static Set<ArrangementGroupingType> getGroupingRules(@Nullable ArrangementSettings settings) {
|
||||
Set<ArrangementGroupingType> groupingRules = EnumSet.noneOf(ArrangementGroupingType.class);
|
||||
@Override
|
||||
public List<JavaElementArrangementEntry> parse(@NotNull PsiElement root,
|
||||
@Nullable Document document,
|
||||
@NotNull Collection<TextRange> ranges,
|
||||
@Nullable ArrangementSettings settings)
|
||||
{
|
||||
// Following entries are subject to arrangement: class, interface, field, method.
|
||||
JavaArrangementParseInfo parseInfo = new JavaArrangementParseInfo();
|
||||
root.accept(new JavaArrangementVisitor(parseInfo, document, ranges, getGroupingRules(settings)));
|
||||
if (settings != null) {
|
||||
for (ArrangementGroupingRule rule : settings.getGroupings()) {
|
||||
groupingRules.add(rule.getGroupingType());
|
||||
if (GETTERS_AND_SETTERS.equals(rule.getGroupingType())) {
|
||||
setupGettersAndSetters(parseInfo);
|
||||
}
|
||||
else if (DEPENDENT_METHODS.equals(rule.getGroupingType())) {
|
||||
setupUtilityMethods(parseInfo, rule.getOrderType());
|
||||
}
|
||||
else if (OVERRIDDEN_METHODS.equals(rule.getGroupingType())) {
|
||||
setupOverriddenMethods(parseInfo);
|
||||
}
|
||||
}
|
||||
}
|
||||
return groupingRules;
|
||||
return parseInfo.getEntries();
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -303,112 +221,153 @@ public class JavaRearranger implements Rearranger<JavaElementArrangementEntry>,
|
||||
}
|
||||
|
||||
CommonCodeStyleSettings commonSettings = settings.getCommonSettings(JavaLanguage.INSTANCE);
|
||||
switch (target.getType()) {
|
||||
case FIELD:
|
||||
if (parent != null && parent.getType() == INTERFACE) {
|
||||
return commonSettings.BLANK_LINES_AROUND_FIELD_IN_INTERFACE;
|
||||
}
|
||||
else {
|
||||
return commonSettings.BLANK_LINES_AROUND_FIELD;
|
||||
}
|
||||
case METHOD:
|
||||
if (parent != null && parent.getType() == INTERFACE) {
|
||||
return commonSettings.BLANK_LINES_AROUND_METHOD_IN_INTERFACE;
|
||||
}
|
||||
else {
|
||||
return commonSettings.BLANK_LINES_AROUND_METHOD;
|
||||
}
|
||||
case CLASS: return commonSettings.BLANK_LINES_AROUND_CLASS;
|
||||
default: return -1;
|
||||
if (FIELD.equals(target.getType())) {
|
||||
if (parent != null && parent.getType() == INTERFACE) {
|
||||
return commonSettings.BLANK_LINES_AROUND_FIELD_IN_INTERFACE;
|
||||
}
|
||||
else {
|
||||
return commonSettings.BLANK_LINES_AROUND_FIELD;
|
||||
}
|
||||
}
|
||||
else if (METHOD.equals(target.getType())) {
|
||||
if (parent != null && parent.getType() == INTERFACE) {
|
||||
return commonSettings.BLANK_LINES_AROUND_METHOD_IN_INTERFACE;
|
||||
}
|
||||
else {
|
||||
return commonSettings.BLANK_LINES_AROUND_METHOD;
|
||||
}
|
||||
}
|
||||
else if (CLASS.equals(target.getType())) {
|
||||
return commonSettings.BLANK_LINES_AROUND_CLASS;
|
||||
}
|
||||
else {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled(@NotNull ArrangementEntryType type, @Nullable ArrangementMatchCondition current) {
|
||||
return SUPPORTED_TYPES.contains(type);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled(@NotNull ArrangementModifier modifier, @Nullable ArrangementMatchCondition current) {
|
||||
if (current == null) {
|
||||
return SUPPORTED_MODIFIERS.contains(modifier);
|
||||
@NotNull
|
||||
private static Set<ArrangementSettingsToken> getGroupingRules(@Nullable ArrangementSettings settings) {
|
||||
Set<ArrangementSettingsToken> groupingRules = ContainerUtilRt.newHashSet();
|
||||
if (settings != null) {
|
||||
for (ArrangementGroupingRule rule : settings.getGroupings()) {
|
||||
groupingRules.add(rule.getGroupingType());
|
||||
}
|
||||
}
|
||||
|
||||
final Ref<Object> typeRef = new Ref<Object>();
|
||||
current.invite(new ArrangementMatchConditionVisitor() {
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementAtomMatchCondition setting) {
|
||||
if (setting.getType() == ArrangementSettingType.TYPE) {
|
||||
typeRef.set(setting.getValue());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementCompositeMatchCondition setting) {
|
||||
for (ArrangementMatchCondition n : setting.getOperands()) {
|
||||
if (typeRef.get() != null) {
|
||||
return;
|
||||
}
|
||||
n.invite(this);
|
||||
}
|
||||
}
|
||||
});
|
||||
Object key = typeRef.get() == null ? NO_TYPE : typeRef.get();
|
||||
Set<ArrangementModifier> modifiers = MODIFIERS_BY_TYPE.get(key);
|
||||
return modifiers != null && modifiers.contains(modifier);
|
||||
return groupingRules;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Collection<Set<?>> getMutexes() {
|
||||
public StdArrangementSettings getDefaultSettings() {
|
||||
List<ArrangementGroupingRule> groupingRules = ContainerUtilRt.newArrayList(new ArrangementGroupingRule(GETTERS_AND_SETTERS));
|
||||
List<StdArrangementMatchRule> matchRules = ContainerUtilRt.newArrayList();
|
||||
ArrangementSettingsToken[] visibility = {PUBLIC, PROTECTED, PACKAGE_PRIVATE, PRIVATE};
|
||||
for (ArrangementSettingsToken modifier : visibility) {
|
||||
and(matchRules, FIELD, STATIC, FINAL, modifier);
|
||||
}
|
||||
for (ArrangementSettingsToken modifier : visibility) {
|
||||
and(matchRules, FIELD, STATIC, modifier);
|
||||
}
|
||||
for (ArrangementSettingsToken modifier : visibility) {
|
||||
and(matchRules, FIELD, FINAL, modifier);
|
||||
}
|
||||
for (ArrangementSettingsToken modifier : visibility) {
|
||||
and(matchRules, FIELD, modifier);
|
||||
}
|
||||
and(matchRules, FIELD);
|
||||
and(matchRules, CONSTRUCTOR);
|
||||
and(matchRules, METHOD, STATIC);
|
||||
and(matchRules, METHOD);
|
||||
and(matchRules, ENUM);
|
||||
and(matchRules, INTERFACE);
|
||||
and(matchRules, CLASS, STATIC);
|
||||
and(matchRules, CLASS);
|
||||
|
||||
return new StdArrangementSettings(groupingRules, matchRules);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<CompositeArrangementSettingsToken> getSupportedGroupingTokens() {
|
||||
return ContainerUtilRt.newArrayList(
|
||||
new CompositeArrangementSettingsToken(GETTERS_AND_SETTERS),
|
||||
new CompositeArrangementSettingsToken(OVERRIDDEN_METHODS, BY_NAME, KEEP),
|
||||
new CompositeArrangementSettingsToken(DEPENDENT_METHODS, BREADTH_FIRST, DEPTH_FIRST)
|
||||
);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<CompositeArrangementSettingsToken> getSupportedMatchingTokens() {
|
||||
return ContainerUtilRt.newArrayList(
|
||||
new CompositeArrangementSettingsToken(TYPE, SUPPORTED_TYPES),
|
||||
new CompositeArrangementSettingsToken(MODIFIER, SUPPORTED_MODIFIERS),
|
||||
new CompositeArrangementSettingsToken(NAME),
|
||||
new CompositeArrangementSettingsToken(ORDER, KEEP, BY_NAME)
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled(@NotNull ArrangementSettingsToken token, @Nullable ArrangementMatchCondition current) {
|
||||
if (SUPPORTED_TYPES.contains(token) || SUPPORTED_ORDERS.contains(token) || NAME.equals(token)) {
|
||||
return true;
|
||||
}
|
||||
ArrangementSettingsToken type = null;
|
||||
if (current != null) {
|
||||
type = ArrangementUtil.parseType(current);
|
||||
}
|
||||
if (type == null) {
|
||||
type = NO_TYPE;
|
||||
}
|
||||
Set<ArrangementSettingsToken> modifiers = MODIFIERS_BY_TYPE.get(type);
|
||||
return modifiers != null && modifiers.contains(token);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public ArrangementEntryMatcher buildMatcher(@NotNull ArrangementMatchCondition condition) throws IllegalArgumentException {
|
||||
throw new IllegalArgumentException("Can't build a matcher for condition " + condition);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Collection<Set<ArrangementSettingsToken>> getMutexes() {
|
||||
return MUTEXES;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public List<Set<ArrangementMatchCondition>> getGroupingConditions() {
|
||||
return Collections.emptyList();
|
||||
//return UI_GROUPING_RULES;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public StdArrangementSettings getDefaultSettings() {
|
||||
return DEFAULT_SETTINGS;
|
||||
}
|
||||
private static void and(@NotNull List<StdArrangementMatchRule> matchRules, @NotNull ArrangementSettingsToken... conditions) {
|
||||
if (conditions.length == 1) {
|
||||
matchRules.add(new StdArrangementMatchRule(new StdArrangementEntryMatcher(new ArrangementAtomMatchCondition(
|
||||
conditions[0], conditions[0]
|
||||
))));
|
||||
return;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isNameFilterSupported() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled(@NotNull ArrangementGroupingType groupingType, @Nullable ArrangementEntryOrderType orderType) {
|
||||
Set<ArrangementEntryOrderType> orderTypes = GROUPING_RULES.get(groupingType);
|
||||
if (orderTypes == null) {
|
||||
return false;
|
||||
ArrangementCompositeMatchCondition composite = new ArrangementCompositeMatchCondition();
|
||||
for (ArrangementSettingsToken condition : conditions) {
|
||||
composite.addOperand(new ArrangementAtomMatchCondition(condition, condition));
|
||||
}
|
||||
matchRules.add(new StdArrangementMatchRule(new StdArrangementEntryMatcher(composite)));
|
||||
}
|
||||
return orderType == null || orderTypes.contains(orderType);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public TextAttributes getTextAttributes(@NotNull EditorColorsScheme scheme, @NotNull ArrangementSettingType type, boolean selected) {
|
||||
public TextAttributes getTextAttributes(@NotNull EditorColorsScheme scheme, @NotNull ArrangementSettingsToken token, boolean selected) {
|
||||
if (selected) {
|
||||
TextAttributes attributes = new TextAttributes();
|
||||
attributes.setForegroundColor(scheme.getColor(EditorColors.SELECTION_FOREGROUND_COLOR));
|
||||
attributes.setBackgroundColor(scheme.getColor(EditorColors.SELECTION_BACKGROUND_COLOR));
|
||||
return attributes;
|
||||
}
|
||||
if (type == ArrangementSettingType.MODIFIER) {
|
||||
else if (SUPPORTED_TYPES.contains(token)) {
|
||||
return getAttributes(scheme, JavaHighlightingColors.KEYWORD);
|
||||
}
|
||||
else if (type == ArrangementSettingType.TYPE) {
|
||||
return getAttributes(scheme, CodeInsightColors.CLASS_NAME_ATTRIBUTES, CodeInsightColors.INTERFACE_NAME_ATTRIBUTES);
|
||||
else if (SUPPORTED_MODIFIERS.contains(token)) {
|
||||
getAttributes(scheme, JavaHighlightingColors.KEYWORD);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
@Nullable
|
||||
private static TextAttributes getAttributes(@NotNull EditorColorsScheme scheme, @NotNull TextAttributesKey ... keys) {
|
||||
TextAttributes result = null;
|
||||
|
||||
+3
-2
@@ -15,8 +15,9 @@
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType.*
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier.*
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.EntryType.*
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Modifier.*
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/30/12 12:14 PM
|
||||
|
||||
+6
-8
@@ -15,13 +15,11 @@
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType
|
||||
import org.junit.Before
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier.PROTECTED
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier.PUBLIC
|
||||
import static com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType.BY_NAME
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Modifier.PROTECTED
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Modifier.PUBLIC
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Order.BY_NAME
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
@@ -50,7 +48,7 @@ class Test {
|
||||
public void setI() {}
|
||||
public void test() {}
|
||||
}''',
|
||||
rules: [rule("get.*")]
|
||||
rules: [nameRule("get.*")]
|
||||
)
|
||||
}
|
||||
|
||||
@@ -68,7 +66,7 @@ class Test {
|
||||
protected void test() {}
|
||||
private void getInner() {}
|
||||
}''',
|
||||
rules: [rule("get.*", PUBLIC), rule(PROTECTED)]
|
||||
rules: [nameRule("get.*", PUBLIC), rule(PROTECTED)]
|
||||
)
|
||||
}
|
||||
|
||||
@@ -88,7 +86,7 @@ class Test {
|
||||
private void getC() {}
|
||||
public void test() {}
|
||||
}''',
|
||||
rules: [rule(BY_NAME, "get.*")]
|
||||
rules: [ruleWithOrder(BY_NAME, nameRule("get.*"))]
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
+8
-7
@@ -15,15 +15,16 @@
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType.*
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier.*
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.EntryType.*
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Modifier.*
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/28/12 6:42 PM
|
||||
*/
|
||||
class JavaRearrangerByTypeAndModifierTest extends AbstractJavaRearrangerTest {
|
||||
|
||||
void testComplex() {
|
||||
void "test complex sample"() {
|
||||
commonSettings.BLANK_LINES_AROUND_METHOD = 0
|
||||
commonSettings.BLANK_LINES_AROUND_CLASS = 0
|
||||
|
||||
@@ -34,7 +35,7 @@ class Test {
|
||||
protected static class ProtectedStaticInner {}
|
||||
public class PublicInner {}
|
||||
private interface PrivateInterface {}
|
||||
public abstract abstractMethod();
|
||||
public abstract void abstractMethod();
|
||||
private void privateMethod() {}
|
||||
public void publicMethod() {}
|
||||
private int privateField;
|
||||
@@ -48,7 +49,7 @@ class Test {
|
||||
public int publicField;
|
||||
private volatile int privateVolatileField;
|
||||
private int privateField;
|
||||
public abstract abstractMethod();
|
||||
public abstract void abstractMethod();
|
||||
public void publicMethod() {}
|
||||
private void privateMethod() {}
|
||||
private interface PrivateInterface {}
|
||||
@@ -70,7 +71,7 @@ class Test {
|
||||
)
|
||||
}
|
||||
|
||||
void testInstanceInitializationBlockBoundToField() {
|
||||
void "test instance initialization block bound to a field"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Test {
|
||||
@@ -89,7 +90,7 @@ class Test {
|
||||
rules: [rule(FIELD, PUBLIC), rule(FIELD, PROTECTED), rule(FIELD, PRIVATE)])
|
||||
}
|
||||
|
||||
void testInstanceInitializationBlockAsFirstChild() {
|
||||
void "test instance initialization block as the first child"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Test {
|
||||
|
||||
+14
-32
@@ -15,13 +15,12 @@
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType
|
||||
import org.junit.Before
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType.*
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier.PRIVATE
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier.PROTECTED
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier.PUBLIC
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Modifier.*
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.EntryType.*
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Order.*
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 7/20/12 2:45 PM
|
||||
@@ -35,7 +34,7 @@ class JavaRearrangerByTypeTest extends AbstractJavaRearrangerTest {
|
||||
commonSettings.BLANK_LINES_AROUND_CLASS = 0
|
||||
}
|
||||
|
||||
void testFieldsBeforeMethods() {
|
||||
void "test fields before methods"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Test {
|
||||
@@ -48,6 +47,7 @@ public void test() {
|
||||
private int i;
|
||||
private int j;
|
||||
}''',
|
||||
rules: [rule(FIELD)],
|
||||
expected: '''\
|
||||
class Test {
|
||||
private int i;
|
||||
@@ -58,12 +58,11 @@ class Test2 {
|
||||
private int j;
|
||||
public void test() {
|
||||
}
|
||||
}''',
|
||||
rules: [rule(FIELD)]
|
||||
}'''
|
||||
)
|
||||
}
|
||||
|
||||
void testAnonymousClassAtFieldInitializer() {
|
||||
void "test anonymous class at field initializer"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Test {
|
||||
@@ -107,7 +106,7 @@ class Test {
|
||||
)
|
||||
}
|
||||
|
||||
void testAnonymousClassAtMethod() {
|
||||
void "test anonymous class at method"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Test {
|
||||
@@ -145,7 +144,7 @@ class Test {
|
||||
)
|
||||
}
|
||||
|
||||
void testInnerClassInterfaceAndEnum() {
|
||||
void "test inner class interface and enum"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Test {
|
||||
@@ -165,7 +164,7 @@ class Test {
|
||||
)
|
||||
}
|
||||
|
||||
void testRanges() {
|
||||
void "test ranges"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Test {
|
||||
@@ -203,7 +202,7 @@ class Test {
|
||||
)
|
||||
}
|
||||
|
||||
void testMethodsAndConstructors() {
|
||||
void "test methods and constructors"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Test {
|
||||
@@ -220,24 +219,7 @@ class Test {
|
||||
rules: [rule(CONSTRUCTOR), rule(METHOD)])
|
||||
}
|
||||
|
||||
void testConstructorAsMethod() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Test {
|
||||
private int i;
|
||||
Test() {}
|
||||
public int j;
|
||||
}''',
|
||||
expected: '''\
|
||||
class Test {
|
||||
public int j;
|
||||
Test() {}
|
||||
private int i;
|
||||
}''',
|
||||
rules: [rule(FIELD, PUBLIC), rule(METHOD), rule(FIELD)])
|
||||
}
|
||||
|
||||
void testMultipleFieldsInOneRow() {
|
||||
void "test multiple fields in one row"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Test {
|
||||
@@ -326,7 +308,7 @@ class Test {
|
||||
int c; // comment
|
||||
int a;
|
||||
}''',
|
||||
rules: [rule(ArrangementEntryOrderType.BY_NAME, FIELD)],
|
||||
rules: [ruleWithOrder(BY_NAME, rule(FIELD))],
|
||||
expected: '''\
|
||||
class Test {
|
||||
int a;
|
||||
|
||||
+9
-11
@@ -17,12 +17,10 @@ package com.intellij.psi.codeStyle.arrangement
|
||||
|
||||
import org.junit.Test
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType.GETTERS_AND_SETTERS
|
||||
import static com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType.OVERRIDDEN_METHODS
|
||||
import static com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType.DEPENDENT_METHODS
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier.PUBLIC
|
||||
import static com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType.BREADTH_FIRST
|
||||
import static com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType.DEPTH_FIRST
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Grouping.*
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Modifier.PUBLIC
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Order.BREADTH_FIRST
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Order.DEPTH_FIRST
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
@@ -35,7 +33,7 @@ class JavaRearrangerGrouperTest extends AbstractJavaRearrangerTest {
|
||||
commonSettings.BLANK_LINES_AROUND_METHOD = 0
|
||||
}
|
||||
|
||||
void testGettersAndSetters() {
|
||||
void "test getters and setters"() {
|
||||
commonSettings.BLANK_LINES_AROUND_METHOD = 1
|
||||
|
||||
doTest(
|
||||
@@ -59,7 +57,7 @@ class Test {
|
||||
}
|
||||
|
||||
@Test
|
||||
void testUtilityMethodsDepthFirst() {
|
||||
void "test utility methods depth-first"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Test {
|
||||
@@ -81,7 +79,7 @@ class Test {
|
||||
}
|
||||
|
||||
@Test
|
||||
void testUtilityMethodsBreadthFirst() {
|
||||
void "test utility methods breadth-first"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Test {
|
||||
@@ -100,7 +98,7 @@ class Test {
|
||||
}''')
|
||||
}
|
||||
|
||||
void testOverriddenMethods() {
|
||||
void "test overridden methods"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Base {
|
||||
@@ -128,7 +126,7 @@ class Sub extends Base {
|
||||
void test2() {}
|
||||
}''')
|
||||
}
|
||||
void testOverriddenAndUtilityMethods() {
|
||||
void "test overriden and utility methods"() {
|
||||
doTest(
|
||||
initial: '''\
|
||||
class Base {
|
||||
|
||||
+10
-18
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2012 JetBrains s.r.o.
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -15,9 +15,6 @@
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.group.ArrangementGroupingRulesControl;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchingRulesControl;
|
||||
import com.intellij.openapi.actionSystem.DataKey;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
|
||||
/**
|
||||
@@ -26,11 +23,6 @@ import org.jetbrains.annotations.NonNls;
|
||||
*/
|
||||
public class ArrangementConstants {
|
||||
|
||||
public static final DataKey<ArrangementGroupingRulesControl> GROUPING_RULES_CONTROL_KEY =
|
||||
DataKey.create("Arrangement.Rule.Group.Control");
|
||||
public static final DataKey<ArrangementMatchingRulesControl> MATCHING_RULES_CONTROL_KEY =
|
||||
DataKey.create("Arrangement.Rule.Match.Control");
|
||||
|
||||
@NonNls public static final String ACTION_GROUP_GROUPING_RULES_CONTROL_TOOLBAR = "Arrangement.Rule.Group.Control.ToolBar";
|
||||
@NonNls public static final String GROUPING_RULES_CONTROL_TOOLBAR_PLACE = "Arrangement.Rule.Group.Control.ToolBar.Place";
|
||||
|
||||
@@ -39,19 +31,19 @@ public class ArrangementConstants {
|
||||
@NonNls public static final String MATCHING_RULES_CONTROL_TOOLBAR_PLACE = "Arrangement.Rule.Match.Control.ToolBar.Place";
|
||||
@NonNls public static final String MATCHING_RULES_CONTROL_PLACE = "Arrangement.Rule.Match.Control.Place";
|
||||
|
||||
public static final int HORIZONTAL_PADDING = 8;
|
||||
public static final int VERTICAL_PADDING = 4;
|
||||
public static final int HORIZONTAL_GAP = 5;
|
||||
public static final int VERTICAL_GAP = 3;
|
||||
public static final int HORIZONTAL_PADDING = 8;
|
||||
public static final int VERTICAL_PADDING = 4;
|
||||
public static final int HORIZONTAL_GAP = 5;
|
||||
public static final int VERTICAL_GAP = 3;
|
||||
public static final int CALLOUT_BORDER_HEIGHT = 10;
|
||||
public static final int BORDER_ARC_SIZE = 12;
|
||||
|
||||
public static final int ANIMATION_ITERATION_PIXEL_STEP = 5;
|
||||
public static final int ANIMATION_STEPS_TIME_GAP_MILLIS = 40;
|
||||
public static final int NAME_CONDITION_UPDATE_DELAY_MILLIS = 1000;
|
||||
|
||||
public static final int ANIMATION_ITERATION_PIXEL_STEP = 5;
|
||||
public static final int ANIMATION_STEPS_TIME_GAP_MILLIS = 40;
|
||||
public static final int TEXT_UPDATE_DELAY_MILLIS = 1000;
|
||||
|
||||
public static final boolean LOG_RULE_MODIFICATION = Boolean.parseBoolean(System.getProperty("log.arrangement.rule.modification"));
|
||||
|
||||
|
||||
private ArrangementConstants() {
|
||||
}
|
||||
}
|
||||
+3
-3
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2012 JetBrains s.r.o.
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,7 +16,7 @@
|
||||
package com.intellij.application.options.codeStyle.arrangement.color;
|
||||
|
||||
import com.intellij.openapi.editor.markup.TextAttributes;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.awt.*;
|
||||
@@ -31,5 +31,5 @@ public interface ArrangementColorsProvider {
|
||||
Color getBorderColor(boolean selected);
|
||||
|
||||
@NotNull
|
||||
TextAttributes getTextAttributes(@NotNull ArrangementSettingType type, boolean selected);
|
||||
TextAttributes getTextAttributes(@NotNull ArrangementSettingsToken token, boolean selected);
|
||||
}
|
||||
-133
@@ -1,133 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.psi.codeStyle.arrangement;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementEntryMatcher;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementCompositeMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 10/31/12 12:30 PM
|
||||
*/
|
||||
public class ArrangementRuleInfo {
|
||||
|
||||
@NotNull private final Set<ArrangementAtomMatchCondition> myAtomConditions = ContainerUtilRt.newHashSet();
|
||||
@NotNull private final Set<Object> myConditions = ContainerUtilRt.newHashSet();
|
||||
|
||||
@NotNull private ArrangementEntryOrderType myOrderType = ArrangementMatchRule.DEFAULT_ORDER_TYPE;
|
||||
|
||||
@Nullable private String myNamePattern;
|
||||
|
||||
@Nullable
|
||||
public String getNamePattern() {
|
||||
return myNamePattern;
|
||||
}
|
||||
|
||||
public void setNamePattern(@Nullable String namePattern) {
|
||||
myNamePattern = namePattern;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public ArrangementEntryOrderType getOrderType() {
|
||||
return myOrderType;
|
||||
}
|
||||
|
||||
public void setOrderType(@NotNull ArrangementEntryOrderType orderType) {
|
||||
myOrderType = orderType;
|
||||
}
|
||||
|
||||
public void addAtomCondition(@NotNull ArrangementAtomMatchCondition condition) {
|
||||
switch (condition.getType()) {
|
||||
case NAME: myNamePattern = condition.getValue().toString(); break;
|
||||
default:
|
||||
myAtomConditions.add(condition);
|
||||
myConditions.add(condition.getValue());
|
||||
}
|
||||
}
|
||||
|
||||
public boolean hasCondition(@NotNull Object condition) {
|
||||
return myConditions.contains(condition);
|
||||
}
|
||||
|
||||
public void removeCondition(@NotNull Object condition) {
|
||||
if (!myConditions.remove(condition)) {
|
||||
return;
|
||||
}
|
||||
for (Iterator<ArrangementAtomMatchCondition> iterator = myAtomConditions.iterator(); iterator.hasNext(); ) {
|
||||
ArrangementAtomMatchCondition c = iterator.next();
|
||||
if (c.getValue().equals(condition)) {
|
||||
iterator.remove();
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void copyConditionsFrom(@NotNull ArrangementRuleInfo info) {
|
||||
clearConditions();
|
||||
myConditions.addAll(info.myConditions);
|
||||
myAtomConditions.addAll(info.myAtomConditions);
|
||||
myNamePattern = info.myNamePattern;
|
||||
}
|
||||
|
||||
public void clear() {
|
||||
clearConditions();
|
||||
myOrderType = ArrangementMatchRule.DEFAULT_ORDER_TYPE;
|
||||
myNamePattern = null;
|
||||
}
|
||||
|
||||
public void clearConditions() {
|
||||
myConditions.clear();
|
||||
myAtomConditions.clear();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public StdArrangementMatchRule buildRule() {
|
||||
ArrangementMatchCondition condition = buildCondition();
|
||||
if (condition == null) {
|
||||
return null;
|
||||
}
|
||||
return new StdArrangementMatchRule(new StdArrangementEntryMatcher(condition), myOrderType);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public ArrangementMatchCondition buildCondition() {
|
||||
if (myAtomConditions.isEmpty()) {
|
||||
return myNamePattern == null ? null : new ArrangementAtomMatchCondition(ArrangementSettingType.NAME, myNamePattern);
|
||||
}
|
||||
else if (myAtomConditions.size() == 1 && myNamePattern == null) {
|
||||
return myAtomConditions.iterator().next();
|
||||
}
|
||||
else {
|
||||
ArrangementCompositeMatchCondition result = new ArrangementCompositeMatchCondition(myAtomConditions);
|
||||
if (myNamePattern != null) {
|
||||
result.addOperand(new ArrangementAtomMatchCondition(ArrangementSettingType.NAME, myNamePattern));
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -51,5 +51,5 @@ public interface ArrangementSettingsSerializer {
|
||||
* @param settings settings to serialize
|
||||
* @param holder element to hold serialized settings
|
||||
*/
|
||||
void serialize(ArrangementSettings settings, @NotNull Element holder);
|
||||
void serialize(@NotNull ArrangementSettings settings, @NotNull Element holder);
|
||||
}
|
||||
|
||||
+122
-22
@@ -15,18 +15,27 @@
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.lang.Language;
|
||||
import com.intellij.openapi.editor.Document;
|
||||
import com.intellij.openapi.extensions.Extensions;
|
||||
import com.intellij.openapi.util.Ref;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.*;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.*;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementCompositeMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchConditionVisitor;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.*;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jdom.Element;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Queue;
|
||||
import java.util.Set;
|
||||
import java.util.Stack;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
@@ -135,22 +144,29 @@ public class ArrangementUtil {
|
||||
}
|
||||
//endregion
|
||||
|
||||
@NotNull
|
||||
public static ArrangementSettingType parseType(@NotNull Object condition) throws IllegalArgumentException {
|
||||
if (condition instanceof ArrangementEntryType) {
|
||||
return ArrangementSettingType.TYPE;
|
||||
}
|
||||
else if (condition instanceof ArrangementModifier) {
|
||||
return ArrangementSettingType.MODIFIER;
|
||||
}
|
||||
else if (condition instanceof String) {
|
||||
return ArrangementSettingType.NAME;
|
||||
}
|
||||
else {
|
||||
throw new IllegalArgumentException(String.format(
|
||||
"Can't parse type for the given condition of class '%s': %s", condition.getClass(), condition
|
||||
));
|
||||
}
|
||||
@Nullable
|
||||
public static ArrangementSettingsToken parseType(@NotNull ArrangementMatchCondition condition) throws IllegalArgumentException {
|
||||
final Ref<ArrangementSettingsToken> result = new Ref<ArrangementSettingsToken>();
|
||||
condition.invite(new ArrangementMatchConditionVisitor() {
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementAtomMatchCondition condition) {
|
||||
if (StdArrangementTokens.EntryType.is(condition.getType())) {
|
||||
result.set(condition.getType());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementCompositeMatchCondition condition) {
|
||||
for (ArrangementMatchCondition c : condition.getOperands()) {
|
||||
c.invite(this);
|
||||
if (result.get() != null) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
return result.get();
|
||||
}
|
||||
|
||||
public static <T> Set<T> flatten(@NotNull Iterable<? extends Iterable<T>> data) {
|
||||
@@ -164,12 +180,12 @@ public class ArrangementUtil {
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static ArrangementRuleInfo extractConditions(@NotNull ArrangementMatchCondition condition) {
|
||||
final ArrangementRuleInfo result = new ArrangementRuleInfo();
|
||||
public static Set<ArrangementSettingsToken> extractTokens(@NotNull ArrangementMatchCondition condition) {
|
||||
final Set<ArrangementSettingsToken> result = ContainerUtilRt.newHashSet();
|
||||
condition.invite(new ArrangementMatchConditionVisitor() {
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementAtomMatchCondition condition) {
|
||||
result.addAtomCondition(condition);
|
||||
result.add(condition.getType());
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -181,4 +197,88 @@ public class ArrangementUtil {
|
||||
});
|
||||
return result;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static ArrangementEntryMatcher buildMatcher(@NotNull ArrangementMatchCondition condition) {
|
||||
final Ref<ArrangementEntryMatcher> result = new Ref<ArrangementEntryMatcher>();
|
||||
final Stack<CompositeArrangementEntryMatcher> composites = new Stack<CompositeArrangementEntryMatcher>();
|
||||
ArrangementMatchConditionVisitor visitor = new ArrangementMatchConditionVisitor() {
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementAtomMatchCondition condition) {
|
||||
ArrangementEntryMatcher matcher = buildMatcher(condition);
|
||||
if (matcher == null) {
|
||||
return;
|
||||
}
|
||||
if (composites.isEmpty()) {
|
||||
result.set(matcher);
|
||||
}
|
||||
else {
|
||||
composites.peek().addMatcher(matcher);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementCompositeMatchCondition condition) {
|
||||
composites.push(new CompositeArrangementEntryMatcher());
|
||||
try {
|
||||
for (ArrangementMatchCondition operand : condition.getOperands()) {
|
||||
operand.invite(this);
|
||||
}
|
||||
}
|
||||
finally {
|
||||
CompositeArrangementEntryMatcher matcher = composites.pop();
|
||||
if (composites.isEmpty()) {
|
||||
result.set(matcher);
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
condition.invite(visitor);
|
||||
return result.get();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static ArrangementEntryMatcher buildMatcher(@NotNull ArrangementAtomMatchCondition condition) {
|
||||
if (StdArrangementTokens.EntryType.is(condition.getType())) {
|
||||
return new ByTypeArrangementEntryMatcher(condition.getType());
|
||||
}
|
||||
else if (StdArrangementTokens.Modifier.is(condition.getType())) {
|
||||
return new ByModifierArrangementEntryMatcher(condition.getType());
|
||||
}
|
||||
else if (StdArrangementTokens.General.NAME.equals(condition.getType())) {
|
||||
return new ByNameArrangementEntryMatcher(condition.getValue().toString());
|
||||
}
|
||||
else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
// TODO den add doc
|
||||
@NotNull
|
||||
public static ArrangementUiComponent buildUiComponent(@NotNull StdArrangementTokenUiRole role,
|
||||
@NotNull List<ArrangementSettingsToken> tokens,
|
||||
@NotNull ArrangementColorsProvider colorsProvider,
|
||||
@NotNull ArrangementStandardSettingsManager settingsManager)
|
||||
throws IllegalArgumentException
|
||||
{
|
||||
for (ArrangementUiComponent.Factory factory : Extensions.getExtensions(ArrangementUiComponent.Factory.EP_NAME)) {
|
||||
ArrangementUiComponent result = factory.build(role, tokens, colorsProvider, settingsManager);
|
||||
if (result != null) {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
throw new IllegalArgumentException("Unsupported UI token role " + role);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static List<CompositeArrangementSettingsToken> flatten(@NotNull CompositeArrangementSettingsToken base) {
|
||||
List<CompositeArrangementSettingsToken> result = ContainerUtilRt.newArrayList();
|
||||
Queue<CompositeArrangementSettingsToken> toProcess = ContainerUtilRt.newLinkedList(base);
|
||||
while (!toProcess.isEmpty()) {
|
||||
CompositeArrangementSettingsToken token = toProcess.remove();
|
||||
result.add(token);
|
||||
toProcess.addAll(token.getChildren());
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
+64
-22
@@ -17,12 +17,13 @@ package com.intellij.psi.codeStyle.arrangement;
|
||||
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.DefaultArrangementEntryMatcherSerializer;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementEntryMatcher;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementSettings;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens;
|
||||
import org.jdom.Element;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -31,14 +32,17 @@ import org.jetbrains.annotations.Nullable;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* {@link ArrangementSettingsSerializer} which knows how to handle {@link StdArrangementSettings built-in arrangement tokens}
|
||||
* and {@link Mixin can be used as a base for custom serializer implementation}.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 7/18/12 10:37 AM
|
||||
*/
|
||||
public class DefaultArrangementSettingsSerializer implements ArrangementSettingsSerializer {
|
||||
|
||||
public static final ArrangementSettingsSerializer INSTANCE = new DefaultArrangementSettingsSerializer();
|
||||
private static final Logger LOG =
|
||||
Logger.getInstance("#" + DefaultArrangementSettingsSerializer.class.getName());
|
||||
public static final ArrangementSettingsSerializer INSTANCE = new DefaultArrangementSettingsSerializer(Mixin.NULL);
|
||||
|
||||
private static final Logger LOG = Logger.getInstance("#" + DefaultArrangementSettingsSerializer.class.getName());
|
||||
|
||||
@NotNull @NonNls private static final String GROUPS_ELEMENT_NAME = "groups";
|
||||
@NotNull @NonNls private static final String GROUP_ELEMENT_NAME = "group";
|
||||
@@ -48,10 +52,16 @@ public class DefaultArrangementSettingsSerializer implements ArrangementSettings
|
||||
@NotNull @NonNls private static final String MATCHER_ELEMENT_NAME = "match";
|
||||
@NotNull @NonNls private static final String ORDER_TYPE_ELEMENT_NAME = "order";
|
||||
|
||||
@NotNull private final DefaultArrangementEntryMatcherSerializer myMatcherSerializer = new DefaultArrangementEntryMatcherSerializer();
|
||||
@NotNull private final DefaultArrangementEntryMatcherSerializer myMatcherSerializer;
|
||||
@NotNull private final Mixin myMixin;
|
||||
|
||||
public DefaultArrangementSettingsSerializer(@NotNull Mixin mixin) {
|
||||
myMixin = mixin;
|
||||
myMatcherSerializer = new DefaultArrangementEntryMatcherSerializer(mixin);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void serialize(ArrangementSettings s, @NotNull Element holder) {
|
||||
public void serialize(@NotNull ArrangementSettings s, @NotNull Element holder) {
|
||||
if (!(s instanceof StdArrangementSettings)) {
|
||||
return;
|
||||
}
|
||||
@@ -65,8 +75,8 @@ public class DefaultArrangementSettingsSerializer implements ArrangementSettings
|
||||
for (ArrangementGroupingRule group : groupings) {
|
||||
Element groupElement = new Element(GROUP_ELEMENT_NAME);
|
||||
groupingsElement.addContent(groupElement);
|
||||
groupElement.addContent(new Element(TYPE_ELEMENT_NAME).setText(group.getGroupingType().toString()));
|
||||
groupElement.addContent(new Element(ORDER_TYPE_ELEMENT_NAME).setText(group.getOrderType().toString()));
|
||||
groupElement.addContent(new Element(TYPE_ELEMENT_NAME).setText(group.getGroupingType().getId()));
|
||||
groupElement.addContent(new Element(ORDER_TYPE_ELEMENT_NAME).setText(group.getOrderType().getId()));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -88,15 +98,29 @@ public class DefaultArrangementSettingsSerializer implements ArrangementSettings
|
||||
if (groups != null) {
|
||||
for (Object group : groups.getChildren(GROUP_ELEMENT_NAME)) {
|
||||
Element groupElement = (Element)group;
|
||||
try {
|
||||
ArrangementGroupingType type = ArrangementGroupingType.valueOf(groupElement.getChildText(TYPE_ELEMENT_NAME));
|
||||
ArrangementEntryOrderType orderType = ArrangementEntryOrderType.valueOf(groupElement.getChildText(ORDER_TYPE_ELEMENT_NAME));
|
||||
ArrangementGroupingRule groupingRule = new ArrangementGroupingRule(type, orderType);
|
||||
result.addGrouping(groupingRule);
|
||||
|
||||
// Grouping type.
|
||||
String groupingTypeId = groupElement.getChildText(TYPE_ELEMENT_NAME);
|
||||
ArrangementSettingsToken groupingType = StdArrangementTokens.byId(groupingTypeId);
|
||||
if (groupingType == null) {
|
||||
groupingType = myMixin.deserializeToken(groupingTypeId);
|
||||
}
|
||||
catch (Exception e) {
|
||||
LOG.warn(String.format("Can't deserialize grouping rule '%s'", groupElement.getText()), e);
|
||||
if (groupingType == null) {
|
||||
LOG.warn(String.format("Can't deserialize grouping type token by id '%s'", groupingTypeId));
|
||||
continue;
|
||||
}
|
||||
|
||||
// Order type.
|
||||
String orderTypeId = groupElement.getChildText(ORDER_TYPE_ELEMENT_NAME);
|
||||
ArrangementSettingsToken orderType = StdArrangementTokens.byId(orderTypeId);
|
||||
if (orderType == null) {
|
||||
orderType = myMixin.deserializeToken(orderTypeId);
|
||||
}
|
||||
if (orderType == null) {
|
||||
LOG.warn(String.format("Can't deserialize grouping order type token by id '%s'", orderTypeId));
|
||||
continue;
|
||||
}
|
||||
result.addGrouping(new ArrangementGroupingRule(groupingType, orderType));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -122,15 +146,21 @@ public class DefaultArrangementSettingsSerializer implements ArrangementSettings
|
||||
}
|
||||
|
||||
Element orderTypeElement = ruleElement.getChild(ORDER_TYPE_ELEMENT_NAME);
|
||||
ArrangementEntryOrderType orderType = ArrangementMatchRule.DEFAULT_ORDER_TYPE;
|
||||
ArrangementSettingsToken orderType = null;
|
||||
if (orderTypeElement != null) {
|
||||
try {
|
||||
orderType = ArrangementEntryOrderType.valueOf(orderTypeElement.getText());
|
||||
String orderTypeId = orderTypeElement.getText();
|
||||
orderType = StdArrangementTokens.byId(orderTypeId);
|
||||
if (orderType == null) {
|
||||
orderType = myMixin.deserializeToken(orderTypeId);
|
||||
}
|
||||
catch (Exception e) {
|
||||
LOG.warn(String.format("Can't deserialize matching rule order type for '%s'", ruleElement.getText()), e);
|
||||
if (orderType == null) {
|
||||
LOG.warn(String.format("Can't deserialize matching rule order type for id '%s'. Falling back to default (%s)",
|
||||
orderTypeId, ArrangementMatchRule.DEFAULT_ORDER_TYPE.getId()));
|
||||
}
|
||||
}
|
||||
if (orderType == null) {
|
||||
orderType = ArrangementMatchRule.DEFAULT_ORDER_TYPE;
|
||||
}
|
||||
result.addRule(new StdArrangementMatchRule(matcher, orderType));
|
||||
}
|
||||
}
|
||||
@@ -148,8 +178,20 @@ public class DefaultArrangementSettingsSerializer implements ArrangementSettings
|
||||
Element result = new Element(RULE_ELEMENT_NAME);
|
||||
result.addContent(new Element(MATCHER_ELEMENT_NAME).addContent(matcherElement));
|
||||
if (rule.getOrderType() != ArrangementMatchRule.DEFAULT_ORDER_TYPE) {
|
||||
result.addContent(new Element(ORDER_TYPE_ELEMENT_NAME).setText(rule.getOrderType().toString()));
|
||||
result.addContent(new Element(ORDER_TYPE_ELEMENT_NAME).setText(rule.getOrderType().getId()));
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
public interface Mixin {
|
||||
|
||||
Mixin NULL = new Mixin() {
|
||||
@Nullable
|
||||
@Override
|
||||
public ArrangementSettingsToken deserializeToken(@NotNull String id) { return null; }
|
||||
};
|
||||
|
||||
@Nullable
|
||||
ArrangementSettingsToken deserializeToken(@NotNull String id);
|
||||
}
|
||||
}
|
||||
|
||||
+2
-3
@@ -15,8 +15,7 @@
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.Set;
|
||||
@@ -28,5 +27,5 @@ import java.util.Set;
|
||||
public interface ModifierAwareArrangementEntry extends ArrangementEntry {
|
||||
|
||||
@NotNull
|
||||
Set<ArrangementModifier> getModifiers();
|
||||
Set<ArrangementSettingsToken> getModifiers();
|
||||
}
|
||||
|
||||
@@ -21,7 +21,7 @@ import com.intellij.openapi.util.Pair;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.codeStyle.CodeStyleSettings;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@@ -49,7 +49,7 @@ public interface Rearranger<E extends ArrangementEntry> {
|
||||
*
|
||||
* @param element element to wrap into format eligible for further processing by arrangement engine
|
||||
* @param settings arrangement settings to use. The primary idea is to make the rearranger aware about
|
||||
* {@link ArrangementGroupingType grouping rules} (if any). E.g. it's not worth to process java method bodies
|
||||
* {@link StdArrangementTokens.Grouping grouping rules} (if any). E.g. it's not worth to process java method bodies
|
||||
* in order to build method dependency graph if no such grouping rule is defined
|
||||
* @return arrangement entry for the given element if it's possible to perform the mapping and list of arrangement entries
|
||||
* available at the given context plus newly created entry for the given element;
|
||||
@@ -69,7 +69,7 @@ public interface Rearranger<E extends ArrangementEntry> {
|
||||
* @param document document which corresponds to the target PSI tree
|
||||
* @param ranges target offsets ranges to use for filtering given root's children
|
||||
* @param settings arrangement settings to use. The primary idea is to make the rearranger aware about
|
||||
* {@link ArrangementGroupingType grouping rules} (if any). E.g. it's not worth to process java method bodies
|
||||
* {@link StdArrangementTokens.Grouping grouping rules} (if any). E.g. it's not worth to process java method bodies
|
||||
* in order to build method dependency graph if no such grouping rule is defined
|
||||
* @return given root's children which are subject for further rearrangement
|
||||
*/
|
||||
|
||||
+2
-3
@@ -15,9 +15,8 @@
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.Set;
|
||||
|
||||
@@ -32,5 +31,5 @@ import java.util.Set;
|
||||
public interface TypeAwareArrangementEntry extends ArrangementEntry {
|
||||
|
||||
@NotNull
|
||||
Set<ArrangementEntryType> getTypes();
|
||||
Set<ArrangementSettingsToken> getTypes();
|
||||
}
|
||||
|
||||
+10
-9
@@ -15,7 +15,8 @@
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement.group;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
/**
|
||||
@@ -28,25 +29,25 @@ import org.jetbrains.annotations.NotNull;
|
||||
*/
|
||||
public class ArrangementGroupingRule {
|
||||
|
||||
@NotNull private final ArrangementGroupingType myGroupingType;
|
||||
@NotNull private final ArrangementEntryOrderType myOrderType;
|
||||
@NotNull private final ArrangementSettingsToken myGroupingType;
|
||||
@NotNull private final ArrangementSettingsToken myOrderType;
|
||||
|
||||
public ArrangementGroupingRule(@NotNull ArrangementGroupingType groupingType) {
|
||||
this(groupingType, ArrangementEntryOrderType.KEEP);
|
||||
public ArrangementGroupingRule(@NotNull ArrangementSettingsToken groupingType) {
|
||||
this(groupingType, StdArrangementTokens.Order.KEEP);
|
||||
}
|
||||
|
||||
public ArrangementGroupingRule(@NotNull ArrangementGroupingType groupingType, @NotNull ArrangementEntryOrderType orderType) {
|
||||
|
||||
public ArrangementGroupingRule(@NotNull ArrangementSettingsToken groupingType, @NotNull ArrangementSettingsToken orderType) {
|
||||
myGroupingType = groupingType;
|
||||
myOrderType = orderType;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public ArrangementGroupingType getGroupingType() {
|
||||
public ArrangementSettingsToken getGroupingType() {
|
||||
return myGroupingType;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public ArrangementEntryOrderType getOrderType() {
|
||||
public ArrangementSettingsToken getOrderType() {
|
||||
return myOrderType;
|
||||
}
|
||||
|
||||
|
||||
-33
@@ -1,33 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.psi.codeStyle.arrangement.group;
|
||||
|
||||
/**
|
||||
* Enumerates available grouping types.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 9/17/12 11:47 AM
|
||||
*/
|
||||
public enum ArrangementGroupingType {
|
||||
|
||||
GETTERS_AND_SETTERS,
|
||||
|
||||
OVERRIDDEN_METHODS,
|
||||
|
||||
DEPENDENT_METHODS,
|
||||
|
||||
GROUP_PROPERTY_FIELD_WITH_GETTER_SETTER
|
||||
}
|
||||
-37
@@ -1,37 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.psi.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementEntry;
|
||||
|
||||
/**
|
||||
* Enumerates all possible {@link ArrangementEntry entry} types.
|
||||
* <p/>
|
||||
* This enum is expected to be populated every time new entry type is introduced.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 7/17/12 11:14 AM
|
||||
*/
|
||||
public enum ArrangementEntryType {
|
||||
|
||||
CLASS, ANONYMOUS_CLASS, FIELD, CONSTRUCTOR, METHOD, ENUM, INTERFACE,
|
||||
|
||||
CONST, VAR, PROPERTY, EVENT_HANDLER, STATIC_INIT,
|
||||
|
||||
NAMESPACE, TRAIT,
|
||||
|
||||
XML_TAG, XML_ATTRIBUTE
|
||||
}
|
||||
+8
-7
@@ -15,7 +15,8 @@
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
/**
|
||||
@@ -30,18 +31,18 @@ import org.jetbrains.annotations.NotNull;
|
||||
*/
|
||||
public class ArrangementMatchRule {
|
||||
|
||||
@NotNull public static final ArrangementEntryOrderType DEFAULT_ORDER_TYPE = ArrangementEntryOrderType.KEEP;
|
||||
@NotNull public static final ArrangementSettingsToken DEFAULT_ORDER_TYPE = StdArrangementTokens.Order.KEEP;
|
||||
|
||||
@NotNull private final ArrangementEntryMatcher myMatcher;
|
||||
@NotNull private final ArrangementEntryOrderType myOrderType;
|
||||
@NotNull private final ArrangementEntryMatcher myMatcher;
|
||||
@NotNull private final ArrangementSettingsToken myOrderType;
|
||||
|
||||
public ArrangementMatchRule(@NotNull ArrangementEntryMatcher matcher) {
|
||||
this(matcher, DEFAULT_ORDER_TYPE);
|
||||
}
|
||||
|
||||
public ArrangementMatchRule(@NotNull ArrangementEntryMatcher matcher, @NotNull ArrangementEntryOrderType type) {
|
||||
public ArrangementMatchRule(@NotNull ArrangementEntryMatcher matcher, @NotNull ArrangementSettingsToken orderType) {
|
||||
myMatcher = matcher;
|
||||
myOrderType = type;
|
||||
myOrderType = orderType;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@@ -50,7 +51,7 @@ public class ArrangementMatchRule {
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public ArrangementEntryOrderType getOrderType() {
|
||||
public ArrangementSettingsToken getOrderType() {
|
||||
return myOrderType;
|
||||
}
|
||||
|
||||
|
||||
-31
@@ -1,31 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.psi.codeStyle.arrangement.match;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 7/17/12 8:54 PM
|
||||
*/
|
||||
public enum ArrangementModifier {
|
||||
|
||||
//region Visibility
|
||||
PUBLIC, PROTECTED, PRIVATE, PACKAGE_PRIVATE,
|
||||
//endregion
|
||||
|
||||
STATIC, FINAL, TRANSIENT, VOLATILE, SYNCHRONIZED, ABSTRACT,
|
||||
|
||||
OVERRIDE // e.g. ActionScript keyword
|
||||
}
|
||||
+9
-4
@@ -17,10 +17,11 @@ package com.intellij.psi.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.ModifierAwareArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.EnumSet;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
@@ -29,12 +30,16 @@ import java.util.Set;
|
||||
*/
|
||||
public class ByModifierArrangementEntryMatcher implements ArrangementEntryMatcher {
|
||||
|
||||
@NotNull private final Set<ArrangementModifier> myModifiers = EnumSet.noneOf(ArrangementModifier.class);
|
||||
@NotNull private final Set<ArrangementSettingsToken> myModifiers = ContainerUtilRt.newHashSet();
|
||||
|
||||
public ByModifierArrangementEntryMatcher(@NotNull Collection<ArrangementModifier> interestedModifiers) {
|
||||
myModifiers.addAll(interestedModifiers);
|
||||
public ByModifierArrangementEntryMatcher(@NotNull ArrangementSettingsToken interestedModifier) {
|
||||
myModifiers.add(interestedModifier);
|
||||
}
|
||||
|
||||
public ByModifierArrangementEntryMatcher(@NotNull Collection<ArrangementSettingsToken> interestedModifiers) {
|
||||
myModifiers.addAll(interestedModifiers);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isMatched(@NotNull ArrangementEntry entry) {
|
||||
if (entry instanceof ModifierAwareArrangementEntry) {
|
||||
|
||||
+8
-8
@@ -17,15 +17,15 @@ package com.intellij.psi.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.TypeAwareArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.EnumSet;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* Filters {@link ArrangementEntry entries} by {@link TypeAwareArrangementEntry#getType() their types}.
|
||||
* Filters {@link ArrangementEntry entries} by {@link TypeAwareArrangementEntry#getTypes() their types}.
|
||||
* <p/>
|
||||
* <b>Note:</b> type-unaware entry will not be matched by the current rule.
|
||||
* <p/>
|
||||
@@ -36,13 +36,13 @@ import java.util.Set;
|
||||
*/
|
||||
public class ByTypeArrangementEntryMatcher implements ArrangementEntryMatcher {
|
||||
|
||||
@NotNull private final Set<ArrangementEntryType> myTypes = EnumSet.noneOf(ArrangementEntryType.class);
|
||||
@NotNull private final Set<ArrangementSettingsToken> myTypes = ContainerUtilRt.newHashSet();
|
||||
|
||||
public ByTypeArrangementEntryMatcher(@NotNull ArrangementEntryType... interestedTypes) {
|
||||
this(Arrays.asList(interestedTypes));
|
||||
public ByTypeArrangementEntryMatcher(@NotNull ArrangementSettingsToken interestedType) {
|
||||
myTypes.add(interestedType);
|
||||
}
|
||||
|
||||
public ByTypeArrangementEntryMatcher(@NotNull Collection<ArrangementEntryType> interestedTypes) {
|
||||
public ByTypeArrangementEntryMatcher(@NotNull Collection<ArrangementSettingsToken> interestedTypes) {
|
||||
myTypes.addAll(interestedTypes);
|
||||
}
|
||||
|
||||
@@ -55,7 +55,7 @@ public class ByTypeArrangementEntryMatcher implements ArrangementEntryMatcher {
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public Set<ArrangementEntryType> getTypes() {
|
||||
public Set<ArrangementSettingsToken> getTypes() {
|
||||
return myTypes;
|
||||
}
|
||||
|
||||
|
||||
+60
-62
@@ -17,18 +17,21 @@ package com.intellij.psi.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.*;
|
||||
import com.intellij.psi.codeStyle.arrangement.DefaultArrangementSettingsSerializer;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementCompositeMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchConditionVisitor;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import com.intellij.util.containers.HashSet;
|
||||
import gnu.trove.TObjectIntHashMap;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jdom.Element;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Comparator;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
@@ -38,18 +41,6 @@ public class DefaultArrangementEntryMatcherSerializer {
|
||||
|
||||
private static final Comparator<ArrangementMatchCondition> CONDITION_COMPARATOR = new Comparator<ArrangementMatchCondition>() {
|
||||
|
||||
private final TObjectIntHashMap<Object> WEIGHTS = new TObjectIntHashMap<Object>();
|
||||
|
||||
{
|
||||
int weight = 0;
|
||||
for (ArrangementEntryType entryType : ArrangementEntryType.values()) {
|
||||
WEIGHTS.put(entryType, weight++);
|
||||
}
|
||||
for (ArrangementModifier modifier : ArrangementModifier.values()) {
|
||||
WEIGHTS.put(modifier, weight++);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public int compare(ArrangementMatchCondition c1, ArrangementMatchCondition c2) {
|
||||
boolean isAtom1 = c1 instanceof ArrangementAtomMatchCondition;
|
||||
@@ -57,30 +48,28 @@ public class DefaultArrangementEntryMatcherSerializer {
|
||||
if (isAtom1 ^ isAtom2) {
|
||||
return isAtom1 ? 1 : -1; // Composite conditions before atom conditions.
|
||||
}
|
||||
else if (!isAtom1 && !isAtom2) {
|
||||
else if (!isAtom1) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
ArrangementAtomMatchCondition atom1 = (ArrangementAtomMatchCondition)c1;
|
||||
ArrangementAtomMatchCondition atom2 = (ArrangementAtomMatchCondition)c2;
|
||||
if (WEIGHTS.containsKey(atom1.getValue()) && WEIGHTS.containsKey(atom2.getValue())) {
|
||||
return WEIGHTS.get(atom1.getValue()) - WEIGHTS.get(atom2.getValue());
|
||||
}
|
||||
else {
|
||||
return 0;
|
||||
int cmp = atom1.getType().compareTo(atom2.getType());
|
||||
if (cmp == 0) {
|
||||
cmp = atom1.getValue().toString().compareTo(atom2.getValue().toString());
|
||||
}
|
||||
return cmp;
|
||||
}
|
||||
};
|
||||
|
||||
private static final Logger LOG = Logger.getInstance("#" + DefaultArrangementEntryMatcherSerializer.class.getName());
|
||||
@NotNull private static final Logger LOG = Logger.getInstance("#" + DefaultArrangementEntryMatcherSerializer.class.getName());
|
||||
|
||||
@NotNull private static final String COMPOSITE_CONDITION_NAME = "AND";
|
||||
private static final Set<String> ATOM_SETTINGS_TYPES = new HashSet<String>();
|
||||
|
||||
static {
|
||||
for (ArrangementSettingType type : ArrangementSettingType.values()) {
|
||||
ATOM_SETTINGS_TYPES.add(type.toString());
|
||||
}
|
||||
private final DefaultArrangementSettingsSerializer.Mixin myMixin;
|
||||
|
||||
public DefaultArrangementEntryMatcherSerializer(DefaultArrangementSettingsSerializer.Mixin mixin) {
|
||||
myMixin = mixin;
|
||||
}
|
||||
|
||||
@SuppressWarnings("MethodMayBeStatic")
|
||||
@@ -111,22 +100,9 @@ public class DefaultArrangementEntryMatcherSerializer {
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private static ArrangementMatchCondition deserializeCondition(@NotNull Element matcherElement) {
|
||||
private ArrangementMatchCondition deserializeCondition(@NotNull Element matcherElement) {
|
||||
String name = matcherElement.getName();
|
||||
if (!COMPOSITE_CONDITION_NAME.equals(name)) {
|
||||
if (ATOM_SETTINGS_TYPES.contains(name)) {
|
||||
return deserializeAtomCondition(matcherElement);
|
||||
}
|
||||
else {
|
||||
LOG.warn(String.format(
|
||||
"Can't deserialize an arrangement entry matcher from matchElement with name '%s'. Reason: only the following elements"
|
||||
+ "are supported: %s and %s",
|
||||
name, COMPOSITE_CONDITION_NAME, ATOM_SETTINGS_TYPES
|
||||
));
|
||||
return null;
|
||||
}
|
||||
}
|
||||
else {
|
||||
if (COMPOSITE_CONDITION_NAME.equals(name)) {
|
||||
ArrangementCompositeMatchCondition composite = new ArrangementCompositeMatchCondition();
|
||||
for (Object child : matcherElement.getChildren()) {
|
||||
ArrangementMatchCondition deserialised = deserializeCondition((Element)child);
|
||||
@@ -136,24 +112,47 @@ public class DefaultArrangementEntryMatcherSerializer {
|
||||
}
|
||||
return composite;
|
||||
}
|
||||
else {
|
||||
return deserializeAtomCondition(matcherElement);
|
||||
}
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private static ArrangementMatchCondition deserializeAtomCondition(@NotNull Element matcherElement) {
|
||||
ArrangementSettingType settingType = ArrangementSettingType.valueOf(matcherElement.getName());
|
||||
Object value;
|
||||
switch (settingType) {
|
||||
case TYPE: value = ArrangementEntryType.valueOf(matcherElement.getText()); break;
|
||||
case MODIFIER: value = ArrangementModifier.valueOf(matcherElement.getText()); break;
|
||||
case NAME: value = StringUtil.unescapeStringCharacters(matcherElement.getText()); break;
|
||||
default:
|
||||
LOG.warn(String.format(
|
||||
"Can't deserialize an arrangement entry matcher from element of type '%s' with text '%s'",
|
||||
settingType, matcherElement.getText()
|
||||
));
|
||||
private ArrangementMatchCondition deserializeAtomCondition(@NotNull Element matcherElement) {
|
||||
String id = matcherElement.getName();
|
||||
ArrangementSettingsToken token = StdArrangementTokens.byId(id);
|
||||
boolean processInnerText = true;
|
||||
|
||||
if (token != null
|
||||
&& (StdArrangementTokens.General.TYPE.equals(token) || StdArrangementTokens.General.MODIFIER.equals(token)))
|
||||
{
|
||||
// Backward compatibility with old arrangement settings format.
|
||||
id = matcherElement.getText();
|
||||
if (StringUtil.isEmpty(id)) {
|
||||
LOG.warn("Can't deserialize match condition at legacy format");
|
||||
return null;
|
||||
}
|
||||
token = StdArrangementTokens.byId(id);
|
||||
processInnerText = false;
|
||||
}
|
||||
return new ArrangementAtomMatchCondition(settingType, value);
|
||||
|
||||
if (token == null) {
|
||||
token = myMixin.deserializeToken(id);
|
||||
}
|
||||
if (token == null) {
|
||||
LOG.warn(String.format("Can't deserialize match condition with id '%s'", id));
|
||||
return null;
|
||||
}
|
||||
|
||||
Object value = token;
|
||||
String text = matcherElement.getText();
|
||||
if (text != null && processInnerText) {
|
||||
text = StringUtil.unescapeStringCharacters(matcherElement.getText());
|
||||
if (!StringUtil.isEmpty(text)) {
|
||||
value = text;
|
||||
}
|
||||
}
|
||||
return new ArrangementAtomMatchCondition(token, value);
|
||||
}
|
||||
|
||||
private static class MySerializationVisitor implements ArrangementMatchConditionVisitor {
|
||||
@@ -163,11 +162,10 @@ public class DefaultArrangementEntryMatcherSerializer {
|
||||
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementAtomMatchCondition condition) {
|
||||
String content = condition.getValue().toString();
|
||||
if (condition.getType() == ArrangementSettingType.NAME) {
|
||||
content = StringUtil.escapeStringCharacters(content);
|
||||
final Element element = new Element(condition.getType().getId());
|
||||
if (StdArrangementTokens.General.NAME.equals(condition.getType())) {
|
||||
element.setText(StringUtil.escapeStringCharacters(condition.getValue().toString()));
|
||||
}
|
||||
Element element = new Element(condition.getType().toString()).setText(content);
|
||||
register(element);
|
||||
}
|
||||
|
||||
@@ -176,7 +174,7 @@ public class DefaultArrangementEntryMatcherSerializer {
|
||||
Element composite = new Element(COMPOSITE_CONDITION_NAME);
|
||||
register(composite);
|
||||
parent = composite;
|
||||
List<ArrangementMatchCondition> operands = new ArrayList<ArrangementMatchCondition>(condition.getOperands());
|
||||
List<ArrangementMatchCondition> operands = ContainerUtilRt.newArrayList(condition.getOperands());
|
||||
ContainerUtil.sort(operands, CONDITION_COMPARATOR);
|
||||
for (ArrangementMatchCondition c : operands) {
|
||||
c.invite(this);
|
||||
|
||||
+19
-15
@@ -17,17 +17,17 @@ package com.intellij.psi.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.*;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.EnumSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* {@link ArrangementEntryMatcher} which is based on standard match conditions like {@link ArrangementEntryType entry type}
|
||||
* or {@link ArrangementModifier modifier}.
|
||||
* {@link ArrangementEntryMatcher} which is based on standard match conditions in form of {@link ArrangementSettingsToken}.
|
||||
* <p/>
|
||||
* Implementations of this interface are expected to be thread-safe.
|
||||
*
|
||||
@@ -76,7 +76,7 @@ public class StdArrangementEntryMatcher implements ArrangementEntryMatcher {
|
||||
public String toString() {
|
||||
return myCondition.toString();
|
||||
}
|
||||
|
||||
|
||||
@NotNull
|
||||
private static ArrangementEntryMatcher doBuildMatcher(@NotNull ArrangementMatchCondition condition) {
|
||||
MyVisitor visitor = new MyVisitor();
|
||||
@@ -87,8 +87,8 @@ public class StdArrangementEntryMatcher implements ArrangementEntryMatcher {
|
||||
private static class MyVisitor implements ArrangementMatchConditionVisitor {
|
||||
|
||||
@NotNull private final List<ArrangementEntryMatcher> myMatchers = ContainerUtilRt.newArrayList();
|
||||
@NotNull private final Set<ArrangementEntryType> myTypes = EnumSet.noneOf(ArrangementEntryType.class);
|
||||
@NotNull private final Set<ArrangementModifier> myModifiers = EnumSet.noneOf(ArrangementModifier.class);
|
||||
@NotNull private final Set<ArrangementSettingsToken> myTypes = ContainerUtilRt.newHashSet();
|
||||
@NotNull private final Set<ArrangementSettingsToken> myModifiers = ContainerUtilRt.newHashSet();
|
||||
|
||||
@Nullable private String myNamePattern;
|
||||
|
||||
@@ -96,15 +96,19 @@ public class StdArrangementEntryMatcher implements ArrangementEntryMatcher {
|
||||
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementAtomMatchCondition condition) {
|
||||
switch (condition.getType()) {
|
||||
case TYPE:
|
||||
myTypes.add((ArrangementEntryType)condition.getValue());
|
||||
break;
|
||||
case MODIFIER:
|
||||
myModifiers.add((ArrangementModifier)condition.getValue());
|
||||
break;
|
||||
case NAME:
|
||||
myNamePattern = condition.getValue().toString();
|
||||
if (StdArrangementTokens.General.NAME.equals(condition.getType())) {
|
||||
myNamePattern = condition.getValue().toString();
|
||||
return;
|
||||
}
|
||||
Object v = condition.getValue();
|
||||
if (v instanceof ArrangementSettingsToken) {
|
||||
ArrangementSettingsToken token = (ArrangementSettingsToken)v;
|
||||
if (StdArrangementTokens.EntryType.is(token)) {
|
||||
myTypes.add(token);
|
||||
}
|
||||
else if (StdArrangementTokens.Modifier.is(token)) {
|
||||
myModifiers.add(token);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+3
-3
@@ -15,7 +15,7 @@
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
/**
|
||||
@@ -32,8 +32,8 @@ public class StdArrangementMatchRule extends ArrangementMatchRule implements Clo
|
||||
super(matcher);
|
||||
}
|
||||
|
||||
public StdArrangementMatchRule(@NotNull StdArrangementEntryMatcher matcher, @NotNull ArrangementEntryOrderType type) {
|
||||
super(matcher, type);
|
||||
public StdArrangementMatchRule(@NotNull StdArrangementEntryMatcher matcher, @NotNull ArrangementSettingsToken orderType) {
|
||||
super(matcher, orderType);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
|
||||
+17
-7
@@ -15,6 +15,7 @@
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement.model;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
/**
|
||||
@@ -27,18 +28,22 @@ import org.jetbrains.annotations.NotNull;
|
||||
*/
|
||||
public class ArrangementAtomMatchCondition implements ArrangementMatchCondition {
|
||||
|
||||
@NotNull private final ArrangementSettingType myType;
|
||||
@NotNull private final Object myValue;
|
||||
|
||||
@NotNull private final ArrangementSettingsToken myType;
|
||||
@NotNull private final Object myValue;
|
||||
|
||||
private boolean myInverted;
|
||||
|
||||
public ArrangementAtomMatchCondition(@NotNull ArrangementSettingType type, @NotNull Object value) {
|
||||
public ArrangementAtomMatchCondition(@NotNull ArrangementSettingsToken type) {
|
||||
this(type, type);
|
||||
}
|
||||
|
||||
public ArrangementAtomMatchCondition(@NotNull ArrangementSettingsToken type, @NotNull Object value) {
|
||||
myType = type;
|
||||
myValue = value;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public ArrangementSettingType getType() {
|
||||
public ArrangementSettingsToken getType() {
|
||||
return myType;
|
||||
}
|
||||
|
||||
@@ -78,7 +83,7 @@ public class ArrangementAtomMatchCondition implements ArrangementMatchCondition
|
||||
if (myInverted != setting.myInverted) {
|
||||
return false;
|
||||
}
|
||||
if (myType != setting.myType) {
|
||||
if (!myType.equals(setting.myType)) {
|
||||
return false;
|
||||
}
|
||||
if (!myValue.equals(setting.myValue)) {
|
||||
@@ -98,6 +103,11 @@ public class ArrangementAtomMatchCondition implements ArrangementMatchCondition
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return String.format("%s: %s%s", myType.toString().toLowerCase(), myInverted ? "not " : "", myValue.toString().toLowerCase());
|
||||
if (myType.equals(myValue)) {
|
||||
return String.format("%s%s", myInverted ? "not " : "", myType.getRepresentationValue());
|
||||
}
|
||||
else {
|
||||
return String.format("%s: %s%s", myType.getRepresentationValue(), myInverted ? "not " : "", myValue.toString().toLowerCase());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
-25
@@ -1,25 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.psi.codeStyle.arrangement.order;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 7/19/12 6:24 PM
|
||||
*/
|
||||
public enum ArrangementEntryOrderType {
|
||||
|
||||
KEEP, BY_NAME, DEPTH_FIRST, BREADTH_FIRST
|
||||
}
|
||||
-44
@@ -1,44 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.psi.codeStyle.arrangement.order;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryMatcher;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Defines a contract for a strategy that knows how to order {@link ArrangementEntry arrangement entries}
|
||||
* {@link ArrangementEntryMatcher#isMatched(ArrangementEntry) matched} against the same rule using particular
|
||||
* {@link ArrangementEntryOrderType order type}.
|
||||
* <p/>
|
||||
* Implementations of this interface are expected to provide correct {@link #equals(Object)} & {@link #hashCode()} implementations.
|
||||
* <p/>
|
||||
* Implementations of this interface are expected to be thread-safe.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 7/18/12 12:41 PM
|
||||
*/
|
||||
public interface ArrangementEntryOrderer {
|
||||
|
||||
/**
|
||||
* Asks to sort given entries matched against the current rule. Given list defines a default order to be used.
|
||||
*
|
||||
* @param entries entries matched against the current rule
|
||||
*/
|
||||
void order(@NotNull List<? extends ArrangementEntry> entries);
|
||||
}
|
||||
-63
@@ -1,63 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.psi.codeStyle.arrangement.order;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.NameAwareArrangementEntry;
|
||||
import gnu.trove.TObjectIntHashMap;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.Comparator;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 7/19/12 6:17 PM
|
||||
*/
|
||||
public class ByNameArrangementEntryOrderer implements ArrangementEntryOrderer {
|
||||
|
||||
@Override
|
||||
public void order(@NotNull List<? extends ArrangementEntry> entries) {
|
||||
TObjectIntHashMap<ArrangementEntry> weights = new TObjectIntHashMap<ArrangementEntry>();
|
||||
for (int i = 0; i < entries.size(); i++) {
|
||||
weights.put(entries.get(i), i);
|
||||
}
|
||||
Collections.sort(entries, new MyComparator(weights));
|
||||
}
|
||||
|
||||
private static class MyComparator implements Comparator<ArrangementEntry> {
|
||||
|
||||
@NotNull
|
||||
private final TObjectIntHashMap<ArrangementEntry> myFallbackWeights;
|
||||
|
||||
MyComparator(@NotNull TObjectIntHashMap<ArrangementEntry> weights) {
|
||||
myFallbackWeights = weights;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int compare(ArrangementEntry o1, ArrangementEntry o2) {
|
||||
if (o1 instanceof NameAwareArrangementEntry && o2 instanceof NameAwareArrangementEntry) {
|
||||
String name1 = ((NameAwareArrangementEntry)o1).getName();
|
||||
String name2 = ((NameAwareArrangementEntry)o1).getName();
|
||||
if (name1 != null && name2 != null) {
|
||||
return name1.compareTo(name2);
|
||||
}
|
||||
}
|
||||
return myFallbackWeights.get(o1) - myFallbackWeights.get(o2);
|
||||
}
|
||||
}
|
||||
}
|
||||
-64
@@ -1,64 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.psi.codeStyle.arrangement.settings;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* Strategy which hints on how arrangement match conditions should be grouped at the UI.
|
||||
* <p/>
|
||||
* Implementations of this interface are expected to be thread-safe.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/15/12 4:21 PM
|
||||
*/
|
||||
public interface ArrangementConditionsGrouper {
|
||||
|
||||
/**
|
||||
* Allows to answer if and how should be grouped given match conditions.
|
||||
* <p/>
|
||||
* Example: we have the following composite <code>'AND'</code> conditions below:
|
||||
* <pre>
|
||||
* <ul>
|
||||
* <li><code>'type: field; modifier: public; modifier: static; modifier: final'</code>;</li>
|
||||
* <li><code>'type: field; modifier: private; modifier: static; modifier: final'</code>;</li>
|
||||
* <li><code>'type: method; modifier: public; modifier: static;'</code>;</li>
|
||||
* <li><code>'type: method; modifier: private; modifier: static;'</code>;</li>
|
||||
* </ul>
|
||||
* </pre>
|
||||
* We might want to show it like below:
|
||||
* <pre>
|
||||
* field
|
||||
* |
|
||||
* |---public---static---final
|
||||
* |---private---static---final
|
||||
* method
|
||||
* |
|
||||
* |---public---static
|
||||
* |---private---static
|
||||
* </pre>
|
||||
* That means that we'll return a list with the single set which contains <code>'type: field'</code> and <code>'type: method'</code>
|
||||
* conditions.
|
||||
*
|
||||
* @return grouping rules to use
|
||||
*/
|
||||
@NotNull
|
||||
List<Set<ArrangementMatchCondition>> getGroupingConditions();
|
||||
}
|
||||
-93
@@ -1,93 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.psi.codeStyle.arrangement.settings;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.NameAwareArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.StdArrangementSettings;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* Strategy that defines what subset of standard arrangement settings can be used during defining arrangement settings
|
||||
* and how they are organised (e.g. single settings can't have more than one visibility modifier for java language).
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/6/12 2:26 PM
|
||||
*/
|
||||
public interface ArrangementStandardSettingsAware {
|
||||
|
||||
/**
|
||||
* @return settings to use by default, i.e. when a user hasn't been explicitly modified arrangement settings;
|
||||
* <code>null</code> as an indication that no default settings are available
|
||||
*/
|
||||
@Nullable
|
||||
StdArrangementSettings getDefaultSettings();
|
||||
|
||||
/**
|
||||
* @return <code>true</code> if name-based rules are supported by the current rearranger (it knows
|
||||
* about {@link NameAwareArrangementEntry});
|
||||
* <code>false</code> otherwise
|
||||
*/
|
||||
boolean isNameFilterSupported();
|
||||
|
||||
/**
|
||||
* Allows to answer if given entry type can be applied for the rule specified by the given settings node.
|
||||
*
|
||||
* @param type target entry type to check
|
||||
* @param current holds information about current rule
|
||||
* (<code>null</code> to indicate a query if given entry type is supported in general)
|
||||
* @return <code>true</code> if given entry type is supported; <code>false</code> otherwise
|
||||
*/
|
||||
boolean isEnabled(@NotNull ArrangementEntryType type, @Nullable ArrangementMatchCondition current);
|
||||
|
||||
/**
|
||||
* Allows to answer if given modifier can be applied for the rule specified by the given settings node.
|
||||
*
|
||||
* @param modifier target modifier to check
|
||||
* @param current holds information about current rule
|
||||
* (<code>null</code> to indicate a query if given modifier is supported in general)
|
||||
* @return <code>true</code> if given modifier is supported; <code>false</code> otherwise
|
||||
*/
|
||||
boolean isEnabled(@NotNull ArrangementModifier modifier, @Nullable ArrangementMatchCondition current);
|
||||
|
||||
|
||||
/**
|
||||
* Allows to answer if given grouping type (optionally with the given order type) can be used.
|
||||
*
|
||||
* @param groupingType target grouping type to check
|
||||
* @param orderType target order type to check whether it can be used with the given grouping type;
|
||||
* <code>null</code> to indicate that we want to know if given grouping type can be used in general
|
||||
* for the languages-specific realisation of this interface
|
||||
* @return <code>true</code> if given arguments are eligible for the languages-specific realisation of this interface;
|
||||
* <code>false</code> otherwise
|
||||
*/
|
||||
boolean isEnabled(@NotNull ArrangementGroupingType groupingType, @Nullable ArrangementEntryOrderType orderType);
|
||||
|
||||
/**
|
||||
* @return collections of mutual exclusion settings. E.g. not more than one visibility modifier can be used for a single
|
||||
* java language rule
|
||||
*/
|
||||
@NotNull
|
||||
Collection<Set<?>> getMutexes();
|
||||
}
|
||||
-77
@@ -1,77 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.psi.codeStyle.arrangement.settings;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.Rearranger;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Allows to inject custom logic for representation {@link ArrangementStandardSettingsAware standard settings-aware}
|
||||
* {@link Rearranger language-specific rearranger}.
|
||||
* <p/>
|
||||
* Implementations of this interface are expected to be thread-safe.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/15/12 10:15 AM
|
||||
*/
|
||||
public interface ArrangementStandardSettingsRepresentationAware {
|
||||
|
||||
/**
|
||||
* @param type target entry type
|
||||
* @return text to show end-user for the given type
|
||||
*/
|
||||
@NotNull
|
||||
String getDisplayValue(@NotNull ArrangementEntryType type);
|
||||
|
||||
/**
|
||||
* @param modifier target modifier
|
||||
* @return text to show end-user for the given modifier
|
||||
*/
|
||||
@NotNull
|
||||
String getDisplayValue(@NotNull ArrangementModifier modifier);
|
||||
|
||||
/**
|
||||
* @param groupingType target grouping type
|
||||
* @return text to show end-user for the given grouping type
|
||||
*/
|
||||
@NotNull
|
||||
String getDisplayValue(@NotNull ArrangementGroupingType groupingType);
|
||||
|
||||
/**
|
||||
* @param orderType target order type
|
||||
* @return text to show end-user for the given order type
|
||||
*/
|
||||
@NotNull
|
||||
String getDisplayValue(@NotNull ArrangementEntryOrderType orderType);
|
||||
|
||||
/**
|
||||
* Allows to sort given arrangement condition ids ('field', 'class', 'method', 'public', 'static', 'final' etc) before showing
|
||||
* them to an end-user.
|
||||
*
|
||||
* @param ids target ids to use
|
||||
* @param <T> id type
|
||||
* @return sorted ids to use
|
||||
*/
|
||||
@NotNull
|
||||
<T> List<T> sort(@NotNull Collection<T> ids);
|
||||
}
|
||||
-151
@@ -1,151 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.psi.codeStyle.arrangement.settings;
|
||||
|
||||
import com.intellij.openapi.application.ApplicationBundle;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import gnu.trove.TObjectIntHashMap;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.*;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/15/12 10:24 AM
|
||||
*/
|
||||
public class DefaultArrangementSettingsRepresentationManager implements ArrangementStandardSettingsRepresentationAware {
|
||||
|
||||
@NotNull public static final DefaultArrangementSettingsRepresentationManager INSTANCE =
|
||||
new DefaultArrangementSettingsRepresentationManager();
|
||||
|
||||
@NotNull private static final TObjectIntHashMap<Object> WEIGHTS = new TObjectIntHashMap<Object>();
|
||||
|
||||
static {
|
||||
Object[] ids = {
|
||||
|
||||
// Types.
|
||||
ArrangementEntryType.FIELD, ArrangementEntryType.CONSTRUCTOR, ArrangementEntryType.METHOD, ArrangementEntryType.CLASS,
|
||||
ArrangementEntryType.INTERFACE, ArrangementEntryType.ENUM,
|
||||
|
||||
ArrangementEntryType.STATIC_INIT, ArrangementEntryType.CONST, ArrangementEntryType.VAR,
|
||||
ArrangementEntryType.PROPERTY, ArrangementEntryType.EVENT_HANDLER,
|
||||
|
||||
ArrangementEntryType.NAMESPACE, ArrangementEntryType.TRAIT,
|
||||
|
||||
// Visibility.
|
||||
ArrangementModifier.PUBLIC, ArrangementModifier.PROTECTED, ArrangementModifier.PACKAGE_PRIVATE, ArrangementModifier.PRIVATE,
|
||||
|
||||
// Other common modifiers.
|
||||
ArrangementModifier.STATIC, ArrangementModifier.FINAL,
|
||||
|
||||
ArrangementModifier.OVERRIDE,
|
||||
|
||||
// Semi-common modifiers.
|
||||
ArrangementModifier.ABSTRACT,
|
||||
|
||||
// Method-specific modifiers.
|
||||
ArrangementModifier.SYNCHRONIZED,
|
||||
|
||||
// Field-specific modifiers.
|
||||
ArrangementModifier.TRANSIENT, ArrangementModifier.VOLATILE
|
||||
};
|
||||
for (int i = 0; i < ids.length; i++) {
|
||||
WEIGHTS.put(ids[i], i);
|
||||
}
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private static final Comparator<Object> COMPARATOR = new Comparator<Object>() {
|
||||
@Override
|
||||
public int compare(Object o1, Object o2) {
|
||||
if (WEIGHTS.containsKey(o1) && WEIGHTS.containsKey(o2)) {
|
||||
return WEIGHTS.get(o1) - WEIGHTS.get(o2);
|
||||
}
|
||||
else if (WEIGHTS.containsKey(o1) && !WEIGHTS.containsKey(o2)) {
|
||||
return -1;
|
||||
}
|
||||
else if (!WEIGHTS.containsKey(o1) && WEIGHTS.containsKey(o2)) {
|
||||
return 1;
|
||||
}
|
||||
else {
|
||||
return o1.hashCode() - o2.hashCode();
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
private static final Map<ArrangementGroupingType, String> GROUPING_TYPES = ContainerUtil.newHashMap();
|
||||
static {
|
||||
GROUPING_TYPES.put(ArrangementGroupingType.GETTERS_AND_SETTERS,
|
||||
ApplicationBundle.message("arrangement.settings.groups.getters.and.setters.together"));
|
||||
GROUPING_TYPES.put(ArrangementGroupingType.OVERRIDDEN_METHODS,
|
||||
ApplicationBundle.message("arrangement.settings.groups.overridden.methods"));
|
||||
GROUPING_TYPES.put(ArrangementGroupingType.DEPENDENT_METHODS,
|
||||
ApplicationBundle.message("arrangement.settings.groups.dependent.methods"));
|
||||
GROUPING_TYPES.put(ArrangementGroupingType.GROUP_PROPERTY_FIELD_WITH_GETTER_SETTER,
|
||||
ApplicationBundle.message("arrangement.settings.groups.property.field"));
|
||||
assert GROUPING_TYPES.size() == ArrangementGroupingType.values().length;
|
||||
}
|
||||
|
||||
private static final Map<ArrangementEntryOrderType, String> ORDER_TYPES = ContainerUtil.newHashMap();
|
||||
static {
|
||||
ORDER_TYPES.put(ArrangementEntryOrderType.KEEP, ApplicationBundle.message("arrangement.settings.order.type.keep"));
|
||||
ORDER_TYPES.put(ArrangementEntryOrderType.BY_NAME, ApplicationBundle.message("arrangement.settings.order.type.by.name"));
|
||||
ORDER_TYPES.put(ArrangementEntryOrderType.DEPTH_FIRST, ApplicationBundle.message("arrangement.settings.order.type.depth.first"));
|
||||
ORDER_TYPES.put(ArrangementEntryOrderType.BREADTH_FIRST, ApplicationBundle.message("arrangement.settings.order.type.breadth.first"));
|
||||
assert ORDER_TYPES.size() == ArrangementEntryOrderType.values().length;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public String getDisplayValue(@NotNull ArrangementEntryType type) {
|
||||
return getDisplayValue(type.toString());
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public String getDisplayValue(@NotNull ArrangementModifier modifier) {
|
||||
return getDisplayValue(modifier.toString());
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private static String getDisplayValue(@NotNull String s) {
|
||||
return s.toLowerCase().replace("_", " ");
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public String getDisplayValue(@NotNull ArrangementGroupingType groupingType) {
|
||||
return GROUPING_TYPES.get(groupingType);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public String getDisplayValue(@NotNull ArrangementEntryOrderType orderType) {
|
||||
return ORDER_TYPES.get(orderType);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public <T> List<T> sort(@NotNull Collection<T> ids) {
|
||||
List<T> result = new ArrayList<T>(ids);
|
||||
Collections.sort(result, COMPARATOR);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
+2
-3
@@ -13,11 +13,10 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement.settings;
|
||||
package com.intellij.psi.codeStyle.arrangement.std;
|
||||
|
||||
import com.intellij.openapi.editor.colors.EditorColorsScheme;
|
||||
import com.intellij.openapi.editor.markup.TextAttributes;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@@ -34,7 +33,7 @@ import java.awt.*;
|
||||
public interface ArrangementColorsAware {
|
||||
|
||||
@Nullable
|
||||
TextAttributes getTextAttributes(@NotNull EditorColorsScheme scheme, @NotNull ArrangementSettingType type, boolean selected);
|
||||
TextAttributes getTextAttributes(@NotNull EditorColorsScheme scheme, @NotNull ArrangementSettingsToken token, boolean selected);
|
||||
|
||||
@Nullable
|
||||
Color getBorderColor(@NotNull EditorColorsScheme scheme, boolean selected);
|
||||
+72
@@ -0,0 +1,72 @@
|
||||
/*
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement.std;
|
||||
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
/**
|
||||
* Stands for an atomic settings element. The general idea is to allow third-party plugin developers to use platform
|
||||
* codebase for managing arrangement settings, that's why we need a general purpose class that represent a setting.
|
||||
* I.e. third-party developers can create their own instances of this class and implement {@link ArrangementStandardSettingsAware}.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 3/6/13 12:38 PM
|
||||
*/
|
||||
public class ArrangementSettingsToken implements Comparable<ArrangementSettingsToken> {
|
||||
|
||||
@NotNull private final String myId;
|
||||
@NotNull private final String myRepresentationName;
|
||||
|
||||
public ArrangementSettingsToken(@NotNull String id, @NotNull String name) {
|
||||
myId = id;
|
||||
myRepresentationName = name;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public String getId() {
|
||||
return myId;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public String getRepresentationValue() {
|
||||
return myRepresentationName;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int compareTo(ArrangementSettingsToken that) {
|
||||
return myId.compareTo(that.myId);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return myId.hashCode();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(@Nullable Object o) {
|
||||
if (this == o) return true;
|
||||
if (o == null || getClass() != o.getClass()) return false;
|
||||
|
||||
ArrangementSettingsToken that = (ArrangementSettingsToken)o;
|
||||
return myId.equals(that.myId);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return myRepresentationName;
|
||||
}
|
||||
}
|
||||
+89
@@ -0,0 +1,89 @@
|
||||
/*
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement.std;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.Rearranger;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryMatcher;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* Defines a contract for {@link Rearranger} implementation which wants to use standard platform UI for configuring
|
||||
* and managing arrangement settings.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/6/12 2:26 PM
|
||||
*/
|
||||
public interface ArrangementStandardSettingsAware {
|
||||
|
||||
/**
|
||||
* @return settings to use by default, i.e. when a user hasn't been explicitly modified arrangement settings;
|
||||
* <code>null</code> as an indication that no default settings are available
|
||||
*/
|
||||
@Nullable
|
||||
StdArrangementSettings getDefaultSettings();
|
||||
|
||||
/**
|
||||
* @return ordered collection of grouping tokens eligible to use with the current rearranger.
|
||||
* <b>Note:</b> platform code which uses this method caches returned results
|
||||
*/
|
||||
@Nullable
|
||||
List<CompositeArrangementSettingsToken> getSupportedGroupingTokens();
|
||||
|
||||
/**
|
||||
* @return ordered collection of matching tokens eligible to use with the current rearranger
|
||||
* <b>Note:</b> platform code which uses this method caches returned results
|
||||
*/
|
||||
@Nullable
|
||||
List<CompositeArrangementSettingsToken> getSupportedMatchingTokens();
|
||||
|
||||
/**
|
||||
* Allows to answer if given token is enabled in combination with other conditions specified by the given condition object.
|
||||
* <p/>
|
||||
* Example: say, current rearranger is for java and given condition is like 'public class'. This method is expected to
|
||||
* return <code>false</code> for token 'volatile' (because it can be applied only to fields) but <code>true</code>
|
||||
* for token 'abstract' (a java class can be abstract).
|
||||
*
|
||||
* @param token target token to check
|
||||
* @param current an object which represents currently chosen tokens; <code>null</code> if no other token is selected
|
||||
* @return <code>true</code> if given token is enabled with the given condition; <code>false</code> otherwise
|
||||
*/
|
||||
boolean isEnabled(@NotNull ArrangementSettingsToken token, @Nullable ArrangementMatchCondition current);
|
||||
|
||||
/**
|
||||
* This method is assumed to be used only by third-party developers. All built-in IJ conditions are supposed
|
||||
* to be implemented in terms of {@link StdArrangementTokens}.
|
||||
*
|
||||
* @param condition target condition
|
||||
* @return a matcher for the given condition
|
||||
* @throws IllegalArgumentException if current rearranger doesn't know how to build a matcher from the given condition
|
||||
*/
|
||||
@NotNull
|
||||
ArrangementEntryMatcher buildMatcher(@NotNull ArrangementMatchCondition condition) throws IllegalArgumentException;
|
||||
|
||||
/**
|
||||
* @return collections of mutual exclusion settings. It's is used by standard arrangement settings UI to automatically
|
||||
* deselect elements on selection change. Example: 'private' modifier was selected. When any other modifier is selected
|
||||
* 'public' modifier is deselected if returned collection contains set of all supported visibility modifiers
|
||||
*/
|
||||
@NotNull
|
||||
Collection<Set<ArrangementSettingsToken>> getMutexes();
|
||||
}
|
||||
+182
@@ -0,0 +1,182 @@
|
||||
/*
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement.std;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementUtil;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryMatcher;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.CompositeArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementSettings;
|
||||
import com.intellij.ui.SimpleColoredComponent;
|
||||
import com.intellij.ui.SimpleTextAttributes;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import gnu.trove.TObjectIntHashMap;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.*;
|
||||
|
||||
/**
|
||||
* Wraps {@link ArrangementStandardSettingsAware} for the common arrangement UI managing code.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 3/7/13 3:11 PM
|
||||
*/
|
||||
public class ArrangementStandardSettingsManager {
|
||||
|
||||
@NotNull private final TObjectIntHashMap<ArrangementSettingsToken> myWidths = new TObjectIntHashMap<ArrangementSettingsToken>();
|
||||
@NotNull private final TObjectIntHashMap<ArrangementSettingsToken> myWeights = new TObjectIntHashMap<ArrangementSettingsToken>();
|
||||
|
||||
@NotNull private final Comparator<ArrangementSettingsToken> myComparator = new Comparator<ArrangementSettingsToken>() {
|
||||
@Override
|
||||
public int compare(ArrangementSettingsToken t1, ArrangementSettingsToken t2) {
|
||||
if (myWeights.containsKey(t1)) {
|
||||
if (myWeights.containsKey(t2)) {
|
||||
return myWeights.get(t1) - myWeights.get(t2);
|
||||
}
|
||||
else {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
else if (myWeights.containsKey(t2)) {
|
||||
return 1;
|
||||
}
|
||||
else {
|
||||
return t1.compareTo(t2);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
@NotNull private final ArrangementStandardSettingsAware myDelegate;
|
||||
@NotNull private final ArrangementColorsProvider myColorsProvider;
|
||||
@NotNull private final Collection<Set<ArrangementSettingsToken>> myMutexes;
|
||||
|
||||
@Nullable private final StdArrangementSettings myDefaultSettings;
|
||||
@Nullable private final List<CompositeArrangementSettingsToken> myGroupingTokens;
|
||||
@Nullable private final List<CompositeArrangementSettingsToken> myMatchingTokens;
|
||||
|
||||
public ArrangementStandardSettingsManager(@NotNull ArrangementStandardSettingsAware delegate,
|
||||
@NotNull ArrangementColorsProvider colorsProvider)
|
||||
{
|
||||
myDelegate = delegate;
|
||||
myColorsProvider = colorsProvider;
|
||||
myMutexes = delegate.getMutexes();
|
||||
myDefaultSettings = delegate.getDefaultSettings();
|
||||
|
||||
SimpleColoredComponent renderer = new SimpleColoredComponent();
|
||||
myGroupingTokens = delegate.getSupportedGroupingTokens();
|
||||
if (myGroupingTokens != null) {
|
||||
parseWidths(myGroupingTokens, renderer);
|
||||
buildWeights(myGroupingTokens);
|
||||
}
|
||||
|
||||
myMatchingTokens = delegate.getSupportedMatchingTokens();
|
||||
if (myMatchingTokens != null) {
|
||||
parseWidths(myMatchingTokens, renderer);
|
||||
buildWeights(myMatchingTokens);
|
||||
}
|
||||
}
|
||||
|
||||
private void parseWidths(@NotNull Collection<CompositeArrangementSettingsToken> compositeTokens,
|
||||
@NotNull SimpleColoredComponent renderer)
|
||||
{
|
||||
int width = 0;
|
||||
for (CompositeArrangementSettingsToken compositeToken : compositeTokens) {
|
||||
width = Math.max(width, parseWidth(compositeToken.getToken(), renderer));
|
||||
}
|
||||
for (CompositeArrangementSettingsToken compositeToken : compositeTokens) {
|
||||
myWidths.put(compositeToken.getToken(), width);
|
||||
parseWidths(compositeToken.getChildren(), renderer);
|
||||
}
|
||||
}
|
||||
|
||||
private void buildWeights(@NotNull Collection<CompositeArrangementSettingsToken> compositeTokens) {
|
||||
for (CompositeArrangementSettingsToken token : compositeTokens) {
|
||||
myWeights.put(token.getToken(), myWeights.size());
|
||||
buildWeights(token.getChildren());
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @see ArrangementStandardSettingsAware#getDefaultSettings()
|
||||
*/
|
||||
@Nullable
|
||||
public StdArrangementSettings getDefaultSettings() {
|
||||
return myDefaultSettings;
|
||||
}
|
||||
|
||||
/**
|
||||
* @see ArrangementStandardSettingsAware#getSupportedGroupingTokens()
|
||||
*/
|
||||
@Nullable
|
||||
public List<CompositeArrangementSettingsToken> getSupportedGroupingTokens() {
|
||||
return myGroupingTokens;
|
||||
}
|
||||
|
||||
/**
|
||||
* @see ArrangementStandardSettingsAware#getSupportedMatchingTokens()
|
||||
*/
|
||||
@Nullable
|
||||
public List<CompositeArrangementSettingsToken> getSupportedMatchingTokens() {
|
||||
return myMatchingTokens;
|
||||
}
|
||||
|
||||
public boolean isEnabled(@NotNull ArrangementSettingsToken token, @Nullable ArrangementMatchCondition current) {
|
||||
return myDelegate.isEnabled(token, current);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public ArrangementEntryMatcher buildMatcher(@NotNull ArrangementMatchCondition condition) throws IllegalArgumentException {
|
||||
ArrangementEntryMatcher matcher = ArrangementUtil.buildMatcher(condition);
|
||||
if (matcher == null) {
|
||||
matcher = myDelegate.buildMatcher(condition);
|
||||
}
|
||||
return matcher;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public Collection<Set<ArrangementSettingsToken>> getMutexes() {
|
||||
return myMutexes;
|
||||
}
|
||||
|
||||
public int getWidth(@NotNull ArrangementSettingsToken token) {
|
||||
if (myWidths.containsKey(token)) {
|
||||
return myWidths.get(token);
|
||||
}
|
||||
return parseWidth(token, new SimpleColoredComponent());
|
||||
}
|
||||
|
||||
private int parseWidth(@NotNull ArrangementSettingsToken token, @NotNull SimpleColoredComponent renderer) {
|
||||
renderer.clear();
|
||||
renderer.append(token.getRepresentationValue(),
|
||||
SimpleTextAttributes.fromTextAttributes(myColorsProvider.getTextAttributes(token, true)));
|
||||
int result = renderer.getPreferredSize().width;
|
||||
|
||||
renderer.clear();
|
||||
renderer.append(token.getRepresentationValue(),
|
||||
SimpleTextAttributes.fromTextAttributes(myColorsProvider.getTextAttributes(token, false)));
|
||||
return Math.max(result, renderer.getPreferredSize().width);
|
||||
}
|
||||
|
||||
public List<ArrangementSettingsToken> sort(@NotNull Collection<ArrangementSettingsToken> tokens) {
|
||||
List<ArrangementSettingsToken> result = ContainerUtilRt.newArrayList(tokens);
|
||||
Collections.sort(result, myComparator);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
+53
-11
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2012 JetBrains s.r.o.
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -13,8 +13,10 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.match;
|
||||
package com.intellij.psi.codeStyle.arrangement.std;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.openapi.extensions.ExtensionPointName;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
@@ -22,44 +24,61 @@ import org.jetbrains.annotations.Nullable;
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.awt.event.MouseEvent;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Component which manages {@link ArrangementMatchCondition match condition} UI representation.
|
||||
* Defines a contract for UI component used at standard arrangement settings managing code.
|
||||
* <p/>
|
||||
* It's assumed that there is a dedicated implementation of this interface for every {@link StdArrangementTokenUiRole}.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/10/12 11:22 AM
|
||||
* @since 3/11/13 10:22 AM
|
||||
*/
|
||||
public interface ArrangementMatchConditionComponent {
|
||||
public interface ArrangementUiComponent {
|
||||
|
||||
@Nullable ArrangementSettingsToken getToken();
|
||||
|
||||
void chooseToken(@NotNull ArrangementSettingsToken data) throws IllegalArgumentException, UnsupportedOperationException;
|
||||
|
||||
@NotNull
|
||||
ArrangementMatchCondition getMatchCondition();
|
||||
|
||||
@NotNull JComponent getUiComponent();
|
||||
|
||||
/**
|
||||
* @return UI component for the {@link #getMatchCondition() target match condition}
|
||||
* We use 'enabled by user' property name here in order to avoid clash
|
||||
* with {@link Component#isEnabled() standard awt 'enabled' property}.
|
||||
*
|
||||
* @return <code>true</code> if current ui token is enabled; <code>false</code> otherwise
|
||||
*/
|
||||
@NotNull
|
||||
JComponent getUiComponent();
|
||||
boolean isEnabled();
|
||||
|
||||
void setEnabled(boolean enabled);
|
||||
|
||||
/**
|
||||
* @return screen bounds for the {@link #getUiComponent() target UI component} (if known)
|
||||
*/
|
||||
@Nullable
|
||||
Rectangle getScreenBounds();
|
||||
|
||||
|
||||
boolean isSelected();
|
||||
|
||||
/**
|
||||
* Instructs current component that it should {@link #getUiComponent() draw} itself according to the given 'selected' state.
|
||||
*
|
||||
* @param selected flag that indicates if current component should be drawn as 'selected'
|
||||
*/
|
||||
void setSelected(boolean selected);
|
||||
|
||||
|
||||
void reset();
|
||||
|
||||
/**
|
||||
* Notifies current component about mose move event.
|
||||
* <p/>
|
||||
* Primary intention is to allow to react on event like 'on mouse hover' etc. We can't do that by subscribing to the
|
||||
* mouse events at the {@link #getUiComponent() corresponding UI control} because it's used only as a renderer and is not put
|
||||
* to the containers hierarchy, hence, doesn't receive mouse events.
|
||||
*
|
||||
*
|
||||
* @param event target mouse move event
|
||||
* @return bounds to be repainted (in screen coordinates) if any; <code>null</code> otherwise
|
||||
*/
|
||||
@@ -73,4 +92,27 @@ public interface ArrangementMatchConditionComponent {
|
||||
|
||||
@Nullable
|
||||
Rectangle onMouseEntered(@NotNull MouseEvent e);
|
||||
|
||||
/**
|
||||
* @param width the width to get baseline for
|
||||
* @param height the height to get baseline for
|
||||
* @return baseline's y coordinate if applicable; negative value otherwise
|
||||
*/
|
||||
int getBaselineToUse(int width, int height);
|
||||
|
||||
void setListener(@NotNull Listener listener);
|
||||
|
||||
interface Factory {
|
||||
ExtensionPointName<Factory> EP_NAME = ExtensionPointName.create("com.intellij.rearranger.ui");
|
||||
|
||||
@Nullable
|
||||
ArrangementUiComponent build(@NotNull StdArrangementTokenUiRole role,
|
||||
@NotNull List<ArrangementSettingsToken> tokens,
|
||||
@NotNull ArrangementColorsProvider colorsProvider,
|
||||
@NotNull ArrangementStandardSettingsManager settingsManager);
|
||||
}
|
||||
|
||||
interface Listener {
|
||||
void stateChanged();
|
||||
}
|
||||
}
|
||||
+118
@@ -0,0 +1,118 @@
|
||||
/*
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement.std;
|
||||
|
||||
import com.intellij.util.Function;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Used to group ordered collections of {@link StdArrangementTokens} along with their {@link StdArrangementTokenUiRole roles}.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 3/6/13 8:01 PM
|
||||
*/
|
||||
public class CompositeArrangementSettingsToken {
|
||||
|
||||
private static final Function<ArrangementSettingsToken, CompositeArrangementSettingsToken> WRAPPER =
|
||||
new Function<ArrangementSettingsToken, CompositeArrangementSettingsToken>() {
|
||||
@Override
|
||||
public CompositeArrangementSettingsToken fun(ArrangementSettingsToken token) {
|
||||
return new CompositeArrangementSettingsToken(token, deduceRole(token), Collections.<CompositeArrangementSettingsToken>emptyList());
|
||||
}
|
||||
};
|
||||
|
||||
@NotNull private final List<CompositeArrangementSettingsToken> myChildren = ContainerUtilRt.newArrayList();
|
||||
|
||||
@NotNull private final ArrangementSettingsToken myToken;
|
||||
@NotNull private final StdArrangementTokenUiRole myRole;
|
||||
|
||||
/**
|
||||
* Creates new <code>CompositeArrangementSettingsToken</code> object with no nested tokens.
|
||||
* <p/>
|
||||
* <b>Note:</b> given token is expected to be one of {@link StdArrangementTokens standard tokens} because
|
||||
* {@link StdArrangementTokenUiRole its role} is deduced.
|
||||
*
|
||||
* @param token token to wrap
|
||||
*/
|
||||
public CompositeArrangementSettingsToken(@NotNull ArrangementSettingsToken token) {
|
||||
this(token, deduceRole(token), Collections.<CompositeArrangementSettingsToken>emptyList());
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates new <code>CompositeArrangementSettingsToken</code> object with the given token and all given children
|
||||
* assuming that every child {@link CompositeArrangementSettingsToken} will have no children.
|
||||
* <p/>
|
||||
* <b>Note:</b> given tokens are expected to be from {@link StdArrangementTokens standard tokens} because
|
||||
* {@link StdArrangementTokenUiRole their roles} are deduced.
|
||||
*
|
||||
* @param token token to wrap
|
||||
* @param children children to wrap
|
||||
*/
|
||||
public CompositeArrangementSettingsToken(@NotNull ArrangementSettingsToken token,
|
||||
@NotNull ArrangementSettingsToken... children)
|
||||
{
|
||||
this(token, deduceRole(token), ContainerUtilRt.map2List(children, WRAPPER));
|
||||
}
|
||||
|
||||
public CompositeArrangementSettingsToken(@NotNull ArrangementSettingsToken token,
|
||||
@NotNull Collection<ArrangementSettingsToken> children)
|
||||
{
|
||||
this(token, deduceRole(token), ContainerUtilRt.map2List(children, WRAPPER));
|
||||
}
|
||||
|
||||
public CompositeArrangementSettingsToken(@NotNull ArrangementSettingsToken token,
|
||||
@NotNull StdArrangementTokenUiRole role,
|
||||
@NotNull List<CompositeArrangementSettingsToken> children)
|
||||
{
|
||||
myToken = token;
|
||||
myRole = role;
|
||||
myChildren.addAll(children);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private static StdArrangementTokenUiRole deduceRole(@NotNull ArrangementSettingsToken token) {
|
||||
StdArrangementTokenUiRole role = StdArrangementTokens.role(token);
|
||||
if (role == null) {
|
||||
throw new IllegalArgumentException("Can't deduce UI role for token " + token);
|
||||
}
|
||||
return role;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public List<CompositeArrangementSettingsToken> getChildren() {
|
||||
return myChildren;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public ArrangementSettingsToken getToken() {
|
||||
return myToken;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public StdArrangementTokenUiRole getRole() {
|
||||
return myRole;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return myToken.toString() + "-" + myRole;
|
||||
}
|
||||
}
|
||||
+3
-2
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2012 JetBrains s.r.o.
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -13,8 +13,9 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement;
|
||||
package com.intellij.psi.codeStyle.arrangement.std;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementSettings;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
+9
-5
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2012 JetBrains s.r.o.
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -13,12 +13,16 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement.model;
|
||||
package com.intellij.psi.codeStyle.arrangement.std;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/6/12 5:02 PM
|
||||
* @since 3/11/13 9:45 AM
|
||||
*/
|
||||
public enum ArrangementSettingType {
|
||||
TYPE, MODIFIER, NAME, ORDER
|
||||
public enum StdArrangementTokenUiRole {
|
||||
LABEL,
|
||||
CHECKBOX,
|
||||
COMBO_BOX,
|
||||
TEXT_FIELD,
|
||||
BULB,
|
||||
}
|
||||
+237
@@ -0,0 +1,237 @@
|
||||
/*
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement.std;
|
||||
|
||||
import com.intellij.openapi.application.ApplicationBundle;
|
||||
import com.intellij.openapi.util.NotNullLazyValue;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
import org.jetbrains.annotations.PropertyKey;
|
||||
|
||||
import java.lang.reflect.Field;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokenUiRole.*;
|
||||
|
||||
/**
|
||||
* // TODO den add doc
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 3/6/13 3:16 PM
|
||||
*/
|
||||
public class StdArrangementTokens {
|
||||
|
||||
private static final Map<String, ArrangementSettingsToken> TOKENS_BY_ID = ContainerUtilRt.newHashMap();
|
||||
private static final Map<ArrangementSettingsToken, StdArrangementTokenUiRole> ROLES_BY_TOKEN = ContainerUtilRt.newHashMap();
|
||||
|
||||
/**
|
||||
* Forces nested classes initialization - otherwise it's possible that, say, {@link #byId(String)} returns null for valid
|
||||
* id just because corresponding nested class hasn't been initialized yet.
|
||||
*/
|
||||
private static final NotNullLazyValue<Integer> NESTED_CLASSES_INITIALIZER = new NotNullLazyValue<Integer>() {
|
||||
@NotNull
|
||||
@Override
|
||||
protected Integer compute() {
|
||||
int dummy = 0;
|
||||
for (Class<?> clazz : StdArrangementTokens.class.getClasses()) {
|
||||
try {
|
||||
dummy += clazz.getDeclaredFields()[0].get(null).hashCode();
|
||||
}
|
||||
catch (IllegalAccessException e) {
|
||||
assert false;
|
||||
}
|
||||
}
|
||||
return dummy;
|
||||
}
|
||||
};
|
||||
|
||||
private StdArrangementTokens() {
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static ArrangementSettingsToken byId(@NotNull String id) {
|
||||
NESTED_CLASSES_INITIALIZER.getValue();
|
||||
return TOKENS_BY_ID.get(id);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static StdArrangementTokenUiRole role(@NotNull ArrangementSettingsToken token) {
|
||||
NESTED_CLASSES_INITIALIZER.getValue();
|
||||
return ROLES_BY_TOKEN.get(token);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private static ArrangementSettingsToken token(@NotNull String id, @NotNull StdArrangementTokenUiRole role) {
|
||||
ArrangementSettingsToken result = new ArrangementSettingsToken(id, id.toLowerCase().replace("_", " "));
|
||||
TOKENS_BY_ID.put(id, result);
|
||||
ROLES_BY_TOKEN.put(result, role);
|
||||
return result;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private static ArrangementSettingsToken token(@NotNull String id,
|
||||
@NotNull @PropertyKey(resourceBundle = ApplicationBundle.BUNDLE) String key,
|
||||
@NotNull StdArrangementTokenUiRole role)
|
||||
{
|
||||
ArrangementSettingsToken result = new ArrangementSettingsToken(id, ApplicationBundle.message(key));
|
||||
TOKENS_BY_ID.put(id, result);
|
||||
ROLES_BY_TOKEN.put(result, role);
|
||||
return result;
|
||||
}
|
||||
|
||||
private static NotNullLazyValue<Set<ArrangementSettingsToken>> collectFields(@NotNull final Class<?> clazz) {
|
||||
return new NotNullLazyValue<Set<ArrangementSettingsToken>>() {
|
||||
@NotNull
|
||||
@Override
|
||||
protected Set<ArrangementSettingsToken> compute() {
|
||||
Set<ArrangementSettingsToken> result = ContainerUtilRt.newHashSet();
|
||||
for (Field field : clazz.getFields()) {
|
||||
if (ArrangementSettingsToken.class.isAssignableFrom(field.getType())) {
|
||||
try {
|
||||
result.add((ArrangementSettingsToken)field.get(null));
|
||||
}
|
||||
catch (IllegalAccessException e) {
|
||||
assert false : e;
|
||||
}
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
public static class General {
|
||||
|
||||
@NotNull public static final ArrangementSettingsToken TYPE = token("TYPE", "arrangement.settings.text.general.type", LABEL);
|
||||
@NotNull public static final ArrangementSettingsToken MODIFIER = token("MODIFIER", "arrangement.settings.text.general.modifier", LABEL);
|
||||
@NotNull public static final ArrangementSettingsToken NAME = token("NAME", "arrangement.settings.text.general.name", TEXT_FIELD);
|
||||
@NotNull public static final ArrangementSettingsToken ORDER = token("ORDER", "arrangement.settings.text.general.order", LABEL);
|
||||
|
||||
private static final NotNullLazyValue<Set<ArrangementSettingsToken>> TOKENS = collectFields(General.class);
|
||||
|
||||
private General() {
|
||||
}
|
||||
|
||||
public static boolean is(@NotNull ArrangementSettingsToken token) {
|
||||
return TOKENS.getValue().contains(token);
|
||||
}
|
||||
}
|
||||
|
||||
public static class EntryType {
|
||||
|
||||
@NotNull public static final ArrangementSettingsToken CLASS = token("CLASS", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken ANONYMOUS_CLASS = token("ANONYMOUS_CLASS", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken FIELD = token("FIELD", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken CONSTRUCTOR = token("CONSTRUCTOR", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken METHOD = token("METHOD", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken ENUM = token("ENUM", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken INTERFACE = token("INTERFACE", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken CONST = token("CONST", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken VAR = token("VAR", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken PROPERTY = token("PROPERTY", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken EVENT_HANDLER = token("EVENT_HANDLER", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken STATIC_INIT = token("STATIC_INIT", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken NAMESPACE = token("NAMESPACE", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken TRAIT = token("TRAIT", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken XML_TAG =
|
||||
token("XML_TAG", "arrangement.settings.text.entry.type.xml.tag", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken XML_ATTRIBUTE =
|
||||
token("XML_ATTRIBUTE", "arrangement.settings.text.entry.type.xml.attribute", BULB);
|
||||
|
||||
private static final NotNullLazyValue<Set<ArrangementSettingsToken>> TOKENS = collectFields(EntryType.class);
|
||||
|
||||
private EntryType() {
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static Set<ArrangementSettingsToken> values() {
|
||||
return TOKENS.getValue();
|
||||
}
|
||||
|
||||
public static boolean is(@NotNull ArrangementSettingsToken token) {
|
||||
return TOKENS.getValue().contains(token);
|
||||
}
|
||||
}
|
||||
|
||||
public static class Modifier {
|
||||
|
||||
@NotNull public static final ArrangementSettingsToken PUBLIC = token("PUBLIC", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken PROTECTED = token("PROTECTED", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken PRIVATE = token("PRIVATE", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken PACKAGE_PRIVATE = token("PACKAGE_PRIVATE", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken STATIC = token("STATIC", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken FINAL = token("FINAL", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken TRANSIENT = token("TRANSIENT", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken VOLATILE = token("VOLATILE", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken SYNCHRONIZED = token("SYNCHRONIZED", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken ABSTRACT = token("ABSTRACT", BULB);
|
||||
@NotNull public static final ArrangementSettingsToken OVERRIDE = token("OVERRIDE", BULB);
|
||||
|
||||
private static final NotNullLazyValue<Set<ArrangementSettingsToken>> TOKENS = collectFields(Modifier.class);
|
||||
|
||||
private Modifier() {
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static Set<ArrangementSettingsToken> values() {
|
||||
return TOKENS.getValue();
|
||||
}
|
||||
|
||||
public static boolean is(@NotNull ArrangementSettingsToken token) {
|
||||
return TOKENS.getValue().contains(token);
|
||||
}
|
||||
}
|
||||
|
||||
public static class Grouping {
|
||||
|
||||
@NotNull public static final ArrangementSettingsToken GETTERS_AND_SETTERS =
|
||||
token("GETTERS_AND_SETTERS", "arrangement.settings.groups.getters.and.setters.together", CHECKBOX);
|
||||
@NotNull public static final ArrangementSettingsToken OVERRIDDEN_METHODS =
|
||||
token("OVERRIDDEN_METHODS", "arrangement.settings.groups.overridden.methods", CHECKBOX);
|
||||
@NotNull public static final ArrangementSettingsToken DEPENDENT_METHODS =
|
||||
token("DEPENDENT_METHODS", "arrangement.settings.groups.dependent.methods", CHECKBOX);
|
||||
@NotNull public static final ArrangementSettingsToken GROUP_PROPERTY_FIELD_WITH_GETTER_SETTER =
|
||||
token("GROUP_PROPERTY_FIELD_WITH_GETTER_SETTER", "arrangement.settings.groups.property.field", CHECKBOX);
|
||||
|
||||
private Grouping() {
|
||||
}
|
||||
}
|
||||
|
||||
public static class Order {
|
||||
|
||||
@NotNull public static final ArrangementSettingsToken KEEP = token("KEEP", "arrangement.settings.order.type.keep",
|
||||
COMBO_BOX);
|
||||
@NotNull public static final ArrangementSettingsToken BY_NAME = token("BY_NAME", "arrangement.settings.order.type.by.name",
|
||||
COMBO_BOX);
|
||||
@NotNull public static final ArrangementSettingsToken DEPTH_FIRST = token("DEPTH_FIRST",
|
||||
"arrangement.settings.order.type.depth.first",
|
||||
COMBO_BOX);
|
||||
@NotNull public static final ArrangementSettingsToken BREADTH_FIRST = token("BREADTH_FIRST",
|
||||
"arrangement.settings.order.type.breadth.first",
|
||||
COMBO_BOX);
|
||||
|
||||
private static final NotNullLazyValue<Set<ArrangementSettingsToken>> TOKENS = collectFields(Order.class);
|
||||
|
||||
private Order() {
|
||||
}
|
||||
|
||||
public static boolean is(@NotNull ArrangementSettingsToken token) {
|
||||
return TOKENS.getValue().contains(token);
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
-7
@@ -16,16 +16,16 @@
|
||||
package com.intellij.psi.codeStyle.arrangement;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementEntryMatcher;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementSettings;
|
||||
import org.jdom.Element;
|
||||
import org.junit.Test;
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.EntryType.FIELD;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Grouping.OVERRIDDEN_METHODS;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Order.BY_NAME;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
|
||||
/**
|
||||
@@ -37,9 +37,9 @@ public class ArrangementSettingsSerializationTest {
|
||||
@Test
|
||||
public void all() {
|
||||
StdArrangementSettings settings = new StdArrangementSettings();
|
||||
settings.addGrouping(new ArrangementGroupingRule(ArrangementGroupingType.OVERRIDDEN_METHODS, ArrangementEntryOrderType.BY_NAME));
|
||||
ArrangementAtomMatchCondition condition = new ArrangementAtomMatchCondition(ArrangementSettingType.TYPE, ArrangementEntryType.FIELD);
|
||||
settings.addRule(new StdArrangementMatchRule(new StdArrangementEntryMatcher(condition), ArrangementEntryOrderType.BY_NAME));
|
||||
settings.addGrouping(new ArrangementGroupingRule(OVERRIDDEN_METHODS, BY_NAME));
|
||||
ArrangementAtomMatchCondition condition = new ArrangementAtomMatchCondition(FIELD);
|
||||
settings.addRule(new StdArrangementMatchRule(new StdArrangementEntryMatcher(condition), BY_NAME));
|
||||
|
||||
Element holder = new Element("holder");
|
||||
ArrangementSettingsSerializer instance = DefaultArrangementSettingsSerializer.INSTANCE;
|
||||
|
||||
+34
-35
@@ -16,24 +16,23 @@
|
||||
package com.intellij.psi.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.openapi.util.Comparing;
|
||||
import com.intellij.psi.codeStyle.arrangement.DefaultArrangementSettingsSerializer;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementCompositeMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jdom.Element;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.junit.Test;
|
||||
|
||||
import java.util.EnumSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType.CLASS;
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType.FIELD;
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType.METHOD;
|
||||
import static com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier.*;
|
||||
import static com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType.MODIFIER;
|
||||
import static com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType.NAME;
|
||||
import static com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType.TYPE;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.EntryType.*;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.General.*;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Modifier.*;
|
||||
import static org.junit.Assert.*;
|
||||
|
||||
/**
|
||||
@@ -42,62 +41,63 @@ import static org.junit.Assert.*;
|
||||
*/
|
||||
public class DefaultArrangementEntryMatcherSerializerTest {
|
||||
|
||||
private final DefaultArrangementEntryMatcherSerializer mySerializer = new DefaultArrangementEntryMatcherSerializer();
|
||||
private final DefaultArrangementEntryMatcherSerializer mySerializer =
|
||||
new DefaultArrangementEntryMatcherSerializer(DefaultArrangementSettingsSerializer.Mixin.NULL);
|
||||
|
||||
@Test
|
||||
public void simpleMatchers() {
|
||||
doTest(new ArrangementAtomMatchCondition(TYPE, CLASS));
|
||||
doTest(new ArrangementAtomMatchCondition(MODIFIER, PRIVATE));
|
||||
doTest(new ArrangementAtomMatchCondition(CLASS));
|
||||
doTest(new ArrangementAtomMatchCondition(PRIVATE));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void compositeMatchers() {
|
||||
ArrangementCompositeMatchCondition condition = new ArrangementCompositeMatchCondition();
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(TYPE, METHOD));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(MODIFIER, SYNCHRONIZED));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(METHOD));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(SYNCHRONIZED));
|
||||
doTest(condition);
|
||||
|
||||
|
||||
condition = new ArrangementCompositeMatchCondition();
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(TYPE, FIELD));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(MODIFIER, PUBLIC));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(MODIFIER, STATIC));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(MODIFIER, FINAL));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(FIELD));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(PUBLIC));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(STATIC));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(FINAL));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void conditionsOrder() {
|
||||
// Inspired by IDEA-91826.
|
||||
ArrangementCompositeMatchCondition condition = new ArrangementCompositeMatchCondition();
|
||||
ArrangementEntryType typeToPreserve = FIELD;
|
||||
Set<ArrangementModifier> modifiersToPreserve = EnumSet.of(PUBLIC, STATIC, FINAL);
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(TYPE, typeToPreserve));
|
||||
for (ArrangementModifier modifier : modifiersToPreserve) {
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(MODIFIER, modifier));
|
||||
ArrangementSettingsToken typeToPreserve = FIELD;
|
||||
Set<ArrangementSettingsToken> modifiersToPreserve = ContainerUtilRt.newHashSet(PUBLIC, STATIC, FINAL);
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(typeToPreserve, typeToPreserve));
|
||||
for (ArrangementSettingsToken modifier : modifiersToPreserve) {
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(modifier, modifier));
|
||||
}
|
||||
Element element = mySerializer.serialize(new StdArrangementEntryMatcher(condition));
|
||||
assertNotNull(element);
|
||||
|
||||
|
||||
// Change hash-container data distribution at the composite condition.
|
||||
for (ArrangementEntryType type : ArrangementEntryType.values()) {
|
||||
for (ArrangementSettingsToken type : StdArrangementTokens.EntryType.values()) {
|
||||
if (type != typeToPreserve) {
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(TYPE, type));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(type, type));
|
||||
}
|
||||
}
|
||||
for (ArrangementModifier modifier : values()) {
|
||||
for (ArrangementSettingsToken modifier : StdArrangementTokens.Modifier.values()) {
|
||||
if (!modifiersToPreserve.contains(modifier)) {
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(MODIFIER, modifier));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(modifier, modifier));
|
||||
}
|
||||
}
|
||||
|
||||
// Revert state to the initial one.
|
||||
for (ArrangementEntryType type : ArrangementEntryType.values()) {
|
||||
for (ArrangementSettingsToken type : StdArrangementTokens.EntryType.values()) {
|
||||
if (type != typeToPreserve) {
|
||||
condition.removeOperand(new ArrangementAtomMatchCondition(TYPE, type));
|
||||
condition.removeOperand(new ArrangementAtomMatchCondition(type, type));
|
||||
}
|
||||
}
|
||||
for (ArrangementModifier modifier : values()) {
|
||||
for (ArrangementSettingsToken modifier : StdArrangementTokens.Modifier.values()) {
|
||||
if (!modifiersToPreserve.contains(modifier)) {
|
||||
condition.removeOperand(new ArrangementAtomMatchCondition(MODIFIER, modifier));
|
||||
condition.removeOperand(new ArrangementAtomMatchCondition(modifier, modifier));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -116,8 +116,8 @@ public class DefaultArrangementEntryMatcherSerializerTest {
|
||||
@Test
|
||||
public void compositeConditionWithName() {
|
||||
ArrangementCompositeMatchCondition condition = new ArrangementCompositeMatchCondition();
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(TYPE, METHOD));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(MODIFIER, SYNCHRONIZED));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(METHOD));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(SYNCHRONIZED));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(NAME, ("get*")));
|
||||
doTest(condition);
|
||||
}
|
||||
@@ -148,7 +148,6 @@ public class DefaultArrangementEntryMatcherSerializerTest {
|
||||
assertNotNull(String.format("Can't serialize match condition '%s'", condition), element);
|
||||
ArrangementEntryMatcher matcher = mySerializer.deserialize(element);
|
||||
assertNotNull(matcher);
|
||||
assertTrue(matcher instanceof StdArrangementEntryMatcher);
|
||||
assertEquals(condition, ((StdArrangementEntryMatcher)matcher).getCondition());
|
||||
}
|
||||
}
|
||||
|
||||
+25
-26
@@ -15,25 +15,24 @@
|
||||
*/
|
||||
package com.intellij.psi.codeStyle.arrangement.match;
|
||||
|
||||
import static org.junit.Assert.*;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.ModifierAwareArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.TypeAwareArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementCompositeMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jmock.Expectations;
|
||||
import org.junit.Test;
|
||||
import org.junit.Before;
|
||||
import org.junit.After;
|
||||
import org.junit.runner.RunWith;
|
||||
import org.jmock.Mockery;
|
||||
import org.jmock.integration.junit4.JMock;
|
||||
import org.jmock.integration.junit4.JUnit4Mockery;
|
||||
import org.jmock.Mockery;
|
||||
import org.jmock.lib.legacy.ClassImposteriser;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
|
||||
import java.util.EnumSet;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.EntryType.*;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Modifier.*;
|
||||
import static org.junit.Assert.*;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
@@ -58,7 +57,7 @@ public class StandardArrangementEntryMatcherTest {
|
||||
|
||||
@Test
|
||||
public void atomCondition() {
|
||||
ArrangementAtomMatchCondition condition = new ArrangementAtomMatchCondition(ArrangementSettingType.TYPE, ArrangementEntryType.FIELD);
|
||||
ArrangementAtomMatchCondition condition = new ArrangementAtomMatchCondition(FIELD);
|
||||
|
||||
StdArrangementEntryMatcher matcher = new StdArrangementEntryMatcher(condition);
|
||||
assertEquals(condition, matcher.getCondition());
|
||||
@@ -67,9 +66,9 @@ public class StandardArrangementEntryMatcherTest {
|
||||
final TypeAwareArrangementEntry classEntry = myMockery.mock(TypeAwareArrangementEntry.class, "class");
|
||||
final ModifierAwareArrangementEntry publicEntry = myMockery.mock(ModifierAwareArrangementEntry.class, "public");
|
||||
myMockery.checking(new Expectations() {{
|
||||
allowing(fieldEntry).getTypes(); will(returnValue(EnumSet.of(ArrangementEntryType.FIELD)));
|
||||
allowing(classEntry).getTypes(); will(returnValue(EnumSet.of(ArrangementEntryType.CLASS)));
|
||||
allowing(publicEntry).getModifiers(); will(returnValue(EnumSet.of(ArrangementModifier.PUBLIC)));
|
||||
allowing(fieldEntry).getTypes(); will(returnValue(ContainerUtilRt.newHashSet(FIELD)));
|
||||
allowing(classEntry).getTypes(); will(returnValue(ContainerUtilRt.newHashSet(CLASS)));
|
||||
allowing(publicEntry).getModifiers(); will(returnValue(ContainerUtilRt.newHashSet(PUBLIC)));
|
||||
}});
|
||||
|
||||
assertTrue(matcher.isMatched(fieldEntry));
|
||||
@@ -80,8 +79,8 @@ public class StandardArrangementEntryMatcherTest {
|
||||
@Test
|
||||
public void compositeAndCondition() {
|
||||
ArrangementCompositeMatchCondition condition = new ArrangementCompositeMatchCondition();
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(ArrangementSettingType.TYPE, ArrangementEntryType.FIELD));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(ArrangementSettingType.MODIFIER, ArrangementModifier.PUBLIC));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(FIELD));
|
||||
condition.addOperand(new ArrangementAtomMatchCondition(PUBLIC));
|
||||
|
||||
StdArrangementEntryMatcher matcher = new StdArrangementEntryMatcher(condition);
|
||||
assertEquals(condition, matcher.getCondition());
|
||||
@@ -93,21 +92,21 @@ public class StandardArrangementEntryMatcherTest {
|
||||
final TypeAndModifierAware publicFieldEntry = myMockery.mock(TypeAndModifierAware.class, "public field");
|
||||
final TypeAndModifierAware publicStaticFieldEntry = myMockery.mock(TypeAndModifierAware.class, "public static field");
|
||||
myMockery.checking(new Expectations() {{
|
||||
allowing(fieldEntry).getTypes(); will(returnValue(EnumSet.of(ArrangementEntryType.FIELD)));
|
||||
allowing(fieldEntry).getTypes(); will(returnValue(ContainerUtilRt.newHashSet(FIELD)));
|
||||
|
||||
allowing(publicEntry).getModifiers(); will(returnValue(EnumSet.of(ArrangementModifier.PUBLIC)));
|
||||
allowing(publicEntry).getModifiers(); will(returnValue(ContainerUtilRt.newHashSet(PUBLIC)));
|
||||
|
||||
allowing(privateFieldEntry).getTypes(); will(returnValue(EnumSet.of(ArrangementEntryType.FIELD)));
|
||||
allowing(privateFieldEntry).getModifiers(); will(returnValue(EnumSet.of(ArrangementModifier.PRIVATE)));
|
||||
allowing(privateFieldEntry).getTypes(); will(returnValue(ContainerUtilRt.newHashSet(FIELD)));
|
||||
allowing(privateFieldEntry).getModifiers(); will(returnValue(ContainerUtilRt.newHashSet(PRIVATE)));
|
||||
|
||||
allowing(publicMethodEntry).getTypes(); will(returnValue(EnumSet.of(ArrangementEntryType.METHOD)));
|
||||
allowing(publicMethodEntry).getModifiers(); will(returnValue(EnumSet.of(ArrangementModifier.PUBLIC)));
|
||||
allowing(publicMethodEntry).getTypes(); will(returnValue(ContainerUtilRt.newHashSet(METHOD)));
|
||||
allowing(publicMethodEntry).getModifiers(); will(returnValue(ContainerUtilRt.newHashSet(PUBLIC)));
|
||||
|
||||
allowing(publicFieldEntry).getTypes(); will(returnValue(EnumSet.of(ArrangementEntryType.FIELD)));
|
||||
allowing(publicFieldEntry).getModifiers(); will(returnValue(EnumSet.of(ArrangementModifier.PUBLIC)));
|
||||
allowing(publicFieldEntry).getTypes(); will(returnValue(ContainerUtilRt.newHashSet(FIELD)));
|
||||
allowing(publicFieldEntry).getModifiers(); will(returnValue(ContainerUtilRt.newHashSet(PUBLIC)));
|
||||
|
||||
allowing(publicStaticFieldEntry).getTypes(); will(returnValue(EnumSet.of(ArrangementEntryType.FIELD)));
|
||||
allowing(publicStaticFieldEntry).getModifiers(); will(returnValue(EnumSet.of(ArrangementModifier.PUBLIC, ArrangementModifier.STATIC)));
|
||||
allowing(publicStaticFieldEntry).getTypes(); will(returnValue(ContainerUtilRt.newHashSet(FIELD)));
|
||||
allowing(publicStaticFieldEntry).getModifiers(); will(returnValue(ContainerUtilRt.newHashSet(PUBLIC, STATIC)));
|
||||
}});
|
||||
|
||||
assertFalse(matcher.isMatched(fieldEntry));
|
||||
|
||||
-167
@@ -1,167 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.application.options.codeStyle.arrangement;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.ArrangementConfigUtil;
|
||||
import com.intellij.openapi.application.ApplicationBundle;
|
||||
import com.intellij.openapi.editor.markup.TextAttributes;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsRepresentationAware;
|
||||
import com.intellij.ui.SimpleColoredComponent;
|
||||
import com.intellij.ui.SimpleTextAttributes;
|
||||
import gnu.trove.TObjectIntHashMap;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* Encapsulates various functionality related to showing arrangement nodes to end-users.
|
||||
* <p/>
|
||||
* Thread-safe.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/9/12 3:02 PM
|
||||
*/
|
||||
@SuppressWarnings("MethodMayBeStatic")
|
||||
public class ArrangementNodeDisplayManager {
|
||||
|
||||
@NotNull private final TObjectIntHashMap<ArrangementSettingType> myMaxWidths = new TObjectIntHashMap<ArrangementSettingType>();
|
||||
|
||||
@NotNull private final ArrangementStandardSettingsAware myFilter;
|
||||
@NotNull private final ArrangementColorsProvider myColorsProvider;
|
||||
@NotNull private ArrangementStandardSettingsRepresentationAware myRepresentationManager;
|
||||
|
||||
public ArrangementNodeDisplayManager(@NotNull ArrangementStandardSettingsAware filter,
|
||||
@NotNull ArrangementColorsProvider colorsProvider,
|
||||
@NotNull ArrangementStandardSettingsRepresentationAware representationManager)
|
||||
{
|
||||
myFilter = filter;
|
||||
myColorsProvider = colorsProvider;
|
||||
myRepresentationManager = representationManager;
|
||||
refreshMaxWidths();
|
||||
}
|
||||
|
||||
private void refreshMaxWidths() {
|
||||
Map<ArrangementSettingType, Set<?>> map = ArrangementConfigUtil.buildAvailableConditions(myFilter, null);
|
||||
for (Map.Entry<ArrangementSettingType, Set<?>> entry : map.entrySet()) {
|
||||
myMaxWidths.put(entry.getKey(), maxWidth(entry.getKey(), entry.getValue()));
|
||||
}
|
||||
}
|
||||
|
||||
private int maxWidth(@NotNull ArrangementSettingType type, @NotNull Collection<?> values) {
|
||||
SimpleColoredComponent renderer = new SimpleColoredComponent();
|
||||
|
||||
int result = 0;
|
||||
for (Object value : values) {
|
||||
renderer.clear();
|
||||
renderer.append(getDisplayValue(value), SimpleTextAttributes.fromTextAttributes(myColorsProvider.getTextAttributes(type, true)));
|
||||
result = Math.max(result, renderer.getPreferredSize().width);
|
||||
|
||||
renderer.clear();
|
||||
renderer.append(getDisplayValue(value), SimpleTextAttributes.fromTextAttributes(myColorsProvider.getTextAttributes(type, false)));
|
||||
result = Math.max(result, renderer.getPreferredSize().width);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public String getDisplayValue(@NotNull ArrangementAtomMatchCondition setting) {
|
||||
return getDisplayValue(setting.getValue());
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public String getDisplayLabel(@NotNull ArrangementSettingType type) {
|
||||
switch (type) {
|
||||
case TYPE:
|
||||
return ApplicationBundle.message("arrangement.text.type");
|
||||
case MODIFIER:
|
||||
return ApplicationBundle.message("arrangement.text.modifier");
|
||||
case NAME:
|
||||
return ApplicationBundle.message("arrangement.text.name");
|
||||
}
|
||||
return type.toString().toLowerCase();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public String getDisplayValue(@NotNull Object value) {
|
||||
if (value instanceof ArrangementEntryType) {
|
||||
return myRepresentationManager.getDisplayValue((ArrangementEntryType)value);
|
||||
}
|
||||
else if (value instanceof ArrangementModifier) {
|
||||
return myRepresentationManager.getDisplayValue((ArrangementModifier)value);
|
||||
}
|
||||
else if (value instanceof ArrangementGroupingType) {
|
||||
return myRepresentationManager.getDisplayValue((ArrangementGroupingType)value);
|
||||
}
|
||||
else if (value instanceof ArrangementEntryOrderType) {
|
||||
return myRepresentationManager.getDisplayValue((ArrangementEntryOrderType)value);
|
||||
}
|
||||
else {
|
||||
return value.toString();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param type target condition type
|
||||
* @return max width in pixels for the condition value of the given type if any;
|
||||
* <code>'-1'</code> as an indication that no max width limit exists for the condition value of the given type
|
||||
*/
|
||||
public int getMaxWidth(@NotNull ArrangementSettingType type) {
|
||||
if (type == ArrangementSettingType.NAME) {
|
||||
return -1;
|
||||
}
|
||||
return myMaxWidths.get(type);
|
||||
}
|
||||
|
||||
public int getMaxWidth(@NotNull ArrangementEntryOrderType... orderTypes) {
|
||||
SimpleColoredComponent renderer = new SimpleColoredComponent();
|
||||
int result = 0;
|
||||
for (ArrangementEntryOrderType type : orderTypes) {
|
||||
renderer.clear();
|
||||
TextAttributes attributes = myColorsProvider.getTextAttributes(ArrangementSettingType.ORDER, true);
|
||||
renderer.append(getDisplayValue(type), SimpleTextAttributes.fromTextAttributes(attributes));
|
||||
result = Math.max(result, renderer.getPreferredSize().width);
|
||||
|
||||
renderer.clear();
|
||||
attributes = myColorsProvider.getTextAttributes(ArrangementSettingType.ORDER, false);
|
||||
renderer.append(getDisplayValue(type), SimpleTextAttributes.fromTextAttributes(attributes));
|
||||
result = Math.max(result, renderer.getPreferredSize().width);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Asks current manager to sort in-place given arrangement condition ids ('field', 'class', 'method', 'public', 'static', 'final' etc).
|
||||
*
|
||||
* @param ids target ids to use
|
||||
* @param <T> id type
|
||||
* @return sorted ids to use (the given list)
|
||||
*/
|
||||
@NotNull
|
||||
public <T> List<T> sort(@NotNull Collection<T> ids) {
|
||||
return myRepresentationManager.sort(ids);
|
||||
}
|
||||
}
|
||||
+12
-21
@@ -32,13 +32,12 @@ import com.intellij.openapi.util.Comparing;
|
||||
import com.intellij.psi.codeStyle.CodeStyleSettings;
|
||||
import com.intellij.psi.codeStyle.CommonCodeStyleSettings;
|
||||
import com.intellij.psi.codeStyle.arrangement.Rearranger;
|
||||
import com.intellij.psi.codeStyle.arrangement.StdArrangementSettings;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementColorsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsRepresentationAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.DefaultArrangementSettingsRepresentationManager;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementColorsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsManager;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementSettings;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -78,17 +77,10 @@ public abstract class ArrangementSettingsPanel extends CodeStyleAbstractPanel {
|
||||
colorsProvider = new ArrangementColorsProviderImpl(null);
|
||||
}
|
||||
|
||||
ArrangementStandardSettingsRepresentationAware representationManager = DefaultArrangementSettingsRepresentationManager.INSTANCE;
|
||||
if (mySettingsAware instanceof ArrangementStandardSettingsRepresentationAware) {
|
||||
representationManager = (ArrangementStandardSettingsRepresentationAware)mySettingsAware;
|
||||
}
|
||||
ArrangementStandardSettingsManager settingsManager = new ArrangementStandardSettingsManager(mySettingsAware, colorsProvider);
|
||||
|
||||
final ArrangementNodeDisplayManager displayManager = new ArrangementNodeDisplayManager(
|
||||
mySettingsAware, colorsProvider, representationManager
|
||||
);
|
||||
|
||||
myGroupingRulesPanel = new ArrangementGroupingRulesPanel(displayManager, mySettingsAware);
|
||||
myMatchingRulesPanel = new ArrangementMatchingRulesPanel(displayManager, colorsProvider, mySettingsAware);
|
||||
myGroupingRulesPanel = new ArrangementGroupingRulesPanel(settingsManager, colorsProvider);
|
||||
myMatchingRulesPanel = new ArrangementMatchingRulesPanel(settingsManager, colorsProvider);
|
||||
|
||||
myContent.add(myGroupingRulesPanel, new GridBag().coverLine().fillCellHorizontally().weightx(1));
|
||||
myContent.add(myMatchingRulesPanel, new GridBag().fillCell().weightx(1).weighty(1));
|
||||
@@ -99,11 +91,6 @@ public abstract class ArrangementSettingsPanel extends CodeStyleAbstractPanel {
|
||||
myMatchingRulesPanel.putClientProperty(AnAction.ourClientProperty, ContainerUtilRt.newArrayList(removeRuleAction));
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected JPanel getGroupingRulesPanel() {
|
||||
return myGroupingRulesPanel;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public JComponent getPanel() {
|
||||
@@ -146,7 +133,11 @@ public abstract class ArrangementSettingsPanel extends CodeStyleAbstractPanel {
|
||||
myMatchingRulesPanel.setRules(null);
|
||||
}
|
||||
else {
|
||||
myGroupingRulesPanel.setRules(new ArrayList<ArrangementGroupingRule>(s.getGroupings()));
|
||||
List<ArrangementGroupingRule> groupings = s.getGroupings();
|
||||
myGroupingRulesPanel.setVisible(!groupings.isEmpty());
|
||||
if (!groupings.isEmpty()) {
|
||||
myGroupingRulesPanel.setRules(ContainerUtilRt.newArrayList(groupings));
|
||||
}
|
||||
myMatchingRulesPanel.setRules(copy(s.getRules()));
|
||||
}
|
||||
}
|
||||
|
||||
+2
-3
@@ -15,7 +15,6 @@
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.action;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchingRulesControl;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchingRulesModel;
|
||||
import com.intellij.openapi.actionSystem.AnAction;
|
||||
@@ -35,7 +34,7 @@ public abstract class AbstractMoveArrangementRuleAction extends AnAction impleme
|
||||
|
||||
@Override
|
||||
public void update(AnActionEvent e) {
|
||||
ArrangementMatchingRulesControl control = ArrangementConstants.MATCHING_RULES_CONTROL_KEY.getData(e.getDataContext());
|
||||
ArrangementMatchingRulesControl control = ArrangementMatchingRulesControl.KEY.getData(e.getDataContext());
|
||||
if (control == null) {
|
||||
e.getPresentation().setEnabled(false);
|
||||
return;
|
||||
@@ -54,7 +53,7 @@ public abstract class AbstractMoveArrangementRuleAction extends AnAction impleme
|
||||
|
||||
@Override
|
||||
public void actionPerformed(AnActionEvent e) {
|
||||
final ArrangementMatchingRulesControl control = ArrangementConstants.MATCHING_RULES_CONTROL_KEY.getData(e.getDataContext());
|
||||
final ArrangementMatchingRulesControl control = ArrangementMatchingRulesControl.KEY.getData(e.getDataContext());
|
||||
if (control == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
+1
-2
@@ -15,7 +15,6 @@
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.action;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchingRulesControl;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchingRulesModel;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.EmptyArrangementRuleComponent;
|
||||
@@ -45,7 +44,7 @@ public class AddArrangementRuleAction extends AnAction implements DumbAware {
|
||||
|
||||
@Override
|
||||
public void actionPerformed(AnActionEvent e) {
|
||||
ArrangementMatchingRulesControl control = ArrangementConstants.MATCHING_RULES_CONTROL_KEY.getData(e.getDataContext());
|
||||
ArrangementMatchingRulesControl control = ArrangementMatchingRulesControl.KEY.getData(e.getDataContext());
|
||||
if (control == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
+2
-3
@@ -15,7 +15,6 @@
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.action;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchingRulesControl;
|
||||
import com.intellij.openapi.actionSystem.AnAction;
|
||||
import com.intellij.openapi.actionSystem.AnActionEvent;
|
||||
@@ -37,13 +36,13 @@ public class EditArrangementRuleAction extends AnAction implements DumbAware, To
|
||||
|
||||
@Override
|
||||
public void update(AnActionEvent e) {
|
||||
ArrangementMatchingRulesControl control = ArrangementConstants.MATCHING_RULES_CONTROL_KEY.getData(e.getDataContext());
|
||||
ArrangementMatchingRulesControl control = ArrangementMatchingRulesControl.KEY.getData(e.getDataContext());
|
||||
e.getPresentation().setEnabled(control != null && control.getSelectedModelRows().size() == 1);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void actionPerformed(AnActionEvent e) {
|
||||
ArrangementMatchingRulesControl control = ArrangementConstants.MATCHING_RULES_CONTROL_KEY.getData(e.getDataContext());
|
||||
ArrangementMatchingRulesControl control = ArrangementMatchingRulesControl.KEY.getData(e.getDataContext());
|
||||
if (control == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
+2
-3
@@ -15,7 +15,6 @@
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.action;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.group.ArrangementGroupingRulesControl;
|
||||
import com.intellij.openapi.actionSystem.AnAction;
|
||||
import com.intellij.openapi.actionSystem.AnActionEvent;
|
||||
@@ -37,7 +36,7 @@ public class MoveArrangementGroupingRuleDownAction extends AnAction implements D
|
||||
|
||||
@Override
|
||||
public void update(AnActionEvent e) {
|
||||
ArrangementGroupingRulesControl control = ArrangementConstants.GROUPING_RULES_CONTROL_KEY.getData(e.getDataContext());
|
||||
ArrangementGroupingRulesControl control = ArrangementGroupingRulesControl.KEY.getData(e.getDataContext());
|
||||
if (control == null) {
|
||||
e.getPresentation().setEnabled(false);
|
||||
return;
|
||||
@@ -49,7 +48,7 @@ public class MoveArrangementGroupingRuleDownAction extends AnAction implements D
|
||||
|
||||
@Override
|
||||
public void actionPerformed(AnActionEvent e) {
|
||||
ArrangementGroupingRulesControl control = ArrangementConstants.GROUPING_RULES_CONTROL_KEY.getData(e.getDataContext());
|
||||
ArrangementGroupingRulesControl control = ArrangementGroupingRulesControl.KEY.getData(e.getDataContext());
|
||||
if (control == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
+2
-3
@@ -15,7 +15,6 @@
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.action;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.group.ArrangementGroupingRulesControl;
|
||||
import com.intellij.openapi.actionSystem.AnAction;
|
||||
import com.intellij.openapi.actionSystem.AnActionEvent;
|
||||
@@ -37,7 +36,7 @@ public class MoveArrangementGroupingRuleUpAction extends AnAction implements Dum
|
||||
|
||||
@Override
|
||||
public void update(AnActionEvent e) {
|
||||
ArrangementGroupingRulesControl control = ArrangementConstants.GROUPING_RULES_CONTROL_KEY.getData(e.getDataContext());
|
||||
ArrangementGroupingRulesControl control = ArrangementGroupingRulesControl.KEY.getData(e.getDataContext());
|
||||
if (control == null) {
|
||||
e.getPresentation().setEnabled(false);
|
||||
return;
|
||||
@@ -49,7 +48,7 @@ public class MoveArrangementGroupingRuleUpAction extends AnAction implements Dum
|
||||
|
||||
@Override
|
||||
public void actionPerformed(AnActionEvent e) {
|
||||
ArrangementGroupingRulesControl control = ArrangementConstants.GROUPING_RULES_CONTROL_KEY.getData(e.getDataContext());
|
||||
ArrangementGroupingRulesControl control = ArrangementGroupingRulesControl.KEY.getData(e.getDataContext());
|
||||
if (control == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
+3
-4
@@ -15,7 +15,6 @@
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.action;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchingRulesControl;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchingRulesModel;
|
||||
import com.intellij.icons.AllIcons;
|
||||
@@ -38,14 +37,14 @@ public class RemoveArrangementRuleAction extends AnAction {
|
||||
|
||||
@Override
|
||||
public void update(AnActionEvent e) {
|
||||
ArrangementMatchingRulesControl control = ArrangementConstants.MATCHING_RULES_CONTROL_KEY.getData(e.getDataContext());
|
||||
e.getPresentation().setEnabled(control != null && !control.getSelectedModelRows().isEmpty());
|
||||
ArrangementMatchingRulesControl control = ArrangementMatchingRulesControl.KEY.getData(e.getDataContext());
|
||||
e.getPresentation().setEnabled(control != null && !control.isEditing() && !control.getSelectedModelRows().isEmpty());
|
||||
e.getPresentation().setIcon(SystemInfoRt.isMac ? AllIcons.ToolbarDecorator.Mac.Remove : AllIcons.ToolbarDecorator.Remove);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void actionPerformed(AnActionEvent e) {
|
||||
ArrangementMatchingRulesControl control = ArrangementConstants.MATCHING_RULES_CONTROL_KEY.getData(e.getDataContext());
|
||||
ArrangementMatchingRulesControl control = ArrangementMatchingRulesControl.KEY.getData(e.getDataContext());
|
||||
if (control == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
+79
-72
@@ -16,17 +16,16 @@
|
||||
package com.intellij.application.options.codeStyle.arrangement.color;
|
||||
|
||||
import com.intellij.openapi.editor.colors.EditorColorsManager;
|
||||
import com.intellij.openapi.editor.colors.EditorColorsScheme;
|
||||
import com.intellij.openapi.editor.markup.TextAttributes;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementColorsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementColorsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.ui.GroupedElementsRenderer;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.awt.*;
|
||||
import java.util.EnumMap;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
@@ -35,34 +34,94 @@ import java.util.Map;
|
||||
*/
|
||||
public class ArrangementColorsProviderImpl implements ArrangementColorsProvider {
|
||||
|
||||
@NotNull private final Map<ArrangementSettingsToken, TextAttributes> myNormalAttributesCache = ContainerUtilRt.newHashMap();
|
||||
@NotNull private final Map<ArrangementSettingsToken, TextAttributes> mySelectedAttributesCache = ContainerUtilRt.newHashMap();
|
||||
|
||||
@NotNull private final TextAttributes myDefaultNormalAttributes = new TextAttributes();
|
||||
@NotNull private final TextAttributes myDefaultSelectedAttributes = new TextAttributes();
|
||||
@NotNull private final Color myDefaultNormalBorderColor;
|
||||
@NotNull private final Color myDefaultSelectedBorderColor;
|
||||
|
||||
@Nullable private final ArrangementColorsAware myColorsAware;
|
||||
|
||||
@NotNull private final Map<ArrangementSettingType, TextAttributes> myTextAttributes
|
||||
= new EnumMap<ArrangementSettingType, TextAttributes>(ArrangementSettingType.class);
|
||||
@NotNull private final Map<ArrangementSettingType, TextAttributes> mySelectedTextAttributes
|
||||
= new EnumMap<ArrangementSettingType, TextAttributes>(ArrangementSettingType.class);
|
||||
|
||||
@NotNull private Color myBorderColor;
|
||||
@NotNull private Color mySelectedBorderColor;
|
||||
@Nullable private Color myCachedNormalBorderColor;
|
||||
@Nullable private Color myCachedSelectedBorderColor;
|
||||
|
||||
public ArrangementColorsProviderImpl(@Nullable ArrangementColorsAware colorsAware) {
|
||||
myColorsAware = colorsAware;
|
||||
applyDefaultColors();
|
||||
if (colorsAware != null) {
|
||||
applyCustomColors(colorsAware);
|
||||
|
||||
// Default settings.
|
||||
myDefaultNormalAttributes.setForegroundColor(UIUtil.getTreeTextForeground());
|
||||
myDefaultNormalAttributes.setBackgroundColor(UIUtil.getPanelBackground());
|
||||
myDefaultSelectedAttributes.setForegroundColor(UIUtil.getTreeSelectionForeground());
|
||||
myDefaultSelectedAttributes.setBackgroundColor(UIUtil.getTreeSelectionBackground());
|
||||
myDefaultNormalBorderColor = UIUtil.getBorderColor();
|
||||
Color selectionBorderColor = UIUtil.getTreeSelectionBorderColor();
|
||||
if (selectionBorderColor == null) {
|
||||
selectionBorderColor = GroupedElementsRenderer.SELECTED_FRAME_FOREGROUND;
|
||||
}
|
||||
myDefaultSelectedBorderColor = selectionBorderColor;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Color getBorderColor(boolean selected) {
|
||||
return selected ? mySelectedBorderColor : myBorderColor;
|
||||
final Color cached;
|
||||
if (selected) {
|
||||
cached = myCachedSelectedBorderColor;
|
||||
}
|
||||
else {
|
||||
cached = myCachedNormalBorderColor;
|
||||
}
|
||||
if (cached != null) {
|
||||
return cached;
|
||||
}
|
||||
|
||||
Color result = null;
|
||||
if (myColorsAware != null) {
|
||||
result = myColorsAware.getBorderColor(EditorColorsManager.getInstance().getGlobalScheme(), selected);
|
||||
}
|
||||
if (result == null) {
|
||||
result = selected ? myDefaultSelectedBorderColor : myDefaultNormalBorderColor;
|
||||
}
|
||||
if (selected) {
|
||||
myCachedSelectedBorderColor = result;
|
||||
}
|
||||
else {
|
||||
myCachedNormalBorderColor = result;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public TextAttributes getTextAttributes(@NotNull ArrangementSettingType type, boolean selected) {
|
||||
return selected ? mySelectedTextAttributes.get(type) : myTextAttributes.get(type);
|
||||
public TextAttributes getTextAttributes(@NotNull ArrangementSettingsToken token, boolean selected) {
|
||||
final TextAttributes cached;
|
||||
if (selected) {
|
||||
cached = mySelectedAttributesCache.get(token);
|
||||
}
|
||||
else {
|
||||
cached = myNormalAttributesCache.get(token);
|
||||
}
|
||||
if (cached != null) {
|
||||
return cached;
|
||||
}
|
||||
|
||||
TextAttributes result = null;
|
||||
if (myColorsAware != null) {
|
||||
result = myColorsAware.getTextAttributes(EditorColorsManager.getInstance().getGlobalScheme(), token, selected);
|
||||
}
|
||||
if (result == null) {
|
||||
result = selected ? myDefaultSelectedAttributes : myDefaultNormalAttributes;
|
||||
}
|
||||
if (selected) {
|
||||
mySelectedAttributesCache.put(token, result);
|
||||
}
|
||||
else {
|
||||
myNormalAttributesCache.put(token, result);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -72,61 +131,9 @@ public class ArrangementColorsProviderImpl implements ArrangementColorsProvider
|
||||
* accordingly.
|
||||
*/
|
||||
public void refresh() {
|
||||
if (myColorsAware == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
myTextAttributes.clear();
|
||||
mySelectedTextAttributes.clear();
|
||||
|
||||
applyDefaultColors();
|
||||
applyCustomColors(myColorsAware);
|
||||
}
|
||||
|
||||
private void applyDefaultColors() {
|
||||
TextAttributes normalTextAttributes = new TextAttributes();
|
||||
normalTextAttributes.setForegroundColor(UIUtil.getTreeTextForeground());
|
||||
normalTextAttributes.setBackgroundColor(UIUtil.getPanelBackground());
|
||||
|
||||
TextAttributes selectedTextAttributes = new TextAttributes();
|
||||
selectedTextAttributes.setForegroundColor(UIUtil.getTreeSelectionForeground());
|
||||
selectedTextAttributes.setBackgroundColor(UIUtil.getTreeSelectionBackground());
|
||||
|
||||
for (ArrangementSettingType type : ArrangementSettingType.values()) {
|
||||
myTextAttributes.put(type, normalTextAttributes);
|
||||
mySelectedTextAttributes.put(type, selectedTextAttributes);
|
||||
}
|
||||
|
||||
myBorderColor = UIUtil.getBorderColor();
|
||||
Color selectionBorderColor = UIUtil.getTreeSelectionBorderColor();
|
||||
if (selectionBorderColor == null) {
|
||||
selectionBorderColor = GroupedElementsRenderer.SELECTED_FRAME_FOREGROUND;
|
||||
}
|
||||
mySelectedBorderColor = selectionBorderColor;
|
||||
}
|
||||
|
||||
private void applyCustomColors(@NotNull ArrangementColorsAware colorsAware) {
|
||||
EditorColorsScheme scheme = EditorColorsManager.getInstance().getGlobalScheme();
|
||||
for (ArrangementSettingType type : ArrangementSettingType.values()) {
|
||||
TextAttributes textAttributes = colorsAware.getTextAttributes(scheme, type, false);
|
||||
if (textAttributes != null) {
|
||||
myTextAttributes.put(type, textAttributes);
|
||||
}
|
||||
|
||||
TextAttributes selectedTextAttributes = colorsAware.getTextAttributes(scheme, type, true);
|
||||
if (selectedTextAttributes != null) {
|
||||
mySelectedTextAttributes.put(type, selectedTextAttributes);
|
||||
}
|
||||
}
|
||||
|
||||
Color borderColor = colorsAware.getBorderColor(scheme, false);
|
||||
if (borderColor != null) {
|
||||
myBorderColor = borderColor;
|
||||
}
|
||||
|
||||
Color selectedBorderColor = colorsAware.getBorderColor(scheme, true);
|
||||
if (selectedBorderColor != null) {
|
||||
mySelectedBorderColor = selectedBorderColor;
|
||||
if (myColorsAware != null) {
|
||||
myNormalAttributesCache.clear();
|
||||
mySelectedAttributesCache.clear();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+151
@@ -0,0 +1,151 @@
|
||||
/*
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.component;
|
||||
|
||||
import com.intellij.openapi.util.NotNullLazyValue;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementUiComponent;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.awt.event.MouseEvent;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 3/11/13 10:41 AM
|
||||
*/
|
||||
public abstract class AbstractArrangementUiComponent implements ArrangementUiComponent {
|
||||
|
||||
@NotNull private final NotNullLazyValue<JComponent> myComponent = new NotNullLazyValue<JComponent>() {
|
||||
@NotNull
|
||||
@Override
|
||||
protected JComponent compute() {
|
||||
JPanel result = new JPanel(new GridBagLayout()) {
|
||||
@Override
|
||||
protected void paintComponent(Graphics g) {
|
||||
Point point = UIUtil.getLocationOnScreen(this);
|
||||
if (point != null) {
|
||||
Rectangle bounds = getBounds();
|
||||
myScreenBounds = new Rectangle(point.x, point.y, bounds.width, bounds.height);
|
||||
}
|
||||
if (!myEnabled && g instanceof Graphics2D) {
|
||||
((Graphics2D)g).setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER, 0.3f));
|
||||
}
|
||||
super.paintComponent(g);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isFocusOwner() {
|
||||
Component[] components = getComponents();
|
||||
if (components != null) {
|
||||
for (Component component : components) {
|
||||
if (component.isFocusOwner()) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean requestFocusInWindow() {
|
||||
if (getComponentCount() > 0) {
|
||||
return getComponent(0).requestFocusInWindow();
|
||||
}
|
||||
else {
|
||||
return super.requestFocusInWindow();
|
||||
}
|
||||
}
|
||||
};
|
||||
result.setOpaque(false);
|
||||
result.add(doGetUiComponent(), new GridBag().fillCell());
|
||||
return result;
|
||||
}
|
||||
};
|
||||
|
||||
@Nullable private Listener myListener;
|
||||
@Nullable private Rectangle myScreenBounds;
|
||||
|
||||
private boolean myEnabled = true;
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public final JComponent getUiComponent() {
|
||||
return myComponent.getValue();
|
||||
}
|
||||
|
||||
protected abstract JComponent doGetUiComponent();
|
||||
|
||||
public void setListener(@Nullable Listener listener) {
|
||||
myListener = listener;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Rectangle getScreenBounds() {
|
||||
return myScreenBounds;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled() {
|
||||
return myEnabled;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setEnabled(boolean enabled) {
|
||||
myEnabled = enabled;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Rectangle onMouseMove(@NotNull MouseEvent event) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onMouseRelease(@NotNull MouseEvent event) {
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Rectangle onMouseExited() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Rectangle onMouseEntered(@NotNull MouseEvent e) {
|
||||
return null;
|
||||
}
|
||||
|
||||
protected void fireStateChanged() {
|
||||
if (myListener != null) {
|
||||
myListener.stateChanged();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public final void reset() {
|
||||
setEnabled(false);
|
||||
setSelected(false);
|
||||
doReset();
|
||||
}
|
||||
|
||||
protected abstract void doReset();
|
||||
}
|
||||
+70
-23
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2012 JetBrains s.r.o.
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -13,65 +13,77 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.match;
|
||||
package com.intellij.application.options.codeStyle.arrangement.component;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.ArrangementConfigUtil;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchNodeComponentFactory;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.*;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementCompositeMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchConditionVisitor;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementUiComponent;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.awt.event.MouseEvent;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* {@link ArrangementMatchConditionComponent Component} for showing {@link ArrangementCompositeMatchCondition composite nodes}.
|
||||
* {@link ArrangementUiComponent Component} for showing {@link ArrangementCompositeMatchCondition composite nodes}.
|
||||
* <p/>
|
||||
* Not thread-safe.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/8/12 10:51 AM
|
||||
*/
|
||||
public class ArrangementAndMatchConditionComponent extends JPanel implements ArrangementMatchConditionComponent {
|
||||
public class ArrangementAndMatchConditionComponent extends JPanel implements ArrangementUiComponent {
|
||||
|
||||
@NotNull private final List<ArrangementMatchConditionComponent> myComponents = new ArrayList<ArrangementMatchConditionComponent>();
|
||||
@NotNull private final List<ArrangementUiComponent> myComponents = ContainerUtilRt.newArrayList();
|
||||
|
||||
@NotNull private final ArrangementCompositeMatchCondition mySetting;
|
||||
@Nullable private Rectangle myScreenBounds;
|
||||
@Nullable private ArrangementMatchConditionComponent myComponentUnderMouse;
|
||||
@Nullable private ArrangementUiComponent myComponentUnderMouse;
|
||||
|
||||
public ArrangementAndMatchConditionComponent(@NotNull StdArrangementMatchRule rule,
|
||||
@NotNull ArrangementCompositeMatchCondition setting,
|
||||
@NotNull ArrangementMatchNodeComponentFactory factory,
|
||||
@NotNull ArrangementNodeDisplayManager manager)
|
||||
@NotNull ArrangementStandardSettingsManager manager)
|
||||
{
|
||||
mySetting = setting;
|
||||
setOpaque(false);
|
||||
setLayout(new GridBagLayout());
|
||||
final Map<Object, ArrangementMatchCondition> operands = new HashMap<Object, ArrangementMatchCondition>();
|
||||
final Map<ArrangementSettingsToken, ArrangementMatchCondition> operands = ContainerUtilRt.newHashMap();
|
||||
ArrangementMatchConditionVisitor visitor = new ArrangementMatchConditionVisitor() {
|
||||
@Override public void visit(@NotNull ArrangementAtomMatchCondition condition) { operands.put(condition.getValue(), condition); }
|
||||
@Override public void visit(@NotNull ArrangementCompositeMatchCondition condition) { operands.put(condition, condition); }
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementAtomMatchCondition condition) {
|
||||
operands.put(condition.getType(), condition);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementCompositeMatchCondition condition) {
|
||||
assert false;
|
||||
}
|
||||
};
|
||||
for (ArrangementMatchCondition operand : setting.getOperands()) {
|
||||
operand.invite(visitor);
|
||||
}
|
||||
|
||||
List<Object> ordered = manager.sort(operands.keySet());
|
||||
List<ArrangementSettingsToken> ordered = manager.sort(operands.keySet());
|
||||
GridBagConstraints constraints = new GridBag().anchor(GridBagConstraints.EAST).insets(0, 0, 0, ArrangementConstants.HORIZONTAL_GAP);
|
||||
for (Object key : ordered) {
|
||||
for (ArrangementSettingsToken key : ordered) {
|
||||
ArrangementMatchCondition operand = operands.get(key);
|
||||
assert operand != null;
|
||||
ArrangementMatchConditionComponent component = factory.getComponent(operand, rule, true);
|
||||
ArrangementUiComponent component = factory.getComponent(operand, rule, true);
|
||||
myComponents.add(component);
|
||||
JComponent uiComponent = component.getUiComponent();
|
||||
add(uiComponent, constraints);
|
||||
@@ -98,7 +110,7 @@ public class ArrangementAndMatchConditionComponent extends JPanel implements Arr
|
||||
|
||||
@Override
|
||||
public void setSelected(boolean selected) {
|
||||
for (ArrangementMatchConditionComponent component : myComponents) {
|
||||
for (ArrangementUiComponent component : myComponents) {
|
||||
component.setSelected(selected);
|
||||
}
|
||||
}
|
||||
@@ -115,7 +127,7 @@ public class ArrangementAndMatchConditionComponent extends JPanel implements Arr
|
||||
|
||||
@Override
|
||||
public void paint(Graphics g) {
|
||||
Point point = ArrangementConfigUtil.getLocationOnScreen(this);
|
||||
Point point = UIUtil.getLocationOnScreen(this);
|
||||
if (point != null) {
|
||||
Rectangle bounds = getBounds();
|
||||
myScreenBounds = new Rectangle(point.x, point.y, bounds.width, bounds.height);
|
||||
@@ -126,7 +138,7 @@ public class ArrangementAndMatchConditionComponent extends JPanel implements Arr
|
||||
@Override
|
||||
public Rectangle onMouseMove(@NotNull MouseEvent event) {
|
||||
Point location = event.getLocationOnScreen();
|
||||
for (ArrangementMatchConditionComponent component : myComponents) {
|
||||
for (ArrangementUiComponent component : myComponents) {
|
||||
Rectangle bounds = component.getScreenBounds();
|
||||
if (bounds == null || !bounds.contains(location)) {
|
||||
continue;
|
||||
@@ -170,7 +182,7 @@ public class ArrangementAndMatchConditionComponent extends JPanel implements Arr
|
||||
@Override
|
||||
public void onMouseRelease(@NotNull MouseEvent event) {
|
||||
Point location = event.getLocationOnScreen();
|
||||
for (ArrangementMatchConditionComponent component : myComponents) {
|
||||
for (ArrangementUiComponent component : myComponents) {
|
||||
Rectangle bounds = component.getScreenBounds();
|
||||
if (bounds != null && bounds.contains(location)) {
|
||||
component.onMouseRelease(event);
|
||||
@@ -182,7 +194,7 @@ public class ArrangementAndMatchConditionComponent extends JPanel implements Arr
|
||||
@Override
|
||||
public Rectangle onMouseEntered(@NotNull MouseEvent event) {
|
||||
Point location = event.getLocationOnScreen();
|
||||
for (ArrangementMatchConditionComponent component : myComponents) {
|
||||
for (ArrangementUiComponent component : myComponents) {
|
||||
Rectangle bounds = component.getScreenBounds();
|
||||
if (bounds != null && bounds.contains(location)) {
|
||||
myComponentUnderMouse = component;
|
||||
@@ -203,6 +215,41 @@ public class ArrangementAndMatchConditionComponent extends JPanel implements Arr
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public ArrangementSettingsToken getToken() {
|
||||
return myComponentUnderMouse == null ? null : myComponentUnderMouse.getToken();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void chooseToken(@NotNull ArrangementSettingsToken data) throws IllegalArgumentException, UnsupportedOperationException {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSelected() {
|
||||
return myComponentUnderMouse != null && myComponentUnderMouse.isSelected();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void reset() {
|
||||
for (ArrangementUiComponent component : myComponents) {
|
||||
component.reset();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getBaselineToUse(int width, int height) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setListener(@NotNull Listener listener) {
|
||||
for (ArrangementUiComponent component : myComponents) {
|
||||
component.setListener(listener);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return String.format("(%s)", StringUtil.join(myComponents, " and "));
|
||||
+64
-24
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2012 JetBrains s.r.o.
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -13,52 +13,46 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.match;
|
||||
package com.intellij.application.options.codeStyle.arrangement.component;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.action.ArrangementRemoveConditionAction;
|
||||
import com.intellij.application.options.codeStyle.arrangement.animation.ArrangementAnimationPanel;
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.ArrangementConfigUtil;
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.InsetsPanel;
|
||||
import com.intellij.openapi.actionSystem.impl.ActionButton;
|
||||
import com.intellij.openapi.editor.markup.TextAttributes;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementUiComponent;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens;
|
||||
import com.intellij.ui.IdeBorderFactory;
|
||||
import com.intellij.ui.RoundedLineBorder;
|
||||
import com.intellij.ui.SimpleColoredComponent;
|
||||
import com.intellij.ui.SimpleTextAttributes;
|
||||
import com.intellij.util.Consumer;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.awt.event.MouseEvent;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* {@link ArrangementMatchConditionComponent} for {@link ArrangementAtomMatchCondition} representation.
|
||||
* {@link ArrangementUiComponent} for {@link ArrangementAtomMatchCondition} representation.
|
||||
* <p/>
|
||||
* Not thread-safe.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/8/12 10:06 AM
|
||||
*/
|
||||
public class ArrangementAtomMatchConditionComponent implements ArrangementMatchConditionComponent {
|
||||
public class ArrangementAtomMatchConditionComponent implements ArrangementUiComponent {
|
||||
|
||||
@NotNull private static final Map<ArrangementSettingType, BorderStrategy> BORDER_STRATEGIES = ContainerUtilRt.newHashMap();
|
||||
static {
|
||||
BORDER_STRATEGIES.put(ArrangementSettingType.NAME, new NameBorderStrategy());
|
||||
|
||||
PredefinedConditionBorderStrategy strategy = new PredefinedConditionBorderStrategy();
|
||||
BORDER_STRATEGIES.put(ArrangementSettingType.TYPE, strategy);
|
||||
BORDER_STRATEGIES.put(ArrangementSettingType.MODIFIER, strategy);
|
||||
}
|
||||
@NotNull private static final BorderStrategy NAME_BORDER_STRATEGY = new NameBorderStrategy();
|
||||
@NotNull private static final BorderStrategy PREDEFINED_BORDER_STRATEGY = new PredefinedConditionBorderStrategy();
|
||||
|
||||
@NotNull
|
||||
private final SimpleColoredComponent myTextControl = new SimpleColoredComponent() {
|
||||
@@ -98,11 +92,13 @@ public class ArrangementAtomMatchConditionComponent implements ArrangementMatchC
|
||||
|
||||
@Nullable private Dimension myTextControlSize;
|
||||
@Nullable private Rectangle myScreenBounds;
|
||||
@Nullable private Listener myListener;
|
||||
|
||||
private boolean myEnabled = true;
|
||||
private boolean mySelected;
|
||||
private boolean myCloseButtonHovered;
|
||||
|
||||
public ArrangementAtomMatchConditionComponent(@NotNull ArrangementNodeDisplayManager manager,
|
||||
public ArrangementAtomMatchConditionComponent(@NotNull ArrangementStandardSettingsManager manager,
|
||||
@NotNull ArrangementColorsProvider colorsProvider,
|
||||
@NotNull ArrangementAtomMatchCondition condition,
|
||||
@Nullable Consumer<ArrangementAtomMatchConditionComponent> closeCallback)
|
||||
@@ -110,12 +106,17 @@ public class ArrangementAtomMatchConditionComponent implements ArrangementMatchC
|
||||
myColorsProvider = colorsProvider;
|
||||
myCondition = condition;
|
||||
myCloseCallback = closeCallback;
|
||||
myBorderStrategy = BORDER_STRATEGIES.get(condition.getType());
|
||||
myText = manager.getDisplayValue(condition);
|
||||
myBorderStrategy = StdArrangementTokens.General.NAME.equals(condition.getType()) ? NAME_BORDER_STRATEGY : PREDEFINED_BORDER_STRATEGY;
|
||||
if (condition.getType().equals(condition.getValue())) {
|
||||
myText = condition.getType().getRepresentationValue();
|
||||
}
|
||||
else {
|
||||
myText = condition.getValue().toString();
|
||||
}
|
||||
myTextControl.setTextAlign(SwingConstants.CENTER);
|
||||
myTextControl.append(myText, SimpleTextAttributes.fromTextAttributes(colorsProvider.getTextAttributes(condition.getType(), false)));
|
||||
myTextControl.setOpaque(false);
|
||||
int maxWidth = manager.getMaxWidth(condition.getType());
|
||||
int maxWidth = manager.getWidth(condition.getType());
|
||||
if (maxWidth > 0) {
|
||||
myTextControlSize = new Dimension(maxWidth, myTextControl.getPreferredSize().height);
|
||||
}
|
||||
@@ -195,7 +196,7 @@ public class ArrangementAtomMatchConditionComponent implements ArrangementMatchC
|
||||
myAnimationPanel = new ArrangementAnimationPanel(roundBorderPanel, false, true) {
|
||||
@Override
|
||||
public void paint(Graphics g) {
|
||||
Point point = ArrangementConfigUtil.getLocationOnScreen(this);
|
||||
Point point = UIUtil.getLocationOnScreen(this);
|
||||
if (point != null) {
|
||||
Rectangle bounds = myAnimationPanel.getBounds();
|
||||
myScreenBounds = new Rectangle(point.x, point.y, bounds.width, bounds.height);
|
||||
@@ -237,11 +238,16 @@ public class ArrangementAtomMatchConditionComponent implements ArrangementMatchC
|
||||
* @param selected flag that indicates if current component should be drawn as 'selected'
|
||||
*/
|
||||
public void setSelected(boolean selected) {
|
||||
boolean notifyListener = selected != mySelected;
|
||||
mySelected = selected;
|
||||
myTextControl.clear();
|
||||
TextAttributes attributes = myColorsProvider.getTextAttributes(myCondition.getType(), selected);
|
||||
myTextControl.append(myText, SimpleTextAttributes.fromTextAttributes(attributes));
|
||||
myBorder.setColor(myColorsProvider.getBorderColor(selected));
|
||||
myBackgroundColor = attributes.getBackgroundColor();
|
||||
if (notifyListener && myListener != null) {
|
||||
myListener.stateChanged();
|
||||
}
|
||||
}
|
||||
|
||||
public boolean isEnabled() {
|
||||
@@ -255,7 +261,9 @@ public class ArrangementAtomMatchConditionComponent implements ArrangementMatchC
|
||||
*/
|
||||
public void setEnabled(boolean enabled) {
|
||||
myEnabled = enabled;
|
||||
setSelected(false);
|
||||
if (!enabled) {
|
||||
setSelected(false);
|
||||
}
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@@ -322,7 +330,39 @@ public class ArrangementAtomMatchConditionComponent implements ArrangementMatchC
|
||||
public String toString() {
|
||||
return myText;
|
||||
}
|
||||
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public ArrangementSettingsToken getToken() {
|
||||
return myCondition.getType();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void chooseToken(@NotNull ArrangementSettingsToken data) throws IllegalArgumentException, UnsupportedOperationException {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSelected() {
|
||||
return mySelected;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void reset() {
|
||||
setSelected(false);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getBaselineToUse(int width, int height) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
@SuppressWarnings("NullableProblems")
|
||||
@Override
|
||||
public void setListener(@NotNull Listener listener) {
|
||||
myListener = listener;
|
||||
}
|
||||
|
||||
private interface BorderStrategy {
|
||||
RoundedLineBorder create();
|
||||
void setup(@NotNull Graphics2D g);
|
||||
+124
@@ -0,0 +1,124 @@
|
||||
/*
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.component;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.ui.components.JBCheckBox;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.awt.event.ItemEvent;
|
||||
import java.awt.event.ItemListener;
|
||||
import java.awt.event.MouseAdapter;
|
||||
import java.awt.event.MouseEvent;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 3/11/13 10:25 AM
|
||||
*/
|
||||
public class ArrangementCheckBoxUiComponent extends AbstractArrangementUiComponent {
|
||||
|
||||
@NotNull private final JPanel myComponent = new JPanel(new GridBagLayout());
|
||||
|
||||
@NotNull private final ArrangementAtomMatchCondition myCondition;
|
||||
@NotNull private final JBCheckBox myCheckBox;
|
||||
@NotNull private final JLabel myTextLabel;
|
||||
|
||||
public ArrangementCheckBoxUiComponent(@NotNull ArrangementSettingsToken token) {
|
||||
myComponent.setOpaque(false);
|
||||
myCondition = new ArrangementAtomMatchCondition(token);
|
||||
myCheckBox = new JBCheckBox();
|
||||
myCheckBox.setOpaque(false);
|
||||
myTextLabel = new JLabel(token.getRepresentationValue());
|
||||
|
||||
myCheckBox.addItemListener(new ItemListener() {
|
||||
@Override
|
||||
public void itemStateChanged(ItemEvent e) {
|
||||
myTextLabel.setEnabled(myCheckBox.isEnabled());
|
||||
fireStateChanged();
|
||||
}
|
||||
});
|
||||
myTextLabel.addMouseListener(new MouseAdapter() {
|
||||
@Override
|
||||
public void mousePressed(MouseEvent e) {
|
||||
myCheckBox.setSelected(!myCheckBox.isSelected());
|
||||
}
|
||||
});
|
||||
|
||||
myComponent.add(myCheckBox, new GridBag().anchor(GridBagConstraints.WEST).insets(0, 0, 0, 2));
|
||||
myComponent.add(myTextLabel, new GridBag().anchor(GridBagConstraints.WEST).insets(0, 0, 0, ArrangementConstants.HORIZONTAL_GAP));
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public ArrangementSettingsToken getToken() {
|
||||
return myCondition.getType();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void chooseToken(@NotNull ArrangementSettingsToken data) throws UnsupportedOperationException {
|
||||
if (!getToken().equals(data)) {
|
||||
throw new UnsupportedOperationException(String.format(
|
||||
"Can't choose '%s' data at the check box token with data '%s'", data, getToken()
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public ArrangementMatchCondition getMatchCondition() {
|
||||
return myCondition;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected JComponent doGetUiComponent() {
|
||||
return myComponent;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void doReset() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled() {
|
||||
return myCheckBox.isEnabled();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setEnabled(boolean enabled) {
|
||||
myCheckBox.setEnabled(enabled);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSelected() {
|
||||
return myCheckBox.isSelected();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setSelected(boolean selected) {
|
||||
myCheckBox.setSelected(selected);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getBaselineToUse(int width, int height) {
|
||||
return myTextLabel.getBaseline(width, height);
|
||||
}
|
||||
}
|
||||
+125
@@ -0,0 +1,125 @@
|
||||
/*
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.component;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.ui.ListCellRendererWrapper;
|
||||
import com.intellij.ui.components.JBList;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.awt.event.ItemEvent;
|
||||
import java.awt.event.ItemListener;
|
||||
import java.util.Arrays;
|
||||
import java.util.Comparator;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 3/11/13 11:56 AM
|
||||
*/
|
||||
public class ArrangementComboBoxUiComponent extends AbstractArrangementUiComponent {
|
||||
|
||||
@NotNull private final JComboBox myComboBox;
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public ArrangementComboBoxUiComponent(@NotNull List<ArrangementSettingsToken> tokens) {
|
||||
ArrangementSettingsToken[] tokensArray = tokens.toArray(new ArrangementSettingsToken[tokens.size()]);
|
||||
Arrays.sort(tokensArray, new Comparator<ArrangementSettingsToken>() {
|
||||
@Override
|
||||
public int compare(ArrangementSettingsToken t1, ArrangementSettingsToken t2) {
|
||||
return t1.getRepresentationValue().compareTo(t2.getRepresentationValue());
|
||||
}
|
||||
});
|
||||
myComboBox = new JComboBox(tokensArray);
|
||||
myComboBox.setRenderer(new ListCellRendererWrapper() {
|
||||
@Override
|
||||
public void customize(JList list, Object value, int index, boolean selected, boolean hasFocus) {
|
||||
setText(((ArrangementSettingsToken)value).getRepresentationValue());
|
||||
}
|
||||
});
|
||||
myComboBox.addItemListener(new ItemListener() {
|
||||
@Override
|
||||
public void itemStateChanged(ItemEvent e) {
|
||||
if (e.getStateChange() == ItemEvent.SELECTED) {
|
||||
fireStateChanged();
|
||||
}
|
||||
}
|
||||
});
|
||||
int minWidth = 0;
|
||||
ListCellRenderer renderer = myComboBox.getRenderer();
|
||||
JBList dummyList = new JBList();
|
||||
for (int i = 0, max = myComboBox.getItemCount(); i < max; i++) {
|
||||
Component rendererComponent = renderer.getListCellRendererComponent(dummyList, myComboBox.getItemAt(i), i, false, true);
|
||||
minWidth = Math.max(minWidth, rendererComponent.getPreferredSize().width);
|
||||
}
|
||||
myComboBox.setPreferredSize(new Dimension(minWidth * 5 / 3, myComboBox.getPreferredSize().height));
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public ArrangementSettingsToken getToken() {
|
||||
return (ArrangementSettingsToken)myComboBox.getSelectedItem();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void chooseToken(@NotNull ArrangementSettingsToken data) throws IllegalArgumentException {
|
||||
myComboBox.setSelectedItem(data);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public ArrangementMatchCondition getMatchCondition() {
|
||||
ArrangementSettingsToken token = getToken();
|
||||
return new ArrangementAtomMatchCondition(token, token);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected JComponent doGetUiComponent() {
|
||||
return myComboBox;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSelected() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setSelected(boolean selected) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled() {
|
||||
return myComboBox.isEnabled();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setEnabled(boolean enabled) {
|
||||
myComboBox.setEnabled(enabled);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void doReset() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getBaselineToUse(int width, int height) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
+87
@@ -0,0 +1,87 @@
|
||||
/*
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.component;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import javax.swing.*;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 3/12/13 11:09 AM
|
||||
*/
|
||||
public class ArrangementLabelUiComponent extends AbstractArrangementUiComponent {
|
||||
|
||||
@NotNull private final ArrangementAtomMatchCondition myCondition;
|
||||
@NotNull private final JLabel myLabel;
|
||||
|
||||
public ArrangementLabelUiComponent(@NotNull ArrangementSettingsToken token) {
|
||||
myCondition = new ArrangementAtomMatchCondition(token);
|
||||
myLabel = new JLabel(token.getRepresentationValue());
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public ArrangementSettingsToken getToken() {
|
||||
return myCondition.getType();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void chooseToken(@NotNull ArrangementSettingsToken data) throws UnsupportedOperationException {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public ArrangementMatchCondition getMatchCondition() {
|
||||
return myCondition;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected JComponent doGetUiComponent() {
|
||||
return myLabel;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSelected() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setSelected(boolean selected) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setEnabled(boolean enabled) {
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void doReset() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getBaselineToUse(int width, int height) {
|
||||
return myLabel.getBaseline(width, height);
|
||||
}
|
||||
}
|
||||
+123
@@ -0,0 +1,123 @@
|
||||
/*
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.component;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.ui.components.JBTextField;
|
||||
import com.intellij.util.Alarm;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import javax.swing.*;
|
||||
import javax.swing.event.DocumentEvent;
|
||||
import javax.swing.event.DocumentListener;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 3/12/13 11:18 AM
|
||||
*/
|
||||
public class ArrangementTextFieldUiComponent extends AbstractArrangementUiComponent {
|
||||
|
||||
@NotNull private final JBTextField myTextField = new JBTextField(20);
|
||||
@NotNull private final Alarm myAlarm = new Alarm(Alarm.ThreadToUse.SWING_THREAD);
|
||||
|
||||
@NotNull private final ArrangementSettingsToken myToken;
|
||||
|
||||
public ArrangementTextFieldUiComponent(@NotNull ArrangementSettingsToken token) {
|
||||
myToken = token;
|
||||
myTextField.getDocument().addDocumentListener(new DocumentListener() {
|
||||
@Override
|
||||
public void insertUpdate(DocumentEvent e) {
|
||||
scheduleUpdate();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeUpdate(DocumentEvent e) {
|
||||
scheduleUpdate();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void changedUpdate(DocumentEvent e) {
|
||||
scheduleUpdate();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void scheduleUpdate() {
|
||||
myAlarm.cancelAllRequests();
|
||||
myAlarm.addRequest(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
fireStateChanged();
|
||||
}
|
||||
}, ArrangementConstants.TEXT_UPDATE_DELAY_MILLIS);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public ArrangementSettingsToken getToken() {
|
||||
return myToken;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void chooseToken(@NotNull ArrangementSettingsToken data) throws IllegalArgumentException, UnsupportedOperationException {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public ArrangementMatchCondition getMatchCondition() {
|
||||
String text = myTextField.getText();
|
||||
return new ArrangementAtomMatchCondition(myToken, StringUtil.isEmpty(text) ? "" : text.trim());
|
||||
}
|
||||
|
||||
@Override
|
||||
protected JComponent doGetUiComponent() {
|
||||
return myTextField;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSelected() {
|
||||
return !StringUtil.isEmpty(myTextField.getText());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setSelected(boolean selected) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled() {
|
||||
return myTextField.isEnabled();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setEnabled(boolean enabled) {
|
||||
myTextField.setEnabled(enabled);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void doReset() {
|
||||
myTextField.setText("");
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getBaselineToUse(int width, int height) {
|
||||
return myTextField.getBaseline(width, height);
|
||||
}
|
||||
}
|
||||
+75
@@ -0,0 +1,75 @@
|
||||
/*
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.component;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementUiComponent;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokenUiRole;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 3/12/13 2:23 PM
|
||||
*/
|
||||
public class DefaultArrangementUiComponentFactory implements ArrangementUiComponent.Factory {
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public ArrangementUiComponent build(@NotNull StdArrangementTokenUiRole role,
|
||||
@NotNull List<ArrangementSettingsToken> tokens,
|
||||
@NotNull ArrangementColorsProvider colorsProvider,
|
||||
@NotNull ArrangementStandardSettingsManager settingsManager)
|
||||
{
|
||||
switch (role) {
|
||||
case CHECKBOX:
|
||||
if (tokens.size() != 1) {
|
||||
throw new IllegalArgumentException("Can't build a checkbox token for elements " + tokens);
|
||||
}
|
||||
else {
|
||||
return new ArrangementCheckBoxUiComponent(tokens.get(0));
|
||||
}
|
||||
case COMBO_BOX:
|
||||
if (tokens.isEmpty()) {
|
||||
throw new IllegalArgumentException("Can't build a combo box token with empty content");
|
||||
}
|
||||
return new ArrangementComboBoxUiComponent(tokens);
|
||||
case LABEL:
|
||||
if (tokens.size() != 1) {
|
||||
throw new IllegalArgumentException("Can't build a label token for elements " + tokens);
|
||||
}
|
||||
return new ArrangementLabelUiComponent(tokens.get(0));
|
||||
case TEXT_FIELD:
|
||||
if (tokens.size() != 1) {
|
||||
throw new IllegalArgumentException("Can't build a text field token for elements " + tokens);
|
||||
}
|
||||
return new ArrangementTextFieldUiComponent(tokens.get(0));
|
||||
case BULB:
|
||||
if (tokens.size() != 1) {
|
||||
throw new IllegalArgumentException("Can't build a bulb token for elements " + tokens);
|
||||
}
|
||||
return new ArrangementAtomMatchConditionComponent(
|
||||
settingsManager, colorsProvider, new ArrangementAtomMatchCondition(tokens.get(0)), null
|
||||
);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
+77
-72
@@ -16,15 +16,14 @@
|
||||
package com.intellij.application.options.codeStyle.arrangement.group;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.component.ArrangementEditorAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.component.ArrangementRepresentationAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ui.ArrangementEditorAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ui.ArrangementRepresentationAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.ArrangementRuleIndexControl;
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.InsetsPanel;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementUtil;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.*;
|
||||
import com.intellij.ui.IdeBorderFactory;
|
||||
import com.intellij.ui.components.JBCheckBox;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -32,11 +31,8 @@ import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.awt.event.ItemEvent;
|
||||
import java.awt.event.ItemListener;
|
||||
import java.awt.event.MouseAdapter;
|
||||
import java.awt.event.MouseEvent;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
@@ -44,18 +40,44 @@ import java.util.Collection;
|
||||
*/
|
||||
public class ArrangementGroupingComponent extends JPanel implements ArrangementRepresentationAware, ArrangementEditorAware {
|
||||
|
||||
@NotNull private final ArrangementGroupingType myGroupingType;
|
||||
@NotNull private final ArrangementUiComponent myGroupingTypeToken;
|
||||
@NotNull private final ArrangementRuleIndexControl myRowIndexControl;
|
||||
@NotNull private final JBCheckBox myCheckedBox;
|
||||
@NotNull private final JLabel myGroupingTypeLabel;
|
||||
|
||||
@Nullable private final JComboBox myOrderTypeBox;
|
||||
@Nullable private final ArrangementUiComponent myOrderTypeToken;
|
||||
|
||||
public ArrangementGroupingComponent(@NotNull final ArrangementNodeDisplayManager displayManager,
|
||||
@NotNull ArrangementGroupingType groupingType,
|
||||
@NotNull Collection<ArrangementEntryOrderType> availableOrderTypes)
|
||||
/**
|
||||
* Assumes that given token {@link CompositeArrangementSettingsToken#getChildren() has no children} or all its children have
|
||||
* the {@link CompositeArrangementSettingsToken#getRole() same UI role}.
|
||||
* <p/>
|
||||
* Lays out given token (and its children if any) in a single row.
|
||||
*
|
||||
* @param token base token which serves as a grouping rule model
|
||||
* @param colorsProvider colors provider
|
||||
*
|
||||
* @throws IllegalArgumentException if invariant described above is not satisfied
|
||||
*/
|
||||
public ArrangementGroupingComponent(@NotNull CompositeArrangementSettingsToken token,
|
||||
@NotNull ArrangementColorsProvider colorsProvider,
|
||||
@NotNull ArrangementStandardSettingsManager settingsManager)
|
||||
throws IllegalArgumentException
|
||||
{
|
||||
myGroupingType = groupingType;
|
||||
List<ArrangementSettingsToken> children = ContainerUtilRt.newArrayList();
|
||||
StdArrangementTokenUiRole childRole = null;
|
||||
for (CompositeArrangementSettingsToken child : token.getChildren()) {
|
||||
if (childRole == null) {
|
||||
childRole = child.getRole();
|
||||
children.add(child.getToken());
|
||||
}
|
||||
else if (!childRole.equals(child.getRole())) {
|
||||
throw new IllegalArgumentException(String.format(
|
||||
"Can't build a grouping component for token '%s'. Reason: its children has different UI roles (%s and %s)",
|
||||
token, childRole, child.getRole()
|
||||
));
|
||||
}
|
||||
else {
|
||||
children.add(child.getToken());
|
||||
}
|
||||
}
|
||||
|
||||
FontMetrics metrics = getFontMetrics(getFont());
|
||||
int maxWidth = 0;
|
||||
@@ -66,32 +88,20 @@ public class ArrangementGroupingComponent extends JPanel implements ArrangementR
|
||||
int diameter = Math.max(maxWidth, height) * 5 / 3;
|
||||
myRowIndexControl = new ArrangementRuleIndexControl(diameter, height);
|
||||
|
||||
myCheckedBox = new JBCheckBox();
|
||||
myCheckedBox.setOpaque(false);
|
||||
myCheckedBox.addItemListener(new ItemListener() {
|
||||
@Override
|
||||
public void itemStateChanged(ItemEvent e) {
|
||||
refreshControl();
|
||||
}
|
||||
});
|
||||
|
||||
myGroupingTypeLabel = new JLabel(displayManager.getDisplayValue(groupingType));
|
||||
myGroupingTypeLabel.addMouseListener(new MouseAdapter() {
|
||||
@Override
|
||||
public void mousePressed(MouseEvent e) {
|
||||
myCheckedBox.setSelected(!myCheckedBox.isSelected());
|
||||
}
|
||||
});
|
||||
myGroupingTypeToken = ArrangementUtil.buildUiComponent(
|
||||
token.getRole(), Collections.singletonList(token.getToken()), colorsProvider, settingsManager
|
||||
);
|
||||
|
||||
if (availableOrderTypes.isEmpty()) {
|
||||
myOrderTypeBox = null;
|
||||
if (children.size() <= 0) {
|
||||
myOrderTypeToken = null;
|
||||
}
|
||||
else {
|
||||
myOrderTypeBox = new JComboBox(availableOrderTypes.toArray());
|
||||
myOrderTypeBox.setRenderer(new ListCellRenderer() {
|
||||
assert childRole != null;
|
||||
myOrderTypeToken = ArrangementUtil.buildUiComponent(childRole, children, colorsProvider, settingsManager);
|
||||
myGroupingTypeToken.setListener(new ArrangementUiComponent.Listener() {
|
||||
@Override
|
||||
public Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) {
|
||||
return new JLabel(displayManager.getDisplayValue(value));
|
||||
public void stateChanged() {
|
||||
myOrderTypeToken.setEnabled(myGroupingTypeToken.isEnabled());
|
||||
}
|
||||
});
|
||||
}
|
||||
@@ -105,17 +115,9 @@ public class ArrangementGroupingComponent extends JPanel implements ArrangementR
|
||||
new GridBag().anchor(GridBagConstraints.CENTER)
|
||||
.insets(0, ArrangementConstants.HORIZONTAL_PADDING, 0, ArrangementConstants.HORIZONTAL_GAP * 2)
|
||||
);
|
||||
add(myCheckedBox, new GridBag().anchor(GridBagConstraints.WEST).insets(0, 0, 0, 2));
|
||||
add(myGroupingTypeLabel, new GridBag().anchor(GridBagConstraints.WEST).insets(0, 0, 0, ArrangementConstants.HORIZONTAL_GAP));
|
||||
if (myOrderTypeBox != null) {
|
||||
int minWidth = 0;
|
||||
ListCellRenderer renderer = myOrderTypeBox.getRenderer();
|
||||
for (int i = 0, max = myOrderTypeBox.getItemCount(); i < max; i++) {
|
||||
Component rendererComponent = renderer.getListCellRendererComponent(null, myOrderTypeBox.getItemAt(i), i, false, true);
|
||||
minWidth = Math.max(minWidth, rendererComponent.getPreferredSize().width);
|
||||
}
|
||||
myOrderTypeBox.setPreferredSize(new Dimension(minWidth * 5 / 3, myOrderTypeBox.getPreferredSize().height));
|
||||
add(myOrderTypeBox, new GridBag().anchor(GridBagConstraints.WEST));
|
||||
add(myGroupingTypeToken.getUiComponent(), new GridBag().anchor(GridBagConstraints.WEST).insets(0, 0, 0, 2));
|
||||
if (myOrderTypeToken != null) {
|
||||
add(myOrderTypeToken.getUiComponent(), new GridBag().anchor(GridBagConstraints.WEST));
|
||||
}
|
||||
add(new JLabel(" "), new GridBag().weightx(1).fillCellHorizontally());
|
||||
|
||||
@@ -127,9 +129,11 @@ public class ArrangementGroupingComponent extends JPanel implements ArrangementR
|
||||
protected void paintComponent(Graphics g) {
|
||||
Dimension size = getSize();
|
||||
if (size != null) {
|
||||
int baseline = myGroupingTypeLabel.getBaseline(size.width, size.height);
|
||||
baseline -= myRowIndexControl.getBounds().y;
|
||||
myRowIndexControl.setBaseLine(baseline);
|
||||
int baseline = myGroupingTypeToken.getBaselineToUse(size.width, size.height);
|
||||
if (baseline > 0) {
|
||||
baseline -= myRowIndexControl.getBounds().y;
|
||||
myRowIndexControl.setBaseLine(baseline);
|
||||
}
|
||||
}
|
||||
super.paintComponent(g);
|
||||
}
|
||||
@@ -140,31 +144,32 @@ public class ArrangementGroupingComponent extends JPanel implements ArrangementR
|
||||
return this;
|
||||
}
|
||||
|
||||
public boolean isChecked() {
|
||||
return myCheckedBox.isSelected();
|
||||
public boolean isSelected() {
|
||||
return myGroupingTypeToken.isSelected();
|
||||
}
|
||||
|
||||
public void setChecked(boolean checked) {
|
||||
myCheckedBox.setSelected(checked);
|
||||
public void setSelected(boolean selected) {
|
||||
myGroupingTypeToken.setSelected(selected);
|
||||
refreshControl();
|
||||
}
|
||||
|
||||
private void refreshControl() {
|
||||
boolean checked = isChecked();
|
||||
myGroupingTypeLabel.setEnabled(checked);
|
||||
if (myOrderTypeBox != null) {
|
||||
myOrderTypeBox.setEnabled(checked);
|
||||
boolean checked = isSelected();
|
||||
if (myOrderTypeToken != null) {
|
||||
myOrderTypeToken.setEnabled(checked);
|
||||
}
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public ArrangementGroupingType getGroupingType() {
|
||||
return myGroupingType;
|
||||
public ArrangementSettingsToken getGroupingType() {
|
||||
ArrangementSettingsToken token = myGroupingTypeToken.getToken();
|
||||
assert token != null;
|
||||
return token;
|
||||
}
|
||||
|
||||
public void setOrderType(@NotNull ArrangementEntryOrderType type) {
|
||||
if (myOrderTypeBox != null) {
|
||||
myOrderTypeBox.setSelectedItem(type);
|
||||
public void setOrderType(@NotNull ArrangementSettingsToken type) {
|
||||
if (myOrderTypeToken != null) {
|
||||
myOrderTypeToken.chooseToken(type);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -177,12 +182,12 @@ public class ArrangementGroupingComponent extends JPanel implements ArrangementR
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public ArrangementEntryOrderType getOrderType() {
|
||||
return myOrderTypeBox == null ? null : (ArrangementEntryOrderType)myOrderTypeBox.getSelectedItem();
|
||||
public ArrangementSettingsToken getOrderType() {
|
||||
return myOrderTypeToken == null ? null : myOrderTypeToken.getToken();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return myGroupingType.toString();
|
||||
return myGroupingTypeToken.toString();
|
||||
}
|
||||
}
|
||||
|
||||
+37
-62
@@ -15,18 +15,18 @@
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.group;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.component.ArrangementEditorAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.component.ArrangementRepresentationAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ui.ArrangementEditorAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ui.ArrangementRepresentationAware;
|
||||
import com.intellij.openapi.actionSystem.DataKey;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.CompositeArrangementSettingsToken;
|
||||
import com.intellij.ui.IdeBorderFactory;
|
||||
import com.intellij.ui.table.JBTable;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import com.intellij.util.ui.AbstractTableCellEditor;
|
||||
import gnu.trove.TObjectIntHashMap;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@@ -35,8 +35,9 @@ import javax.swing.table.DefaultTableModel;
|
||||
import javax.swing.table.TableCellRenderer;
|
||||
import java.awt.*;
|
||||
import java.awt.event.MouseEvent;
|
||||
import java.util.*;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
@@ -44,15 +45,19 @@ import java.util.List;
|
||||
*/
|
||||
public class ArrangementGroupingRulesControl extends JBTable {
|
||||
|
||||
@NotNull private final Map<ArrangementGroupingType, ArrangementGroupingComponent> myComponents
|
||||
= new EnumMap<ArrangementGroupingType, ArrangementGroupingComponent>(ArrangementGroupingType.class);
|
||||
|
||||
@NotNull public static final DataKey<ArrangementGroupingRulesControl> KEY = DataKey.create("Arrangement.Rule.Group.Control");
|
||||
|
||||
@NotNull private final Map<ArrangementSettingsToken, ArrangementGroupingComponent> myComponents = ContainerUtilRt.newHashMap();
|
||||
|
||||
@NotNull private final ArrangementStandardSettingsManager mySettingsManager;
|
||||
|
||||
private int myRowUnderMouse = -1;
|
||||
|
||||
public ArrangementGroupingRulesControl(@NotNull ArrangementNodeDisplayManager displayManager,
|
||||
@NotNull ArrangementStandardSettingsAware settingsFilter)
|
||||
public ArrangementGroupingRulesControl(@NotNull ArrangementStandardSettingsManager settingsManager,
|
||||
@NotNull ArrangementColorsProvider colorsProvider)
|
||||
{
|
||||
super(new DefaultTableModel(0, 1));
|
||||
mySettingsManager = settingsManager;
|
||||
setDefaultRenderer(Object.class, new MyRenderer());
|
||||
getColumnModel().getColumn(0).setCellEditor(new MyEditor());
|
||||
setShowColumns(false);
|
||||
@@ -61,19 +66,13 @@ public class ArrangementGroupingRulesControl extends JBTable {
|
||||
setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
|
||||
putClientProperty("terminateEditOnFocusLost", Boolean.TRUE);
|
||||
|
||||
for (ArrangementGroupingType groupingType : ArrangementGroupingType.values()) {
|
||||
if (!settingsFilter.isEnabled(groupingType, null)) {
|
||||
continue;
|
||||
List<CompositeArrangementSettingsToken> groupingTokens = settingsManager.getSupportedGroupingTokens();
|
||||
if (groupingTokens != null) {
|
||||
for (CompositeArrangementSettingsToken token : groupingTokens) {
|
||||
ArrangementGroupingComponent component = new ArrangementGroupingComponent(token, colorsProvider, settingsManager);
|
||||
myComponents.put(token.getToken(), component);
|
||||
getModel().addRow(new Object[]{component});
|
||||
}
|
||||
List<ArrangementEntryOrderType> orderTypes = new ArrayList<ArrangementEntryOrderType>();
|
||||
for (ArrangementEntryOrderType orderType : ArrangementEntryOrderType.values()) {
|
||||
if (settingsFilter.isEnabled(groupingType, orderType)) {
|
||||
orderTypes.add(orderType);
|
||||
}
|
||||
}
|
||||
ArrangementGroupingComponent component = new ArrangementGroupingComponent(displayManager, groupingType, orderTypes);
|
||||
myComponents.put(groupingType, component);
|
||||
getModel().addRow(new Object[]{component});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -84,9 +83,9 @@ public class ArrangementGroupingRulesControl extends JBTable {
|
||||
|
||||
public void setRules(@Nullable List<ArrangementGroupingRule> rules) {
|
||||
for (ArrangementGroupingComponent component : myComponents.values()) {
|
||||
component.setChecked(false);
|
||||
component.setSelected(false);
|
||||
}
|
||||
|
||||
|
||||
if (rules == null) {
|
||||
return;
|
||||
}
|
||||
@@ -96,15 +95,15 @@ public class ArrangementGroupingRulesControl extends JBTable {
|
||||
model.removeRow(model.getRowCount() - 1);
|
||||
}
|
||||
|
||||
List<ArrangementGroupingType> types = new ArrayList<ArrangementGroupingType>(myComponents.keySet());
|
||||
ContainerUtil.sort(types, new MyComparator(rules));
|
||||
for (ArrangementGroupingType type : types) {
|
||||
model.addRow(new Object[] { myComponents.get(type) });
|
||||
List<ArrangementSettingsToken> types = ContainerUtilRt.newArrayList(myComponents.keySet());
|
||||
types = mySettingsManager.sort(types);
|
||||
for (ArrangementSettingsToken type : types) {
|
||||
model.addRow(new Object[]{myComponents.get(type)});
|
||||
}
|
||||
for (ArrangementGroupingRule rule : rules) {
|
||||
ArrangementGroupingComponent component = myComponents.get(rule.getGroupingType());
|
||||
component.setChecked(true);
|
||||
ArrangementEntryOrderType orderType = rule.getOrderType();
|
||||
component.setSelected(true);
|
||||
ArrangementSettingsToken orderType = rule.getOrderType();
|
||||
component.setOrderType(orderType);
|
||||
}
|
||||
}
|
||||
@@ -115,10 +114,10 @@ public class ArrangementGroupingRulesControl extends JBTable {
|
||||
DefaultTableModel model = getModel();
|
||||
for (int i = 0, max = model.getRowCount(); i < max; i++) {
|
||||
ArrangementGroupingComponent component = (ArrangementGroupingComponent)model.getValueAt(i, 0);
|
||||
if (!component.isChecked()) {
|
||||
if (!component.isSelected()) {
|
||||
continue;
|
||||
}
|
||||
ArrangementEntryOrderType orderType = component.getOrderType();
|
||||
ArrangementSettingsToken orderType = component.getOrderType();
|
||||
if (orderType == null) {
|
||||
result.add(new ArrangementGroupingRule(component.getGroupingType()));
|
||||
}
|
||||
@@ -154,6 +153,7 @@ public class ArrangementGroupingRulesControl extends JBTable {
|
||||
super.processMouseEvent(e);
|
||||
}
|
||||
|
||||
@SuppressWarnings("ConstantConditions")
|
||||
private class MyRenderer implements TableCellRenderer {
|
||||
@Override
|
||||
public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
|
||||
@@ -170,6 +170,7 @@ public class ArrangementGroupingRulesControl extends JBTable {
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressWarnings("ConstantConditions")
|
||||
private static class MyEditor extends AbstractTableCellEditor {
|
||||
|
||||
@Nullable Object myValue;
|
||||
@@ -195,30 +196,4 @@ public class ArrangementGroupingRulesControl extends JBTable {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
private static class MyComparator implements Comparator<ArrangementGroupingType> {
|
||||
|
||||
@NotNull private final TObjectIntHashMap<ArrangementGroupingType> myWeights = new TObjectIntHashMap<ArrangementGroupingType>();
|
||||
|
||||
MyComparator(@NotNull List<ArrangementGroupingRule> list) {
|
||||
int weight = 0;
|
||||
for (ArrangementGroupingRule rule : list) {
|
||||
myWeights.put(rule.getGroupingType(), weight++);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public int compare(ArrangementGroupingType t1, ArrangementGroupingType t2) {
|
||||
if (myWeights.containsKey(t1) && myWeights.containsKey(t2)) {
|
||||
return myWeights.get(t1) - myWeights.get(t2);
|
||||
}
|
||||
else if (myWeights.containsKey(t1)) {
|
||||
return -1;
|
||||
}
|
||||
else if (myWeights.containsKey(t2)) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+6
-6
@@ -16,12 +16,12 @@
|
||||
package com.intellij.application.options.codeStyle.arrangement.group;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.TitleWithToolbar;
|
||||
import com.intellij.openapi.actionSystem.DataProvider;
|
||||
import com.intellij.openapi.application.ApplicationBundle;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsAware;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -39,12 +39,12 @@ public class ArrangementGroupingRulesPanel extends JPanel implements DataProvide
|
||||
|
||||
@NotNull private final ArrangementGroupingRulesControl myControl;
|
||||
|
||||
public ArrangementGroupingRulesPanel(@NotNull ArrangementNodeDisplayManager displayManager,
|
||||
@NotNull ArrangementStandardSettingsAware settingsFilter)
|
||||
public ArrangementGroupingRulesPanel(@NotNull ArrangementStandardSettingsManager settingsManager,
|
||||
@NotNull ArrangementColorsProvider colorsProvider)
|
||||
{
|
||||
super(new GridBagLayout());
|
||||
|
||||
myControl = new ArrangementGroupingRulesControl(displayManager, settingsFilter);
|
||||
myControl = new ArrangementGroupingRulesControl(settingsManager, colorsProvider);
|
||||
|
||||
TitleWithToolbar top = new TitleWithToolbar(
|
||||
ApplicationBundle.message("arrangement.settings.section.groups"),
|
||||
@@ -69,7 +69,7 @@ public class ArrangementGroupingRulesPanel extends JPanel implements DataProvide
|
||||
@Nullable
|
||||
@Override
|
||||
public Object getData(@NonNls String dataId) {
|
||||
if (ArrangementConstants.GROUPING_RULES_CONTROL_KEY.is(dataId)) {
|
||||
if (ArrangementGroupingRulesControl.KEY.is(dataId)) {
|
||||
return myControl;
|
||||
}
|
||||
return null;
|
||||
|
||||
+2
-5
@@ -16,11 +16,8 @@
|
||||
package com.intellij.application.options.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.animation.ArrangementAnimationManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.animation.ArrangementAnimationPanel;
|
||||
import com.intellij.application.options.codeStyle.arrangement.component.ArrangementEditorAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.component.ArrangementRepresentationAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchingRuleEditor;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchingRulesControl;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ui.ArrangementEditorAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ui.ArrangementRepresentationAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.CalloutBorder;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
-120
@@ -1,120 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.application.options.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.ArrangementConfigUtil;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.awt.event.MouseEvent;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 9/12/12 5:39 PM
|
||||
*/
|
||||
public class ArrangementGroupingMatchConditionComponent extends JPanel implements ArrangementMatchConditionComponent {
|
||||
|
||||
private static final int TOP_INSET = 3;
|
||||
|
||||
@NotNull private final ArrangementAtomMatchCondition myCondition;
|
||||
|
||||
@Nullable private Rectangle myScreenBounds;
|
||||
@NotNull private Dimension myPreferredSize;
|
||||
|
||||
public ArrangementGroupingMatchConditionComponent(@NotNull ArrangementNodeDisplayManager manager,
|
||||
@NotNull ArrangementAtomMatchCondition condition)
|
||||
{
|
||||
myCondition = condition;
|
||||
String text = StringUtil.capitalize(StringUtil.pluralize(manager.getDisplayValue(myCondition.getValue())));
|
||||
setLayout(new GridBagLayout());
|
||||
GridBag constraints = new GridBag().anchor(GridBagConstraints.WEST).weightx(1).insets(TOP_INSET * 2, 20, 0, 0);
|
||||
add(new JLabel(String.format("<html><i>%s", text)), constraints);
|
||||
myPreferredSize = super.getPreferredSize();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public ArrangementMatchCondition getMatchCondition() {
|
||||
return myCondition;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public JComponent getUiComponent() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Rectangle getScreenBounds() {
|
||||
return myScreenBounds;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Dimension getPreferredSize() {
|
||||
return myPreferredSize;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setSelected(boolean selected) {
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Rectangle onMouseMove(@NotNull MouseEvent event) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onMouseRelease(@NotNull MouseEvent event) {
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void paintComponent(Graphics g) {
|
||||
super.paintComponent(g);
|
||||
Rectangle bounds = getBounds();
|
||||
g.setColor(UIManager.getColor("Tree.hash"));
|
||||
int cornerX = UIUtil.getTreeLeftChildIndent();
|
||||
int y = TOP_INSET;
|
||||
g.drawLine(cornerX, y, bounds.width, y);
|
||||
g.drawLine(cornerX, y, cornerX, y + bounds.height);
|
||||
|
||||
Point point = ArrangementConfigUtil.getLocationOnScreen(this);
|
||||
if (point != null) {
|
||||
myScreenBounds = new Rectangle(point.x, point.y, bounds.width, bounds.height);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Rectangle onMouseEntered(@NotNull MouseEvent e) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Rectangle onMouseExited() {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
+20
-14
@@ -16,15 +16,21 @@
|
||||
package com.intellij.application.options.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.animation.ArrangementAnimationManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.animation.ArrangementAnimationPanel;
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.application.options.codeStyle.arrangement.component.ArrangementAndMatchConditionComponent;
|
||||
import com.intellij.application.options.codeStyle.arrangement.component.ArrangementAtomMatchConditionComponent;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.util.Ref;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementEntryMatcher;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.*;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementCompositeMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchConditionVisitor;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementUiComponent;
|
||||
import com.intellij.util.Consumer;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
@@ -38,15 +44,15 @@ public class ArrangementMatchNodeComponentFactory {
|
||||
|
||||
private static final Logger LOG = Logger.getInstance("#" + ArrangementMatchNodeComponentFactory.class.getName());
|
||||
|
||||
@NotNull private final ArrangementNodeDisplayManager myDisplayManager;
|
||||
@NotNull private final ArrangementColorsProvider myColorsProvider;
|
||||
@NotNull private final ArrangementMatchingRulesControl myList;
|
||||
@NotNull private final ArrangementStandardSettingsManager mySettingsManager;
|
||||
@NotNull private final ArrangementColorsProvider myColorsProvider;
|
||||
@NotNull private final ArrangementMatchingRulesControl myList;
|
||||
|
||||
public ArrangementMatchNodeComponentFactory(@NotNull ArrangementNodeDisplayManager manager,
|
||||
public ArrangementMatchNodeComponentFactory(@NotNull ArrangementStandardSettingsManager manager,
|
||||
@NotNull ArrangementColorsProvider provider,
|
||||
@NotNull ArrangementMatchingRulesControl list)
|
||||
{
|
||||
myDisplayManager = manager;
|
||||
mySettingsManager = manager;
|
||||
myColorsProvider = provider;
|
||||
myList = list;
|
||||
}
|
||||
@@ -61,24 +67,24 @@ public class ArrangementMatchNodeComponentFactory {
|
||||
* @return renderer for the given model
|
||||
*/
|
||||
@NotNull
|
||||
public ArrangementMatchConditionComponent getComponent(@NotNull final ArrangementMatchCondition rendererTarget,
|
||||
@NotNull final StdArrangementMatchRule rule,
|
||||
final boolean allowModification)
|
||||
public ArrangementUiComponent getComponent(@NotNull final ArrangementMatchCondition rendererTarget,
|
||||
@NotNull final StdArrangementMatchRule rule,
|
||||
final boolean allowModification)
|
||||
{
|
||||
final Ref<ArrangementMatchConditionComponent> ref = new Ref<ArrangementMatchConditionComponent>();
|
||||
final Ref<ArrangementUiComponent> ref = new Ref<ArrangementUiComponent>();
|
||||
rendererTarget.invite(new ArrangementMatchConditionVisitor() {
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementAtomMatchCondition condition) {
|
||||
RemoveAtomConditionCallback callback = allowModification ? new RemoveAtomConditionCallback(rule) : null;
|
||||
ArrangementMatchConditionComponent component = new ArrangementAtomMatchConditionComponent(
|
||||
myDisplayManager, myColorsProvider, condition, callback
|
||||
ArrangementUiComponent component = new ArrangementAtomMatchConditionComponent(
|
||||
mySettingsManager, myColorsProvider, condition, callback
|
||||
);
|
||||
ref.set(component);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visit(@NotNull ArrangementCompositeMatchCondition condition) {
|
||||
ref.set(new ArrangementAndMatchConditionComponent(rule, condition, ArrangementMatchNodeComponentFactory.this, myDisplayManager));
|
||||
ref.set(new ArrangementAndMatchConditionComponent(rule, condition, ArrangementMatchNodeComponentFactory.this, mySettingsManager));
|
||||
}
|
||||
});
|
||||
return ref.get();
|
||||
|
||||
+233
-220
@@ -16,34 +16,25 @@
|
||||
package com.intellij.application.options.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.ArrangementConfigUtil;
|
||||
import com.intellij.openapi.application.ApplicationBundle;
|
||||
import com.intellij.openapi.util.Comparing;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementRuleInfo;
|
||||
import com.intellij.openapi.util.Pair;
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementUtil;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryMatcher;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementEntryMatcher;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.*;
|
||||
import com.intellij.ui.IdeBorderFactory;
|
||||
import com.intellij.ui.components.JBTextField;
|
||||
import com.intellij.util.Alarm;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import com.intellij.util.ui.MultiRowFlowPanel;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import javax.swing.event.DocumentEvent;
|
||||
import javax.swing.event.DocumentListener;
|
||||
import java.awt.*;
|
||||
import java.awt.event.MouseAdapter;
|
||||
import java.awt.event.MouseEvent;
|
||||
@@ -58,148 +49,184 @@ import java.util.List;
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/14/12 9:54 AM
|
||||
*/
|
||||
public class ArrangementMatchingRuleEditor extends JPanel {
|
||||
public class ArrangementMatchingRuleEditor extends JPanel implements ArrangementUiComponent.Listener {
|
||||
|
||||
@NotNull private final Map<Object, ArrangementAtomMatchConditionComponent> myConditionComponents = ContainerUtilRt.newHashMap();
|
||||
@NotNull private final List<MultiRowFlowPanel> myRows = ContainerUtilRt.newArrayList();
|
||||
@NotNull private final Map<ArrangementSettingsToken, ArrangementUiComponent> myComponents = ContainerUtilRt.newHashMap();
|
||||
@NotNull private final List<MultiRowFlowPanel> myRows = ContainerUtilRt.newArrayList();
|
||||
|
||||
@NotNull private final Map<ArrangementEntryOrderType, ArrangementOrderTypeComponent> myOrderTypeComponents
|
||||
= new EnumMap<ArrangementEntryOrderType, ArrangementOrderTypeComponent>(ArrangementEntryOrderType.class);
|
||||
|
||||
@NotNull private final ArrangementRuleInfo myRuleInfo = new ArrangementRuleInfo();
|
||||
@NotNull private final Alarm myAlarm = new Alarm(Alarm.ThreadToUse.SWING_THREAD);
|
||||
@NotNull private final JBTextField myNameField = new JBTextField(20);
|
||||
|
||||
@NotNull private final ArrangementMatchingRulesControl myControl;
|
||||
@NotNull private final ArrangementStandardSettingsAware myFilter;
|
||||
@NotNull private final ArrangementColorsProvider myColorsProvider;
|
||||
@NotNull private final ArrangementMatchingRulesControl myControl;
|
||||
@NotNull private final ArrangementStandardSettingsManager mySettingsManager;
|
||||
@NotNull private final ArrangementColorsProvider myColorsProvider;
|
||||
|
||||
private int myRow = -1;
|
||||
private int myLabelWidth;
|
||||
private boolean myRequestFocus;
|
||||
private int myLabelWidth;
|
||||
|
||||
@Nullable private JComponent myDefaultFocusRequestor;
|
||||
@Nullable private JComponent myFocusRequestor;
|
||||
|
||||
private boolean mySkipStateChange;
|
||||
|
||||
public ArrangementMatchingRuleEditor(@NotNull ArrangementStandardSettingsAware filter,
|
||||
@NotNull ArrangementColorsProvider provider,
|
||||
@NotNull ArrangementNodeDisplayManager displayManager,
|
||||
public ArrangementMatchingRuleEditor(@NotNull ArrangementStandardSettingsManager settingsManager,
|
||||
@NotNull ArrangementColorsProvider colorsProvider,
|
||||
@NotNull ArrangementMatchingRulesControl control)
|
||||
{
|
||||
myFilter = filter;
|
||||
myColorsProvider = provider;
|
||||
mySettingsManager = settingsManager;
|
||||
myColorsProvider = colorsProvider;
|
||||
myControl = control;
|
||||
init(displayManager);
|
||||
init(settingsManager);
|
||||
addMouseListener(new MouseAdapter() {
|
||||
@Override
|
||||
public void mouseClicked(MouseEvent e) {
|
||||
onMouseClicked(e);
|
||||
}
|
||||
});
|
||||
myNameField.getDocument().addDocumentListener(new DocumentListener() {
|
||||
@Override public void insertUpdate(DocumentEvent e) { scheduleNameUpdate(); }
|
||||
@Override public void removeUpdate(DocumentEvent e) { scheduleNameUpdate(); }
|
||||
@Override public void changedUpdate(DocumentEvent e) { scheduleNameUpdate(); }
|
||||
});
|
||||
}
|
||||
|
||||
private void init(@NotNull ArrangementNodeDisplayManager displayManager) {
|
||||
private void init(@NotNull ArrangementStandardSettingsManager settingsManager) {
|
||||
setLayout(new GridBagLayout());
|
||||
setBorder(IdeBorderFactory.createEmptyBorder(5));
|
||||
|
||||
Map<ArrangementSettingType, Set<?>> supportedSettings = ArrangementConfigUtil.buildAvailableConditions(myFilter, null);
|
||||
addRowIfPossible(ArrangementSettingType.TYPE, supportedSettings, displayManager);
|
||||
addRowIfPossible(ArrangementSettingType.MODIFIER, supportedSettings, displayManager);
|
||||
addNameFilterIfPossible();
|
||||
addOrderRowIfPossible(displayManager);
|
||||
List<CompositeArrangementSettingsToken> tokens = settingsManager.getSupportedMatchingTokens();
|
||||
if (tokens != null) {
|
||||
for (CompositeArrangementSettingsToken token : tokens) {
|
||||
addToken(token);
|
||||
}
|
||||
}
|
||||
|
||||
applyBackground(UIUtil.getListBackground());
|
||||
}
|
||||
|
||||
private void addRowIfPossible(@NotNull ArrangementSettingType key,
|
||||
@NotNull Map<ArrangementSettingType, Set<?>> supportedSettings,
|
||||
@NotNull ArrangementNodeDisplayManager manager)
|
||||
{
|
||||
Set<?> values = supportedSettings.get(key);
|
||||
if (values == null || values.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
MultiRowFlowPanel valuesPanel = newRow(manager.getDisplayLabel(key));
|
||||
for (Object value : manager.sort(values)) {
|
||||
ArrangementAtomMatchConditionComponent component =
|
||||
new ArrangementAtomMatchConditionComponent(manager, myColorsProvider, new ArrangementAtomMatchCondition(key, value), null);
|
||||
myConditionComponents.put(value, component);
|
||||
valuesPanel.add(component.getUiComponent());
|
||||
}
|
||||
}
|
||||
|
||||
private void addNameFilterIfPossible() {
|
||||
if (!myFilter.isNameFilterSupported()) {
|
||||
return;
|
||||
}
|
||||
MultiRowFlowPanel panel = newRow(ApplicationBundle.message("arrangement.text.name"));
|
||||
panel.add(myNameField);
|
||||
}
|
||||
|
||||
private void addOrderRowIfPossible(@NotNull ArrangementNodeDisplayManager displayManager) {
|
||||
if (!myFilter.isNameFilterSupported()) {
|
||||
return;
|
||||
}
|
||||
MultiRowFlowPanel panel = newRow(ApplicationBundle.message("arrangement.order.name"));
|
||||
ArrangementEntryOrderType[] orderTypes = { ArrangementEntryOrderType.KEEP, ArrangementEntryOrderType.BY_NAME };
|
||||
int maxWidth = displayManager.getMaxWidth(orderTypes);
|
||||
for (ArrangementEntryOrderType type : orderTypes) {
|
||||
ArrangementOrderTypeComponent component = new ArrangementOrderTypeComponent(type, displayManager, myColorsProvider, maxWidth);
|
||||
panel.add(component);
|
||||
myOrderTypeComponents.put(type, component);
|
||||
}
|
||||
}
|
||||
|
||||
private MultiRowFlowPanel newRow(@NotNull String rowLabel) {
|
||||
MultiRowFlowPanel result = new MultiRowFlowPanel(
|
||||
private void addToken(@NotNull CompositeArrangementSettingsToken rowToken) {
|
||||
List<CompositeArrangementSettingsToken> tokens = ArrangementUtil.flatten(rowToken);
|
||||
GridBag labelConstraints = new GridBag().anchor(GridBagConstraints.NORTHWEST).insets(ArrangementConstants.VERTICAL_PADDING, 0, 0, 0);
|
||||
MultiRowFlowPanel panel = new MultiRowFlowPanel(
|
||||
FlowLayout.LEFT, ArrangementConstants.HORIZONTAL_GAP, ArrangementConstants.VERTICAL_GAP
|
||||
);
|
||||
JLabel label = new JLabel(rowLabel + ":");
|
||||
add(label, new GridBag().anchor(GridBagConstraints.NORTHWEST).insets(ArrangementConstants.VERTICAL_PADDING, 0, 0, 0));
|
||||
myLabelWidth = Math.max(myLabelWidth, label.getPreferredSize().width);
|
||||
|
||||
add(result, new GridBag().anchor(GridBagConstraints.WEST).weightx(1).fillCellHorizontally().coverLine());
|
||||
myRows.add(result);
|
||||
return result;
|
||||
}
|
||||
|
||||
private void scheduleNameUpdate() {
|
||||
myAlarm.cancelAllRequests();
|
||||
myAlarm.addRequest(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
updateName();
|
||||
List<ArrangementSettingsToken> prevTokens = ContainerUtilRt.newArrayList();
|
||||
StdArrangementTokenUiRole prevRole = null;
|
||||
ArrangementUiComponent component;
|
||||
JComponent uiComponent;
|
||||
for (CompositeArrangementSettingsToken token : tokens) {
|
||||
StdArrangementTokenUiRole role = token.getRole();
|
||||
if (role != prevRole && !prevTokens.isEmpty()) {
|
||||
component = ArrangementUtil.buildUiComponent(
|
||||
role, prevTokens, myColorsProvider, mySettingsManager
|
||||
);
|
||||
component.setListener(this);
|
||||
for (ArrangementSettingsToken prevToken : prevTokens) {
|
||||
myComponents.put(prevToken, component);
|
||||
}
|
||||
panel.add(component.getUiComponent());
|
||||
panel = addRowIfNecessary(panel);
|
||||
prevRole = null;
|
||||
prevTokens.clear();
|
||||
}
|
||||
}, ArrangementConstants.NAME_CONDITION_UPDATE_DELAY_MILLIS);
|
||||
component = ArrangementUtil.buildUiComponent(
|
||||
role, Collections.singletonList(token.getToken()), myColorsProvider, mySettingsManager
|
||||
);
|
||||
component.setListener(this);
|
||||
uiComponent = component.getUiComponent();
|
||||
switch (role) {
|
||||
case LABEL:
|
||||
panel = addRowIfNecessary(panel);
|
||||
add(uiComponent, labelConstraints);
|
||||
myLabelWidth = Math.max(myLabelWidth, uiComponent.getPreferredSize().width);
|
||||
prevRole = null;
|
||||
break;
|
||||
case TEXT_FIELD:
|
||||
panel = addRowIfNecessary(panel);
|
||||
|
||||
ArrangementUiComponent textLabel = ArrangementUtil.buildUiComponent(
|
||||
StdArrangementTokenUiRole.LABEL, Collections.singletonList(token.getToken()), myColorsProvider, mySettingsManager
|
||||
);
|
||||
JComponent textLabelComponent = textLabel.getUiComponent();
|
||||
add(textLabelComponent, labelConstraints);
|
||||
myLabelWidth = Math.max(myLabelWidth, textLabelComponent.getPreferredSize().width);
|
||||
|
||||
panel.add(uiComponent);
|
||||
panel = addRowIfNecessary(panel);
|
||||
prevRole = null;
|
||||
|
||||
myComponents.put(token.getToken(), component);
|
||||
|
||||
if (myDefaultFocusRequestor == null) {
|
||||
myDefaultFocusRequestor = uiComponent;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
if (role == StdArrangementTokenUiRole.COMBO_BOX) {
|
||||
prevTokens.add(token.getToken());
|
||||
prevRole = role;
|
||||
break;
|
||||
}
|
||||
|
||||
panel.add(uiComponent);
|
||||
myComponents.put(token.getToken(), component);
|
||||
}
|
||||
}
|
||||
|
||||
if (prevRole != null && !prevTokens.isEmpty()) {
|
||||
component = ArrangementUtil.buildUiComponent(prevRole, prevTokens, myColorsProvider, mySettingsManager);
|
||||
panel.add(component.getUiComponent());
|
||||
component.setListener(this);
|
||||
for (ArrangementSettingsToken prevToken : prevTokens) {
|
||||
myComponents.put(prevToken, component);
|
||||
}
|
||||
}
|
||||
addRowIfNecessary(panel);
|
||||
}
|
||||
|
||||
private void updateName() {
|
||||
myAlarm.cancelAllRequests();
|
||||
if (myRow < 0) {
|
||||
return;
|
||||
@NotNull
|
||||
private MultiRowFlowPanel addRowIfNecessary(@NotNull MultiRowFlowPanel panel) {
|
||||
if (panel.getComponentCount() <= 0) {
|
||||
return panel;
|
||||
}
|
||||
|
||||
String namePattern = myNameField.getText();
|
||||
if (StringUtil.isEmpty(namePattern)) {
|
||||
namePattern = null;
|
||||
}
|
||||
if (Comparing.equal(namePattern, myRuleInfo.getNamePattern())) {
|
||||
return;
|
||||
}
|
||||
myRuleInfo.setNamePattern(namePattern);
|
||||
apply();
|
||||
add(panel, new GridBag().anchor(GridBagConstraints.WEST).weightx(1).fillCellHorizontally().coverLine());
|
||||
myRows.add(panel);
|
||||
return new MultiRowFlowPanel(
|
||||
FlowLayout.LEFT, ArrangementConstants.HORIZONTAL_GAP, ArrangementConstants.VERTICAL_GAP
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void paintComponent(Graphics g) {
|
||||
if (myRequestFocus) {
|
||||
if (myNameField.isFocusOwner()) {
|
||||
myRequestFocus = false;
|
||||
public void stateChanged() {
|
||||
if (!mySkipStateChange) {
|
||||
apply();
|
||||
}
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private Pair<ArrangementMatchCondition, ArrangementSettingsToken> buildCondition() {
|
||||
List<ArrangementMatchCondition> conditions = ContainerUtilRt.newArrayList();
|
||||
ArrangementSettingsToken orderType = null;
|
||||
for (ArrangementUiComponent component : myComponents.values()) {
|
||||
if (!component.isEnabled() || !component.isSelected()) {
|
||||
continue;
|
||||
}
|
||||
ArrangementSettingsToken token = component.getToken();
|
||||
if (token != null && StdArrangementTokens.Order.is(token)) {
|
||||
orderType = token;
|
||||
}
|
||||
else {
|
||||
myNameField.requestFocusInWindow();
|
||||
conditions.add(component.getMatchCondition());
|
||||
}
|
||||
}
|
||||
if (orderType != null && !conditions.isEmpty()) {
|
||||
return Pair.create(ArrangementUtil.combine(conditions.toArray(new ArrangementMatchCondition[conditions.size()])), orderType);
|
||||
}
|
||||
else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void paintComponent(Graphics g) {
|
||||
if (myFocusRequestor != null) {
|
||||
if (myFocusRequestor.isFocusOwner()) {
|
||||
myFocusRequestor = null;
|
||||
}
|
||||
else {
|
||||
myFocusRequestor.requestFocusInWindow();
|
||||
}
|
||||
}
|
||||
super.paintComponent(g);
|
||||
@@ -213,17 +240,16 @@ public class ArrangementMatchingRuleEditor extends JPanel {
|
||||
*/
|
||||
public void reset(int row) {
|
||||
// Reset state.
|
||||
myNameField.setText("");
|
||||
myAlarm.cancelAllRequests();
|
||||
myRow = row;
|
||||
myRuleInfo.clear();
|
||||
myRequestFocus = true;
|
||||
for (ArrangementAtomMatchConditionComponent component : myConditionComponents.values()) {
|
||||
component.setEnabled(false);
|
||||
component.setSelected(false);
|
||||
myFocusRequestor = myDefaultFocusRequestor;
|
||||
mySkipStateChange = true;
|
||||
try {
|
||||
for (ArrangementUiComponent component : myComponents.values()) {
|
||||
component.reset();
|
||||
}
|
||||
}
|
||||
for (ArrangementOrderTypeComponent component : myOrderTypeComponents.values()) {
|
||||
component.setSelected(false);
|
||||
finally {
|
||||
mySkipStateChange = false;
|
||||
}
|
||||
|
||||
ArrangementMatchingRulesModel model = myControl.getModel();
|
||||
@@ -233,69 +259,69 @@ public class ArrangementMatchingRuleEditor extends JPanel {
|
||||
}
|
||||
|
||||
Object element = model.getElementAt(row);
|
||||
if (element instanceof EmptyArrangementRuleComponent) {
|
||||
// Disable conditions which are not applicable for empty rules (e.g. we don't want to enable 'volatile' condition
|
||||
// for java rearranger if no 'field' condition is selected.
|
||||
for (ArrangementAtomMatchConditionComponent component : myConditionComponents.values()) {
|
||||
ArrangementAtomMatchCondition condition = component.getMatchCondition();
|
||||
Map<ArrangementSettingType, Set<?>> map = ArrangementConfigUtil.buildAvailableConditions(myFilter, condition);
|
||||
component.setEnabled(map.get(condition.getType()).contains(condition.getValue()));
|
||||
}
|
||||
return;
|
||||
}
|
||||
if (!(element instanceof StdArrangementMatchRule)) {
|
||||
return;
|
||||
}
|
||||
|
||||
StdArrangementMatchRule rule = (StdArrangementMatchRule)element;
|
||||
myRuleInfo.setOrderType(rule.getOrderType());
|
||||
ArrangementOrderTypeComponent orderTypeComponent = myOrderTypeComponents.get(rule.getOrderType());
|
||||
if (orderTypeComponent != null) {
|
||||
orderTypeComponent.setSelected(true);
|
||||
}
|
||||
|
||||
ArrangementMatchCondition condition = rule.getMatcher().getCondition();
|
||||
ArrangementRuleInfo infoWithConditions = ArrangementUtil.extractConditions(condition);
|
||||
myRuleInfo.copyConditionsFrom(infoWithConditions);
|
||||
myNameField.setText(myRuleInfo.getNamePattern());
|
||||
|
||||
for (ArrangementAtomMatchConditionComponent component : myConditionComponents.values()) {
|
||||
if (myRuleInfo.hasCondition(component.getMatchCondition().getValue())) {
|
||||
component.setEnabled(true);
|
||||
component.setSelected(true);
|
||||
}
|
||||
}
|
||||
ArrangementSettingsToken orderType = element instanceof ArrangementMatchRule ? ((ArrangementMatchRule)element).getOrderType() : null;
|
||||
final ArrangementMatchCondition condition;
|
||||
final Set<ArrangementSettingsToken> conditionTokens;
|
||||
|
||||
refreshConditions();
|
||||
if (element instanceof EmptyArrangementRuleComponent) {
|
||||
// We need to disable conditions which are not applicable for empty rules (e.g. we don't want to enable 'volatile' condition
|
||||
// for java rearranger if no 'field' condition is selected.
|
||||
condition = null;
|
||||
conditionTokens = ContainerUtilRt.newHashSet();
|
||||
}
|
||||
else if (!(element instanceof StdArrangementMatchRule)) {
|
||||
return;
|
||||
}
|
||||
else {
|
||||
condition = ((StdArrangementMatchRule)element).getMatcher().getCondition();
|
||||
conditionTokens = ArrangementUtil.extractTokens(condition);
|
||||
}
|
||||
|
||||
mySkipStateChange = true;
|
||||
try {
|
||||
for (ArrangementUiComponent component : myComponents.values()) {
|
||||
ArrangementSettingsToken token = component.getToken();
|
||||
if (token != null && (token.equals(orderType) || mySettingsManager.isEnabled(token, condition))) {
|
||||
component.setEnabled(true);
|
||||
component.setSelected(conditionTokens.contains(token));
|
||||
}
|
||||
}
|
||||
|
||||
refreshConditions();
|
||||
}
|
||||
finally {
|
||||
mySkipStateChange = false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Disable conditions not applicable at the current context (e.g. disable 'synchronized' if no 'method' is selected).
|
||||
*/
|
||||
private void refreshConditions() {
|
||||
Map<ArrangementSettingType, Set<?>> available = ArrangementConfigUtil.buildAvailableConditions(myFilter, myRuleInfo.buildCondition());
|
||||
for (ArrangementAtomMatchConditionComponent component : myConditionComponents.values()) {
|
||||
ArrangementAtomMatchCondition c = component.getMatchCondition();
|
||||
Set<?> s = available.get(c.getType());
|
||||
if (s == null || !s.contains(c.getValue())) {
|
||||
if (myRuleInfo.hasCondition(c.getValue())) {
|
||||
removeCondition(component);
|
||||
}
|
||||
else {
|
||||
component.setEnabled(false);
|
||||
}
|
||||
Pair<ArrangementMatchCondition, ArrangementSettingsToken> pair = buildCondition();
|
||||
ArrangementMatchCondition condition = pair == null ? null : pair.first;
|
||||
for (ArrangementUiComponent component : myComponents.values()) {
|
||||
ArrangementSettingsToken token = component.getToken();
|
||||
if (token == null) {
|
||||
continue;
|
||||
}
|
||||
else if (s.contains(c.getValue()) && !component.isEnabled()) {
|
||||
component.setEnabled(true);
|
||||
boolean enabled = mySettingsManager.isEnabled(token, condition);
|
||||
component.setEnabled(enabled);
|
||||
if (!enabled) {
|
||||
component.setSelected(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void apply() {
|
||||
Object modelValue = myRuleInfo.buildRule();
|
||||
if (modelValue == null) {
|
||||
final Pair<ArrangementMatchCondition, ArrangementSettingsToken> pair = buildCondition();
|
||||
final Object modelValue;
|
||||
if (pair == null) {
|
||||
modelValue = new EmptyArrangementRuleComponent(myControl.getRowHeight(myRow));
|
||||
}
|
||||
else {
|
||||
modelValue = new StdArrangementMatchRule(new StdArrangementEntryMatcher(pair.first), pair.second);
|
||||
}
|
||||
myControl.getModel().set(myRow, modelValue);
|
||||
myControl.repaintRows(myRow, myRow, true);
|
||||
}
|
||||
@@ -320,13 +346,13 @@ public class ArrangementMatchingRuleEditor extends JPanel {
|
||||
}
|
||||
|
||||
Point locationOnScreen = e.getLocationOnScreen();
|
||||
for (ArrangementAtomMatchConditionComponent component : myConditionComponents.values()) {
|
||||
for (ArrangementUiComponent component : myComponents.values()) {
|
||||
Rectangle screenBounds = component.getScreenBounds();
|
||||
if (screenBounds == null || !screenBounds.contains(locationOnScreen)) {
|
||||
continue;
|
||||
}
|
||||
if (component.isEnabled()) {
|
||||
if (myRuleInfo.hasCondition(component.getMatchCondition().getValue())) {
|
||||
if (component.isSelected()) {
|
||||
removeCondition(component);
|
||||
}
|
||||
else {
|
||||
@@ -336,50 +362,37 @@ public class ArrangementMatchingRuleEditor extends JPanel {
|
||||
apply();
|
||||
return;
|
||||
}
|
||||
for (ArrangementOrderTypeComponent component : myOrderTypeComponents.values()) {
|
||||
Rectangle bounds = component.getScreenBounds();
|
||||
if (bounds == null || !bounds.contains(locationOnScreen)) {
|
||||
continue;
|
||||
}
|
||||
if (component.getOrderType() != myRuleInfo.getOrderType()) {
|
||||
ArrangementOrderTypeComponent orderTypeComponent = myOrderTypeComponents.get(myRuleInfo.getOrderType());
|
||||
if (orderTypeComponent != null) {
|
||||
orderTypeComponent.setSelected(false);
|
||||
}
|
||||
|
||||
private void addCondition(@NotNull ArrangementUiComponent component) {
|
||||
mySkipStateChange = true;
|
||||
try {
|
||||
component.setSelected(true);
|
||||
Collection<Set<ArrangementSettingsToken>> mutexes = mySettingsManager.getMutexes();
|
||||
|
||||
// Update 'mutex conditions', i.e. conditions which can't be active at the same time (e.g. type 'field' and type 'method').
|
||||
for (Set<ArrangementSettingsToken> mutex : mutexes) {
|
||||
if (!mutex.contains(component.getToken())) {
|
||||
continue;
|
||||
}
|
||||
orderTypeComponent = myOrderTypeComponents.get(component.getOrderType());
|
||||
if (orderTypeComponent != null) {
|
||||
orderTypeComponent.setSelected(true);
|
||||
for (ArrangementSettingsToken key : mutex) {
|
||||
if (key.equals(component.getToken())) {
|
||||
continue;
|
||||
}
|
||||
ArrangementUiComponent c = myComponents.get(key);
|
||||
if (c != null && c.isEnabled()) {
|
||||
removeCondition(c);
|
||||
}
|
||||
}
|
||||
myRuleInfo.setOrderType(component.getOrderType());
|
||||
apply();
|
||||
}
|
||||
return;
|
||||
refreshConditions();
|
||||
}
|
||||
finally {
|
||||
mySkipStateChange = false;
|
||||
}
|
||||
}
|
||||
|
||||
private void addCondition(@NotNull ArrangementAtomMatchConditionComponent component) {
|
||||
ArrangementAtomMatchCondition chosenCondition = component.getMatchCondition();
|
||||
myRuleInfo.addAtomCondition(chosenCondition);
|
||||
component.setSelected(true);
|
||||
Collection<Set<?>> mutexes = myFilter.getMutexes();
|
||||
|
||||
// Update 'mutex conditions', i.e. conditions which can't be active at the same time (e.g. type 'field' and type 'method').
|
||||
for (Set<?> mutex : mutexes) {
|
||||
if (!mutex.contains(chosenCondition.getValue())) {
|
||||
continue;
|
||||
}
|
||||
for (Object key : mutex) {
|
||||
if (!chosenCondition.getValue().equals(key) && myRuleInfo.hasCondition(key)) {
|
||||
removeCondition(myConditionComponents.get(key));
|
||||
myRuleInfo.addAtomCondition(chosenCondition);
|
||||
}
|
||||
}
|
||||
}
|
||||
refreshConditions();
|
||||
}
|
||||
|
||||
private void removeCondition(@NotNull ArrangementAtomMatchConditionComponent component) {
|
||||
myRuleInfo.removeCondition(component.getMatchCondition().getValue());
|
||||
private void removeCondition(@NotNull ArrangementUiComponent component) {
|
||||
component.setSelected(false);
|
||||
refreshConditions();
|
||||
}
|
||||
|
||||
+18
-15
@@ -16,20 +16,20 @@
|
||||
package com.intellij.application.options.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.application.options.codeStyle.arrangement.component.*;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ui.ArrangementEditorAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ui.ArrangementRepresentationAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.ArrangementListRowDecorator;
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.IntObjectMap;
|
||||
import com.intellij.openapi.actionSystem.DataKey;
|
||||
import com.intellij.openapi.application.ApplicationBundle;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementEntryMatcher;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementUiComponent;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens;
|
||||
import com.intellij.ui.table.JBTable;
|
||||
import com.intellij.util.ui.AbstractTableCellEditor;
|
||||
import gnu.trove.TIntArrayList;
|
||||
@@ -56,6 +56,8 @@ import java.util.List;
|
||||
*/
|
||||
public class ArrangementMatchingRulesControl extends JBTable {
|
||||
|
||||
@NotNull public static final DataKey<ArrangementMatchingRulesControl> KEY = DataKey.create("Arrangement.Rule.Match.Control");
|
||||
|
||||
@NotNull private static final Logger LOG = Logger.getInstance("#" + ArrangementMatchingRulesControl.class.getName());
|
||||
@NotNull private static final JLabel EMPTY_RENDERER = new JLabel(ApplicationBundle.message("arrangement.text.empty.rule"));
|
||||
|
||||
@@ -72,14 +74,13 @@ public class ArrangementMatchingRulesControl extends JBTable {
|
||||
private int myEditorRow = -1;
|
||||
private boolean mySkipSelectionChange;
|
||||
|
||||
public ArrangementMatchingRulesControl(@NotNull ArrangementNodeDisplayManager displayManager,
|
||||
public ArrangementMatchingRulesControl(@NotNull ArrangementStandardSettingsManager settingsManager,
|
||||
@NotNull ArrangementColorsProvider colorsProvider,
|
||||
@NotNull ArrangementStandardSettingsAware settingsFilter,
|
||||
@NotNull RepresentationCallback callback)
|
||||
{
|
||||
super(new ArrangementMatchingRulesModel());
|
||||
myRepresentationCallback = callback;
|
||||
myFactory = new ArrangementMatchNodeComponentFactory(displayManager, colorsProvider, this);
|
||||
myFactory = new ArrangementMatchNodeComponentFactory(settingsManager, colorsProvider, this);
|
||||
myRenderer = new MyRenderer();
|
||||
setDefaultRenderer(Object.class, myRenderer);
|
||||
getColumnModel().getColumn(0).setCellEditor(new MyEditor());
|
||||
@@ -89,12 +90,12 @@ public class ArrangementMatchingRulesControl extends JBTable {
|
||||
setSurrendersFocusOnKeystroke(true);
|
||||
putClientProperty("terminateEditOnFocusLost", Boolean.TRUE);
|
||||
|
||||
ArrangementAtomMatchCondition condition = new ArrangementAtomMatchCondition(ArrangementSettingType.TYPE, ArrangementEntryType.CLASS);
|
||||
ArrangementAtomMatchCondition condition = new ArrangementAtomMatchCondition(StdArrangementTokens.EntryType.CLASS);
|
||||
StdArrangementMatchRule rule = new StdArrangementMatchRule(new StdArrangementEntryMatcher(condition));
|
||||
ArrangementMatchConditionComponent component = myFactory.getComponent(condition, rule, true);
|
||||
ArrangementUiComponent component = myFactory.getComponent(condition, rule, true);
|
||||
myMinRowHeight = new ArrangementListRowDecorator(component, this).getPreferredSize().height;
|
||||
|
||||
myEditor = new ArrangementMatchingRuleEditor(settingsFilter, colorsProvider, displayManager, this);
|
||||
myEditor = new ArrangementMatchingRuleEditor(settingsManager, colorsProvider, this);
|
||||
addMouseMotionListener(new MouseAdapter() {
|
||||
@Override
|
||||
public void mouseMoved(MouseEvent e) {
|
||||
@@ -108,7 +109,8 @@ public class ArrangementMatchingRulesControl extends JBTable {
|
||||
}
|
||||
});
|
||||
getModel().addTableModelListener(new TableModelListener() {
|
||||
@Override public void tableChanged(TableModelEvent e) { onTableChange(e); }
|
||||
@Override
|
||||
public void tableChanged(TableModelEvent e) { onTableChange(e); }
|
||||
});
|
||||
}
|
||||
|
||||
@@ -467,7 +469,7 @@ public class ArrangementMatchingRulesControl extends JBTable {
|
||||
return EMPTY_RENDERER;
|
||||
}
|
||||
StdArrangementMatchRule rule = (StdArrangementMatchRule)value;
|
||||
ArrangementMatchConditionComponent ruleComponent = myFactory.getComponent(rule.getMatcher().getCondition(), rule, true);
|
||||
ArrangementUiComponent ruleComponent = myFactory.getComponent(rule.getMatcher().getCondition(), rule, true);
|
||||
component = new ArrangementListRowDecorator(ruleComponent, ArrangementMatchingRulesControl.this);
|
||||
myComponents.set(row, component);
|
||||
}
|
||||
@@ -477,12 +479,13 @@ public class ArrangementMatchingRulesControl extends JBTable {
|
||||
component.setSelected(getSelectionModel().isSelectedIndex(row) || (myEditorRow >= 0 && row == myEditorRow - 1));
|
||||
component.setBeingEdited(myEditorRow >= 0 && myEditorRow == row + 1);
|
||||
boolean showSortIcon = value instanceof StdArrangementMatchRule
|
||||
&& ((StdArrangementMatchRule)value).getOrderType() == ArrangementEntryOrderType.BY_NAME;
|
||||
&& StdArrangementTokens.Order.BY_NAME.equals(((StdArrangementMatchRule)value).getOrderType());
|
||||
component.setShowSortIcon(showSortIcon);
|
||||
return component.getUiComponent();
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressWarnings("ConstantConditions")
|
||||
private class MyEditor extends AbstractTableCellEditor {
|
||||
|
||||
private int myRow;
|
||||
|
||||
+1
-1
@@ -16,7 +16,7 @@
|
||||
package com.intellij.application.options.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.component.ArrangementEditorAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ui.ArrangementEditorAware;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
|
||||
+5
-7
@@ -16,14 +16,13 @@
|
||||
package com.intellij.application.options.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.TitleWithToolbar;
|
||||
import com.intellij.ide.ui.customization.CustomizationUtil;
|
||||
import com.intellij.openapi.actionSystem.DataProvider;
|
||||
import com.intellij.openapi.application.ApplicationBundle;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsAware;
|
||||
import com.intellij.ui.components.JBScrollPane;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
@@ -42,9 +41,8 @@ public class ArrangementMatchingRulesPanel extends JPanel implements DataProvide
|
||||
|
||||
@NotNull private final ArrangementMatchingRulesControl myControl;
|
||||
|
||||
public ArrangementMatchingRulesPanel(@NotNull ArrangementNodeDisplayManager displayManager,
|
||||
@NotNull ArrangementColorsProvider colorsProvider,
|
||||
@NotNull ArrangementStandardSettingsAware settingsFilter)
|
||||
public ArrangementMatchingRulesPanel(@NotNull ArrangementStandardSettingsManager settingsManager,
|
||||
@NotNull ArrangementColorsProvider colorsProvider)
|
||||
{
|
||||
super(new GridBagLayout());
|
||||
|
||||
@@ -69,7 +67,7 @@ public class ArrangementMatchingRulesPanel extends JPanel implements DataProvide
|
||||
}
|
||||
}
|
||||
};
|
||||
myControl = new ArrangementMatchingRulesControl(displayManager, colorsProvider, settingsFilter, callback);
|
||||
myControl = new ArrangementMatchingRulesControl(settingsManager, colorsProvider, callback);
|
||||
scrollPane.setViewportView(myControl);
|
||||
CustomizationUtil.installPopupHandler(
|
||||
myControl, ArrangementConstants.ACTION_GROUP_MATCHING_RULES_CONTEXT_MENU, ArrangementConstants.MATCHING_RULES_CONTROL_PLACE
|
||||
@@ -97,7 +95,7 @@ public class ArrangementMatchingRulesPanel extends JPanel implements DataProvide
|
||||
@Nullable
|
||||
@Override
|
||||
public Object getData(@NonNls String dataId) {
|
||||
if (ArrangementConstants.MATCHING_RULES_CONTROL_KEY.is(dataId)) {
|
||||
if (ArrangementMatchingRulesControl.KEY.is(dataId)) {
|
||||
return myControl;
|
||||
}
|
||||
return null;
|
||||
|
||||
-104
@@ -1,104 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.application.options.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.application.options.codeStyle.arrangement.color.ArrangementColorsProvider;
|
||||
import com.intellij.application.options.codeStyle.arrangement.util.ArrangementConfigUtil;
|
||||
import com.intellij.openapi.editor.markup.TextAttributes;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.ui.IdeBorderFactory;
|
||||
import com.intellij.ui.SideBorder;
|
||||
import com.intellij.ui.SimpleColoredComponent;
|
||||
import com.intellij.ui.SimpleTextAttributes;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 11/15/12 1:01 PM
|
||||
*/
|
||||
public class ArrangementOrderTypeComponent extends JPanel {
|
||||
|
||||
@NotNull
|
||||
private final SimpleColoredComponent myTextControl = new SimpleColoredComponent() {
|
||||
@Override public Dimension getMinimumSize() { return getPreferredSize(); }
|
||||
|
||||
@Override public Dimension getMaximumSize() { return getPreferredSize(); }
|
||||
|
||||
@Override public Dimension getPreferredSize() { return myTextControlSize == null ? super.getPreferredSize() : myTextControlSize; }
|
||||
|
||||
@Override public String toString() { return "text component for " + this; }
|
||||
};
|
||||
@NotNull private final ArrangementEntryOrderType myOrderType;
|
||||
@NotNull private final ArrangementColorsProvider myColorsProvider;
|
||||
@NotNull private final String myText;
|
||||
@NotNull private final SideBorder myBorder;
|
||||
@Nullable private final Dimension myTextControlSize;
|
||||
@Nullable private Rectangle myScreenBounds;
|
||||
|
||||
public ArrangementOrderTypeComponent(@NotNull ArrangementEntryOrderType orderType,
|
||||
@NotNull ArrangementNodeDisplayManager displayManager,
|
||||
@NotNull ArrangementColorsProvider colorsProvider,
|
||||
int width)
|
||||
{
|
||||
super(new GridBagLayout());
|
||||
myOrderType = orderType;
|
||||
myColorsProvider = colorsProvider;
|
||||
myTextControl.setTextAlign(SwingConstants.CENTER);
|
||||
myText = displayManager.getDisplayValue(orderType);
|
||||
TextAttributes attributes = colorsProvider.getTextAttributes(ArrangementSettingType.ORDER, false);
|
||||
myTextControl.append(myText, SimpleTextAttributes.fromTextAttributes(attributes));
|
||||
myTextControlSize = new Dimension(width, myTextControl.getPreferredSize().height);
|
||||
|
||||
add(myTextControl, new GridBag().anchor(GridBagConstraints.WEST));
|
||||
setBorder(myBorder = (SideBorder)IdeBorderFactory.createBorder());
|
||||
}
|
||||
|
||||
public void setSelected(boolean selected) {
|
||||
myTextControl.clear();
|
||||
TextAttributes attributes = myColorsProvider.getTextAttributes(ArrangementSettingType.ORDER, selected);
|
||||
myTextControl.append(myText, SimpleTextAttributes.fromTextAttributes(attributes));
|
||||
myBorder.setLineColor(myColorsProvider.getBorderColor(selected));
|
||||
Color myBackgroundColor = attributes.getBackgroundColor();
|
||||
myTextControl.setBackground(myBackgroundColor);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void paintComponent(Graphics g) {
|
||||
Point point = ArrangementConfigUtil.getLocationOnScreen(this);
|
||||
if (point != null) {
|
||||
Rectangle bounds = getBounds();
|
||||
myScreenBounds = new Rectangle(point.x, point.y, bounds.width, bounds.height);
|
||||
}
|
||||
super.paintComponent(g);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public ArrangementEntryOrderType getOrderType() {
|
||||
return myOrderType;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public Rectangle getScreenBounds() {
|
||||
return myScreenBounds;
|
||||
}
|
||||
}
|
||||
+1
-2
@@ -15,8 +15,7 @@
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.match;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.component.ArrangementRepresentationAware;
|
||||
import com.intellij.application.options.codeStyle.arrangement.ui.ArrangementRepresentationAware;
|
||||
import com.intellij.openapi.application.ApplicationBundle;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
|
||||
-94
@@ -1,94 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.application.options.codeStyle.arrangement.node;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.ui.components.JBCheckBox;
|
||||
import com.intellij.util.Consumer;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.awt.event.ItemEvent;
|
||||
import java.awt.event.ItemListener;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 9/27/12 3:10 PM
|
||||
*/
|
||||
public class ArrangementCheckBoxNode<T>/* extends ArrangementTreeNode
|
||||
implements ArrangementRepresentationAwareNode, ArrangementEditableNode*/
|
||||
{
|
||||
@NotNull private final JPanel myRenderer = new JPanel(new GridBagLayout());
|
||||
@NotNull private final JBCheckBox myCheckBox = new JBCheckBox();
|
||||
|
||||
@NotNull private final T myData;
|
||||
|
||||
@Nullable private Consumer<ArrangementCheckBoxNode<T>> myListener;
|
||||
|
||||
public ArrangementCheckBoxNode(@NotNull ArrangementNodeDisplayManager displayManager, @NotNull T data) {
|
||||
//super(null);
|
||||
myCheckBox.setText(displayManager.getDisplayValue(data));
|
||||
myData = data;
|
||||
myCheckBox.setBackground(UIUtil.getTreeBackground());
|
||||
myRenderer.add(myCheckBox, new GridBag().anchor(GridBagConstraints.WEST));
|
||||
myCheckBox.addItemListener(new ItemListener() {
|
||||
@Override
|
||||
public void itemStateChanged(ItemEvent e) {
|
||||
if (myListener != null) {
|
||||
myListener.consume(ArrangementCheckBoxNode.this);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@NotNull
|
||||
//@Override
|
||||
public JComponent getRenderer() {
|
||||
return myRenderer;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
//@Override
|
||||
public JComponent getEditor() {
|
||||
return myRenderer;
|
||||
}
|
||||
|
||||
public boolean isSelected() {
|
||||
return myCheckBox.isSelected();
|
||||
}
|
||||
|
||||
public void setSelected(boolean selected) {
|
||||
myCheckBox.setSelected(selected);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public T getValue() {
|
||||
return myData;
|
||||
}
|
||||
|
||||
public void setChangeCallback(@Nullable Consumer<ArrangementCheckBoxNode<T>> listener) {
|
||||
myListener = listener;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return myData.toString();
|
||||
}
|
||||
}
|
||||
-86
@@ -1,86 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.application.options.codeStyle.arrangement.node;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementNodeDisplayManager;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 9/27/12 5:01 PM
|
||||
*/
|
||||
public class ArrangementComboBoxNode<T> /*extends ArrangementTreeNode implements ArrangementRepresentationAwareNode, ArrangementEditableNode*/ {
|
||||
|
||||
@NotNull private final JPanel myControl = new JPanel(new GridBagLayout());
|
||||
@NotNull private final JLabel myLabel = new JLabel();
|
||||
@NotNull private final JComboBox myComboBox = new JComboBox();
|
||||
@NotNull private final List<T> myData = new ArrayList<T>();
|
||||
|
||||
public ArrangementComboBoxNode(@NotNull ArrangementNodeDisplayManager displayManager, @NotNull String text, @NotNull Iterable<T> data) {
|
||||
//super(null);
|
||||
for (T t : data) {
|
||||
myData.add(t);
|
||||
myComboBox.addItem(displayManager.getDisplayValue(t));
|
||||
}
|
||||
myLabel.setText(text);
|
||||
myControl.add(myLabel, new GridBag().setColumn(0).insets(0, 3, 0, 0));
|
||||
myControl.add(myComboBox, new GridBag().setColumn(1));
|
||||
}
|
||||
|
||||
@NotNull
|
||||
//@Override
|
||||
public JComponent getEditor() {
|
||||
return myControl;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
//@Override
|
||||
public JComponent getRenderer() {
|
||||
return myControl;
|
||||
}
|
||||
|
||||
public void setEnabled(boolean enabled) {
|
||||
myLabel.setEnabled(enabled);
|
||||
myComboBox.setEnabled(enabled);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public T getSelectedValue() {
|
||||
int index = myComboBox.getSelectedIndex();
|
||||
if (index < 0 || index >= myData.size()) {
|
||||
return myData.get(0);
|
||||
}
|
||||
return myData.get(index);
|
||||
}
|
||||
|
||||
public void setSelectedValue(@NotNull T value) {
|
||||
int i = myData.indexOf(value);
|
||||
if (i >= 0) {
|
||||
myComboBox.setSelectedIndex(i);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return myData.toString();
|
||||
}
|
||||
}
|
||||
-31
@@ -1,31 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.application.options.codeStyle.arrangement.node;
|
||||
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import javax.swing.*;
|
||||
import javax.swing.tree.TreeNode;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 9/27/12 4:44 PM
|
||||
*/
|
||||
public interface ArrangementEditableNode extends TreeNode {
|
||||
|
||||
@NotNull
|
||||
JComponent getEditor();
|
||||
}
|
||||
-31
@@ -1,31 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.application.options.codeStyle.arrangement.node;
|
||||
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import javax.swing.*;
|
||||
import javax.swing.tree.TreeNode;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 9/27/12 2:48 PM
|
||||
*/
|
||||
public interface ArrangementRepresentationAwareNode extends TreeNode {
|
||||
|
||||
@NotNull
|
||||
JComponent getRenderer();
|
||||
}
|
||||
-46
@@ -1,46 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.application.options.codeStyle.arrangement.node;
|
||||
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import javax.swing.*;
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 9/27/12 2:24 PM
|
||||
*/
|
||||
public class ArrangementSectionNode /*extends ArrangementTreeNode implements ArrangementRepresentationAwareNode*/ {
|
||||
|
||||
@NotNull private final JPanel myRenderer = new JPanel();
|
||||
@NotNull private final JLabel myTextLabel = new JLabel();
|
||||
|
||||
public ArrangementSectionNode(@NotNull String text) {
|
||||
//super(null);
|
||||
myTextLabel.setText(text);
|
||||
myRenderer.add(myTextLabel);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public JComponent getRenderer() {
|
||||
return myRenderer;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return String.format("section '%s'", myTextLabel.getText());
|
||||
}
|
||||
}
|
||||
+2
-3
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2012 JetBrains s.r.o.
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -13,10 +13,9 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.component;
|
||||
package com.intellij.application.options.codeStyle.arrangement.ui;
|
||||
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
|
||||
+2
-2
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2012 JetBrains s.r.o.
|
||||
* Copyright 2000-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -13,7 +13,7 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.application.options.codeStyle.arrangement.component;
|
||||
package com.intellij.application.options.codeStyle.arrangement.ui;
|
||||
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
-117
@@ -1,117 +0,0 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.application.options.codeStyle.arrangement.util;
|
||||
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementSettingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsAware;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.util.EnumMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* Contains various utility methods to be used during showing arrangement settings.
|
||||
* <p/>
|
||||
* Thread-safe.
|
||||
*
|
||||
* @author Denis Zhdanov
|
||||
* @since 8/8/12 9:14 AM
|
||||
*/
|
||||
public class ArrangementConfigUtil {
|
||||
|
||||
private ArrangementConfigUtil() {
|
||||
}
|
||||
|
||||
/**
|
||||
* Allows to answer what settings are available for a particular match condition.
|
||||
*
|
||||
* @param filter filter to use
|
||||
* @param condition object that encapsulates information about current arrangement matcher settings
|
||||
* @return map which contains information on what settings are available at the current situation
|
||||
*/
|
||||
@NotNull
|
||||
public static Map<ArrangementSettingType, Set<?>> buildAvailableConditions(@NotNull ArrangementStandardSettingsAware filter,
|
||||
@Nullable ArrangementMatchCondition condition)
|
||||
{
|
||||
Map<ArrangementSettingType, Set<?>> result = new EnumMap<ArrangementSettingType, Set<?>>(ArrangementSettingType.class);
|
||||
processData(filter, condition, result, ArrangementSettingType.TYPE, ArrangementEntryType.values());
|
||||
processData(filter, condition, result, ArrangementSettingType.MODIFIER, ArrangementModifier.values());
|
||||
return result;
|
||||
}
|
||||
|
||||
private static <T> void processData(@NotNull ArrangementStandardSettingsAware filter,
|
||||
@Nullable ArrangementMatchCondition settings,
|
||||
@NotNull Map<ArrangementSettingType, Set<?>> result,
|
||||
@NotNull ArrangementSettingType type,
|
||||
@NotNull T[] values)
|
||||
{
|
||||
Set<T> data = null;
|
||||
for (T v : values) {
|
||||
if (!isEnabled(v, filter, settings)) {
|
||||
continue;
|
||||
}
|
||||
if (data == null) {
|
||||
data = new HashSet<T>();
|
||||
}
|
||||
data.add(v);
|
||||
}
|
||||
if (data != null) {
|
||||
result.put(type, data);
|
||||
}
|
||||
}
|
||||
|
||||
public static boolean isEnabled(@NotNull Object conditionId,
|
||||
@NotNull ArrangementStandardSettingsAware filter,
|
||||
@Nullable ArrangementMatchCondition condition)
|
||||
{
|
||||
if (conditionId instanceof ArrangementEntryType) {
|
||||
return filter.isEnabled((ArrangementEntryType)conditionId, condition);
|
||||
}
|
||||
else if (conditionId instanceof ArrangementModifier) {
|
||||
return filter.isEnabled((ArrangementModifier)conditionId, condition);
|
||||
}
|
||||
else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static Point getLocationOnScreen(@NotNull JComponent component) {
|
||||
int dx = 0;
|
||||
int dy = 0;
|
||||
for (Container c = component; c != null; c = c.getParent()) {
|
||||
if (c.isShowing()) {
|
||||
Point locationOnScreen = c.getLocationOnScreen();
|
||||
locationOnScreen.translate(dx, dy);
|
||||
return locationOnScreen;
|
||||
}
|
||||
else {
|
||||
Point location = c.getLocation();
|
||||
dx += location.x;
|
||||
dy += location.y;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
+43
-11
@@ -16,7 +16,6 @@
|
||||
package com.intellij.application.options.codeStyle.arrangement.util;
|
||||
|
||||
import com.intellij.application.options.codeStyle.arrangement.ArrangementConstants;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchConditionComponent;
|
||||
import com.intellij.application.options.codeStyle.arrangement.match.ArrangementMatchingRulesControl;
|
||||
import com.intellij.icons.AllIcons;
|
||||
import com.intellij.openapi.actionSystem.ActionManager;
|
||||
@@ -25,6 +24,8 @@ import com.intellij.openapi.actionSystem.Presentation;
|
||||
import com.intellij.openapi.actionSystem.Toggleable;
|
||||
import com.intellij.openapi.actionSystem.impl.ActionButton;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementUiComponent;
|
||||
import com.intellij.ui.IdeBorderFactory;
|
||||
import com.intellij.ui.SimpleColoredComponent;
|
||||
import com.intellij.util.ui.GridBag;
|
||||
@@ -40,28 +41,28 @@ import java.awt.event.MouseEvent;
|
||||
* @author Denis Zhdanov
|
||||
* @since 10/31/12 5:00 PM
|
||||
*/
|
||||
public class ArrangementListRowDecorator extends JPanel implements ArrangementMatchConditionComponent {
|
||||
public class ArrangementListRowDecorator extends JPanel implements ArrangementUiComponent {
|
||||
|
||||
@NotNull private final JLabel mySortLabel = new JLabel(AllIcons.Icons.Inspector.SortByName);
|
||||
|
||||
@NotNull private final ArrangementRuleIndexControl myRowIndexControl;
|
||||
@NotNull private final ArrangementMatchConditionComponent myDelegate;
|
||||
@NotNull private final ArrangementMatchingRulesControl myControl;
|
||||
@NotNull private final MyActionButton myEditButton;
|
||||
@NotNull private final ArrangementRuleIndexControl myRowIndexControl;
|
||||
@NotNull private final ArrangementUiComponent myDelegate;
|
||||
@NotNull private final ArrangementMatchingRulesControl myControl;
|
||||
@NotNull private final MyActionButton myEditButton;
|
||||
|
||||
@Nullable private Rectangle myScreenBounds;
|
||||
|
||||
private boolean myBeingEdited;
|
||||
private boolean myUnderMouse;
|
||||
|
||||
public ArrangementListRowDecorator(@NotNull ArrangementMatchConditionComponent delegate,
|
||||
public ArrangementListRowDecorator(@NotNull ArrangementUiComponent delegate,
|
||||
@NotNull ArrangementMatchingRulesControl control)
|
||||
{
|
||||
myDelegate = delegate;
|
||||
myControl = control;
|
||||
|
||||
|
||||
mySortLabel.setVisible(false);
|
||||
|
||||
|
||||
AnAction action = ActionManager.getInstance().getAction("Arrangement.Rule.Edit");
|
||||
Presentation presentation = action.getTemplatePresentation().clone();
|
||||
Icon editIcon = presentation.getIcon();
|
||||
@@ -95,7 +96,7 @@ public class ArrangementListRowDecorator extends JPanel implements ArrangementMa
|
||||
|
||||
@Override
|
||||
protected void paintComponent(Graphics g) {
|
||||
Point point = ArrangementConfigUtil.getLocationOnScreen(this);
|
||||
Point point = UIUtil.getLocationOnScreen(this);
|
||||
if (point != null) {
|
||||
Rectangle bounds = getBounds();
|
||||
myScreenBounds = new Rectangle(point.x, point.y, bounds.width, bounds.height);
|
||||
@@ -228,7 +229,38 @@ public class ArrangementListRowDecorator extends JPanel implements ArrangementMa
|
||||
Rectangle bounds = myEditButton.getBounds();
|
||||
return new Rectangle(bounds.x + myScreenBounds.x, bounds.y + myScreenBounds.y, bounds.width, bounds.height);
|
||||
}
|
||||
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public ArrangementSettingsToken getToken() {
|
||||
return myDelegate.getToken();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void chooseToken(@NotNull ArrangementSettingsToken data) throws IllegalArgumentException, UnsupportedOperationException {
|
||||
myDelegate.chooseToken(data);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSelected() {
|
||||
return myDelegate.isSelected();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void reset() {
|
||||
myDelegate.reset();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getBaselineToUse(int width, int height) {
|
||||
return myDelegate.getBaselineToUse(width, height);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setListener(@NotNull Listener listener) {
|
||||
myDelegate.setListener(listener);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "list row decorator for " + myDelegate.toString();
|
||||
|
||||
+1
-1
@@ -20,7 +20,7 @@ import com.intellij.openapi.util.Pair;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.codeStyle.CommonCodeStyleSettings;
|
||||
import com.intellij.psi.codeStyle.arrangement.engine.ArrangementEngine;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsAware;
|
||||
import com.intellij.util.containers.HashSet;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
+6
-6
@@ -32,8 +32,8 @@ import com.intellij.psi.codeStyle.arrangement.ArrangementSettings;
|
||||
import com.intellij.psi.codeStyle.arrangement.NameAwareArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.Rearranger;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import com.intellij.util.containers.HashSet;
|
||||
@@ -226,9 +226,9 @@ public class ArrangementEngine {
|
||||
public static <E extends ArrangementEntry> List<E> arrange(@NotNull Collection<E> entries,
|
||||
@NotNull List<? extends ArrangementMatchRule> rules)
|
||||
{
|
||||
List<E> arranged = new ArrayList<E>();
|
||||
Set<E> unprocessed = new LinkedHashSet<E>();
|
||||
List<Pair<Set<ArrangementEntry>, E>> dependent = new ArrayList<Pair<Set<ArrangementEntry>, E>>();
|
||||
List<E> arranged = ContainerUtilRt.newArrayList();
|
||||
Set<E> unprocessed = ContainerUtilRt.newLinkedHashSet();
|
||||
List<Pair<Set<ArrangementEntry>, E>> dependent = ContainerUtilRt.newArrayList();
|
||||
for (E entry : entries) {
|
||||
List<? extends ArrangementEntry> dependencies = entry.getDependencies();
|
||||
if (dependencies == null) {
|
||||
@@ -261,7 +261,7 @@ public class ArrangementEngine {
|
||||
unprocessed.removeAll(matched);
|
||||
|
||||
// Sort by name if necessary.
|
||||
if (rule.getOrderType() == ArrangementEntryOrderType.BY_NAME) {
|
||||
if (StdArrangementTokens.Order.BY_NAME.equals(rule.getOrderType())) {
|
||||
sortByName(arranged, startIndex);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,7 +29,7 @@ import java.util.ResourceBundle;
|
||||
public class ApplicationBundle {
|
||||
private static Reference<ResourceBundle> ourBundle;
|
||||
|
||||
@NonNls private static final String BUNDLE = "messages.ApplicationBundle";
|
||||
@NonNls public static final String BUNDLE = "messages.ApplicationBundle";
|
||||
|
||||
private ApplicationBundle() {
|
||||
}
|
||||
|
||||
@@ -589,6 +589,12 @@ arrangement.settings.order.type.keep=keep order
|
||||
arrangement.settings.order.type.by.name=order by name
|
||||
arrangement.settings.order.type.depth.first=depth-first order
|
||||
arrangement.settings.order.type.breadth.first=breadth-first order
|
||||
arrangement.settings.text.general.type=Type:
|
||||
arrangement.settings.text.general.modifier=Modifier:
|
||||
arrangement.settings.text.general.name=Name:
|
||||
arrangement.settings.text.general.order=Order:
|
||||
arrangement.settings.text.entry.type.xml.tag=tag
|
||||
arrangement.settings.text.entry.type.xml.attribute=attribute
|
||||
|
||||
checkbox.spaces.around.lambda.arrow=Lambda arrow
|
||||
checkbox.spaces.around.method.ref.dbl.colon.arrow=Method reference double colon
|
||||
@@ -186,6 +186,7 @@
|
||||
<extensionPoint name="lang.rearranger" beanClass="com.intellij.lang.LanguageExtensionPoint">
|
||||
<with attribute="implementationClass" implements="com.intellij.psi.codeStyle.arrangement.Rearranger"/>
|
||||
</extensionPoint>
|
||||
<extensionPoint name="rearranger.ui" interface="com.intellij.psi.codeStyle.arrangement.std.ArrangementUiComponent$Factory"/>
|
||||
|
||||
<extensionPoint name="lang.surroundDescriptor" beanClass="com.intellij.lang.LanguageExtensionPoint">
|
||||
<with attribute="implementationClass" implements="com.intellij.lang.surroundWith.SurroundDescriptor"/>
|
||||
|
||||
@@ -189,6 +189,7 @@
|
||||
|
||||
<applicationService serviceImplementation="com.intellij.psi.codeStyle.arrangement.engine.ArrangementEngine"/>
|
||||
<applicationService serviceImplementation="com.intellij.psi.codeStyle.arrangement.MemberOrderService"/>
|
||||
<rearranger.ui implementation="com.intellij.application.options.codeStyle.arrangement.component.DefaultArrangementUiComponentFactory"/>
|
||||
|
||||
<projectService serviceInterface="com.intellij.ui.EditorTextFieldProvider"
|
||||
serviceImplementation="com.intellij.ui.EditorTextFieldProviderImpl"/>
|
||||
|
||||
+46
-18
@@ -24,16 +24,18 @@ import com.intellij.psi.codeStyle.CodeStyleSettingsManager
|
||||
import com.intellij.psi.codeStyle.CommonCodeStyleSettings
|
||||
import com.intellij.psi.codeStyle.arrangement.engine.ArrangementEngine
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingRule
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementEntryMatcher
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementAtomMatchCondition
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementSettings
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens
|
||||
import com.intellij.testFramework.fixtures.LightPlatformCodeInsightFixtureTestCase
|
||||
import org.jetbrains.annotations.NotNull
|
||||
import org.junit.Assert
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Order.KEEP
|
||||
|
||||
/**
|
||||
* @author Denis Zhdanov
|
||||
* @since 7/20/12 2:54 PM
|
||||
@@ -63,36 +65,62 @@ abstract class AbstractRearrangerTest extends LightPlatformCodeInsightFixtureTes
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected static ArrangementGroupingRule group(@NotNull ArrangementGroupingType type) {
|
||||
group(type, ArrangementEntryOrderType.KEEP)
|
||||
protected static ArrangementGroupingRule group(@NotNull ArrangementSettingsToken type) {
|
||||
group(type, KEEP)
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected static ArrangementGroupingRule group(@NotNull ArrangementGroupingType type, @NotNull ArrangementEntryOrderType order) {
|
||||
protected static ArrangementGroupingRule group(@NotNull ArrangementSettingsToken type, @NotNull ArrangementSettingsToken order) {
|
||||
new ArrangementGroupingRule(type, order)
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected static StdArrangementMatchRule rule(@NotNull Object ... conditions) {
|
||||
rule(ArrangementEntryOrderType.KEEP, conditions)
|
||||
protected static StdArrangementMatchRule rule(@NotNull ArrangementSettingsToken token) {
|
||||
new StdArrangementMatchRule(new StdArrangementEntryMatcher(atom(token)))
|
||||
}
|
||||
|
||||
|
||||
@NotNull
|
||||
protected static StdArrangementMatchRule rule(@NotNull ArrangementEntryOrderType orderType, @NotNull Object ... conditions) {
|
||||
def condition
|
||||
if (conditions.length == 1) {
|
||||
condition = atom(conditions[0])
|
||||
protected static StdArrangementMatchRule nameRule(@NotNull String nameFilter, @NotNull ArrangementSettingsToken ... tokens) {
|
||||
if (tokens.length == 0) {
|
||||
new StdArrangementMatchRule(new StdArrangementEntryMatcher(atom(nameFilter)))
|
||||
}
|
||||
else {
|
||||
condition = ArrangementUtil.combine(conditions.collect { atom(it) } as ArrangementMatchCondition[])
|
||||
def compositeCondition = ArrangementUtil.combine([atom(nameFilter)] + tokens.collect { atom(it) } as ArrangementAtomMatchCondition[])
|
||||
new StdArrangementMatchRule(new StdArrangementEntryMatcher(compositeCondition))
|
||||
}
|
||||
|
||||
new StdArrangementMatchRule(new StdArrangementEntryMatcher(condition), orderType)
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected static ArrangementAtomMatchCondition atom(@NotNull Object condition) {
|
||||
new ArrangementAtomMatchCondition(ArrangementUtil.parseType(condition), condition)
|
||||
protected static StdArrangementMatchRule rule(@NotNull ArrangementSettingsToken ... conditions) {
|
||||
rule(conditions.collect { atom(it) })
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected static StdArrangementMatchRule rule(@NotNull ArrangementAtomMatchCondition ... conditions) {
|
||||
def compositeCondition = ArrangementUtil.combine(conditions)
|
||||
new StdArrangementMatchRule(new StdArrangementEntryMatcher(compositeCondition))
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected static StdArrangementMatchRule rule(@NotNull List<ArrangementAtomMatchCondition> conditions) {
|
||||
rule(conditions as ArrangementAtomMatchCondition[])
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected static StdArrangementMatchRule ruleWithOrder(@NotNull ArrangementSettingsToken orderType,
|
||||
@NotNull StdArrangementMatchRule rule)
|
||||
{
|
||||
new StdArrangementMatchRule(rule.matcher, orderType)
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected static ArrangementAtomMatchCondition atom(@NotNull ArrangementSettingsToken token) {
|
||||
new ArrangementAtomMatchCondition(token)
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected static ArrangementAtomMatchCondition atom(@NotNull String nameFilter) {
|
||||
new ArrangementAtomMatchCondition(StdArrangementTokens.General.NAME, nameFilter)
|
||||
}
|
||||
|
||||
protected void doTest(@NotNull args) {
|
||||
|
||||
@@ -2604,4 +2604,24 @@ public class UIUtil {
|
||||
public static Paint getGradientPaint(float x1, float y1, @NotNull Color c1, float x2, float y2, @NotNull Color c2) {
|
||||
return (Registry.is("ui.no.bangs.and.whistles", false)) ? ColorUtil.mix(c1, c2, .5) : new GradientPaint(x1, y1, c1, x2, y2, c2);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static Point getLocationOnScreen(@NotNull JComponent component) {
|
||||
int dx = 0;
|
||||
int dy = 0;
|
||||
for (Container c = component; c != null; c = c.getParent()) {
|
||||
if (c.isShowing()) {
|
||||
Point locationOnScreen = c.getLocationOnScreen();
|
||||
locationOnScreen.translate(dx, dy);
|
||||
return locationOnScreen;
|
||||
}
|
||||
else {
|
||||
Point location = c.getLocation();
|
||||
dx += location.x;
|
||||
dy += location.y;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -4,7 +4,7 @@ import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.XmlElementVisitor;
|
||||
import com.intellij.psi.codeStyle.arrangement.DefaultArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.xml.XmlAttribute;
|
||||
import com.intellij.psi.xml.XmlFile;
|
||||
import com.intellij.psi.xml.XmlTag;
|
||||
@@ -14,6 +14,9 @@ import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.Collection;
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.EntryType.XML_ATTRIBUTE;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.EntryType.XML_TAG;
|
||||
|
||||
/**
|
||||
* @author Eugene.Kudelevsky
|
||||
*/
|
||||
@@ -41,7 +44,7 @@ public class XmlArrangementVisitor extends XmlElementVisitor {
|
||||
@Override
|
||||
public void visitXmlTag(XmlTag tag) {
|
||||
final XmlElementArrangementEntry entry = createNewEntry(
|
||||
tag.getTextRange(), ArrangementEntryType.XML_TAG, null, true);
|
||||
tag.getTextRange(), XML_TAG, null, true);
|
||||
processEntry(entry, tag);
|
||||
}
|
||||
|
||||
@@ -49,7 +52,7 @@ public class XmlArrangementVisitor extends XmlElementVisitor {
|
||||
public void visitXmlAttribute(XmlAttribute attribute) {
|
||||
final String name = attribute.isNamespaceDeclaration() ? "" : attribute.getName();
|
||||
final XmlElementArrangementEntry entry = createNewEntry(
|
||||
attribute.getTextRange(), ArrangementEntryType.XML_ATTRIBUTE, name, true);
|
||||
attribute.getTextRange(), XML_ATTRIBUTE, name, true);
|
||||
processEntry(entry, null);
|
||||
}
|
||||
|
||||
@@ -68,7 +71,7 @@ public class XmlArrangementVisitor extends XmlElementVisitor {
|
||||
|
||||
@Nullable
|
||||
private XmlElementArrangementEntry createNewEntry(@NotNull TextRange range,
|
||||
@NotNull ArrangementEntryType type,
|
||||
@NotNull ArrangementSettingsToken type,
|
||||
@Nullable String name,
|
||||
boolean canBeMatched) {
|
||||
if (!isWithinBounds(range)) {
|
||||
@@ -100,4 +103,6 @@ public class XmlArrangementVisitor extends XmlElementVisitor {
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -5,7 +5,7 @@ import com.intellij.psi.codeStyle.arrangement.ArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.DefaultArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.NameAwareArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.TypeAwareArrangementEntry;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@@ -18,14 +18,15 @@ import java.util.Set;
|
||||
public class XmlElementArrangementEntry extends DefaultArrangementEntry
|
||||
implements TypeAwareArrangementEntry, NameAwareArrangementEntry {
|
||||
|
||||
private final ArrangementEntryType myType;
|
||||
private final String myName;
|
||||
private final ArrangementSettingsToken myType;
|
||||
private final String myName;
|
||||
|
||||
public XmlElementArrangementEntry(@Nullable ArrangementEntry parent,
|
||||
@NotNull TextRange range,
|
||||
@NotNull ArrangementEntryType type,
|
||||
@NotNull ArrangementSettingsToken type,
|
||||
@Nullable String name,
|
||||
boolean canBeMatched) {
|
||||
boolean canBeMatched)
|
||||
{
|
||||
super(parent, range.getStartOffset(), range.getEndOffset(), canBeMatched);
|
||||
myName = name;
|
||||
myType = type;
|
||||
@@ -39,12 +40,7 @@ public class XmlElementArrangementEntry extends DefaultArrangementEntry
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Set<ArrangementEntryType> getTypes() {
|
||||
public Set<ArrangementSettingsToken> getTypes() {
|
||||
return Collections.singleton(myType);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public ArrangementEntryType getType() {
|
||||
return myType;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -7,69 +7,41 @@ import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.codeStyle.CodeStyleSettings;
|
||||
import com.intellij.psi.codeStyle.arrangement.ArrangementSettings;
|
||||
import com.intellij.psi.codeStyle.arrangement.Rearranger;
|
||||
import com.intellij.psi.codeStyle.arrangement.StdArrangementSettings;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.group.ArrangementGroupingType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryType;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementModifier;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.ArrangementEntryMatcher;
|
||||
import com.intellij.psi.codeStyle.arrangement.match.StdArrangementMatchRule;
|
||||
import com.intellij.psi.codeStyle.arrangement.model.ArrangementMatchCondition;
|
||||
import com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.ArrangementStandardSettingsRepresentationAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.settings.DefaultArrangementSettingsRepresentationManager;
|
||||
import gnu.trove.TObjectIntHashMap;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.ArrangementStandardSettingsAware;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.CompositeArrangementSettingsToken;
|
||||
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementSettings;
|
||||
import com.intellij.util.containers.ContainerUtilRt;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.*;
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.EntryType.XML_ATTRIBUTE;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.EntryType.XML_TAG;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.General.NAME;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.General.ORDER;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.General.TYPE;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Order.BY_NAME;
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Order.KEEP;
|
||||
|
||||
/**
|
||||
* @author Eugene.Kudelevsky
|
||||
*/
|
||||
public class XmlRearranger
|
||||
implements Rearranger<XmlElementArrangementEntry>,
|
||||
ArrangementStandardSettingsAware,
|
||||
ArrangementStandardSettingsRepresentationAware {
|
||||
|
||||
private static final Set<ArrangementEntryType> SUPPORTED_TYPES = EnumSet.of(
|
||||
ArrangementEntryType.XML_ATTRIBUTE, ArrangementEntryType.XML_TAG);
|
||||
ArrangementStandardSettingsAware {
|
||||
|
||||
private static final Set<ArrangementSettingsToken> SUPPORTED_TYPES = ContainerUtilRt.newLinkedHashSet(XML_TAG, XML_ATTRIBUTE);
|
||||
private static final List<StdArrangementMatchRule> DEFAULT_MATCH_RULES = new ArrayList<StdArrangementMatchRule>();
|
||||
|
||||
private static final StdArrangementSettings DEFAULT_SETTINGS = new StdArrangementSettings(
|
||||
Collections.<ArrangementGroupingRule>emptyList(), DEFAULT_MATCH_RULES);
|
||||
|
||||
@NotNull private static final TObjectIntHashMap<Object> WEIGHTS = new TObjectIntHashMap<Object>();
|
||||
|
||||
@NotNull
|
||||
private static final Comparator<Object> COMPARATOR = new Comparator<Object>() {
|
||||
@Override
|
||||
public int compare(Object o1, Object o2) {
|
||||
if (WEIGHTS.containsKey(o1) && WEIGHTS.containsKey(o2)) {
|
||||
return WEIGHTS.get(o1) - WEIGHTS.get(o2);
|
||||
}
|
||||
else if (WEIGHTS.containsKey(o1) && !WEIGHTS.containsKey(o2)) {
|
||||
return -1;
|
||||
}
|
||||
else if (!WEIGHTS.containsKey(o1) && WEIGHTS.containsKey(o2)) {
|
||||
return 1;
|
||||
}
|
||||
else {
|
||||
return o1.hashCode() - o2.hashCode();
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
static {
|
||||
final Object[] ids = {
|
||||
ArrangementEntryType.XML_TAG, ArrangementEntryType.XML_ATTRIBUTE
|
||||
};
|
||||
for (int i = 0; i < ids.length; i++) {
|
||||
WEIGHTS.put(ids[i], i);
|
||||
}
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public StdArrangementSettings getDefaultSettings() {
|
||||
@@ -77,29 +49,14 @@ public class XmlRearranger
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isNameFilterSupported() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled(@NotNull ArrangementEntryType type, @Nullable ArrangementMatchCondition current) {
|
||||
return SUPPORTED_TYPES.contains(type);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled(@NotNull ArrangementModifier modifier, @Nullable ArrangementMatchCondition current) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEnabled(@NotNull ArrangementGroupingType groupingType, @Nullable ArrangementEntryOrderType orderType) {
|
||||
return false;
|
||||
public boolean isEnabled(@NotNull ArrangementSettingsToken token, @Nullable ArrangementMatchCondition current) {
|
||||
return NAME.equals(token) || KEEP.equals(token) || BY_NAME.equals(token) || SUPPORTED_TYPES.contains(token);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Collection<Set<?>> getMutexes() {
|
||||
return Collections.<Set<?>>singleton(SUPPORTED_TYPES);
|
||||
public Collection<Set<ArrangementSettingsToken>> getMutexes() {
|
||||
return Collections.singleton(SUPPORTED_TYPES);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@@ -108,7 +65,8 @@ public class XmlRearranger
|
||||
@Nullable Document document,
|
||||
@NotNull Collection<TextRange> ranges,
|
||||
@NotNull PsiElement element,
|
||||
@Nullable ArrangementSettings settings) {
|
||||
@Nullable ArrangementSettings settings)
|
||||
{
|
||||
final XmlArrangementParseInfo newEntryInfo = new XmlArrangementParseInfo();
|
||||
element.accept(new XmlArrangementVisitor(newEntryInfo, Collections.singleton(element.getTextRange())));
|
||||
|
||||
@@ -140,43 +98,25 @@ public class XmlRearranger
|
||||
return -1;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Nullable
|
||||
@Override
|
||||
public String getDisplayValue(@NotNull ArrangementEntryType type) {
|
||||
switch (type) {
|
||||
case XML_TAG:
|
||||
return "tag";
|
||||
case XML_ATTRIBUTE:
|
||||
return "attribute";
|
||||
default:
|
||||
return DefaultArrangementSettingsRepresentationManager.
|
||||
INSTANCE.getDisplayValue(type);
|
||||
}
|
||||
public List<CompositeArrangementSettingsToken> getSupportedGroupingTokens() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<CompositeArrangementSettingsToken> getSupportedMatchingTokens() {
|
||||
return ContainerUtilRt.newArrayList(
|
||||
new CompositeArrangementSettingsToken(TYPE, SUPPORTED_TYPES),
|
||||
new CompositeArrangementSettingsToken(NAME),
|
||||
new CompositeArrangementSettingsToken(ORDER, KEEP, BY_NAME)
|
||||
);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public String getDisplayValue(@NotNull ArrangementModifier modifier) {
|
||||
return DefaultArrangementSettingsRepresentationManager.INSTANCE.getDisplayValue(modifier);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public String getDisplayValue(@NotNull ArrangementGroupingType groupingType) {
|
||||
return DefaultArrangementSettingsRepresentationManager.INSTANCE.getDisplayValue(groupingType);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public String getDisplayValue(@NotNull ArrangementEntryOrderType orderType) {
|
||||
return DefaultArrangementSettingsRepresentationManager.INSTANCE.getDisplayValue(orderType);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public <T> List<T> sort(@NotNull Collection<T> ids) {
|
||||
final List<T> result = new ArrayList<T>(ids);
|
||||
Collections.sort(result, COMPARATOR);
|
||||
return result;
|
||||
public ArrangementEntryMatcher buildMatcher(@NotNull ArrangementMatchCondition condition) throws IllegalArgumentException {
|
||||
throw new IllegalArgumentException("Can't build a matcher for condition " + condition);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,7 +3,8 @@ import com.intellij.ide.highlighter.XmlFileType
|
||||
import com.intellij.lang.xml.XMLLanguage
|
||||
import com.intellij.psi.codeStyle.arrangement.AbstractRearrangerTest
|
||||
|
||||
import static com.intellij.psi.codeStyle.arrangement.order.ArrangementEntryOrderType.BY_NAME
|
||||
import static com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens.Order.BY_NAME
|
||||
|
||||
/**
|
||||
* @author Eugene.Kudelevsky
|
||||
*/
|
||||
@@ -17,7 +18,7 @@ class XmlRearrangerTest extends AbstractRearrangerTest {
|
||||
doTest(
|
||||
initial: '''<root xmlns:ns="http://ns.com" attr2="value2" attr1="value1" attr3="value3"/>''',
|
||||
expected: '''<root xmlns:ns="http://ns.com" attr1="value1" attr2="value2" attr3="value3"/>''',
|
||||
rules: [rule(BY_NAME, ".*")]
|
||||
rules: [ruleWithOrder(BY_NAME, nameRule(".*"))]
|
||||
)
|
||||
}
|
||||
|
||||
@@ -25,7 +26,7 @@ class XmlRearrangerTest extends AbstractRearrangerTest {
|
||||
doTest(
|
||||
initial: '''<root attr3="value3" attr2="value2" attr1="value1" xmlns:ns="http://ns.com"/>''',
|
||||
expected: '''<root xmlns:ns="http://ns.com" attr1="value1" attr2="value2" attr3="value3"/>''',
|
||||
rules: [rule(BY_NAME, ".*")]
|
||||
rules: [ruleWithOrder(BY_NAME, nameRule(".*"))]
|
||||
)
|
||||
}
|
||||
|
||||
@@ -47,7 +48,7 @@ class XmlRearrangerTest extends AbstractRearrangerTest {
|
||||
</tag1>
|
||||
</root>
|
||||
''',
|
||||
rules: [rule(BY_NAME, ".*")]
|
||||
rules: [ruleWithOrder(BY_NAME, nameRule(".*"))]
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user