The Interfaces Sock

Trevor Nash

Melvaig Software Engineering Limited

Table of Contents

1. Writing Java Code
Core Language
The class element
The useClass element
The method element
Command line processing
GUIs
Layouts
Border Layout
Grid Layout
Menus and Commands
Commands
Toggles
Menu Structure
Cursors
Drop site

Chapter 1. Writing Java Code

Core Language

The class element

java:class declares a Java class to be produced from this specification. @id uniquely identifies this class within the document, and is different to any other id - specifically it must not collide with any m21:file @id. If the actual class name is different to the value of @id then @name is present. java:interface is similar.

For Object java:class replacement:java:class|java:interface
<sk:replace match="java:class|java:interface">
   <xsl:variable name="javaSrc" select="saxon:if(@src, @src, './src')"/>
   <xsl:variable name="class" select="string(saxon:if(@name, @name, @id))"/>
   <xsl:variable name="path" select="           concat($javaSrc,           concat('/',           concat(translate(@package, '.', '/'),           concat(saxon:if(@package, '/', ''),           concat(@name,           '.java')))))"/>
   <java:class-or-interface name="{$class}" id="{@id}" package="{@package}"/>
   <sk:file id="{@id}" name="{$path}">
       <sk:text-file>
<sk:sink id="copyright"/>
<xsl:if test="@package">package <xsl:value-of select="@package"/>;</xsl:if>
<sk:sorted-sink id="import" select="unique">
import <sk:copy/>;<sk:separator test="last"><xsl:text>
</xsl:text></sk:separator></sk:sorted-sink>
<xsl:text>
</xsl:text>
<sk:sink id="classHeader"/>
<xsl:if test="@qualifiers"><xsl:value-of select="concat(@qualifiers, ' ')"/></xsl:if>
<sk:sink id="classQualifiers"><sk:copy/><xsl:text> </xsl:text></sk:sink>
<!-- class or interface -->
<xsl:value-of select="local-name()"/>
<xsl:text> </xsl:text>
<xsl:value-of select="$class"/>
   <sk:sorted-sink id="classExtends" select="unique">
      <sk:separator test="first" value=" extends "/>
      <sk:separator test="not first" value=", "/>
      <sk:copy/>
   </sk:sorted-sink>
   <sk:sorted-sink id="classImplements" select="unique">
      <sk:separator test="first" value=" implements "/>
      <sk:separator test="not first" value=", "/>
      <sk:copy/>
   </sk:sorted-sink>
    <xsl:text> </xsl:text>{
<sk:sink id="constructors"/>
<sk:sink id="methods"/>
}
       </sk:text-file>
   </sk:file>
   <xsl:apply-templates/>
</sk:replace>
<sk:object name="java:interface">
   <!-- implementation handled by java:class -->
</sk:object>

Here are some values we need to use later.

For Object java:class.name generate:
<sk:generate>
      <sk:object-reference name="class" type="'java:class-or-interface'" object.id="@id"/>
      <xsl:value-of select="$class/@name"/>
   </sk:generate>
For Object java:class.qualified-name generate:
<sk:generate>
      <sk:object-reference name="class" type="'java:class-or-interface'" object.id="@id"/>
      <xsl:if test="$class/@package">
         <xsl:value-of select="$class/@package"/><xsl:text>.</xsl:text>
      </xsl:if> 
      <xsl:value-of select="$class/@name"/>
   </sk:generate>

Here are abbreviations for class inheritance. The elements may be used inside a java:class or separately.

For Object java:extends replacement:
<sk:replace>
   <sk:source sink.id="classExtends" file.id="{saxon:if(@id,@id,../@id)}">
   <xsl:choose>
      <xsl:when test="@name">{@name}</xsl:when>
      <xsl:when test="@class.id">[{@class.id}]</xsl:when>
   </xsl:choose>
   </sk:source>
