\begindata{text,11869184} \textdsversion{12} \template{default} \define{global } \define{concat menu:[Font,Concat] attr:[Script PreviousScriptMovement Point 6] attr:[FontSize PreviousFontSize Point 2]} \define{sans menu:[Font,Sans] attr:[FontFamily AndySans Int 0]} \flushright{16 July 1993} \majorheading{Ness Language Reference Manual} \center{by Wilfred J. Hansen} \indent{\flushright{\smaller{_________________________________ Andrew Consortium Carnegie Mellon University _________________________________ }} Ness is a programming language for the Andrew ToolKit. With it, documents can be processed and can even contain active elements controlled by Ness scripts. The language features an innovative substring algebra for string processing. This document is a reference manual describing the language. For a description of other Ness documents, see the \bold{Ness User's Manual}. 1. Program Structure 2. Statement Forms 3. Expression Forms 4. Extending Insets 5. Tokens Rules 6. Recent Changes }\ \begindata{bp,11870528} \enddata{bp,11870528} \view{bpv,11870528,83,0,0} Copyright IBM Corporation 1988, 1989 - All Rights Reserved Copyright Carnegie Mellon 1990, 1993 - All Rights Reserved \smaller{\smaller{$Disclaimer: Permission to use, copy, modify, and distribute this software and its documentation for any purpose is hereby granted without fee, provided that the above copyright notice appear in all copies and that both that copyright notice, this permission notice, and the following disclaimer appear in supporting documentation, and that the names of IBM, Carnegie Mellon University, and other copyright holders, not be used in advertising or publicity pertaining to distribution of the software without specific, written prior permission. IBM, CARNEGIE MELLON UNIVERSITY, AND THE OTHER COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL IBM, CARNEGIE MELLON UNIVERSITY, OR ANY OTHER COPYRIGHT HOLDER BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. $ $Log: nessman.doc,v $ Revision 1.13 1993/07/17 04:31:45 wjh remove notes about future developments modernize layout, copyrights, etc. }} \begindata{bp,4088320} \enddata{bp,4088320} \view{bpv,4088320,84,0,0} Ness \italic{programs} reside in their own files and process other files. Ness \italic{scripts} reside within Ness insets in a document or application; from there they extend and influence the behavior of other insets. In contrast with other languages, Ness is rather simplistic: it has arithmetic expressions, functions, if-then-else, while-do, and little else. The two major innovations are the control of insets--with \bold{extend} and \bold{on}--and an algebra of functions for string operations. This manual includes a description of Ness's various statement and expression forms. If you are familiar with other programming languages you should review the section on statement and expression forms and the various sections on functions available. You should also review the sections on the string algebra in the Tutorial. This manual describes version 1 of the Ness processor. If the language is changed incompatibly, this version number will be incremented. For Ness scripts within Ness insets, the version number is preserved in the document. A standalone program should record its expected language version by incorporating the comment --$Ness 1 somewhere in the program text. (Note that spacing counts; there are no spaces except the one before the version number.) In the template forms below, bold words are to appear in programs as shown. Words that are to be replaced with statements, expressions, or other elements are hyphenated compounds as in "statement-list". \section{1. Program Structure} A Ness program is a sequence of global-variable-declarations, function-definitions, and object-extension-specifications. If the program is standalone, execution generated call to the function main(), which will function-definition. If the program is begins when one of the events specified object-extension-specification occurs. begins by an artificially be defined with a a script in an inset, execution in an Global-variable-declarations are written in the same form as a variable-declaration inside a function-definition; see the description below. A global variable may be referred to from within function definitions anywhere after the point at which it appears in the program. An initialization expression in a global declaration may refer to other global variables previously defined and to functions defined anywhere; however, all global variables referred to by such function calls must already have values by earlier initializations. A function-definition gives the type returned, the name of the function, a list of the parameters expected, and a list of statements to be executed when this function is called. The form of these elements is: \leftindent{\leftindent{ness-type function-name \bold{(} parameter-list \leftindent{statement-list \bold{end} \bold{function} \bold{function} } \bold{)} } } The ness-type indicates what type of value this function will return. Valid types are \bold{marker}, \bold{integer}, \bold{real}, \bold{Boolean}, and \bold{object}, for all of which the function must execute a \bold{return} statement returning a value of the appropriate type. The ness-type may also be \bold{void}, in which case the function must not return a value. (It can return via \bold{exit function}.) It is permitted to omit the ness-type, in which case the function either returns a \bold{marker} value or none at all. If the function is called in a context that requires a particular type of returned value and none is returned, an error will be indicated when the caling statement is executed. The parameter-list is a list of names separated by commas. Each name may have a type-name in front of it; if not, the type is \bold{marker}. When the function is called, the arguments are evaluated and the value of each is assigned to a parameter variable allocated for the duration of execution of the function. Thereafter parameter variables behave the same as variables declared within the statement-list. Before executing the statements in statement-list space is set aside for all variables declared within the list. Then execution begins with the first statement and continues to the last, except as directed by \bold{if}, \bold{while}, \bold{return}, or \bold{exit function} statements. Suggested indentation is shown in the syntax form above. This is not mandatory, but it is of value when a syntax error is detected during compilation. In that case, the parse skips ahead to the next function-definition, which is recognized partially on the basis of indentation. For a function definition to be recognized, at least one of function-type, \bold{function}, and function-name must be directly at the left margin. The function main(args) has a special role. Main() is called whenever nessrun is applied to the file; at that time, the value passed for args is evrything from the command line after the command name ("nessrun") and the \italic{filename}.n. Semi-colons are allowed anywhere between global variable definitions, function definitions, and extends. An object-extension-specification is a block with the form \leftindent{\bold{extend} "insetName" event-interceptor-list \bold{end exend}} where "insetName" is the name of an inset in the same document or application with the Ness. For details, see section 4 below. \section{2. Statement Forms} The statement-list in a function-definition consists of a sequence of statements. Statements are executed in succession unless dictated otherwise by function-call, \bold{if}, or \bold{while}. The remainder of this section describes the various statement forms. \subsection{Semi-colon} A single semi-colon as a statement is ignored. This rule permits semi-colons in a script anywhere between statements. If the start of a statement is preceded on a line by other than spaces or tabs, it must be preceded by a semi-colon. \subsection{Declaration} Declarations are of the form \leftindent{ness-type variable-name \leftindent{ness-type variable-name} \leftindent{ness-type variable-name \bold{,} ness-type name variable-name \bold{,} \bold{:=} ness-expression} variable-name variable-name \bold{,} variable- . . .} where ness-type is one of \bold{integer}, \bold{real}, \bold{marker}, \bold{object}, or \bold{Boolean}. The variable(s) named will be of the given type throughout the remainder of the statement-list, even beyond an \bold{end if} or \bold{end while} for an enclosing \bold{if} or \bold{while} statement. Although declarations are thus allowed to appear anywhere, it is conventional to collect them at the beginning of a statement-list. In the first form of declaration, the single variable is declared and will be initialized to have the value of the ness-expression. The computation of the expression can involve function calls and references to variables initialized prior to this one. If there is an initialization, there can be only one variable declared. With no initialization, the other forms of declaration are possible; that is, the ness-type may be followed by a comma-separated list of variables. All are declared and given no legal initial value. \subsection{Assignment} A variable is given a value with the assignment statement: \leftindent{variable-name \bold{:= } ness-expression} For assignment of types other than object and marker, the value of the ness-expression is copied and the copy is stored in the named variable. When the variable and expression are of type \bold{object}, only a reference to the object is assigned, the object is not copied. When the variable and expression are of type \bold{marker}, the target variable receives only a reference to the appropriate substring of the base. No new string text is created. \subsection{String append} One way to build up string values from smaller strings is to append values onto the end of the string. A special statement form is provided for this: \leftindent{variable-name \concat{~}\bold{:=} ness-expression} This concatenates the value of the expression onto the end of the base of the string referred to by variable-name and changes variable-name to refer to the entire resulting base string. (The following explanation will make more sense after reading Section 3.5.) One way to think of \concat{~}\bold{:=} is that it concatenates the value of the expression to the value of the variable, as would be done by: \leftindent{var inaccurate model} \bold{:= } base(var) \concat{~} expr -- This model is inaccurate because in that it implies that all markers to the old value of var will no longer refer to the same string as var does (because concatenation creates a new string value). The accurate description of the append statement is this: \leftindent{var \bold{:=} base(replace(finish(base(var)), expr)) accurate definition of \concat{~}:=} -- In other words, the value of the expression is inserted at the end of the base string of var and then var is assigned a marker for the entire base string, including the new piece. A common programming error is to assign v := "" -- initialize v and then attempt to extend the value of v with v ~:= somemarkerexpression -- FAILS after v := "" This fails because "" is a constant whose value cannot be modified. Instead the initialization assignment should have been v := newbase() -- initialize v \subsection{Function call} A function call by itself constitutes a statement: \leftindent{function-name \bold{(} argument-list \bold{)} } where the argument-list is a sequence of zero or more expressions separated by commas. This is the only context in which it is acceptable to call a function declared to have type "\bold{void}"; however, functions of other types can also be called and the value they return is ignored. \subsection{Return} The \bold{return} statement terminates execution of the enclosing function or event body. If the function has a type, the return statement must have an expression that gives a value of that type: \leftindent{\bold{return} ness-expression } For a return from an event body or a function declared to have the type \bold{void}, use the form \bold{\leftindent{exit function}} \{The error checks implied in this section are not made. Any function or event body can return a value of any type or none at all.\} \subsection{If} The \bold{if} statement tests a Boolean expression and conditionally executes one of a set of clauses. The simplest form is: \leftindent{\bold{if} Boolean-expression \bold{then} \leftindent{then-clause-statement-list }\bold{end if}} If the Boolean expression is \bold{True}, the statements in the then-clause-statement-list are executed. Sometimes alternative statements need to be done when the Boolean value is \bold{False}. This is done by adding an else-clause-statement-list: \leftindent{\bold{if} Boolean-expression \bold{then} \leftindent{then-clause-statement-list }\bold{else} \leftindent{else-clause-statement-list }\bold{end if}} (Note the indentation; it is standard for Ness programs.) Here the else-clause-statement-list is done if the Boolean value is \bold{False}. When more than two alternatives exist, the sequence \bold{else if} may be used, but this requires an \bold{end if} for each \bold{if}. To reduce the number of \bold{end if}s, any number of \bold{elif} forms can be inserted after the then-clause-statement-list: \leftindent{\bold{elif} Boolean-expression \bold{then} \leftindent{elif-clause-statement-list}} This construct is executed in place of an \bold{else} and first evaluates its own Boolean-expression. If \bold{True}, the elif-clause-statementlist is executed and control continues after the \bold{end if}. If \bold{False}, controls proceeds to the next corresponding \bold{elif}, \bold{else}, or \bold{end if}. \subsection{While} The \bold{while} construct provides for repeated execution of a sequence of statements until some condition is met: \leftindent{\bold{while} Boolean-expression \bold{do} \leftindent{do-clause-statement-list }\bold{end while}} (Again note the indentation standard.) When control reaches the \bold{while}, the Boolean expression is tested. If \bold{False}, control proceeds to after the \bold{end while}; otherwise the do-clause-statement-list is executed and control returns to the \bold{while} for a repeat of the whole process. The statement \leftindent{\bold{exit while} } transfers control to just after the next succeeding \bold{end while} which corresponds to a preceding \bold{while}. \section{3. Expression Forms} The common forms of expression in Ness are \leftindent{constants, variables, parenthesized expressions, and function calls. } Only a few infix and prefix operators are defined; they are described in the discussion of each data type below. Variables must be declared before they are used and may be global to an entire program, a formal parameter to a function, or local to a function or event. A declaration is written as the type name followed by the identifier. An execution error occurs if an attempt is made to utilize the value of an uninitialized variable or if the type of an expression does not match the type required by the context.. For all ness-types function calls are of the form: function-name \bold{(} argument-list \bold{)} where argument-list is a sequence of zero or more ness-expressions separated with commas. By default, parameters and the function return value are of type \bold{marker}. If the function call is a forward reference, the type returned is expected to be \bold{marker} The precedence of operators is: \indent{\bold{or} lowest \bold{and} \bold{not} \bold{= + - * / /= < <= > >= %} \concat{~} highest} \subsection{3.1 Boolean expressions} The two Boolean constants are \bold{True} and \bold{False}. Each Boolean variable and expression has one of these two values. The following operators apply to, or generate, Boolean values: \description{\bold{and } \bold{or } \bold{not}: The usual Boolean operations. Execution of expressions involving \bold{and} and \bold{or} is "short-circuited;" operands whose values are immaterial to the value of the expression are not evaluated. That is, the second operand is not evaluated if the first is \bold{True} for \bold{or} or \bold{False} for \bold{and}. \bold{= /= < <= > >= }The usual comparison operations. (Note that not-equal is written as "\bold{/=}".) All six comparisons are defined for integer, real, and marker values. Only equality and inequality are defined for Booleans and pointers. (Marker comparisons test the values of the strings referenced and not the relative positions indicated by the markers, but see the discussion in the Section 3.5 on marker expressions.)} \formatnote{.ne 1.5i} \subsection{3.2 Integer expressions} Integer constants are described in Section 5 on "Tokens." The usual arithmetic operations are defined: \bold{+}, \bold{-}, \bold{*}, \bold{/}, and \bold{%}. Unary-plus and unary-minus are both defined. Division (\bold{/}) discards the remainder; another operator (\bold{%}) returns the remainder. Overflow is ignored by the interpreter; divide-by-zero is a run-time error. All six comparison operators are defined for integer values. \formatnote{.ne 1.5i} \subsection{3.3 Real expressions} Real constants are described in Section 5 on "Tokens." The usual arithmetic operations are defined: \bold{+}, \bold{-}, \bold{*}, and \bold{/}. Unary-plus and unary-minus are both defined. Overflow, underflow, and divide by zero are ignored by the interpreter; the results can be tested for validity with isnan() and finite() \{These functions are not available on all hardware.\}. All six comparison operators are defined for real values. At present, there are no automatic conversions between integer and real. Use float(), round(), floor(), and ceil(). \formatnote{.ne 1.5i} \subsection{3.4 Object expressions} An object expression refers to some object in the system, usually an inset in the document or application. Equality and inequality are defined for object values. The constant \bold{null} is an object value which can be assigned as value to any object variable in order to indicate that it refers to no object. For full details of functions and predefined identifiers related to objects see the \bold{Ness Function Reference Manual}. Here are a few: The \bold{inset}() function has one marker value argument; it returns a pointer to the object for the inset named by the marker value. The inset must have had its name registered with the surrounding arbiter; Section 4 on "Extending Insets". see The class() function returns a quintessential object for the class named by its argument. The new() function has as its argument an object and returns a brand new object of the same class. The predefined object variables defaulttext, currentinset, currentinputfocus, and currentwindow refer to specific objects in the environment at the given time. The principal utility of object values is to pass them to functions defined in C code. One set of functions are those in the "proctable" and specified in the documentation as being available to be bound to keys and menu entries. Another set are the methods, class procedures and instances variables defined in the class declaration for the class (the .ch file). When calling functions from either of these sets, the Ness interpreter takes care to get the proper object from the two or more that constitute an inset. The inset() function actually returns a \italic{celview} object which points to the \italic{data} object and \italic{view} object that actually produce the visible image. If the function does not apply to the celview class, a check is made to see if it applies to the class of the data object, the view, or one of several other possibilities. \subsection{3.5 Marker expressions} A marker value refers to a substring of contiguous characters in some underlying base string. String constants are described below in Section 5 on "Tokens". The value of a string constant is a marker value referring to the entire string. New, non-constant string values are created only by \italic{newbase}(), concatenation, \italic{readfile}(), and \italic{system}(). Assignment of a marker value to a marker variable does NOT create a new string value; the marker variable will subsequently refer to the same base string as did the original value. All six comparison operators are defined for marker values. The values compared are the strings referred to by the markers, whether or not they are on the same base. A marker for a string of length zero is always equal to any other marker for a string of length zero and less than any marker for a non-zero length string. String concatenation is indicated with the tilde operator as in \leftindent{<string-expression> \concat{~} <string-expression> } This expression constructs a brand new string having a base different from all other strings, including its arguments. The value of the expression is a marker referring to the entirety of the new string. One way to append to an existing string is with the string-append statement using \concat{~}:= as described in Section 2. Another way is to replace a portion of a base string with the replace() function, one of the six primitive marker functions. For details on these operation and other marker functions see the \bold{Ness Function Reference Manual}: \indent{newbase() - returns a marker for a new, empty base string. This is not a constant string and thus it can be modified with replace() or string-append. base(m) - returns a marker for the entire base string of which m refers to a portion. start(m) - returns a marker for the empty strings which starts where m does. next(m) - returns a marker for the single character following m in its base. extent(m, n) - returns a marker for the substring which starts where m does and ends where n does. If they are on different bases, the value is an empty marker on an empty constant string. If they are on the same base but the end of n precedes the end of m, the value is an empty marker at the end of n. replace(m, n) - returns a marker for a copy of n which has replaced m in base(m).} Given two markers m and p on the same base, their relative start positions in the base can be determined by testing extent(start(m), start(p)) . This expression will be non-empty if start(m) strictly precedes start(p), but will be empty if they are at the same position or start(p) precedes start(m). \section{4. Extending Insets} When a Ness script is embedded as an inset in a document or application (or drawing or table or ...), it can specify extensions to other named insets in its surroundings. For details of how insets become named and nested within cel insets, see \bold{Ness Author's Reference Manual} and the documents in /usr/andrew/doc/adew. Given an inset with the name <celname>, its behavior can be controlled through Ness with an object-extension-specification. These have the form \leftindent{\bold{extend} "insetName" event-interceptor-list \bold{end exend}} where "insetName" is a constant naming one of the insets in the same document or application. The effect is that the enclosed event-interceptor-list applies to the named cel and its embedded inset. When one of the intercepted events occurs for that inset, the corresponding Ness code is executed. Since it is crucial that operations added by extension should work properly as soon as the extended objects are visible, embedded Ness objects prompt for empowerment (compilation) as soon as they are displayed to the user. (Therefore, every Ness that extends an object should be visible in the display "close" to where the extended object lies.) When a Ness is compiled, the arbiter is informed of it and any cels which should be extended are extended as soon as they become visible. The event-interceptor-list may include global-variable-declarations and function-definitions as described above in Section 1. These apply only within the limits of the current \bold{extend} ... \bold{end extend}. In addition, the list may include event-interception-specifications, each of which begins with the keyword \bold{on} followed by one of the eventclass names \bold{keys}, \bold{menu}, \bold{mouse}, or \bold{event}. The form of these specifications is \indent{\bold{on} event-class "event-specification" \indent{statement-list} \bold{end} event-class} The specification has a different interpretation for each event-class and the statement list is executed exactly as would be one in the body of a function. Each of the event-classes is described in ensuing subsections. There is one additional option for the "insetName"; it can be a string beginning with 'view:' and continuing with the name of a class of view objects--textview, rasterview, zipview, ... . In this case the key and menu elements in the event-interceptor-list apply to all views of the given class in any window created after this compilation. This is primarily of interest when ~/.atkinit or some other initialization file loads the Ness file with lines like load ness call ness-load /usr/andrew/lib/ness/wc.n (The first line is needed once, there can a call ness-load line for each of any number of files.) See Section 3 of the \bold{Ness Hacker's Manual} for details. \subsection{4.1 On Keys} For \bold{on keys}, the event-specification is a sequence of keys. When that sequence of keys is typed by the user, the event occurs and the statement-list is executed. \{The keys are also recognized if sent via dokeys(), but this causes a Ness failure.\} During execution of the statement-list, two predefined variables have values. \indent{\italic{currentinset} is an object value referring to the object which is extended by this event-interceptor. \italic{lastkeys }is a constant marker value having the eventspecification string.} Relying on these variables, the statement-list can call on a generalized function to handle interception for a number of objects or menu items and this function can determine exactly which ones it has been called for this time. \subsection{4.2 On Menu} For \bold{on menu}, the event-specification is a menu string. When that menu item is selected by the user, the event occurs and the statementlist is executed. The full syntax of a menu string is [ menu-card-name [\concat{~}<n>]]\bold{, }menu-item-name [\concat{~}<n>] where brackets indicate optionality and <n> is a two digit number. There are no spaces, except possibly within the names. If no menu-card-name is specified, the item will be on the front card instead of one of the named cards. If an <n> is specified, the position of the card in the stack or the item in the card is influenced; items are in numerical order of <n> (Although there is little documentation on the value of <n> for existing menu items). If two items have <n>s differing in the tens digits, there will be a blank line between those items. During execution of the statement-list, two predefined variables have values. \indent{\italic{currentinset} is an object value referring to the object which is extended by this event-interceptor. \italic{lastmenu }is a constant marker value having the eventspecification string.} Relying on these variables, the statement-list can call on a generalized function to handle interception for a number of objects or menu items and this function can determine exactly which ones it has been called for this time. \subsection{4.3 On Mouse} For \bold{on mouse}, the event-specification is "any". When any mouse event occurs to the inset, the event occurs and the statement-list is executed. If more than one \bold{on} \bold{mouse} appears within an \bold{extend}, block only one of them will be honored. During execution of the statement-list, several predefined variables have values. \indent{\italic{currentinset} is an object value referring to the object which is extended by this event-interceptor. \italic{mouseaction }is an integer value encoding which button this event is for and whether it went up or down or the mouse moved. It should be tested by comparing it with the mouse constants below. \italic{mousex} is an integer giving the x coordinate of the mouse within the object image.\indent{ } \italic{mousey} is an integer giving the y coordinate of the mouse within the object image.\indent{ }} The following predefined constants are possible \italic{mouseaction} values: \italic{mouseleftup}, \italic{mouseleftdown}, \italic{mouseleftmove}, \italic{mouserightup}, \italic{mouserightdown}, \italic{mouserightmove}. Each indicates which button the action is for and whether the button has gone down or up or the mouse has moved with the button down. It may be necessary within a mouse event interception to pass the event along to the object so it can update itself for the mouse hit. This is done with the function \italic{dohit} which causes an object to believe a mouse hit has occurred for it. Dohit has four arguments: the object to be moused, a mouseaction value, and the x and y coordinates of the hit. Given the above, a typical mouse interception routine looks like this: on mouse "any" dohit(currentinset, mouseaction, mousex, mousey) if mouseaction = mouseleftup then --do something interesting end if end mouse \subsection{4.4 On Event} For \bold{on event}, the event-specification is the name of a \italic{trigger} as defined by the inset that is named in the surrounding \bold{extend} block. For example, the hyplink inset defines a trigger "buttonpushed"; whenever the button is pushed hyplink pulls this trigger. If an extend block for a hyplink inset has on event "buttonpushed" -- action statements end event and the mouse is clicked on the button, the action statements will be executed. Other triggers are defined in the documentation for individual insets. The extend block for any object may include a handler for "\bold{BecameVisible}". This handler will be called whenever the object first becomes visible on the screen. \section{5. Tokens} Ness programs and scripts can be enhanced with styles, including bold and italic. These styles are ignored except within string constants. Comments begin with "--" and extend to the end of the line. There is no difficulty with inserting insets in comments and string constants. Identifiers begin with a letter and continue with letters and digits. The case of a letter is ignored; "aToZ" refers to the same thing as "AtoZ". The following may not be used as identifiers: \bold{\indent{and boolean do elif else end event exit extend false function if integer keys marker menu mouse not null object on or real return then true void while }}(and for future expansion:\bold{ \indent{by case find forall forward from gotoelse in select}}) Integer and real constants are written as they are in C. Integer values may also be expressed with octal, hexadecimal, and character constants. Here are some examples: \leftindent{Decimal integers: Real values: 12.3 Octal integers: 12e3 0123 Hexadecimal integer: Character constant: 0 12E-3 0001 .2 2. 91 2.e+5 077 0x12abc 'a' 123123 0x0 0xFFFF0000 '@'} Characters in character and string constants may utilize the escape sequences found in C and some additional ones: \leftindent{ \\e escape \\n newline \\r carriage return \\b backspace \\t tab \\f formfeed \\v vertical tab \\\\ backslash \\' apostrophe \\" double-quote \\\italic{ooo} \\^@ \\000 \\^A control-A octal digit representation ... \\^Z control-Z \\^[ \\033 \\^\\ \\034 \\^] \\035 \\^^ \\036 \\^_ \\037 } String constants are delimited with double quote (") at both ends and must not cross a newline character. They may include the special characters shown as special character constants. Another form of string constant is the\italic{ long string}. Such constants are delimited at the start by a line containing only "//" and at the finish by a line starting with "\\\\". Neither the initial nor final line or newline is part of the constant. For example: \leftindent{replace (m, // This is a \italic{long string} which contains\underline{ }newlines, \bold{styled text}, and an embedded object: \begindata{raster,11869312} 2 0 68266 68266 0 0 57 24 bits 11869312 57 24 g7fIc0h | g7fIc0h | g7fIc0h | g7fIc0h | g7fIc0h | g7fIc0h | g7fIc0h | g7ff8k | g7ff8k | g7ff8h03Gg | g7ff8h03Gg | g"555003Gg | g2a!aaa003Gg | g"555003Gg | g2a!aaa003Gg | g"555fHg | g2a!aaafHg | g"555fHg | g2a!aaafHg | g"555fHg | g2a!aaafHg | n | n | n | \enddata{raster, 11869312} \view{rasterview,11869312,80,0,0} The string length can be as long as desired. \\\\ )} Whitespace characters are space, tab, newline, DEL, all other control characters, and all characters with the high order bit set. They terminate reserved words, identifiers, and numbers. They are included in strings; except for newline, which causes an error. Otherwise they are ignored until a syntax error is detected. When a syntax error occurs, the compilation skips immediately to the beginning of the next function, extend, or event. Functions and extends are detected with the aid of unindented text. To be recognized as a resynchronization point after a syntax error, a line must begin with an unindented element of function-type \bold{function } function-name or an unindented element of \bold{extend} inset-name-string or the possibly-indented sequence \bold{on} event-keyword \section{ 6. Recent Changes} May-June, 1990 o Added function launchApplication. Applications can now be initiated from nessrun, so the program need not occupy screen space and the user need not empower the Ness program. o Added functions nextstylesegment, searchforstyle, definestyle, and addstylebyname. \subsection{September-December 1989} o Removed the need for semicolons. They are now optional everywhere. o Allowed multiple variable names in declarations. three marker variables with One may now declare \leftindent{marker a, b, c} o Allowed initialization in declarations. variable and initialize it at the same time: On may now declare a \leftindent{marker a := "This is the life" ~ punctuation} Note that if a declaration has an initialization, it cannot be part of a list. The initialization expression can be any expression as long as the variables mentioned have been given values before this statement (that is, either earlier in the same function definition or as global values. o Added \bold{exit function} statement form. control This form transfer from this function back to the calling function. It serves as would a "return" statement without an expression value. (One cannot use just plain "return" any longer because there are no longer any semicolons.) o Added \bold{exit while} statement form. This form transfers control from its location to just after the "end while" of the smallest enclosing while-loop. o Changed the semantics of the five search functions: search, match, anyof, span, token. The old semantics had two properties which seemed wrong in light of experience: \indent{The search area extended from the beginning of the first argument to the end of the base. The value if the search failed was the beginning of the first argument. } The new semantics are these: \indent{The search area extends only through the first argument. However, if the first argument is empty the search area extends from the first argument to the end of the base. The value for a failed search is the finish of the first argument. } The first of these rules means the search can be restricted to any portion of the document. The second provides more flexibility in nesting search requests. You now have two options for a search that is to have an area from a given point to the end of the base: \indent{a) Have the first argument extend from the given point to the end of the base. For failure the result is the end of the base. b) Have the first argument be an empty marker. For failure the result is the beginning of the search area (which is the end of the first argument).} Notice that the second of these options gives exactly the original semantics. Therefore: In converting a program from the old semantics to the new it is sufficient to wrap the first argument expression for each search-type function with start(). o Replaced \bold{extend} "proctable:..." with \bold{extend} "view:..." and eliminated \bold{on proc} "...". In the old way, a function was inserted in the proctable with on proc and the .XXXinit file contained addkey or addmenu operations to refer to the proctable function. After the revision, the key or menu binding is specified directly in the Ness file. Example: \leftindent{extend "view:textview" on keys "\\030\\014" -- control-X control-L wc_showcount() end keys end extend} This binds control-X control-L to count the words in the current selection. o Added the event type \bold{event} to reflect the addition of triggers to the C definition of objects. The event specification \bold{on event} "trigger-name" ... \bold{end event} must appear with the extend block for an inset which defines the trigger "trigger-name". When the C code pulls the trigger, the code within the \bold{on event} ... \bold{end event} will be executed. \subsection{May, 1989.} Initial release to CMU campus. \enddata{text,11869184}