<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
    <head>
        <!-- -*- xhtml -*- -->
        <title>NetBeans Visual Library Tutorial for NetBeans Platform 7.1</title>
        <link rel="stylesheet" type="text/css" href="https://netbeans.org/netbeans.css"/>
        <meta name="AUDIENCE" content="NBUSER"/>
        <meta name="TYPE" content="ARTICLE"/>
        <meta name="EXPIRES" content="N"/>
        <meta name="developer" content="geertjan.wielenga@sun.com"/>
        <meta name="indexed" content="y"/>
        <meta name="description" content="A walk-through of the basic features of the Visual Library API."/>
        <!--      Copyright (c) 2009, 2010, Oracle and/or its affiliates. All rights reserved. -->
        <!--     Use is subject to license terms.-->
    </head>
    <body>
        <h1>NetBeans Visual Library Tutorial</h1>

        <p>In this tutorial, you will learn how to use the main
            features provided by the <a href="http://bits.netbeans.org/dev/javadoc/org-netbeans-api-visual/overview-summary.html">NetBeans Visual Library API</a>.
            The library provides a set of reusable pieces, called "widgets".
            When you compose them together, you are able to create a visualization
            in a simple and flexible way.
            Each widget has, built into it, various properties, such as "layout", "border",
            and "actions". The set of predefined widgets provided by the library can be extended.</p>

        <p>All the pluggable pieces are declared as interfaces or abstract classes, such
            as "WidgetAction", "Anchor", "AnchorShape", "PointShape", "Animator", "Border",
            "GraphLayout", "LookFeel", "Layout", "SceneLayout", "Router", and "CollisionsCollector".</p>

        <p>In summary, the Visual Library API
            is a visualization API, useful in the context of modeling and graphing features.</p>

        <p><strong class="notes">Note: </strong>This document uses 
            NetBeans Platform 7.1 and NetBeans IDE 7.1. If you
            are using an earlier version, see <a href="70/nbm-visual_library.html">the previous version
                of this document</a>.</p>

        <p><b>Contents</b></p>

        <p><img src="../images/articles/74/netbeans_stamp_74_73_72.png" class="stamp" width="114" height="114" alt="Content on this page applies to NetBeans IDE 7.1" title="Content on this page applies to NetBeans IDE 7.1"/></p>

        <ul class="toc">
            <li><a href="#getting-started">Setting Up the Module</a></li>
            <li><a href="#creating-the-scene">Creating the Scene</a></li>
            <li><a href="#creating-a-palette">Creating a Component Palette for the Scene</a></li>
            <li><a href="#adding-a-layer-widget">Adding a LayerWidget</a></li>
            <li><a href="#adding-an-icon-widget">Adding an IconNodeWidget via Drag and Drop Functionality</a></li>
            <li><a href="#adding-to-scene">Adding Functionality to the Scene</a></li>
            <li><a href="#adding-to-widget">Adding Functionality to the IconNodeWidget</a></li>
        </ul>

        <p><b>To follow this tutorial, you need the software and resources listed in the following 
                table.</b></p>

        <table>
            <tbody>
                <tr>
                    <th class="tblheader" scope="col">Software or Resource</th>
                    <th class="tblheader" scope="col">Version Required</th>
                </tr> 
                <tr>
                    <td class="tbltd1"><a href="https://netbeans.org/downloads/index.html">NetBeans IDE</a></td>
                    <td class="tbltd1">version 7.1 or above</td>
                </tr>
                <tr>
                    <td class="tbltd1"><a href="http://java.sun.com/javase/downloads/index.jsp">Java Developer Kit (JDK)</a></td>
                    <td class="tbltd1">version 7 or above</td>
                </tr>
            </tbody>
        </table>

        <p>Also, you will use 3 icons in the tutorial. You can right-click
            them here and save them locally, then copy them to the module project's
            location, after you create the module project later in this tutorial. Here are
            the 3 icons:</p>

        <p><img alt="" src="../images/tutorials/vislib/image1.png"/>
            <img alt="" src="../images/tutorials/vislib/image2.png"/>
            <img alt="" src="../images/tutorials/vislib/image3.png"/></p>


        <p>All the information you need to know for working with the Visual Library API
            is collected at these two locations:</p>

        <ul>
            <li><a href="http://graph.netbeans.org/">Visual Library Project Page</a></li>
            <li><a href="http://graph.netbeans.org/documentation.html">Visual Library 2.0 - Documentation</a></li>
        </ul>

        <!-- ===================================================================================== -->

        <h2><a name="getting-started"></a>Setting Up the Module</h2>

        <p>In this section, we use wizards to create a module project and
            a custom window component.</p>

        <div class="indent">

            <ol>
                <li>Choose File &gt; New Project (Ctrl+Shift+N). Under Categories, select NetBeans Modules.
                    Under Projects, select Module. Click Next.</li>
                <li>In the Name and Location panel, type <tt>ShapeSample</tt> in the Project Name field.
                    Change the Project Location to any directory on your computer. Leave the Standalone Module option
                    and Set as Main Project checkbox selected. Click Next.</li>
                <li><p>In the Basic Module Configuration panel, type <tt>org.netbeans.shapesample</tt>
                        in Code Name Base. Click Finish.</p>

                    <p>The IDE creates the <tt>ShapeSample</tt> project. The project contains all of your sources and project
                        metadata, such as the project's Ant build script. The project opens in the IDE. You can view its logical
                        structure in the Projects window (Ctrl+1) and its file structure in the Files window (Ctrl+2).
                    </p></li>

                <li>Right-click the module project, choose
                    New &gt; Other and choose Window from the
                    Module Development category. Click Next. Choose <tt>editor</tt>
                    in the drop-down list and select Open on Application Start. Click Next.</li>

                <li><p>Type <tt>Shape</tt> in Class Name Prefix. Optionally,
                        add an icon with a dimension of 16x16 pixels. Click Finish.</p> 

                    <p>A Java class is created, named <tt>ShapeTopComponent</tt>.
                        Open this file in "Design" mode. You should now see this:</p>

                    <p><img alt="" style="border:1px solid black" src="../images/tutorials/vislib/71/shapetopcomponent.png"/></p>
                </li>

                <li><p>Right-click the project, choose Properties, click Libraries
                        in the Project Properties dialog box and declare a dependency on the Visual Library API.</p>

                    <p class="notes"><b>Note:</b> The Visual Library is not one of the modules included
                        in a new NetBeans Platform application. To set a dependency on it in a new
                        NetBeans Platform application,
                        you first need to include it in the application. To do so, right-click 
                        the application, choose Properties, go to Libraries panel, expand 
                        'platform', and at the end of the list select Visual Library. Then you can set
                        a dependency on it in your module.</p>


                    <p>Click OK.</p>
                </li>

            </ol>

        </div>

        <h2><a name="creating-the-scene"></a>Creating the Scene</h2>

        <p>Programming with the Visual Library API is similar to programming in Swing. You build
            and modify a tree of visual elements that are called "widgets". The root of the tree is 
            represented by a Scene class which holds all the visual data of the scene. The scene is a widget. 
            You have to create a scene view, which is a JComponent. You must then add
            the JComponent to a JScrollPane.</p>

        <p>In this section,
            we add a JScrollPane to our TopComponent. Then we create a new
            scene. Next, we pass the scene view to the TopComponent, so that it can be displayed in
            the TopComponent's JScrollPane. We then install the module project and display
            our first scene.</p>

        <div class="indent">

            <ol>

                <li><p>In the <tt>org.netbeans.shapesample</tt> package, create a Java class called <tt>GraphSceneImpl</tt>.
                        Let the class extend <tt>GraphScene</tt>.</p>

                    <p>A red error underline and a lightbulb appears. Let the IDE generate the import statement.</p>

                    <p>A red error underline and a lightbulb appears again. Let the IDE generate the class's abstract methods.</p>
                </li>
                <li>Create a dummy implementation of the class by adding
                    meaningful identifiers and setting <tt>null</tt> to be returned where necessary, 
                    so that all of the class's requirements are fulfilled:

                    <pre class="examplecode">public class GraphSceneImpl extends GraphScene {
    
    public GraphSceneImpl() {
    }
    
    @Override
    protected Widget attachNodeWidget(Object node) {
        return null;
    }
    
    @Override
    protected Widget attachEdgeWidget(Object edge) {
        return null;
    }
    
    @Override
    protected void attachEdgeSourceAnchor(Object edge, Object oldSourceNode, Object newSourceNode) {
    
    }
    
    @Override
    protected void attachEdgeTargetAnchor(Object edge, Object oldTargetNode, Object newTargetNode) {
            
    }
    
}</pre></li>

                <li>Now use the TopComponent's 
                    constructor to hold an instance of the <tt>GraphSceneImpl</tt> class. To do so, add
                    the following to the end of the <tt>ShapeTopComponent</tt> class's constructor:

                    <pre class="examplecode">setLayout(new BorderLayout());

