private ITypeBinding[] computeTypeVariables(ITypeBinding[] bindings) {
   Selection selection = getSelection();
   Set<ITypeBinding> result = new HashSet<>();
   // first remove all type variables that come from outside of the method
   // or are covered by the selection
   CompilationUnit compilationUnit = (CompilationUnit) fEnclosingBodyDeclaration.getRoot();
   for (int i = 0; i < bindings.length; i++) {
     ASTNode decl = compilationUnit.findDeclaringNode(bindings[i]);
     if (decl == null
         || (!selection.covers(decl) && decl.getParent() instanceof MethodDeclaration))
       result.add(bindings[i]);
   }
   // all all type variables which are needed since a local variable uses it
   for (int i = 0; i < fArguments.length; i++) {
     IVariableBinding arg = fArguments[i];
     ITypeBinding type = arg.getType();
     if (type != null && type.isTypeVariable()) {
       ASTNode decl = compilationUnit.findDeclaringNode(type);
       if (decl == null
           || (!selection.covers(decl) && decl.getParent() instanceof MethodDeclaration))
         result.add(type);
     }
   }
   return result.toArray(new ITypeBinding[result.size()]);
 }
  private ASTRewrite doAddEnumConst(CompilationUnit astRoot) {
    SimpleName node = fOriginalNode;

    ASTNode newTypeDecl = astRoot.findDeclaringNode(fSenderBinding);
    if (newTypeDecl == null) {
      astRoot = ASTResolving.createQuickFixAST(getCompilationUnit(), null);
      newTypeDecl = astRoot.findDeclaringNode(fSenderBinding.getKey());
    }

    if (newTypeDecl != null) {
      AST ast = newTypeDecl.getAST();

      ASTRewrite rewrite = ASTRewrite.create(ast);

      EnumConstantDeclaration constDecl = ast.newEnumConstantDeclaration();
      constDecl.setName(ast.newSimpleName(node.getIdentifier()));

      ListRewrite listRewriter =
          rewrite.getListRewrite(newTypeDecl, EnumDeclaration.ENUM_CONSTANTS_PROPERTY);
      listRewriter.insertLast(constDecl, null);

      addLinkedPosition(rewrite.track(constDecl.getName()), false, KEY_NAME);

      return rewrite;
    }
    return null;
  }
  @Override
  protected ASTRewrite getRewrite() throws CoreException {
    ASTNode boundNode = fAstRoot.findDeclaringNode(fBinding);
    ASTNode declNode = null;
    CompilationUnit newRoot = fAstRoot;
    if (boundNode != null) {
      declNode = boundNode; // is same CU
    } else {
      newRoot = ASTResolving.createQuickFixAST(getCompilationUnit(), null);
      declNode = newRoot.findDeclaringNode(fBinding.getKey());
    }
    ImportRewrite imports = createImportRewrite(newRoot);

    if (declNode instanceof TypeDeclaration) {
      AST ast = declNode.getAST();
      ASTRewrite rewrite = ASTRewrite.create(ast);

      ImportRewriteContext importRewriteContext =
          new ContextSensitiveImportRewriteContext(declNode, imports);
      Type newInterface = imports.addImport(fNewInterface, ast, importRewriteContext);
      ListRewrite listRewrite =
          rewrite.getListRewrite(declNode, TypeDeclaration.SUPER_INTERFACE_TYPES_PROPERTY);
      listRewrite.insertLast(newInterface, null);

      // set up linked mode
      final String KEY_TYPE = "type"; // $NON-NLS-1$
      addLinkedPosition(rewrite.track(newInterface), true, KEY_TYPE);
      return rewrite;
    }
    return null;
  }
 private static SourceProvider resolveSourceProvider(
     RefactoringStatus status, ITypeRoot typeRoot, ASTNode invocation) {
   CompilationUnit root = (CompilationUnit) invocation.getRoot();
   IMethodBinding methodBinding = Invocations.resolveBinding(invocation);
   if (methodBinding == null) {
     status.addFatalError(
         RefactoringCoreMessages.InlineMethodRefactoring_error_noMethodDeclaration);
     return null;
   }
   MethodDeclaration declaration = (MethodDeclaration) root.findDeclaringNode(methodBinding);
   if (declaration != null) {
     return new SourceProvider(typeRoot, declaration);
   }
   IMethod method = (IMethod) methodBinding.getJavaElement();
   if (method != null) {
     CompilationUnit methodDeclarationAstRoot;
     ICompilationUnit methodCu = method.getCompilationUnit();
     if (methodCu != null) {
       methodDeclarationAstRoot = new RefactoringASTParser(AST.JLS3).parse(methodCu, true);
     } else {
       IClassFile classFile = method.getClassFile();
       if (!JavaElementUtil.isSourceAvailable(classFile)) {
         String methodLabel =
             JavaElementLabels.getTextLabel(
                 method,
                 JavaElementLabels.M_FULLY_QUALIFIED | JavaElementLabels.M_PARAMETER_TYPES);
         status.addFatalError(
             Messages.format(
                 RefactoringCoreMessages.InlineMethodRefactoring_error_classFile, methodLabel));
         return null;
       }
       methodDeclarationAstRoot = new RefactoringASTParser(AST.JLS3).parse(classFile, true);
     }
     ASTNode node =
         methodDeclarationAstRoot.findDeclaringNode(methodBinding.getMethodDeclaration().getKey());
     if (node instanceof MethodDeclaration) {
       return new SourceProvider(methodDeclarationAstRoot.getTypeRoot(), (MethodDeclaration) node);
     }
   }
   status.addFatalError(RefactoringCoreMessages.InlineMethodRefactoring_error_noMethodDeclaration);
   return null;
 }
  private ASTRewrite doAddField(CompilationUnit astRoot) {
    SimpleName node = fOriginalNode;
    boolean isInDifferentCU = false;

    ASTNode newTypeDecl = astRoot.findDeclaringNode(fSenderBinding);
    if (newTypeDecl == null) {
      astRoot = ASTResolving.createQuickFixAST(getCompilationUnit(), null);
      newTypeDecl = astRoot.findDeclaringNode(fSenderBinding.getKey());
      isInDifferentCU = true;
    }
    ImportRewrite imports = createImportRewrite(astRoot);
    ImportRewriteContext importRewriteContext =
        new ContextSensitiveImportRewriteContext(
            ASTResolving.findParentBodyDeclaration(node), imports);

    if (newTypeDecl != null) {
      AST ast = newTypeDecl.getAST();

      ASTRewrite rewrite = ASTRewrite.create(ast);

      VariableDeclarationFragment fragment = ast.newVariableDeclarationFragment();
      fragment.setName(ast.newSimpleName(node.getIdentifier()));

      Type type = evaluateVariableType(ast, imports, importRewriteContext, fSenderBinding);

      FieldDeclaration newDecl = ast.newFieldDeclaration(fragment);
      newDecl.setType(type);
      newDecl
          .modifiers()
          .addAll(ASTNodeFactory.newModifiers(ast, evaluateFieldModifiers(newTypeDecl)));

      if (fSenderBinding.isInterface() || fVariableKind == CONST_FIELD) {
        fragment.setInitializer(ASTNodeFactory.newDefaultExpression(ast, type, 0));
      }

      ChildListPropertyDescriptor property = ASTNodes.getBodyDeclarationsProperty(newTypeDecl);
      List<BodyDeclaration> decls =
          ASTNodes.<BodyDeclaration>getChildListProperty(newTypeDecl, property);

      int maxOffset = isInDifferentCU ? -1 : node.getStartPosition();

      int insertIndex = findFieldInsertIndex(decls, newDecl, maxOffset);

      ListRewrite listRewriter = rewrite.getListRewrite(newTypeDecl, property);
      listRewriter.insertAt(newDecl, insertIndex, null);

      ModifierCorrectionSubProcessor.installLinkedVisibilityProposals(
          getLinkedProposalModel(), rewrite, newDecl.modifiers(), fSenderBinding.isInterface());

      addLinkedPosition(rewrite.track(newDecl.getType()), false, KEY_TYPE);
      if (!isInDifferentCU) {
        addLinkedPosition(rewrite.track(node), true, KEY_NAME);
      }
      addLinkedPosition(rewrite.track(fragment.getName()), false, KEY_NAME);

      if (fragment.getInitializer() != null) {
        addLinkedPosition(rewrite.track(fragment.getInitializer()), false, KEY_INITIALIZER);
      }
      return rewrite;
    }
    return null;
  }