by Lars Vogel

Follow me on twitter

Lars Vogel on Google+

Eclipse RCP Tutorial

Lars Vogel

Version 6.8

15.01.2012

Revision History
Revision 0.1 - 0.7 14.08.2007 - 03.09.2007 Lars
Vogel
Eclipse RCP with Eclipse 3.3
Revision 0.8 - 6.8 03.11.2008 - 15.01.2012 Lars
Vogel
Several bug fixes and enhancements

Eclipse RCP

This tutorial describes how to develop Eclipse RCP applications. It is based on Eclipse 3.7 (Eclipse Indigo).


Table of Contents

1. Eclipse based Applications
1.1. What are Eclipse RCP applications?
1.2. Advantages of Eclipse based applications
2. The Architecture of Eclipse
2.1. Eclipse IDE vrs. Eclipse RCP
2.2. Software components, Plug-ins, Bundles, OSGi
2.3. Configuration files
3. What are Extension Points?
4. Main components of an Eclipse RCP application
5. Prerequisite
6. Installation
6.1. Java
6.2. Download the Eclipse plug-in package
6.3. Update an Eclipse Java IDE
7. Approach
8. Tutorial: Create your first RCP application
8.1. Create an RCP application
8.2. Start an RCP application
9. Tutorial: Create and Launch Product
9.1. Create your product configuration
9.2. Launch your product
10. Run configuration
11. Common launch configuration problems
12. Application and Advisor Classes
13. Products and Branding
13.1. Product and application
13.2. Dependencies
13.3. Configuration
14. Deployment
15. Common product export problems
16. WorkbenchParts and Perspectives
16.1. WorkbenchParts - Views and Editors
16.2. Perspective
17. Convention
18. Tutorial: Adding Views to your application
18.1. Create a view
18.2. Add the view to your perspective
18.3. Result
18.4. Add view to perspective via code
19. SWT
20. JFace Viewers
21. Tutorial: ControlDecorations
22. Tutorial: FieldAssists
23. Commands
24. Tutorial: Adding an Perspectives
25. Tutorial: System Tray
26. Target Platform
26.1. Developing against the Eclipse IDE
26.2. Defining your Target Platform
26.3. Creating a Target Platform definition
27. Tips and Tricks
27.1. Load an image from your plugin
27.2. Save users layout
27.3. Accessing the status line
27.4. Finding unused dependencies
27.5. Multi-User settings
28. Questions and Discussion
29. Links and Literature
29.1. Source Code
29.2. Eclipse Resources
29.3. vogella Resources

1. Eclipse based Applications

1.1. What are Eclipse RCP applications?

Eclipse was originally started as a modular IDE application. In 2004 the Eclipse 3.0 version was released which supported the re-use of the Eclipse platform to build stand-alone applications based on the same technology as the Eclipse IDE.

At this point the term Eclipse RCP was coined. RCP stands for Rich Client Platform and indicates that the Eclipse platform is used to created feature-rich standalone applications.

Eclipse applications are built upon a plug-in architecture. Plug-ins are software components. Plug-ins are the smallest deployable and installable components of Eclipse.

A plug-in is a collection of files and a configuration file (MANIFEST.MF) which describes the plug-in and its dependencies.

This plug-in architecture allows Eclipse based applications to get extended by third parties.

The Eclipse 4 platform extends the concept of building Eclipse based applications with new technologies, for example with dependency injection and declarative styling via CSS files.

1.2. Advantages of Eclipse based applications

The Eclipse platform is the basis for the most successful Java IDE and therefore very stable and broadly used. It uses native UI components to provide as much as possible a native look and feel and with its strong modularity approach allow to design component based systems.

Companies like IBM and Google use the Eclipse framework heavily for their products and therefore ensure that Eclipse is flexible, fast and continues to evolve.

The Eclipse platform also fosters a large community of individuals which provide support, information and extensions to the Eclipse framework. Tapping into this Eco-system allows you to find required resources and information.

2. The Architecture of Eclipse

2.1. Eclipse IDE vrs. Eclipse RCP

An Eclipse application consists of individual software components.

The Eclipse IDE is a collection of specific software components. The components of the Eclipse IDE are primarily the following.

Primary Eclipse IDE components

An Eclipse based application (RCP) uses only parts of these components. An Eclipse application typically uses:

Typical components of an Eclipse RCP application

For a headless Eclipse based applications (without UI), only the runtime is necessary.

The OSGi runtime provides the framework to run the modular application. SWT is the standard UI component library used by Eclipse and JFace provides some convenient API on top of SWT. The workbench provides the framework for your application. The workbench is responsible for displaying all other UI components.

2.2.  Software components, Plug-ins, Bundles, OSGi

The basis for the Eclipse architecture is the OSGi specification. The OSGI specification defines a modularity layer.

Equinox is the reference implementation of OSGi and is used by the Eclipse platform.

A software component in Eclipse is called "Plug-in". A software component in OSGi is called "bundle". Both terms can be used interchangeably.

A plug-in defines:

  • its API - public classes which can be used by other plug-ins

  • its dependencies - package or plug-ins which are required by the plug-in

OSGi defines also services. Services are dynamic components.

2.3. Configuration files

An Eclipse plug-in has two main configuration files.

  • MANIFEST.MF - contains the OSGi configuration information.

  • plugin.xml - Information about the extensions and extension points

3. What are Extension Points?

On top of OSGi the Eclipse framework provides also extension-points. Extension-points define interfaces for other plug-ins to contribute functionality (code and non-code ).