GraphSceneImpl scene = new GraphSceneImpl();

JScrollPane shapePane = new JScrollPane();

shapePane.setViewportView(scene.createView());

add(shapePane, BorderLayout.CENTER);
add(scene.createSatelliteView(), BorderLayout.WEST);</pre>

                    <p>Notice that we are creating two views. The first will be a large view for
                        visualization of your graphs or models, and so on. The second is a satellite view,
                        which we have placed in the WEST (i.e., the left side) of the TopComponent. This will
                        let the user navigate quickly across the view and gives an overview of the entire scene.</p>
                </li> 
                <li>Right-click the project node and choose "Run".</li>

            </ol>

        </div>

        <p>A new instance of the application starts up.
            When the module installs, look under the Window menu and you will find a new menu item
            called "Shape", at the top of the list of menu items. 
            Choose it and you will see the start of your Visual Library API implementation:</p>

        <p><img alt="" src="../images/tutorials/vislib/firstscene.png"/></p>

        <!-- ===================================================================================== -->
        <h2><a name="creating-a-palette"></a>Creating a Component Palette for the Scene</h2>

        <p>To do something useful with the Visual Library API, we will implement the <a href="http://bits.netbeans.org/dev/javadoc/org-netbeans-spi-palette/overview-summary.html">Palette API</a>
            so that we end up with a Component Palette containing the shapes shown at the start of this
            tutorial. Later, we will add the Visual Library API's drag and drop functionality so that 
            we can drag and drop the shapes
            into the scene. After that, we will be able to enrich the scene with additional features,
            such as the ability to zoom and pan in the scene.</p>

        <div class="indent">

            <ol>
                <li><p>Since the focus of this tutorial is the Visual Library API, and not the Palette API,
                        no time will be spent here explaining how the Palette API works. Many tutorials
                        exist on this subject already (<a href="https://netbeans.org/kb/trails/platform.html">here</a>).
                        Therefore, you can simply copy and paste the following files into a new package
                        called <tt>org.netbeans.shapesample.palette</tt>:</p>

                    <ul>
                        <li><a href="../images/tutorials/vislib/Category.java">Category.java</a></li>
                        <li><a href="../images/tutorials/vislib/CategoryChildren.java">CategoryChildren.java</a></li>
                        <li><a href="../images/tutorials/vislib/CategoryNode.java">CategoryNode.java</a></li>
                        <li><a href="../images/tutorials/vislib/PaletteSupport.java">PaletteSupport.java</a></li>
                        <li><a href="../images/tutorials/vislib/Shape.java">Shape.java</a></li>
                        <li><a href="../images/tutorials/vislib/ShapeChildren.java">ShapeChildren.java</a></li>
                        <li><a href="../images/tutorials/vislib/ShapeNode.java">ShapeNode.java</a></li>
                    </ul>

                </li>

                <li>In the same way as explained in step 3 of the section called "Getting Started", earlier in this tutorial,
                    add dependencies on the Actions API, Nodes API, and Common Palette API.</li>

                <li>Next, add the palette to the TopComponent's Lookup, by adding this
                    line to the end of the TopComponent's constructor:

                    <pre class="examplecode">associateLookup( Lookups.singleton(PaletteSupport.createPalette() ));</pre>

                </li>

                <li>The IDE will prompt you to insert import statements for <tt>org.openide.util.lookup.Lookups</tt>
                    and <tt>org.netbeans.shapesample.palette.PaletteSupport</tt>. Accept the prompts and let
                    the IDE generate the import statements.</li>

                <li><p>Place the images found at the start of this tutorial
                        into the <tt>org.netbeans.shapesample.palette</tt> package. 
                        The Projects window should now look as follows:</p>
                    <p><img alt="" src="../images/tutorials/vislib/71/proj-window.png"/></p></li>

                <li><p>Install the module again. The new
                        Component Palette is shown to the right of the scene:</p>

                    <p><img alt="" src="../images/tutorials/vislib/firstpalette.png"/></p>

                </li>

            </ol>

        </div>

        <p>When you try to drag and drop a widget onto
            the scene, nothing happens because you need
            a <tt>LayerWidget</tt> on which you will be
            able to drop your widgets. You will
            be shown how to do so in the next section.</p>

        <!-- ===================================================================================== -->

        <h2><a name="adding-a-layer-widget"></a>Adding a LayerWidget</h2>

        <p>A <a href="http://bits.netbeans.org/dev/javadoc/org-netbeans-api-visual/org/netbeans/api/visual/widget/LayerWidget.html">LayerWidget</a>
            represents a glasspane, similar to JGlassPane in Swing. It is transparent by default. So,
            before we go any further, we will add a LayerWidget to the scene, so that
            we have somewhere to place the visible widgets that we will drag and drop onto the scene.</p>

        <div class="indent">

            <ol><li>In the <tt>GraphSceneImpl</tt> class, declare the LayerWidget:

                    <pre class="examplecode">private LayerWidget mainLayer;</pre></li>

                <li>In the <tt>GraphSceneImpl</tt> class's constructor, add the LayerWidget
                    as a child of the scene:

                    <pre class="examplecode">mainLayer = new LayerWidget (this);
