4.1 Reporting and code generation
Reports, document generation and code generation can be
performed in MetaEdit+ with the Report Browser. This is a tool for accessing
information on the repository and transforming that either to various reports,
documents, checks, or to program code. With the tool you can also make your own
reports and queries on the repository.
In the following sections we describe reporting, document
generation, and code generation features in detail, including how to create your
own reports.
4.1.1 Reporting
MetaEdit+ offers
reporting functions to
check, review or document the design results. Some of the most useful reports
are pre-defined into MetaEdit+ and they can be used to study the design results
independently of the method in use. These method independent
reports are:
 | Object
List to describe all the objects included in the
graphs. |
 | Property
List to describe all the properties of the
objects. |
 | Dictionary
to print out all the objects with related definitions and documentation (taken
from the documentation field of the
object). |
 | Object
Connections to show how different objects are related to each
other. |
 | Checkings
to list the objects that have no relationships to other objects (orphans) and
the properties of objects that have not been
filled. |
 | Export
graph to HTML produces an HTML file for web browsers. It shows any diagram
representation of the graph as a GIF picture with a clickable image map, and
describes the objects in the graph with their relationships and subgraph links.
For more information on documentation generation see Section
4.1.2.
|
 | Export
graph to Word includes the same design information as the above HTML report, but
produces the file for Microsoft Word. This report uses a Word template called
MetaEdit+.dot. This template files is located in the same directory as the
MetaEdit+ program and it is used for styles, headers, cover page, and an
automatic macro which saves the report output to a Word document. The diagram is
represented as an editable vector graphic picture in
Word. |
In addition to these method-independent
reports MetaEdit+ provides several method-dependent reports. Examples of these
reports are flow-in/flow-out in Data Flow Diagram and transitions between states
in most State Transition Diagrams. Similarly, all code generation reports are
method-dependent (see Section
4.1.3).
Running reports
To use reporting:
1) | Select
any graph (e.g. ‘Sales system’) in a Graph Browser.
|
2) | Open the
pop-up menu with the right mouse button
(Figure 4-1) and select Reports |
Run....
|
 | You
can also access reporting from a Type Browser or from any of the editors through
Graph | Reports | Run.... |

Figure 4-1. Running reports for the graph.
After the
selection a dialog opens allowing you to select one of the reports that are
available. That report is then run on the graph you selected, and a Report
Output tool opens showing the text generated by the report
(
Figure 4-2). Alternatively, reports can
be generated directly to files: then a dialog will open listing the file names
and sizes. If a file could not be written to, the dialog will show the operating
system’s message stating why not, e.g. the directory did not exist. The
output intended for the file will be opened in a Report Output tool, named after
the desired file.

Figure 4-2. Example of a generated report.
In the
Report Output tool you can edit the generated report as
well as do cut, copy, paste, find and replace functions. These can be accessed
through the pop-up menu or
Edit menu.
The Report Output tool also
includes a menu for saving the report to a file, to
insert ASCII text from a file, and to print the report (for printing see also
Section
4.2).
To exit from the Report Output tool select
File |
Exit.
4.1.2 Documentation generation
Design information can be published from MetaEdit+ to other
applications, allowing you to review
designs and document
a project. MetaEdit+ has pre-defined project and graph documentation reports
which create
HTML
files for web
browsers and a .DOC document file for Microsoft Word.
Graph documentation
Graph documentation
reports are
available for all graphs. The graph documentation report documents a single
graph into a file. Graph documentation includes:
 | Information
about the graph name, graph status, personnel worked with the graph and
free-form graph documentation. These are retrieved from the graph’s
properties.
|
 | If
there is a diagram representation, a picture of the diagram. The picture in HTML
documentation is a GIF file with a clickable image map, and in Word it is an
editable vector graphic picture.
|
 | A
short table of contents of the graph, including object names and their
documentation. |
 | Detailed