</sk:replace>
For Object java:implements replacement:
<sk:replace>
   <sk:source sink.id="classImplements" file.id="{saxon:if(@id,@id,../@id)}">
   <xsl:choose>
      <xsl:when test="@name">{@name}</xsl:when>
      <xsl:when test="@class.id">[{@class.id}]</xsl:when>
   </xsl:choose>
   </sk:source>
</sk:replace>

The useClass element

When used with the id attribute this refers to a class declared in the same specification. In the browser we will see the identifier (in a later release we should be able to get the full name).

For Object java:useClass generate:java:useClass[@id]
<sk:generate match="java:useClass[@id]">
   <java:class.name id="{@id}"/>
   <sk:source sink.id="import" file.id="_parent">
      <java:class.qualified-name id="{@id}"/>
   </sk:source>
</sk:generate>
For Object java:useClass presentation:java:useClass[@id]
<sk:presentation match="java:useClass[@id]">
<db:wordasword>[<xsl:value-of select="@id"/>]</db:wordasword>
</sk:presentation>

When used with the name attribute this refers to a class from the class library. If there is more than one class with the given name then the hint attribute should be used to supply enough of the package name to uniquely identify the class required. Example: to use java.lang.reflect.Array you might say <java:useClass name="Array" hint="lang"/> in order to avoid confusion with the interface java.sql.Array.

For Object java:useClass generate:java:useClass[@name]
<sk:generate match="java:useClass[@name]">
   <xsl:value-of select="@name"/>
   <java:importClass name="{@name}" hint="{@hint}"/>
</sk:generate>
For Object java:useClass presentation:java:useClass[@name]
<sk:presentation match="java:useClass[@name]">
<db:wordasword><xsl:value-of select="@name"/></db:wordasword>
</sk:presentation>
For Object java:importClass generate:java:importClass[@name]
<sk:generate match="java:importClass[@name]">
   <sk:declare>
      <xsl:key name="java:class-by-name" match="class" use="@name"/>
      <saxon:function name="java:findClass">
         <xsl:param name="name"/>
         <xsl:for-each select="document('javaClassLibrary.xml')">
            <saxon:return select="key('java:class-by-name', $name)"/>
         </xsl:for-each>
      </saxon:function>
   </sk:declare>
   <xsl:variable name="hint" select="@hint"/>
   <sk:source sink.id="import" file.id="_parent">
      <xsl:variable name="classInfo" select="             java:findClass(@name)      [contains(ancestor::package/@name, $hint)]"/>
      <xsl:choose>
         <xsl:when test="count($classInfo)=1">
            <xsl:for-each select="$classInfo">
               <xsl:value-of select="../@name"/>.<xsl:value-of select="@name"/>
            </xsl:for-each>
         </xsl:when>
         <xsl:when test="count($classInfo)=0">
            <xsl:message><xsl:value-of select="@name"/>:- class not listed in library</xsl:message>
         </xsl:when>
         <xsl:otherwise>
            <xsl:message><xsl:value-of select="@name"/>:- needs hint to make unique</xsl:message>
         </xsl:otherwise>
      </xsl:choose>
   </sk:source>
</sk:generate>

java:import is used with third party code. It generates import statements for a list of names and/or ids but does not contribute to the generated program text.

For Object java:import replacement:
<sk:replace>
   <xsl:for-each select="saxon:tokenize(@names)">
      <java:importClass name="{.}"/>
   </xsl:for-each>
</sk:replace>

The method element

This will produce JavaDoc and signature at the same time. Not implemented yet.

Command line processing

Define information for command line options to be used to write code and documentation.

Put java:getOptions where the options are to be analysed: usually at the start of main. String[] args will be referenced. The content of this element provides code to be executed when a non-option argument is found.

For Object java:getOptions replacement:
<sk:replace>
        int argIndex = 0;
        String arg;
        boolean parseError = false;
<sk:sink id="java:optDecls"/>

        while (argIndex<args.length) {
            arg = args[argIndex];
            // check for options here
            if (arg.startsWith("-")) {
<sk:sink id="java:optChecks"/>
                System.err.println ("Illegal option: '"+arg+"'");
                parseError = true; argIndex++; continue;
            }
<sk:sink id="java:argChecks"/>
<sk:instantiate/>
            argIndex++;
        }