addChild (mainLayer);</pre>
                </li>

            </ol>

        </div>

        <p>Now, when we drag and drop items from the palette as widgets to the scene,
            we will add them as children of the LayerWidget. Because LayerWidgets are
            transparent by default, you could have various LayerWidgets transparently on
            top of each other so that, for example, you can add a background image to the scene.</p>

        <p>For details, see <a href="http://bits.netbeans.org/dev/javadoc/org-netbeans-api-visual/org/netbeans/api/visual/widget/LayerWidget.html">LayerWidget</a>
            in the Javadoc.</p>

        <!-- ===================================================================================== -->
        <h2><a name="adding-an-icon-widget"></a>Adding an IconNodeWidget via Drag and Drop Functionality</h2>

        <p>Earlier, we used the <tt>GraphSceneImpl</tt> class's constructor to pass a scene to the TopComponent's JScrollPane.
            So far, the scene exists but has no behavior. Behavior is added through actions.
            The action that we will look at in this section is called <tt><a href="http://graph.netbeans.org/documentation.html#AcceptAction">AcceptAction</a></tt>. This
            action enables drag and drop functionality. The drag and drop functionality could
            be applied to a widget, but here we apply it to the scene itself.</p>

        <p>We use <tt>createAcceptAction</tt> to specify what should happen
            when an item from the palette is dragged over the scene. Two methods are involved
            here. The first, <tt>isAcceptable()</tt>, is used to determine whether the
            item is acceptable to the scene. Here you can test the item, by using
            the transferable. You can also set the drag image, which is all that we
            do in the implementation below. If <tt>true</tt> is returned, the <tt>accept</tt>
            method is called. Here we get the image from the transferable, using the same
            helper method as before. Then we call the <tt>addNode</tt> method, instantiating
            a new <a href="http://bits.netbeans.org/dev/javadoc/org-netbeans-api-visual/org/netbeans/api/visual/widget/general/IconNodeWidget.html">IconNodeWidget</a>
            and passing the image retrieved from the transferable.</p>

        <p>All the code in this section is interrelated, and you will
            receive red error underlines in your code until all the methods below
            have been added, but we will try to add everything
            in some kind of logical order anyway!</p>

        <div class="indent">

            <ol>
                <li>First, add the <tt>createAcceptAction</tt>, with its two methods, to the <tt>GraphSceneImpl</tt> class's constructor:

                    <pre class="examplecode">getActions().addAction(ActionFactory.createAcceptAction(new AcceptProvider() {

    @Override
    public ConnectorState isAcceptable(Widget widget, Point point, Transferable transferable) {
        Image dragImage = getImageFromTransferable(transferable);
        JComponent view = getView();
        Graphics2D g2 = (Graphics2D) view.getGraphics();
        Rectangle visRect = view.getVisibleRect();
        view.paintImmediately(visRect.x, visRect.y, visRect.width, visRect.height);
        g2.drawImage(dragImage,
                AffineTransform.getTranslateInstance(point.getLocation().getX(),
                point.getLocation().getY()),
                null);
        return ConnectorState.ACCEPT;
    }

    @Override
    public void accept(Widget widget, Point point, Transferable transferable) {
        Image image = getImageFromTransferable(transferable);
        Widget w = GraphSceneImpl.this.addNode(new MyNode(image));
        w.setPreferredLocation(widget.convertLocalToScene(point));
    }

}));</pre>

                    <p><strong class="notes">Note: </strong> After you add the above code, some red underlines will remain, denoting that there are errors.
                        These errors are because the code above refers to a method and a class that you have not yet created.
                        You will create them in the next steps.</p></li>

                <li>Next, in the <tt>GraphSceneImpl</tt> class, add a helper method for retrieving the image from the transferable:

                    <pre class="examplecode">private Image getImageFromTransferable(Transferable transferable) {
    Object o = null;
    try {
        o = transferable.getTransferData(DataFlavor.imageFlavor);
    } catch (IOException ex) {
    } catch (UnsupportedFlavorException ex) {
    }
    return o instanceof Image ? (Image) o : ImageUtilities.loadImage("org/netbeans/shapesample/palette/shape1.png");
}</pre>

                    <p><strong class="notes">Note: </strong> You can define
                        any kind of image when an image
                        is not successfully returned from this helper method. For now we will use the "<tt>shape1.png</tt>" image instead.</p>
                </li>
                <li>Create a new class called <tt>MyNode</tt>. This class represents a node in a graph-oriented model.
                    It cannot be an image directly, since each node has to be unique
                    (checked by "equals" method) in the model. If you would use the images
                    directly, then you would be able to have only 3 nodes (one for each
                    image) in the scene. Using the MyNode class, you can have multiple nodes and
                    each node can have its own or a shared image instance.

                    <pre class="examplecode">public class MyNode {
    
    private Image image;
    
    public MyNode(Image image) {
        this.image = image;
    }
    
    public Image getImage() {
        return image;
    }

}</pre>
                </li>
                <li>Change the signature of the <tt>GraphSceneImpl</tt> class to the following, so that the node is
                    received by the Visual Library implementation class:

                    <pre class="examplecode">extends GraphScene&lt;MyNode, String&gt;</pre>

                    <p class="tips">You must let the IDE generate new stubs for the abstract methods.</p>

                </li>

                <li>Finally, define the new widget in the <tt>GraphSceneImpl</tt> class. This method is called automatically by the <tt>accept</tt>
                    method. Use it to define a Visual Library widget when the palette item is dropped.

                    <pre class="examplecode">@Override