They are defined in the "plugin.xml" file, which must be in the root directory of your plug-in project. This file is an XML file which provides a user interface for editing this file.

Existing extensions (contributions) are collected during the start of an Eclipse application. The information in the extension points is converted into so-called descriptors and stored in registries.

The Eclipse IDE provides an editors for the "plugin.xml" file (via the so called Plug-in Development Environment).

4.  Main components of an Eclipse RCP application

The minimal required plug-ins to create and run an minimal Eclipse RCP application (with UI) are the two plugins "org.eclipse.core.runtime" and "org.eclipse.ui". Based on these components an Eclipse RCP application must define the following elements:

  • Main program - A RCP main application class implements the interface "IApplication". This class can be viewed as the equivalent to the main method for standard Java application. Eclipse expects that the application class is defined via the extension point "org.eclipse.core.runtime.application".

  • A Perspective - defines the layout of your application. Must be declared via the extension point "org.eclipse.ui.perspective".

  • Workbench Advisor- invisible technical component which controls the appearance of the application (menus, toolbars, perspectives, etc)

The Eclipse application is the equivalent of the Java main() method. Applications are defined via the extension point org.eclipse.core.runtime.applications and must extend IApplication.

5. Prerequisite

The following assumes that you already have some knowledge in using the Eclipse IDE for standard Java development. See Eclipse IDE Tutorial if you don't have this knowledge.

Is also assume that you are familiar with using the Eclipse update manager. See Eclipse Update Manager to learn how to use it.

6. Installation

6.1. Java

The following assumes that you have already Java installed. If not please Google for "How to installed Java for MyOS", while replacing "MyOS" with the operating system your are using.

6.2. Download the Eclipse plug-in package

Browse to Eclipse download site and download the package "Eclipse for RCP and RAP Developers". Extract the download to your harddisk. Avoid having special characters or spaces in the path to Eclipse.

6.3. Update an Eclipse Java IDE

In case you have downloaded the Eclipse Java IDE (or any other non RCP flavor) distribution you can use the Eclipse Update Manager to install the plug-ins required for RCP development.

Install General Purpose Tools Eclipse Plug-in Development Environment Eclipse RCP Plug-in Developer Resources from the Eclipse update site for your release. You may have to remove the "Group items by category" flag to see all available features.

Update dialog showing how the group by flag can be removed

Selecting the Ecipse RCP development package in the update manager.

7. Approach

If you teach programming you basically have two extreme choices. The first approach is that you explain everything first and then do it. The second choice is that you first do everything and then explain what you have done.

The following description tends towards the second approach.

We will develop a small RCP application, create a product and launch it, before explaining the project structure, the involved classes and what a product or a launch configuration is.

In my experience its easier to understand an explanation, if you have already created an example.

The risk associated with that approach is that if you run into a problem you don't know how to solve it.

Therefore if you have problem starting your product, I suggest to read the chapter about launch configurations and if that doesn't help, check the "Products and Branding" chapter.

8. Tutorial: Create your first RCP application

8.1. Create an RCP application

The following explains how to create a simple RCP application. In Eclipse select File-> New Project. From the list select "Plug-In Project".

Selection the Eclipse Plug-in Wizard

Give your plugin the name "de.vogella.rcp.intro.first" .

First page of the Eclipse Plug-in Wizard specifying the project name.

Press "Next" and make the following settings. As we are going to develop an RCP application, select "Yes" at the question "Would you like to create a rich client application".

Second page of the Eclipse Plug-in Wizard specifying the plug-in ID, version, Name, Activator and the RCP type.

Press next and select the template "Hello RCP" .

Third page of the Eclipse Plug-in Wizard selecting the template "Hello RCP".

Press next and select "Add branding" and press Finish.

Forth page of the Eclipse Plug-in Wizard specifying the branding.

As a result a project with the following project structure will be created. Have a look at the different files especially the Java files to get a first feeling about the project structure.

Screenshot of the created project after the wizard finished

8.2. Start an RCP application

While it is possible in Eclipse 3.7 to start an application directly, it is consistent to create a product to start the application. Therefore we will not run the application directly but create first an product.

This is also in line with Eclipse 4.x. In Eclipse 4.x you cannot start an Application directly, you always need a product.

9. Tutorial: Create and Launch Product

9.1. Create your product configuration

Right-click on your "de.vogella.rcp.intro.first" project and select NewProduct Configuration .

Creating the product configuration file

Name your product configuration "de.vogella.rcp.intro.first.product". Select "Create a configuration file with basis settings". Press finish.

Open the file de.vogella.rcp.intro.first.product" and select the "Overview" tab. Enter the name "DeployTest". Leave the ID empty. The name is the default which will be displayed in the title of the window, the ID is not required and entering it leads sometimes to problems. You can change this default name in class ApplicationWorkbenchWindowAdvisor in the method preWindowOpen() via the configurer.setTitle("New title");)

Select the overview tab of the product file

Press "New" in the "Product Definition" part and select the application of your plugin "de.vogella.rcp.intro.first.application".

Selecting the application which should be started by the product

Selecting the application which should be started by the product, part II

As a result the "Product Definition" part of the overview tab should now be filled with your selection.

The product identifier is stored as the extension "org.eclipse.core.runtime.product" in the file "plugin.xml".

Switch to the "Dependencies" Tab and click "Add". Add your application plugins. Press the button "Add Required Plug-ins" to add all dependent plugins to your product. Save.