descriptions of each object: its name, properties, links to other objects and
possible explosion or decomposition
links. |
 | The
Word document also includes a cover page with the status of the graph
documented, generation date of the report, author of file (from Word), and
document file name. |
To create documentation
for a graph:
1) | Select
any graph (e.g. ‘Sales system’) in a Graph Browser.
|
2) | Open the
pop-up menu with the right mouse button and select Reports |
Run.... |
3) | Choose
Export graph to HTML or to Word. |
Depending on
your choice the generated Graph documentation is opened in a web browser or
Word.
 | Note
that the generated files are stored in the main directory of
MetaEdit+. |
Project documentation
In addition to documenting individual graphs, documentation
can be created for the whole project. For this purpose the graphs which you want
to document for the project must be defined with a Project Model (see
Figure 4-3). Project
Model
is a specific modelling technique for illustrating
the subprojects, graphs belonging to a certain (sub)project, and relationships
between graphs. Subprojects can be decomposed into other project
models.
 | Note
that the Project Model is not created automatically, but must be created and
maintained manually. You can thus have several Project Models to generate
different sets of documentation, e.g. one for the analysis phase and another for
the design phase. |

Figure 4-3. An example of a Project Model.
As with graph
documentation, the project documentation reports can produce HTML files or a
Word document file. The Export to HTML and Export to Word documentation reports
create the following information:
 | The
Project name and description, its current status, the project manager, and the
personnel involved, with their contact details. All this information is
retrieved from the project model’s own
properties. |
 | If
there is a diagram representation, a picture of the diagram. For HTML
documentation the picture is a GIF file with a clickable image map. For Word it
is an editable vector graphic embedded in the
document. |
 | A
dictionary of the graphs belonging to the Project Model, along with their
descriptions. Each graph name forms a hyperlink to its detailed documentation,
generated with the corresponding Graph Documentation report. For HTML, each
graph is generated to a separate HTML file; for Word, each is generated as part
of the whole project file. |
Hence, project
documentation creates documentation pages for a selection of graphs for the
whole project. The Word document file
also includes a cover page with document information,
and a table of contents.
To create project documentation:
1) | Create
a Project Model
graph. |
2) | Enter
information about the project (such as name, personnel etc.) to the graph
properties.
|
3) | Open the
Project Model as a
diagram. |
4) | Add
new graph objects to the Project Model, attaching existing graphs as their
properties (see Section 2.3.1 for
Property Dialog
functions). |
 | You
may also create relationships between graph objects and define
subprojects. |
5) | Create
project documentation by selecting Graph | Reports | Run... from the menu
bar of the editor. |
As a result, the report
creates documentation files and opens them in a web-browser
(
Figure 4-4) or in Word, if your system
supports this.

Figure 4-4. Browsing HTML-based project documentation.
4.1.3 Code generation
Code generation
works similarly to
other reports described in the previous section. In MetaEdit+ code generation
reports are predefined for C++
,
Smalltalk
, CORBA IDL, Java
,
Delphi
and
SQL
. Depending on the method used and languages to be
generated various constructs can be produced automatically.
Basically, code generation is always dependent on the
method used and the language to be generated. The following table summarises
code generation alternatives: it describes which languages can be generated from
which methods, using predefined reports. You can of course add new reports to
extend the code generation abilities. More detailed descriptions of each report
can be found from the comments at the start of that report’s definition.
You may look at these in a Report Browser as described in Section
4.1.4.
Method
|
Language
|
Entity Relationship Diagram
|
SQL
|
Object-Oriented Design
|
C++, CORBA IDL, Delphi, Java, Smalltalk
|
Object-Oriented Analysis and Design
|
C++, CORBA IDL, Delphi, Java, Smalltalk
|
Object Modelling Technique
|
C++, CORBA IDL, Delphi, Java, Smalltalk
|
Fusion
|
C++, CORBA IDL, Delphi, Java, Smalltalk
|
Moses
|
C++, CORBA IDL, Delphi, Java, Smalltalk
|
Unified Modeling Language
|
C++, CORBA IDL, Delphi, Java, Smalltalk
|
Object-Oriented Systems Analysis
|
C++, CORBA IDL, Delphi, Java, Smalltalk
|
OODLE
|
C++, CORBA IDL, Delphi, Java, Smalltalk
|
As with reporting, code generation is performed with the
Report Browser. Code generation is available from the Graph | Reports |
Run... menu that is available in all editors, as well as through the
Report | Run... menu in Graph and Type Browsers when a graph is selected.
For example, to generate Smalltalk definitions from object-oriented
designs:
1) | Choose
a Class Diagram in Graph
Browser. |
2) | Open
the pop-up menu with the right mouse
button. |
3) | Select
Reports | Run....
|
4) | Select
‘Smalltalk’ from the dialog that appears
(Figure 4-5). |