</sk:replace>

Write java:helpText when the option help text is to be output.

For Object java:helpText replacement:
<sk:replace>
            System.err.println (
                  "\nUsage:\n\n"+
                  "<sk:sink id="java:progName"/><sk:sink id="java:progSynopsis"/>\n"+
   <sk:sink id="java:progSummary"/>
   <sk:sorted-sink id="java:argHelp"/>
                  "\n"+
   <sk:sink id="java:progDescription"/>
                  "\n\n");
</sk:replace>

Put java:manPage to define a file to contain the documentation (a DocBook RefEntry). If there is no such element then no documentation is produced.

For Object java:manPage replacement:
<sk:replace>
   <sk:file id="{@file.id}-doc" name="{@name}">
      <db:refentry>
         <db:refmeta>
            <db:refentrytitle><sk:sink id="java:progName"/></db:refentrytitle>
         </db:refmeta>

         <db:refnamediv>
            <db:refname><sk:sink id="java:progName"/></db:refname>
            <db:refpurpose><sk:sink id="java:purpose"/></db:refpurpose>
         </db:refnamediv>

         <db:refsynopsisdiv>
         <db:cmdsynopsis>
            <db:command><sk:sink id="java:progName"/></db:command>
            <sk:sink id="java:progSynopsis"/>
         </db:cmdsynopsis>
         </db:refsynopsisdiv>
         <db:refsect1><db:title>Description</db:title>
            <db:para>
                <sk:sink id="java:progDescription"/>
            </db:para>
            <db:para>
            <db:table frame="all"><title>Arguments</title>
               <db:tgroup cols="3" align="left" colsep="1" rowsep="1">
                  <db:colspec colname="short" colwidth="1*"/>
                  <db:colspec colname="long" colwidth="1*"/>
                  <db:colspec colname="desc" colwidth="5*"/>
                  <db:thead>
                     <db:row>
                        <db:entry>Short Form</db:entry>
                        <db:entry>Long Form</db:entry>
                        <db:entry>Description</db:entry>
                     </db:row>
                  </db:thead>
                  <db:tbody valign="top">
                     <sk:sorted-sink id="java:argDescs"/>
                  </db:tbody>
               </db:tgroup>
            </db:table>
            </db:para>
         </db:refsect1>
      </db:refentry>
   </sk:file>
</sk:replace>

To give information about the program use java:progDescription.

For Object java:progDescription replacement:
<sk:replace>
   <sk:source sink.id="java:progDescription" file.id="{@file.id}">
      <sk:instantiate select="java:shortDesc"/>
   </sk:source>
   <sk:source sink.id="java:progDescription" file.id="{@file.id}-doc">
      <sk:instantiate select="java:longDesc"/>
   </sk:source>
   <sk:source sink.id="java:purpose" file.id="{@file.id}-doc">
      <sk:instantiate select="java:purpose"/>
   </sk:source>
   <sk:source sink.id="java:progSynopsis" file.id="{@file.id} {@file.id}-doc">
      <sk:instantiate select="java:synopsis"/>
   </sk:source>
   <sk:source sink.id="java:progName" file.id="{@file.id} {@file.id}-doc"><xsl:value-of select="@name"/></sk:source>
</sk:replace>

To define an option use java:option.

