diff --git a/src/com/zephir/completion/Priority.java b/src/com/zephir/completion/Priority.java index 41b2c66..c3f5d06 100644 --- a/src/com/zephir/completion/Priority.java +++ b/src/com/zephir/completion/Priority.java @@ -6,5 +6,7 @@ public class Priority { public static double METHOD_SCOPE_PRIORITY = 2.0; - + public static double CLASS_METHOD_PRIORITY = 1.7; + public static double CLASS_CONSTS_PRIORITY = 1.6; + public static double CLASS_PROPERTY_PRIORITY = 1.5; } diff --git a/src/com/zephir/completion/providers/MethodScopeCompletionProvider.java b/src/com/zephir/completion/providers/MethodScopeCompletionProvider.java index 25bf9f4..26ec694 100644 --- a/src/com/zephir/completion/providers/MethodScopeCompletionProvider.java +++ b/src/com/zephir/completion/providers/MethodScopeCompletionProvider.java @@ -10,10 +10,7 @@ import com.intellij.psi.PsiElement; import com.intellij.util.ProcessingContext; import com.zephir.completion.Priority; -import com.zephir.psi.ZephirArgument; -import com.zephir.psi.ZephirArguments; -import com.zephir.psi.ZephirFile; -import com.zephir.psi.ZephirMethodDefinition; +import com.zephir.psi.*; import org.jetbrains.annotations.NotNull; @@ -22,7 +19,6 @@ public class MethodScopeCompletionProvider extends CompletionProvider { - private static int MAX_SYNTAX_TREE_DEEP = 256; private String[] keywords = new String[] { @@ -48,11 +44,95 @@ protected void addCompletions(@NotNull CompletionParameters parameters, return; } - ZephirMethodDefinition methodDefinition = getMethodByCurrentPos(psiElement); + ZephirMethodDefinition methodDefinition = (ZephirMethodDefinition)getPsiByCurrentPos(psiElement, "method"); if (methodDefinition == null) { return; } + processMethodArguments(methodDefinition, result); + + ZephirClassBody classBody = (ZephirClassBody)getPsiByCurrentPos(psiElement, "class"); + if (classBody == null) { + return; + } + processClassMembers(classBody, result); + processClassConstants(classBody, result); + processClassMethods(classBody, result); + + //process keywords + for (String keyword : this.keywords) { + result.addElement(LookupElementBuilder.create(keyword)); + } + + for (String typeHint : this.typeHints) { + result.addElement(LookupElementBuilder.create(typeHint)); + } + } + + + private void processClassMembers(ZephirClassBody classBody, @NotNull CompletionResultSet result) { + + for(ZephirPropertyDefinition propDef : classBody.getPropertyDefinitionList()) { + LookupElementBuilder completionElement = LookupElementBuilder + .create(propDef.getId().getText(), "this->" + propDef.getId().getText()) + .withTypeText(propDef.getVisibility().getText(), true) + .withLookupString(propDef.getId().getText()) + .withTailText( + propDef.getDefaultValue() != null ? " " + propDef.getDefaultValue().getText() : "", + true + ); + + result.addElement( + PrioritizedLookupElement.withPriority(completionElement, Priority.CLASS_PROPERTY_PRIORITY) + ); + } + } + + private void processClassConstants(ZephirClassBody classBody, @NotNull CompletionResultSet result) { + + for(ZephirConstantDefinition constDef : classBody.getConstantDefinitionList()) { + LookupElementBuilder completionElement = LookupElementBuilder + .create(constDef.getId().getText(), "self::" + constDef.getId().getText()) + .withTypeText(constDef.getDefaultValue().getText()) + .withLookupString(constDef.getId().getText()); + + result.addElement( + PrioritizedLookupElement.withPriority(completionElement, Priority.CLASS_CONSTS_PRIORITY) + ); + } + } + + private void processClassMethods(ZephirClassBody classBody, @NotNull CompletionResultSet result) { + + for(ZephirAbstractMethodDefinition abstractDef : classBody.getAbstractMethodDefinitionList()) { + ZephirInterfaceMethodDefinition interDef = abstractDef.getInterfaceMethodDefinition(); + + LookupElementBuilder completionElement = LookupElementBuilder + .create(interDef.getId().getText(), "this->" + interDef.getId().getText() + "()") + .withTypeText(interDef.getReturnType() != null ? interDef.getReturnType().getText() : "") + .withLookupString(interDef.getId().getText()); + + result.addElement( + PrioritizedLookupElement.withPriority(completionElement, Priority.CLASS_METHOD_PRIORITY) + ); + } + + for(ZephirMethodDefinition methodDef : classBody.getMethodDefinitionList()) { + + LookupElementBuilder completionElement = LookupElementBuilder + .create(methodDef.getId().getText(), "this->" + methodDef.getId().getText() + "()") + .withTypeText(methodDef.getReturnType() != null ? methodDef.getReturnType().getText() : "") + .withLookupString(methodDef.getId().getText()); + + result.addElement( + PrioritizedLookupElement.withPriority(completionElement, Priority.CLASS_METHOD_PRIORITY) + ); + } + + } + + private void processMethodArguments(ZephirMethodDefinition methodDefinition, @NotNull CompletionResultSet result) { + List methodArgs = new LinkedList(); for(ZephirArguments args : methodDefinition.getArgumentsList()) { methodArgs.addAll(args.getArgumentList()); @@ -60,7 +140,6 @@ protected void addCompletions(@NotNull CompletionParameters parameters, for (ZephirArgument arg : methodArgs) { LookupElementBuilder completionElement = LookupElementBuilder - //empty space to pull up arguments of method .create(arg.getId().getText(), arg.getId().getText()) .withTypeText(arg.getType() != null ? arg.getType().getText() : "", true) .withBoldness(true) @@ -70,19 +149,14 @@ protected void addCompletions(@NotNull CompletionParameters parameters, true ); - result.addElement(PrioritizedLookupElement.withPriority(completionElement, Priority.METHOD_SCOPE_PRIORITY)); + result.addElement( + PrioritizedLookupElement.withPriority(completionElement, Priority.METHOD_SCOPE_PRIORITY) + ); } - for (String keyword : this.keywords) { - result.addElement(LookupElementBuilder.create(keyword)); - } - - for (String typeHint : this.typeHints) { - result.addElement(LookupElementBuilder.create(typeHint)); - } } - private ZephirMethodDefinition getMethodByCurrentPos(PsiElement psiElement) { + private PsiElement getPsiByCurrentPos(PsiElement psiElement, String objectType) { PsiElement parent = psiElement.getParent(); if (parent == null || parent instanceof ZephirFile) { @@ -94,12 +168,15 @@ private ZephirMethodDefinition getMethodByCurrentPos(PsiElement psiElement) { parent = parent.getParent(); if (parent == null || parent instanceof ZephirFile) { return null; - } else if (parent instanceof ZephirMethodDefinition) { - return (ZephirMethodDefinition)parent; + } else if (objectType.equals("method") && parent instanceof ZephirMethodDefinition) { + return parent; + } else if (objectType.equals("class") && parent instanceof ZephirClassBody) { + return parent; } ++findLimitCounter; } while (findLimitCounter < MAX_SYNTAX_TREE_DEEP); // to avoid possible infinite cycles return null; } + }