Figure 4-5. Selecting reports to be run.
As a result of the
selection Smalltalk class definitions are written into files. One file is
created for each class. The resulting code is illustrated in
Figure 4-6, opened in Notepad.
Similarly, C++ class and function definitions can be generated
(
Figure 4-7). These include .h and .cpp
files.

Figure 4-6. Part of the generated Smalltalk code.

Figure 4-7. Generated C++ definitions.
In line with the
other customisable metaCASE features of MetaEdit+, code generation can be
extended to cover other languages or methods. Thus, as with normal reports,
specifications of code generation can be modified with the Report Browser. This
function is explained in the following
section.
4.1.4 Report Browser: making your own reports
 | See
also the Menu Reference, Section
7.9. |
Instead
of running pre-defined reports you can also modify them or even create your own
reports. This can be done with the Report
Browser
. The Report Browser is a
special text editor for creating, editing and managing reports. It allows you to
view, edit and run available report definitions, and to create new reports for
your needs.
An empty Report Browser window is shown in
Figure 4-8.

Figure 4-8. Report Browser.
Components of a Report Browser
The
Report Box, the left list
box, offers a list of reports that are defined for the currently selected Graph
type. The centre list box is the
Concept Box,
where you can select what to view in the right list box: Object, Relationship or
Role types of the current method, or report language code templates. The right
list box, called the
Choice Box, provides a list
of concepts of the type that has been selected in the Concept Box. Select any of
the listed items to paste it and its type identifier (
. for Object,
: for Property,
> for Relationship or
~ for Role) into
the
Editing Area. Under the list boxes is the editing area, which shows
the currently selected report code. The editing area supports the normal editing
operations (cut, copy, paste, select, find, replace) and font
formatting.
In the following we shall describe the features and
functions of the Report Browser.
Opening Report Browser
1) | Select
any graph in a Graph Browser.
|
2) | Open the
pop-up menu with the right mouse button.
|
3) | Select
Reports | Create
|
 | You
can also access reporting from a Type Browser or from any editor through
Graph | Reports | Create. |
As a
result of the operation a Report Browser opens as illustrated in
Figure 4-8. Based on the graph type of
the graph selection, the Report Browser is opened for making reports on that
particular graph type. For example in
Figure 4-8 the Report Browser is open
for graphs of type ‘Class Diagram [UML]’. Similarly, if a Report
Browser is opened from an editor the graph type is automatically changed to the
that of the graph in the editor.
To manage report
definitions for other methods use
Report | Change Graph Type... in the
Report Browser.
Making a new report definition
Reports are always defined specific to a given method, because
the report uses the data structures of the method in its definition. The
following report definition is appropriate only for Data Flow Diagrams, thus for
testing it you should have a Report Browser opened for Data Flow
Diagrams.
To make a new report select
Report | New.... You
will be asked for the name of the new report
(
Figure 4-9).
Enter a name like
‘Test’ and press
OK.

