Identifiers


This chapter describes identifiers (variables) and their use within the Fire language.

Identifier is a general term given to named objects and variables within the system.

There are several different types of identifiers available, each with its own usage and function. Some identifier types are predefined by the system, but others, known generically as Structures, can be user-defined. Structures are analogous to Classes in other languages.

Typically, the predefined system identifiers contain useful constants, or monitor the current state of the modelling and language environment. Some have their values changed dynamically, others may have their values changed by the user. System identifiers may not be deleted or renamed.

User identifiers are created to hold user-information for use within other language statements. Once they have been declared and assigned values, they may be deleted or renamed at the user’s discretion.

Identifiers can be declared to have single values (known as scalars), or multiple values (known as arrays). Arrays may be of fixed or variable length. Currently, only one-dimensional arrays are permitted. Array indexing is 1-based, i.e. element 1 is the first. Some other languages have 0-based array indexing.

Identifier Types

The predefined identifier types are as follows:

Atable

Alias

Blob

Channel

Color

Command

Component

Cursor

Database

Entity

Epointer

Fillstyle

Filter

Font

Grid

Group

Hatchstyle

Label

Linestyle

Menupane

Message File

Rule

Numeric

Panel

Point

Projection

Rule

Stanza

String

Textstyle

Tile

Time

Window

Command

A command identifier is a variable whose value is a Fire language command. Command identifiers are system-defined, user-defined command identifiers are not permitted.

Atable

An atable (derived from the words Application Table) is a table used to hold identifier names, definitions and values. All identifiers must belong to an atable. An atable is analogous to a namespace in other languages.

There are two system atables: global and local.

User-defined atables, known as application atables, may be created to hold sets of identifiers related to specific applications or tasks. Such atables may be written to and retrieved from file so that an identifier environment may be reused in subsequent sessions.

Numeric

A numeric identifier is a variable with a numeric value. There are predefined system numeric identifiers recording the current state of system environment settings, or constant numeric values, e.g. pi.

User-defined numerics may be single values or arrays.

A range of numeric numeric functions is also available, each yielding a numeric value from user-given parameters. Users may create their own functions returning numeric values (scalar or array).

Unlike other languages, numerics have no precision attached to them and may record integers or floating-point values, interpreted according to context.

Point

A point identifier is a variable with a 3-D point value (x,y,z). There are predefined system point identifiers recording the current state of system environment settings.

User-defined points may be single values or arrays. The individual coordinates of a point may be accessed by reference to member elements.

A range of system point functions is available, each yielding a point value from user-given parameters. Users may create their own functions returning point values (scalar or array).

String

A string identifier is a variable with a text value. There are predefined system string identifiers recording the current state of system environment settings.

User-defined strings may be single values or arrays.

A range of system string functions is available, each yielding a string value from user-given parameters.

Users may create their own functions returning string values (scalar or array).

An important use of a string identifier is caret subsitution whereby a portion of a language statement can be replaced dynamically with a string value.

Time

A time identifier is a variable with a time and date value. There are predefined system time identifiers recording the current state of system environment settings.

User-defined times may be single values or arrays.

For attribute purposes, time identifiers can be treated as structures, and access to time attributes is provided via member reference.

A range of system time functions is available, each yielding a time value from user-given parameters.

Users may create their own functions returning time values (scalar or array).

Window

A window identifier is a variable which points to a window on the display. There are predefined a set of 255 system window identifiers, known as window slots, and user-defined window identifiers act as references to these system windows.

For attribute purposes window identifiers can be thought of as structures, and access to window attributes is provided via member reference.

Arrays of window identifiers are permitted.

Users may create their own functions returning window values (scalar or array).

Panel

A panel identifier is a variable containing the attributes of a sub-panel within a parent window or menu, e.g. a clickable button. Panels are not created directly, but result from the creation of windows with gui facilities, e.g. panel, table or tab windows.

For attribute purposes panel identifiers can be thought of as structures, and access to panel attributes is provided via member reference.