For Object java:option replacement:
<sk:replace>
   <sk:source sink.id="java:optDecls" file.id="{@file.id}">
        boolean <xsl:value-of select="@name"/> = false;
   </sk:source>
   <sk:source sink.id="java:optChecks" file.id="{@file.id}">
                if (arg.equals("-<xsl:value-of select="@short"/>")||arg.equals("--<xsl:value-of select="@long"/>")) {
      <xsl:choose>
         <xsl:when test="java:optArgSpec">
                    if (argIndex+<xsl:value-of select="count(java:optArgspec)"/>>args.length) {
                        System.err.println ("Missing argument for "+arg);
                        parseError = true;
                    } else {
            <xsl:for-each select="java:optArgSpec">
                        arg = args[++argIndex];
               <sk:instantiate select="java:argCheck"/>
            </xsl:for-each>
                    }
         </xsl:when>
         <xsl:otherwise>
                   <xsl:value-of select="@name"/>=true;
         </xsl:otherwise>
      </xsl:choose>
                   argIndex++; continue; }
   </sk:source>
   <sk:source sink.id="java:argHelp" file.id="{@file.id}" key="{@sequence}">
                  "  -<xsl:value-of select="@short"/>
                  <xsl:for-each select="java:optArgSpec/@name">
                     <xsl:text> </xsl:text>
                     <xsl:value-of select="."/>
                  </xsl:for-each>
                  <xsl:text>\n"+
                  "  --</xsl:text>
                  <xsl:value-of select="@long"/>
                  <xsl:for-each select="java:optArgSpec/@name">
                     <xsl:text> </xsl:text>
                     <xsl:value-of select="."/>
                  </xsl:for-each>
                  <xsl:text/>\n"+
                  "         <xsl:value-of select="java:shortDesc"/>\n"+
   </sk:source>

   <sk:source sink.id="java:argDescs" file.id="{@file.id}-doc" key="{@sequence}">
      <db:row>
         <db:entry>-<xsl:value-of select="@short"/>
            <xsl:for-each select="java:optArgSpec/@name">
               <xsl:text> </xsl:text>
               <xsl:value-of select="."/>
            </xsl:for-each>
         </db:entry>
         <db:entry>--<xsl:value-of select="@long"/>
            <xsl:for-each select="java:optArgSpec/@name">
               <xsl:text> </xsl:text>
               <xsl:value-of select="."/>
            </xsl:for-each>
         </db:entry>
         <db:entry>
            <sk:instantiate select="java:longDesc"/>
         </db:entry>
      </db:row>

   </sk:source>
   
</sk:replace>

GUIs

