Implementing CompletionContributor for existing languages
What I'm trying to do is customize the autocompletion for my ruby framework. The tutorial creates its own "Simple" language, and implements the autocompletion for that language, but I want to do it for an existing language, Ruby.
public class SimpleCompletionContributor extends CompletionContributor {
public SimpleCompletionContributor() {
extend(CompletionType.BASIC,
PlatformPatterns.psiElement(SimpleTypes.VALUE).withLanguage(SimpleLanguage.INSTANCE), //<== Here's where my focus is
new CompletionProvider<CompletionParameters>() {
public void addCompletions(@NotNull CompletionParameters parameters,
ProcessingContext context,
@NotNull CompletionResultSet resultSet) {
resultSet.addElement(LookupElementBuilder.create("Hello"));
}
}
);
}
}
So far I've tried:
- Defining my framework as its own language, as in the tutorial - this worked of course, but I really don't want to have to rewrite the existing Ruby plugin. I only want to replace how it handles autocompletion.
- Trying to get it to work with any language (PlatformPatterns.psiElement(SimpleTypes.VALUE).withLanguage(Language.ANY)) - compiles, but doesn't seem to do anything
- Importing/passing in ruby as the language - this would probably be exactly what I need, but I can't figure out how to do that. Is it possible?
Or, maybe I'm going about this completely the wrong way. Any help or suggestions are appreciated.
请先登录再写评论。
If you're using Gradle and gradle-intellij for building your plugin (which I recommend), you can have Ruby plugin as a dependency, see example: https://github.com/JetBrains/ruby-type-inference/blob/master/ide-plugin/build.gradle#L42
With such installation, `Ruby` language becomes available for using in plugin.xml and RubyLanguage class for runtime.
Excellent, thank you! I'm now able to use
without having to define a new Language, but unfortunately it still doesn't work. I think my new problem is that my contributor is being overridden, or rather, that the ruby plugin is stopping the system before mine is invoked, as described in the last question of the FAQ:
"If your contributor isn't even invoked, probably there was another contributor that said 'stop' to the system, and yours happened to be ordered after that contributor. To test this hypothesis, put a breakpoint to {@link CompletionService#getVariantsFromContributors(CompletionParameters, CompletionContributor, Consumer)}, to the 'return false' line."
But the FAQ doesn't explain how to get around this problem. How can I prioritize my contributor? Or maybe get the Ruby contributor to not stop the system? Will writing my own fillCompletionVariants help with that?
edit: I've tried adding order="first" in my plugin.xml, which seems to have helped other people with my problem, but mine still isn't being called at all.
edit2: Hmm, adding a break point in getVariantsFromContributors shows that my contributor isn't even on the list to be checked. I may have a more fundamental problem after all
edit3: Where I'm at right now is if I pass in SimpleLanguage.INSTANCE and edit a test.simple file, my contributor is put on the list. If I pass in RubyLanguage.INSTANCE and edit a test.rb file, my contributor is not on the list (my contributor is registered with language="any", so I'm sure that's not the problem)