Menupane

A menupane identifier is a variable used to reference a set of a sub-panels within a window menu-bar or popup/pulldown menu. Menupanes are not created directly, but result from the creation of windows with gui facilities, e.g. a panel window.

For attribute purposes menupane identifiers can be thought of as structures, and access to panel attributes is provided via member reference.

Entity

An entity identifier is a variable which has a corresponding graphic form in the Fire's graphic database. It is also known as a graphic primitive. All entities are user-defined.

For attribute purposes, entity identifiers can be thought of as structures, and access to their attributes and geometry is provided via member reference.

Arrays of entity identifiers are permitted.

Epointer

An epointer identifier is a variable which points to an entity (graphic primitive) or user-defined graphic object (compound or gstructure) in the graphic database. Epointers do not themselves have associated graphics since the graphics are inherent in the primitives to which they point.

There are system epointer identifiers which, during modelling, point to currently active entities.

User-defined epointers may be single values or arrays.

For structure member access purposes, epointers are treated as the entity or graphic primitives to which they point.

Various system epointer functions are available, each yielding an epointer value from user-given parameters.

Users may create their own functions returning epointer values (scalar or array).

Group

A group identifier is a variable holding a classification (i.e. a set) of entities and graphic primitives. There are predefined system group identifiers which retain common entity classifications dynamically.

Entities may belong to any number of groups, although a group may be defined as a layer group, in which case an entity can only belong to one of such groups at any time.

User-defined groups may be created to classify user-specific combinations of entities.

Arrays of groups are not permitted.

Filter

A filter identifier is a variable holding selection criteria for graphic entity selection. There are predefined system filter identifiers, and user-defined filters may be created to record particular combinations of entity-attribute conditions, e.g. all entities with a red color.

Filters are used when dynamically selecting graphic primitives.

Arrays of filters are not permitted.

A range of filter system functions is available for entity selection.

Channel

A channel identifier is a variable which points to an input/output stream to communicate with a disc file or external process. There are a predefined set of system channel identifiers, known as channel slots, and user-defined channel identifiers act as references to these system channels.

For attribute purposes channel identifiers can be thought of as structures, and access to channel attributes is provided via member reference.

Arrays of channel identifiers are permitted.

Users may create their own functions returning channel values (scalar or array).

Database

A database identifier is a user-defined variable holding a link to an external proprietary database. Once communication has been established, database-specific commands may be sent to the database and values may be read from or written to it.

For attribute purposes database identifiers can be thought of as structures, and access to database attributes is provided via member reference.

Arrays of database identifiers are not permitted.

Blob

A blob identifier is a variable which points to a block of unstructured binary data. User-defined blobs may be single values or arrays.

A blob can be treated as an in-memory file and manipulations can be done on individual or blocks of bytes within.

A range of system blob functions is available, each yielding a blob value from user-given parameters. They enable blobs to be constructed from text, raw byte or file data.

Users may create their own functions returning blob values (scalar or array).

Projection

A projection identifier is a variable containing details of a Cartographic projection, i.e. a transformation from Longitude/Latitude into some Cartesian system. There is a system projection identifier maintaining the notion of a current projection.

User-defined projections may be created for specific transformations, with facilities for algorithm, earth model and datum shifts definition.

For attribute purposes projection identifiers can be thought of as structures, and access to projection attributes is provided via member reference.

Arrays of projection identifiers are permitted.

Message File

A message file identifier is a variable pointing to an external .mes file. By switching message files, locale-specific text messages can be displayed thereby enabling for example the same application to be run in different countries.

The source of system messages is defined by a predefined system message file identifier.

Arrays of message file identifiers are not permitted.

Color

A color is symbology identifier used by graphic primitives and other symbology-type identifiers. There are predefined system colors and users may create their own.

For attribute purposes, color identifiers can be thought of as structures, and access to color attributes, e.g. their red, green and blue components, is provided via member reference.