For Object java:GUI replacement:
<sk:replace>
   <java:class id="{@id}" name="{@name}" package="{@package}" qualifiers="public">
      <java:extends name="JPanel"/>
   </java:class>
   <sk:source file.id="{@id}" sink.id="methods">
      <xsl:text>    </xsl:text><xsl:value-of select="@name"/>
      <xsl:text> (</xsl:text>
      <sk:sink id="gui-constructor-parameters"/>
      <xsl:text>) {
    </xsl:text>
      <sk:sink id="gui-constructor"/>
      <xsl:text>
        frame = new </xsl:text>JFrame
        <xsl:text>("</xsl:text><xsl:value-of select="@frameTitle"/>
        <xsl:text>");
    </xsl:text>
      <sk:sink id="gui-init"/>
      <xsl:text>
        frame.getContentPane().add("Center", this);

        frame.pack ();
</xsl:text>
      <sk:sink id="gui-post-pack"/>
      <xsl:text>

        frame.setVisible(true);
    }
</xsl:text>
    private JFrame frame;
   </sk:source>
</sk:replace>

Layouts

Border Layout

These objects use BorderLayout and BoxLayout to arrange things like option buttons.

For Object java:borderLayout replacement:
<sk:replace>
   <sk:source sink.id="gui-init" file.id="{@gui.id}">
        setLayout (new BorderLayout());
       <xsl:for-each select=".//java:vBox">
          <xsl:variable name="name" select="@name"/>
        Box
        <xsl:text> </xsl:text>
        <xsl:value-of select="$name"/>
        <xsl:text> = </xsl:text>Box
        <xsl:text>.createVerticalBox();
        </xsl:text>
          <xsl:if test="@topMargin">
             <java:vStrut box="{$name}" size="{@topMargin}"/>
          </xsl:if>
          <xsl:apply-templates select="*" mode="java:Box">
             <xsl:with-param name="name" select="$name"/>
          </xsl:apply-templates>
          <xsl:if test="@bottomMargin">
             <java:vStrut box="{$name}" size="{@bottomMargin}"/>
          </xsl:if>
       </xsl:for-each>
       <xsl:apply-templates select="*" mode="java:borderLayout"/>
       </sk:source>
    <sk:declare>
       <xsl:template match="java:item" mode="java:Box">
          <xsl:param name="name"/>
             <xsl:variable name="rowBox" select="concat($name, position())"/>
        Box
        <xsl:text> </xsl:text>
        <xsl:value-of select="$rowBox"/>
        <xsl:text> = </xsl:text>Box
        <xsl:text>.createHorizontalBox();
        </xsl:text>
             <xsl:if test="../@leftIndent">
                <java:hStrut box="{$rowBox}" size="{../@leftIndent}"/>
             </xsl:if>
        <xsl:value-of select="$rowBox"/>
        <xsl:text>.add (</xsl:text>
        <xsl:value-of select="@item"/>
        <xsl:text>);
        </xsl:text>
        <java:hGlue box="{$rowBox}"/>
        <xsl:value-of select="$name"/>
        <xsl:text>.add (</xsl:text>
        <xsl:value-of select="$rowBox"/>
        <xsl:text>);
        </xsl:text>
       </xsl:template>
       <xsl:template match="java:*[@item]" mode="java:borderLayout">
        <xsl:text>add (</xsl:text>
        <xsl:value-of select="@item"/>
        <xsl:text>, </xsl:text>
        BorderLayout
        <xsl:text>.</xsl:text>
        <xsl:value-of select="local-name()"/>
        <xsl:text>);
        </xsl:text>
       </xsl:template>
       <xsl:template match="java:*[*/@name]" mode="java:borderLayout">
        <xsl:text>add (</xsl:text>
        <xsl:value-of select="*/@name"/>
        <xsl:text>, </xsl:text>
        BorderLayout
        <xsl:text>.</xsl:text>
        <xsl:value-of select="local-name()"/>
        <xsl:text>);
        </xsl:text>
       </xsl:template>
    </sk:declare>
    </sk:replace>

A vertical strut.

For Object java:vStrut replacement:
<sk:replace>
        <xsl:value-of select="@box"/>
        <xsl:text>.add (</xsl:text>
        Box
        <xsl:text>.createVerticalStrut (</xsl:text>
        <xsl:value-of select="@size"/>
        <xsl:text>));
        </xsl:text>
</sk:replace>

A horizontal strut.

For Object java:hStrut replacement:
<sk:replace>
        <xsl:value-of select="@box"/>
        <xsl:text>.add (</xsl:text>
        Box
        <xsl:text>.createHorizontalStrut (</xsl:text>
        <xsl:value-of select="@size"/>
        <xsl:text>));
        </xsl:text>
</sk:replace>

Vertical glue.

For Object java:vGlue replacement:
<sk:replace>
        <xsl:value-of select="@box"/>
        <xsl:text>.add (</xsl:text>
        Box
        <xsl:text>.createVerticalStrut ());
        </xsl:text>
</sk:replace>

Horizontal glue.

For Object java:hGlue replacement:
<sk:replace>
        <xsl:value-of select="@box"/>
        <xsl:text>.add (</xsl:text>
        Box
        <xsl:text>.createHorizontalGlue ());
        </xsl:text>
</sk:replace>

Grid Layout

This lays out a set of GUI components in a rectangular grid.

For Object java:gridLayout replacement:
<sk:replace>
   <sk:source sink.id="gui-init" file.id="{@gui.id}">

        GridBagLayout lmgr = new GridBagLayout ();
        GridBagConstraints constraint = new GridBagConstraints ();
        setLayout (lmgr);

        constraint.weightx = 0.5;
        constraint.fill = GridBagConstraints.HORIZONTAL;
   <xsl:for-each select="java:row">
      <xsl:variable name="y" select="position()-1"/>
      <xsl:for-each select="java:widget">
         <xsl:variable name="x" select="position()-1"/>
        constraint.gridx = <xsl:value-of select="$x"/>;
        constraint.gridy = <xsl:value-of select="$y"/>;<xsl:text/>
         <xsl:if test="@span">
        constraint.gridwidth = <xsl:value-of select="@span"/>;<xsl:text/>
         </xsl:if>
        lmgr.setConstraints (<xsl:value-of select="@name"/>, constraint);
        add (<xsl:value-of select="@name"/>);

      </xsl:for-each>
   </xsl:for-each>
   </sk:source>
</sk:replace>

Menus and Commands

This section tries to do menus plus buttons in a scheme where both may be provided to carry out the same task.

Commands

For Object java:GUIcommand replacement:
<sk:replace>
   <sk:source sink.id="methods" file.id="{@gui.id}">
    private void <xsl:value-of select="@name"/>SetEnabled (boolean enable) {
        <sk:sink id="{concat(@name, 'Enable')}"/>
    }

    private void <xsl:value-of select="@name"/>Action () {
        <sk:sink id="{concat(@name, 'Action')}"/>
    }
    </sk:source>
    <xsl:apply-templates/>
</sk:replace>
For Object java:enableCommand replacement:
<sk:replace><xsl:value-of select="@name"/>SetEnabled (true);</sk:replace>
For Object java:disableCommand replacement:
<sk:replace><xsl:value-of select="@name"/>SetEnabled (false);</sk:replace>
For Object java:GUIcommand/java:menuEntry replacement:
<sk:replace>
   <sk:source sink.id="methods" file.id="{../@gui.id}">
        JMenuItem
        <xsl:text> </xsl:text>
        <xsl:value-of select="../@name"/>MenuEntry = new <xsl:text/>
        JMenuItem ("<xsl:text/>
        <xsl:value-of select="../@label"/>", <xsl:text/>
        KeyEvent.VK_<xsl:text/>
        <xsl:value-of select="@key"/><xsl:text>);
        </xsl:text>
   </sk:source>
   <sk:source sink.id="{concat(../@name, 'Enable')}" file.id="{../@gui.id}">
        <xsl:text>
        </xsl:text><xsl:value-of select="../@name"/><xsl:text>MenuEntry.setEnabled (enable);
        </xsl:text>
   </sk:source>
   <sk:source sink.id="gui-init" file.id="{../@gui.id}">
        <xsl:value-of select="../@name"/>MenuEntry.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent ae){
                <xsl:value-of select="../@name"/>Action();
            }
        });
   </sk:source>
