Search in sources :

Example 1 with GrReferenceExpression

use of org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression in project intellij-community by JetBrains.

the class GroovyCodeFragmentFactory method externalParameters.

public static Pair<Map<String, String>, GroovyFile> externalParameters(String text, @NotNull final PsiElement context) {
    final GroovyPsiElementFactory factory = GroovyPsiElementFactory.getInstance(context.getProject());
    final GroovyFile toEval = factory.createGroovyFile(text, false, context);
    final GrClosableBlock closure = PsiTreeUtil.getParentOfType(context, GrClosableBlock.class);
    final Map<String, String> parameters = new THashMap<>();
    final Map<GrExpression, String> replacements = new HashMap<>();
    toEval.accept(new GroovyRecursiveElementVisitor() {

        @Override
        public void visitReferenceExpression(@NotNull GrReferenceExpression referenceExpression) {
            super.visitReferenceExpression(referenceExpression);
            if (PsiUtil.isThisReference(referenceExpression) || PsiUtil.isSuperReference(referenceExpression)) {
                replaceWithReference(referenceExpression, "delegate");
                return;
            }
            PsiElement resolved = referenceExpression.resolve();
            if (resolved instanceof PsiMember && (resolved instanceof PsiClass || ((PsiMember) resolved).hasModifierProperty(PsiModifier.STATIC))) {
                String qName = com.intellij.psi.util.PsiUtil.getMemberQualifiedName((PsiMember) resolved);
                if (qName != null && qName.contains(".") && !referenceExpression.isQualified()) {
                    replaceWithReference(referenceExpression, qName);
                    return;
                }
            }
            if (shouldDelegate(referenceExpression, resolved)) {
                replaceWithReference(referenceExpression, "delegate." + referenceExpression.getReferenceName());
                return;
            }
            if (resolved instanceof GrVariable && !(resolved instanceof GrField) && !PsiTreeUtil.isAncestor(toEval, resolved, false)) {
                final String name = ((GrVariable) resolved).getName();
                if (resolved instanceof ClosureSyntheticParameter && PsiTreeUtil.isAncestor(toEval, ((ClosureSyntheticParameter) resolved).getClosure(), false)) {
                    return;
                }
                if (resolved instanceof GrBindingVariable && !PsiTreeUtil.isAncestor(resolved.getContainingFile(), toEval, false)) {
                    return;
                }
                String value;
                if (closure != null && PsiTreeUtil.findCommonParent(resolved, closure) != closure && !(resolved instanceof ClosureSyntheticParameter)) {
                    // Evaluating inside closure for outer variable definitions
                    // All non-local variables are accessed by references
                    value = "this." + name;
                } else {
                    value = name;
                }
                parameters.put(name, value);
                return;
            }
            if (resolved instanceof PsiLocalVariable || resolved instanceof PsiParameter && !(resolved instanceof GrParameter)) {
                String name = referenceExpression.getReferenceName();
                parameters.put(name, name);
            }
        }

        private boolean shouldDelegate(GrReferenceExpression referenceExpression, @Nullable PsiElement resolved) {
            if (referenceExpression.isQualified()) {
                return false;
            }
            if (resolved instanceof GrField) {
                return true;
            }
            if (resolved instanceof PsiMethod) {
                String methodName = ((PsiMethod) resolved).getName();
                if (closure != null && "getDelegate".equals(methodName) || "call".equals(methodName)) {
                    return true;
                }
            }
            return closure != null && resolved instanceof GrLightVariable && "owner".equals(((GrLightVariable) resolved).getName());
        }

        private void replaceWithReference(GrExpression expr, final String exprText) {
            replacements.put(expr, exprText);
        }

        @Override
        public void visitCodeReferenceElement(@NotNull GrCodeReferenceElement refElement) {
            super.visitCodeReferenceElement(refElement);
            if (refElement.getQualifier() == null) {
                PsiElement resolved = refElement.resolve();
                if (resolved instanceof PsiClass) {
                    String qName = ((PsiClass) resolved).getQualifiedName();
                    if (qName != null) {
                        int dotIndex = qName.lastIndexOf(".");
                        if (dotIndex < 0)
                            return;
                        String packageName = qName.substring(0, dotIndex);
                        refElement.setQualifier(factory.createReferenceElementFromText(packageName));
                    }
                }
            }
        }
    });
    for (GrExpression expression : replacements.keySet()) {
        expression.replaceWithExpression(factory.createExpressionFromText(replacements.get(expression)), false);
    }
    return Pair.create(parameters, toEval);
}
Also used : GrField(org.jetbrains.plugins.groovy.lang.psi.api.statements.GrField) THashMap(gnu.trove.THashMap) GrParameter(org.jetbrains.plugins.groovy.lang.psi.api.statements.params.GrParameter) GrVariable(org.jetbrains.plugins.groovy.lang.psi.api.statements.GrVariable) THashMap(gnu.trove.THashMap) GrBindingVariable(org.jetbrains.plugins.groovy.lang.psi.impl.synthetic.GrBindingVariable) GrClosableBlock(org.jetbrains.plugins.groovy.lang.psi.api.statements.blocks.GrClosableBlock) GrExpression(org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrExpression) GroovyRecursiveElementVisitor(org.jetbrains.plugins.groovy.lang.psi.GroovyRecursiveElementVisitor) ClosureSyntheticParameter(org.jetbrains.plugins.groovy.lang.psi.impl.synthetic.ClosureSyntheticParameter) GrReferenceExpression(org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression) GroovyPsiElementFactory(org.jetbrains.plugins.groovy.lang.psi.GroovyPsiElementFactory) GrCodeReferenceElement(org.jetbrains.plugins.groovy.lang.psi.api.types.GrCodeReferenceElement) GrLightVariable(org.jetbrains.plugins.groovy.lang.psi.impl.synthetic.GrLightVariable) GroovyFile(org.jetbrains.plugins.groovy.lang.psi.GroovyFile)