Arrays of user color identifiers are not permitted.

Font

A font is a symbology identifier linked to either a system resource (a system font) or to an external file containing font stroke details (a software font). Fonts are used by graphic primitives and other symbology-type identifiers. There are predefined system fonts and users may create their own.

For attribute purposes, font identifiers can be thought of as structures, and access to font attributes is provided via member reference.

Arrays of font identifiers are not permitted.

Linestyle

A linestyle is a symbology identifier containing a line pattern definition. Linestyles are used by graphic primitives and other symbology-type identifiers. There are predefined system linestyles and users may create their own.

For attribute purposes linestyle identifiers can be thought of as structures, and access to linestyle attributes is provided via member reference.

Arrays of linestyle identifiers are permitted and represent multiple-stroke line patterns.

Markerstyle

A markerstyle is a symbology identifier containing characteristics for the display of point entities (also known as nodes). Markerstyles are used by graphic primitives and other symbology-type identifiers. There are predefined system markerstyles and users may create their own.

For attribute purposes, markerstyle identifiers can be thought of as structures, and access to markerstyle attributes is provided via member reference.

Arrays of markerstyle identifiers are not permitted.

Textstyle

A textstyle is a symbology identifier containing characteristics for the display of text. Textstyles are used by graphic primitives and other symbology-type identifiers. There are predefined system textstyles and users may create their own.

For attribute purposes, textstyle identifiers can be thought of as structures, and access to textstyle attributes is provided via member reference.

Arrays of textstyle identifiers are not permitted.

Fillstyle

A fillstyle is a symbology identifier containing characteristics for the display of filled areas. Fillstyles can be used by graphic primitives and other symbology-type identifiers. There are predefined system fillstyles and users may create their own.

For attribute purposes fillstyle identifiers can be thought of as structures, and access to fillstyle attributes is provided via member reference.

Arrays of fillstyle identifiers are not permitted.

Hatchstyle

A hatchstyle is a symbology identifier containing a hatch pattern definition. Hatchstyles are used by graphic primitives and other symbology-type identifiers. There are predefined system hatchstyles and users may create their own.

For attribute purposes, hatchstyle identifiers can be thought of as structures, and access to hatchstyle attributes is provided via member reference.

Arrays of hatchstyle identifiers are permitted and represent multiple-stroke or cross-hatch patterns.

Tile

A tile is a symbology identifier linked to an external file containing details of a tile image. Tiles are used by graphic primitives and other symbology-type identifiers. There are predefined system tiles and users may create their own.

For attribute purposes, tile identifiers can be thought of as structures, and access to tile attributes is provided via member reference.

Arrays of tile identifiers are not permitted.

Cursor

A cursor is a symbology identifier linked to an external file containing details of a cursor image. Cursors are used during graphic input and are associated with windows. Users are expected to create their own. There are no system cursors available within the language.

For attribute purposes, cursor identifiers can be thought of as structures, and access to cursor attributes is provided via member reference.

Arrays of cursor identifiers are not permitted.

Grid

A grid identifier is a variable containing grid characteristics for a graphic window. A grid identifier cannot be created directly but is a system-supplied element of a window structure.

Component

A component identifier is a variable referencing an object external to the Fire system, e.g. an ActiveX component on a Windows system.

Depending on the type of external object, component attributes may be accessible via structure members.

Arrays of component identifiers are permitted.

Users may create their own functions returning channel values (scalar or array).

Rule

A rule identifier is a variable containing a set of conditional statements. When a rule is applied to an entity or graphic primitive, it enables the entity's symbology to set as a result of evaluating the rule's conditions.

All rule identifiers are user-defined. Arrays of rules are not permitted.

Stanza

A stanza identifier is a variable with a text value containing an executable sequence of commands. There are a few predefined system stanza identifiers.

User-defined stanzas may be single values or arrays.

Stanza identifiers may be executed and may have parameters passed to them, but in all other respects are treated as string identifiers.

