private static boolean shouldSkipLine(final PsiFile file, Document doc, int line) {
    final int start = doc.getLineStartOffset(line);
    final int end = doc.getLineEndOffset(line);
    final int _start = CharArrayUtil.shiftForward(doc.getCharsSequence(), start, " \n\t");
    if (_start >= end) {
      return true;
    }

    TextRange alreadyChecked = null;
    for (PsiElement elem = file.findElementAt(_start);
        elem != null
            && elem.getTextOffset() <= end
            && (alreadyChecked == null || !alreadyChecked.contains(elem.getTextRange()));
        elem = elem.getNextSibling()) {
      for (PsiElement _elem = elem; _elem.getTextOffset() >= _start; _elem = _elem.getParent()) {
        alreadyChecked = _elem.getTextRange();

        if (_elem instanceof PsiDeclarationStatement) {
          final PsiElement[] declared = ((PsiDeclarationStatement) _elem).getDeclaredElements();
          for (PsiElement declaredElement : declared) {
            if (declaredElement instanceof PsiVariable) {
              return false;
            }
          }
        }

        if (_elem instanceof PsiJavaCodeReferenceElement) {
          final PsiElement resolved = ((PsiJavaCodeReferenceElement) _elem).resolve();
          if (resolved instanceof PsiVariable) {
            return false;
          }
        }
      }
    }
    return true;
  }
예제 #2
0
  public static List<PsiLambdaExpression> collectLambdas(
      @NotNull SourcePosition position, final boolean onlyOnTheLine) {
    ApplicationManager.getApplication().assertReadAccessAllowed();
    PsiFile file = position.getFile();
    final int line = position.getLine();
    final Document document = PsiDocumentManager.getInstance(file.getProject()).getDocument(file);
    if (document == null || line >= document.getLineCount()) {
      return Collections.emptyList();
    }
    PsiElement element = position.getElementAt();
    final TextRange lineRange = DocumentUtil.getLineTextRange(document, line);
    do {
      PsiElement parent = element.getParent();
      if (parent == null || (parent.getTextOffset() < lineRange.getStartOffset())) {
        break;
      }
      element = parent;
    } while (true);

    final List<PsiLambdaExpression> lambdas = new ArrayList<PsiLambdaExpression>(3);
    final PsiElementVisitor lambdaCollector =
        new JavaRecursiveElementVisitor() {
          @Override
          public void visitLambdaExpression(PsiLambdaExpression expression) {
            super.visitLambdaExpression(expression);
            if (!onlyOnTheLine || getFirstElementOnTheLine(expression, document, line) != null) {
              lambdas.add(expression);
            }
          }
        };
    element.accept(lambdaCollector);
    // add initial lambda if we're inside already
    PsiElement method = getContainingMethod(element);
    if (method instanceof PsiLambdaExpression) {
      lambdas.add((PsiLambdaExpression) method);
    }
    for (PsiElement sibling = getNextElement(element);
        sibling != null;
        sibling = getNextElement(sibling)) {
      if (!intersects(lineRange, sibling)) {
        break;
      }
      sibling.accept(lambdaCollector);
    }
    return lambdas;
  }