mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-18 09:34:34 +07:00
don't apply single-line folding to methods exceeding the right margin (IDEA-120719)
This commit is contained in:
+29
-49
@@ -7,6 +7,7 @@ import com.intellij.codeInsight.generation.OverrideImplementExploreUtil;
|
||||
import com.intellij.lang.ASTNode;
|
||||
import com.intellij.lang.folding.CustomFoldingBuilder;
|
||||
import com.intellij.lang.folding.FoldingDescriptor;
|
||||
import com.intellij.lang.folding.NamedFoldingDescriptor;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.editor.Document;
|
||||
import com.intellij.openapi.editor.FoldingGroup;
|
||||
@@ -69,10 +70,8 @@ public abstract class JavaFoldingBuilderBase extends CustomFoldingBuilder implem
|
||||
return "...";
|
||||
}
|
||||
|
||||
private static boolean areOnAdjacentLines(PsiElement e1, PsiElement e2) {
|
||||
Document document = e1.getContainingFile().getViewProvider().getDocument();
|
||||
return document != null &&
|
||||
document.getLineNumber(e1.getTextRange().getEndOffset()) + 1 == document.getLineNumber(e2.getTextRange().getStartOffset());
|
||||
private static boolean areOnAdjacentLines(PsiElement e1, PsiElement e2, Document document) {
|
||||
return document.getLineNumber(e1.getTextRange().getEndOffset()) + 1 == document.getLineNumber(e2.getTextRange().getStartOffset());
|
||||
}
|
||||
|
||||
private static boolean isSimplePropertyAccessor(PsiMethod method) {
|
||||
@@ -576,13 +575,14 @@ public abstract class JavaFoldingBuilderBase extends CustomFoldingBuilder implem
|
||||
}
|
||||
}
|
||||
|
||||
private static boolean addOneLineMethodFolding(List<FoldingDescriptor> descriptorList, PsiMethod method) {
|
||||
private boolean addOneLineMethodFolding(List<FoldingDescriptor> descriptorList, PsiMethod method) {
|
||||
if (!JavaCodeFoldingSettings.getInstance().isCollapseOneLineMethods()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
Document document = method.getContainingFile().getViewProvider().getDocument();
|
||||
PsiCodeBlock body = method.getBody();
|
||||
if (body == null) {
|
||||
if (body == null || document == null) {
|
||||
return false;
|
||||
}
|
||||
PsiJavaToken lBrace = body.getLBrace();
|
||||
@@ -597,7 +597,7 @@ public abstract class JavaFoldingBuilderBase extends CustomFoldingBuilder implem
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!areOnAdjacentLines(body.getLBrace(), statement) || !areOnAdjacentLines(statement, body.getRBrace())) {
|
||||
if (!areOnAdjacentLines(lBrace, statement, document) || !areOnAdjacentLines(statement, rBrace, document)) {
|
||||
//the user might intend to type at an empty line
|
||||
return false;
|
||||
}
|
||||
@@ -610,22 +610,15 @@ public abstract class JavaFoldingBuilderBase extends CustomFoldingBuilder implem
|
||||
return false;
|
||||
}
|
||||
|
||||
FoldingGroup group = FoldingGroup.newGroup("one-liner");
|
||||
descriptorList.add(new FoldingDescriptor(lBrace.getNode(), new TextRange(leftStart, leftEnd), group) {
|
||||
@Nullable
|
||||
@Override
|
||||
public String getPlaceholderText() {
|
||||
return " { ";
|
||||
}
|
||||
});
|
||||
String leftText = " { ";
|
||||
String rightText = " }";
|
||||
if (!fitsRightMargin(method, document, leftStart, rightEnd, rightStart - leftEnd + leftText.length() + rightText.length())) {
|
||||
return false;
|
||||
}
|
||||
|
||||
descriptorList.add(new FoldingDescriptor(rBrace.getNode(), new TextRange(rightStart, rightEnd), group) {
|
||||
@Nullable
|
||||
@Override
|
||||
public String getPlaceholderText() {
|
||||
return " }";
|
||||
}
|
||||
});
|
||||
FoldingGroup group = FoldingGroup.newGroup("one-liner");
|
||||
descriptorList.add(new NamedFoldingDescriptor(lBrace, leftStart, leftEnd, group, leftText));
|
||||
descriptorList.add(new NamedFoldingDescriptor(rBrace, rightStart, rightEnd, group, rightText));
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -797,41 +790,22 @@ public abstract class JavaFoldingBuilderBase extends CustomFoldingBuilder implem
|
||||
final int closureEnd = expression.getTextRange().getEndOffset();
|
||||
boolean oneLine = false;
|
||||
String contents = seq.subSequence(firstLineStart, lastLineEnd).toString();
|
||||
if (contents.indexOf('\n') < 0) {
|
||||
final int beforeLength = closureStart - document.getLineStartOffset(document.getLineNumber(closureStart));
|
||||
final int afterLength = document.getLineEndOffset(document.getLineNumber(closureEnd)) - closureEnd;
|
||||
final int resultLineLength = beforeLength + lambdas.length() + contents.length() + 5 + afterLength;
|
||||
|
||||
if (isBelowRightMargin(aClass.getProject(), resultLineLength)) {
|
||||
rangeStart = CharArrayUtil.shiftForward(seq, rangeStart, " \n\t");
|
||||
rangeEnd = CharArrayUtil.shiftBackward(seq, rangeEnd - 1, " \n\t") + 1;
|
||||
oneLine = true;
|
||||
}
|
||||
if (contents.indexOf('\n') < 0 &&
|
||||
fitsRightMargin(aClass, document, closureStart, closureEnd, lambdas.length() + contents.length() + 5)) {
|
||||
rangeStart = CharArrayUtil.shiftForward(seq, rangeStart, " \n\t");
|
||||
rangeEnd = CharArrayUtil.shiftBackward(seq, rangeEnd - 1, " \n\t") + 1;
|
||||
oneLine = true;
|
||||
}
|
||||
|
||||
if (rangeStart >= rangeEnd) return false;
|
||||
|
||||
FoldingGroup group = FoldingGroup.newGroup("lambda");
|
||||
|
||||
final String prettySpace = oneLine ? " " : "";
|
||||
|
||||
foldElements.add(
|
||||
new FoldingDescriptor(expression.getNode(), new TextRange(closureStart, rangeStart), group) {
|
||||
@Override
|
||||
public String getPlaceholderText() {
|
||||
return lambdas + prettySpace;
|
||||
}
|
||||
});
|
||||
|
||||
foldElements.add(new NamedFoldingDescriptor(expression, closureStart, rangeStart, group, lambdas + prettySpace));
|
||||
if (rbrace != null && rangeEnd + 1 < closureEnd) {
|
||||
foldElements
|
||||
.add(new FoldingDescriptor(rbrace.getNode(), new TextRange(rangeEnd, closureEnd), group) {
|
||||
@Override
|
||||
public String getPlaceholderText() {
|
||||
return prettySpace + "}";
|
||||
}
|
||||
});
|
||||
foldElements.add(new NamedFoldingDescriptor(rbrace, rangeEnd, closureEnd, group, prettySpace + "}"));
|
||||
}
|
||||
|
||||
addCodeBlockFolds(body, foldElements, processedComments, document, quick);
|
||||
}
|
||||
}
|
||||
@@ -841,6 +815,12 @@ public abstract class JavaFoldingBuilderBase extends CustomFoldingBuilder implem
|
||||
return isClosure;
|
||||
}
|
||||
|
||||
private boolean fitsRightMargin(PsiElement element, Document document, int foldingStart, int foldingEnd, int collapsedLength) {
|
||||
final int beforeLength = foldingStart - document.getLineStartOffset(document.getLineNumber(foldingStart));
|
||||
final int afterLength = document.getLineEndOffset(document.getLineNumber(foldingEnd)) - foldingEnd;
|
||||
return isBelowRightMargin(element.getProject(), beforeLength + collapsedLength + afterLength);
|
||||
}
|
||||
|
||||
protected abstract boolean isBelowRightMargin (Project project, final int lineLength);
|
||||
|
||||
@Override
|
||||
|
||||
@@ -512,6 +512,20 @@ class Test {
|
||||
checkAccessorFolding(regions[0], regions[1], fooClass.methods[0])
|
||||
}
|
||||
|
||||
public void "test don't inline very long one-line methods"() {
|
||||
configure """class Foo {
|
||||
int someVeryVeryLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongVariable;
|
||||
|
||||
// don't create folding that would exceed the right margin
|
||||
int getSomeVeryVeryLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongVariable() {
|
||||
return someVeryVeryLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongLongVariable;
|
||||
}
|
||||
}"""
|
||||
def regions = myFixture.editor.foldingModel.allFoldRegions.sort { it.startOffset }
|
||||
assert regions.size() == 1
|
||||
assert regions[0].placeholderText == '{...}'
|
||||
}
|
||||
|
||||
private def changeFoldRegions(Closure op) {
|
||||
myFixture.editor.foldingModel.runBatchFoldingOperationDoNotCollapseCaret(op)
|
||||
}
|
||||
|
||||
@@ -0,0 +1,49 @@
|
||||
/*
|
||||
* Copyright 2000-2014 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.intellij.lang.folding;
|
||||
|
||||
import com.intellij.lang.ASTNode;
|
||||
import com.intellij.openapi.editor.FoldingGroup;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
public class NamedFoldingDescriptor extends FoldingDescriptor {
|
||||
private final String myPlaceholderText;
|
||||
|
||||
public NamedFoldingDescriptor(@NotNull PsiElement e, int start, int end, @Nullable FoldingGroup group, @NotNull String placeholderText) {
|
||||
this(e.getNode(), new TextRange(start, end), group, placeholderText);
|
||||
}
|
||||
|
||||
public NamedFoldingDescriptor(@NotNull ASTNode node, int start, int end, @Nullable FoldingGroup group, @NotNull String placeholderText) {
|
||||
this(node, new TextRange(start, end), group, placeholderText);
|
||||
}
|
||||
|
||||
public NamedFoldingDescriptor(@NotNull ASTNode node,
|
||||
@NotNull final TextRange range,
|
||||
@Nullable FoldingGroup group,
|
||||
@NotNull String placeholderText) {
|
||||
super(node, range, group);
|
||||
myPlaceholderText = placeholderText;
|
||||
}
|
||||
|
||||
@Override
|
||||
@NotNull
|
||||
public String getPlaceholderText() {
|
||||
return myPlaceholderText;
|
||||
}
|
||||
}
|
||||
+3
-20
@@ -21,6 +21,7 @@ import com.intellij.codeInsight.folding.impl.JavaFoldingBuilderBase;
|
||||
import com.intellij.lang.ASTNode;
|
||||
import com.intellij.lang.folding.CustomFoldingBuilder;
|
||||
import com.intellij.lang.folding.FoldingDescriptor;
|
||||
import com.intellij.lang.folding.NamedFoldingDescriptor;
|
||||
import com.intellij.openapi.editor.Document;
|
||||
import com.intellij.openapi.editor.FoldingGroup;
|
||||
import com.intellij.openapi.project.DumbAware;
|
||||
@@ -124,8 +125,8 @@ public class GroovyFoldingBuilder extends CustomFoldingBuilder implements Groovy
|
||||
if (next != null && PsiImplUtil.isWhiteSpaceOrNls(next) &&
|
||||
prev != null && PsiImplUtil.isWhiteSpaceOrNls(prev)) {
|
||||
final FoldingGroup group = FoldingGroup.newGroup("block_group");
|
||||
descriptors.add(new NamedFoldingDescriptor(psi.getNode(), lbrace.getTextRange().getStartOffset(), next.getTextRange().getEndOffset(), group, "{"));
|
||||
descriptors.add(new NamedFoldingDescriptor(psi.getNode(), prev.getTextRange().getStartOffset(), rbrace.getTextRange().getEndOffset(), group, "}"));
|
||||
descriptors.add(new NamedFoldingDescriptor(psi, lbrace.getTextRange().getStartOffset(), next.getTextRange().getEndOffset(), group, "{"));
|
||||
descriptors.add(new NamedFoldingDescriptor(psi, prev.getTextRange().getStartOffset(), rbrace.getTextRange().getEndOffset(), group, "}"));
|
||||
return;
|
||||
}
|
||||
}
|
||||
@@ -191,24 +192,6 @@ public class GroovyFoldingBuilder extends CustomFoldingBuilder implements Groovy
|
||||
}
|
||||
}
|
||||
|
||||
private static class NamedFoldingDescriptor extends FoldingDescriptor {
|
||||
private final String myPlaceholderText;
|
||||
|
||||
private NamedFoldingDescriptor(@NotNull ASTNode node, int start, int end, @Nullable FoldingGroup group, @NotNull String placeholderText) {
|
||||
this(node, new TextRange(start, end), group, placeholderText);
|
||||
}
|
||||
|
||||
private NamedFoldingDescriptor(@NotNull ASTNode node, @NotNull final TextRange range, @Nullable FoldingGroup group, @NotNull String placeholderText) {
|
||||
super(node, range, group);
|
||||
myPlaceholderText = placeholderText;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getPlaceholderText() {
|
||||
return myPlaceholderText;
|
||||
}
|
||||
}
|
||||
|
||||
private static void processImports(final List<FoldingDescriptor> descriptors, GrImportStatement[] imports) {
|
||||
if (imports.length < 2) return;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user