|
|||||
Event handling | |||||
Prerequisite Concepts | Related Syntax |
In OmniMark, data events occur in the processing of the current input. What kind of event occurs depends on which processor, the pattern processor or the markup processor, is presently acting on the current input. Events occurring in the pattern processor cause find rules to fire. Events occurring in the markup processor cause markup rules to fire.
To handle an event, you attach actions to the appropriate find or markup
rule. Processing continues until the input is exhausted. During the processing of
an event, however, you may do something that
starts processing a new piece of input. In this case, processing of the
original input is suspended while the new input is processed. This is where
things begin to get interesting, because, by default, this new input will be
processed by exactly the same rules as were processing the original input.
Consider the following program:
process submit "Mary had a little lamb" find "had" submit "Joe bought a big lamb" find "lamb" output "sheep"
This program will output "Mary Joe bought a big sheep a little sheep".
The submit in the rule find "had"
suspended processing of the
originally submitted data. The find rule for "lamb" fired once for the
"lamb" in the second input. When processing of the second submit finished,
the first resumed and the "lamb" rule fired once again for the "lamb" in the
first input. Can you see why writing code like the following is not a good
idea? (The second submit now reads "Joe had a big lamb".) If you feel
compelled to try it, save your other work first:
process submit "Mary had a little lamb" find "had" submit "Joe had a big lamb" find "lamb" output "sheep"
When pattern processing, your input is processed completely, unless you decide to pause and begin processing something else in the middle. When processing markup, however, you will have to deal with every level of nesting in the markup. Every element has content, which may include other elements. When an element occurs you have to deal with three things: the start of the element, its content, and its end. To give you the opportunity to decide how and when to deal with the element content, markup processing stalls at each element, and you need to explictly get it going again.
How do you continue parsing? The OmniMark keyword %c
causes
parsing to continue. You may think of it as equivalent to "continue
xml-parse" or "continue sgml-parse". (Since you will always want to continue
parsing in the middle of the output of the current element, the parse
continuation operator takes a form ("%c") that can easily be dropped into
a text string.). A do xml-parse
or do
sgml-parse
simply sets up the parser in the appropriate initial state to process the input it is receiving. To actually start parsing
you must output the parse continuation operator ("%c"):
do xml-parse document scan file "fred.xml" output "Beginning %c End") done
Every markup rule must output the parsing continuation operator ("%c") or
its alternative, suppress
, which continues parsing, but
suppresses output of the parsed content. Without them, your program would
stall permanently.
For obvious reasons, you cannot use %c
or
suppress
more than once in a markup rule. Don't fall into the
trap of thinking of %c
as standing for the content of an
element. It does not. It is an instruction to continuing parsing that
content. Any output that appears in the place where %c
occurs
in an output string is created by the rules which fire as a result of
parsing element content.
Can you mix pattern processing and markup processing in the same program?
Certainly you can. Consider the following code:
element fred submit "Element fred contains: %c That's all."
The result of parsing the content of element fred will be inserted into the string at the position %c
occurs. The entire string will then be submitted to the find rules.
Prerequisite Concepts About OmniMark |
Related Syntax %c element find suppress |
---- |