migrated to artifacts
[fedora-idea.git] / java / idea-ui / src / com / intellij / openapi / roots / ui / configuration / ModulesConfigurator.java
blob14027a2945f8118242e6369d548d25a985244a2b
1 package com.intellij.openapi.roots.ui.configuration;
3 import com.intellij.compiler.ModuleCompilerUtil;
4 import com.intellij.facet.Facet;
5 import com.intellij.facet.FacetModel;
6 import com.intellij.facet.impl.ProjectFacetsConfigurator;
7 import com.intellij.facet.impl.ui.FacetEditorImpl;
8 import com.intellij.ide.util.newProjectWizard.AddModuleWizard;
9 import com.intellij.ide.util.projectWizard.ModuleBuilder;
10 import com.intellij.ide.util.projectWizard.ProjectBuilder;
11 import com.intellij.openapi.application.ApplicationManager;
12 import com.intellij.openapi.module.ModifiableModuleModel;
13 import com.intellij.openapi.module.Module;
14 import com.intellij.openapi.module.ModuleManager;
15 import com.intellij.openapi.options.ConfigurationException;
16 import com.intellij.openapi.options.ShowSettingsUtil;
17 import com.intellij.openapi.project.Project;
18 import com.intellij.openapi.project.ProjectBundle;
19 import com.intellij.openapi.projectRoots.Sdk;
20 import com.intellij.openapi.roots.LibraryOrderEntry;
21 import com.intellij.openapi.roots.ModifiableRootModel;
22 import com.intellij.openapi.roots.ModuleRootModel;
23 import com.intellij.openapi.roots.impl.ProjectRootManagerImpl;
24 import com.intellij.openapi.roots.ui.configuration.actions.ModuleDeleteProvider;
25 import com.intellij.openapi.roots.ui.configuration.projectRoot.ModuleStructureConfigurable;
26 import com.intellij.openapi.roots.ui.configuration.projectRoot.ProjectJdksModel;
27 import com.intellij.openapi.roots.ui.configuration.projectRoot.StructureConfigurableContext;
28 import com.intellij.openapi.ui.Messages;
29 import com.intellij.openapi.util.Comparing;
30 import com.intellij.openapi.util.Computable;
31 import com.intellij.packaging.artifacts.Artifact;
32 import com.intellij.packaging.artifacts.ModifiableArtifactModel;
33 import com.intellij.projectImport.ProjectImportBuilder;
34 import com.intellij.util.graph.GraphGenerator;
35 import org.jetbrains.annotations.NotNull;
36 import org.jetbrains.annotations.Nullable;
38 import javax.swing.*;
39 import java.awt.*;
40 import java.util.*;
41 import java.util.List;
43 /**
44 * @author Eugene Zhuravlev
45 * Date: Dec 15, 2003
47 public class ModulesConfigurator implements ModulesProvider, ModuleEditor.ChangeListener {
48 private final Project myProject;
49 //private final ModuleStructureConfigurable myProjectRootConfigurable;
51 private boolean myModified = false;
53 private final ProjectConfigurable myProjectConfigurable;
55 private final List<ModuleEditor> myModuleEditors = new ArrayList<ModuleEditor>();
57 private final Comparator<ModuleEditor> myModuleEditorComparator = new Comparator<ModuleEditor>() {
58 final ModulesAlphaComparator myModulesComparator = new ModulesAlphaComparator();
60 public int compare(ModuleEditor editor1, ModuleEditor editor2) {
61 return myModulesComparator.compare(editor1.getModule(), editor2.getModule());
64 @SuppressWarnings({"EqualsWhichDoesntCheckParameterClass"})
65 public boolean equals(Object o) {
66 return false;
69 private ModifiableModuleModel myModuleModel;
70 private ProjectFacetsConfigurator myFacetsConfigurator;
72 private StructureConfigurableContext myContext;
74 public ModulesConfigurator(Project project, ProjectJdksModel projectJdksModel) {
75 myProject = project;
76 myModuleModel = ModuleManager.getInstance(myProject).getModifiableModel();
77 myProjectConfigurable = new ProjectConfigurable(project, this, projectJdksModel);
80 public void setContext(final StructureConfigurableContext context) {
81 myContext = context;
82 myFacetsConfigurator = createFacetsConfigurator();
85 public ProjectFacetsConfigurator getFacetsConfigurator() {
86 return myFacetsConfigurator;
89 public void disposeUIResources() {
90 ApplicationManager.getApplication().runWriteAction(new Runnable() {
91 public void run() {
92 for (final ModuleEditor moduleEditor : myModuleEditors) {
93 final ModifiableRootModel model = moduleEditor.dispose();
94 if (model != null) {
95 model.dispose();
98 myModuleEditors.clear();
100 myModuleModel.dispose();
102 myFacetsConfigurator.disposeEditors();
108 public ProjectConfigurable getModulesConfigurable() {
109 return myProjectConfigurable;
112 public Module[] getModules() {
113 return myModuleModel.getModules();
116 @Nullable
117 public Module getModule(String name) {
118 final Module moduleByName = myModuleModel.findModuleByName(name);
119 if (moduleByName != null) {
120 return moduleByName;
122 return myModuleModel.getModuleToBeRenamed(name); //if module was renamed
125 @Nullable
126 public ModuleEditor getModuleEditor(Module module) {
127 for (final ModuleEditor moduleEditor : myModuleEditors) {
128 if (module.equals(moduleEditor.getModule())) {
129 return moduleEditor;
132 return null;
135 public ModuleRootModel getRootModel(Module module) {
136 final ModuleEditor editor = getModuleEditor(module);
137 ModuleRootModel rootModel = null;
138 if (editor != null) {
139 rootModel = editor.getModifiableRootModel();
141 if (rootModel == null && getModule(module.getName()) != null) {
142 createModuleEditor(module);
143 rootModel = getModuleEditor(module).getModifiableRootModel();
146 return rootModel;
149 public FacetModel getFacetModel(Module module) {
150 return myFacetsConfigurator.getOrCreateModifiableModel(module);
153 public void resetModuleEditors() {
154 myModuleModel = ModuleManager.getInstance(myProject).getModifiableModel();
156 ApplicationManager.getApplication().runWriteAction(new Runnable() {
157 public void run() {
158 for (final ModuleEditor moduleEditor : myModuleEditors) {
159 moduleEditor.removeChangeListener(ModulesConfigurator.this);
161 myModuleEditors.clear();
162 final Module[] modules = myModuleModel.getModules();
163 if (modules.length > 0) {
164 for (Module module : modules) {
165 createModuleEditor(module);
167 Collections.sort(myModuleEditors, myModuleEditorComparator);
171 myFacetsConfigurator.resetEditors();
172 myModified = false;
175 public void createModuleEditor(final Module module) {
176 final ModuleEditor moduleEditor = new ModuleEditor(myProject, this, myFacetsConfigurator, module);
177 myModuleEditors.add(moduleEditor);
178 moduleEditor.addChangeListener(this);
181 public void moduleStateChanged(final ModifiableRootModel moduleRootModel) {
182 myProjectConfigurable.updateCircularDependencyWarning();
185 public GraphGenerator<ModifiableRootModel> createGraphGenerator() {
186 final Map<Module, ModifiableRootModel> models = new HashMap<Module, ModifiableRootModel>();
187 for (ModuleEditor moduleEditor : myModuleEditors) {
188 models.put(moduleEditor.getModule(), moduleEditor.getModifiableRootModel());
190 return ModuleCompilerUtil.createGraphGenerator(models);
193 public void apply() throws ConfigurationException {
194 final ProjectRootManagerImpl projectRootManager = ProjectRootManagerImpl.getInstanceImpl(myProject);
196 final ConfigurationException[] ex = new ConfigurationException[1];
198 ApplicationManager.getApplication().runWriteAction(new Runnable() {
199 public void run() {
200 try {
201 myFacetsConfigurator.applyEditors();
202 final List<ModifiableRootModel> models = new ArrayList<ModifiableRootModel>(myModuleEditors.size());
203 for (final ModuleEditor moduleEditor : myModuleEditors) {
204 final ModifiableRootModel model = moduleEditor.applyAndDispose();
205 if (model != null) {
206 models.add(model);
210 final ModifiableRootModel[] rootModels = models.toArray(new ModifiableRootModel[models.size()]);
211 projectRootManager.multiCommit(myModuleModel, rootModels);
212 myFacetsConfigurator.commitFacets();
215 catch (ConfigurationException e) {
216 ex[0] = e;
218 finally {
219 myFacetsConfigurator.disposeEditors();
220 ModuleStructureConfigurable.getInstance(myProject).getFacetEditorFacade().clearMaps();
221 myFacetsConfigurator = createFacetsConfigurator();
222 myModuleModel = ModuleManager.getInstance(myProject).getModifiableModel();
224 ApplicationManager.getApplication().saveAll();
228 if (ex[0] != null) {
229 throw ex[0];
232 ApplicationManager.getApplication().saveAll();
234 myModified = false;
237 private ProjectFacetsConfigurator createFacetsConfigurator() {
238 return new ProjectFacetsConfigurator(myContext, myProject);
241 public void setModified(final boolean modified) {
242 myModified = modified;
245 public ModifiableModuleModel getModuleModel() {
246 return myModuleModel;
249 public boolean deleteModule(final Module module) {
250 return doRemoveModule(getModuleEditor(module));
254 @Nullable
255 public List<Module> addModule(Component parent) {
256 if (myProject.isDefault()) return null;
257 final ProjectBuilder builder = runModuleWizard(parent);
258 if (builder != null ) {
259 final List<Module> modules = new ArrayList<Module>();
260 final List<Module> commitedModules;
261 if (builder instanceof ProjectImportBuilder<?>) {
262 final ModifiableArtifactModel artifactModel =
263 ProjectStructureConfigurable.getInstance(myProject).getArtifactsStructureConfigurable().getModifiableArtifactModel();
264 commitedModules = ((ProjectImportBuilder<?>)builder).commit(myProject, myModuleModel, this, artifactModel);
266 else {
267 commitedModules = builder.commit(myProject, myModuleModel, this);
269 if (commitedModules != null) {
270 modules.addAll(commitedModules);
272 ApplicationManager.getApplication().runWriteAction(new Runnable() {
273 public void run() {
274 for (Module module : modules) {
275 createModuleEditor(module);
279 return modules;
281 return null;
284 private Module createModule(final ModuleBuilder builder) {
285 final Exception[] ex = new Exception[]{null};
286 final Module module = ApplicationManager.getApplication().runWriteAction(new Computable<Module>() {
287 @SuppressWarnings({"ConstantConditions"})
288 public Module compute() {
289 try {
290 return builder.createModule(myModuleModel);
292 catch (Exception e) {
293 ex[0] = e;
294 return null;
298 if (ex[0] != null) {
299 Messages.showErrorDialog(ProjectBundle.message("module.add.error.message", ex[0].getMessage()),
300 ProjectBundle.message("module.add.error.title"));
302 return module;
305 @Nullable
306 public Module addModule(final ModuleBuilder moduleBuilder) {
307 final Module module = createModule(moduleBuilder);
308 if (module != null) {
309 ApplicationManager.getApplication().runWriteAction(new Runnable() {
310 public void run() {
311 createModuleEditor(module);
312 Collections.sort(myModuleEditors, myModuleEditorComparator);
315 processModuleCountChanged();
317 return module;
320 @Nullable
321 ProjectBuilder runModuleWizard(Component dialogParent) {
322 AddModuleWizard wizard = new AddModuleWizard(dialogParent, myProject, this);
323 wizard.show();
324 if (wizard.isOK()) {
325 final ProjectBuilder builder = wizard.getProjectBuilder();
326 if (builder instanceof ModuleBuilder) {
327 final ModuleBuilder moduleBuilder = (ModuleBuilder)builder;
328 if (moduleBuilder.getName() == null) {
329 moduleBuilder.setName(wizard.getProjectName());
331 if (moduleBuilder.getModuleFilePath() == null) {
332 moduleBuilder.setModuleFilePath(wizard.getModuleFilePath());
335 if (!builder.validate(myProject, myProject)) {
336 return null;
338 return wizard.getProjectBuilder();
341 return null;
345 private boolean doRemoveModule(ModuleEditor selectedEditor) {
347 String question;
348 if (myModuleEditors.size() == 1) {
349 question = ProjectBundle.message("module.remove.last.confirmation");
351 else {
352 question = ProjectBundle.message("module.remove.confirmation", selectedEditor.getModule().getName());
354 int result =
355 Messages.showYesNoDialog(myProject, question, ProjectBundle.message("module.remove.confirmation.title"), Messages.getQuestionIcon());
356 if (result != 0) {
357 return false;
359 // do remove
360 myModuleEditors.remove(selectedEditor);
362 // destroyProcess removed module
363 final Module moduleToRemove = selectedEditor.getModule();
364 // remove all dependencies on the module that is about to be removed
365 List<ModifiableRootModel> modifiableRootModels = new ArrayList<ModifiableRootModel>();
366 for (final ModuleEditor moduleEditor : myModuleEditors) {
367 final ModifiableRootModel modifiableRootModel = moduleEditor.getModifiableRootModelProxy();
368 modifiableRootModels.add(modifiableRootModel);
370 // destroyProcess editor
371 final ModifiableRootModel model = selectedEditor.dispose();
372 ModuleDeleteProvider.removeModule(moduleToRemove, model, modifiableRootModels, myModuleModel);
373 processModuleCountChanged();
374 return true;
378 private void processModuleCountChanged() {
379 for (ModuleEditor moduleEditor : myModuleEditors) {
380 moduleEditor.moduleCountChanged();
384 public void processModuleCompilerOutputChanged(String baseUrl) {
385 for (ModuleEditor moduleEditor : myModuleEditors) {
386 moduleEditor.updateCompilerOutputPathChanged(baseUrl, moduleEditor.getName());
390 public boolean isModified() {
391 if (myModuleModel.isChanged()) {
392 return true;
394 for (ModuleEditor moduleEditor : myModuleEditors) {
395 if (moduleEditor.isModified()) {
396 return true;
399 return myModified || myFacetsConfigurator.isModified();
402 public static boolean showSdkSettings(@NotNull Project project, final Sdk sdk) {
403 final ProjectStructureConfigurable configurable = ProjectStructureConfigurable.getInstance(project);
404 return ShowSettingsUtil.getInstance().editConfigurable(project, configurable, new Runnable() {
405 public void run() {
406 configurable.select(sdk, true);
411 public static boolean showLibrarySettings(@NotNull Project project, @NotNull final LibraryOrderEntry library) {
412 final ProjectStructureConfigurable configurable = ProjectStructureConfigurable.getInstance(project);
413 return ShowSettingsUtil.getInstance().editConfigurable(project, configurable, new Runnable() {
414 public void run() {
415 configurable.select(library, true);
420 public static boolean showArtifactSettings(@NotNull Project project, @Nullable final Artifact artifact) {
421 final ProjectStructureConfigurable configurable = ProjectStructureConfigurable.getInstance(project);
422 return ShowSettingsUtil.getInstance().editConfigurable(project, configurable, new Runnable() {
423 public void run() {
424 configurable.select(artifact, true);
429 public static boolean showFacetSettingsDialog(@NotNull final Facet facet,
430 @Nullable final String tabNameToSelect) {
431 final Project project = facet.getModule().getProject();
432 final ProjectStructureConfigurable config = ProjectStructureConfigurable.getInstance(project);
433 return ShowSettingsUtil.getInstance().editConfigurable(project, config, new Runnable() {
434 public void run() {
435 final ModuleStructureConfigurable modulesConfig = config.getModulesConfig();
436 config.select(facet, true).doWhenDone(new Runnable() {
437 public void run() {
438 if (tabNameToSelect != null) {
439 FacetEditorImpl facetEditor = modulesConfig.getFacetConfigurator().getOrCreateEditor(facet);
440 facetEditor.setSelectedTabName(tabNameToSelect);
448 public static boolean showDialog(Project project,
449 @Nullable final String moduleToSelect,
450 final String tabNameToSelect,
451 final boolean showModuleWizard) {
452 final ProjectStructureConfigurable config = ProjectStructureConfigurable.getInstance(project);
453 return ShowSettingsUtil.getInstance().editConfigurable(project, config, new Runnable() {
454 public void run() {
455 final ModuleStructureConfigurable modulesConfig = config.getModulesConfig();
456 config.select(moduleToSelect, tabNameToSelect, true).doWhenDone(new Runnable() {
457 public void run() {
458 modulesConfig.setStartModuleWizard(showModuleWizard);
459 SwingUtilities.invokeLater(new Runnable() {
460 public void run() {
461 modulesConfig.setStartModuleWizard(false);
470 public void moduleRenamed(Module module, final String oldName, final String name) {
471 for (ModuleEditor moduleEditor : myModuleEditors) {
472 if (module == moduleEditor.getModule() && Comparing.strEqual(moduleEditor.getName(), oldName)) {
473 moduleEditor.setModuleName(name);
474 moduleEditor.updateCompilerOutputPathChanged(ProjectStructureConfigurable.getInstance(myProject).getProjectConfig().getCompilerOutputUrl(), name);
475 myContext.invalidateModuleName(moduleEditor.getModule());
476 return;