Package com.jetbrains.lang.dart.ide.actions

Source Code of com.jetbrains.lang.dart.ide.actions.DartGotoSuperHandler

package com.jetbrains.lang.dart.ide.actions;

import com.intellij.codeInsight.daemon.DaemonBundle;
import com.intellij.codeInsight.daemon.impl.PsiElementListNavigator;
import com.intellij.ide.util.DefaultPsiElementCellRenderer;
import com.intellij.lang.LanguageCodeInsightActionHandler;
import com.intellij.openapi.editor.Editor;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.Condition;
import com.intellij.psi.NavigatablePsiElement;
import com.intellij.psi.PsiElement;
import com.intellij.psi.PsiFile;
import com.intellij.psi.util.PsiTreeUtil;
import com.intellij.util.containers.ContainerUtil;
import com.jetbrains.lang.dart.DartComponentType;
import com.jetbrains.lang.dart.DartLanguage;
import com.jetbrains.lang.dart.psi.DartClass;
import com.jetbrains.lang.dart.psi.DartComponent;
import com.jetbrains.lang.dart.psi.DartType;
import com.jetbrains.lang.dart.util.DartClassResolveResult;
import com.jetbrains.lang.dart.util.DartResolveUtil;
import org.jetbrains.annotations.NotNull;

import java.util.ArrayList;
import java.util.List;

public class DartGotoSuperHandler implements LanguageCodeInsightActionHandler {
  @Override
  public boolean isValidFor(Editor editor, PsiFile file) {
    return file.getLanguage() == DartLanguage.INSTANCE;
  }

  @Override
  public void invoke(@NotNull Project project, @NotNull Editor editor, @NotNull PsiFile file) {
    final PsiElement at = file.findElementAt(editor.getCaretModel().getOffset());

    final DartComponent component = PsiTreeUtil.getParentOfType(at, DartComponent.class);
    final DartClass dartClass = PsiTreeUtil.getParentOfType(at, DartClass.class);
    if (at == null || dartClass == null || component == null) return;

    final List<DartClass> supers = new ArrayList<DartClass>();
    final DartType superClass = dartClass.getSuperClass();
    // looks like there's no sense in jumping to Object class
    if (superClass != null && !DartResolveUtil.OBJECT.equals(superClass.getReferenceExpression().getText())) {
      final DartClassResolveResult dartClassResolveResult = DartResolveUtil.resolveClassByType(superClass);
      if (dartClassResolveResult.getDartClass() != null) {
        supers.add(dartClassResolveResult.getDartClass());
      }
    }

    List<DartClassResolveResult> implementsAndMixinsList =
      DartResolveUtil.resolveClassesByTypes(DartResolveUtil.getImplementsAndMixinsList(dartClass));
    for (DartClassResolveResult resolveResult : implementsAndMixinsList) {
      final DartClass resolveResultDartClass = resolveResult.getDartClass();
      if (resolveResultDartClass != null) {
        supers.add(resolveResultDartClass);
      }
    }
    final List<DartComponent> superItems = DartResolveUtil.findNamedSubComponents(false, supers.toArray(new DartClass[supers.size()]));

    final DartComponentType type = DartComponentType.typeOf(component);
    if (type == DartComponentType.METHOD) {
      tryNavigateToSuperMethod(editor, component, superItems);
    }
    else if (!supers.isEmpty() && component instanceof DartClass) {
      PsiElementListNavigator.openTargets(
        editor,
        DartResolveUtil.getComponentNames(supers).toArray(new NavigatablePsiElement[supers.size()]),
        DaemonBundle.message("navigation.title.subclass", component.getName(), supers.size()),
        "Subclasses of " + component.getName(),
        new DefaultPsiElementCellRenderer()
      );
    }
  }

  private static void tryNavigateToSuperMethod(Editor editor,
                                               DartComponent methodDeclaration,
                                               List<DartComponent> superItems) {
    final String methodName = methodDeclaration.getName();
    if (methodName == null || !methodDeclaration.isPublic()) {
      return;
    }
    final List<DartComponent> filteredSuperItems = ContainerUtil.filter(superItems, new Condition<DartComponent>() {
      @Override
      public boolean value(DartComponent component) {
        return methodName.equals(component.getName());
      }
    });
    if (!filteredSuperItems.isEmpty()) {
      final NavigatablePsiElement[] targets =
        DartResolveUtil.getComponentNames(filteredSuperItems).toArray(new NavigatablePsiElement[filteredSuperItems.size()]);
      PsiElementListNavigator.openTargets(editor,
                                          targets,
                                          DaemonBundle.message("navigation.title.super.method", methodName),
                                          null,
                                          new DefaultPsiElementCellRenderer());
    }
  }

  @Override
  public boolean startInWriteAction() {
    return true;
  }
}
TOP

Related Classes of com.jetbrains.lang.dart.ide.actions.DartGotoSuperHandler

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.