Use configured resolution for login/outgame/ingame
[ryzomcore.git] / ryzom / tools / pd_parser / templatizer.h
blobe6b67708b7d9dc71f80fc764f612a0aa74bc432f
1 // Ryzom - MMORPG Framework <http://dev.ryzom.com/projects/ryzom/>
2 // Copyright (C) 2010 Winch Gate Property Limited
3 //
4 // This program is free software: you can redistribute it and/or modify
5 // it under the terms of the GNU Affero General Public License as
6 // published by the Free Software Foundation, either version 3 of the
7 // License, or (at your option) any later version.
8 //
9 // This program is distributed in the hope that it will be useful,
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 // GNU Affero General Public License for more details.
14 // You should have received a copy of the GNU Affero General Public License
15 // along with this program. If not, see <http://www.gnu.org/licenses/>.
17 #ifndef NL_TEMPLATIZER_H
18 #define NL_TEMPLATIZER_H
20 #include <nel/misc/types_nl.h>
21 #include <nel/misc/common.h>
22 #include <nel/misc/debug.h>
23 #include <nel/misc/eval_num_expr.h>
25 #include <vector>
26 #include <string>
27 #include <map>
29 class ITemplatizerBloc;
31 const char EnvSeparator = '/';
40 /**
41 * A Templatizer Env
43 class CTemplatizerEnv : public NLMISC::CEvalNumExpr
45 public:
47 /// Constructor
48 CTemplatizerEnv(CTemplatizerEnv* parent) : Parent(parent), CurrentArrayNode(0) { }
50 /// Destructor
51 virtual ~CTemplatizerEnv();
53 /// Clear Env
54 virtual void clear();
56 /// Get value
57 virtual std::string get(const std::string& name);
59 /// Set value
60 template<typename T>
61 void set(const std::string& name, const T& value)
63 std::string::size_type dotpos = name.find(EnvSeparator);
64 std::string child = name.substr(0, dotpos);
66 if (dotpos == std::string::npos)
68 setAsRawText(name, NLMISC::toString(value));
70 else
72 getEnv(child)->set(name.substr(dotpos+1), value);
76 /// Set a Define
77 void define(const std::string& name)
79 set(name, 1);
82 /// Set a Conditional Define
83 void define(bool isdef, const std::string& name)
85 if (isdef)
86 set(name, 1);
89 /// Does Variable exist?
90 virtual bool exists(const std::string& name) const
92 TValueMap::const_iterator it = Values.find(name);
93 if (it == Values.end())
94 return (Parent == NULL ? false : Parent->exists(name));
95 return true;
98 /// Does Sub Environment exist?
99 virtual bool envExists(const std::string& name) const
101 std::string::size_type dotpos = name.find(EnvSeparator);
102 std::string child = name.substr(0, dotpos);
104 if (child.empty())
105 return true;
107 TEnvMap::const_iterator it = Envs.find(child);
108 if (it == Envs.end())
109 return false;
111 return (dotpos == std::string::npos) ? true : (*it).second->envExists(name.substr(dotpos+1));
114 /// Enter Sub Env, like getEnv() but it doesn't look in parent, and always goes in current env
115 virtual CTemplatizerEnv* getSubEnv(const std::string& name)
117 std::string::size_type dotpos = name.find(EnvSeparator);
118 std::string child = name.substr(0, dotpos);
120 if (child.empty())
121 return this;
123 CTemplatizerEnv* env = NULL;
125 if (child == ".")
127 env = this;
129 else if (child == "..")
131 env = (Parent != NULL ? Parent : this);
133 else if (child == "...")
135 env = getRootEnv();
137 else
139 TEnvMap::iterator it = Envs.find(child);
140 if (it != Envs.end())
142 env = (*it).second;
144 else
146 env = new CTemplatizerEnv(this);
147 Envs[child] = env;
152 return (dotpos == std::string::npos) ? env : env->getSubEnv(name.substr(dotpos+1));
155 /// Get Sub Env
156 virtual CTemplatizerEnv* getEnv(const std::string& name)
158 std::string::size_type dotpos = name.find(EnvSeparator);
159 std::string child = name.substr(0, dotpos);
161 if (child.empty())
162 return this;
164 if (child == ".")
166 return (dotpos == std::string::npos) ? this : this->getSubEnv(name.substr(dotpos+1));
168 else if (child == "..")
170 CTemplatizerEnv* env = (Parent != NULL ? Parent : this);
171 return (dotpos == std::string::npos) ? env : env->getSubEnv(name.substr(dotpos+1));
173 else if (child == "...")
175 CTemplatizerEnv* env = getRootEnv();
176 return (dotpos == std::string::npos) ? env : env->getSubEnv(name.substr(dotpos+1));
178 else
180 TEnvMap::iterator it = Envs.find(child);
181 if (it != Envs.end())
183 return (dotpos == std::string::npos) ? (*it).second : (*it).second->getSubEnv(name.substr(dotpos+1));
185 else
187 return Parent != NULL ? Parent->getEnv(name) : getSubEnv(name);
192 /// Get Sub Env
193 CTemplatizerEnv* getEnv(uint node)
195 return getEnv(NLMISC::toString("%08X", node));
198 /// Evaluate string (string replacement)
199 virtual std::string eval(const std::string& text);
201 /// Get Next Array Node
202 CTemplatizerEnv* nextArrayNode(const std::string& array)
204 CTemplatizerEnv* aenv = getSubEnv(array);
205 uint node = (aenv->CurrentArrayNode)++;
206 return aenv->getSubEnv(NLMISC::toString("%08X", node));
209 /// Set Sub Env
210 virtual void setSubEnv(const std::string& name, CTemplatizerEnv* subenv)
212 Envs[name] = subenv;
215 /// Get Parent Env
216 virtual CTemplatizerEnv* getParent()
218 return Parent;
221 public:
223 /// Parent Env
224 CTemplatizerEnv* Parent;
226 typedef std::map<std::string, ITemplatizerBloc*> TValueMap;
227 typedef std::map<std::string, CTemplatizerEnv*> TEnvMap;
229 /// Contained Values
230 TValueMap Values;
232 /// Sub Env
233 TEnvMap Envs;
235 /// Get Root Env
236 virtual CTemplatizerEnv* getRootEnv()
238 CTemplatizerEnv* root = this;
239 while (root->getParent() != NULL)
240 root = root->getParent();
242 return root;
245 /// Current Array Node
246 uint CurrentArrayNode;
248 /// Set As Raw Text
249 virtual void setAsRawText(const std::string& name, const std::string& text);
251 /// Set Value Node
252 virtual void setValueNode(const std::string& name, ITemplatizerBloc* bloc)
254 Values[name] = bloc;
257 /// Get Value Node
258 virtual ITemplatizerBloc* getValueNode(const std::string& name)
260 ITemplatizerBloc* node = NULL;
261 CTemplatizerEnv* env = NULL;
262 return getValueNodeAndEnv(name, node, env) ? node : NULL;
265 /// Get Value Node
266 virtual bool getValueNodeAndEnv(const std::string& name, ITemplatizerBloc*& node, CTemplatizerEnv*& env)
268 std::string::size_type pos = name.find_last_of(EnvSeparator);
269 if (pos == std::string::npos)
271 node = getNode(name);
272 env = this;
273 while (node == NULL && env != NULL)
275 env = env->getParent();
276 if (env != NULL)
277 node = env->getNode(name);
280 else
282 env = getEnv(name.substr(0, pos));
283 if (env != NULL)
284 node = env->getNode(name.substr(pos+1));
287 return node != NULL && env != NULL;
290 virtual ITemplatizerBloc* getNode(const std::string& name)
292 TValueMap::iterator it = Values.find(name);
293 return it == Values.end() ? NULL : (*it).second;
296 virtual NLMISC::CEvalNumExpr::TReturnState evalValue (const char *value, double &result, uint32 userData);
301 * A Templatizer Env
303 class CTemplatizerRefEnv : public CTemplatizerEnv
305 public:
307 /// Constructor
308 CTemplatizerRefEnv(CTemplatizerEnv* ref) : CTemplatizerEnv(NULL), Reference(ref) { }
310 /// Clear Env
311 virtual void clear()
313 Reference = NULL;
316 /// Get value
317 virtual std::string get(const std::string& name)
319 return Reference->get(name);
322 /// Does Variable exist?
323 virtual bool exists(const std::string& name) const
325 return Reference->exists(name);
328 /// Does Sub Environment exist?
329 virtual bool envExists(const std::string& name) const
331 return Reference->envExists(name);
334 /// Get Sub Env
335 virtual CTemplatizerEnv* getEnv(const std::string& name)
337 return Reference->getEnv(name);
340 /// Evaluate string (string replacement)
341 virtual std::string eval(const std::string& text)
343 return Reference->eval(text);
346 /// Enter Sub Env, like getEnv() but it doesn't look in parent, and always goes in current env
347 virtual CTemplatizerEnv* getSubEnv(const std::string& name)
349 return Reference->getSubEnv(name);
352 /// Get Parent Env
353 virtual CTemplatizerEnv* getParent()
355 return Reference->getParent();
357 public:
359 CTemplatizerEnv* Reference;
361 /// Get Root Env
362 virtual CTemplatizerEnv* getRootEnv()
364 return Reference->getRootEnv();
367 /// Set As Raw Text
368 virtual void setAsRawText(const std::string& name, const std::string& text)
370 Reference->setAsRawText(name, text);
373 /// Set Value Node
374 virtual void setValueNode(const std::string& name, ITemplatizerBloc* bloc)
376 Reference->setValueNode(name, bloc);
379 /// Get Value Node
380 virtual ITemplatizerBloc* getValueNode(const std::string& name)
382 return Reference->getValueNode(name);
385 /// Get Value Node
386 virtual bool getValueNodeAndEnv(const std::string& name, ITemplatizerBloc*& node, CTemplatizerEnv*& env)
388 return Reference->getValueNodeAndEnv(name, node, env);
391 virtual ITemplatizerBloc* getNode(const std::string& name)
393 return Reference->getNode(name);
399 * <Class description>
400 * \author Benjamin Legros
401 * \author Nevrax France
402 * \date 2003
404 class CTemplatizer
406 public:
408 /// Constructor
409 CTemplatizer();
411 /// Destructor
412 ~CTemplatizer();
417 * Build templatizer from text
419 bool build(const char* text);
423 * Evaluate template and render to string
425 std::string eval();
429 * Set Value in env
431 template<typename T>
432 void set(const std::string& var, const T& value)
434 if (RootEnv == NULL)
435 return;
437 std::string::size_type pos = var.find_last_of(EnvSeparator);
439 if (pos == std::string::npos)
441 RootEnv->set(var, value);
443 else
445 RootEnv->getEnv(var.substr(0, pos))->set(var.substr(pos+1), value);
449 public:
451 ITemplatizerBloc* RootBloc;
453 CTemplatizerEnv* RootEnv;
459 class CTemplatizerParser
461 public:
463 CTemplatizerParser() : _Buffer(NULL), _Line(0), _Valid(false) { }
464 CTemplatizerParser(const CTemplatizerParser& ptr) : _Buffer(ptr._Buffer), _Line(ptr._Line), _Valid(ptr._Valid) { }
465 CTemplatizerParser(const char* buffer, uint linestart = 1) : _Buffer(buffer), _Line(linestart), _Valid(_Buffer != NULL) { }
467 char operator * () const { return *_Buffer; }
468 char operator [] (int i) const { return _Buffer[i]; }
470 CTemplatizerParser& operator = (const CTemplatizerParser& ptr)
472 _Buffer = ptr._Buffer;
473 _Line = ptr._Line;
474 _Valid = ptr._Valid;
475 return *this;
478 CTemplatizerParser& operator ++ ()
480 if (*_Buffer == '\0')
481 return *this;
483 if (*_Buffer == '\n')
484 ++_Line;
486 ++_Buffer;
487 return *this;
490 CTemplatizerParser operator ++ (int)
492 CTemplatizerParser ret(*this);
493 ++(*this);
494 return ret;
497 void invalidate() { _Valid = false; }
498 bool isValid() const { return _Valid; }
500 uint getLine() const { return _Line; }
502 private:
504 const char* _Buffer;
506 uint _Line;
508 bool _Valid;
516 * A Templatizer node
518 class ITemplatizerBloc
520 public:
522 /// Constructor
523 ITemplatizerBloc();
525 /// Destructor
526 virtual ~ITemplatizerBloc();
530 /// Evaluate node
531 virtual std::string eval(CTemplatizerEnv* env)
533 std::string res;
534 uint i;
535 for (i=0; i<Blocs.size(); ++i)
536 res += Blocs[i]->eval(env);
537 return res;
540 /// Get Text (assuming this is a raw text bloc)
541 virtual std::string getText(CTemplatizerEnv* env)
543 return "";
546 /// Get Param list
547 virtual const char** getDefParamList()
549 return NULL;
552 /// Get Actual Bloc (not a reference)
553 virtual ITemplatizerBloc* getActualBloc()
555 return this;
558 public:
560 std::string evalParam(const std::string& param, CTemplatizerEnv* env)
562 TParamMap::iterator it = Params.find(param);
563 if (it == Params.end())
564 return "";
565 return (*it).second->eval(env);
568 public:
570 /// Bloc types
571 enum TType
573 Text,
576 /// Bloc type
577 TType Type;
579 typedef std::vector<ITemplatizerBloc*> TBlocList;
580 typedef std::map<std::string, ITemplatizerBloc*> TParamMap;
582 /// Params
583 TParamMap Params;
585 /// Sub blocs
586 TBlocList Blocs;
589 /// Parse bloc
590 static ITemplatizerBloc* parseBloc(CTemplatizerParser& ptr);
592 /// Parse bloc header
593 virtual CTemplatizerParser parseHeader(CTemplatizerParser ptr);
595 /// Parse bloc internal data
596 virtual CTemplatizerParser parseInternal(CTemplatizerParser ptr);
598 /// Has A Internal Bloc of data
599 virtual bool hasInternal() const { return true; }
606 /// Root Templatizer
607 class CTemplatizerRootBloc : public ITemplatizerBloc
609 public:
613 /// Reference Node
614 class CTemplatizerReferenceBloc : public ITemplatizerBloc
616 public:
618 ITemplatizerBloc* Reference;
620 /// Constructor
621 CTemplatizerReferenceBloc(ITemplatizerBloc* ref = NULL) : Reference(ref) {}
623 /// Destructor
624 virtual ~CTemplatizerReferenceBloc()
626 Reference = NULL;
629 /// Evaluate node
630 virtual std::string eval(CTemplatizerEnv* env)
632 std::string name = evalParam("name", env);
633 std::string ref = evalParam("ref", env);
634 ITemplatizerBloc* refnode = env->getValueNode(ref);
635 if (refnode != NULL)
636 env->setValueNode(name, new CTemplatizerReferenceBloc(refnode));
637 else
638 nlwarning("Failed to create reference on '%s', not found", name.c_str());
639 return "";
642 /// Get Text (assuming this is a raw text bloc)
643 virtual std::string getText(CTemplatizerEnv* env)
645 return Reference->getText(env);
648 /// Get Param list
649 virtual const char** getDefParamList()
651 static const char* args[] = { "name", "ref" };
652 return (const char**)args;
655 /// Get Actual Bloc (not a reference)
656 virtual ITemplatizerBloc* getActualBloc()
658 return Reference->getActualBloc();
661 /// Has A Internal Bloc of data
662 virtual bool hasInternal() const { return false; }
666 /// RefEnv Bloc
667 class CTemplatizerRefEnvBloc : public ITemplatizerBloc
669 public:
671 /// Evaluate node
672 virtual std::string eval(CTemplatizerEnv* env)
674 std::string name = evalParam("name", env);
675 std::string ref = evalParam("ref", env);
677 CTemplatizerEnv* refenv = env->getEnv(ref);
678 if (refenv != NULL)
679 env->setSubEnv(name, new CTemplatizerRefEnv(refenv));
680 else
681 nlwarning("Failed to create reference on env '%s', not found", name.c_str());
682 return "";
685 /// Get Param list
686 virtual const char** getDefParamList()
688 static const char* args[] = { "name", "ref" };
689 return (const char**)args;
692 /// Has A Internal Bloc of data
693 virtual bool hasInternal() const { return false; }
701 * Comment Bloc
703 class CTemplatizerCommentBloc : public ITemplatizerBloc
705 public:
707 virtual std::string eval(CTemplatizerEnv* env)
709 return "";
712 /// Parse bloc internal data
713 virtual CTemplatizerParser parseInternal(CTemplatizerParser ptr);
719 * Raw Text Bloc
721 class CTemplatizerRawTextBloc : public ITemplatizerBloc
723 public:
725 std::string Text;
727 virtual std::string eval(CTemplatizerEnv* env)
729 return Text;
732 virtual std::string getText(CTemplatizerEnv* env)
734 return Text;
738 // Set As Raw Text
739 inline void CTemplatizerEnv::setAsRawText(const std::string& name, const std::string& text)
741 CTemplatizerRawTextBloc* bloc = new CTemplatizerRawTextBloc();
742 bloc->Text = text;
743 setValueNode(name, bloc);
746 // Get value
747 inline std::string CTemplatizerEnv::get(const std::string& name)
749 ITemplatizerBloc* bloc = getValueNode(name);
751 return (bloc == NULL) ? std::string("") : bloc->getText(this);
754 // eval num expr override
755 inline NLMISC::CEvalNumExpr::TReturnState CTemplatizerEnv::evalValue (const char *value, double &result, uint32 userData)
757 if (*value != '$')
759 return NLMISC::CEvalNumExpr::ValueError;
762 std::string strvalue = get(value+1);
764 if (sscanf(strvalue.c_str(), "%lf", &result) != 1)
766 result = (strvalue.empty() ? 0.0 : 1.0);
769 return NLMISC::CEvalNumExpr::NoError;
775 * Text Bloc
777 class CTemplatizerTextBloc : public ITemplatizerBloc
779 public:
781 std::string Text;
783 virtual std::string eval(CTemplatizerEnv* env)
785 return env->eval(Text);
788 virtual std::string getText(CTemplatizerEnv* env)
790 return env->eval(Text);
793 /// Parse bloc internal data
794 virtual CTemplatizerParser parseInternal(CTemplatizerParser ptr);
801 * Sub bloc
803 class CTemplatizerSubBloc : public ITemplatizerBloc
805 public:
807 virtual std::string eval(CTemplatizerEnv* env)
809 std::string subname = evalParam("name", env);
810 CTemplatizerEnv* subenv = env->getSubEnv(subname);
812 return ITemplatizerBloc::eval(subenv);
815 /// Get Param list
816 virtual const char** getDefParamList()
818 static const char* args[] = { "name" };
819 return (const char**)args;
825 * Loop bloc
827 class CTemplatizerLoopBloc : public ITemplatizerBloc
829 public:
831 virtual std::string eval(CTemplatizerEnv* env)
833 std::string subname = evalParam("name", env);
834 CTemplatizerEnv* subenv = env->getSubEnv(subname);
836 std::string res;
838 CTemplatizerEnv::TEnvMap::iterator it;
839 for (it=subenv->Envs.begin(); it!=subenv->Envs.end(); ++it)
840 res += ITemplatizerBloc::eval((*it).second);
842 return res;
845 /// Get Param list
846 virtual const char** getDefParamList()
848 static const char* args[] = { "name" };
849 return (const char**)args;
855 * IfDefEnv bloc
857 class CTemplatizerIfDefEnvBloc : public ITemplatizerBloc
859 public:
861 virtual std::string eval(CTemplatizerEnv* env)
863 std::string subname = evalParam("name", env);
864 std::string evalinsub = evalParam("evalinsub", env);
866 if (env->envExists(subname))
868 sint eval;
869 NLMISC::fromString(evalinsub, eval);
870 CTemplatizerEnv* subenv = (eval ? env->getEnv(subname) : env);
871 return ITemplatizerBloc::eval(subenv);
874 return "";
877 /// Get Param list
878 virtual const char** getDefParamList()
880 static const char* args[] = { "name", "evalinsub" };
881 return (const char**)args;
887 * IfDef bloc
889 class CTemplatizerIfDefBloc : public ITemplatizerBloc
891 public:
893 virtual std::string eval(CTemplatizerEnv* env)
895 std::string varname = evalParam("name", env);
897 if (env->exists(varname))
899 return ITemplatizerBloc::eval(env);
902 return "";
905 /// Get Param list
906 virtual const char** getDefParamList()
908 static const char* args[] = { "name" };
909 return (const char**)args;
915 * IfDefEnv bloc
917 class CTemplatizerIfNotDefEnvBloc : public ITemplatizerBloc
919 public:
921 virtual std::string eval(CTemplatizerEnv* env)
923 std::string subname = evalParam("name", env);
925 if (!env->envExists(subname))
927 return ITemplatizerBloc::eval(env);
930 return "";
933 /// Get Param list
934 virtual const char** getDefParamList()
936 static const char* args[] = { "name" };
937 return (const char**)args;
943 * IfDef bloc
945 class CTemplatizerIfNotDefBloc : public ITemplatizerBloc
947 public:
949 virtual std::string eval(CTemplatizerEnv* env)
951 std::string varname = evalParam("name", env);
953 if (!env->exists(varname))
955 return ITemplatizerBloc::eval(env);
958 return "";
961 /// Get Param list
962 virtual const char** getDefParamList()
964 static const char* args[] = { "name" };
965 return (const char**)args;
971 * Switch bloc
973 class CTemplatizerSwitchBloc : public ITemplatizerBloc
975 public:
977 virtual std::string eval(CTemplatizerEnv* env)
979 std::string switchvalue = evalParam("value", env);
981 uint i;
982 for (i=0; i<Blocs.size(); ++i)
983 if (Blocs[i]->evalParam("case", env) == switchvalue)
984 return Blocs[i]->eval(env);
986 return "";
989 /// Get Param list
990 virtual const char** getDefParamList()
992 static const char* args[] = { "value" };
993 return (const char**)args;
998 * File bloc
1000 class CTemplatizerFileBloc : public ITemplatizerBloc
1002 public:
1004 virtual std::string eval(CTemplatizerEnv* env)
1006 std::string clearfile = evalParam("clear", env);
1007 std::string filename = evalParam("name", env);
1009 std::string result = ITemplatizerBloc::eval(env);
1011 FILE* f;
1012 f = NLMISC::nlfopen(filename, (clearfile == "true" ? "w" : "a"));
1013 if (f != NULL)
1015 fwrite(result.c_str(), 1, result.size(), f);
1016 fclose(f);
1019 return result;
1022 /// Get Param list
1023 virtual const char** getDefParamList()
1025 static const char* args[] = { "name" };
1026 return (const char**)args;
1031 * Set bloc
1033 class CTemplatizerSetBloc : public ITemplatizerBloc
1035 public:
1037 virtual std::string eval(CTemplatizerEnv* env)
1039 std::string var = evalParam("name", env);
1040 std::string result = ITemplatizerBloc::eval(env);
1042 env->set(var, result);
1044 return "";
1047 /// Get Param list
1048 virtual const char** getDefParamList()
1050 static const char* args[] = { "name" };
1051 return (const char**)args;
1056 * Append bloc
1058 class CTemplatizerAppendBloc : public ITemplatizerBloc
1060 public:
1062 virtual std::string eval(CTemplatizerEnv* env)
1064 std::string var = evalParam("name", env);
1065 std::string result = ITemplatizerBloc::eval(env);
1067 ITemplatizerBloc* bloc = env->getValueNode(var);
1068 if (bloc == NULL)
1069 return "";
1071 CTemplatizerRawTextBloc* text = dynamic_cast<CTemplatizerRawTextBloc*>(bloc->getActualBloc());
1072 if (text == NULL)
1073 return "";
1075 text->Text += result;
1077 return "";
1080 /// Get Param list
1081 virtual const char** getDefParamList()
1083 static const char* args[] = { "name" };
1084 return (const char**)args;
1089 * Define Bloc
1091 class CTemplatizerDefineBloc : public ITemplatizerBloc
1093 public:
1095 virtual std::string eval(CTemplatizerEnv* env)
1097 std::string name = evalParam("name", env);
1098 env->setValueNode(name, new CTemplatizerReferenceBloc(this));
1099 return "";
1102 virtual std::string getText(CTemplatizerEnv* env)
1104 return ITemplatizerBloc::eval(env);
1107 /// Get Param list
1108 virtual const char** getDefParamList()
1110 static const char* args[] = { "name" };
1111 return (const char**)args;
1116 * If Bloc
1118 class CTemplatizerIfBloc : public ITemplatizerBloc
1120 public:
1122 virtual std::string eval(CTemplatizerEnv* env)
1124 std::string value = evalParam("cond", env);
1125 double result;
1126 NLMISC::CEvalNumExpr::TReturnState res = env->evalExpression(value.c_str(), result, NULL);
1128 if (res == NLMISC::CEvalNumExpr::NoError && result != 0.0)
1130 return ITemplatizerBloc::eval(env);
1132 else
1134 return "";
1138 /// Get Param list
1139 virtual const char** getDefParamList()
1141 static const char* args[] = { "cond" };
1142 return (const char**)args;
1147 * If Not Bloc
1149 class CTemplatizerIfNotBloc : public ITemplatizerBloc
1151 public:
1153 virtual std::string eval(CTemplatizerEnv* env)
1155 std::string value = evalParam("cond", env);
1157 if (value.empty())
1159 return ITemplatizerBloc::eval(env);
1161 else
1163 return "";
1167 /// Get Param list
1168 virtual const char** getDefParamList()
1170 static const char* args[] = { "cond" };
1171 return (const char**)args;
1176 * Join bloc
1178 class CTemplatizerJoinBloc : public ITemplatizerBloc
1180 public:
1182 virtual std::string eval(CTemplatizerEnv* env)
1184 std::string sep = evalParam("separator", env);
1186 std::string res;
1187 uint i;
1188 for (i=0; i<Blocs.size(); ++i)
1190 std::string token = Blocs[i]->eval(env);
1192 if (token.empty())
1193 continue;
1195 if (!res.empty())
1196 res += sep;
1198 res += token;
1200 return res;
1203 /// Get Param list
1204 virtual const char** getDefParamList()
1206 static const char* args[] = { "separator" };
1207 return (const char**)args;
1212 * User Defined function call
1214 class CTemplatizerUserFunctionBloc : public ITemplatizerBloc
1216 public:
1218 CTemplatizerUserFunctionBloc(const std::string& name) : Name(name) {}
1220 std::string Name;
1222 virtual std::string eval(CTemplatizerEnv* env)
1224 ITemplatizerBloc* func = NULL;
1225 CTemplatizerEnv* fenv = NULL;
1226 if (!env->getValueNodeAndEnv(Name, func, fenv))
1228 nlwarning("Unknown user function '%s'", Name.c_str());
1229 return "";
1232 // subenv is child of object env, not of current env
1233 CTemplatizerEnv* subenv = new CTemplatizerEnv(fenv);
1235 // deport params in subenv
1236 // \todo : eval param in current env
1237 TParamMap::iterator it;
1238 for (it=Params.begin(); it!=Params.end(); ++it)
1239 subenv->setAsRawText((*it).first, (*it).second->getText(env));
1240 //subenv->setValueNode((*it).first, new CTemplatizerReferenceBloc((*it).second));
1242 std::string res = func->getText(subenv);
1244 delete subenv;
1246 return res;
1249 /// Get Param list
1250 virtual const char** getDefParamList()
1252 return NULL;
1255 /// Has A Internal Bloc of data
1256 virtual bool hasInternal() const
1258 return false;
1263 * Class
1265 class CTemplatizerClassBloc : public ITemplatizerBloc
1267 public:
1269 virtual std::string eval(CTemplatizerEnv* env)
1271 std::string name = evalParam("name", env);
1272 env->setValueNode(name, new CTemplatizerReferenceBloc(this));
1273 return "";
1276 virtual std::string instantiate(CTemplatizerEnv* env)
1278 return ITemplatizerBloc::eval(env);
1281 /// Get Param list
1282 virtual const char** getDefParamList()
1284 static const char* args[] = { "name" };
1285 return (const char**)args;
1290 * Class
1292 class CTemplatizerObjectBloc : public ITemplatizerBloc
1294 public:
1296 virtual std::string eval(CTemplatizerEnv* env)
1298 std::string classname = evalParam("class", env);
1299 std::string name = evalParam("name", env);
1301 ITemplatizerBloc* bloc = env->getValueNode(classname);
1302 if (bloc == NULL)
1304 nlwarning("Unknown class '%s'", classname.c_str());
1305 return "";
1308 CTemplatizerClassBloc* classbloc = dynamic_cast<CTemplatizerClassBloc*>(bloc->getActualBloc());
1309 if (classbloc == NULL)
1311 nlwarning("object '%s' is not a class", classname.c_str());
1312 return "";
1315 CTemplatizerEnv* objectenv = env->getSubEnv(name);
1316 objectenv->clear();
1318 return classbloc->instantiate(objectenv);
1321 /// Get Param list
1322 virtual const char** getDefParamList()
1324 static const char* args[] = { "class", "name" };
1325 return (const char**)args;
1328 /// Has A Internal Bloc of data
1329 virtual bool hasInternal() const { return false; }
1334 * Breakpoint
1336 class CTemplatizerBreakpointBloc : public ITemplatizerBloc
1338 public:
1340 virtual std::string eval(CTemplatizerEnv* env)
1342 std::string value = evalParam("name", env);
1343 return "";
1346 /// Get Param list
1347 virtual const char** getDefParamList()
1349 static const char* args[] = { "name" };
1350 return (const char**)args;
1355 #endif // NL_TEMPLATIZER_H
1357 /* End of templatizer.h */