protected Widget attachNodeWidget(MyNode node) {
    IconNodeWidget widget = new IconNodeWidget(this);
    widget.setImage(node.getImage());
    widget.setLabel(Long.toString(node.hashCode()));
    widget.getActions().addAction(ActionFactory.createMoveAction());
    mainLayer.addChild(widget);
    return widget;
}</pre>

                    <p>Notice that we set the image retrieved from the node. We also generate a random
                        number so that we have a label. By default, the widget exists but has no behavior.
                        Here, we create a move action, so that the widget can be moved in the scene. Finally,
                        before returning the widget to the scene, we add it as a child to the LayerWidget that
                        we created in the previous section.</p></li>

                <li><p>Run the module and open the Shape window again.</p>

                    <p>Now you can drag and drop items from the palette. As you drag an item over the scene,
                        you will see the drag image. When you drop an item, it becomes a widget and is visible
                        within the scene as well as within the satellite view, as you can see here:</p>

                    <p><img alt="" src="../images/tutorials/vislib/finishedscene.png"/></p>
                </li>

            </ol>

        </div>
        <!-- ===================================================================================== -->
        <h2><a name="adding-to-scene"></a>Adding Functionality to the Scene</h2>

        <p>In the previous section, we added <tt><a href="http://graph.netbeans.org/documentation.html#AcceptAction">AcceptAction</a></tt>
            to the scene. We had to define two methods to specify whether the item should
            be dropped and for resolving the item. In this section, we use <tt><a href="http://graph.netbeans.org/documentation.html#ZoomAction">ZoomAction</a></tt>,
            to add zoom/unzoom functionality to the scene.</p>

        <div class="indent">

            <ol>
                <li>At the end of the <tt>GraphSceneImpl</tt> class's constructor, add this line:
                    <pre class="examplecode">getActions().addAction(ActionFactory.createZoomAction());</pre></li>

                <li>Install the module again.</li>

                <li><p>While holding CTRL key, use the mouse wheel to zoom in and out of the scene:</p>

                    <p><img alt="" src="../images/tutorials/vislib/zoom.png"/></p>

                    <p><img alt="" src="../images/tutorials/vislib/unzoom.png"/></p>
                </li>

            </ol>

        </div>

        <p><strong class="notes">Note: </strong> The shapes are rendered as images. SVG is currently not supported.</p>

        <p>In the same way as described above, you can add Pan functionality to the scene,
            by means of this line:</p>

        <pre class="examplecode">getActions().addAction(ActionFactory.createPanAction());</pre>

        <p>When you add this line, the user will be able to hold down the mouse wheel
            and then scroll in any direction in the scene.</p>

        <!-- ===================================================================================== -->
        <h2><a name="adding-to-widget"></a>Adding Functionality to the IconNodeWidget</h2>

        <p>Earlier we added <tt><a href="http://graph.netbeans.org/documentation.html#MoveAction">MoveAction</a></tt>
            to the IconNodeWidget, to enable move behavior for the widget. In the same way, a lot
            of other behavior can be added to the widget. In this section, we add
            <tt><a href="http://graph.netbeans.org/documentation.html#HoverAction">HoverAction</a></tt>,
            <tt><a href="http://graph.netbeans.org/documentation.html#SelectAction">SelectAction</a></tt>,
            and <tt><a href="http://graph.netbeans.org/documentation.html#InplaceEditorAction">InplaceEditorAction</a></tt>.</p>

        <p>The <tt>InplaceEditorAction</tt> will let the user change the label:</p>

        <p><img alt="" src="../images/tutorials/vislib/editable.png"/></p>

        <p>The <tt>SelectAction</tt> will change the color of the label when the widget is selected,
            while the <tt>HoverAction</tt> will change the color of the label when the mouse hovers over the widget:</p>

        <p><img alt="" src="../images/tutorials/vislib/selectable-hoverable.png"/></p>

        <div class="indent">

            <ol>
                <li>First define the editor action that we will add to the IconNodeWidget:

                    <pre class="examplecode">private WidgetAction editorAction = ActionFactory.createInplaceEditorAction(new LabelTextFieldEditor());</pre>   

                </li>

                <li>Now define the <tt>LabelTextFieldEditor</tt>, as follows:

                    <pre class="examplecode">private class LabelTextFieldEditor implements TextFieldInplaceEditor {

    public boolean isEnabled(Widget widget) {
        return true;
    }

    public String getText(Widget widget) {
        return ((LabelWidget) widget).getLabel();
    }

    public void setText(Widget widget, String text) {
        ((LabelWidget) widget).setLabel(text);
    }

}</pre>
                </li>

                <li>Finally, assign the editor action to the IconNodeWidget, in the same way
                    as done for the move action earlier:

                    <pre class="examplecode">widget.getLabelWidget().getActions().addAction(editorAction);</pre>   

                    <p>Here, we first get the IconNodeWidget's LabelWidget. Then we add the editor action
                        to the LabelWidget.</p>
                </li>

                <li>The IDE will prompt you to add several import statements. In each case,
                    accept the suggestion offered by the IDE.</li>

                <li>Next, in the case of <tt>SelectAction</tt> and <tt>HoverAction</tt>, you need do
                    nothing more than assign these actions to the IconNodeWidget:

                    <pre class="examplecode">widget.getActions().addAction(createSelectAction());