Example 2 with GrReferenceExpression

use of org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression in project intellij-community by JetBrains.

the class GroovyEditorTextProvider method getEditorText.

@Override
public TextWithImports getEditorText(PsiElement elementAtCaret) {
    String result = "";
    PsiElement element = findExpressionInner(elementAtCaret, true);
    if (element != null) {
        if (element instanceof GrReferenceExpression) {
            final GrReferenceExpression reference = (GrReferenceExpression) element;
            if (reference.getQualifier() == null) {
                final PsiElement resolved = reference.resolve();
                if (resolved instanceof PsiEnumConstant) {
                    final PsiEnumConstant enumConstant = (PsiEnumConstant) resolved;
                    final PsiClass enumClass = enumConstant.getContainingClass();
                    if (enumClass != null) {
                        result = enumClass.getName() + "." + enumConstant.getName();
                    }
                }
            }
        }
        if (result.isEmpty()) {
            result = element.getText();
        }
    }
    return new TextWithImportsImpl(CodeFragmentKind.EXPRESSION, result);
}
Also used : PsiEnumConstant(com.intellij.psi.PsiEnumConstant) PsiClass(com.intellij.psi.PsiClass) TextWithImportsImpl(com.intellij.debugger.engine.evaluation.TextWithImportsImpl) PsiElement(com.intellij.psi.PsiElement) GroovyPsiElement(org.jetbrains.plugins.groovy.lang.psi.GroovyPsiElement) GrReferenceExpression(org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression)

Example 3 with GrReferenceExpression

use of org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression in project intellij-community by JetBrains.

the class GroovyEnterHandler method handleInString.

