protected void invokeImpl(final PsiClass targetClass) {
    final Project project = myConstructorCall.getProject();
    PsiElementFactory elementFactory = JavaPsiFacade.getInstance(project).getElementFactory();

    try {
      PsiMethod constructor = (PsiMethod) targetClass.add(elementFactory.createConstructor());

      final PsiFile file = targetClass.getContainingFile();
      TemplateBuilderImpl templateBuilder = new TemplateBuilderImpl(constructor);
      CreateFromUsageUtils.setupMethodParameters(
          constructor,
          templateBuilder,
          myConstructorCall.getArgumentList(),
          getTargetSubstitutor(myConstructorCall));
      final PsiMethod superConstructor =
          CreateClassFromNewFix.setupSuperCall(targetClass, constructor, templateBuilder);

      constructor = CodeInsightUtilBase.forcePsiPostprocessAndRestoreElement(constructor);
      Template template = templateBuilder.buildTemplate();
      if (targetClass == null) return;
      final Editor editor = positionCursor(project, targetClass.getContainingFile(), targetClass);
      final TextRange textRange = constructor.getTextRange();
      editor.getDocument().deleteString(textRange.getStartOffset(), textRange.getEndOffset());
      editor.getCaretModel().moveToOffset(textRange.getStartOffset());

      startTemplate(
          editor,
          template,
          project,
          new TemplateEditingAdapter() {
            public void templateFinished(Template template, boolean brokenOff) {
              ApplicationManager.getApplication()
                  .runWriteAction(
                      new Runnable() {
                        public void run() {
                          try {
                            PsiDocumentManager.getInstance(project)
                                .commitDocument(editor.getDocument());
                            final int offset = editor.getCaretModel().getOffset();
                            PsiMethod constructor =
                                PsiTreeUtil.findElementOfClassAtOffset(
                                    file, offset, PsiMethod.class, false);
                            if (superConstructor == null) {
                              CreateFromUsageUtils.setupMethodBody(constructor);
                            } else {
                              OverrideImplementUtil.setupMethodBody(
                                  constructor, superConstructor, targetClass);
                            }
                            CreateFromUsageUtils.setupEditor(constructor, editor);
                          } catch (IncorrectOperationException e) {
                            LOG.error(e);
                          }
                        }
                      });
            }
          });
    } catch (IncorrectOperationException e) {
      LOG.error(e);
    }
  }
  protected boolean isValidElement(PsiElement element) {
    PsiConstructorCall constructorCall = (PsiConstructorCall) element;
    PsiMethod method = constructorCall.resolveConstructor();
    PsiExpressionList argumentList = constructorCall.getArgumentList();
    PsiClass targetClass = getTargetClasses(constructorCall).get(0);

    return !CreateFromUsageUtils.shouldCreateConstructor(targetClass, argumentList, method);
  }
 @Override
 protected boolean isValidElement(PsiElement element) {
   PsiMethodCallExpression methodCall = (PsiMethodCallExpression) element;
   PsiMethod method = (PsiMethod) methodCall.getMethodExpression().resolve();
   PsiExpressionList argumentList = methodCall.getArgumentList();
   List<PsiClass> classes = getTargetClasses(element);
   return !classes.isEmpty()
       && !CreateFromUsageUtils.shouldCreateConstructor(classes.get(0), argumentList, method);
 }
  protected boolean isAvailableImpl(int offset) {
    PsiElement element = getElement(myConstructorCall);

    PsiFile targetFile = getTargetFile(myConstructorCall);
    if (targetFile != null && !targetFile.getManager().isInProject(targetFile)) {
      return false;
    }

    if (CreateFromUsageUtils.shouldShowTag(offset, element, myConstructorCall)) {
      setText(QuickFixBundle.message("create.constructor.from.new.text"));
      return true;
    }

    return false;
  }
  @Override
  protected boolean isAvailableImpl(int offset) {
    PsiReferenceExpression ref = myMethodCall.getMethodExpression();
    if (!ref.getText().equals(getSyntheticMethodName())) return false;

    PsiMethod method = PsiTreeUtil.getParentOfType(myMethodCall, PsiMethod.class);
    if (method == null || !method.isConstructor()) return false;
    if (CreateMethodFromUsageFix.hasErrorsInArgumentList(myMethodCall)) return false;
    List<PsiClass> targetClasses = getTargetClasses(myMethodCall);
    if (targetClasses.isEmpty()) return false;

    if (CreateFromUsageUtils.shouldShowTag(offset, ref.getReferenceNameElement(), myMethodCall)) {
      setText(QuickFixBundle.message("create.constructor.text", targetClasses.get(0).getName()));
      return true;
    }

    return false;
  }
  @Override
  protected void invokeImpl(PsiClass targetClass) {
    final PsiFile callSite = myMethodCall.getContainingFile();
    final Project project = myMethodCall.getProject();
    PsiElementFactory elementFactory = JavaPsiFacade.getInstance(project).getElementFactory();

    IdeDocumentHistory.getInstance(project).includeCurrentPlaceAsChangePlace();

    try {
      PsiMethod constructor = elementFactory.createConstructor();
      constructor = (PsiMethod) targetClass.add(constructor);

      final TemplateBuilderImpl templateBuilder = new TemplateBuilderImpl(constructor);
      CreateFromUsageUtils.setupMethodParameters(
          constructor,
          templateBuilder,
          myMethodCall.getArgumentList(),
          getTargetSubstitutor(myMethodCall));

      final PsiFile psiFile = myMethodCall.getContainingFile();

      templateBuilder.setEndVariableAfter(constructor.getBody().getLBrace());
      final RangeMarker rangeMarker =
          psiFile.getViewProvider().getDocument().createRangeMarker(myMethodCall.getTextRange());

      constructor = CodeInsightUtilCore.forcePsiPostprocessAndRestoreElement(constructor);

      targetClass = constructor.getContainingClass();
      myMethodCall =
          CodeInsightUtil.findElementInRange(
              psiFile,
              rangeMarker.getStartOffset(),
              rangeMarker.getEndOffset(),
              myMethodCall.getClass());
      rangeMarker.dispose();

      Template template = templateBuilder.buildTemplate();
      final Editor editor = positionCursor(project, targetClass.getContainingFile(), targetClass);
      if (editor == null) return;
      final TextRange textRange = constructor.getTextRange();
      final PsiFile file = targetClass.getContainingFile();
      editor.getDocument().deleteString(textRange.getStartOffset(), textRange.getEndOffset());
      editor.getCaretModel().moveToOffset(textRange.getStartOffset());

      startTemplate(
          editor,
          template,
          project,
          new TemplateEditingAdapter() {
            @Override
            public void templateFinished(Template template, boolean brokenOff) {
              ApplicationManager.getApplication()
                  .runWriteAction(
                      new Runnable() {
                        @Override
                        public void run() {
                          try {
                            PsiDocumentManager.getInstance(project)
                                .commitDocument(editor.getDocument());
                            final int offset = editor.getCaretModel().getOffset();
                            PsiMethod constructor =
                                PsiTreeUtil.findElementOfClassAtOffset(
                                    file, offset, PsiMethod.class, false);
                            CreateFromUsageUtils.setupMethodBody(constructor);
                            CreateFromUsageUtils.setupEditor(constructor, editor);

                            UndoUtil.markPsiFileForUndo(callSite);
                          } catch (IncorrectOperationException e) {
                            LOG.error(e);
                          }
                        }
                      });
            }
          });
    } catch (IncorrectOperationException e) {
      LOG.error(e);
    }
  }
  @Override
  protected void invokeImpl(final PsiClass targetClass) {
    if (CreateFromUsageUtils.isValidReference(myReferenceExpression, true)) {
      return;
    }

    final Project project = myReferenceExpression.getProject();
    PsiElementFactory factory = JavaPsiFacade.getInstance(project).getElementFactory();

    final PsiFile targetFile = targetClass.getContainingFile();

    PsiType[] expectedTypes = CreateFromUsageUtils.guessType(myReferenceExpression, false);
    PsiType type = expectedTypes[0];

    String varName = myReferenceExpression.getReferenceName();
    PsiExpression initializer = null;
    boolean isInline = false;
    PsiExpression[] expressions =
        CreateFromUsageUtils.collectExpressions(
            myReferenceExpression, PsiMember.class, PsiFile.class);
    PsiStatement anchor = getAnchor(expressions);
    if (anchor instanceof PsiExpressionStatement
        && ((PsiExpressionStatement) anchor).getExpression() instanceof PsiAssignmentExpression) {
      PsiAssignmentExpression assignment =
          (PsiAssignmentExpression) ((PsiExpressionStatement) anchor).getExpression();
      if (assignment.getLExpression().textMatches(myReferenceExpression)) {
        initializer = assignment.getRExpression();
        isInline = true;
      }
    }

    PsiDeclarationStatement decl =
        factory.createVariableDeclarationStatement(varName, type, initializer);

    TypeExpression expression = new TypeExpression(project, expectedTypes);

    if (isInline) {
      final PsiExpression expr = ((PsiExpressionStatement) anchor).getExpression();
      final PsiElement semicolon = expr.getNextSibling();
      if (semicolon != null) {
        final PsiElement nextSibling = semicolon.getNextSibling();
        if (nextSibling != null) {
          decl.addRange(nextSibling, anchor.getLastChild());
        }
      }
      decl = (PsiDeclarationStatement) anchor.replace(decl);
    } else {
      decl = (PsiDeclarationStatement) anchor.getParent().addBefore(decl, anchor);
    }

    PsiVariable var = (PsiVariable) decl.getDeclaredElements()[0];
    boolean isFinal =
        CodeStyleSettingsManager.getSettings(project).GENERATE_FINAL_LOCALS
            && !CreateFromUsageUtils.isAccessedForWriting(expressions);
    PsiUtil.setModifierProperty(var, PsiModifier.FINAL, isFinal);

    var = CodeInsightUtilBase.forcePsiPostprocessAndRestoreElement(var);
    if (var == null) return;
    TemplateBuilderImpl builder = new TemplateBuilderImpl(var);
    builder.replaceElement(var.getTypeElement(), expression);
    builder.setEndVariableAfter(var.getNameIdentifier());
    Template template = builder.buildTemplate();

    final Editor newEditor = positionCursor(project, targetFile, var);
    TextRange range = var.getTextRange();
    newEditor.getDocument().deleteString(range.getStartOffset(), range.getEndOffset());

    startTemplate(
        newEditor,
        template,
        project,
        new TemplateEditingAdapter() {
          @Override
          public void templateFinished(Template template, boolean brokenOff) {
            PsiDocumentManager.getInstance(project).commitDocument(newEditor.getDocument());
            final int offset = newEditor.getCaretModel().getOffset();
            final PsiLocalVariable localVariable =
                PsiTreeUtil.findElementOfClassAtOffset(
                    targetFile, offset, PsiLocalVariable.class, false);
            if (localVariable != null) {
              ApplicationManager.getApplication()
                  .runWriteAction(
                      new Runnable() {
                        @Override
                        public void run() {
                          CodeStyleManager.getInstance(project).reformat(localVariable);
                        }
                      });
            }
          }
        });
  }