Optional create a "splash.bmp" via your favorite graphics tool and save it in the project with contains the product. Also add a message and a progress bar to your splash screen.

Change the launch name to "myapplication".

9.2. Launch your product

On the overview tab press synchronize and then press "Launch an Eclipse application". Make sure your product starts.

The result should look like the following:

Running example application

Congratulations, you have created and started your first RCP application.

10. Run configuration

A run configuration in Eclipse defines the environment under which an Eclipse application will be started. For example it defines compiler flags, plug-in (classpath) dependencies etc. Sometimes a run configuration is called "launch configuration".

If you start your Eclipse application the first time, a run configuration will be automatically created.

If you select this run configuration and start it, it will be used as defined. Changes in the product configuration file will not be considered.

If you start the application from the product definition file, an existing launch configuration will be updated based on the new product configuration.

To see and edit your run configuration select your product configuration file, right-click on it and select Run AsRun Configurations

On the "Main tab" in the field "location" you specify where the Eclipse IDE will create the files necessary to start your RCP application.

Shows the launch configuration, highlighting the location setting

11. Common launch configuration problems

Launch configurations are frequent sources of problems.

The most common problem is that required plug-ins are missing.

Eclipse can check this automatically for you before every start. On the "Plug-ins" Tab select "Validate plug-ins prior to launching". This will check if you have all required plug-ins in your launch configuration.

If this check reports that some plug-ins are missing, try clicking the "Add Required-Plug-Ins" button. Also make sure to define all dependencies in your product.

Pressing the "Add required Plug-ins" button in the Eclipse launch configuration

The launch configuration allows on the "Arguments" tab to add additional parameters. Per default -consoleLog is included. This will write error messsages of the running Eclipse RCP instance to the Eclipse IDE "Console" View.

-consoleLog in the launch configuration

The following table lists potential problems and solutions.

Table 1. Common launch problems

Problem How to investigate or solve
During start you get error messages like "One or more bundles are not resolved because the following root constraints are not resolved" or "java.lang.RuntimeException: No application id has been found." Check that all required plug-ins are included in your launch configuration. Make sure that your product defines dependencies to all required plug-ins or features.
Strange behavior but no error message. Check if your launch configuration includes the parameter -consoleLog. This option allows to see errors in the RCP application in the console view and is very helpful to identify problems.
Runtime configuration is frequently missing required plug-ins Make sure that your product includes all required dependencies.
A change in the product dependencies, e.g. a new plug-in is added, is not included in the launch configuration. A product updates an existing launch configuration if you start the product directly from the product definition file. If you select the launch configuration directly it will not be updated.


Other useful parameters are -console (which will give you a OSGI console where you can check the status of your application) and -noExit (which will keep the OSGI console open even if the application ends / crashes).

12. Application and Advisor Classes

During the startup of an Eclipse RCP application the Eclipse runtime will evaluate which class is defined via the org.eclipse.core.runtime.application extension point.

This is the equivalent of the main class of standard Java programs. This class is responsible for creating the SWT Display and for starting the event loop for the application.

This class is typically called Application and must implement the interface IApplication.

			
Display display = PlatformUI.createDisplay();
PlatformUI.createAndRunWorkbench(display, new ApplicationWorkbenchAdvisor());
		

PlatformUI.createAndRunWorkbench() creates and runs a Workbench. The Workbench represents the graphical user interface of Eclipse. The visual part of the Workbench is represented via the WorkbenchWindow class. A Workbench can have several WorkbenchWindows opened. The inner part of the WorkbenchWindow is represented via the class WorkbenchPage.

The Workbench is configured via a class of type WorkbenchAdvisor. This class defines the initial Perspective and defines the WorkbenchWindowAdvisor class.

WorkbenchWindowAdvisor calls the class ActionBarAdvisor which configures Actions for the Workbench and defines initial attribute for the WorkbenchWindow as initial size, title and visibility of the statusline.

			
public ActionBarAdvisor createActionBarAdvisor(IActionBarConfigurer configurer) {
	return new ApplicationActionBarAdvisor(configurer);
}

public void preWindowOpen() {
	IWorkbenchWindowConfigurer configurer = getWindowConfigurer();
	configurer.setInitialSize(new Point(400, 300));
	configurer.setShowCoolBar(false);
	configurer.setShowStatusLine(false);
	configurer.setTitle("Todo"); //$NON-NLS-1$
}
		

For example you could set the initial position of the application via postWindowCreate() method.

			

// For further info see https://bugs.eclipse.org/bugs/show_bug.cgi?id=84938
@Override
public void postWindowCreate() {
	Shell shell = getWindowConfigurer().getWindow().getShell();
	shell.setLocation(100, 400);
	super.postWindowCreate();
}
		

The ActionBarAdvisor class is as of Eclipse 3.7 not important any more as the Action framework is replaced by the superior command framework.

Each adviser allow to configure certain behavior of the application, e.g. the WorkbenchAdvisor allows to perform certain actions at startup or shutdown by overriding the preStartUp() and preShutdown() methods. .

13. Products and Branding

13.1. Product and application

A product configuration (short: product) defines all resources that goes with your Eclipse application , e.g. icons, splash screen, external jars, other plugins, etc. The product is a development artifact which describes the content of your application and is not required at runtime.

A product always points to one Application class. This Application class must implement the IApplication interface.

You define your product configuration via a ".product" file. A product configuration file can be created via a right-click on your project and select NewProduct Configuration.

