These code snippets show how it is possible to executes task in Eclipse by showing a progress dialog, which is possible to hide
This is the code to start the job:
// create action to be called after the action is completed // this action shows a success dialog if the job executed without // an exception, otherwise it shows an error dialog final CompletionAction completionAction = new CompletionAction(AdminClientActivator.PLUGIN_ID, parent.getShell(), view); completionAction.setOkTitle("Job sucess"); completionAction.setOkMsg("Sucessfully executed job"); completionAction.setFailTitle("Job failed"); completionAction.setFailMsg("There was an exception while executing job"); RSPClientJob job = new ClientJob("Long job...", completionAction); // if short action, otherwise is long Job.LONG job.setPriority(Job.SHORT); // show a dialog immediately job.setUser(true); // start as soon as possible job.schedule();
This snippet is the Job class:
/** * Abstract {@link Job} class for executing tasks with a progress dialog * @author Robert von Burg */ public class ClientJob extends Job { private CompletionAction completedAction; /** * @param name * @param completedAction */ public ClientJob(String name, CompletionAction completedAction) { super(name); this.completedAction = completedAction; } protected IStatus run(IProgressMonitor monitor) { // activate the progress bar with an unknown amount of task work monitor.beginTask("Loading Hibernate configuration", IProgressMonitor.UNKNOWN); // perform the job try { // execute task work... Thread.sleep(10000); // at the end of the successfully ended work, set the completion // task to be ok completionAction.setOk(true); } catch (Exception e1) { logger.error(e1, e1); // if the work failed then set the completion // task to be NOT ok and set the exception so it // can be shown to the user completionAction.setThrowable(e1); completionAction.setOk(false); } // stop the monitor monitor.done(); // execute the completion task complete(); return Status.OK_STATUS; } /** * completes the task by showing the user a dialog about the execution * state of the job */ protected void complete() { setProperty(IProgressConstants.ICON_PROPERTY, ImageFactory. getImg(ImageFactory.IMG_OK)); Boolean isModal = (Boolean) this.getProperty( IProgressConstants.PROPERTY_IN_DIALOG); if (isModal != null && isModal.booleanValue()) { // The progress dialog is still open so // just open the message showResults(completedAction); } else { setProperty(IProgressConstants.KEEP_PROPERTY, Boolean.TRUE); setProperty(IProgressConstants.ACTION_PROPERTY, completedAction); } } /** * Asynchronous execution of an {@link Action} * @param action */ protected static void showResults(final Action action) { Display.getDefault().asyncExec(new Runnable() { public void run() { action.run(); } }); } }
And since we want to notify the caller about task completion we use this interface:
/** * Interface for notifying objects to be refreshed * @author robertb */ public interface Refreshable { public void refresh(); }
And task completion is handled with this Action:
/** * The completion task, which either shows a success dialog, or an error dialog, * depending on the ok state set and then notifies the {@link Refreshable} to * refresh its contents * @author robertb */ public class CompletionAction extends Action { private boolean ok; private String okTitle; private String okMsg; private String failMsg; private String failTitle; private Throwable throwable; private Refreshable refreshable; private Shell shell; private String pluginId; /** * @param pluginId * @param shell * @param refreshable */ public CompletionAction(String pluginId, Shell shell, Refreshable refreshable) { this.pluginId = pluginId; this.shell = shell; this.refreshable = refreshable; } public void setOk(boolean ok) { this.ok = ok; } public void setOkTitle(String okTitle) { this.okTitle = okTitle; } public void setOkMsg(String okMsg) { this.okMsg = okMsg; } public void setFailMsg(String failMsg) { this.failMsg = failMsg; } public void setFailTitle(String failTitle) { this.failTitle = failTitle; } public void setThrowable(Throwable throwable) { this.throwable = throwable; } public void run() { // first refresh refreshable.refresh(); // then show the dialog if (ok) { MessageDialog.openInformation(shell, okTitle, okMsg); } else { Status status = new Status(IStatus.ERROR, pluginId, throwable.getLocalizedMessage(), throwable); ErrorDialog.openError(shell, failTitle, failMsg, status); } } }
I put this together with help from the following site:
Job Concurrency
Thanks
eitch
This is a great article! It helped me a lot! Cheers