NodeIndentStrategy: J2K and cleanup
This commit is contained in:
@@ -17,7 +17,6 @@
|
||||
package org.jetbrains.kotlin.idea.formatter
|
||||
|
||||
import com.intellij.formatting.*
|
||||
import com.intellij.formatting.ChildAttributes.DELEGATE_TO_NEXT_CHILD
|
||||
import com.intellij.lang.ASTNode
|
||||
import com.intellij.psi.TokenType
|
||||
import com.intellij.psi.codeStyle.CodeStyleSettings
|
||||
@@ -26,7 +25,7 @@ import com.intellij.psi.tree.TokenSet
|
||||
import org.jetbrains.kotlin.KtNodeTypes
|
||||
import org.jetbrains.kotlin.idea.KotlinLanguage
|
||||
import org.jetbrains.kotlin.idea.core.formatter.KotlinCodeStyleSettings
|
||||
import org.jetbrains.kotlin.idea.formatter.NodeIndentStrategy.strategy
|
||||
import org.jetbrains.kotlin.idea.formatter.NodeIndentStrategy.Companion.strategy
|
||||
import org.jetbrains.kotlin.kdoc.lexer.KDocTokens
|
||||
import org.jetbrains.kotlin.kdoc.parser.KDocElementTypes
|
||||
import org.jetbrains.kotlin.lexer.KtTokens
|
||||
@@ -330,21 +329,21 @@ abstract class KotlinCommonBlock(
|
||||
|
||||
private val INDENT_RULES = arrayOf<NodeIndentStrategy>(
|
||||
strategy("No indent for braces in blocks")
|
||||
.`in`(KtNodeTypes.BLOCK, KtNodeTypes.CLASS_BODY, KtNodeTypes.FUNCTION_LITERAL)
|
||||
.within(KtNodeTypes.BLOCK, KtNodeTypes.CLASS_BODY, KtNodeTypes.FUNCTION_LITERAL)
|
||||
.forType(RBRACE, LBRACE)
|
||||
.set(Indent.getNoneIndent()),
|
||||
|
||||
strategy("Indent for block content")
|
||||
.`in`(KtNodeTypes.BLOCK, KtNodeTypes.CLASS_BODY, KtNodeTypes.FUNCTION_LITERAL)
|
||||
.within(KtNodeTypes.BLOCK, KtNodeTypes.CLASS_BODY, KtNodeTypes.FUNCTION_LITERAL)
|
||||
.notForType(RBRACE, LBRACE, KtNodeTypes.BLOCK)
|
||||
.set(Indent.getNormalIndent(false)),
|
||||
|
||||
strategy("Indent for property accessors")
|
||||
.`in`(KtNodeTypes.PROPERTY).forType(KtNodeTypes.PROPERTY_ACCESSOR)
|
||||
.within(KtNodeTypes.PROPERTY).forType(KtNodeTypes.PROPERTY_ACCESSOR)
|
||||
.set(Indent.getNormalIndent()),
|
||||
|
||||
strategy("For a single statement in 'for'")
|
||||
.`in`(KtNodeTypes.BODY).notForType(KtNodeTypes.BLOCK)
|
||||
.within(KtNodeTypes.BODY).notForType(KtNodeTypes.BLOCK)
|
||||
.set(Indent.getNormalIndent()),
|
||||
|
||||
strategy("For the entry in when")
|
||||
@@ -352,51 +351,51 @@ private val INDENT_RULES = arrayOf<NodeIndentStrategy>(
|
||||
.set(Indent.getNormalIndent()),
|
||||
|
||||
strategy("For single statement in THEN and ELSE")
|
||||
.`in`(KtNodeTypes.THEN, KtNodeTypes.ELSE).notForType(KtNodeTypes.BLOCK)
|
||||
.within(KtNodeTypes.THEN, KtNodeTypes.ELSE).notForType(KtNodeTypes.BLOCK)
|
||||
.set(Indent.getNormalIndent()),
|
||||
|
||||
strategy("Indent for parts")
|
||||
.`in`(KtNodeTypes.PROPERTY, KtNodeTypes.FUN, KtNodeTypes.DESTRUCTURING_DECLARATION, KtNodeTypes.SECONDARY_CONSTRUCTOR)
|
||||
.within(KtNodeTypes.PROPERTY, KtNodeTypes.FUN, KtNodeTypes.DESTRUCTURING_DECLARATION, KtNodeTypes.SECONDARY_CONSTRUCTOR)
|
||||
.notForType(KtNodeTypes.BLOCK, FUN_KEYWORD, VAL_KEYWORD, VAR_KEYWORD, CONSTRUCTOR_KEYWORD)
|
||||
.set(Indent.getContinuationWithoutFirstIndent()),
|
||||
|
||||
strategy("Chained calls")
|
||||
.`in`(KtNodeTypes.DOT_QUALIFIED_EXPRESSION, KtNodeTypes.SAFE_ACCESS_EXPRESSION)
|
||||
.within(KtNodeTypes.DOT_QUALIFIED_EXPRESSION, KtNodeTypes.SAFE_ACCESS_EXPRESSION)
|
||||
.set(Indent.getContinuationWithoutFirstIndent(false)),
|
||||
|
||||
strategy("Colon of delegation list")
|
||||
.`in`(KtNodeTypes.CLASS, KtNodeTypes.OBJECT_DECLARATION)
|
||||
.within(KtNodeTypes.CLASS, KtNodeTypes.OBJECT_DECLARATION)
|
||||
.forType(KtTokens.COLON)
|
||||
.set(Indent.getNormalIndent(false)),
|
||||
|
||||
strategy("Delegation list")
|
||||
.`in`(KtNodeTypes.SUPER_TYPE_LIST, KtNodeTypes.INITIALIZER_LIST)
|
||||
.within(KtNodeTypes.SUPER_TYPE_LIST, KtNodeTypes.INITIALIZER_LIST)
|
||||
.set(Indent.getContinuationIndent(false)),
|
||||
|
||||
strategy("Indices")
|
||||
.`in`(KtNodeTypes.INDICES)
|
||||
.within(KtNodeTypes.INDICES)
|
||||
.set(Indent.getContinuationIndent(false)),
|
||||
|
||||
strategy("Binary expressions")
|
||||
.`in`(BINARY_EXPRESSIONS)
|
||||
.within(BINARY_EXPRESSIONS)
|
||||
.set(Indent.getContinuationWithoutFirstIndent(false)),
|
||||
|
||||
strategy("Parenthesized expression")
|
||||
.`in`(KtNodeTypes.PARENTHESIZED)
|
||||
.within(KtNodeTypes.PARENTHESIZED)
|
||||
.set(Indent.getContinuationWithoutFirstIndent(false)),
|
||||
|
||||
strategy("Round Brackets around conditions")
|
||||
.forType(LPAR, RPAR)
|
||||
.`in`(KtNodeTypes.IF, KtNodeTypes.WHEN_ENTRY, KtNodeTypes.WHILE, KtNodeTypes.DO_WHILE)
|
||||
.within(KtNodeTypes.IF, KtNodeTypes.WHEN_ENTRY, KtNodeTypes.WHILE, KtNodeTypes.DO_WHILE)
|
||||
.set(Indent.getContinuationWithoutFirstIndent(true)),
|
||||
|
||||
strategy("KDoc comment indent")
|
||||
.`in`(KDOC_CONTENT)
|
||||
.within(KDOC_CONTENT)
|
||||
.forType(KDocTokens.LEADING_ASTERISK, KDocTokens.END)
|
||||
.set(Indent.getSpaceIndent(KDOC_COMMENT_INDENT)),
|
||||
|
||||
strategy("Block in when entry")
|
||||
.`in`(KtNodeTypes.WHEN_ENTRY)
|
||||
.within(KtNodeTypes.WHEN_ENTRY)
|
||||
.notForType(KtNodeTypes.BLOCK, KtNodeTypes.WHEN_CONDITION_EXPRESSION, KtNodeTypes.WHEN_CONDITION_IN_RANGE, KtNodeTypes.WHEN_CONDITION_IS_PATTERN, ELSE_KEYWORD, ARROW)
|
||||
.set(Indent.getNormalIndent()))
|
||||
|
||||
|
||||
@@ -14,151 +14,130 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.jetbrains.kotlin.idea.formatter;
|
||||
package org.jetbrains.kotlin.idea.formatter
|
||||
|
||||
import com.intellij.formatting.Indent;
|
||||
import com.intellij.lang.ASTNode;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
import com.intellij.psi.tree.TokenSet;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
import com.intellij.formatting.Indent
|
||||
import com.intellij.lang.ASTNode
|
||||
import com.intellij.psi.tree.IElementType
|
||||
import com.intellij.psi.tree.TokenSet
|
||||
import java.util.*
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
abstract class NodeIndentStrategy {
|
||||
|
||||
@SuppressWarnings("UnusedDeclaration")
|
||||
public abstract class NodeIndentStrategy {
|
||||
public static NodeIndentStrategy constIndent(Indent indent) {
|
||||
return new ConstIndentStrategy(indent);
|
||||
}
|
||||
abstract fun getIndent(node: ASTNode): Indent?
|
||||
|
||||
public static PositionStrategy strategy(@Nullable String debugInfo) {
|
||||
return new PositionStrategy(debugInfo);
|
||||
}
|
||||
class ConstIndentStrategy(private val indent: Indent) : NodeIndentStrategy() {
|
||||
|
||||
@Nullable
|
||||
public abstract Indent getIndent(@NotNull ASTNode node);
|
||||
|
||||
public static class ConstIndentStrategy extends NodeIndentStrategy {
|
||||
private final Indent indent;
|
||||
|
||||
public ConstIndentStrategy(Indent indent) {
|
||||
this.indent = indent;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Indent getIndent(@NotNull ASTNode node) {
|
||||
return indent;
|
||||
override fun getIndent(node: ASTNode): Indent? {
|
||||
return indent
|
||||
}
|
||||
}
|
||||
|
||||
public static class PositionStrategy extends NodeIndentStrategy {
|
||||
private Indent defaultIndent = Indent.getNoneIndent();
|
||||
class PositionStrategy(private val debugInfo: String?) : NodeIndentStrategy() {
|
||||
private var defaultIndent = Indent.getNoneIndent()
|
||||
|
||||
private final List<IElementType> in = new ArrayList<IElementType>();
|
||||
private final List<IElementType> notIn = new ArrayList<IElementType>();
|
||||
private final List<IElementType> forElement = new ArrayList<IElementType>();
|
||||
private final List<IElementType> notForElement = new ArrayList<IElementType>();
|
||||
private val within = ArrayList<IElementType>()
|
||||
private val notIn = ArrayList<IElementType>()
|
||||
private val forElement = ArrayList<IElementType>()
|
||||
private val notForElement = ArrayList<IElementType>()
|
||||
|
||||
private final String debugInfo;
|
||||
|
||||
public PositionStrategy(@Nullable String debugInfo) {
|
||||
this.debugInfo = debugInfo;
|
||||
override fun toString(): String {
|
||||
return "PositionStrategy " + (debugInfo ?: "No debug info")
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "PositionStrategy " + (debugInfo != null ? debugInfo : "No debug info");
|
||||
fun set(indent: Indent): PositionStrategy {
|
||||
defaultIndent = indent
|
||||
return this
|
||||
}
|
||||
|
||||
public PositionStrategy set(Indent indent) {
|
||||
defaultIndent = indent;
|
||||
return this;
|
||||
}
|
||||
|
||||
public PositionStrategy in(@NotNull TokenSet parents) {
|
||||
IElementType[] types = parents.getTypes();
|
||||
if (types.length == 0) {
|
||||
throw new IllegalArgumentException("Empty token set is unexpected");
|
||||
fun within(parents: TokenSet): PositionStrategy {
|
||||
val types = parents.types
|
||||
if (types.isEmpty()) {
|
||||
throw IllegalArgumentException("Empty token set is unexpected")
|
||||
}
|
||||
|
||||
fillTypes(in, types[0], Arrays.copyOfRange(types, 1, types.length));
|
||||
return this;
|
||||
fillTypes(within, types[0], Arrays.copyOfRange(types, 1, types.size))
|
||||
return this
|
||||
}
|
||||
|
||||
public PositionStrategy in(@NotNull IElementType parentType, @NotNull IElementType... orParentTypes) {
|
||||
fillTypes(in, parentType, orParentTypes);
|
||||
return this;
|
||||
fun within(parentType: IElementType, vararg orParentTypes: IElementType): PositionStrategy {
|
||||
fillTypes(within, parentType, orParentTypes)
|
||||
return this
|
||||
}
|
||||
|
||||
public PositionStrategy notIn(@NotNull IElementType parentType, @NotNull IElementType... orParentTypes) {
|
||||
fillTypes(notIn, parentType, orParentTypes);
|
||||
return this;
|
||||
fun notWithin(parentType: IElementType, vararg orParentTypes: IElementType): PositionStrategy {
|
||||
fillTypes(notIn, parentType, orParentTypes)
|
||||
return this
|
||||
}
|
||||
|
||||
public PositionStrategy inAny() {
|
||||
in.clear();
|
||||
notIn.clear();
|
||||
return this;
|
||||
fun withinAny(): PositionStrategy {
|
||||
within.clear()
|
||||
notIn.clear()
|
||||
return this
|
||||
}
|
||||
|
||||
public PositionStrategy forType(@NotNull IElementType elementType, @NotNull IElementType... otherTypes) {
|
||||
fillTypes(forElement, elementType, otherTypes);
|
||||
return this;
|
||||
fun forType(elementType: IElementType, vararg otherTypes: IElementType): PositionStrategy {
|
||||
fillTypes(forElement, elementType, otherTypes)
|
||||
return this
|
||||
}
|
||||
|
||||
public PositionStrategy notForType(@NotNull IElementType elementType, @NotNull IElementType... otherTypes) {
|
||||
fillTypes(notForElement, elementType, otherTypes);
|
||||
return this;
|
||||
fun notForType(elementType: IElementType, vararg otherTypes: IElementType): PositionStrategy {
|
||||
fillTypes(notForElement, elementType, otherTypes)
|
||||
return this
|
||||
}
|
||||
|
||||
public PositionStrategy forAny() {
|
||||
forElement.clear();
|
||||
notForElement.clear();
|
||||
return this;
|
||||
fun forAny(): PositionStrategy {
|
||||
forElement.clear()
|
||||
notForElement.clear()
|
||||
return this
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Indent getIndent(@NotNull ASTNode node) {
|
||||
override fun getIndent(node: ASTNode): Indent? {
|
||||
if (!forElement.isEmpty()) {
|
||||
if (!forElement.contains(node.getElementType())) {
|
||||
return null;
|
||||
if (!forElement.contains(node.elementType)) {
|
||||
return null
|
||||
}
|
||||
}
|
||||
|
||||
if (notForElement.contains(node.getElementType())) {
|
||||
return null;
|
||||
if (notForElement.contains(node.elementType)) {
|
||||
return null
|
||||
}
|
||||
|
||||
ASTNode parent = node.getTreeParent();
|
||||
val parent = node.treeParent
|
||||
if (parent != null) {
|
||||
if (!in.isEmpty()) {
|
||||
if (!in.contains(parent.getElementType())) {
|
||||
return null;
|
||||
if (!within.isEmpty()) {
|
||||
if (!within.contains(parent.elementType)) {
|
||||
return null
|
||||
}
|
||||
}
|
||||
|
||||
if (notIn.contains(parent.getElementType())) {
|
||||
return null;
|
||||
if (notIn.contains(parent.elementType)) {
|
||||
return null
|
||||
}
|
||||
}
|
||||
else {
|
||||
if (!in.isEmpty()) {
|
||||
return null;
|
||||
if (!within.isEmpty()) {
|
||||
return null
|
||||
}
|
||||
}
|
||||
|
||||
return defaultIndent;
|
||||
return defaultIndent
|
||||
}
|
||||
|
||||
private static void fillTypes(List<IElementType> resultCollection, IElementType singleType, IElementType[] otherTypes) {
|
||||
resultCollection.clear();
|
||||
resultCollection.add(singleType);
|
||||
Collections.addAll(resultCollection, otherTypes);
|
||||
private fun fillTypes(resultCollection: MutableList<IElementType>, singleType: IElementType, otherTypes: Array<out IElementType>) {
|
||||
resultCollection.clear()
|
||||
resultCollection.add(singleType)
|
||||
Collections.addAll(resultCollection, *otherTypes)
|
||||
}
|
||||
}
|
||||
|
||||
companion object {
|
||||
fun constIndent(indent: Indent): NodeIndentStrategy {
|
||||
return ConstIndentStrategy(indent)
|
||||
}
|
||||
|
||||
fun strategy(debugInfo: String?): PositionStrategy {
|
||||
return PositionStrategy(debugInfo)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user