Alias

An alternative name for another identifier, including an array element. There are predefined system aliases, and user-defined aliases are permitted. Arrays of aliases are not permitted.

Label

A label is used within a command macros to mark a control position subsequently referred to in a goto statement. Labels are defined automatically by their occurrence, and are not specifically declared.

User Types (Structures)

In addition to the above predefined identifier types, users may create their own identifier types. These are in the form of structures made up of combinations of other identifiers. The following types of structure are available for definition:

Structure

Gstructure

Compound

Dbstructure

Treenode

Structure

A structure is a combination of scalar or array identifiers. The structure members may be any combination of non-graphic identifiers.

A structure has no associated graphics.

Gstructure

A gstructure is a combination of scalar or array identifiers. The gstructure members may be any combination of non-graphic identifiers.

The gstructure itself has an associated graphic primitive, thus it may be treated like an entity identifier.

Compound

A compound is a combination of scalar or array identifiers. The members of a compound may be any combination of graphic and non-graphic identifiers (graphic identifiers comprise entities, gstructures and other compounds).

A compound entity has an associated graphic primitive of type compound which acts as a parent to all its members (its children), which may themselves have associated graphic primitives.

Graphically the compound is accessible as a single object, and its children are also individually accessible via member reference.

Dbstructure

A dbstructure is a combination of scalar identifiers. The structure is linked to a database identifier which itself is linked to an external data base, with the effect that references to structure members are references to column values in the external database. In effect the dbstructure is mapped to one or more rows in the external database.

Because the range of identifier types in most external data bases is limited, dbstructure members can currently only be of type: string, numeric and time. A dbstructure has no associated graphics.

Treenode

A treenode is a definition of behavior for a node in a tree window. By default treenodes have default behavior but a user treenode definition, extending the default behavior, specifies how a node reacts to events, e.g. selection, expansion, contraction etc.

A treenode can also be extended with scalar or array identifiers, similar to a structure.

Identifier Naming

An identifier name is any sequence of letters, decimal digits and an underscore, but the first character must be a letter or underscore. The name can be up to 48 characters in length.

Example names:

x
current_date
The_one_I_created_yesterday
_yellow_snow

Name definition and usage is case-insensitive.

Elements of structure-type identifiers are referenced by concatenating the parent and member names with a period separator:

win1.frame_color

which is an element of a window.

This may be applied to any depth:

duct23.previous.previous.origin

When an identifier from a particular atable of identifiers is required, it should be referenced with an atable prefix:

~mytable.nomad

is an identifier nomad in an atable mytable

This is discussed in more detail in the next section.

Atables

As mentioned already atables are namespaces. All identifiers, and functions, belong to an atable. The are 3 types: global, local and application. Global and local are system defined, application atables are user-defined.

Note: Although we haven't come across them yet, user-defined functions are sequences of commands similar to macros except that they reside in atables rather than as external files.

Global Atable

There is only one global atable, containing at all system identifiers created when Fire starts up. This atable cannot be deleted and is referenced by the name global.

Identifiers within the global atable are referred to as having global scope, and can be referenced anywhere in a program, i.e. from the keyboard and within any function or macro.

User identifiers can be added to the global atable by declaring their scope as global when they are declared:

numeric ~global.x

The above statement declares a numeric identifier x in the global atable. Note how the ~ character is used to precede the atable name. This could also have been achieved by the following two commands:

scope = global
numeric x

The first statement uses the system atable identifier scope. All new identifiers without an atable prefix are entered into the atable to which scope points. This by default is the current local identifier table, discussed in the next section, but may be set to any valid atable: global in our example.

Identifiers remain in the global atable until they are specifically deleted, using the delid command, or until the end of the program session.

It is good programming practice to keep the number of user identifiers in the global atable to a minimum. The global atable is useful for identifiers which are applicable to multiple applications running under one Fire session, but otherwise indicates less than elegant coding.

Local Atable(s)

