- add argc/argv arguments to FGNasalSys::call
- add support for childAdded/childRemoved listeners - use regular function arguments for property ghosts - warning--
This commit is contained in:
parent
02a813abde
commit
3a03671566
2 changed files with 56 additions and 24 deletions
|
@ -80,12 +80,12 @@ FGNasalSys::FGNasalSys()
|
||||||
// drop the lock in every extension function that might call back into
|
// drop the lock in every extension function that might call back into
|
||||||
// Nasal, we keep a stack depth counter here and only unlock/lock
|
// Nasal, we keep a stack depth counter here and only unlock/lock
|
||||||
// around the naCall if it isn't the first one.
|
// around the naCall if it isn't the first one.
|
||||||
naRef FGNasalSys::call(naRef code, naRef locals)
|
naRef FGNasalSys::call(naRef code, int argc, naRef* args, naRef locals)
|
||||||
{
|
{
|
||||||
naContext ctx = naNewContext();
|
naContext ctx = naNewContext();
|
||||||
if(_callCount) naModUnlock();
|
if(_callCount) naModUnlock();
|
||||||
_callCount++;
|
_callCount++;
|
||||||
naRef result = naCall(ctx, code, 0, 0, naNil(), locals);
|
naRef result = naCall(ctx, code, argc, args, naNil(), locals);
|
||||||
if(naGetError(ctx))
|
if(naGetError(ctx))
|
||||||
logError(ctx);
|
logError(ctx);
|
||||||
_callCount--;
|
_callCount--;
|
||||||
|
@ -111,7 +111,7 @@ bool FGNasalSys::parseAndRun(const char* sourceCode)
|
||||||
strlen(sourceCode));
|
strlen(sourceCode));
|
||||||
if(naIsNil(code))
|
if(naIsNil(code))
|
||||||
return false;
|
return false;
|
||||||
call(code, naNil());
|
call(code, 0, 0, naNil());
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -586,7 +586,7 @@ static naRef f_airportinfo(naContext c, naRef me, int argc, naRef* args)
|
||||||
|
|
||||||
|
|
||||||
// Table of extension functions. Terminate with zeros.
|
// Table of extension functions. Terminate with zeros.
|
||||||
static struct { char* name; naCFunction func; } funcs[] = {
|
static struct { const char* name; naCFunction func; } funcs[] = {
|
||||||
{ "getprop", f_getprop },
|
{ "getprop", f_getprop },
|
||||||
{ "setprop", f_setprop },
|
{ "setprop", f_setprop },
|
||||||
{ "print", f_print },
|
{ "print", f_print },
|
||||||
|
@ -792,7 +792,7 @@ void FGNasalSys::createModule(const char* moduleName, const char* fileName,
|
||||||
|
|
||||||
_cmdArg = (SGPropertyNode*)arg;
|
_cmdArg = (SGPropertyNode*)arg;
|
||||||
|
|
||||||
call(code, locals);
|
call(code, 0, 0, locals);
|
||||||
hashset(_globals, moduleName, locals);
|
hashset(_globals, moduleName, locals);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -845,7 +845,7 @@ bool FGNasalSys::handleCommand(const SGPropertyNode* arg)
|
||||||
// code doesn't need it.
|
// code doesn't need it.
|
||||||
_cmdArg = (SGPropertyNode*)arg;
|
_cmdArg = (SGPropertyNode*)arg;
|
||||||
|
|
||||||
call(code, locals);
|
call(code, 0, 0, locals);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -889,7 +889,7 @@ void FGNasalSys::setTimer(naContext c, int argc, naRef* args)
|
||||||
|
|
||||||
void FGNasalSys::handleTimer(NasalTimer* t)
|
void FGNasalSys::handleTimer(NasalTimer* t)
|
||||||
{
|
{
|
||||||
call(t->handler, naNil());
|
call(t->handler, 0, 0, naNil());
|
||||||
gcRelease(t->gcKey);
|
gcRelease(t->gcKey);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -944,9 +944,9 @@ naRef FGNasalSys::setListener(naContext c, int argc, naRef* args)
|
||||||
return naNil();
|
return naNil();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool persistent = argc > 3 ? naTrue(args[3]) : true;
|
int type = argc > 3 && naIsNum(args[3]) ? args[3].num : 1;
|
||||||
FGNasalListener *nl = new FGNasalListener(node, handler, this,
|
FGNasalListener *nl = new FGNasalListener(node, handler, this,
|
||||||
gcSave(handler), _listenerId, persistent);
|
gcSave(handler), _listenerId, type);
|
||||||
|
|
||||||
bool initial = argc > 2 && naTrue(args[2]);
|
bool initial = argc > 2 && naTrue(args[2]);
|
||||||
node->addChangeListener(nl, initial);
|
node->addChangeListener(nl, initial);
|
||||||
|
@ -984,17 +984,16 @@ naRef FGNasalSys::removeListener(naContext c, int argc, naRef* args)
|
||||||
// FGNasalListener class.
|
// FGNasalListener class.
|
||||||
|
|
||||||
FGNasalListener::FGNasalListener(SGPropertyNode_ptr node, naRef handler,
|
FGNasalListener::FGNasalListener(SGPropertyNode_ptr node, naRef handler,
|
||||||
FGNasalSys* nasal, int key, int id,
|
FGNasalSys* nasal, int key, int id, int type) :
|
||||||
bool persistent) :
|
|
||||||
_node(node),
|
_node(node),
|
||||||
_handler(handler),
|
_handler(handler),
|
||||||
_gcKey(key),
|
_gcKey(key),
|
||||||
_id(id),
|
_id(id),
|
||||||
_nas(nasal),
|
_nas(nasal),
|
||||||
|
_type(type),
|
||||||
_active(0),
|
_active(0),
|
||||||
_dead(false),
|
_dead(false),
|
||||||
_first_call(true),
|
_first_call(true),
|
||||||
_persistent(persistent),
|
|
||||||
_last_int(0L),
|
_last_int(0L),
|
||||||
_last_float(0.0)
|
_last_float(0.0)
|
||||||
{
|
{
|
||||||
|
@ -1006,21 +1005,50 @@ FGNasalListener::~FGNasalListener()
|
||||||
_nas->gcRelease(_gcKey);
|
_nas->gcRelease(_gcKey);
|
||||||
}
|
}
|
||||||
|
|
||||||
void FGNasalListener::valueChanged(SGPropertyNode* node)
|
void FGNasalListener::call(SGPropertyNode* cmdarg, int argc, naRef* args)
|
||||||
{
|
{
|
||||||
// drop recursive listener calls
|
|
||||||
if(_active || _dead)
|
if(_active || _dead)
|
||||||
return;
|
return;
|
||||||
if(_persistent || changed(node) || _first_call) {
|
SG_LOG(SG_NASAL, SG_DEBUG, "trigger listener #" << _id);
|
||||||
SG_LOG(SG_NASAL, SG_DEBUG, "trigger listener #" << _id);
|
_active++;
|
||||||
_active++;
|
_nas->_cmdArg = cmdarg;
|
||||||
_nas->_cmdArg = node;
|
_nas->call(_handler, argc, args, naNil());
|
||||||
_nas->call(_handler, naNil());
|
_active--;
|
||||||
_active--;
|
}
|
||||||
|
|
||||||
|
void FGNasalListener::valueChanged(SGPropertyNode* node)
|
||||||
|
{
|
||||||
|
if(_type < 2 && node != _node)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if(_type > 0 || changed(_node) || _first_call) {
|
||||||
|
naRef arg[3];
|
||||||
|
arg[0] = _nas->propNodeGhost(_node);
|
||||||
|
arg[1] = _nas->propNodeGhost(node);
|
||||||
|
arg[2] = naNil();
|
||||||
|
call(_node, 3, arg);
|
||||||
}
|
}
|
||||||
_first_call = false;
|
_first_call = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void FGNasalListener::childAdded(SGPropertyNode* parent, SGPropertyNode* child)
|
||||||
|
{
|
||||||
|
naRef arg[3];
|
||||||
|
arg[0] = _nas->propNodeGhost(_node);
|
||||||
|
arg[1] = _nas->propNodeGhost(child);
|
||||||
|
arg[2] = naNum(1);
|
||||||
|
call(parent, 3, arg);
|
||||||
|
}
|
||||||
|
|
||||||
|
void FGNasalListener::childRemoved(SGPropertyNode* parent, SGPropertyNode* child)
|
||||||
|
{
|
||||||
|
naRef arg[3];
|
||||||
|
arg[0] = _nas->propNodeGhost(_node);
|
||||||
|
arg[1] = _nas->propNodeGhost(child);
|
||||||
|
arg[2] = naNum(0);
|
||||||
|
call(parent, 3, arg);
|
||||||
|
}
|
||||||
|
|
||||||
bool FGNasalListener::changed(SGPropertyNode* node)
|
bool FGNasalListener::changed(SGPropertyNode* node)
|
||||||
{
|
{
|
||||||
SGPropertyNode::Type type = node->getType();
|
SGPropertyNode::Type type = node->getType();
|
||||||
|
|
|
@ -58,7 +58,7 @@ public:
|
||||||
|
|
||||||
void deleteModule(const char* moduleName);
|
void deleteModule(const char* moduleName);
|
||||||
|
|
||||||
naRef call(naRef code, naRef locals);
|
naRef call(naRef code, int argc, naRef* args, naRef locals);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
friend class FGNasalScript;
|
friend class FGNasalScript;
|
||||||
|
@ -132,23 +132,27 @@ private:
|
||||||
class FGNasalListener : public SGPropertyChangeListener {
|
class FGNasalListener : public SGPropertyChangeListener {
|
||||||
public:
|
public:
|
||||||
FGNasalListener(SGPropertyNode_ptr node, naRef handler,
|
FGNasalListener(SGPropertyNode_ptr node, naRef handler,
|
||||||
FGNasalSys* nasal, int key, int id, bool persistent);
|
FGNasalSys* nasal, int key, int id, int type);
|
||||||
|
|
||||||
~FGNasalListener();
|
~FGNasalListener();
|
||||||
void valueChanged(SGPropertyNode* node);
|
void valueChanged(SGPropertyNode* node);
|
||||||
bool changed(SGPropertyNode* node);
|
void childAdded(SGPropertyNode* parent, SGPropertyNode* child);
|
||||||
|
void childRemoved(SGPropertyNode* parent, SGPropertyNode* child);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
bool changed(SGPropertyNode* node);
|
||||||
|
void call(SGPropertyNode* cmdarg, int argc, naRef* args);
|
||||||
|
|
||||||
friend class FGNasalSys;
|
friend class FGNasalSys;
|
||||||
SGPropertyNode_ptr _node;
|
SGPropertyNode_ptr _node;
|
||||||
naRef _handler;
|
naRef _handler;
|
||||||
int _gcKey;
|
int _gcKey;
|
||||||
int _id;
|
int _id;
|
||||||
FGNasalSys* _nas;
|
FGNasalSys* _nas;
|
||||||
|
int _type;
|
||||||
unsigned int _active;
|
unsigned int _active;
|
||||||
bool _dead;
|
bool _dead;
|
||||||
bool _first_call;
|
bool _first_call;
|
||||||
bool _persistent;
|
|
||||||
long _last_int;
|
long _last_int;
|
||||||
double _last_float;
|
double _last_float;
|
||||||
string _last_string;
|
string _last_string;
|
||||||
|
|
Loading…
Add table
Reference in a new issue