Hi ,
i try to understand this for a while but i get crazy with tha %1 etc thing..
what does that exactely mean?..
Hi Tuur,
Ah. I'd like to have an argument, please -- Michael Palin, The Argument Clinic
As you know krpano actions are of the form:
|
Source code
|
1
2
3
|
<action name="action_name">
body
</action>
|
where
body is the action code.
The actions may be called in the following manner:
|
Source code
|
1
|
action_name(arg1,arg2,arg3,...,argN);
|
or
|
Source code
|
1
|
action(action_name,arg1,arg2,arg3,...,argN);
|
where
N is 99 or less. In other words, you may have up to 99 arguments (krpano versions less than 1.0.8.10 supported only 9 arguments).
krpano actions allow you to access arguments from within the body of your code via the
%N reference, where
N is a number from 1 to 99.
%0 may be used to reference the name of the action from within the action's body.
In other words:
- %0 is the name of the action that is being called
- %1 is the first argument passed to that function, null if no first argument
- %2 is the second argument passed to that action, null if no second argument
....
- %9 is the ninth argument passed to that action, null if no ninth argument
For the new version 1.0.8.10 of krpano you can now have up to 99 arguments.
- %10 is the tenth argument passed to that action, null if no tenth argument
- %11 is the tenth argument passed to that action, null if no eleventh argument
....
First, a simple example:
|
Source code
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
|
<krpano version="1.0.8" onstart="showtext(press the 'o' key to see the output,infostyle);main()" >
<textstyle name="infostyle" origin="center" fontsize="20" showtime="2.0" fadetime="1.0" />
<action name="hello">
trace("hello ",%1);
</action>
<action name="main">
hello(world);
hello(kitty);
hello(Klaus);
hello();
</action>
</krpano>
|
produces:
INFO: hello world
INFO: hello kitty
INFO: hello Klaus
INFO: hello null
This code snippet includes two actions:
hello which prints the string hello followed by whatever the user passes in as the first argument, and
main which calls the
hello function four times with different arguments. Note that the fourth call passes no arguments:
hello();. This produces the output
INFO: hello null.
ARGUMENT SUBSTITUTION
Krpano's action language is different from other programming languages in that the arguments
do not become local variables within the code body, rather arguments are substituted into the code prior to the execution of the code body. You can think of it as if you are using a text editor on the body of the code, and doing a search and replace for each argument, replacing all occurrences of
%1 with the string that is the first argument, replacing all occurrences of
%2 with the string that is the second argument, etc. If no argument has been provided for a given
%N, then a global replace of null is performed for that particular
%N.
This substitution occurs after the action is called, but before the action is executed. Consider this example:
|
Source code
|
1
2
3
4
5
6
7
8
9
10
11
12
|
<krpano version="1.0.8" onstart="showtext(press the 'o' key to see the output,infostyle);main()" >
<textstyle name="infostyle" origin="center" fontsize="20" showtime="2.0" fadetime="1.0" />
<action name="test">
trace("action ",%0," arg1 is ",%1,", arg2 is ",%2,", args 3 and 4 are %3%4");
</action>
<action name="main">
test(abc,def,123,456);
test(krpano,is,#,1);
</action>
</krpano>
|
In the
main action, the first call to
test is
test(abc,def,123,456);. When this line of the program is reached, then the arguments are substituted into the body of
test. That is, before the
test action is executed,
- the name of the action "test" replaces all instances of %0
- the first argument "abc" replaces all instances of %1
- the second argument "def" replaces all instances of %2
- the third argument "123" replaces all instances of %3
- and the fourth argument"456" replaces all instances of %4
Thus the original
test body code
|
Source code
|
1
|
trace("action ",%0," arg1 is ",%1,", arg2 is ",%2,", args 3 and 4 are %3%4");
|
becomes
|
Source code
|
1
|
trace("action ",test," arg1 is ",abc,", arg2 is ",def,", args 3 and 4 are 123456");
|
. After the substitution, the body is executed and produces the output:
action test arg1 is abc, arg2 is def, args 3 and 4 are 123456
.
We then proceed to the next line in
main where
test is called again with different arguments:
test(krpano,is,#,1). Here the action name "test" replaces
%0, "krpano" replaces
%1, "is" replaces
%2, "#" replaces
%3, and "1" replaces
%4. Thus, before execution, the code body
|
Source code
|
1
|
trace("action ",%0," arg1 is ",%1,", arg2 is ",%2,", args 3 and 4 are %3%4");
|
is converted to
|
Source code
|
1
|
trace("action ",test," arg1 is ",krpano,", arg2 is ",is,", args 3 and 4 are #1");
|
Once executed, this produces the output
action test arg1 is krpano, arg2 is is, args 3 and 4 are #1
One interesting thing to note, is that in this example, the replacement of arguments %3 and %4 occur
within a quoted string. Krpano's handles argument through a simple substitution mechanism, without regard for syntax. The resulting code of course must be syntactically correct, but substitutions can occur within quoted strings, in or out of argument lists, in function names, really anywhere within the body of the code. In fact,
entire code segments may be passed through the argument list as in the following example.
Suppose we want to add debugging code which is only executed when the global variable
debug is set to true. We can create such an action, let's call it
dbg, through which we can pass a code fragment that can be conditionally executed:
|
Source code
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
|
<krpano version="1.0.8" onstart="showtext(press the 'o' key to see the output,infostyle);main()" >
<textstyle name="infostyle" origin="center" fontsize="20" showtime="2.0" fadetime="1.0" />
<action name="dbg">
if (debug == true, %1);
</action>
<action name="main">
set(a,123);
set(b,345);
dbg(
trace("hello world");
trace("a is ",get(a)," b is ",get(b));
);
set(debug,true);
set(a,2000);
set(b,1000);
dbg(
if (a GT b,
trace("a is ",a);
<!--else-->,
trace("b is ",b);
);
);
</action>
</krpano>
|
When this is executed, what happens? The only output produced is:
INFO: a is 2000
If we walk step by step through the
main code, first we see the variable
a is set to the value 123 and then the variable
b is set to the value 345. The
dbg action is then called with the argument
|
Source code
|
1
2
|
trace("hello world");
trace("a is ",get(a)," b is ",get(b));
|
This multi-line, multi command argument (complete with quoted strings) get's substituted into every %1 found in the body of dbg. Thus
|
Source code
|
1
|
if(debug == true, %1);
|
becomes
|
Source code
|
1
2
3
4
|
if(debug == true,
trace("hello world");
trace("a is ",get(a)," b is ",get(b));
);
|
When this is executed, the variable
debug has not been set, so the if test fails and the traces do not get executed.
The next line in
main sets the variable
debug to true. Then the variable
a is changed to 2000 and
b is changed to 1000. The
dbg action is called with the following argument:
|
Source code
|
1
2
3
4
5
|
if (a GT b,
trace("a is ",a);
<!--else-->,
trace("b is ",b);
);
|
This is substituted into the
dbg function wherever there is a
%1, thus
|
Source code
|
1
|
if(debug == true, %1);
|
is converted to
|
Source code
|
1
2
3
4
5
6
7
|
if(debug == true,
if (a GT b,
trace("a is ",a);
<!--else-->,
trace("b is ",b);
);
);
|
This code now executes, and since
debug has previously been set to true the nested if statement is executed where
a is compared to
b and is found to be greater resulting in the
trace("a is ",a) code being executed which produces the (only) output
a is 2000.
...more in
Part 2