</sk:replace>

For Object java:button replacement:
<sk:replace>
   <sk:source sink.id="methods" file.id="{../@gui.id}">
    JButton
    <xsl:text> </xsl:text>
    <xsl:value-of select="../@name"/>
    <xsl:text>Button
            = new </xsl:text>
    JButton
    <xsl:text>("</xsl:text>
    <xsl:value-of select="../@label"/>
    <xsl:text>");
    </xsl:text>
   </sk:source>
   <sk:source sink.id="gui-init" file.id="{../@gui.id}">
      <xsl:text>
        </xsl:text><xsl:value-of select="../@name"/><xsl:text>Button.setMnemonic('</xsl:text>
        <xsl:value-of select="@key"/>
        <xsl:text>');
</xsl:text>
   </sk:source>
   <sk:source sink.id="{concat(../@name, 'Enable')}" file.id="{../@gui.id}">
        <xsl:text>
        </xsl:text><xsl:value-of select="../@name"/><xsl:text>Button.setEnabled (enable);
        </xsl:text>
   </sk:source>
   <sk:source sink.id="gui-init" file.id="{../@gui.id}">
        <xsl:value-of select="../@name"/>Button.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent ae){
                <xsl:value-of select="../@name"/>Action();
            }
        });
   </sk:source>
</sk:replace>

For Object java:action replacement:
<sk:replace>
   <sk:source sink.id="{concat(../@name, 'Action')}" file.id="{../@gui.id}">
       <xsl:apply-templates mode="copy"/>
   </sk:source>
</sk:replace>

Toggles