private static boolean handleInString(Editor editor, int caretOffset, DataContext dataContext, EditorActionHandler originalHandler) {
    Project project = CommonDataKeys.PROJECT.getData(dataContext);
    if (project == null)
        return false;
    final VirtualFile vfile = FileDocumentManager.getInstance().getFile(editor.getDocument());
    assert vfile != null;
    PsiFile file = PsiManager.getInstance(project).findFile(vfile);
    Document document = editor.getDocument();
    String fileText = document.getText();
    if (fileText.length() == caretOffset)
        return false;
    if (!checkStringApplicable(editor, caretOffset))
        return false;
    if (file == null)
        return false;
    PsiDocumentManager.getInstance(project).commitDocument(document);
    final PsiElement stringElement = inferStringPair(file, caretOffset);
    if (stringElement == null)
        return false;
    ASTNode node = stringElement.getNode();
    final IElementType nodeElementType = node.getElementType();
    boolean isInsertIndent = isInsertIndent(caretOffset, stringElement.getTextRange().getStartOffset(), fileText);
    // For simple String literals like 'abc'
    CaretModel caretModel = editor.getCaretModel();
    if (nodeElementType == GroovyTokenTypes.mSTRING_LITERAL) {
        if (isSingleQuoteString(stringElement)) {
            //the case of print '\<caret>'
            if (isSlashBeforeCaret(caretOffset, fileText)) {
                EditorModificationUtil.insertStringAtCaret(editor, "\n");
            } else if (stringElement.getParent() instanceof GrReferenceExpression) {
                TextRange range = stringElement.getTextRange();
                convertEndToMultiline(range.getEndOffset(), document, fileText, '\'');
                document.insertString(range.getStartOffset(), "''");
                caretModel.moveToOffset(caretOffset + 2);
                EditorModificationUtil.insertStringAtCaret(editor, "\n");
            } else {
                EditorModificationUtil.insertStringAtCaret(editor, "'+");
                originalHandler.execute(editor, dataContext);
                EditorModificationUtil.insertStringAtCaret(editor, "'");
                PsiDocumentManager.getInstance(project).commitDocument(document);
                CodeStyleManager.getInstance(project).reformatRange(file, caretOffset, caretModel.getOffset());
            }
        } else {
            insertLineFeedInString(editor, dataContext, originalHandler, isInsertIndent);
        }
        return true;
    }
    if (GSTRING_TOKENS.contains(nodeElementType) || nodeElementType == GroovyElementTypes.GSTRING_CONTENT && GSTRING_TOKENS.contains(node.getFirstChildNode().getElementType()) || nodeElementType == GroovyTokenTypes.mDOLLAR && node.getTreeParent().getTreeParent().getElementType() == GroovyElementTypes.GSTRING) {
        PsiElement parent = stringElement.getParent();
        if (nodeElementType == GroovyTokenTypes.mGSTRING_LITERAL) {
            parent = stringElement;
        } else {
            while (parent != null && !(parent instanceof GrLiteral)) {
                parent = parent.getParent();
            }
        }
        if (parent == null)
            return false;
        if (isDoubleQuotedString(parent)) {
            PsiElement exprSibling = stringElement.getNextSibling();
            boolean rightFromDollar = exprSibling instanceof GrExpression && exprSibling.getTextRange().getStartOffset() == caretOffset;
            if (rightFromDollar)
                caretOffset--;
            TextRange parentRange = parent.getTextRange();
            if (rightFromDollar || parent.getParent() instanceof GrReferenceExpression) {
                convertEndToMultiline(parent.getTextRange().getEndOffset(), document, fileText, '"');
                document.insertString(parentRange.getStartOffset(), "\"\"");
                caretModel.moveToOffset(caretOffset + 2);
                EditorModificationUtil.insertStringAtCaret(editor, "\n");
                if (rightFromDollar) {
                    caretModel.moveCaretRelatively(1, 0, false, false, true);
                }
            } else if (isSlashBeforeCaret(caretOffset, fileText)) {
                EditorModificationUtil.insertStringAtCaret(editor, "\n");
            } else {
                EditorModificationUtil.insertStringAtCaret(editor, "\"+");
                originalHandler.execute(editor, dataContext);
                EditorModificationUtil.insertStringAtCaret(editor, "\"");
                PsiDocumentManager.getInstance(project).commitDocument(document);
                CodeStyleManager.getInstance(project).reformatRange(file, caretOffset, caretModel.getOffset());
            }
        } else {
            insertLineFeedInString(editor, dataContext, originalHandler, isInsertIndent);
        }
        return true;
    }
    if (REGEX_TOKENS.contains(nodeElementType) || nodeElementType == GroovyElementTypes.GSTRING_CONTENT && REGEX_TOKENS.contains(node.getFirstChildNode().getElementType()) || nodeElementType == GroovyTokenTypes.mDOLLAR && node.getTreeParent().getTreeParent().getElementType() == GroovyElementTypes.REGEX) {
        PsiElement parent = stringElement.getParent();
        if (nodeElementType == GroovyTokenTypes.mREGEX_LITERAL || nodeElementType == GroovyTokenTypes.mDOLLAR_SLASH_REGEX_LITERAL) {
            parent = stringElement;
        } else {
            while (parent != null && !(parent instanceof GrLiteral)) {
                parent = parent.getParent();
            }
        }
        if (parent == null || parent.getLastChild() instanceof PsiErrorElement)
            return false;
        PsiElement exprSibling = stringElement.getNextSibling();
        boolean rightFromDollar = exprSibling instanceof GrExpression && exprSibling.getTextRange().getStartOffset() == caretOffset;
        if (rightFromDollar) {
            caretModel.moveToOffset(caretOffset - 1);
        }
        insertLineFeedInString(editor, dataContext, originalHandler, isInsertIndent);
        if (rightFromDollar) {
            caretModel.moveCaretRelatively(1, 0, false, false, true);
        }
        return true;
    }
    return false;
}
Also used : VirtualFile(com.intellij.openapi.vfs.VirtualFile) CaretModel(com.intellij.openapi.editor.CaretModel) TextRange(com.intellij.openapi.util.TextRange) GrExpression(org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrExpression) Document(com.intellij.openapi.editor.Document) GrReferenceExpression(org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression) IElementType(com.intellij.psi.tree.IElementType) Project(com.intellij.openapi.project.Project) ASTNode(com.intellij.lang.ASTNode) GrLiteral(org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.literals.GrLiteral)