widget.getActions().addAction(createObjectHoverAction());</pre>
                </li>

                <li>Next, you need to think about the order of the actions that
                    you have created. For details, see the <a href="http://bits.netbeans.org/dev/javadoc/org-netbeans-api-visual/org/netbeans/api/visual/widget/doc-files/documentation.html#OrderOfActions">Order of Actions</a>
                    section in the documentation. After you have reordered
                    the actions, the <tt>attachNodeWidget</tt> should look as follows:

                    <pre class="examplecode">protected Widget attachNodeWidget(MyNode node) {
    IconNodeWidget widget = new IconNodeWidget(this);
    widget.setImage(node.getImage());
    widget.setLabel(Long.toString(node.hashCode()));

    //double-click, the event is consumed while double-clicking only:
    widget.getLabelWidget().getActions().addAction(editorAction);

    //single-click, the event is not consumed:
    widget.getActions().addAction(createSelectAction()); 

    //mouse-dragged, the event is consumed while mouse is dragged:
    widget.getActions().addAction(ActionFactory.createMoveAction()); 

    //mouse-over, the event is consumed while the mouse is over the widget:
    widget.getActions().addAction(createObjectHoverAction()); 

    mainLayer.addChild(widget);
    return widget;
}</pre>
                </li>

                <li>Install and try out the module again. As shown at the start of this section,
                    when you hover over a widget's label, or when you select it, its color will change. Also,
                    when you click on a label, you are able to edit its content.
                </li>

            </ol>

        </div>

        <p>Congratulations, you have completed your first Visual Library scene.</p>

        <div class="feedback-box"><a href="https://netbeans.org/about/contact_form.html?to=3&amp;subject=Feedback:%20Visual%20Library%20API%207.1%20Tutorial%20NetBeans">Send Us Your Feedback</a></div>


        <h2><a name="next_steps"></a>Next Steps</h2>
        <p>For more information
            on working with the Visual Library API, see:</p> 

        <ul>
            <li><a href="http://graph.netbeans.org/">Visual Library Project Page</a></li>
            <li><a href="http://graph.netbeans.org/documentation.html">Visual Library 2.0 - Documentation</a></li>
        </ul>

    </body>
    
</html>
