mirror of
https://port.numenaute.org/aleajactaest/khanat-opennel-code.git
synced 2025-01-01 21:53:58 +00:00
Avoid having to use 'set' action handler, which parses the value expression on every use, in interface links by implementing use of cdb nodes as targets
--HG-- branch : kaetemi-optimize
This commit is contained in:
parent
19a8b48355
commit
5a9537dfcc
6 changed files with 119 additions and 9 deletions
|
@ -66,6 +66,11 @@ namespace NLGUI
|
||||||
*/
|
*/
|
||||||
bool affect(const CInterfaceExprValue &value);
|
bool affect(const CInterfaceExprValue &value);
|
||||||
};
|
};
|
||||||
|
struct CCDBTargetInfo
|
||||||
|
{
|
||||||
|
NLMISC::CRefPtr<NLMISC::CCDBNodeLeaf> Leaf;
|
||||||
|
std::string LeafName;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
/// Updates triggered interface links when triggered by the observed branch
|
/// Updates triggered interface links when triggered by the observed branch
|
||||||
|
@ -85,7 +90,7 @@ namespace NLGUI
|
||||||
* If there are no target element, the link is permanent (removed at exit)
|
* If there are no target element, the link is permanent (removed at exit)
|
||||||
* NB : The target is not updated during this call.
|
* NB : The target is not updated during this call.
|
||||||
*/
|
*/
|
||||||
bool init(const std::vector<CTargetInfo> &targets, const std::string &expr, const std::string &actionHandler, const std::string &ahParams, const std::string &ahCond, CInterfaceGroup *parent);
|
bool init(const std::vector<CTargetInfo> &targets, const std::vector<CCDBTargetInfo> &cdbTargets, const std::string &expr, const std::string &actionHandler, const std::string &ahParams, const std::string &ahCond, CInterfaceGroup *parent);
|
||||||
// force all the links that have been created to update their targets. This can be called when the interface has been loaded, and when the databse entries have been retrieved.
|
// force all the links that have been created to update their targets. This can be called when the interface has been loaded, and when the databse entries have been retrieved.
|
||||||
static void updateAllLinks();
|
static void updateAllLinks();
|
||||||
// force all trigered links to be updated
|
// force all trigered links to be updated
|
||||||
|
@ -119,6 +124,7 @@ namespace NLGUI
|
||||||
* \return true if all targets are valid
|
* \return true if all targets are valid
|
||||||
*/
|
*/
|
||||||
static bool splitLinkTargets(const std::string &targets, CInterfaceGroup *parentGroup, std::vector<CInterfaceLink::CTargetInfo> &targetsVect);
|
static bool splitLinkTargets(const std::string &targets, CInterfaceGroup *parentGroup, std::vector<CInterfaceLink::CTargetInfo> &targetsVect);
|
||||||
|
static bool splitLinkTargetsExt(const std::string &targets, CInterfaceGroup *parentGroup, std::vector<CInterfaceLink::CTargetInfo> &targetsVect, std::vector<CInterfaceLink::CCDBTargetInfo> &cdbTargetsVect);
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
private:
|
private:
|
||||||
friend struct CRemoveTargetPred;
|
friend struct CRemoveTargetPred;
|
||||||
|
@ -135,6 +141,7 @@ namespace NLGUI
|
||||||
typedef std::vector<NLMISC::ICDBNode *> TNodeVect;
|
typedef std::vector<NLMISC::ICDBNode *> TNodeVect;
|
||||||
private:
|
private:
|
||||||
std::vector<CTarget> _Targets;
|
std::vector<CTarget> _Targets;
|
||||||
|
std::vector<CCDBTargetInfo> _CDBTargets;
|
||||||
TNodeVect _ObservedNodes;
|
TNodeVect _ObservedNodes;
|
||||||
std::string _Expr;
|
std::string _Expr;
|
||||||
CInterfaceExprNode *_ParseTree;
|
CInterfaceExprNode *_ParseTree;
|
||||||
|
|
|
@ -2325,7 +2325,8 @@ namespace NLGUI
|
||||||
_LUAOnDbChange[dbList]= newLink;
|
_LUAOnDbChange[dbList]= newLink;
|
||||||
// Init and attach to list of untargeted links
|
// Init and attach to list of untargeted links
|
||||||
std::vector<CInterfaceLink::CTargetInfo> noTargets;
|
std::vector<CInterfaceLink::CTargetInfo> noTargets;
|
||||||
newLink->init(noTargets, NLMISC::toString("depends(%s)", dbList.c_str()), "lua", script, "", this);
|
std::vector<CInterfaceLink::CCDBTargetInfo> noCdbTargets;
|
||||||
|
newLink->init(noTargets, noCdbTargets, NLMISC::toString("depends(%s)", dbList.c_str()), "lua", script, "", this);
|
||||||
}
|
}
|
||||||
|
|
||||||
// ------------------------------------------------------------------------------------------------
|
// ------------------------------------------------------------------------------------------------
|
||||||
|
|
|
@ -194,7 +194,7 @@ namespace NLGUI
|
||||||
}
|
}
|
||||||
|
|
||||||
//===========================================================
|
//===========================================================
|
||||||
bool CInterfaceLink::init(const std::vector<CTargetInfo> &targets, const std::string &expr, const std::string &actionHandler, const std::string &ahParams, const std::string &ahCond, CInterfaceGroup *parentGroup)
|
bool CInterfaceLink::init(const std::vector<CTargetInfo> &targets, const std::vector<CCDBTargetInfo> &cdbTargets, const std::string &expr, const std::string &actionHandler, const std::string &ahParams, const std::string &ahCond, CInterfaceGroup *parentGroup)
|
||||||
{
|
{
|
||||||
CInterfaceExprValue result;
|
CInterfaceExprValue result;
|
||||||
// Build the parse tree
|
// Build the parse tree
|
||||||
|
@ -240,6 +240,7 @@ namespace NLGUI
|
||||||
// There are no target for this link, so, put in a dedicated list to ensure that the link will be destroyed at exit
|
// There are no target for this link, so, put in a dedicated list to ensure that the link will be destroyed at exit
|
||||||
_LinksWithNoTarget.push_back(TLinkSmartPtr(this));
|
_LinksWithNoTarget.push_back(TLinkSmartPtr(this));
|
||||||
}
|
}
|
||||||
|
_CDBTargets = cdbTargets;
|
||||||
|
|
||||||
// create observers
|
// create observers
|
||||||
createObservers(_ObservedNodes);
|
createObservers(_ObservedNodes);
|
||||||
|
@ -365,12 +366,41 @@ namespace NLGUI
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if (_CDBTargets.size())
|
||||||
|
{
|
||||||
|
CInterfaceExprValue resultCopy = result;
|
||||||
|
if (resultCopy.toInteger())
|
||||||
|
{
|
||||||
|
sint64 resultValue = resultCopy.getInteger();
|
||||||
|
for (uint k = 0; k < _CDBTargets.size(); ++k)
|
||||||
|
{
|
||||||
|
NLMISC::CCDBNodeLeaf *node = _CDBTargets[k].Leaf;
|
||||||
|
if (!node)
|
||||||
|
{
|
||||||
|
node = _CDBTargets[k].Leaf = NLGUI::CDBManager::getInstance()->getDbProp(_CDBTargets[k].LeafName, false);
|
||||||
|
}
|
||||||
|
if (node)
|
||||||
|
{
|
||||||
|
// assuming setvalue64 always works
|
||||||
|
node->setValue64(resultValue);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
nlwarning("CInterfaceLink::update: Node does not exist: '%s'", _CDBTargets[k].LeafName.c_str());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
nlwarning("CInterfaceLink::update: Result conversion to db target failed");
|
||||||
|
}
|
||||||
|
}
|
||||||
// if there's an action handler, execute it
|
// if there's an action handler, execute it
|
||||||
if (!_ActionHandler.empty())
|
if (!_ActionHandler.empty())
|
||||||
{
|
{
|
||||||
// If there is a condition, test it.
|
// If there is a condition, test it.
|
||||||
bool launch = _AHCond.empty();
|
bool launch = _AHCond.empty();
|
||||||
if (_AHCondParsed)
|
if (_AHCondParsed) // todo: maybe makes more sense to make condition also cover target
|
||||||
{
|
{
|
||||||
CInterfaceExprValue result;
|
CInterfaceExprValue result;
|
||||||
_AHCondParsed->eval(result);
|
_AHCondParsed->eval(result);
|
||||||
|
@ -525,6 +555,11 @@ namespace NLGUI
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
std::string::size_type lastPos = targetNames[k].find_last_not_of(" ");
|
std::string::size_type lastPos = targetNames[k].find_last_not_of(" ");
|
||||||
|
if (startPos >= lastPos)
|
||||||
|
{
|
||||||
|
nlwarning("<splitLinkTargets> empty target encountered");
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
if (!splitLinkTarget(targetNames[k].substr(startPos, lastPos - startPos+1), parentGroup, ti.PropertyName, ti.Elem))
|
if (!splitLinkTarget(targetNames[k].substr(startPos, lastPos - startPos+1), parentGroup, ti.PropertyName, ti.Elem))
|
||||||
{
|
{
|
||||||
|
@ -539,6 +574,70 @@ namespace NLGUI
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// ***************************************************************************
|
||||||
|
bool CInterfaceLink::splitLinkTargetsExt(const std::string &targets, CInterfaceGroup *parentGroup,std::vector<CInterfaceLink::CTargetInfo> &targetsVect, std::vector<CInterfaceLink::CCDBTargetInfo> &cdbTargetsVect)
|
||||||
|
{
|
||||||
|
std::vector<std::string> targetNames;
|
||||||
|
NLMISC::splitString(targets, ",", targetNames);
|
||||||
|
targetsVect.clear();
|
||||||
|
targetsVect.reserve(targetNames.size());
|
||||||
|
cdbTargetsVect.clear(); // no reserve because less used
|
||||||
|
bool everythingOk = true;
|
||||||
|
for (uint k = 0; k < targetNames.size(); ++k)
|
||||||
|
{
|
||||||
|
std::string::size_type startPos = targetNames[k].find_first_not_of(" ");
|
||||||
|
if(startPos == std::string::npos)
|
||||||
|
{
|
||||||
|
// todo hulud interface syntax error
|
||||||
|
nlwarning("<splitLinkTargets> empty target encountered");
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
std::string::size_type lastPos = targetNames[k].find_last_not_of(" ");
|
||||||
|
if (startPos >= (lastPos+1))
|
||||||
|
{
|
||||||
|
nlwarning("<splitLinkTargets> empty target encountered");
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (targetNames[k][startPos] == '@')
|
||||||
|
{
|
||||||
|
CInterfaceLink::CCDBTargetInfo ti;
|
||||||
|
ti.LeafName = targetNames[k].substr((startPos+1), (lastPos+1) - (startPos+1));
|
||||||
|
// Do not allow Write on SERVER: or LOCAL:
|
||||||
|
static const std::string dbServer= "SERVER:";
|
||||||
|
static const std::string dbLocal= "LOCAL:";
|
||||||
|
static const std::string dbLocalR2= "LOCAL:R2";
|
||||||
|
if( (0==ti.LeafName.compare(0, dbServer.size(), dbServer)) ||
|
||||||
|
(0==ti.LeafName.compare(0, dbLocal.size(), dbLocal))
|
||||||
|
)
|
||||||
|
{
|
||||||
|
if (0!=ti.LeafName.compare(0, dbLocalR2.size(), dbLocalR2))
|
||||||
|
{
|
||||||
|
//nlwarning("You are not allowed to write on 'SERVER:...' or 'LOCAL:...' database");
|
||||||
|
nlstop;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
ti.Leaf = NLGUI::CDBManager::getInstance()->getDbProp(ti.LeafName, false);
|
||||||
|
cdbTargetsVect.push_back(ti);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
CInterfaceLink::CTargetInfo ti;
|
||||||
|
if (!splitLinkTarget(targetNames[k].substr(startPos, lastPos - startPos+1), parentGroup, ti.PropertyName, ti.Elem))
|
||||||
|
{
|
||||||
|
// todo hulud interface syntax error
|
||||||
|
nlwarning("<splitLinkTargets> Can't get link target");
|
||||||
|
everythingOk = false;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
targetsVect.push_back(ti);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return everythingOk;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
//===========================================================
|
//===========================================================
|
||||||
void CInterfaceLink::checkNbRefs()
|
void CInterfaceLink::checkNbRefs()
|
||||||
{
|
{
|
||||||
|
|
|
@ -997,6 +997,7 @@ namespace NLGUI
|
||||||
|
|
||||||
|
|
||||||
std::vector<CInterfaceLink::CTargetInfo> targets;
|
std::vector<CInterfaceLink::CTargetInfo> targets;
|
||||||
|
std::vector<CInterfaceLink::CCDBTargetInfo> cdbTargets;
|
||||||
|
|
||||||
ptr = (char*) xmlGetProp (cur, (xmlChar*)"target");
|
ptr = (char*) xmlGetProp (cur, (xmlChar*)"target");
|
||||||
std::string target;
|
std::string target;
|
||||||
|
@ -1004,7 +1005,7 @@ namespace NLGUI
|
||||||
{
|
{
|
||||||
target = std::string( (const char*)ptr );
|
target = std::string( (const char*)ptr );
|
||||||
if( !editorMode )
|
if( !editorMode )
|
||||||
CInterfaceLink::splitLinkTargets(std::string((const char*)ptr), parentGroup, targets);
|
CInterfaceLink::splitLinkTargetsExt(std::string((const char*)ptr), parentGroup, targets, cdbTargets);
|
||||||
}
|
}
|
||||||
|
|
||||||
// optional action handler
|
// optional action handler
|
||||||
|
@ -1022,7 +1023,7 @@ namespace NLGUI
|
||||||
if( !editorMode )
|
if( !editorMode )
|
||||||
{
|
{
|
||||||
CInterfaceLink *il = new CInterfaceLink;
|
CInterfaceLink *il = new CInterfaceLink;
|
||||||
il->init(targets, expr, action, params, cond, parentGroup); // init will add 'il' in the list of link present in 'elm'
|
il->init(targets, cdbTargets, expr, action, params, cond, parentGroup); // init will add 'il' in the list of link present in 'elm'
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
|
@ -425,14 +425,15 @@ class CActionHandlerAddLink : public IActionHandler
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<CInterfaceLink::CTargetInfo> targetsVect;
|
std::vector<CInterfaceLink::CTargetInfo> targetsVect;
|
||||||
bool result = CInterfaceLink::splitLinkTargets(targets, parentGroup, targetsVect);
|
std::vector<CInterfaceLink::CCDBTargetInfo> cdbTargetsVect;
|
||||||
|
bool result = CInterfaceLink::splitLinkTargetsExt(targets, parentGroup, targetsVect, cdbTargetsVect);
|
||||||
if (!result)
|
if (!result)
|
||||||
{
|
{
|
||||||
nlwarning("<CActionHandlerAddLink> Couldn't parse all links");
|
nlwarning("<CActionHandlerAddLink> Couldn't parse all links");
|
||||||
}
|
}
|
||||||
// add the link
|
// add the link
|
||||||
CInterfaceLink *il = new CInterfaceLink;
|
CInterfaceLink *il = new CInterfaceLink;
|
||||||
il->init(targetsVect, expr, ah, ahparam, ahcond, parentGroup);
|
il->init(targetsVect, cdbTargetsVect, expr, ah, ahparam, ahcond, parentGroup);
|
||||||
CInterfaceManager *im = CInterfaceManager::getInstance();
|
CInterfaceManager *im = CInterfaceManager::getInstance();
|
||||||
CWidgetManager::getInstance()->getParser()->addLink(il, id);
|
CWidgetManager::getInstance()->getParser()->addLink(il, id);
|
||||||
il->update();
|
il->update();
|
||||||
|
|
|
@ -558,7 +558,8 @@ void CPeopleInterraction::createTeamList()
|
||||||
{
|
{
|
||||||
CInterfaceLink *il = new CInterfaceLink;
|
CInterfaceLink *il = new CInterfaceLink;
|
||||||
vector<CInterfaceLink::CTargetInfo> targets;
|
vector<CInterfaceLink::CTargetInfo> targets;
|
||||||
il->init(targets, sExpr, sAction, sParams, sCond, TeamChat->getContainer());
|
vector<CInterfaceLink::CCDBTargetInfo> cdbTargets;
|
||||||
|
il->init(targets, cdbTargets, sExpr, sAction, sParams, sCond, TeamChat->getContainer());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue