Unify getSourceRange() for declaration and expression movers

This commit is contained in:
Alexey Sedunov
2013-06-04 14:14:46 +04:00
parent cda940f415
commit a78822ddba
3 changed files with 75 additions and 106 deletions
@@ -3,6 +3,7 @@ package org.jetbrains.jet.plugin.codeInsight.upDownMover;
import com.intellij.codeInsight.editorActions.moveUpDown.LineMover; import com.intellij.codeInsight.editorActions.moveUpDown.LineMover;
import com.intellij.codeInsight.editorActions.moveUpDown.LineRange; import com.intellij.codeInsight.editorActions.moveUpDown.LineRange;
import com.intellij.openapi.editor.Editor; import com.intellij.openapi.editor.Editor;
import com.intellij.openapi.util.Pair;
import com.intellij.psi.PsiElement; import com.intellij.psi.PsiElement;
import com.intellij.psi.PsiFile; import com.intellij.psi.PsiFile;
import com.intellij.psi.util.PsiTreeUtil; import com.intellij.psi.util.PsiTreeUtil;
@@ -14,6 +15,45 @@ public abstract class AbstractJetUpDownMover extends LineMover {
protected AbstractJetUpDownMover() { protected AbstractJetUpDownMover() {
} }
protected abstract boolean checkSourceElement(@NotNull PsiElement element);
protected abstract LineRange getElementSourceLineRange(@NotNull PsiElement element, @NotNull Editor editor, @NotNull LineRange oldRange);
@Nullable
protected LineRange getSourceRange(@NotNull PsiElement firstElement, @NotNull PsiElement lastElement, @NotNull Editor editor, LineRange oldRange) {
if (firstElement == lastElement) {
LineRange sourceRange = getElementSourceLineRange(firstElement, editor, oldRange);
if (sourceRange != null) {
sourceRange.firstElement = sourceRange.lastElement = firstElement;
}
return sourceRange;
}
PsiElement parent = PsiTreeUtil.findCommonParent(firstElement, lastElement);
if (parent == null) return null;
Pair<PsiElement, PsiElement> combinedRange = getElementRange(parent, firstElement, lastElement);
if (combinedRange == null
|| !checkSourceElement(combinedRange.first)
|| !checkSourceElement(combinedRange.second)) {
return null;
}
LineRange lineRange1 = getElementSourceLineRange(combinedRange.first, editor, oldRange);
if (lineRange1 == null) return null;
LineRange lineRange2 = getElementSourceLineRange(combinedRange.second, editor, oldRange);
if (lineRange2 == null) return null;
LineRange sourceRange = new LineRange(lineRange1.startLine, lineRange2.endLine);
sourceRange.firstElement = combinedRange.first;
sourceRange.lastElement = combinedRange.second;
return sourceRange;
}
@Nullable @Nullable
protected static PsiElement getSiblingOfType(@NotNull PsiElement element, boolean down, @NotNull Class<? extends PsiElement> type) { protected static PsiElement getSiblingOfType(@NotNull PsiElement element, boolean down, @NotNull Class<? extends PsiElement> type) {
return down ? PsiTreeUtil.getNextSiblingOfType(element, type) : PsiTreeUtil.getPrevSiblingOfType(element, type); return down ? PsiTreeUtil.getNextSiblingOfType(element, type) : PsiTreeUtil.getPrevSiblingOfType(element, type);
@@ -79,34 +79,6 @@ public class JetDeclarationMover extends AbstractJetUpDownMover {
return memberSuspects; return memberSuspects;
} }
@Nullable
private static LineRange adjustDeclarationRange(
@NotNull JetDeclaration declaration,
@NotNull Editor editor,
@NotNull LineRange lineRange
) {
Document doc = editor.getDocument();
TextRange textRange = declaration.getTextRange();
if (doc.getTextLength() < textRange.getEndOffset()) return null;
int startLine = editor.offsetToLogicalPosition(textRange.getStartOffset()).line;
int endLine = editor.offsetToLogicalPosition(textRange.getEndOffset()).line + 1;
if (startLine == lineRange.startLine || startLine == lineRange.endLine
|| endLine == lineRange.startLine || endLine == lineRange.endLine) {
return new LineRange(startLine, endLine);
}
TextRange lineTextRange = new TextRange(doc.getLineStartOffset(lineRange.startLine),
doc.getLineEndOffset(lineRange.endLine));
for (PsiElement anchor : getDeclarationAnchors(declaration)) {
TextRange suspectTextRange = anchor.getTextRange();
if (suspectTextRange != null && lineTextRange.intersects(suspectTextRange)) return new LineRange(startLine, endLine);
}
return null;
}
private static final Class[] DECLARATION_CONTAINER_CLASSES = private static final Class[] DECLARATION_CONTAINER_CLASSES =
{JetClassBody.class, JetClassInitializer.class, JetFunction.class, JetPropertyAccessor.class, JetFile.class}; {JetClassBody.class, JetClassInitializer.class, JetFunction.class, JetPropertyAccessor.class, JetFile.class};
@@ -126,45 +98,35 @@ public class JetDeclarationMover extends AbstractJetUpDownMover {
CLASSBODYLIKE_DECLARATION_CONTAINER_CLASSES) ? declaration : null; CLASSBODYLIKE_DECLARATION_CONTAINER_CLASSES) ? declaration : null;
} }
@Nullable @Override
private static LineRange getSourceRange( protected boolean checkSourceElement(@NotNull PsiElement element) {
@NotNull JetDeclaration firstDecl, return element instanceof JetDeclaration;
@NotNull JetDeclaration lastDecl, }
@NotNull Editor editor,
@NotNull LineRange oldRange
) {
if (firstDecl == lastDecl) {
LineRange range = adjustDeclarationRange(firstDecl, editor, oldRange);
if (range != null) { @Override
range.firstElement = range.lastElement = firstDecl; protected LineRange getElementSourceLineRange(@NotNull PsiElement element, @NotNull Editor editor, @NotNull LineRange oldRange) {
} JetDeclaration declaration = (JetDeclaration) element;
return range; Document doc = editor.getDocument();
TextRange textRange = declaration.getTextRange();
if (doc.getTextLength() < textRange.getEndOffset()) return null;
int startLine = editor.offsetToLogicalPosition(textRange.getStartOffset()).line;
int endLine = editor.offsetToLogicalPosition(textRange.getEndOffset()).line + 1;
if (startLine == oldRange.startLine || startLine == oldRange.endLine
|| endLine == oldRange.startLine || endLine == oldRange.endLine) {
return new LineRange(startLine, endLine);
} }
PsiElement parent = PsiTreeUtil.findCommonParent(firstDecl, lastDecl); TextRange lineTextRange = new TextRange(doc.getLineStartOffset(oldRange.startLine),
if (parent == null) return null; doc.getLineEndOffset(oldRange.endLine));
for (PsiElement anchor : getDeclarationAnchors(declaration)) {
Pair<PsiElement, PsiElement> combinedRange = getElementRange(parent, firstDecl, lastDecl); TextRange suspectTextRange = anchor.getTextRange();
if (suspectTextRange != null && lineTextRange.intersects(suspectTextRange)) return new LineRange(startLine, endLine);
if (combinedRange == null
|| !(combinedRange.first instanceof JetDeclaration)
|| !(combinedRange.second instanceof JetDeclaration)) {
return null;
} }
LineRange lineRange1 = adjustDeclarationRange((JetDeclaration) combinedRange.getFirst(), editor, oldRange); return null;
if (lineRange1 == null) return null;
LineRange lineRange2 = adjustDeclarationRange((JetDeclaration) combinedRange.getSecond(), editor, oldRange);
if (lineRange2 == null) return null;
LineRange range = new LineRange(lineRange1.startLine, lineRange2.endLine);
range.firstElement = combinedRange.getFirst();
range.lastElement = combinedRange.getSecond();
return range;
} }
@Nullable @Nullable
@@ -30,17 +30,6 @@ public class JetExpressionMover extends AbstractJetUpDownMover {
private static Class[] FUNCTIONLIKE_ELEMENT_CLASSES = private static Class[] FUNCTIONLIKE_ELEMENT_CLASSES =
{JetFunction.class, JetPropertyAccessor.class, JetClassInitializer.class}; {JetFunction.class, JetPropertyAccessor.class, JetClassInitializer.class};
@Nullable
private static LineRange getLineRange(@NotNull PsiElement element, @NotNull Editor editor) {
TextRange textRange = element.getTextRange();
if (editor.getDocument().getTextLength() < textRange.getEndOffset()) return null;
int startLine = editor.offsetToLogicalPosition(textRange.getStartOffset()).line;
int endLine = editor.offsetToLogicalPosition(textRange.getEndOffset()).line + 1;
return new LineRange(startLine, endLine);
}
@Nullable @Nullable
private static PsiElement getStandaloneClosingBrace(@NotNull PsiFile file, @NotNull Editor editor) { private static PsiElement getStandaloneClosingBrace(@NotNull PsiFile file, @NotNull Editor editor) {
LineRange range = getLineRangeFromSelection(editor); LineRange range = getLineRangeFromSelection(editor);
@@ -259,42 +248,20 @@ public class JetExpressionMover extends AbstractJetUpDownMover {
return null; return null;
} }
@Nullable @Override
private static LineRange getSourceRange(@NotNull PsiElement firstElement, @NotNull PsiElement lastElement, @NotNull Editor editor) { protected boolean checkSourceElement(@NotNull PsiElement element) {
if (firstElement == lastElement) { return PsiTreeUtil.instanceOf(element, MOVABLE_ELEMENT_CLASSES);
//noinspection ConstantConditions }
LineRange sourceRange = getLineRange(firstElement, editor);
if (sourceRange != null) { @Override
sourceRange.firstElement = sourceRange.lastElement = firstElement; protected LineRange getElementSourceLineRange(@NotNull PsiElement element, @NotNull Editor editor, @NotNull LineRange oldRange) {
} TextRange textRange = element.getTextRange();
if (editor.getDocument().getTextLength() < textRange.getEndOffset()) return null;
return sourceRange; int startLine = editor.offsetToLogicalPosition(textRange.getStartOffset()).line;
} int endLine = editor.offsetToLogicalPosition(textRange.getEndOffset()).line + 1;
//noinspection ConstantConditions return new LineRange(startLine, endLine);
PsiElement parent = PsiTreeUtil.findCommonParent(firstElement, lastElement);
if (parent == null) return null;
Pair<PsiElement, PsiElement> combinedRange = getElementRange(parent, firstElement, lastElement);
if (combinedRange == null
|| !(PsiTreeUtil.instanceOf(combinedRange.first, MOVABLE_ELEMENT_CLASSES))
|| !(PsiTreeUtil.instanceOf(combinedRange.second, MOVABLE_ELEMENT_CLASSES))) {
return null;
}
LineRange lineRange1 = getLineRange(combinedRange.first, editor);
if (lineRange1 == null) return null;
LineRange lineRange2 = getLineRange(combinedRange.second, editor);
if (lineRange2 == null) return null;
LineRange sourceRange = new LineRange(lineRange1.startLine, lineRange2.endLine);
sourceRange.firstElement = combinedRange.first;
sourceRange.lastElement = combinedRange.second;
return sourceRange;
} }
@Nullable @Nullable
@@ -415,7 +382,7 @@ public class JetExpressionMover extends AbstractJetUpDownMover {
return true; return true;
} }
LineRange sourceRange = getSourceRange(firstElement, lastElement, editor); LineRange sourceRange = getSourceRange(firstElement, lastElement, editor, oldRange);
if (sourceRange == null) return false; if (sourceRange == null) return false;
PsiElement sibling = adjustWhiteSpaceSibling(editor, sourceRange, info, down); PsiElement sibling = adjustWhiteSpaceSibling(editor, sourceRange, info, down);