This configuration file contains all the information about required plug-ins, configuration files, resources etc. The configuration file is used for exporting / creating your product.

It is recommended to leave the product ID blank, because the product export may have issues if the product ID is the same as a plug-in ID.

On the overview tab of your product you can start the product and select synchronize. Synchronize will align your product artifacts with the launch configuration.

Product definition file show the overview tab

13.2.  Dependencies

A product configuration file can either be based on plug-ins or features. Features are groupings of other features and plug-ins. This setting is done on the overview tab.

Configuration of the product can be based on features or plug-ins

On the dependency tab you can maintain the plug-ins your products consists of. A product will not do any automatic dependency resolution for you. If you add a plug-in to your product and want to add the dependencies, press the dependency button.

13.3. Configuration

The tab "Splash" allows you to specify the plug-in which contains the splash screen. You need to put the file "splash.bmp" into the project directory. The name and the format is hard-coded in Eclipse and cannot be changed.

Show the tab splash from the product configuration file

You can also configure the launcher name and icon for your exported product. The launcher is the executable program that is created during the deployment of the product. Per default a launcher specific to your platform is created. For example "eclipse.exe" on the Windows platform. The launcher will also get an "eclipse" icon. To change the name and the icon select the launcher tab of your product configuration.

Here you can specify the name of the application and the icon which should be used. Make sure the size of the icons is correctly maintained otherwise Eclipse will not use these icons.

Highlighting the section where the icons are maintained.

In the launcher section you can also specify parameters to your Eclipse program or JVM arguments.

14. Deployment

Your product configuration file can be used to export your application to run outside of Eclipse.

Exporting your product will create a file which contains all artifacts required to run your application. It will also contain a native launcher specific to the platforms, e.g. Windows or Linux, you have exported for.

The resulting directory can be shared with others which can start the application via the native launcher.

The included artefacts are defined by the "build.properties" file.

Eclipse will per default add the compiled Java classes. You have to manage manually the other files, e.g. icons or splash screen images.

To change the "build.properties" file you can use the "plugin.xml" editor. Open the "plugin.xml" file and select the build tab.

Make sure the "META-INF "directory and the file "plugin.xml" and all other static files, e.g. icons, splash.bmp and in the case of Eclipse 4.x Application.e4xmi and potentially CSS files, are flagged to be included in the exported product.

To export the product switch to your product configuration file and select the tab Overview. Click on the "Eclipse Product export wizard" to export your product. On the second page of the wizard you can specify the destination directory and the root directory for the exported application.

This root directory will be a sub-folder in the destination directory and will contains the application which you can start.

The following screenshots show the export wizard in action.

Exporting the Eclipse Product

Selecting the output directory in the product export dialog

After the export you will find the required application files in the destination folder in the root folder. A double-click on the native launcher should start your application.

If you transfer the content of this directory to another machine (with the same architecture, e.g. Linux 64 bit) your application should run on this machine. The machine only needs to have Java installed. launcher should start your application.

The export dialog allows to created an archive file. This file could be shared with the users of the application.

You can also deploy your own RCP application to make sure that a certain JRE is used. An Eclipse RCP application first searches in the installation directory for a folder "jre" and for a contained Java-VM. If it finds one, then this JRE is used to start the Eclipse application.

15. Common product export problems

If export encounters a problem please have a look into the following for a solution:

Table 2. Problems with the product export

Problem Possible cause
Export fails Try using an empty target directory, sometimes the export cannot delete the existing files and therefore fails.
No .exe file after the export Check the flag "The product includes native launcher artifacts in your .product file on the "Overview" tab.
Product could not be found Validates that all dependencies are included in the product. Delete an existing launch configuration and restart the product from the IDE to see if everything is configured correctly.
Splash Screen or other icons are missing Check build.properties to see if all binary artefacts are included in the export.
Issues during startup Check the log file in the workspace folder of your export product to see the error messages during startup. Alternative add -consoleLog to the .ini in folder of the export product.


16. WorkbenchParts and Perspectives

16.1. WorkbenchParts - Views and Editors

As described earlier the WorkbenchWindow and the WorkbenchPage represent the visual and inner part of the graphical user interface.

The WorkbenchPage contains Parts, which can be Views or Editors.

Views are used to display information in an RCP application; they can also be used to change data. Views extend the abstract class ViewPart. Editors extend the abstract EditorPart. Both extend WorkbenchPart.

An editor typically requires that the user explicitly select "save" to apply the changes to the data while a view typically changes the data immediately. All editors are opened in the same area. Via the perspective you can configure if the editor area is visible or not.

Views and Editors are defined via extension points in the file "plugin.xml" via the tab "Extensions".

Views are defined via the extension point "org.eclipse.ui.views" and Editors via the extension point "org.eclipse.ui.editors".

Views must implement the createPartControl() and setFocus() methods.

createPartControl() is used to create the UI components of the View.

createPartControl() will get as parameter a Composite which can be used to construct the user interface. This composite has per default a FillLayout layout manager assigned to it. This layout manager assigns the same space to all components equally.

setFocus() must set the focus to a specific UI component.

16.2. Perspective

A Perspective describes a certain configuration of Views and Editors.

A Perspective is defined via "org.eclipse.ui.perspectives". The WorkbenchParts which are part of a Perspective are either defined via a Java class defined in the extension point "org.eclipse.ui.perspectives" or via the "org.eclipse.ui.perspectiveExtensions".

				
public class Perspective implements IPerspectiveFactory {
	public void createInitialLayout(IPageLayout layout) {
		layout.addView("de.vogella.rcp.intro.first.MyView", IPageLayout.TOP,
				IPageLayout.RATIO_MAX, IPageLayout.ID_EDITOR_AREA);
	}
}
			

