mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
javafx: Use modern API for sorting completion suggestions, store completion suggestions in cache (IDEA-150446)
This commit is contained in:
+19
-2
@@ -22,7 +22,10 @@ import com.intellij.testFramework.LightProjectDescriptor;
|
||||
import com.intellij.util.ArrayUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.*;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
/**
|
||||
@@ -240,6 +243,20 @@ public class JavaFxCompletionTest extends LightFixtureCompletionTestCase {
|
||||
doOptionsTest(Arrays.asList("pane", "node", "box", "model", "text", "target"), "FxIdGuessedOptionsController");
|
||||
}
|
||||
|
||||
public void testVariableCompletionBooleanFirst() throws Exception {
|
||||
doOrderTest("zAssignable", "dConvertible", "tConvertible", "controller", "mUnknown");
|
||||
}
|
||||
|
||||
public void testVariableCompletionTooltipFirst() throws Exception {
|
||||
doOrderTest("tAssignable", "controller", "mUnknown", "dIncompatible");
|
||||
}
|
||||
|
||||
private void doOrderTest(String... expected) {
|
||||
myFixture.configureByFiles(getTestName(true) + ".fxml");
|
||||
complete();
|
||||
assertOrderedEquals(myFixture.getLookupElementStrings(), expected);
|
||||
}
|
||||
|
||||
private void doOptionsTest(final List<String> expectedOptions, final String... javaClasses) {
|
||||
final List<String> files = new ArrayList<>();
|
||||
files.add(getTestName(true) + ".fxml");
|
||||
@@ -248,7 +265,7 @@ public class JavaFxCompletionTest extends LightFixtureCompletionTestCase {
|
||||
complete();
|
||||
|
||||
final Set<String> actualOptions = Arrays.stream(myItems).map(LookupElement::getLookupString).collect(Collectors.toSet());
|
||||
assertEquals(new HashSet<>(expectedOptions), actualOptions);
|
||||
assertSameElements(expectedOptions, actualOptions);
|
||||
}
|
||||
|
||||
public void testOnlyCssAsStylesheets() throws Exception {
|
||||
|
||||
@@ -35,6 +35,7 @@ import com.intellij.psi.xml.*;
|
||||
import com.intellij.util.Processor;
|
||||
import com.intellij.xml.XmlAttributeDescriptor;
|
||||
import com.intellij.xml.XmlElementDescriptor;
|
||||
import gnu.trove.THashMap;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
import org.jetbrains.plugins.javaFX.fxml.descriptors.JavaFxClassBackedElementDescriptor;
|
||||
@@ -603,31 +604,45 @@ public class JavaFxPsiUtil {
|
||||
return null;
|
||||
}
|
||||
|
||||
private static final Key<CachedValue<Map<String, XmlAttributeValue>>> FILE_IDS_KEY = Key.create("FILE_IDS_KEY");
|
||||
|
||||
@NotNull
|
||||
public static Map<String, XmlAttributeValue> collectFileIds(final XmlTag currentTag) {
|
||||
final Map<String, XmlAttributeValue> fileIds = new HashMap<String, XmlAttributeValue>();
|
||||
currentTag.getContainingFile().accept(new XmlRecursiveElementVisitor() {
|
||||
@Override
|
||||
public void visitXmlTag(XmlTag tag) {
|
||||
super.visitXmlTag(tag);
|
||||
if (currentTag != tag) {
|
||||
final XmlAttribute attribute = tag.getAttribute(FxmlConstants.FX_ID);
|
||||
if (attribute != null) {
|
||||
fileIds.put(attribute.getValue(), attribute.getValueElement());
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
public static Map<String, XmlAttributeValue> collectFileIds(@Nullable final XmlTag currentTag) {
|
||||
if (currentTag == null) return Collections.emptyMap();
|
||||
final PsiFile containingFile = currentTag.getContainingFile();
|
||||
if (containingFile instanceof XmlFile) {
|
||||
final XmlTag rootTag = ((XmlFile)containingFile).getRootTag();
|
||||
if (rootTag != null) {
|
||||
final XmlAttribute attribute = rootTag.getAttribute(FxmlConstants.FX_CONTROLLER);
|
||||
if (attribute != null) {
|
||||
fileIds.put(FxmlConstants.CONTROLLER, attribute.getValueElement());
|
||||
}
|
||||
if (!(containingFile instanceof XmlFile)) return Collections.emptyMap();
|
||||
final XmlTag rootTag = ((XmlFile)containingFile).getRootTag();
|
||||
if (rootTag == null) return Collections.emptyMap();
|
||||
|
||||
final Map<String, XmlAttributeValue> cachedIds = CachedValuesManager.getManager(containingFile.getProject())
|
||||
.getCachedValue(rootTag, FILE_IDS_KEY,
|
||||
() -> new CachedValueProvider.Result<>(prepareFileIds(rootTag), PsiModificationTracker.MODIFICATION_COUNT), false);
|
||||
|
||||
final XmlAttribute currentIdAttribute = currentTag.getAttribute(FxmlConstants.FX_ID);
|
||||
if (currentIdAttribute != null) {
|
||||
final String currentId = currentIdAttribute.getValue();
|
||||
if (cachedIds.containsKey(currentId)) {
|
||||
final Map<String, XmlAttributeValue> filteredIds = new THashMap<>(cachedIds);
|
||||
filteredIds.remove(currentId);
|
||||
return filteredIds;
|
||||
}
|
||||
}
|
||||
return cachedIds;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private static Map<String, XmlAttributeValue> prepareFileIds(XmlTag rootTag) {
|
||||
final Map<String, XmlAttributeValue> fileIds = new THashMap<>();
|
||||
for (XmlTag tag : SyntaxTraverser.psiTraverser().withRoot(rootTag).filter(XmlTag.class)) {
|
||||
final XmlAttribute idAttribute = tag.getAttribute(FxmlConstants.FX_ID);
|
||||
if (idAttribute != null) {
|
||||
fileIds.put(idAttribute.getValue(), idAttribute.getValueElement());
|
||||
}
|
||||
}
|
||||
final XmlAttribute controllerAttribute = rootTag.getAttribute(FxmlConstants.FX_CONTROLLER);
|
||||
if (controllerAttribute != null) {
|
||||
fileIds.put(FxmlConstants.CONTROLLER, controllerAttribute.getValueElement());
|
||||
}
|
||||
return fileIds;
|
||||
}
|
||||
|
||||
|
||||
+6
-7
@@ -15,7 +15,9 @@
|
||||
*/
|
||||
package org.jetbrains.plugins.javaFX.fxml.refs;
|
||||
|
||||
import com.intellij.codeInsight.lookup.LookupItem;
|
||||
import com.intellij.codeInsight.completion.PrioritizedLookupElement;
|
||||
import com.intellij.codeInsight.lookup.LookupElement;
|
||||
import com.intellij.codeInsight.lookup.LookupElementBuilder;
|
||||
import com.intellij.openapi.util.Comparing;
|
||||
import com.intellij.openapi.util.TextRange;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
@@ -185,12 +187,9 @@ class JavaFxComponentIdReferenceProvider extends PsiReferenceProvider {
|
||||
@NotNull
|
||||
@Override
|
||||
public Object[] getVariants() {
|
||||
return myAcceptableIds.stream().map(
|
||||
id -> {
|
||||
LookupItem<String> item = new LookupItem<String>(id, id);
|
||||
item.setPriority(TypeMatch.getPriority(myTypeMatches.get(id)));
|
||||
return item;
|
||||
}).toArray(LookupItem[]::new);
|
||||
return myAcceptableIds.stream()
|
||||
.map(id -> PrioritizedLookupElement.withPriority(LookupElementBuilder.create(id), TypeMatch.getPriority(myTypeMatches.get(id))))
|
||||
.toArray(LookupElement[]::new);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,25 @@
|
||||
<?import javafx.scene.layout.GridPane?>
|
||||
<?import javafx.scene.control.Button?>
|
||||
<?import javafx.scene.control.Tooltip?>
|
||||
<?import java.lang.Double?>
|
||||
<?import java.lang.Boolean?>
|
||||
<?import sample.UnknownModel?>
|
||||
<GridPane fx:controller="sample.Controller" xmlns:fx="http://javafx.com/fxml">
|
||||
<fx:define>
|
||||
<Tooltip text="tooltip" fx:id="tConvertible"/>
|
||||
</fx:define>
|
||||
|
||||
<fx:define>
|
||||
<Double fx:value="123.45" fx:id="dConvertible"/>
|
||||
</fx:define>
|
||||
|
||||
<fx:define>
|
||||
<Boolean fx:value="123.45" fx:id="zAssignable"/>
|
||||
</fx:define>
|
||||
|
||||
<fx:define>
|
||||
<UnknownModel fx:id="mUnknown"/>
|
||||
</fx:define>
|
||||
|
||||
<Button onAction="#sayHello" text="Hello" fx:id="b1" defaultButton="$<caret>" />
|
||||
</GridPane>
|
||||
@@ -0,0 +1,20 @@
|
||||
<?import javafx.scene.layout.GridPane?>
|
||||
<?import javafx.scene.control.Button?>
|
||||
<?import javafx.scene.control.Tooltip?>
|
||||
<?import java.lang.Double?>
|
||||
<?import sample.UnknownModel?>
|
||||
<GridPane fx:controller="sample.Controller" xmlns:fx="http://javafx.com/fxml">
|
||||
<fx:define>
|
||||
<Tooltip text="tooltip" fx:id="tAssignable"/>
|
||||
</fx:define>
|
||||
|
||||
<fx:define>
|
||||
<Double fx:value="123.45" fx:id="dIncompatible"/>
|
||||
</fx:define>
|
||||
|
||||
<fx:define>
|
||||
<UnknownModel fx:id="mUnknown"/>
|
||||
</fx:define>
|
||||
|
||||
<Button onAction="#sayHello" text="Hello" fx:id="b1" tooltip="$<caret>" />
|
||||
</GridPane>
|
||||
Reference in New Issue
Block a user