Example 4 with GrReferenceExpression

use of org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression in project intellij-community by JetBrains.

the class GroovyChangeContextUtil method encodeContextInfo.

public static void encodeContextInfo(PsiElement element, PsiElement scope) {
    if (!(element instanceof GroovyPsiElement))
        return;
    if (PsiUtil.isThisReference(element)) {
        GrReferenceExpression thisExpr = (GrReferenceExpression) element;
        final PsiClass containingClass = PsiTreeUtil.getParentOfType(thisExpr, PsiClass.class);
        element.putCopyableUserData(KEY_ENCODED, KEY_ENCODED);
        thisExpr.putCopyableUserData(QUALIFIER_CLASS_KEY, containingClass);
    } else if (element instanceof GrReferenceExpression) {
        GrReferenceExpression refExpr = (GrReferenceExpression) element;
        final GrExpression qualifier = refExpr.getQualifierExpression();
        if (qualifier == null) {
            PsiElement refElement = refExpr.resolve();
            element.putCopyableUserData(KEY_ENCODED, KEY_ENCODED);
            if (refElement != null && !PsiTreeUtil.isContextAncestor(scope, refElement, false)) {
                if (refElement instanceof GrAccessorMethod)
                    refElement = ((GrAccessorMethod) refElement).getProperty();
                if (refElement instanceof PsiClass) {
                    refExpr.putCopyableUserData(REF_TO_CLASS, (PsiClass) refElement);
                } else if (refElement instanceof PsiMember) {
                    refExpr.putCopyableUserData(REF_TO_MEMBER, (PsiMember) refElement);
                }
            }
        }
    } else if (element instanceof GrCodeReferenceElement) {
        final PsiElement resolvedElement = ((GrCodeReferenceElement) element).resolve();
        element.putCopyableUserData(KEY_ENCODED, KEY_ENCODED);
        if (resolvedElement instanceof PsiClass && !PsiTreeUtil.isContextAncestor(scope, resolvedElement, false)) {
            element.putCopyableUserData(REF_TO_CLASS, (PsiClass) resolvedElement);
        }
    }
    for (PsiElement child = element.getFirstChild(); child != null; child = child.getNextSibling()) {
        encodeContextInfo(child, scope);
    }
}
Also used : GrAccessorMethod(org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.members.GrAccessorMethod) GrCodeReferenceElement(org.jetbrains.plugins.groovy.lang.psi.api.types.GrCodeReferenceElement) GroovyPsiElement(org.jetbrains.plugins.groovy.lang.psi.GroovyPsiElement) GrExpression(org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrExpression) GroovyPsiElement(org.jetbrains.plugins.groovy.lang.psi.GroovyPsiElement) GrReferenceExpression(org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression)

Example 5 with GrReferenceExpression

use of org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression in project intellij-community by JetBrains.

the class GantMemberContributor method processDynamicElements.

