-
Notifications
You must be signed in to change notification settings - Fork 2
Common Eclipse Tasks
-
In Eclipse IDE, File Menu > New > Plugin Project.
-
Give the Project a name, e.g.
uk.ac.stfc.isis.ibex.foo
. If it is a UI plugin, it should have a "ui" in the top part of the name e.g.uk.ac.stfc.isis.ibex.ui.foo
-
For location, select the base source code folder, e.g.,
C:\Instrument\Dev\Client\base\uk.ac.stfc.isis.ibex.foo
, rather than the default option (which will probably be the workspace). -
Click next.
-
Make sure 'Generate an activator, a Java...' is checked.
-
If this is to be a UI plugin, check 'This plug-in will make contributions to the UI'. This will cause the Activator to extend
AbstractUIPlugin
rather thanBundleActivator
. Plugins that contribute to the UI in any way such as by adding a preference page or menu item, need to be UI plugins -
Click finish.
-
In the plugin
uk.ac.stfc.isis.ibex.feature.base
, openfeature.xml
and go to the 'Plug-ins' tab. Add your new plugin to the plug-ins list. -
Add a
pom.xml file
to the plugin so that it can be built with maven. This should be the same as the pom file in every other project; the only thing you'll need to change is the plugin's name (theartifactId
). The contents should be as below. Other sections of the pom follow will be inherited fromorg.csstudio.isis.tycho.parent
and so don't need to be explicitly included:<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <artifactId>uk.ac.stfc.isis.ibex.foo</artifactId> <packaging>eclipse-plugin</packaging> <parent> <groupId>CSS_ISIS</groupId> <version>1.0.0-SNAPSHOT</version> <artifactId>uk.ac.stfc.isis.ibex.client.tycho.parent</artifactId> <relativePath>../uk.ac.stfc.isis.ibex.client.tycho.parent</relativePath> </parent> <version>1.0.0-SNAPSHOT</version> </project>
-
In the plugin
uk.ac.stfc.isis.ibex.client.tycho.parent
, add your new plugin to the list of modules (you may have to do this manually in the XML view).
One option to enable easy access to your plug-in object is to use the singleton pattern. Declare a static variable in your plug-in class for the singleton. Store the first (and only) instance of the plug-in class in the singleton when it is created. Then access the singleton when needed through a static getDefault()
method. Your Activator class should look something like this:
public class Activator extends AbstractUIPlugin
{
public static final String PLUGIN_ID = "org.csstudio.isis.ui.logger";
private static Activator plugin;
public Activator() {
}
public static Activator getDefault() {
return plugin;
}
public void start(BundleContext context) throws Exception {
super.start(context);
plugin = this;
}
public void stop(BundleContext context) throws Exception {
plugin = null;
super.stop(context);
}
}
Normally plugins are loaded lazily, i.e., the first time they are actually needed. It can be useful to force a plugin to start when the program launches.
In your plugin:
- Make a class called, e.g.,
org.csstudio.isis.foo.FooStartup
that extends the Eclipse interface,IStartup
. Override the public methodearlyStartup()
, with blank implementation. - Open
META-INF
>MANIFEST.MF
>Extensions
tab. Make sure "Show only extension points from required plug-ins" is unchecked. - Click
Add
and type:org.eclipse.ui.startup
. - In the Extension element details, select the startup,
FooStartup
, class you created earlier.
In Eclipse, Jobs are units of runnable work that can be scheduled to be run with the job manager. Once a job has completed, it can be scheduled to run again (jobs are reusable). You might want to use a job to prevent UI freeze, i.e., if clicking a button performs a long operation or calculation, you still want the UI to respond while performing the operation. You might also use a job if a task needs to run continuously in the background for the lifetime of the program (as is the case for the JMS handler thread that receives messages from the IOC log server).
A job can be prepared as follows:
Job fooJob = new Job("My Foo Job")
{
@Override
protected IStatus run(IProgressMonitor monitor)
{
fooCalculator.performLongTask();
return Status.OK_STATUS;
}
};
The string passed to the constructor will be the name of the thread that you will see if you are debugging the application.
The job can be started with:
fooJob.schedule();
More details can be found in the Vogella tutorial.
Where possible, you should use the Eclipse data binding framework to update UI elements (see Vogella databinding tutorial; however in some cases this is not convenient or possible.
The display of UI elements is not handled in the main execution thread but in a separate UI thread. Consequently, if you attempt to alter the display of any UI element from the main thread, you will get an Invalid Thread Access exception. We can overcome this limitation by calling the Display.asyncExec()
, which passes a runnable command to the UI thread and asks for it to be run at the next available opportunity.
As an example, if you had a UI class, FooDisplay, which had a method, setLabelText()
, you might implement it as follows:
public class FooDisplay extends Canvas
{
private Label fooLabel;
private void setLabelText(final String text)
{
Display.getDefault().asyncExec(new Runnable()
{
@Override
public void run() {
fooLabel.setText(text);
}
});
}
}
Instructions on adding a new perspective can be found here.
Many plugins may have options that you want the user of the client to be able to configure. The simplest way to achieve this is to have the plugin contribute a preference page to the client's preference window.
-
Make sure your plugin contributes to the UI, i.e., that its activator class extends
AbstractUIPlugin
, notBundleActivator
, and that it has a staticgetDefault()
method. -
In your plugin, add a new preference package, called e.g.,
org.csstudio.isis.foo.preferences
. -
Create a new class called e.g.,
FooPreferenceConstants
, which will store tags and default values for each preference in your plugin. In the below example, we specify tags and defaults for a String preference called name and a integer preference called count. The tags are used internally by eclipse to refer to the preference and will not be displayed to the user:public class FooPreferenceConstants { public static final String TAG_NAME = "fooName"; public static final String TAG_COUNT = "fooCount"; public static final String DEFAULT_NAME = "This is my foo name!"; public static final int DEFAULT_COUNT = 5; }
-
Create a new class called e.g.,
FooPreferenceInitializer
, that extendsAbstractPreferenceInitializer
, which will set the default values of each preference:public class FooPreferenceInitializer extends AbstractPreferenceInitializer { public void initializeDefaultPreferences() { IPreferenceStore store = Activator.getDefault().getPreferenceStore(); store.setDefault(FooPreferenceConstants.TAG_NAME, FooPreferenceConstants.DEFAULT_NAME); store.setDefault(FooPreferenceConstants.TAG_COUNT, FooPreferenceConstants.DEFAULT_COUNT); } }
-
Add a new preference page class called, e.g.,
FooPreferencePage
, and have it extend the Eclipse classFieldEditorPreferencePage
and implement the interfaceIWorkbenchPreferencePage
. -
Add a constructor and implementations of the functions
creatFieldEditors()
andinit()
:public class FooPreferencePage extends FieldEditorPreferencePage implements IWorkbenchPreferencePage { public FooPreferencePage() { super(GRID); setPreferenceStore(Activator.getDefault().getPreferenceStore()); setDescription("Settings for Foo."); } @Override public void createFieldEditors() { addField(new StringFieldEditor(FooPreferenceConstants.TAG_NAME, "Foo Name", getFieldEditorParent())); addField(new StringFieldEditor(FooPreferenceConstants.TAG_COUNT, "Foo Count", getFieldEditorParent())); } @Override public void init(IWorkbench workbench) { } }
-
Open the plugins
plugin.xml
and navigate to the Extensions tab.
- Add the extension
org.eclipse.core.runtime.preferences
. - To this, add a new
Initializer
and set its class asFooPreferenceInitializer
. - Add the extension
org.eclipse.ui.preferencePages
. - To this, add a new
Page
and set its class toFooPreferencePage
. You can also set thename
, which will displayed in the UI.
The plugin.xml
should look like the following:
<?xml version="1.0" encoding="UTF-8"?>
<?eclipse version="3.4"?>
<plugin>
<extension point="org.eclipse.core.runtime.preferences">
<initializer
class="org.csstudio.isis.foo.preferences.FooPreferenceInitializer">
</initializer>
</extension>
<extension point="org.eclipse.ui.preferencePages">
<page
class="org.csstudio.isis.foo.preferences.FooPreferencePage"
id="org.csstudio.isis.foo.preferences.FooPreferencePage"
name="Foo Preferences">
</page>
</extension>
</plugin>
When you start the client, the Foo preference page should now appear in the Eclipse Preferences window. Changes made by the user will be persisted to file automatically by the Eclipse framework and will be reloaded next time the user starts the client.
For more details see the Vogella preferences tutorial.
Sometimes it may be necessary to add a new menu item to the menu bar in the Eclipse client so you can open some sort of dialog window or perform some other action. If you want the menu item to open a dialog, make sure you already have a Dialog
class prepared in your plugin.
- Create a class that extends
org.eclipse.core.commands.IHandler
; call it something likeFooHandler
. Add the unimplemented methods. - Make
isEnabled()
andisHandled()
returntrue
. - Make
execute()
instantiate and open your dialog (or perform whatever other action you have in mind):public class FooHandler implements IHandler { @Override public void addHandlerListener(IHandlerListener handlerListener) { } @Override public void dispose() { } @Override public Object execute(ExecutionEvent event) throws ExecutionException { Shell shell = PlatformUI.getWorkbench().getActiveWorkbenchWindow().getShell(); FooDialog dialog = new FooDialog(shell); dialog.open(); return null; } @Override public boolean isEnabled() { return true; } @Override public boolean isHandled() { return true; } @Override public void removeHandlerListener(IHandlerListener handlerListener) { } }
- Open the plugins
plugin.xml
and navigate to the Extensions tab.
- Add the extension
org.eclipse.ui.commands
. - To this, add a new
command
. Set theid
, give it aname
, and set thedefaultHandler
to theFooHandler
class that you made earlier. - Add the extension
org.eclipse.ui.menus
. - To this, add a new
menuContribution
; set thelocationURI
tomenu:org.eclipse.ui.main.menu
. - To this, add a new
menu
. Give it anid
andlabel
(this will be displayed on the menu bar). - To the
menu
, add a newcommand
. Set thecommandId
to be theid of the
command`` you created earlier and give it a label that will be displayed in the menu on the UI;
The plugin.xml
should now resemble:
<?xml version="1.0" encoding="UTF-8"?>
<?eclipse version="3.4"?>
<plugin>
<extension point="org.eclipse.ui.menus">
<menuContribution
allPopups="false"
locationURI="menu:org.eclipse.ui.main.menu">
<menu label="Foo Menu">
<command
commandId="org.csstudio.isis.foo.command"
label="Foo Menu Item"
style="push">
</command>
</menu>
</menuContribution>
</extension>
<extension point="org.eclipse.ui.commands">
<command
defaultHandler="org.csstudio.isis.foo.FooHandler"
id="org.csstudio.isis.foo.command"
name="Do Foo">
</command>
</extension>
</plugin>
The menu should now be visible in the client UI. For more details see the Vogella menus tutorial.
To do