mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
new select word handlers for Groovy
This commit is contained in:
@@ -366,11 +366,13 @@
|
||||
<extendWordSelectionHandler implementation="org.jetbrains.plugins.groovy.editor.selection.GroovyTypeCastSelectioner"/>
|
||||
<extendWordSelectionHandler implementation="org.jetbrains.plugins.groovy.editor.selection.GroovyDocParamsSelectioner"/>
|
||||
<extendWordSelectionHandler implementation="org.jetbrains.plugins.groovy.editor.selection.GroovyArgListSelectioner"/>
|
||||
<extendWordSelectionHandler implementation="org.jetbrains.plugins.groovy.editor.selection.GroovyFieldSemicolonSelectioner"/>
|
||||
<extendWordSelectionHandler implementation="org.jetbrains.plugins.groovy.editor.selection.GroovyGStringSelectioner"
|
||||
order="before wordSelectioner"/>
|
||||
<extendWordSelectionHandler implementation="org.jetbrains.plugins.groovy.editor.selection.GroovyParameterListSelectioner"/>
|
||||
<extendWordSelectionHandler implementation="org.jetbrains.plugins.groovy.editor.selection.GroovyElseSelectioner"/>
|
||||
<extendWordSelectionHandler implementation="org.jetbrains.plugins.groovy.editor.selection.GroovyWordSelectionHandler"/>
|
||||
<extendWordSelectionHandler implementation="org.jetbrains.plugins.groovy.editor.selection.GroovyStatementSelectioner"/>
|
||||
|
||||
|
||||
<methodReferencesSearch implementation="org.jetbrains.plugins.groovy.findUsages.AccessorMethodReferencesSearcher"/>
|
||||
<methodReferencesSearch implementation="org.jetbrains.plugins.groovy.findUsages.MethodLateBoundReferencesSearcher"/>
|
||||
|
||||
+91
-91
@@ -1,91 +1,91 @@
|
||||
#
|
||||
# Copyright 2000-2007 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.
|
||||
#
|
||||
|
||||
########################################################################################################################
|
||||
# Unuzed imports
|
||||
########################################################################################################################
|
||||
unused.import=Unused import
|
||||
optimize.imports=Optimize imports
|
||||
optimize.all.imports=Optimize unused import statements
|
||||
|
||||
########################################################################################################################
|
||||
# Create class fix
|
||||
########################################################################################################################
|
||||
dialog.create.class.package.chooser.title=Choose destination package
|
||||
create.directory.command=Create directory
|
||||
destination.package=Destination package:
|
||||
dialog.create.class.label.0=Create class ''{0}''
|
||||
second.unsafe.call=Second unsafe call
|
||||
call.can.throw.npe=Calling chain can throw NullPointerException
|
||||
|
||||
groovy.dfa.issues=Data flow issues
|
||||
|
||||
unused.assignment=Unused Assignment
|
||||
unused.assignment.tooltip=Assignment is not used
|
||||
|
||||
unused.inc.dec=Unused Incrementing or Decrementing
|
||||
|
||||
unassigned.access=Variable Not Assigned
|
||||
unassigned.access.short.name=VariableNotAssigned
|
||||
unassigned.access.tooltip=Variable ''{0}'' might not be assigned
|
||||
no.return.display.name=Missing Return Statement
|
||||
no.return.short.name=MissingReturnStatement
|
||||
no.return.message=Not all execution paths return a value
|
||||
create.dynamic.property=Create dynamic property
|
||||
dynamic.property=Dynamic property
|
||||
unresolved.type.status=Type ''{0}'' is not resolved
|
||||
resolved.type.status=Type ''{0}'' is resolved
|
||||
no.type.specified=No type specified
|
||||
dynamic.element=Dynamic Element
|
||||
|
||||
########################################################################################################################
|
||||
# InpectorGroovy properties
|
||||
########################################################################################################################
|
||||
pointless.boolean.problem.descriptor=#ref can be simplified to ''{0}'' #loc
|
||||
pointless.arithmetic.error.message=#ref can be replaced with ''{0}'' #loc
|
||||
pointless.boolean.display.name=Pointless boolean expression
|
||||
pointless.boolean.quickfix=Simplify
|
||||
|
||||
Cannot.perform.undo.operation=Cannot perform undo operation
|
||||
Undo.disable=Undo Disabled
|
||||
field.already.defined=Variables with field names
|
||||
clashing.getters=Clashing getters
|
||||
|
||||
access.to.inaccessible.element=Access to inaccessible element
|
||||
|
||||
cannot.reference.nonstatic=Cannot reference nonstatic symbol ''{0}'' from static context
|
||||
|
||||
type.doesnt.contain.method=Type ''{0}'' cannot be iterated in range because it does not have method ''{1}''
|
||||
incorrect.range.argument=Incorrect range arguments
|
||||
type.doesnt.implemnt.comparable=Type ''{0}'' doesnt implement Comparable
|
||||
add.method=Add method ''{0}()'' to class ''{1}''
|
||||
implement.class=Implement {0}
|
||||
fix.class=Fix class {0}
|
||||
check.labeled.statement=Labeled statement inspection
|
||||
unnecessary.qualified.reference=Unnecessary qualified reference
|
||||
rtype.cannot.contain.ltype=''{1}'' cannot contain ''{0}''
|
||||
new.instance.of.singleton=New instance of class annotated with @groovy.lang.Singleton
|
||||
replace.new.expression.with.0.instance=Replace with ''{0}.instance''
|
||||
getter.0.clashes.with.getter.1={0} clashes with {1}
|
||||
unused.0=Unused {0}
|
||||
remove.0=Remove {0}
|
||||
replace.postfix.0.with.prefix.0=Replace postfix {0} with prefix {0}
|
||||
replace.0.with.1=Replace {0} with binary {1}
|
||||
gr.deprecated.api.usage=Deprecated API inspection
|
||||
category,method.0.cannot.be.applied.to.1=Category method ''{0}'' cannot be applied to ''{1}''
|
||||
local.var.0.is.reassigned.in.closure=Local variable {0} is reassigned in {1} with other type
|
||||
anonymous.class=anonymous class
|
||||
closure=closure
|
||||
other.scope=Other scope
|
||||
#
|
||||
# Copyright 2000-2007 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.
|
||||
#
|
||||
|
||||
########################################################################################################################
|
||||
# Unuzed imports
|
||||
########################################################################################################################
|
||||
unused.import=Unused import
|
||||
optimize.imports=Optimize imports
|
||||
optimize.all.imports=Optimize unused import statements
|
||||
|
||||
########################################################################################################################
|
||||
# Create class fix
|
||||
########################################################################################################################
|
||||
dialog.create.class.package.chooser.title=Choose destination package
|
||||
create.directory.command=Create directory
|
||||
destination.package=Destination package:
|
||||
dialog.create.class.label.0=Create class ''{0}''
|
||||
second.unsafe.call=Second unsafe call
|
||||
call.can.throw.npe=Calling chain can throw NullPointerException
|
||||
|
||||
groovy.dfa.issues=Data flow issues
|
||||
|
||||
unused.assignment=Unused Assignment
|
||||
unused.assignment.tooltip=Assignment is not used
|
||||
|
||||
unused.inc.dec=Unused Incrementing or Decrementing
|
||||
|
||||
unassigned.access=Variable Not Assigned
|
||||
unassigned.access.short.name=VariableNotAssigned
|
||||
unassigned.access.tooltip=Variable ''{0}'' might not be assigned
|
||||
no.return.display.name=Missing Return Statement
|
||||
no.return.short.name=MissingReturnStatement
|
||||
no.return.message=Not all execution paths return a value
|
||||
create.dynamic.property=Create dynamic property
|
||||
dynamic.property=Dynamic property
|
||||
unresolved.type.status=Type ''{0}'' is not resolved
|
||||
resolved.type.status=Type ''{0}'' is resolved
|
||||
no.type.specified=No type specified
|
||||
dynamic.element=Dynamic Element
|
||||
|
||||
########################################################################################################################
|
||||
# InpectorGroovy properties
|
||||
########################################################################################################################
|
||||
pointless.boolean.problem.descriptor=#ref can be simplified to ''{0}'' #loc
|
||||
pointless.arithmetic.error.message=#ref can be replaced with ''{0}'' #loc
|
||||
pointless.boolean.display.name=Pointless boolean expression
|
||||
pointless.boolean.quickfix=Simplify
|
||||
|
||||
Cannot.perform.undo.operation=Cannot perform undo operation
|
||||
Undo.disable=Undo Disabled
|
||||
field.already.defined=Variables with field names
|
||||
clashing.getters=Clashing getters
|
||||
|
||||
access.to.inaccessible.element=Access to inaccessible element
|
||||
|
||||
cannot.reference.nonstatic=Cannot reference nonstatic symbol ''{0}'' from static context
|
||||
|
||||
type.doesnt.contain.method=Type ''{0}'' cannot be iterated in range because it does not have method ''{1}''
|
||||
incorrect.range.argument=Incorrect range arguments
|
||||
type.doesnt.implemnt.comparable=Type ''{0}'' doesnt implement Comparable
|
||||
add.method=Add method ''{0}()'' to class ''{1}''
|
||||
implement.class=Implement {0}
|
||||
fix.class=Fix class {0}
|
||||
check.labeled.statement=Labeled statement inspection
|
||||
unnecessary.qualified.reference=Unnecessary qualified reference
|
||||
rtype.cannot.contain.ltype=''{1}'' cannot contain ''{0}''
|
||||
new.instance.of.singleton=New instance of class annotated with @groovy.lang.Singleton
|
||||
replace.new.expression.with.0.instance=Replace with ''{0}.instance''
|
||||
getter.0.clashes.with.getter.1={0} clashes with {1}
|
||||
unused.0=Unused {0}
|
||||
remove.0=Remove {0}
|
||||
replace.postfix.0.with.prefix.0=Replace postfix {0} with prefix {0}
|
||||
replace.0.with.1=Replace {0} with binary {1}
|
||||
gr.deprecated.api.usage=Deprecated API inspection
|
||||
category.method.0.cannot.be.applied.to.1=Category method ''{0}'' cannot be applied to ''{1}''
|
||||
local.var.0.is.reassigned.in.closure=Local variable {0} is reassigned in {1} with other type
|
||||
anonymous.class=anonymous class
|
||||
closure=closure
|
||||
other.scope=Other scope
|
||||
|
||||
+17
-1
@@ -293,6 +293,8 @@ public class GroovyAssignabilityCheckInspection extends BaseInspection {
|
||||
|
||||
private void checkConstructorCall(GrConstructorCall constructorCall, GroovyPsiElement refElement) {
|
||||
final GrArgumentList argList = constructorCall.getArgumentList();
|
||||
if (hasErrorElements(argList)) return;
|
||||
|
||||
if (!checkCannotInferArgumentTypes(refElement)) return;
|
||||
final GroovyResolveResult constructorResolveResult = constructorCall.advancedResolve();
|
||||
final PsiElement constructor = constructorResolveResult.getElement();
|
||||
@@ -555,7 +557,21 @@ public class GroovyAssignabilityCheckInspection extends BaseInspection {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* checks only children of e
|
||||
*/
|
||||
private static boolean hasErrorElements(@Nullable PsiElement e) {
|
||||
if (e == null) return false;
|
||||
|
||||
for (PsiElement child = e.getFirstChild(); child != null; child = child.getNextSibling()) {
|
||||
if (child instanceof PsiErrorElement) return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private void checkMethodCall(GrMethodCall call) {
|
||||
if (hasErrorElements(call.getArgumentList())) return;
|
||||
|
||||
final GrExpression expression = call.getInvokedExpression();
|
||||
if (!(expression instanceof GrReferenceExpression)) { //it checks in visitRefExpr(...)
|
||||
final PsiType type = expression.getType();
|
||||
@@ -709,7 +725,7 @@ public class GroovyAssignabilityCheckInspection extends BaseInspection {
|
||||
final PsiType qualifier = inferQualifierTypeByPlace((GrReferenceExpression)place);
|
||||
if (qualifier != null && !MixinMemberContributor.isCategoryMethod(staticMethod, qualifier, methodResolveResult.getSubstitutor())) {
|
||||
registerError(((GrReferenceExpression)place).getReferenceNameElement(),
|
||||
GroovyInspectionBundle.message("category,method.0.cannot.be.applied.to.1", method.getName(),
|
||||
GroovyInspectionBundle.message("category.method.0.cannot.be.applied.to.1", method.getName(),
|
||||
qualifier.getCanonicalText()));
|
||||
return false;
|
||||
}
|
||||
|
||||
-56
@@ -1,56 +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 org.jetbrains.plugins.groovy.editor.selection;
|
||||
|
||||
import com.intellij.codeInsight.editorActions.ExtendWordSelectionHandlerBase;
|
||||
import com.intellij.openapi.editor.Editor;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import org.jetbrains.plugins.groovy.lang.lexer.GroovyTokenTypes;
|
||||
import org.jetbrains.plugins.groovy.lang.lexer.TokenSets;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.GrVariableDeclaration;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author Max Medvedev
|
||||
*/
|
||||
public class GroovyFieldSemicolonSelectioner extends ExtendWordSelectionHandlerBase {
|
||||
@Override
|
||||
public boolean canSelect(PsiElement e) {
|
||||
return e instanceof GrVariableDeclaration;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TextRange> select(PsiElement e, CharSequence editorText, int cursorOffset, Editor editor) {
|
||||
PsiElement next = e.getNextSibling();
|
||||
while (next != null &&
|
||||
next.getNode() != null &&
|
||||
TokenSets.WHITE_SPACES_SET.contains(next.getNode().getElementType()) &&
|
||||
!next.textContains('\n')) {
|
||||
next = next.getNextSibling();
|
||||
}
|
||||
|
||||
final List<TextRange> ranges = new ArrayList<TextRange>();
|
||||
ranges.add(e.getTextRange());
|
||||
if (next != null && next.getNode().getElementType() == GroovyTokenTypes.mSEMI) {
|
||||
ranges.add(new TextRange(e.getTextRange().getStartOffset(), next.getTextRange().getEndOffset()));
|
||||
}
|
||||
return ranges;
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -42,7 +42,7 @@ public class GroovyGStringSelectioner extends ExtendWordSelectionHandlerBase {
|
||||
|
||||
@Override
|
||||
public List<TextRange> select(PsiElement e, CharSequence editorText, int cursorOffset, Editor editor) {
|
||||
List<TextRange> ranges = new ArrayList<TextRange>();
|
||||
List<TextRange> ranges = super.select(e, editorText, cursorOffset, editor);
|
||||
PsiElement parent = e.getParent();
|
||||
|
||||
if (parent instanceof GrString) {
|
||||
|
||||
+143
@@ -0,0 +1,143 @@
|
||||
/*
|
||||
* 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 org.jetbrains.plugins.groovy.editor.selection;
|
||||
|
||||
import com.intellij.codeInsight.editorActions.ExtendWordSelectionHandler;
|
||||
import com.intellij.codeInsight.editorActions.ExtendWordSelectionHandlerBase;
|
||||
import com.intellij.openapi.editor.Editor;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiWhiteSpace;
|
||||
import org.jetbrains.plugins.groovy.lang.lexer.GroovyTokenTypes;
|
||||
import org.jetbrains.plugins.groovy.lang.lexer.TokenSets;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.GrStatement;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrExpression;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.util.PsiUtil;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author Max Medvedev
|
||||
*/
|
||||
public class GroovyStatementSelectioner implements ExtendWordSelectionHandler {
|
||||
@Override
|
||||
public boolean canSelect(PsiElement e) {
|
||||
return e instanceof GrExpression && PsiUtil.isExpressionStatement(e) ||
|
||||
(e instanceof GrStatement && !(e instanceof GrExpression)) ||
|
||||
e.getNode().getElementType() == GroovyTokenTypes.mSEMI;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TextRange> select(PsiElement e, CharSequence editorText, int cursorOffset, Editor editor) {
|
||||
TextRange originalRange;
|
||||
|
||||
PsiElement first;
|
||||
PsiElement last;
|
||||
if (e instanceof GrStatement) {
|
||||
first = e;
|
||||
PsiElement next = e.getNextSibling();
|
||||
next = skipWhitespacesForward(next);
|
||||
if (next != null && next.getNode().getElementType() == GroovyTokenTypes.mSEMI) {
|
||||
originalRange = new TextRange(e.getTextRange().getStartOffset(), next.getTextRange().getEndOffset());
|
||||
last = next;
|
||||
}
|
||||
else {
|
||||
originalRange = e.getTextRange();
|
||||
last = e;
|
||||
}
|
||||
}
|
||||
|
||||
else {
|
||||
last = e;
|
||||
PsiElement prev = e.getPrevSibling();
|
||||
prev = skipWhitespaceBack(prev);
|
||||
if (prev instanceof GrStatement) {
|
||||
originalRange = new TextRange(prev.getTextRange().getStartOffset(), e.getTextRange().getEndOffset());
|
||||
first = prev;
|
||||
}
|
||||
else {
|
||||
originalRange = e.getTextRange();
|
||||
first = e;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
final List<TextRange> ranges = ExtendWordSelectionHandlerBase.expandToWholeLine(editorText, originalRange);
|
||||
|
||||
|
||||
final TextRange blockRange = inferBlockRange(first, last);
|
||||
|
||||
if (!blockRange.equals(originalRange)) {
|
||||
ranges.addAll(ExtendWordSelectionHandlerBase.expandToWholeLine(editorText, blockRange, true));
|
||||
}
|
||||
|
||||
return ranges;
|
||||
}
|
||||
|
||||
private static TextRange inferBlockRange(PsiElement first, PsiElement last) {
|
||||
while (true) {
|
||||
PsiElement prev = first.getPrevSibling();
|
||||
|
||||
prev = skipWhitespaceBack(prev);
|
||||
if (isOneLineFeed(prev)) prev = prev.getPrevSibling();
|
||||
prev = skipWhitespaceBack(prev);
|
||||
if (prev != null && prev.getNode().getElementType() == GroovyTokenTypes.mSEMI || prev instanceof GrStatement) {
|
||||
first = prev;
|
||||
}
|
||||
else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
while (true) {
|
||||
PsiElement next = last.getNextSibling();
|
||||
|
||||
next = skipWhitespacesForward(next);
|
||||
if (isOneLineFeed(next)) next = next.getNextSibling();
|
||||
next = skipWhitespacesForward(next);
|
||||
if (next != null && next.getNode().getElementType() == GroovyTokenTypes.mSEMI || next instanceof GrStatement) {
|
||||
last = next;
|
||||
}
|
||||
else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return new TextRange(first.getTextRange().getStartOffset(), last.getTextRange().getEndOffset());
|
||||
}
|
||||
|
||||
private static PsiElement skipWhitespacesForward(PsiElement next) {
|
||||
while (isSpaceWithoutLineFeed(next)) next = next.getNextSibling();
|
||||
return next;
|
||||
}
|
||||
|
||||
private static PsiElement skipWhitespaceBack(PsiElement prev) {
|
||||
while (isSpaceWithoutLineFeed(prev)) prev = prev.getPrevSibling();
|
||||
return prev;
|
||||
}
|
||||
|
||||
private static boolean isOneLineFeed(PsiElement e) {
|
||||
if (e == null) return false;
|
||||
if (!TokenSets.WHITE_SPACES_SET.contains(e.getNode().getElementType())) return false;
|
||||
|
||||
final String text = e.getText();
|
||||
return text.indexOf('\n') == text.lastIndexOf('\n');
|
||||
}
|
||||
|
||||
private static boolean isSpaceWithoutLineFeed(PsiElement e) {
|
||||
return e instanceof PsiWhiteSpace && e.getText().indexOf('\n') == -1;
|
||||
}
|
||||
}
|
||||
+5
-11
@@ -15,24 +15,18 @@
|
||||
*/
|
||||
package org.jetbrains.plugins.groovy.editor.selection;
|
||||
|
||||
import com.intellij.lang.ASTNode;
|
||||
import com.intellij.openapi.util.Condition;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.auxiliary.GrListOrMap;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.arguments.GrArgumentList;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.blocks.GrCodeBlock;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.params.GrParameterList;
|
||||
|
||||
import static org.jetbrains.plugins.groovy.lang.lexer.GroovyTokenTypes.*;
|
||||
import org.jetbrains.plugins.groovy.GroovyFileType;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.GroovyPsiElement;
|
||||
|
||||
/**
|
||||
* @author Maxim.Medvedev
|
||||
*/
|
||||
public class GroovyWordSelectionFilter implements Condition<PsiElement> {
|
||||
public boolean value(PsiElement element) {
|
||||
|
||||
final ASTNode node = element.getNode();
|
||||
return !(element instanceof GroovyPsiElement || element.getLanguage() == GroovyFileType.GROOVY_LANGUAGE);
|
||||
/* final ASTNode node = element.getNode();
|
||||
if (node == null) return false;
|
||||
|
||||
final IElementType type = node.getElementType();
|
||||
@@ -61,6 +55,6 @@ public class GroovyWordSelectionFilter implements Condition<PsiElement> {
|
||||
!(element instanceof GrArgumentList) &&
|
||||
!(type == mDOLLAR)
|
||||
|
||||
;
|
||||
;*/
|
||||
}
|
||||
}
|
||||
|
||||
+91
@@ -0,0 +1,91 @@
|
||||
/*
|
||||
* 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 org.jetbrains.plugins.groovy.editor.selection;
|
||||
|
||||
import com.intellij.codeInsight.editorActions.ExtendWordSelectionHandler;
|
||||
import com.intellij.codeInsight.editorActions.ExtendWordSelectionHandlerBase;
|
||||
import com.intellij.codeInsight.editorActions.SelectWordUtil;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.editor.Editor;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.impl.source.tree.LeafPsiElement;
|
||||
import org.jetbrains.plugins.groovy.GroovyFileType;
|
||||
import org.jetbrains.plugins.groovy.lang.lexer.GroovyTokenTypes;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.GroovyPsiElement;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.GrClassInitializer;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.GrStatement;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.GrVariableDeclaration;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.blocks.GrOpenBlock;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrExpression;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.GrTypeDefinition;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.members.GrMethod;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.toplevel.imports.GrImportStatement;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.api.toplevel.packaging.GrPackageDefinition;
|
||||
import org.jetbrains.plugins.groovy.lang.psi.util.PsiUtil;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author Max Medvedev
|
||||
*/
|
||||
public class GroovyWordSelectionHandler implements ExtendWordSelectionHandler {
|
||||
private static final Logger LOG = Logger.getInstance(GroovyWordSelectionHandler.class);
|
||||
|
||||
@Override
|
||||
public boolean canSelect(PsiElement e) {
|
||||
return (e instanceof GroovyPsiElement || e.getLanguage() == GroovyFileType.GROOVY_LANGUAGE) &&
|
||||
!(e.getNode().getElementType() == GroovyTokenTypes.mDOLLAR);
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TextRange> select(PsiElement e, CharSequence editorText, int cursorOffset, Editor editor) {
|
||||
final TextRange originalRange = e.getTextRange();
|
||||
LOG.assertTrue(originalRange.getEndOffset() <= editorText.length(), getClass() + "; " + e);
|
||||
|
||||
List<TextRange> ranges;
|
||||
if (isSeparateStatement(e)) {
|
||||
ranges = ExtendWordSelectionHandlerBase.expandToWholeLine(editorText, originalRange, true);
|
||||
if (ranges.size() == 1 && ranges.contains(originalRange)) {
|
||||
ranges = ExtendWordSelectionHandlerBase.expandToWholeLine(editorText, originalRange, false);
|
||||
}
|
||||
}
|
||||
else {
|
||||
ranges = new ArrayList<TextRange>();
|
||||
ranges.add(e.getTextRange());
|
||||
}
|
||||
|
||||
SelectWordUtil.addWordSelection(editor.getSettings().isCamelWords(), editorText, cursorOffset, ranges);
|
||||
|
||||
return ranges;
|
||||
}
|
||||
|
||||
private static boolean isSeparateStatement(PsiElement e) {
|
||||
return
|
||||
e instanceof LeafPsiElement ||
|
||||
e instanceof GrExpression && PsiUtil.isExpressionStatement(e) ||
|
||||
e instanceof GrVariableDeclaration ||
|
||||
e instanceof GrStatement && !(e instanceof GrExpression) ||
|
||||
e instanceof GrMethod ||
|
||||
e instanceof GrClassInitializer ||
|
||||
e instanceof GrImportStatement ||
|
||||
e instanceof GrPackageDefinition ||
|
||||
e instanceof GrOpenBlock ||
|
||||
e instanceof GrTypeDefinition && !((GrTypeDefinition)e).isAnonymous()
|
||||
;
|
||||
}
|
||||
}
|
||||
@@ -57,7 +57,7 @@ public class GroovyActionsTest extends LightCodeInsightFixtureTestCase {
|
||||
"a.<selection>foo(b)</selection>"
|
||||
}
|
||||
|
||||
public void testSWInCodeBlock() {doTestForSelectWord 3}
|
||||
public void testSWInCodeBlock() {doTestForSelectWord 5}
|
||||
|
||||
public void testElseBranch() {
|
||||
doTestForSelectWord (3, '''\
|
||||
@@ -77,6 +77,46 @@ def foo() {
|
||||
''')
|
||||
}
|
||||
|
||||
void testBlocksOfCode() {
|
||||
doTestForSelectWord(8, '''\
|
||||
this.allOptions = [:];
|
||||
confTag.option.each{ opt ->
|
||||
def value = opt.'@value';
|
||||
if (value == null) {
|
||||
value = opt.value ? opt.value[0].'@defaultName' : null;
|
||||
}
|
||||
this.allOptions[opt.'@name'] = value;
|
||||
}
|
||||
|
||||
def moduleNode = confTag.mod<caret>ule[0] ;
|
||||
if (moduleNode != null && !"wholeProject".equals(this.allOptions['TEST_SEARCH_SCOPE'])) {
|
||||
this.moduleRef = JpsElementFactory.instance.createModuleReference(moduleNode.'@name');
|
||||
} else {
|
||||
this.moduleRef = null;
|
||||
}
|
||||
|
||||
this.macroExpander = macroExpander;
|
||||
''', '''\
|
||||
this.allOptions = [:];
|
||||
confTag.option.each{ opt ->
|
||||
def value = opt.'@value';
|
||||
if (value == null) {
|
||||
value = opt.value ? opt.value[0].'@defaultName' : null;
|
||||
}
|
||||
this.allOptions[opt.'@name'] = value;
|
||||
}
|
||||
|
||||
<selection> def moduleNode = confTag.mod<caret>ule[0] ;
|
||||
if (moduleNode != null && !"wholeProject".equals(this.allOptions['TEST_SEARCH_SCOPE'])) {
|
||||
this.moduleRef = JpsElementFactory.instance.createModuleReference(moduleNode.'@name');
|
||||
} else {
|
||||
this.moduleRef = null;
|
||||
}
|
||||
</selection>
|
||||
this.macroExpander = macroExpander;
|
||||
''')
|
||||
}
|
||||
|
||||
private void doTestForSelectWord(int count, String input, String expected) {
|
||||
myFixture.configureByText("a.groovy", input);
|
||||
selectWord(count)
|
||||
|
||||
Reference in New Issue
Block a user