There can be as many local atables as there are command macros and functions currently executing, but only one local atable can be active at any time, this being the one associated with the currently executing command frame (i.e. macro or function).

Local atables cannot be created or deleted by the user. This is done automatically at macro or function entry and exit time.

Reference to the current local atable is via the global atable identifier local, whose actual value will change as macros and functions are entered and exited.

Identifiers within a local atable are referred to as having local scope, and generally can be used only within the current command frame. There is an exception to this rule, and is discussed later.

All identifiers in a local atable are user defined, and can be created by a suitable declaration:

scope = local; # Usually redundant
numeric locx

or

numeric ~local.locx

In this example a numeric identifier locx has been declared and may be referred to anywhere in the current macro or function after its definition. However, as soon as another macro or function is entered, the current local atable is suspended and another is opened. The identifier locx then becomes unavailable to the language (known as out of scope) until a return is made from the child macro back to its parent macro.

Macro and function parameters have local scope and are entered into the local atable as soon as the command frame begins execution.

Consider an example

# dosqrt.cmd
# Declare arguments
args arg1=numeric, answer=&numeric
# Compute the answer
answer = sqrt(arg1)
return
# Declare two local numeric identifiers, then execute a
# macro passing the numerics as parameters.
numeric x=10, y
exec dosqrt(x,y)

In this Einsteinian macro (dosqrt.cmd), the identifiers arg1 and answer are automatically created as local numerics and can be referenced within the macro. The identifiers x and y cannot be referenced because they are only in the scope of the parent command frame.

Note how in this example x was passed by value (arg1=numeric), but y was passed by address (answer=&numeric). Passing a parameter by value means that its value is passed to the child macro, and if its value is changed (as arg1) within the child macro, the value of the parent identifier (in this case x) is unaffected. Passing a parameter by address means that its address is passed to the child macro, and if its value is changed (as answer) within the child macro, the value of the parent identifier (in this case y) is also changed. It is very important to understand this concept.

When macros are interrupted, the local scope is still that of the macro. This enables local identifier values to be examined and changed if necessary.

It was mentioned earlier that local scope is suspended when a child macro is executed. This can be suppressed by using a maintain scope switch on the exec command:

exec mymacro,-sc

This code will execute a macro called mymacro.cmd but will maintain the local scope of the parent command frame. This means that no new atable will be created within mymacro but all current local variables will still be available, i.e. they will remain in scope. However, it is not permitted to use this maintain scope method if parameters are passed to the child macro.

Application Atables

An application atable is the name given to a user-defined atable. Such atables are used to hold application specific definitions and constants, or project information.

There can be as many application atables as the user wishes up to a maximum of 4080. They are useful when multiple applications are running, since each application can have its own environment, protected from other applications.

An application atable is created by the atable command:

atable my_env

and its name has global scope. All atables have global scope.

New identifiers may then be added to the atable my_env in one of two ways,

numeric ~my_env.wall_height

or

scope = my_env
numeric wall_height

A common requirement is to store atable contents for future use. This can be achieved by the command:

unload my_env,my_env.ata

This will create a file my_env.ata. It may subsequently be retrieved (reloaded) by the following:

atable my_env,my_env.ata,-ov

The -ov switch tells Fire that you want to overwrite the atable my_env even if it already exists.

Search Path and Scope

New Identifiers

Whenever a new identifier without an atable prefix is created, the identifier is entered into the atable indicated by the system atable scope.. At the beginning of every command frame, scope has the value local. When the value of scope changes within a command frame, this change is valid only until an exit is made from the command frame, at which point the value of scope reverts to that of the parent command frame.

Unless the application is very complex and you have many new identifiers to add, we advise not changing the value of scope, but advise always to prefix new non-local identifiers with their atable name.

Existing Identifiers

Whenever an identifier without an atable prefix is encountered by the system, a maximum of four atables are searched to find its existence and properties. The search rules are as follows:

The local atable is searched.