Figure 4-9. Entering a name for the new report.
Reports
whose names
begin with '_' are hidden from the list shown
to the user when he chooses
Report | Run... elsewhere than the Report
Browser (e.g. from a Diagram Editor). Names like this should thus be used for
reports that are intended only for use as subreports, e.g. if they assume that
the report output is already going to a file, or that something other than a
graph is already in the report stack. If necessary, a user can still see and
even run these reports elsewhere by holding down shift while choosing
Reports
| Run....
The contents of the editing area are now:
Report 'Test'
endreport
The meaning of these lines is described in the
following subsections, but now we can continue the definition. The next step is
to select the operation and object type that we will be operating on. To proceed
with report definition, put the cursor on the blank (second) line:
1) | Select
‘Templates’ in the Concept Box (with the left
mouse button).
|
2) | Double click
‘ForEach’ from the Choice box.
Or |
2) | Select
‘ForEach’ from the Choice Box with the left mouse button and select
Insert from the Choice Box pop-up menu.
|
The contents of the editing area are
now:
Report 'Test'
foreach objectType
{
}
endreport
After operation
selection we proceed by selecting an object type. Because we are interested in
Process objects:
1) | Select
the text objectType in the Editing
Area. |
2) | Click
‘Object’ in the Concept
Box. |
3) | Select
‘Process’ and choose Insert from the Choice Box pop-up menu.
Alternatively you can double click ‘Process’ from the Choice
Box. |
As a result of the selection the text
.Process is added into the
Editing Area, replacing the selected
objectType text. Notice that the
concept was automatically preceded with its type character, the dot (others
being : for property, > for Relationship and ~ for
role).
The next step is to add the desired operations for listing
the objects into the report. The operations to be performed for each object of
the specified type (in this case Process) are placed within the curly brackets.
To print out the name of each Process:
1) | Place
the mouse cursor after the opening
bracket. |
2) | Select
‘Object’ from the Concept
Box. |
3) | Select
Process from the Choice
Box. |
4) | Select
Properties from the Choice Box pop-up
menu. |

Figure 4-10. Selecting a property type.
As a result of the
operation a dialog (
Figure 4-10) opens
showing all the properties that a Process has.
1) | Select
Process name from the
list. |
After this operation the report
specification looks like this:
Report 'Test'
foreach .Process
{:Process name;
}
endreport
Notice that every statement in a report should
be followed by ‘;’ and this character has thus also be added at the
end of the process name.
Running reports
Now, if we think that this report might work, we can test it
by running it from the menu bar, by selecting Report | Run.... This
operation runs the report specification against a graph of the current type: you
will be asked to specify which graph in a dialog. We can run and adjust the
report until we are satisfied.
We notice however, that we need to add some strings into
the output and that we should separate the output for each Process onto a new
line. We should also list the ID of the
Process. To make these modifications we
extend the report definition as below:
Report 'Test'
foreach .Process
{ 'Process : ';
:Process ID;
' ';
:Process name;
newline;
}
endreport
By selecting
Report | Run... from the
menu again we can see what the result looks like
(
Figure 4-11): see Section
2.3.4 for more information about the
Report Output Tool.

Figure 4-11. An example of a report output.
Editing report definitions
To view and edit existing report definitions select any of the
reports from the Report Box. After the operation the report definition will be
shown in the Editing Area. If your current report has been modified and not
saved, you will be prompted whether to save it first.
 | A
new report only appears in the Report Box when it has been saved.
|
You can continue making the
‘Test’ report. For example, the next major improvement for the
‘Test’ report could be adding for each Process a list of the Stores
that it uses. After this modification the new report definition should look
like:
Report 'Test'
foreach .Process
{ 'Process : ';
:Process ID;
' ';
:Process name;
newline;
'Used data stores: ';
newline;
do >().Store
{ ' ';
:Name;
newline;
}
newline;
}
endreport
Note the ‘
do
{}’ loop about half way down the report, which takes the
current object (from the outer ‘
foreach
.Process {}’ loop) and ranges over all its
relationships
‘
>’ of any type
‘
()’ connected to a Store
object ‘
.Store’, using the
final element, i.e. the stores, as the basis for the
‘
do {}’ loop.
When we run the modified report, the result looks like
Figure 4-12 below.