A toggle is something that has a boolean state. In GUI terms this could be a radio button or check box - currently we only do check boxes. A radio button will use the same element but be enclosed in a flag group element.

For Object java:GUItoggle replacement:
<sk:replace>
   <sk:source sink.id="methods" file.id="{@gui.id}">
    private void <xsl:value-of select="@name"/>SetEnabled (boolean enable) {
        <sk:sink id="{concat(@name, 'Enable')}"/>
    }

    private void <xsl:value-of select="@name"/>Set () {
        <sk:sink id="{concat(@name, 'Set')}"/>
    }

    private void <xsl:value-of select="@name"/>Clear () {
        <sk:sink id="{concat(@name, 'Clear')}"/>
    }
    </sk:source>
    <sk:instantiate/>
</sk:replace>
For Object java:GUItoggle/java:menuEntry replacement:
<sk:replace>
   <sk:source sink.id="methods" file.id="{../@gui.id}">
        JCheckBoxMenuItem
        <xsl:text> </xsl:text>
        <xsl:value-of select="../@name"/>MenuEntry = new <xsl:text/>
        JCheckBoxMenuItem ("<xsl:text/>
        <xsl:value-of select="../@label"/><xsl:text>");
        </xsl:text>
   </sk:source>
   <sk:source sink.id="{concat(../@name, 'Enable')}" file.id="{../@gui.id}">
        <xsl:text>
        </xsl:text><xsl:value-of select="../@name"/><xsl:text>MenuEntry.setEnabled (enable);
        </xsl:text>
   </sk:source>
   <sk:source sink.id="gui-init" file.id="{../@gui.id}">
        <xsl:value-of select="../@name"/>MenuEntry.setMnemonic(<xsl:text/>
        KeyEvent.VK_<xsl:text/>
        <xsl:value-of select="@key"/><xsl:text>);
        </xsl:text>
        <xsl:value-of select="../@name"/>MenuEntry.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent ae){
                if (<xsl:value-of select="../@name"/>MenuEntry.getState()) {
                   <xsl:value-of select="../@name"/>Set();
                } else {
                   <xsl:value-of select="../@name"/>Clear();
                }
            }
        });
   </sk:source>
</sk:replace>

For Object java:checkBox replacement:
<sk:replace>
   <sk:source sink.id="methods" file.id="{../@gui.id}">
    JCheckBox
    <xsl:text> </xsl:text>
    <xsl:value-of select="../@name"/>
    <xsl:text>CheckBox
            = new </xsl:text>
    JCheckBox
    <xsl:text>("</xsl:text>
    <xsl:value-of select="../@label"/>
    <xsl:text>");
    </xsl:text>
   </sk:source>
   <sk:source sink.id="gui-init" file.id="{../@gui.id}">
      <xsl:text>
        </xsl:text><xsl:value-of select="../@name"/><xsl:text>CheckBox.setMnemonic('</xsl:text>
        <xsl:value-of select="@key"/>
        <xsl:text>');
</xsl:text>
   </sk:source>
   <sk:source sink.id="{concat(../@name, 'Enable')}" file.id="{../@gui.id}">
        <xsl:text>
        </xsl:text><xsl:value-of select="../@name"/><xsl:text>Button.setEnabled (enable);
        </xsl:text>
   </sk:source>
   <sk:source sink.id="gui-init" file.id="{../@gui.id}">
        <xsl:value-of select="../@name"/>Button.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent ae){
                <xsl:value-of select="../@name"/>Action();
            }
        });
   </sk:source>
</sk:replace>

For Object java:onSet replacement:
<sk:replace>
   <sk:source sink.id="{concat(../@name, 'Set')}" file.id="{../@gui.id}">
       <sk:instantiate/>
   </sk:source>
</sk:replace>
For Object java:onClear replacement:
<sk:replace>
   <sk:source sink.id="{concat(../@name, 'Clear')}" file.id="{../@gui.id}">
       <sk:instantiate/>
   </sk:source>
</sk:replace>

Menu Structure

This defines the logical structure of a menu bar.