The atable indicated by the system atable identifier scope is searched, unless the value of scope is local or global.

If the current command frame is a user function which belongs to an atable, that atable is searched, unless the atable has already been searched or is global.

If the current command frame is an object's callback procedure (aka an event handler), e.g. a window, channel, and the object has an associated search atable, that atable is searched, unless the atable has already been searched or is global. An objects' search atable is set by the -at at creation time.

The global atable is searched.

It is permitted for the user to add to local or application atables identifiers with the same names as system identifiers. This just means that while such identifiers remain in scope, their system equivalents are inaccessible. This should be avoided where possible because it tends to confuse the reader, as well as the author eventually.

Scope Restrictions

Some types of identifier can have any scope, i.e. they can reside in any type of atable : local, global or application, but others are prohibited from having local scope, defaulting to global if local is attempted. This is because of a necessity for such identifiers to be accessible to all aspects of the language in all situations, and for reasons of file-persistence.

Identifiers which can only have local scope are: label.

Identifiers which can only have global scope, i.e. can only reside in the global atable, are: atable, command, entity, gstructure object, compound object.

Identifiers which can only have global or application scope, i.e. cannot reside in a local atable, are: group, database, color, font, tile, linestyle, cursor, markerstyle, hatchstyle, textstyle, fillstyle.

Identifiers which can only have application scope, i.e. can only reside in an application atable, are user-type definitions.

All other identifiers can have any scope (i.e. local, global or application).

Identifier Arrays

An identifier array is indicated by square brackets [ and ] after the identifier name, e.g.

numeric xar[5]

declares a numeric array of length 5.

Arrays can be declared fixed or variable length:

numeric xar[5]  ;# fixed length of 5
numeric xar[]   ;#  variable length (initially 0)
numeric xar[-5] ;#  variable length (initially 5)

Array values are multiply assigned within hairpins < and >:

numeric xar[3] = <1, 1.5, 2 >

Individual array elements are referenced starting at 1:

tell xar[1]   ;# Print the first element of xar
tell xar[10]  ;# Print the 10th element of xar
tell xar[*]   ;# Print the last element of xar

Multiple array elements are referenced by a range using a colon ( : ) :

tell xar[3:6]  ;# Print elements 3 through 6 of xar
tell xar[1:*]  ;# Print all elements of xar
tell xar[]     ;# Print all elements of xar
tell xar       ;# Print all elements of xar
tell xar[*-2:*];# Print the last 3 elements of xar

The current length of an array can be referenced via the generic structure element alength:

numeric xar[] = <5,10,20>
tell xar.alength

This will print the value 3.

When array elements are given values, if the element goes beyond the declared bounds of a fixed array an error is recorded. Going beyond the bounds of a variable length array extends the array. Consider:

numeric xar[5]
xar[8] = 5

The above will produce an error, but consider:

numeric xar[]
xar[2] = 5

This will extend the array length to 2.

Variable length arrays can be truncated or shortened by removing unwanted elements, e.g.

numeric xar[-10]
delid xar[5:6]
delid xar[5:*]

This creates a variable length array of length 10, then deletes elements 5 and 6, the length is then 8. Finally elements 5 to the end are deleted leaving its length as 4. The last operation could also have been achieved by setting the identifier's array length:

xar.alength = 4

It is important to note that the command:

delid xar

will remove the whole array and the identifier itself.

Values can be inserted into variable length arrays, thereby extending or contracting their length by means of three operators := , =: , and :=: . Consider

numeric xar[-10] ;# Creates an array of variable length 10.
xar[4] := <5,6>  ;# Inserts two values before element 4
xar[4] =: <5,6>  ;# Inserts two values after element 4
xar[4:5] :=: <6,7,8> ;#Replaces two values by three new values

Array values can be block assigned by use of the set command:

numeric xar[10]
set xar = 5       ;# Sets all elements of xar to the value 5.
set xar[3:6] = 10 ;# Sets elements 3 through 6 to the value 10.
set xar[1:5] += 8 ;# Adds 8 to elements 1 through 5.