Figure 4-12. Report output for use of data stores.
Font formatting in reporter
Layout of reports can be modified by formatting fonts
according to their type (underline, italic or bold) and size. Font formatting
options are applied by selecting the item and pressing one of the shortcut keys
(
Help | Shortcut keys, see also Section
2.3.4).
Saving report definitions
Report definitions can be saved with the menu selection
Report | Save.... If the current report has been modified but not saved
and Report Browser is closed or another report definition is chosen from the
Report Box the tool will ask whether the report definition should be
saved.
Writing reports to files
Report | Write to file... lets you write the current
contents of the editing area to a text file. Note that only the text is saved,
not any formatting applied with shortcut keys.
Reading reports from files
Report | Read from file... lets you read an existing
report definition from a text file. When reading a report from a file, you are
normally warned if the report would have the same name as an existing report.
Also, the report is not actually saved, but is left in the text area, ready to
be saved explicitly or via a prompt when you select another report or close the
Report Browser.
If you wish to read many reports, this can be
time-consuming, so there is a way to select a set of reports with a wildcard,
and read them all in, saving them without further interaction with users. In
Windows 95, the system file dialogs do not allow selection of wildcard path
names, so you must bypass the system file dialog by holding shift down when
selecting
Read from file.... You can then give a directory name and *.rep
wildcard, e.g. ‘C:\reports\*.rep’ and a dialog will open showing all
report files in that directory. By choosing
Select all you can read all
of the reports in at once: note that this will overwrite any existing reports of
the same name.
4.1.5 Report Definition Language
Reports are specified in MetaEdit+ using the Report Definition
Language
in the Report Browser. This section lists and
describes the constructs of the Report Definition Language. For those familiar
with other similar languages, the main extension is the use of the prefixes
‘
.>~:’ to distinguish
Objects, Relationships, Roles and Properties.
Report keywords must always be preceded by white space
(space, tab, or carriage return) and followed by a semicolon, ‘;’.
An exception is the chaining of type names, where the type prefix
‘.>~:’ is sufficient to
end the previous type name, e.g.
‘>Specialization~Generalization;’
Report header
The report header is the name of the report:
report 'data flow report'
Report end
Reports must always end with an endreport statement:
endreport
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.
Properties of non-properties in containing loops can be
accessed by immediately following the property statement with a level number and
a semicolon:
:property local name;level number;
E.g.
:Documentation;1; refers to the
Documentation property of the object in the loop immediately containing the
current loop. If no level number is specified the default is 0, the current
loop. Note that outside of all loops the current element is the graph the report
is being run on.
Object type
An object type can be specified by its name prefixed with
‘.’
.object type name;
Relationship type
A relationship type can be specified by its name prefixed with
‘>’
>relationship type name;
Role type
A role type can be referred to by its name prefixed with
‘~’
~role type name;
Type
The name of the current element’s type can be printed to
the report output by:
type;
An example of what is printed for a type is
‘Process’.
Identifier
The identifier of the current element is printed by:
id;
IDs in containing loops can be accessed by
following the id; with a level number:
id;level number;
E.g.
id;1; refers to the ID of the loop
immediately containing the current loop. If no level number is specified the
default is 0, the current loop. Note that outside of all loops the current
element is the graph the report is being run on.
Newline
New lines are inserted in the report output by the keyword
newline.
newline;
String
The strings to be reported appear as they are written inside '
single quote marks. To print a ' in a string write it twice '' (2 single
quotes).
'This will appear as it is here'; newline;
'This will ''appear'' a little different';
would appear
like this in the report output:
This will appear as it is here
This will 'appear' a little different
Line end
Each statement within the report body (except the foreach
construct) ends with a semicolon. Note that several statements can be written on
the same line by separating them with semicolons
‘;’, and preferably a space
after the semicolon.
()
All instances of a 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 e.g. 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.
Foreach loop
The main control structure of a report loop is the foreach
loop. In a typical report the foreach clause selects all elements of the
specified type to be operated on. The elements are processed in alphabetical
order of type name then identifying property.
A foreach loop can only be used when the current element
is a graph: this is always the case at the start of a report. The element to be
looped over cannot be a property: only objects, roles and relationships are
appropriate. The operations that will be performed on the retrieved elements are
written within the {}.
As well as selecting the type of the elements, a foreach
loop can specify that a property of the element must obey a condition with the
optional ‘where’
keyword.
foreach .objType where :propName = 'value'
{ /* Operations for the elements */ }
If clause
Conditional clauses contain a condition and parts that are
performed if the condition is true (‘then’ part) and parts that are
performed if the condition is false (‘else’ part). The
‘not’ keyword can be used before the condition to reverse it. There
is a possibility to test whether an unary condition is true or false by giving
only the value to test and leaving the condition
(= or
<>) and other value out. In this
case the true part will be performed if the first value is not nil: unary tests
too can be reversed by adding not
before the value. Boolean properties can also be used as unary tests.
if :property = 'value'
then /* operations on true-part */
else /* operations on false-part */
endif
Do loop
The do loop iterates over a set of things that are related to
the current element. The do loop can also be performed over properties. For
example one could query the relations of the objects like this:
do >relType
{/* Operations for relationships */ }
The dowhile clause
differs from the do clause in that it exits immediately from the loop when the
last retrieved thing has been reported. Thus any actions in the
‘tail’ of the loop are left off the report. This should be used for
avoiding trailing strings (e.g. commas or spaces) between the items to be
reported, e.g.
do .Process {id; ', ';} produces “1.0, 1.1, 1.2,”
dowhile .Process {id; ', ';} produces “1.0, 1.1, 1.2”
Note
that the do and dowhile loops differ from foreach in that foreach is used when
the current element is a graph, and loops over all instances of the specified
type in the graph, and do and dowhile are used when the current element is an
object, role or relationship, and loop over only those instances of the
specified type that are attached to the current element. As mentioned above, do
and dowhile can also be used when the current element is a collection property,
and then they loop over all elements in that collection.
Special do and dowhile loops also exist for lines of text
properties, decompositions and explosions: see below.
Lines of text properties
The do and dowhile loops can also be used for iterating over
the lines of a property of data type Text. Note that the currently selected
element should be the object, role, relationship of graph which has the text
property, and the operator for the do loop should be the local name of the text
property. The loop is then executed as many times as there are lines in that
text property: use id; to output the
current line.
do :property
{ id; }
This is particularly useful for translating line
breaks in a property into character sequences which represent a new line or
paragraph in a particular formatting language, such as RTF or HTML. The example
below adds a <BR> tag in HTML; the newline; is simply for clearer
formatting of the HTML source.
do :Documentation
{ id; '<BR>'; newline; }
It can also be used for
programming languages where a comment is preceded by a certain character
sequence, and is not allowed to extend over more than one line. The first
example below shows how to make sure each line of a comment is preceded by the
comment sequence, and the second example strings all the lines together into one
long line, effectively replacing each carriage return with a space.
do :Documentation
{ '// '; id; newline; }
'// ';
dowhile :Documentation
{ id; ' '; }
Explosions
The links of an object into related explosion graphs can be
followed through the ‘explosions’ keyword. The related explosion
graphs can be operated on in the loop, e.g.:
do explosions {
' ';
id;
newline;
}
makes a list of related explosion graphs. A foreach
loop could also be used within the loop: it would then operate on the explosion
graphs.
Decompositions
The link of an object into a decomposition graph can be
followed through the ‘decompositions’ keyword. The related
decomposition graph can be operated on in the loop, e.g.:
do decompositions {
' ';
id;
newline;
}
makes a list of related decomposition graphs. A foreach
loop could also be used within the loop: it would then operate on the
decomposition graph.
Note that a do decomposition loop’s contents are
executed at most once: an object may only have one decomposition. The loop
structure is however used to maintain the similarity with explosions.
Subreport
Instead of defining a single large report you can separate the
report into several subreports, which can call each other using the Subreport
template:
subreport; 'name'; run;
All output from commands
between subreport and run is directed to a temporary stream, where it builds up
the name of the report to run. Normally, the only output would be a single
string, e.g. ‘name’ above, but any report commands can be used, e.g.
the name of the current element’s type could be used to call different
reports.
The subreport to run is looked up from the type of the
current graph (in the closest containing loop), through the supertypes of that
graph type to the Graph metatype. Thus graph types can override reports in their
supertypes, by defining a report with the same name. In particular, you can
override the pre-defined reports from the Graph metatype by defining a report of
the same name in a graph type. For example you could add a new ‘Export
graph to HTML’ report to Class Diagram to output more detail for the
individual Attributes and Operations of each class.
Ask
During reporting user-entered data can be prompted for using
the Ask template:
prompt; 'Enter a string'; ask;
This shows the user a
dialog with the specified prompt text. The text the user enters is then output
to the report output, useful for example to name generated files.
Write
Report output is normally opened in a Report Output tool, from
which it can be printed, saved to a file, or copied and pasted to another
application. Report output can also be redirected to a file, or even different
parts of the output can be written to different files:
filename; 'name'; write;
/* report output commands here */
close;
‘Name’ can include strings and
keywords, all of whose output goes to building up the filename to be used. A
useful command here is prompt...ask, which opens a dialog asking the user for a
string, and then outputs that string: this then is used in building up the
filename, just as any output from any other keyword:
filename;
prompt;
'Enter file to output ';
id;
' to?';
ask;
write;
/* report output commands here */
close;
The ‘Name’ string can also include
information about directory paths. The Close keyword returns the output to the
previous file or the screen. All commands between write and close thus output to
the file specified.
Output to files is only executed at the end of the whole
report; a dialog will show how many characters were written to each file. If an
error occurs trying to write to a file, the dialog will show the error message
and output for that file will be redirected to its own Report Output
tool.
Append
Append works like write with the exception that it does not
overwrite the old file if it already exists, but rather adds the generated
report to the end of the file.
filename; 'name'; append;
close;
To write several times to a file in a report, when
it is impractical to keep the file open, you can open it the first time with
write (to overwrite any old version), and use append each time you open the file
later in the report.
Print
The diagram for the current graph can be exported to the
printer, a PostScript file, a PICT file or a GIF file using the Print
template:
filename; 'name'; print;
If the filename is lpt1,
the diagram is printed directly to the default printer. If the filename ends in
.pct or .gif, a PICT or GIF file is generated showing the whole diagram at 100%.
Otherwise, the output is of the whole diagram scaled to fit on one page, and to
the 'report' printer, whose settings can be edited by selecting print with shift
held down from any editor. If the ‘report’ printer is of type
PostScript (not of type Host), the printer diagram will be saved as a PostScript
file with the name given; in this case the output is only sent to the printer if
the ‘Print script’ string setting of the ‘report’
printer is not empty.
Again, all output between filename and print keywords goes
to building up the filename to export to.
For HTML files MetaEdit+ automatically creates imagemap
information to make GIF pictures clickable. When a filename;...;print; command
is executed in the report, if the stream that is open after the print; command
is a file named *.htm*, an image map will be written to that stream at the
current position. That position should thus not be inside any other tag; other
than that, it may be anywhere in the body of the HTML file.
The image map includes a polygon entry for each object,
based on the connection points of that object. The href parameter for each entry
is generated by an automatically run subreports, _imagemap_href. The default for
this is in Graph, and makes the link point to a local target named with the oid
of the object, e.g. #16_2876. It also uses onMouseOver and onMouseOut to display
the name and type of that object in the browser status bar. If the name or type
contains an apostrophe, Netscape 4.5 gives a JavaScript error: 4.6 and Internet
Explorer 4.0 do not have this problem.
You may override the default _imagemap_href report in your
own Graph types by making reports there with the same name. For instance,
Project Model defines its own such report. Add the USEMAP="#filename.gif"
parameter to the IMG tag: the filename.gif should be exactly the same as the SRC
parameter, preceded by #.
External
External commands, e.g. compilers, can be executed using the
External template:
external; 'javac '; id; '.java'; execute;
Again, all
output between external and execute keywords goes to building up the command to
be executed. For example, the command above would run a Java compiler on a .java
file named after the current object, e.g. ‘javac BallGame.java’.
Commands are executed immediately they are encountered, and the report continues
executing without waiting for the command to return. Thus compiler commands
should be executed at the end of a report, in principle via a batch or shell
file which waits for the user to press a key — report output to files is
only actually performed after the last report command.
4.1.6 Syntax
STRING | : "'"
CHAR* "'"
where CHAR is any character from the ASCII
character set; a ' character must be
doubled |
|
NAME | : {"a"|"b"|..|”z”|
"A"|..|"Z"|"0"|..|"9"|"_"|"-"}*
If NAME contains a space, the whole name should
have a ";" after it, or one of ".>~" forming the start of the next element in
a
chainClause |
|
report | : headersection
clause*
endsection |
|
headersection | : "report
"
STRING |
|
endsection | : "endreport" |
|
clause | : literal |
| | newlineClause |
| | simpleClause |
| | comment |
| | loop |
| | ifClause |
| | fileClause |
| | subreportClause |
| | askClause |
| | printClause |
| | externalClause |
| | chainOutputClause |
|
literal | : STRING
";
" |
|
newlineClause | : "newline;
" |
|
simpleClause | : {"id;"
| "type;" | "oid;"}
[{"0"|..|"9"}* ";
"] |
|
comment | : "/*"
COMMENTTEXT "*/"
where COMMENTTEXT may be any ASCII characters,
but may only contain the following text sequences in legally closed pairs: ',
if, else, endif, {, }, /*,
*/ |
|
loop | : {"do"
| "dowhile"} argClause
"{" clause*
"}" |
| | "foreach"
graphEltClause
["where" propClause "=" STRING]
"{" clause*
"}" |
|
ifClause | : "if
" condition "then " clause* ["else " clause*]
"
endif" |
|
condition | : ["not
"]
{argClause | literal}
[comp {argClause |
literal}] |
|
comp | : "="
|
"<>" |
|
fileClause | : "filename;
"
clause*
{"write; " | "append; "}
clause*
"close;
" |
|
subreportClause | : "subreport;
" clause*
"run;
" |
|
askClause | : "prompt;
" clause*
"ask;
" |
|
printClause | : "filename;
" clause*
"print;
" |
|
externalClause | : "external;
" clause*
"execute;
" |
chainOutputClause | : [chainClause]
propClause ";
" |
|
chainClause | : chainClause
chainClause |
| | graphEltClause
|
| | propClause
|
|
propClause | : ":"
NAME |
|
graphEltClause | : objClause
|
| | relClause
|
| | roleClause
|
|
objClause | : "."
typeChoiceClause |
|
relClause | : ">"
typeChoiceClause |
|
roleClause | : "~"
typeChoiceClause |
|
typeChoiceClause | : NAME |
| |
"()" |
| |
"( " NAME {" | " NAME}*
")" |
|
argClause | : chainClause
";
" |
| | decompClause
";
" |
| | explClause
";
" |
|
decompClause | : "decompositions" |
|
explClause | : "explosions" |