Enable completion autopopup inside PsiLiteral for my LookupElements

Hello guys,

I have my own completion contributor

class TypeSafeConfCompletionContributor extends CompletionContributor {   extend(CompletionType.BASIC,     PlatformPatterns.psiElement(),     new CompletionProvider[CompletionParameters]() {       def addCompletions(parameters: CompletionParameters, context: ProcessingContext, resultSet: CompletionResultSet) {         parameters.getPosition.getContext match {           case literal: PsiLiteral if literal.getValue.isInstanceOf[String] =>             val text = literal.getValue.toString.replace(DummyId, "").replace(DummyIdTrimmed, "")             val variants = getVariants(text, literal.getProject).map(_.getFirstChild.asInstanceOf[NodeName]).toSet             val prefix = if (text.endsWith(".")) "" else if (text.contains(".")) text.split("\\.").last else text             variants.foreach(v => resultSet.caseInsensitive().withPrefixMatcher(prefix).addElement(v.toLookup))           case _ => //just ignore         }       }     }   )   def getVariants(text: String, project: Project) = {     val confFiles = ReferenceUtil.getFilesByType(project, TypeSafeConfFileType())     val nodeParts = (if (text.endsWith(".")) text + DummyIdTrimmed else text).split("\\.").toList     val nodes = confFiles.map(_.getFirstChild.getChildren).flatten.toList     getNodes(nodeParts.head, nodeParts.tail, nodes)   }   def getNodes(nodeName: String, nodeNames: List[String], nodes: List[PsiElement]): List[PsiElement] = {     val n = filterNodes(nodeName, nodeNames.isEmpty, nodes)     if (nodeNames.nonEmpty) getNodes(nodeNames.head, nodeNames.tail, n.map(_.getChildren).flatten)     else n   }   def filterNodes(nodeName: String, lastNode: Boolean, nodes: List[PsiElement]) = {     nodes.filter {       case n: Node if nodeName == DummyIdTrimmed => true       case n: Node if n.getFirstChild.isInstanceOf[NodeName] => if (lastNode) n.getFirstChild.getText startsWith nodeName else n.getFirstChild.getText == nodeName       case _ => false     }   } }

It works fine inside PsiLiteral when I press Ctrl + Space
This is how it looks like inside Idea

My question is how to enable autopopup inside PsiLiteral with my own lookup elements?

Comment actions Permalink

If you mean LookupElements in order to provide Psi Navigation then you shouldn't be using the Contributor API. That API is used within scenarios where you don't have a reference to a specific element, for instance a list of keywords available within a particular context.

You'll want to provide an implementation of PsiReferenceContributor in order to provide LookupElements + resolving support.
As a side note, you can use the intellij patterns for matching Psi Elements rather than Scala's pattern matching, which is useful in more complex scenarios.

Hopefully this answers your question, apologies if i've misunderstood.

Comment actions Permalink

Hi Alan,

Thank you very much for your answer and suggestion to use intellij patterns. I will take a look.
But I mean how to enable auto-appearing small window with completion variants instead of clicking Ctrl+Space. Like when in java you wrote object name than enter dot and can see autopopup with all methods. You don't need to press Ctrl+Space, because window appears automatically.

Thanks again!

Comment actions Permalink

Unfortunately I do not  know the inner-workings of IJ's autocompletion - so I can't fully answer this question.
However, for my plugin this happens automatically when your caret is in a position in which psi reference contribution has successfully been invoked
i.e. I did not explicitly register this intention with the contributor/reference API.

Hopefully someone from JetBrains may be able to answer this question, otherwise you'll have to search through the code to find out the exact scenario in which this behaviour occurs :)

Comment actions Permalink

There's CompletionConfidence API (shouldSkipAutopopup method) to control whether to show the autopopup. You can register your own extension there and enable autopopup for your string literals. By default it's disabled by SkipAutopopupInStrings class, so make sure your extension has order="before javaSkipAutopopupInStrings" attribute.

Comment actions Permalink

Peter, thank you very much. It works fine for me.


Please sign in to leave a comment.