@Override
public void processDynamicElements(@NotNull PsiType qualifierType, PsiClass aClass, @NotNull PsiScopeProcessor processor, @NotNull PsiElement place, @NotNull ResolveState state) {
    if (aClass != null && ClassUtil.getSuperClassesWithCache(aClass).containsKey("groovy.util.AntBuilder")) {
        processAntTasks(processor, place, state);
        return;
    }
    if (!(place instanceof GrReferenceExpression) || ((GrReferenceExpression) place).isQualified()) {
        return;
    }
    GrClosableBlock closure = PsiTreeUtil.getContextOfType(place, GrClosableBlock.class, true);
    boolean antTasksProcessed = false;
    while (closure != null) {
        final PsiElement parent = closure.getParent();
        if (parent instanceof GrMethodCall) {
            final PsiMethod method = ((GrMethodCall) parent).resolveMethod();
            if (method instanceof AntBuilderMethod) {
                antTasksProcessed = true;
                if (!processAntTasks(processor, place, state)) {
                    return;
                }
                if (!((AntBuilderMethod) method).processNestedElements(processor)) {
                    return;
                }
                break;
            }
        }
        closure = PsiTreeUtil.getContextOfType(closure, GrClosableBlock.class, true);
    }
    // ------- gant-specific
    PsiFile file = place.getContainingFile();
    if (file == null || !GroovyScriptUtil.isSpecificScriptFile(file, GantScriptType.INSTANCE)) {
        return;
    }
    if (aClass instanceof GroovyScriptClass) {
        for (GrArgumentLabel label : GantUtils.getScriptTargets((GroovyFile) file)) {
            final String targetName = label.getName();
            if (targetName != null) {
                final PsiNamedElement variable = new LightVariableBuilder(targetName, GroovyCommonClassNames.GROOVY_LANG_CLOSURE, label).setBaseIcon(JetgroovyIcons.Groovy.Gant_target);
                if (!ResolveUtil.processElement(processor, variable, state)) {
                    return;
                }
            }
        }
    }
    if (!antTasksProcessed) {
        processAntTasks(processor, place, state);
    }
}
Also used : GrMethodCall(org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrMethodCall) GrArgumentLabel(org.jetbrains.plugins.groovy.lang.psi.api.statements.arguments.GrArgumentLabel) GrClosableBlock(org.jetbrains.plugins.groovy.lang.psi.api.statements.blocks.GrClosableBlock) GrReferenceExpression(org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression) LightVariableBuilder(com.intellij.psi.impl.light.LightVariableBuilder) GroovyScriptClass(org.jetbrains.plugins.groovy.lang.psi.impl.synthetic.GroovyScriptClass)

Aggregations

GrReferenceExpression (org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrReferenceExpression)177 GrExpression (org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrExpression)92 PsiElement (com.intellij.psi.PsiElement)56 Nullable (org.jetbrains.annotations.Nullable)28 GroovyPsiElement (org.jetbrains.plugins.groovy.lang.psi.GroovyPsiElement)27 GrClosableBlock (org.jetbrains.plugins.groovy.lang.psi.api.statements.blocks.GrClosableBlock)26 NotNull (org.jetbrains.annotations.NotNull)25 GroovyResolveResult (org.jetbrains.plugins.groovy.lang.psi.api.GroovyResolveResult)22 GrMethodCall (org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrMethodCall)22 GroovyPsiElementFactory (org.jetbrains.plugins.groovy.lang.psi.GroovyPsiElementFactory)21 GrArgumentList (org.jetbrains.plugins.groovy.lang.psi.api.statements.arguments.GrArgumentList)17 GrParameter (org.jetbrains.plugins.groovy.lang.psi.api.statements.params.GrParameter)16 GrField (org.jetbrains.plugins.groovy.lang.psi.api.statements.GrField)15 GroovyRecursiveElementVisitor (org.jetbrains.plugins.groovy.lang.psi.GroovyRecursiveElementVisitor)14 GrVariable (org.jetbrains.plugins.groovy.lang.psi.api.statements.GrVariable)14 PsiType (com.intellij.psi.PsiType)13 GrAssignmentExpression (org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrAssignmentExpression)12 Project (com.intellij.openapi.project.Project)11 ArrayList (java.util.ArrayList)11 GrMethodCallExpression (org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.path.GrMethodCallExpression)11