init project under one progress, open it under another

This commit is contained in:
Dmitry Avdeev
2011-09-23 16:16:10 +04:00
parent 96835396c2
commit 5ca49db3eb
3 changed files with 114 additions and 148 deletions
@@ -17,6 +17,7 @@ package com.intellij.openapi.progress;
import com.intellij.openapi.components.ServiceManager;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.ThrowableComputable;
import org.jetbrains.annotations.Nls;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -102,6 +103,22 @@ public abstract class ProgressManager {
boolean canBeCanceled,
@Nullable Project project);
/**
* Runs the specified operation in a background thread and shows a modal progress dialog in the
* main thread while the operation is executing.
*
* @param process the operation to execute.
* @param progressTitle the title of the progress window.
* @param canBeCanceled whether "Cancel" button is shown on the progress window.
* @param project the project in the context of which the operation is executed.
* @return true result of operation
* @throws Exception exception thrown by process
*/
public abstract <T> T runProcessWithProgressSynchronously(@NotNull ThrowableComputable<T, Exception> process,
@NotNull @Nls String progressTitle,
boolean canBeCanceled,
@Nullable Project project) throws Exception;
/**
* Runs the specified operation in a background thread and shows a modal progress dialog in the
* main thread while the operation is executing.
@@ -24,8 +24,7 @@ import com.intellij.openapi.progress.*;
import com.intellij.openapi.progress.util.ProgressWindow;
import com.intellij.openapi.progress.util.SmoothProgressAdapter;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.Comparing;
import com.intellij.openapi.util.Disposer;
import com.intellij.openapi.util.*;
import com.intellij.openapi.wm.WindowManager;
import com.intellij.openapi.wm.ex.ProgressIndicatorEx;
import com.intellij.psi.PsiLock;
@@ -229,6 +228,30 @@ public class ProgressManagerImpl extends ProgressManager implements Disposable{
return runProcessWithProgressSynchronously(process, progressTitle, canBeCanceled, project, null);
}
@Override
public <T> T runProcessWithProgressSynchronously(@NotNull final ThrowableComputable<T, Exception> process,
@NotNull @Nls String progressTitle,
boolean canBeCanceled,
@Nullable Project project) throws Exception {
final Ref<T> result = new Ref<T>();
final Ref<Exception> exceptionRef = new Ref<Exception>();
Task.Modal task = new Task.Modal(project, progressTitle, canBeCanceled) {
public void run(@NotNull ProgressIndicator indicator) {
try {
T compute = process.compute();
result.set(compute);
}
catch (Exception e) {
exceptionRef.set(e);
}
}
};
runProcessWithProgressSynchronously(task, null);
if (!exceptionRef.isNull()) throw exceptionRef.get();
return result.get();
}
public boolean runProcessWithProgressSynchronously(@NotNull final Runnable process,
@NotNull String progressTitle,
boolean canBeCanceled,
@@ -242,7 +265,7 @@ public class ProgressManagerImpl extends ProgressManager implements Disposable{
return runProcessWithProgressSynchronously(task, parentComponent);
}
private static boolean runProcessWithProgressSynchronously(final Task task, final JComponent parentComponent) {
private static boolean runProcessWithProgressSynchronously(final Task task, @Nullable final JComponent parentComponent) {
final long start = System.currentTimeMillis();
long time = 0;
final boolean result = ((ApplicationEx)ApplicationManager.getApplication())
@@ -402,35 +402,32 @@ public class ProjectManagerImpl extends ProjectManagerEx implements NamedJDOMExt
myOpenProjects.add(project);
cacheOpenProjects();
UIUtil.invokeAndWaitIfNeeded(new Runnable() {
public void run() {
fireProjectOpened(project);
}
});
fireProjectOpened(project);
final StartupManagerImpl startupManager = (StartupManagerImpl)StartupManager.getInstance(project);
boolean ok;
ProgressIndicator indicator = myProgressManager.getProgressIndicator();
if (indicator == null) {
ok = myProgressManager.runProcessWithProgressSynchronously(new Runnable() {
public void run() {
startupManager.runStartupActivities();
}
}, ProjectBundle.message("project.load.progress"), true, project);
}
else {
try {
boolean ok = myProgressManager.runProcessWithProgressSynchronously(new Runnable() {
public void run() {
startupManager.runStartupActivities();
ok = true;
// dumb mode should start before post-startup activities
// only when startCacheUpdate is called from UI thread, we can guarantee that
// when the method returns, the application has entered dumb mode
UIUtil.invokeAndWaitIfNeeded(new Runnable() {
public void run() {
startupManager.startCacheUpdate();
}
});
startupManager.runPostStartupActivitiesFromExtensions();
UIUtil.invokeLaterIfNeeded(new Runnable() {
public void run() {
startupManager.runPostStartupActivities();
}
});
}
catch (Throwable e) {
LOG.info(e);
ok = false;
}
}
}, ProjectBundle.message("project.load.progress"), true, project);
if (!ok) {
closeProject(project, false, false);
@@ -438,24 +435,6 @@ public class ProjectManagerImpl extends ProjectManagerEx implements NamedJDOMExt
return false;
}
// dumb mode should start before post-startup activities
// only when startCacheUpdate is called from UI thread, we can guarantee that
// when the method returns, the application has entered dumb mode
UIUtil.invokeAndWaitIfNeeded(new Runnable() {
public void run() {
startupManager.startCacheUpdate();
}
});
startupManager.runPostStartupActivitiesFromExtensions();
UIUtil.invokeLaterIfNeeded(new Runnable() {
public void run() {
startupManager.runPostStartupActivities();
}
});
if (!application.isHeadlessEnvironment() && !application.isUnitTestMode()) {
// should be invoked last
StartupManager.getInstance(project).runWhenProjectIsInitialized(new Runnable() {
@@ -476,67 +455,16 @@ public class ProjectManagerImpl extends ProjectManagerEx implements NamedJDOMExt
myOpenProjectsArrayCache = myOpenProjects.toArray(new Project[myOpenProjects.size()]);
}
public Project loadAndOpenProject(@NotNull final String filePath) throws IOException, JDOMException, InvalidDataException {
final Ref<Project> projectRef = new Ref<Project>();
final Ref<IOException> exceptionRef = new Ref<IOException>();
myProgressManager.runProcessWithProgressSynchronously(new Runnable() {
@Override
public void run() {
try {
final Project project = convertAndLoadProject(filePath, new Ref<Boolean>());
if (project == null) {
return;
}
if (!openProject(project)) {
ApplicationManager.getApplication().runWriteAction(new Runnable() {
public void run() {
Disposer.dispose(project);
}
});
return;
}
projectRef.set(project);
}
catch (StateStorageException e) {
exceptionRef.set(new IOException(e.getMessage()));
}
catch (IOException e) {
exceptionRef.set(e);
}
}
}, ProjectBundle.message("project.load.progress"), true, null);
if (!exceptionRef.isNull()) {
throw exceptionRef.get();
}
return projectRef.get();
}
@Nullable
public Project convertAndLoadProject(String filePath, Ref<Boolean> cancelled) throws IOException {
final Ref<ConversionResult> conversionResult = new Ref<ConversionResult>();
final String fp = canonicalize(filePath);
UIUtil.invokeAndWaitIfNeeded(new Runnable() {
@Override
public void run() {
conversionResult.set(ConversionService.getInstance().convert(fp));
}
});
if (conversionResult.get().openingIsCanceled()) {
cancelled.set(true);
public Project loadAndOpenProject(@NotNull final String filePath) throws IOException {
final Project project = convertAndLoadProject(filePath, new Ref<Boolean>());
if (project == null) {
return null;
}
final Project project = loadProjectWithProgress(filePath, new Ref<Boolean>());
if (project == null) return null;
if (!conversionResult.get().conversionNotNeeded()) {
StartupManager.getInstance(project).registerPostStartupActivity(new Runnable() {
if (!openProject(project)) {
ApplicationManager.getApplication().runWriteAction(new Runnable() {
public void run() {
conversionResult.get().postStartupActivity(project);
Disposer.dispose(project);
}
});
}
@@ -544,57 +472,55 @@ public class ProjectManagerImpl extends ProjectManagerEx implements NamedJDOMExt
}
@Nullable
public Project loadProjectWithProgress(final String filePath, final Ref<Boolean> canceled) throws IOException {
final IOException[] io = {null};
final StateStorageException[] stateStorage = {null};
if (filePath != null) {
refreshProjectFiles(filePath);
}
final Project[] project = new Project[1];
canceled.set(false);
Runnable runnable = new Runnable() {
public void run() {
try {
project[0] = doLoadProject(filePath);
}
catch (IOException e) {
io[0] = e;
}
catch (StateStorageException e) {
stateStorage[0] = e;
}
catch (ProcessCanceledException e) {
canceled.set(true);
throw e;
}
}
};
if (ProgressManager.getInstance().getProgressIndicator() == null) {
myProgressManager.runProcessWithProgressSynchronously(runnable, ProjectBundle.message("project.load.progress"), true, null);
}
else {
runnable.run();
public Project convertAndLoadProject(String filePath, Ref<Boolean> cancelled) throws IOException {
final String fp = canonicalize(filePath);
final ConversionResult conversionResult = ConversionService.getInstance().convert(fp);
if (conversionResult.openingIsCanceled()) {
cancelled.set(true);
return null;
}
if (canceled.get() || project[0] == null) {
if (project[0] != null) {
ApplicationManager.getApplication().runWriteAction(new Runnable() {
public void run() {
Disposer.dispose(project[0]);
}
});
}
final Project project = loadProjectWithProgress(filePath);
if (project == null) return null;
if (!conversionResult.conversionNotNeeded()) {
StartupManager.getInstance(project).registerPostStartupActivity(new Runnable() {
public void run() {
conversionResult.postStartupActivity(project);
}
});
}
return project;
}
@Nullable
private Project loadProjectWithProgress(final @NotNull String filePath) throws IOException {
refreshProjectFiles(filePath);
Project project = null;
try {
project = myProgressManager.runProcessWithProgressSynchronously(new ThrowableComputable<Project, Exception>() {
@Nullable
public Project compute() throws Exception {
return doLoadProject(filePath);
}
}, ProjectBundle.message("project.load.progress"), true, null);
}
catch (StateStorageException e) {
throw new IOException(e);
}
catch (IOException e) {
throw e;
}
catch (Exception ignore) {
// ignore
}
if (project == null) {
notifyProjectOpenFailed();
}
if (io[0] != null) throw io[0];
if (stateStorage[0] != null) throw stateStorage[0];
if (project[0] == null || canceled.get()) {
return null;
}
return project [0];
return project;
}
private static void refreshProjectFiles(final String filePath) {