layout.addView() adds a view to the perspective. You can also add placeholders for views via the layout.addPlaceholder() method call. This methods accepts wildcards and a View with a matching ID would open in this area.

You can also group view via a IFolderLayout which can be created via layout.createFolder() call and by adding Views to this folder via the addView(id) method on IFolderLayout.

17. Convention

In this tutorial we will always create RCP applications. Therefore if the instruction says "Create an RCP project" you should create a new plug-in project with the flag "Would you like to create a rich client application" enabled.

18. Tutorial: Adding Views to your application

18.1. Create a view

The following will explain how to add views to your application. We will continue to use the RCP project "de.vogella.rcp.intro.first".

Add the extension "org.eclipse.ui.views" to your plugin. Select ""plugin.xml" and the tab "Extentions". Right mouse-click on your new view extension and select New -> View. Maintain the id "de.vogella.rcp.intro.view.MyView" and the class "de.vogella.rcp.intro.view.MyView".

Data for the "org.eclipse.ui.views" extension point

Data for the "org.eclipse.ui.views" extension point

Create the class "MyView" by clicking on the "class" hyperlink and maintain the following code. Afterwards your view is ready to be used.

				
package de.vogella.rcp.intro.first;

import org.eclipse.swt.SWT;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Text;
import org.eclipse.ui.part.ViewPart;

public class MyView extends ViewPart {

	@Override
	public void createPartControl(Composite parent) {
		Text text = new Text(parent, SWT.BORDER);
		text.setText("Imagine a fantastic user interface here");
	}

	@Override
	public void setFocus() {
	}
}

			

18.2. Add the view to your perspective

You have to add the view to your perspective. Add the extension "org.eclipse.ui.perspectiveExtensions" to your plugin.

Adding a view to your perspective via the "org.eclipse.ui.perspectiveExtensions" extension

Right click "*(perspectiveExtension)" -> New -> view". Maintain your view id "de.vogella.rcp.intro.first.MyView". Make the view relative to "org.eclipse.ui.editorss" which is the currently invisible editor area and make the view use all the space by selecting the maximum ratio of "0.95f".

Maintaining the layout data for the view in the "org.eclipse.ui.perspectiveExtensions" extension point

18.3. Result

Run your application to see the result.

Running application with a new view

18.4. Add view to perspective via code

I personally prefer extension points over code. But instead of using the extension point "org.eclipse.ui.perspectiveExtensions" you could also add the view via code to the perspective. For this modify "Perspective.java" to the following.

				
package de.vogella.rcp.intro.view;

import org.eclipse.ui.IPageLayout;
import org.eclipse.ui.IPerspectiveFactory;

public class Perspective implements IPerspectiveFactory {

	public void createInitialLayout(IPageLayout layout) {
		layout.addView("de.vogella.rcp.intro.first.MyView", IPageLayout.TOP,
				IPageLayout.RATIO_MAX, IPageLayout.ID_EDITOR_AREA);
	}
}

			

19. SWT

SWT is the UI library used by Eclipse. SWT provides the same rich UI components on several platforms using the native widgets of the platform whenever possible. If a widget is not available on a certain platform, SWT emulates the unavailable widget. The native widgets of the OS are accessed by the SWT framework via JNI.

For an introduction into SWT please use the SWT Tutorial.

20. JFace Viewers

JFace provides also viewers which allow to work with Java object directly to create an user interface. Viewers are available for trees, tables, lists and comboboxes. Please see JFaces Tables Tutorial and JFace Tree Viewer Tutorial for a detailed tutorial.

21. Tutorial: ControlDecorations

Field Assist can be used to provide information about the possible inputs and status of a simple field, e.g. text field or combo box. The "org.eclipse.jface.fieldassist" package provides assistance in two ways: ControlDecorations and Content Proposals.

Control decorations allow you to place image decorations on SWT controls to show additional information about the control. These decorations can also have descriptions which are displayed once the user places the mouse over them. During the layout of your screen you need to make sure that enough space is available to display these decorations.

The following shows how to create ControlDecorations and how to set a description and an icon to it.

				
// Create the decoration for the text UI component
final ControlDecoration deco = new ControlDecoration(text, SWT.TOP | SWT.RIGHT);

// Re-use an existing image
Image image = FieldDecorationRegistry.getDefault().getFieldDecoration(FieldDecorationRegistry.DEC_INFORMATION).getImage();
// Set description and image
deco.setDescriptionText("Use CNTL + SPACE to see possible values");
deco.setImage(image);
// Hide deco if not in focus
deco.setShowOnlyOnFocus(false);
			

You can also hide and show the decoration.

				
deco.hide();
deco.show();
			

Content proposal provides the user input help for the possible choices of a field.

22. Tutorial: FieldAssists

Re-use the project "de.vogella.rcp.intro.first". In our example the content proposal should get activated via certain keys ("." and "#") as well as the key combination "CTRL+Space".

Change the View.java to the following.

			
package de.vogella.rcp.intro.fieldassist;