The swap operator <=> may be applied to arrays and array ranges:

numeric xar[3] = <1,2,3>, yar[3] = <4,5,6>
xar <=> yar 
# xar now has <4,5,6>, yar has <1,2,3>
xar[2:3] <=> yar[1:2]
# xar now has <4,1,2>, yar has <5,6,3>

The arrays being swapped must be of the same type and length.

Arrays may be passed to macros, procedures and functions by value or address. Value parameters are indicated as dummy parameters within the called module by the [ ] sequence. Consider

procedure print_array  ={
	args xpar = numeric[]
	tell xpar.alength
}
numeric xar[10]
print_array(xar[4:8])

In the above situation any change to array values within the procedure will have no effect on the values in the calling command frame because the array is passed by value.

Compare this to the following, where the array is passed by address indicated by an &

procedure parray {
	args xpar = &numeric
	tell xpar.alength
}
numeric xar[10]
print_array(xar[4:8])

In this situation any change to array values within the procedure will change the values in the calling command frame because the array is passed by address. An array of length 5 is passed.

Macros, functions and procedures are discussed in detail in later sections. Not all identifier types are permitted in array form. It is not permitted to create arrays of the following types: alias, atable, color, command, cursor, database, fillstyle, filter, font, grid, label, markerstyle, tile.

Null Identifier

The special system identifier null is used to "zeroize" an identifier, i.e. give it a default value. For most identifier types this value is 0 or empty text as appropriate, although zeroizing entities and structures requires more than just a value assignment. Suffice it to say that an assignment such as:

my_ident = null

reinitializes my_ident irrespective of the type of my_ident.

For most identifiers, the null value is the same as that given to the identifier when it was declared. The one exception to this rule is a time identifier, which on creation is set to the current time, but which when nullified becomes undefined. This is the only identifier type which can have an undefined state.

To reinitialize all elements of an array, the set command can be used, e.g.

numeric xar[10]
set xar = null

Identifier Text Output

Often there is a requirement to create a line of text made up of one or more identifier values, not only straight text (string values) but other values in text form, e.g. numeric, point, time and so on.

There is the concept of a message line which is such a combination of values. Many commands accept a message line as a parameter. In the syntax definitions of commands within the Reference Manual message line parameters are denoted by <message>.

The tell command, used in an example in the previous section to display identifier values , is a typical example of message line use,

tell "My value"  ;# Displays a string value
tell 45          ;# Displays a numeric value

A message line made up of several values can be defined by enclosure within hairpins, e.g.

numeric x = 45
tell <'X has the value’'x>

A space character is used to separate items.

The hairpins are not always necessary, and their presence will depend on the context in which the message line is being used. In the case of the tell command they are necessary because each message item constitutes one output line, and enclosing items within hairpins defines one message item. Thus multiple lines can be output in the same command:

numeric x = 45, y=50
tell <'X has the value',x>, <'Y has the value',y>

will display:
       X has the value 45
       Y has the value 50

but:

tell 'X has the value',x, 'Y has the value',y

will display:
       X has the value
       45
       Y has the value
       50

How each value type (numeric, string, point etc.) is formatted into a message item is explained in later sections when discussing individual identifier types in more detail.

Although not relevant to message lines, it is useful here to note the existence of a quick form of the tell command which should be used when no variable values are required:

!Output stuff

is functionally equivalent to:

tell 'Output stuff'

and executes faster.

Another common use of message lines is the definition of title text for menus:

menu {
    0: 'Application Menu'
    1: 'Start Application',symbs {
        # commands to execute 
    }
    2: 'Stop Application',symbs {
       # commands to execute
    }
}

The menu title message just contains a string constant, but both option title messages contain two message items, a string constant and a string identifier symbs whose value appears in the message. In this use of a message line, the hairpins are not required.


Prev Chapter    Next Chapter