[ Home | Prev | Next ]

Chapter 4


The UserTalk Language

This chapter provides an overview of the UserTalk scripting language. For detailed information, see DocServer.

Repetition, Decisions

UserTalk includes many language "structures" for repetition (looping) and decisions (branching). Each structure consists of one or more "blocks", i.e. a keyword line and one or more lines indented underneath (i.e. at a lower level). A keyword line contains one or more reserved words (such as "for" or "if") and usually user variables, data or expressions. This section presents a brief overview; see DocServer for details. Note that these examples are just script fragments; they may assume that certain local variables have been defined or specific verbs exist earlier in the script (e.g. to open a file). As you review the examples, remember that most UserTalk verbs follow the category.name format. Verbs will be covered in detail later in this chapter.

A for loop repeats a specified number of times, incrementing a variable each time.

for i = 1 to 5
   msg (i)
   clock.waitSeconds (1)

A for loop can also iterate through every element of a list, assigning the loop variable to each element in turn.

for element in myList
   dialog.alert (element)

A while loop repeats as long as a certain condition is true.

while not file.endOfFile (f)
   msg (file.readLine (f))

A fileloop structure iterates through every item in a folder or on a disk (or even every disk), assigning the loop variable to each element in turn. See DocServer for a description of the optional "depth" parameter.

fileloop (f in path)
   msg (file.fileFromPath (f))

A loop structure repeats forever (sort of). To exit from a loop, use "break". Although a loop and break sometimes looks easier, many software experts recommend rewriting your script to use "while" or "for" instead of "loop". Frontier leaves the choice up to you!

loop
   msg (i)
   i = i + 1
   if i > 5
      break

An if decision structure executes the block of one or more indented lines if the expression is true.

if answer > 6
   msg ("Big family!")

An if structure may include an else block. It will be executed if the expression is false.

if answer > 6
   msg ("Big family!")
else
   msg ("Not such a big family!")

A case structure executes the block of code that corresponds to the value of the expression. The else block is optional. Note that more than one value (or expression) may lead to the same action.

case letter
   "a"
   "e"
      msg ("Vowel")
   "b"
      msg ("Consonant")
else
   msg ("This example isn't very thorough.")

Some languages include an else if extension to the standard if structure. Frontier's case statement can be used to create an equivalent.

case true
   temperature > minimum
      dialog.alert ("Too cold.")
   temperature < maximum
      dialog.alert ("Too hot.")
else
   dialog.notify ("Delicious porridge.")

Error Handling

The first way to handle errors is to avoid them! UserTalk includes many verbs that can be used to check possible error-causing situations before the error arises. For example, before you call file.delete, you should call file.exists to ensure you are not attempting to delete a file that isn't there.
if file.exists (f)
   file.delete (f)

There are two sorts of errors that a running script may encounter: some verbs return "false" if they fail, others halt the script. For verbs that return true or false, the "if" statement is typically used to catch errors (often in conjunction with the "not" keyword).

if file.open (f)
   theLine = file.readLine (f)

In the previous example, the sole purpose of the "if" line was to check a certain condition -- it didn't perform any action (only the indented line peformed an action). This example is different; it will attempt to perform a certain action, returning false if it failed. The differences between these two types of error handling is subtle and will become more clear with experience.

To handle errors that normally halt the script, UserTalk includes a try structure.

try
   file.delete (f)

The try block will trap the error and the script will continue (assuming there are additional statements after this small fragment). As with any other block structure in Frontier, a try block can contain multiple statements (lines). If any line causes an error, the remaining lines in the block will be skipped. A try block has an optional else block, providing code to execute when an error is encountered. The else block even has access to the error message, through a variable called "tryError". Sometimes you just want to display the error and continue.

try
   file.delete (f)
else
   dialog.alert (tryError)

Simple scripts or those used only occasionally may not need error-handling. When you create scripts that you use regularly -- or to share with others -- think about different ways the script could fail and use the techniques described in this section to anticipate and handle possible errors.

Bundles

The ability to collapse sections of code to hide unnecessary detail is a key advantage of editing scripts as outlines. UserTalk's looping, branching and error-handling blocks all have an outline structure. Sometimes it's useful to group other lines together. Bundling a group of related lines can result in code that is more readable at a higher level than the individual lines would be. It's a good idea to bundle lines that make up a multiple-line process whose details many or most readers of your script will not need to understand. A bundle structure is used to group a series of lines into a single block.
bundle « create a TeachText file
   file.new (path)
   file.setType (path, "TEXT")
   file.setCreator (path, "ttxt")

There are two ways to create a bundle. The first is to type the word "bundle" into your UserTalk script and then indent the group of lines under this heading. (An easy way to indent those lines is to choose the "Demote" option from the Script menu.) The second is to position the cursor on the first line you wish to be part of the bundle and then choose "Bundle-ize" from the Frontier Script menu. You can undo a bundling operation by positioning the cursor on the heading where the "bundle" is defined or any line contained in the bundle and choosing the "De-Bundle" option from the Script menu.

Contents Page | Next Section -- Variables in UserTalk
HTML formatting by Steven Noreyko January 1996, User Guide revised by UserLand June 1996