import org.eclipse.jface.bindings.keys.KeyStroke;
import org.eclipse.jface.bindings.keys.ParseException;
import org.eclipse.jface.fieldassist.ContentProposalAdapter;
import org.eclipse.jface.fieldassist.ControlDecoration;
import org.eclipse.jface.fieldassist.FieldDecorationRegistry;
import org.eclipse.jface.fieldassist.SimpleContentProposalProvider;
import org.eclipse.jface.fieldassist.TextContentAdapter;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.KeyEvent;
import org.eclipse.swt.events.KeyListener;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Label;
import org.eclipse.swt.widgets.Text;
import org.eclipse.ui.part.ViewPart;

public class View extends ViewPart {
	public static final String ID = "de.vogella.rcp.intro.fieldassist.view";

	public void createPartControl(Composite parent) {
		GridLayout layout = new GridLayout(2, false);
		layout.marginWidth = 10;
		parent.setLayout(layout);
		Label label = new Label(parent, SWT.NONE);
		label.setText("Please select a value:   ");
		Text text = new Text(parent, SWT.BORDER);

		GridData data = new GridData(GridData.FILL_HORIZONTAL);
		text.setLayoutData(data);

		// Create the decoration for the text UI component
		final ControlDecoration deco = new ControlDecoration(text, SWT.TOP
				| SWT.RIGHT);

		// Re-use an existing image
		Image image = FieldDecorationRegistry.getDefault()
				.getFieldDecoration(FieldDecorationRegistry.DEC_INFORMATION)
				.getImage();
		// Set description and image
		deco.setDescriptionText("Use CNTL + SPACE to see possible values");
		deco.setImage(image);
		// Hide deco if not in focus
		deco.setShowOnlyOnFocus(false);

		// Also if the text UI componet is not empty hide the decoration
		text.addKeyListener(new KeyListener() {

			@Override
			public void keyReleased(KeyEvent e) {
				Text text = (Text) e.getSource();
				if (text.getText().length() > 0) {
					deco.hide();
				} else {
					deco.show();
				}
			}

			@Override
			public void keyPressed(KeyEvent e) {
			}
		});

		// Help the user with the possible inputs
		// "." and "#" will also activate the content proposals
		char[] autoActivationCharacters = new char[] { '.', '#' };
		KeyStroke keyStroke;
		try {
			//
			keyStroke = KeyStroke.getInstance("Ctrl+Space");
			// assume that myTextControl has already been created in some way
			ContentProposalAdapter adapter = new ContentProposalAdapter(text,
					new TextContentAdapter(),
					new SimpleContentProposalProvider(new String[] {
							"ProposalOne", "ProposalTwo", "ProposalThree" }),
					keyStroke, autoActivationCharacters);
		} catch (ParseException e) {
			e.printStackTrace();
		}
	}

	public void setFocus() {
	}

}
		

Run the application and check that the control decorations and the content proposal works.

Running application with ControlDecoration and FieldAssists

23. Commands

A command is a declarative description of a component and is independent from the implementation details. A command can be categorized and a hot key (key binding) can be assigned to it. Commands can be used in menus, toolbars and / or context menus.

See Eclipse Commands Tutorial for an introduction into the commands framework.

24. Tutorial: Adding an Perspectives

Create a new RCP project called "de.vogella.rcp.intro.perspective". Use the "RCP application with a view" as a template. In "plugin.xml" add a new extension point "org.eclipse.ui.perspectives". Give the perspective with the id "de.vogella.rcp.intro.perspective.perspective" and the name "vogella.de Perspective". Change the class name to "de.vogella.rcp.intro.perspective.Perspective".

Maintaining the "org.eclipse.ui.perspectives" perspective extension point

Click on the "class*" link to create the class. The method createInitialLayout() in your new class is responsible for creating the new perspective. We re-use the existing view in the coding. After this step the perspective is defined but not yet reachable via the application.

			
package de.vogella.rcp.intro.perspective;

import org.eclipse.ui.IPageLayout;
import org.eclipse.ui.IPerspectiveFactory;

public class Perspective implements IPerspectiveFactory {

	public void createInitialLayout(IPageLayout layout) {
		String editorArea = layout.getEditorArea();
		layout.setEditorAreaVisible(false);
		layout.setFixed(true);
		layout.addStandaloneView(View.ID,  false, IPageLayout.LEFT, 1.0f, editorArea);
	}

}

		

After defining your perspective you also need to enable your application so that the user can select this perspective.

One alternative is to allow the user to select the perspective via the toolbar / coolbar. You can activate the switch between perspectives the ApplicationWorkbenchWindowAdvisor in method preWindowOpen() with configurer.setShowPerspectiveBar(true);

			
package de.vogella.rcp.intro.perspective;

import org.eclipse.swt.graphics.Point;
import org.eclipse.ui.application.ActionBarAdvisor;
import org.eclipse.ui.application.IActionBarConfigurer;
import org.eclipse.ui.application.IWorkbenchWindowConfigurer;
import org.eclipse.ui.application.WorkbenchWindowAdvisor;

public class ApplicationWorkbenchWindowAdvisor extends WorkbenchWindowAdvisor {

	public ApplicationWorkbenchWindowAdvisor(
			IWorkbenchWindowConfigurer configurer) {
		super(configurer);
	}

	public ActionBarAdvisor createActionBarAdvisor(
			IActionBarConfigurer configurer) {
		return new ApplicationActionBarAdvisor(configurer);
	}

	public void preWindowOpen() {
		IWorkbenchWindowConfigurer configurer = getWindowConfigurer();
		configurer.setInitialSize(new Point(400, 300));
		configurer.setShowStatusLine(false);
		configurer.setTitle("RCP Application");
		configurer.setShowPerspectiveBar(true);
	}
}

		

