@Override
  protected boolean preprocessUsages(@NotNull final Ref<UsageInfo[]> refUsages) {
    final MultiMap<PsiElement, String> conflicts = new MultiMap<PsiElement, String>();
    myExtractEnumProcessor.findEnumConstantConflicts(refUsages);
    if (!DestinationFolderComboBox.isAccessible(
        myProject,
        sourceClass.getContainingFile().getVirtualFile(),
        myClass.getContainingFile().getContainingDirectory().getVirtualFile())) {
      conflicts.putValue(
          sourceClass,
          "Extracted class won't be accessible in "
              + RefactoringUIUtil.getDescription(sourceClass, true));
    }
    ApplicationManager.getApplication()
        .runWriteAction(
            new Runnable() {
              public void run() {
                myClass.delete();
              }
            });
    final Project project = sourceClass.getProject();
    final GlobalSearchScope scope = GlobalSearchScope.allScope(project);
    final PsiClass existingClass =
        JavaPsiFacade.getInstance(project).findClass(getQualifiedName(), scope);
    if (existingClass != null) {
      conflicts.putValue(
          existingClass,
          RefactorJBundle.message("cannot.perform.the.refactoring")
              + RefactorJBundle.message("there.already.exists.a.class.with.the.chosen.name"));
    }

    if (!myGenerateAccessors) {
      calculateInitializersConflicts(conflicts);
      final NecessaryAccessorsVisitor visitor = checkNecessaryGettersSetters4ExtractedClass();
      final NecessaryAccessorsVisitor srcVisitor = checkNecessaryGettersSetters4SourceClass();
      final Set<PsiField> fieldsNeedingGetter = new LinkedHashSet<PsiField>();
      fieldsNeedingGetter.addAll(visitor.getFieldsNeedingGetter());
      fieldsNeedingGetter.addAll(srcVisitor.getFieldsNeedingGetter());
      for (PsiField field : fieldsNeedingGetter) {
        conflicts.putValue(field, "Field \'" + field.getName() + "\' needs getter");
      }
      final Set<PsiField> fieldsNeedingSetter = new LinkedHashSet<PsiField>();
      fieldsNeedingSetter.addAll(visitor.getFieldsNeedingSetter());
      fieldsNeedingSetter.addAll(srcVisitor.getFieldsNeedingSetter());
      for (PsiField field : fieldsNeedingSetter) {
        conflicts.putValue(field, "Field \'" + field.getName() + "\' needs setter");
      }
    }
    checkConflicts(refUsages, conflicts);
    return showConflicts(conflicts, refUsages.get());
  }
  private PsiClass buildClass() {
    final PsiManager manager = sourceClass.getManager();
    final Project project = sourceClass.getProject();
    final ExtractedClassBuilder extractedClassBuilder = new ExtractedClassBuilder();
    extractedClassBuilder.setProject(myProject);
    extractedClassBuilder.setClassName(newClassName);
    extractedClassBuilder.setPackageName(newPackageName);
    extractedClassBuilder.setOriginalClassName(sourceClass.getQualifiedName());
    extractedClassBuilder.setRequiresBackPointer(requiresBackpointer);
    extractedClassBuilder.setExtractAsEnum(enumConstants);
    for (PsiField field : fields) {
      extractedClassBuilder.addField(field);
    }
    for (PsiMethod method : methods) {
      extractedClassBuilder.addMethod(method);
    }
    for (PsiClass innerClass : innerClasses) {
      extractedClassBuilder.addInnerClass(
          innerClass, innerClassesToMakePublic.contains(innerClass));
    }
    extractedClassBuilder.setTypeArguments(typeParams);
    final List<PsiClass> interfaces = calculateInterfacesSupported();
    extractedClassBuilder.setInterfaces(interfaces);

    if (myGenerateAccessors) {
      final NecessaryAccessorsVisitor visitor = checkNecessaryGettersSetters4ExtractedClass();
      sourceClass.accept(visitor);
      extractedClassBuilder.setFieldsNeedingGetters(visitor.getFieldsNeedingGetter());
      extractedClassBuilder.setFieldsNeedingSetters(visitor.getFieldsNeedingSetter());
    }

    final String classString = extractedClassBuilder.buildBeanClass();
    if (extractInnerClass) {
      final PsiFileFactory factory = PsiFileFactory.getInstance(project);
      final PsiJavaFile newFile =
          (PsiJavaFile)
              factory.createFileFromText(
                  newClassName + ".java", JavaFileType.INSTANCE, classString);
      final PsiClass psiClass = newFile.getClasses()[0];
      if (!psiClass.isEnum()) {
        final PsiModifierList modifierList = psiClass.getModifierList();
        assert modifierList != null;
        modifierList.setModifierProperty(PsiModifier.STATIC, true);
      }
      final PsiElement addedClass = sourceClass.add(psiClass);
      return (PsiClass)
          CodeStyleManager.getInstance(manager)
              .reformat(
                  JavaCodeStyleManager.getInstance(project).shortenClassReferences(addedClass));
    }

    try {
      final PsiFile containingFile = sourceClass.getContainingFile();
      final PsiDirectory directory;
      final PsiDirectory containingDirectory = containingFile.getContainingDirectory();
      if (myMoveDestination != null) {
        directory = myMoveDestination.getTargetDirectory(containingDirectory);
      } else {
        final Module module = ModuleUtil.findModuleForPsiElement(containingFile);
        assert module != null;
        directory =
            PackageUtil.findOrCreateDirectoryForPackage(
                module, newPackageName, containingDirectory, false, true);
      }
      if (directory != null) {
        final PsiFileFactory factory = PsiFileFactory.getInstance(project);
        final PsiFile newFile =
            factory.createFileFromText(newClassName + ".java", JavaFileType.INSTANCE, classString);
        final PsiElement addedFile = directory.add(newFile);
        final CodeStyleManager codeStyleManager =
            CodeStyleManager.getInstance(manager.getProject());
        final PsiElement shortenedFile =
            JavaCodeStyleManager.getInstance(project).shortenClassReferences(addedFile);
        return ((PsiJavaFile) codeStyleManager.reformat(shortenedFile)).getClasses()[0];
      } else {
        return null;
      }
    } catch (IncorrectOperationException e) {
      return null;
    }
  }
  protected void performRefactoring(@NotNull UsageInfo[] usageInfos) {
    final PsiClass psiClass = buildClass();
    if (psiClass == null) return;
    if (delegationRequired) {
      buildDelegate();
    }
    myExtractEnumProcessor.performEnumConstantTypeMigration(usageInfos);
    final Set<PsiMember> members = new HashSet<PsiMember>();
    for (PsiMethod method : methods) {
      final PsiMethod member = psiClass.findMethodBySignature(method, false);
      if (member != null) {
        members.add(member);
      }
    }
    for (PsiField field : fields) {
      final PsiField member = psiClass.findFieldByName(field.getName(), false);
      if (member != null) {
        members.add(member);
        final PsiExpression initializer = member.getInitializer();
        if (initializer != null) {
          final boolean[] moveInitializerToConstructor = new boolean[1];
          initializer.accept(
              new JavaRecursiveElementWalkingVisitor() {
                @Override
                public void visitReferenceExpression(PsiReferenceExpression expression) {
                  super.visitReferenceExpression(expression);
                  final PsiElement resolved = expression.resolve();
                  if (resolved instanceof PsiField && !members.contains(resolved)) {
                    moveInitializerToConstructor[0] = true;
                  }
                }
              });

          if (moveInitializerToConstructor[0]) {
            final PsiElementFactory elementFactory = JavaPsiFacade.getElementFactory(myProject);
            PsiMethod[] constructors = psiClass.getConstructors();
            if (constructors.length == 0) {
              final PsiMethod constructor =
                  (PsiMethod) elementFactory.createConstructor().setName(psiClass.getName());
              constructors = new PsiMethod[] {(PsiMethod) psiClass.add(constructor)};
            }
            for (PsiMethod constructor : constructors) {
              MoveInstanceMembersUtil.moveInitializerToConstructor(
                  elementFactory, constructor, member);
            }
          }
        }
      }
    }

    if (myGenerateAccessors) {
      final NecessaryAccessorsVisitor visitor = checkNecessaryGettersSetters4SourceClass();
      for (PsiField field : visitor.getFieldsNeedingGetter()) {
        sourceClass.add(GenerateMembersUtil.generateGetterPrototype(field));
      }

      for (PsiField field : visitor.getFieldsNeedingSetter()) {
        sourceClass.add(GenerateMembersUtil.generateSetterPrototype(field));
      }
    }
    super.performRefactoring(usageInfos);
    if (myNewVisibility == null) return;
    for (PsiMember member : members) {
      VisibilityUtil.fixVisibility(UsageViewUtil.toElements(usageInfos), member, myNewVisibility);
    }
  }