For Object java:menuBar replacement:
<sk:replace>
   <sk:source sink.id="gui-init" file.id="{@gui.id}">
        JMenuBar menuBar = new JMenuBar();
    <sk:instantiate/>
        <xsl:text>frame.setJMenuBar (menuBar);
        </xsl:text>
   </sk:source>
   <sk:declare>
      <xsl:template match="java:menuBar" mode="java:varName">
         <xsl:text>menuBar</xsl:text>
      </xsl:template>
   </sk:declare>
</sk:replace>

A menu.

For Object java:menu replacement:
<sk:replace>
    <xsl:variable name="var" select="concat(@name, 'Menu')"/>
        JMenu
        <xsl:text> </xsl:text>
        <xsl:value-of select="$var"/>
        <xsl:text> = new </xsl:text>
        JMenu
        <xsl:text> ("</xsl:text><xsl:value-of select="@label"/><xsl:text>");
        </xsl:text>
    <xsl:if test="@key">
        <xsl:value-of select="$var"/>
        <xsl:text>.setMnemonic (</xsl:text>
        KeyEvent
        <xsl:text>.VK_</xsl:text>
        <xsl:value-of select="@key"/>
        <xsl:text>);
        </xsl:text>
    </xsl:if>
    <sk:instantiate/>
        <xsl:apply-templates select=".." mode="java:varName"/><xsl:text>.add(</xsl:text>
        <xsl:value-of select="$var"/><xsl:text>);
        </xsl:text>
    <sk:declare>
      <xsl:template match="java:menu" mode="java:varName">
         <xsl:value-of select="@name"/><xsl:text>Menu</xsl:text>
      </xsl:template>
    </sk:declare>
</sk:replace>
For Object java:menu/java:item replacement:
<sk:replace>
        <xsl:apply-templates select=".." mode="java:varName"/>
        <xsl:text>.add(</xsl:text>
        <xsl:value-of select="@item"/>
        <xsl:text>MenuEntry);
        </xsl:text>
</sk:replace>
For Object java:menu/java:separator replacement:
<sk:replace>
        <xsl:apply-templates select=".." mode="java:varName"/>
        <xsl:text>.addSeparator();
        </xsl:text>
</sk:replace>

Cursors

For Object java:waitCursor replacement:
<sk:replace>frame.setCursor (Cursor.getPredefinedCursor (Cursor.WAIT_CURSOR));</sk:replace>

For Object java:defaultCursor replacement:
<sk:replace>frame.setCursor (Cursor.getPredefinedCursor (Cursor.DEFAULT_CURSOR));</sk:replace>

Drop site

Makes an object a drag and drop target, by implementing DropTargetListener. The subject class identified by @id should be some descendant of a GUI object such as a JLabel.

For Object java:dropTarget replacement:
<sk:replace>
   <java:implements id="{@id}" name="DropTargetListener"/>
   <sk:source sink.id="methods" file.id="{@id}">
   private DropTarget dropTarget =
      new DropTarget (this, this);

   /**
    * Called when a drag operation has encountered the DropTarget.
    * 
    */

   public void dragEnter (DropTargetDragEvent event) {
      <sk:sink id="dnd.dragEnter"/>
   }

   /**
    * The drag operation has departed the DropTarget without dropping.
    *
    */

   public void dragExit (DropTargetEvent event) {
      <sk:sink id="dnd.dragExit"/>
   }

   /**
    * Called when a drag operation is ongoing on the DropTarget.
    * 
    */

   public void dragOver (DropTargetDragEvent event) {
      <sk:sink id="dnd.dragOver"/>
   }

   /**
    * The drag operation has terminated with a drop on this DropTarget.
    * 
    */

   public void drop (DropTargetDropEvent event) {
      <sk:sink id="dnd.drop"/>
   }

   /**
    * Called if the user has modified the current drop gesture.
    * 
    */

   public void dropActionChanged ( DropTargetDragEvent event ) {
      <sk:sink id="dnd.dropActionChanged"/>
   }

   </sk:source>
</sk:replace>