You should now be able to select your perspective interactively.

Selecting the perspective in the running application

In addition you could re-use the Eclipse command "org.eclipse.ui.perspectives.showPerspective" which allows to switch between perspectives. See Eclipse Commands.

25. Tutorial: System Tray

The following add an icon for the RCP application to the system tray and adds a menu to this icon. We add the functionality that if the window is minimized then the program is not visible in the taskpane (only via the tray icon).

Taskpane showing the application icon

Create a new project "de.vogella.rcp.intro.traytest". Use the "Hello RCP" as a template. Open the class "ApplicationWorkbenchWindowAdvisor" and maintain the following code.

			
package de.vogella.rcp.intro.traytest;

import org.eclipse.swt.SWT;
import org.eclipse.swt.events.MenuDetectEvent;
import org.eclipse.swt.events.MenuDetectListener;
import org.eclipse.swt.events.SelectionAdapter;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.events.ShellAdapter;
import org.eclipse.swt.events.ShellEvent;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.widgets.Menu;
import org.eclipse.swt.widgets.MenuItem;
import org.eclipse.swt.widgets.Shell;
import org.eclipse.swt.widgets.Tray;
import org.eclipse.swt.widgets.TrayItem;
import org.eclipse.ui.IWorkbenchWindow;
import org.eclipse.ui.application.ActionBarAdvisor;
import org.eclipse.ui.application.IActionBarConfigurer;
import org.eclipse.ui.application.IWorkbenchWindowConfigurer;
import org.eclipse.ui.application.WorkbenchWindowAdvisor;

public class ApplicationWorkbenchWindowAdvisor extends WorkbenchWindowAdvisor {

	private IWorkbenchWindow window;
	private TrayItem trayItem;
	private Image trayImage;

	public ApplicationWorkbenchWindowAdvisor(
			IWorkbenchWindowConfigurer configurer) {
		super(configurer);
	}

	public ActionBarAdvisor createActionBarAdvisor(
			IActionBarConfigurer configurer) {
		return new ApplicationActionBarAdvisor(configurer);
	}

	public void preWindowOpen() {
		IWorkbenchWindowConfigurer configurer = getWindowConfigurer();
		configurer.setInitialSize(new Point(400, 300));
		configurer.setShowCoolBar(false);
		configurer.setShowStatusLine(false);
		configurer.setTitle("Hello RCP"); //$NON-NLS-1$
	}

	// As of here is the new stuff
	@Override
	public void postWindowOpen() {
		super.postWindowOpen();
		window = getWindowConfigurer().getWindow();
		trayItem = initTaskItem(window);
		// Some OS might not support tray items
		if (trayItem != null) {
			minimizeBehavior();
			// Create exit and about action on the icon
			hookPopupMenu();
		}
	}

	// Add a listener to the shell

	private void minimizeBehavior() {
		window.getShell().addShellListener(new ShellAdapter() {
			// If the window is minimized hide the window
			public void shellIconified(ShellEvent e) {
				window.getShell().setVisible(false);
			}
		});
		// If user double-clicks on the tray icons the application will be
		// visible again
		trayItem.addSelectionListener(new SelectionAdapter() {
			@Override
			public void widgetSelected(SelectionEvent e) {
				Shell shell = window.getShell();
				if (!shell.isVisible()) {
					window.getShell().setMinimized(false);
					shell.setVisible(true);
				}
			}
		});
	}

	// We hook up on menu entry which allows to close the application
	private void hookPopupMenu() {
		trayItem.addMenuDetectListener(new MenuDetectListener() {

			@Override
			public void menuDetected(MenuDetectEvent e) {
				Menu menu = new Menu(window.getShell(), SWT.POP_UP);
				// Creates a new menu item that terminates the program
				MenuItem exit = new MenuItem(menu, SWT.NONE);
				exit.setText("Goodbye!");
				exit.addSelectionListener(new SelectionAdapter() {
					@Override
					public void widgetSelected(SelectionEvent e) {
						window.getWorkbench().close();
					}
				});
				// We need to make the menu visible
				menu.setVisible(true);
			}
		});
	}

	// This methods create the tray item and return a reference
	private TrayItem initTaskItem(IWorkbenchWindow window) {
		final Tray tray = window.getShell().getDisplay().getSystemTray();
		TrayItem trayItem = new TrayItem(tray, SWT.NONE);
		trayImage = Activator.getImageDescriptor("/icons/alt_about.gif")
				.createImage();
		trayItem.setImage(trayImage);
		trayItem.setToolTipText("TrayItem");
		return trayItem;

	}

	// We need to clean-up after ourself
	@Override
	public void dispose() {
		if (trayImage != null) {
			trayImage.dispose();
		}
		if (trayItem != null) {
			trayItem.dispose();
		}
	}

}

		

Run your application and see that you have a system tray icon. Test the menu and the minimized behavior. If the application is minimized it should not be visible in the taskbar but only in the system tray.

Showing the application icon in the taskpane

26. Target Platform

26.1. Developing against the Eclipse IDE

If you develop Eclipse plug-ins, you reuse components of the Eclipse Platform for example SWT or JFace.

The question is: how can you control which version of a specific plug-in is used?

Per default these plug-ins are sourced directly from your Eclipse IDE.

This is not an ideal approach, as this makes you dependent on your version of the Eclipse IDE. This can lead to problems, if developers are using different versions of Eclipse. It also makes it difficult to upgrade these plug-ins for everyone at the same time.

