diff options
Diffstat (limited to 'sd-plugin/src/main/java/org/intellij/sdk/language/hierarchy/SdCallTreeStructure.java')
-rw-r--r-- | sd-plugin/src/main/java/org/intellij/sdk/language/hierarchy/SdCallTreeStructure.java | 73 |
1 files changed, 73 insertions, 0 deletions
diff --git a/sd-plugin/src/main/java/org/intellij/sdk/language/hierarchy/SdCallTreeStructure.java b/sd-plugin/src/main/java/org/intellij/sdk/language/hierarchy/SdCallTreeStructure.java new file mode 100644 index 00000000000..fb612ed851a --- /dev/null +++ b/sd-plugin/src/main/java/org/intellij/sdk/language/hierarchy/SdCallTreeStructure.java @@ -0,0 +1,73 @@ +package org.intellij.sdk.language.hierarchy; + +import com.intellij.ide.hierarchy.HierarchyNodeDescriptor; +import com.intellij.ide.hierarchy.HierarchyTreeStructure; +import com.intellij.openapi.project.Project; +import com.intellij.psi.PsiElement; +import com.intellij.psi.util.PsiTreeUtil; +import com.intellij.util.ArrayUtil; +import com.intellij.util.ArrayUtilRt; +import org.intellij.sdk.language.SdUtil; +import org.intellij.sdk.language.psi.SdFile; +import org.intellij.sdk.language.psi.SdFunctionDefinition; +import org.intellij.sdk.language.psi.SdIdentifierVal; +import org.intellij.sdk.language.psi.SdRankProfileDefinition; +import org.intellij.sdk.language.psi.impl.SdPsiImplUtil; +import org.jetbrains.annotations.NotNull; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.HashSet; +import java.util.List; + +public abstract class SdCallTreeStructure extends HierarchyTreeStructure { + protected final String myScopeType; + protected final SdFile myFile; + protected HashMap<String, List<PsiElement>> macrosMap; + protected HashMap<String, HashSet<SdRankProfileDefinition>> ranksHeritageMap; + + public SdCallTreeStructure(Project project, PsiElement element, String currentScopeType) { + super(project, new SdCallHierarchyNodeDescriptor(null, element, true)); + myScopeType = currentScopeType; + myFile = (SdFile) element.getContainingFile(); + macrosMap = SdUtil.createMacrosMap(myFile); + ranksHeritageMap = new HashMap<>(); + } + + @NotNull + protected abstract HashSet<PsiElement> getChildren(@NotNull SdFunctionDefinition element); + + @Override + protected Object @NotNull [] buildChildren(@NotNull HierarchyNodeDescriptor descriptor) { + final List<SdCallHierarchyNodeDescriptor> descriptors = new ArrayList<>(); + + if (descriptor instanceof SdCallHierarchyNodeDescriptor) { + PsiElement element = descriptor.getPsiElement(); + if (element == null) { + return ArrayUtilRt.EMPTY_OBJECT_ARRAY; + } + boolean isCallable = SdHierarchyUtil.isExecutable(element); + HierarchyNodeDescriptor nodeDescriptor = getBaseDescriptor(); + if (!isCallable || nodeDescriptor == null) { + return ArrayUtilRt.EMPTY_OBJECT_ARRAY; + } + + HashSet<PsiElement> children = getChildren((SdFunctionDefinition) element); + + final HashMap<PsiElement, SdCallHierarchyNodeDescriptor> callerToDescriptorMap = new HashMap<>(); + PsiElement baseClass = PsiTreeUtil.getParentOfType(element, SdRankProfileDefinition.class); + + for (PsiElement caller : children) { + if (isInScope(baseClass, caller, myScopeType)) { + SdCallHierarchyNodeDescriptor callerDescriptor = callerToDescriptorMap.get(caller); + if (callerDescriptor == null) { + callerDescriptor = new SdCallHierarchyNodeDescriptor(descriptor, caller, false); + callerToDescriptorMap.put(caller, callerDescriptor); + descriptors.add(callerDescriptor); + } + } + } + } + return ArrayUtil.toObjectArray(descriptors); + } +} |