Nasal scripting language: Difference between revisions

Jump to navigation Jump to search
Line 58: Line 58:


Also, note that as of 05/2009, Nasal in FlightGear does not yet support any form of dependency resolution. In other words, there's no "import", "require" or "include" directive - this is also why most code in FlightGear is wrapped inside a _setlistener() call instead, which in turn waits for a FlightGear signal before executing the code (see below for details).
Also, note that as of 05/2009, Nasal in FlightGear does not yet support any form of dependency resolution. In other words, there's no "import", "require" or "include" directive - this is also why most code in FlightGear is wrapped inside a _setlistener() call instead, which in turn waits for a FlightGear signal before executing the code (see below for details).
== Variables ==
Nasal scripts should make use of the var keyword when declaring variables. The "var" keyword makes a variable guaranteed to be local. Nasal, natively provides support for scalars (numbers, strings), lists (arrays, vectors) and hashes (objects or dictionaries), more complex data structures (such as trees) can be built using vectors or hashes.
<syntaxhighlight lang="php">
var w=100;    # w is a local numerical variable
var x="hello"; # x is a local string variable
var y=[];      # y is a local vector (array)
var z={};      # z is a local hash (dictionary or table) - also used for OOP
</syntaxhighlight>
Now you may be wondering, what the heck is a vector, and what is a hash - and where's the difference?
The difference is, elements in a vector are sequentially numbered, i.e. each element has a numeric index:
<syntaxhighlight lang="php">
var my_vector = ['A','B','C'];
</syntaxhighlight>
This initializes a vector with three elements: A, B and C.
Now, to access each element of the vector, you would need to use the element's numerical index:
<syntaxhighlight lang="php">
var my_vector = ['A','B','C'];
print (my_vector[0] ); #prints A
print (my_vector[1] ); #prints B
print (my_vector[2] ); #prints C
</syntaxhighlight>
As can be seen, indexing starts at 0.
Compared to vectors, hashes don't use square brackets but curly  braces instead:
<syntaxhighlight lang="php">
var my_hash = {};
</syntaxhighlight>
Now, hashes may not just have numerical indexes, but also symbolic indexes as lookup keys:
<syntaxhighlight lang="php">
var my_hash = {first:'A',second:'B',third:'C'};
</syntaxhighlight>
This will create a hash (imagine it like a storage container for a bunch of related variables) and initialize it with three values (A,B and C) which are assigned to three different lookup keys: first, second, third.
In other words, you can access each element in the hash by using its lookup key:
<syntaxhighlight lang="php">
var my_hash = {first:'A',second:'B',third:'C'};
print ( my_hash.first ); # will print A
print ( my_hash.second ); # will print B
print ( my_hash.third ); # will print C
</syntaxhighlight>
Nasal supports a "nil" value for use as a null pointer equivalent:
<syntaxhighlight lang="php">
var foo=nil;
</syntaxhighlight>
Also, note that Nasal symbols are case-sensitive, these are all different variables:
<syntaxhighlight lang="php">
var show = func(what) {print(what,"\n");}
var abc=1; # these are all different symbols
var ABC=2; # different from abc
var aBc=3; # different from abc and ABC
show(abc);
show(ABC);
show(aBc);
</syntaxhighlight>
Please note that functions assigned to variables are no exception. If you write code without using "var" on variables, then you risk (often hard to debug) breakage at a later time because you may be overwriting symbols in another namespace.
So functions bound to variables should use the "var" keyword as well:
<syntaxhighlight lang="php">
var hello = func {
  print("hello\n");
}
</syntaxhighlight>
But there's another reason why "var" should be used consequently, even if a variable is safe enough from later side effects, because it has a relatively specific or unique name: The "var" keyword makes
reading code for others (and for the author after some time) easier, as it makes clear: "this variable starts its life *HERE*". No need to search around to see whether assigning a value to it means something to other code outside or not. Also, with an editor offering proper syntax highlighting reading such code is actually easier, despite the "noise".
The problem with nasal code that does not make use of the var keyword is, that it can break other code, and with it the whole system, but no Nasal error message will point you there, as it's syntactically and semantically correct code. Just doing things that it wasn't supposed to do.
For a more in-depth discussion, please see [http://www.mail-archive.com/flightgear-devel@lists.sourceforge.net/msg13557.html Nasal & "var"].
Also, Nasal scripts that are loaded from $FG_ROOT/Nasal are automatically placed inside a namespace that is based on the script's name.
For example, referring to our earlier "Hello World" example, global variables defined in the hello.nas script would be accessible by using "hello" as prefix from other modules:
<syntaxhighlight lang="php">
# hello.nas
var greeting="Hello World"; # define a greeting symbol inside the hello namespace
</syntaxhighlight>
If you were now to read out the value from the greeting variable from another Nasal module, you would have to use the hello prefix:
<syntaxhighlight lang="php">
# greetme.nas
print(hello.greeting); # the hello prefix is referring to the hello namespace (or module).
</syntaxhighlight>


==Namespaces==
==Namespaces==

Navigation menu