If you follow this approach you would also need to install every plug-in required for your product either in your workspace or in your Eclipse IDE.

The last problem with this approach is that you might unintentionally add plug-ins from the Eclipse IDE to your product.

26.2. Defining your Target Platform

Via a Target Platform you define the set of plug-ins which are available for development. For example you define which version of the SWT and JFace plug-in is part of your target platform.

This makes you independent from the Eclipse IDE you are using. Developers with different versions of Eclipse will compile their work against the same set of plug-ins.

A Target Platform is defined via a ".target" file. This target file defines the list of plug-ins and features. You typically share this target file between different developers to ensure that everyone is using the same basis for development.

The most effective way of defining your Target Platform is to use (Eclipse p2) update sites. These are the same type of update sites which you use if you want to install a new set of plug-ins. If the content in the update site defined by your target platform is changed, your local set of plug-ins can also be updated.

It is also possible to define your target platform based on a file system, but this is not as flexible and therefore should be avoided.

26.3. Creating a Target Platform definition

A Target Definition file can be created via FileNewOtherPlug-in DevelopmentTarget Definition.

Define File name for Target Definition

You can add new locations via the "Add" button in the location section. To add an Eclipse p2 update site, select "Software Site" and specify the URL.

After you have defined your Target Definition file, you can set it as target in your Eclipse IDE via the "Set as Target Platform" button.

Setting the new defined target definition as target for the development

You can switch the target platform in the Eclipse Preferences. Select Window PreferencesPlug-in DevelopmentTarget Platform

Setting the target definition via the Eclipse Preferences

27. Tips and Tricks

27.1. Load an image from your plugin

To load an image from your plug-in your use the AbstractUIPlugin.

				
AbstractUIPlugin.imageDescriptorFromPlugin(“YourPluginId”,”/icons/your.gif”).createImage();
			

Alternatively you could load the framework directly.

				
Bundle bundle = FrameworkUtil.getBundle(this.getClass());
URL url = FileLocator.find(bundle, new Path("icons/alt_window_32.gif"), null);
Image image = ImageDescriptor.createFromURL(url).createImage();
			

27.2. Save users layout

To remember the user's layout and window size for the next time you start your application, add configurer.setSaveAndRestore(true); to the initialize method of ApplicationWorkbenchAdvisor.

				
package addactiontoview;

import org.eclipse.ui.application.IWorkbenchConfigurer;
import org.eclipse.ui.application.IWorkbenchWindowConfigurer;
import org.eclipse.ui.application.WorkbenchAdvisor;
import org.eclipse.ui.application.WorkbenchWindowAdvisor;

public class ApplicationWorkbenchAdvisor extends WorkbenchAdvisor {

	private static final String PERSPECTIVE_ID = "AddActiontoView.perspective";

	public WorkbenchWindowAdvisor createWorkbenchWindowAdvisor(
			IWorkbenchWindowConfigurer configurer) {
		return new ApplicationWorkbenchWindowAdvisor(configurer);
	}

	public String getInitialWindowPerspectiveId() {
		return PERSPECTIVE_ID;
	}

	@Override
	public void initialize(IWorkbenchConfigurer configurer) {
		super.initialize(configurer);
		configurer.setSaveAndRestore(true);
	}

}

			

Eclipse has a pre-defined command to reset the perspective. See Eclipse Commands .

27.3. Accessing the status line

The status line in an RCP application can be used to give the user some information about the running application. The shared message area can be used by all parts of the application to write messages to this area. The whole RCP application has access to the information in the shared status line therefore the information in the shared status line might be overwritten.

To show the status line in your RCP application use the "ApplicationWorkbenchWindowAdvisor" and set the status line visible in the method preWindowOpen().


				
public class ApplicationWorkbenchWindowAdvisor extends WorkbenchWindowAdvisor {
    //...
    @Override
    public void preWindowOpen() {
    	// ....
        configurer.setShowStatusLine(false);
    }
}

			

The following writes a text to the status line from a view.


				
IStatusLineManager manager = getViewSite().getActionBars().getStatusLineManager();
manager.setMessage("Information for the status line");
			

From an editor you can access the status line via the following:

				
IEditorPart.getEditorSite().getActionBars();

			

27.4. Finding unused dependencies

In the file plugin.xml (tab dependencies) you define on which plugins your plugin depends. Of course you should only define the required plugins here. You can check if you have any dependency maintained which is actually not used, by selecting Dependency Analysis -> Find unused dependencies.

How to remove unused dependencies

27.5. Multi-User settings

Eclipse RCP applications save configuration files in the folder ".metadata". In the standard settings the Eclipse RCP installation directory will be used for this folder. If several users are using the same installation folder, then you should supply the parameter "-data" to specify an alternative location. If you specify the value "@user.home/applicationname" the configuration will be saved in a user specific folder.

28. Questions and Discussion

Before posting questions, please see the vogella FAQ. If you have questions or find an error in this article please use the www.vogella.de Google Group. I have created a short list how to create good questions which might also help you.

29. Links and Literature

29.1. Source Code

Source Code of Examples

29.3. vogella Resources

Eclipse RCP Training (German) Eclipse RCP Training with Lars Vogel

Android Tutorial Introduction to Android Programming

GWT Tutorial Program in Java and compile to JavaScript and HTML

Eclipse RCP Tutorial Create native applications in Java

JUnit Tutorial Test your application

Git Tutorial Put everything you have under distributed version control system