Jump to: navigation, search

Difference between revisions of "SOA/BPMN Modeler/Developing with the BPMN modeler"

(added main ideas to develop on top of the BPMN modeler)
 
(27 intermediate revisions by the same user not shown)
Line 1: Line 1:
 
This page is about developing with the STP BPMN modeler, by contributing and/or removing actions, shapes, etc.
 
This page is about developing with the STP BPMN modeler, by contributing and/or removing actions, shapes, etc.
  
 +
== Menus ==
  
h1. Adding menu extensions
+
=== Adding menu items ===
  
h1. Adding toolbar extensions
+
==== Adding a menu item ====
  
h1. Creating a new drag and drop (DND) interaction
+
==== Adding a menu ====
  
h2. Creating a DND to add a semantic element (eg annotation)
+
=== Adding toolbar extensions ===
  
h2. Creating a DND to add a graphical element
+
==== Adding a toolbar item ====
  
h1. Hiding elements of the palette
+
==== Adding a toolbar group ====
  
h1. Hiding elements in the popup toolbar and the end connections menus
+
=== Removing menu items ===
 +
 
 +
== Creating a new drag and drop (DND) interaction ==
 +
 
 +
=== Creating a DND to add a semantic element (eg annotation) ===
 +
[[STP/BPMN_Component/Samples#Annotation_Drag_and_Drop|Full sample]]
 +
 
 +
You need to expose a <code>IDnDHandler</code> object through an <code>IAdapterFactory</code>.
 +
 
 +
The <code>IDnDHandler</code> must return a command that will effectively drop the annotation on the diagram's selected shape.
 +
 
 +
In the case of an <code>EAnnotation</code> drop, it is recommended to extend the <code>AbstractEAnnotationDnDHandler</code> class, and provide your own method:
 +
 
 +
<code><pre>public Command getDropCommand(IGraphicalEditPart hoverPart, int index,
 +
            Point dropLocation) {
 +
       
 +
        Map<String, String> details = new HashMap<String, String>();
 +
        try {
 +
            details.put("lastModified", String.valueOf(_file.getLocalTimeStamp()));
 +
            details.put("name", _file.getName());
 +
            details.put("fileExtension", _file.getFileExtension());
 +
            details.put("content-type", _file.getContentDescription().getContentType().getName());
 +
 
 +
            Reader in = new BufferedReader(new InputStreamReader(_file.getContents()));
 +
            StringBuffer buffer= new StringBuffer(1024);
 +
            [..]
 +
            details.put("text", buffer.toString());
 +
        } catch(Exception e) {
 +
            e.printStackTrace();
 +
        }
 +
       
 +
        return createEAnnotationDropCommand(
 +
                createAnnotation(TEXT_ANNOTATION_SOURCE, details),
 +
                (EModelElement) hoverPart.resolveSemanticElement());
 +
    }</pre></code>
 +
 
 +
The <code>createAnnotation</code> and <code>createEAnnotationDropCommand</code> are two methods exposed by the super class for your convenience.
 +
 
 +
=== Creating a DND to add a graphical element ===
 +
 
 +
 
 +
== Annotation decoration ==
 +
 
 +
[[STP/BPMN_Component/Samples#Decoration_of_an_annotation|Sample]]
 +
 
 +
You can decorate annotations through our own extension point.
 +
 
 +
 
 +
<source lang="xml">
 +
<extension point="org.eclipse.stp.bpmn.diagram.EAnnotationDecorator">
 +
      <decorator
 +
            class="org.eclipse.stp.bpmn.sample.annotationdecoration.AnnotationDecorator" <!-- the class of the IEAnnotationDecorator implementation -->
 +
            source="textAnnotationSource"/> <!-- the source of the annotation to use -->
 +
</extension>
 +
</source>
 +
 
 +
Our decorator looks like this:
 +
 
 +
<source lang="java">
 +
public class AnnotationDecorator implements IEAnnotationDecorator {
 +
 
 +
    public String getAssociatedAnnotationSource() {
 +
        return "textAnnotationSource";
 +
    }
 +
 
 +
    public Direction getDirection(EditPart part, EModelElement elt,
 +
            EAnnotation ann) {
 +
        return Direction.WEST;
 +
    }
 +
 
 +
    public ImageDescriptor getImageDescriptor(EditPart part,
 +
            EModelElement element, EAnnotation annotation) {
 +
        return PlatformUI.getWorkbench().getSharedImages().
 +
            getImageDescriptor(ISharedImages.IMG_OBJ_FILE);
 +
    }
 +
 
 +
    public IFigure getToolTip(EditPart part, EModelElement element,
 +
            EAnnotation annotation) {
 +
        if (annotation != null) {
 +
            Label label = new Label();
 +
            label.setText(annotation.getDetails().get("name"));
 +
            return label;
 +
        }
 +
        return null;
 +
    }
 +
}
 +
 
 +
</source>
 +
 
 +
== Hiding elements of the palette ==
 +
 
 +
[[STP/BPMN_Component/Samples#Hiding_palette_elements|Full sample]]
 +
 
 +
You can remove elements by overriding the palette provider
 +
 
 +
<source lang="xml">
 +
  <extension point="org.eclipse.gmf.runtime.diagram.ui.paletteProviders">
 +
      <paletteProvider class="org.eclipse.stp.bpmn.sample.editor.NoTextAnnotationPaletteContributor">
 +
        <Priority name="Lowest"/>
 +
        <editor id="org.eclipse.stp.bpmn.sample.noTextAnnotationInPalette.editor1"/>
 +
      </paletteProvider>
 +
  </extension>
 +
 
 +
</source>
 +
 
 +
You can override the <code>BpmnPaletteProvider</code> class, call the super method and remove a specific entry from the palette containers. Obviously you can also override the <code>BpmnPaletteFactory</code> and have it your way.
 +
 
 +
<source lang="java">
 +
    public void contributeToPalette(IEditorPart editor, Object content,
 +
            PaletteRoot root, Map predefinedEntries) {
 +
        //this is the short way
 +
        super.contributeToPalette(editor, content, root, predefinedEntries);
 +
        ((PaletteContainer) root.getChildren().get(1)).getChildren().remove(0);
 +
       
 +
        //the long way consists in populating the palette with your own factory.
 +
    }
 +
</source>
 +
 
 +
Be aware that it is difficult to catch exceptions while the palette is being filled. No stacktrace will appear in the error log in case something goes wrong.
 +
 
 +
== Hiding elements in the popup toolbar and the end connections menus ==
 +
 
 +
[[STP/BPMN_Component/Samples#Hiding_elements_in_toolbar_and_connection_menus|Full sample]]
 +
 
 +
You need to create your own editor, subclassing the <code>BpmnDiagramEditor</code>.
 +
 
 +
In this editor you will override the method <code>createDiagramEditDomain</code>:
 +
<source lang="java">
 +
    protected void createDiagramEditDomain() {
 +
        BpmnDiagramEditDomain domain = new BpmnDiagramEditDomain(this);
 +
        domain.setActionManager(createActionManager());
 +
       
 +
        Set<IElementType> types = new HashSet<IElementType>();
 +
        for (Object gatewayType : ActivityType.VALUES_GATEWAYS) {
 +
            types.add(ElementTypeEx.wrap(BpmnElementTypes.Activity_2001,
 +
                    ((ActivityType) gatewayType).getLiteral()));
 +
        }
 +
        types.add(BpmnElementTypes.Group_1004);
 +
        types.add(BpmnElementTypes.Group_2006);
 +
        domain.setRemovedElementTypes(types);
 +
       
 +
        setEditDomain(domain);
 +
    }
 +
</source>
 +
 
 +
== Provide your own edit parts ==
 +
 
 +
[[STP/BPMN_Component/Samples#Provide_your_own_edit_parts|Full sample]]
 +
 
 +
When extending the modeler, you might want to change the look and feel of a particular figure, or modify the behavior of an edit part by manipulating its edit policies. You can achieve that by providing your own edit parts.
 +
 
 +
To do this, you declare your own edit part provider:
 +
 
 +
<source lang="xml">
 +
<extension point="org.eclipse.gmf.runtime.diagram.ui.editpartProviders">
 +
      <editpartProvider class="org.eclipse.stp.bpmn.sample.neweditpartprovider.NewEditPartProvider">
 +
        <Priority name="Highest"/>
 +
      </editpartProvider>
 +
  </extension>
 +
</source>
 +
 
 +
In your own implementation of the edit part provider, return your own factory in the constructor:
 +
 
 +
<source lang="java">
 +
    public NewEditPartProvider() {
 +
        setFactory(new NewEditPartFactory());
 +
        setAllowCaching(true);
 +
    }
 +
</source>
 +
 
 +
You should override the <code>createEditPart</code> method of the factory to return what you want:
 +
 
 +
<source lang="java">
 +
    private class NewEditPartFactory extends BpmnEditPartFactory {
 +
       
 +
        /**
 +
        * Creates a special text annotation edit part
 +
        */
 +
        public EditPart createEditPart(EditPart context, Object model) {
 +
            if (model instanceof View) {
 +
                final View view = (View) model;
 +
                int viewVisualID = BpmnVisualIDRegistry.getVisualID(view);
 +
                switch (viewVisualID) {
 +
                case TextAnnotationEditPart.VISUAL_ID :
 +
                    return new TextAnnotationEditPartWithBackground(view);
 +
                case TextAnnotation2EditPart.VISUAL_ID :
 +
                    return new TextAnnotation2EditPartWithBackground(view);
 +
                }
 +
            }
 +
            return super.createEditPart(context, model);
 +
        }
 +
    }
 +
</source>
 +
 
 +
== FAQ ==
 +
 
 +
=== why do you have IElementTypeEx ? ===
 +
<code>IElementType</code> is a GMF interface to describe a view type. It is passed in requests to create elements.
 +
 
 +
The <code>BpmnElementTypes</code> class contains all the element types for the BPMN modeler.
 +
That also means that each element type corresponds to a view and an edit part.
 +
 
 +
We did not want to generate an edit part per activity type. Instead we have created two edit parts for activities, one for normal activities and the other one for event handlers.
 +
 
 +
Then we use <code>IElementTypeEx</code> to add a secondary semantic hint that is the literal of the <code>ActivityType</code>.
 +
 
 +
To create a <code>IElementTypeEx</code> object, you can use this:
 +
 
 +
<source lang="java">
 +
ElementTypeEx.wrap(BpmnElementTypes.Activity_2001,
 +
                  ActivityType.EVENT_INTERMEDIATE_MESSAGE_LITERAL.getLiteral());
 +
</source>
 +
 
 +
[[Category:BPMN]]
 +
[[Category:SOA]]
 +
[[Category:STP]]

Latest revision as of 12:06, 4 November 2010

This page is about developing with the STP BPMN modeler, by contributing and/or removing actions, shapes, etc.

Menus

Adding menu items

Adding a menu item

Adding a menu

Adding toolbar extensions

Adding a toolbar item

Adding a toolbar group

Removing menu items

Creating a new drag and drop (DND) interaction

Creating a DND to add a semantic element (eg annotation)

Full sample

You need to expose a IDnDHandler object through an IAdapterFactory.

The IDnDHandler must return a command that will effectively drop the annotation on the diagram's selected shape.

In the case of an EAnnotation drop, it is recommended to extend the AbstractEAnnotationDnDHandler class, and provide your own method:

public Command getDropCommand(IGraphicalEditPart hoverPart, int index,
            Point dropLocation) {
        
        Map<String, String> details = new HashMap<String, String>();
        try {
            details.put("lastModified", String.valueOf(_file.getLocalTimeStamp()));
            details.put("name", _file.getName());
            details.put("fileExtension", _file.getFileExtension());
            details.put("content-type", _file.getContentDescription().getContentType().getName());

            Reader in = new BufferedReader(new InputStreamReader(_file.getContents()));
            StringBuffer buffer= new StringBuffer(1024);
            [..]
            details.put("text", buffer.toString());
        } catch(Exception e) {
            e.printStackTrace();
        }
        
        return createEAnnotationDropCommand(
                createAnnotation(TEXT_ANNOTATION_SOURCE, details),
                (EModelElement) hoverPart.resolveSemanticElement());
    }

The createAnnotation and createEAnnotationDropCommand are two methods exposed by the super class for your convenience.

Creating a DND to add a graphical element

Annotation decoration

Sample

You can decorate annotations through our own extension point.


<extension point="org.eclipse.stp.bpmn.diagram.EAnnotationDecorator">
      <decorator
            class="org.eclipse.stp.bpmn.sample.annotationdecoration.AnnotationDecorator" <!-- the class of the IEAnnotationDecorator implementation -->
            source="textAnnotationSource"/> <!-- the source of the annotation to use -->
</extension>

Our decorator looks like this:

public class AnnotationDecorator implements IEAnnotationDecorator {
 
    public String getAssociatedAnnotationSource() {
        return "textAnnotationSource";
    }
 
    public Direction getDirection(EditPart part, EModelElement elt,
            EAnnotation ann) {
        return Direction.WEST;
    }
 
    public ImageDescriptor getImageDescriptor(EditPart part,
            EModelElement element, EAnnotation annotation) {
        return PlatformUI.getWorkbench().getSharedImages().
            getImageDescriptor(ISharedImages.IMG_OBJ_FILE);
    }
 
    public IFigure getToolTip(EditPart part, EModelElement element,
            EAnnotation annotation) {
        if (annotation != null) {
            Label label = new Label();
            label.setText(annotation.getDetails().get("name"));
            return label;
        }
        return null;
    }
}

Hiding elements of the palette

Full sample

You can remove elements by overriding the palette provider

   <extension point="org.eclipse.gmf.runtime.diagram.ui.paletteProviders">
      <paletteProvider class="org.eclipse.stp.bpmn.sample.editor.NoTextAnnotationPaletteContributor">
         <Priority name="Lowest"/>
         <editor id="org.eclipse.stp.bpmn.sample.noTextAnnotationInPalette.editor1"/>
      </paletteProvider>
   </extension>

You can override the BpmnPaletteProvider class, call the super method and remove a specific entry from the palette containers. Obviously you can also override the BpmnPaletteFactory and have it your way.

    public void contributeToPalette(IEditorPart editor, Object content,
            PaletteRoot root, Map predefinedEntries) {
        //this is the short way
        super.contributeToPalette(editor, content, root, predefinedEntries);
        ((PaletteContainer) root.getChildren().get(1)).getChildren().remove(0);
 
        //the long way consists in populating the palette with your own factory.
    }

Be aware that it is difficult to catch exceptions while the palette is being filled. No stacktrace will appear in the error log in case something goes wrong.

Hiding elements in the popup toolbar and the end connections menus

Full sample

You need to create your own editor, subclassing the BpmnDiagramEditor.

In this editor you will override the method createDiagramEditDomain:

    protected void createDiagramEditDomain() {
        BpmnDiagramEditDomain domain = new BpmnDiagramEditDomain(this);
        domain.setActionManager(createActionManager());
 
        Set<IElementType> types = new HashSet<IElementType>();
        for (Object gatewayType : ActivityType.VALUES_GATEWAYS) {
            types.add(ElementTypeEx.wrap(BpmnElementTypes.Activity_2001, 
                    ((ActivityType) gatewayType).getLiteral()));
        }
        types.add(BpmnElementTypes.Group_1004);
        types.add(BpmnElementTypes.Group_2006);
        domain.setRemovedElementTypes(types);
 
        setEditDomain(domain);
    }

Provide your own edit parts

Full sample

When extending the modeler, you might want to change the look and feel of a particular figure, or modify the behavior of an edit part by manipulating its edit policies. You can achieve that by providing your own edit parts.

To do this, you declare your own edit part provider:

<extension point="org.eclipse.gmf.runtime.diagram.ui.editpartProviders">
      <editpartProvider class="org.eclipse.stp.bpmn.sample.neweditpartprovider.NewEditPartProvider">
         <Priority name="Highest"/>
      </editpartProvider>
   </extension>

In your own implementation of the edit part provider, return your own factory in the constructor:

    public NewEditPartProvider() {
        setFactory(new NewEditPartFactory());
        setAllowCaching(true);
    }

You should override the createEditPart method of the factory to return what you want:

    private class NewEditPartFactory extends BpmnEditPartFactory {
 
        /**
         * Creates a special text annotation edit part
         */
        public EditPart createEditPart(EditPart context, Object model) {
             if (model instanceof View) {
                 final View view = (View) model;
                 int viewVisualID = BpmnVisualIDRegistry.getVisualID(view);
                 switch (viewVisualID) {
                 case TextAnnotationEditPart.VISUAL_ID :
                     return new TextAnnotationEditPartWithBackground(view);
                 case TextAnnotation2EditPart.VISUAL_ID :
                     return new TextAnnotation2EditPartWithBackground(view);
                 }
             }
             return super.createEditPart(context, model);
        }
    }

FAQ

why do you have IElementTypeEx ?

IElementType is a GMF interface to describe a view type. It is passed in requests to create elements.

The BpmnElementTypes class contains all the element types for the BPMN modeler. That also means that each element type corresponds to a view and an edit part.

We did not want to generate an edit part per activity type. Instead we have created two edit parts for activities, one for normal activities and the other one for event handlers.

Then we use IElementTypeEx to add a secondary semantic hint that is the literal of the ActivityType.

To create a IElementTypeEx object, you can use this:

ElementTypeEx.wrap(BpmnElementTypes.Activity_2001,
                   ActivityType.EVENT_INTERMEDIATE_MESSAGE_LITERAL.getLiteral());