5.3.2 Design element access and output commands
Commands in this category access the design elements and
retrieve information from them for the
output.
Property
A property can be specified by its local name prefixed by
‘:’
:property local name;
Note that this is the local
name of the property in the current non-property type, not the name of the
actual property type. Note that the local name here is terminated with a
semicolon because the name contains spaces.
The property command can be used as a direct output
command, writing the value of the property to the current output stream. It can
also be used as a condition in
if
statements. If the property data type is a NonProperty or a Collection, it can
also be used as the argument to
do or
dowhile
loops.
Level number
Properties of non-properties in the containing loops can be
accessed by immediately following the property statement with a level number and
a semicolon:
:property local name;levelNumber
E.g.
:Documentation;1 refers to the
Documentation property of the object in the loop immediately containing the
current loop.
The level number can be used as a suffix on many other
commands that output information abou the current element, e.g.
id. If no level number is specified the
default is 0, the current loop. Note that outside of all the loops the current
element is the element (normally a graph) the generator is being run on.
Negative level numbers can also be used: –1 is the element (normally a
graph) the generator is being run on, –2 the element of the outermost
loop, etc. In generators in symbols, the stack is pre-loaded with the graph and
the element whose symbol is being displayed. In identifier
generators
, the stack is pre-loaded with the element
whose identifier is being generated.
Object type
An object type can be specified by its name prefixed with
‘.’
.object type name;
An object type can be used as the
argument to a foreach,
do or
dowhile loop. It can also be used as a
condition in if statements. An object
type can only be used as an output command as part of a chain output
command.
Relationship type
A relationship type can be specified by its name prefixed with
‘>’
>relationship type name;
A relationship type can
be used as the argument to a foreach,
do or
dowhile loop. It can also be used as a
condition in if statements. A
relationship type can only be used as an output command as part of a chain
output command.
Role type
A role type can be referred to by its name prefixed with
‘~’
~role type name;
A role type can be used as the
argument to a foreach,
do or
dowhile loop. It can also be used as a
condition in if statements. A role type
can only be used as an output command as part of a chain output
command.
Port type
A port type can be referred to by its name prefixed with
‘#’
#port type name;
A role type can be used as the
argument to a do or
dowhile loop. It can also be used as a
condition in if statements. Please note
that it is not possible to navigate to an object, relationship or role from a
port instance. This is due to the fact that the same port instance is used in
each object instance, and thus it may be associated with several objects,
relationships or roles. There is no way to make a distinction between them from
within the generator, which only knows that it is ‘in’ a port in a
certain graph. Navigating to a port thus forms a dead end for further
navigation. Instead, navigate to the role, and from there query or generator the
information you need from the port, then navigate to the object.
()
All types of a given metatype (Object, Property, Role or
Relationship) can be denoted by () instead of a type name. This is especially
useful when you want to loop over, say, all objects, regardless of their type,
e.g.
.()
The brackets can also contain one or more type
name strings, separated by |. A type name can contain wildcards, e.g.
.(Class* | Package)
will run for all Classes,
Class-&-Objects, and Packages.
If a type name string is immediately preceded by a caret
^, instances matching that type string are disallowed, e.g.
.(St* | ^State [UML])
will run for instances of
Start or Stop, but not State [UML] or Note.
Chain output commands
Quite often, navigating with do loops would produce exactly
one element (or none), whose name we want to output. For example, navigating
from a UML Class to its superclass (with no multiple inheritance), to output its
name:
do ~Specialization
{ do >Generalization [UML]
{ do ~Superclass
{ :Class name;
}
}
}
In such cases, it is possible to use a shortcut syntax,
the chain output command:
~Specialization>Generalization [UML]~Superclass:Class name;
A
chain output command is thus a chain of type commands, ending in a property
output command. There must always be only one element satisfying the chain
conditions up to the property command. For this reason, a generator using this
structure will show a warning to the metamodeler when run from the Generator
Editor (but not to modelers, when run from elsewhere).