Add infos into target window
[ryzomcore.git] / ryzom / server / src / ai_share / ai_actions.h
blob98c387d43c442268cd1d401b8e00270b0395734f
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/>.
19 // forward declaration of class useful in the case of circular class refferences
20 #ifndef RYAI_AI_ACTIONS_H
21 #define RYAI_AI_ACTIONS_H
23 #include "game_share/persistent_data.h"
25 #include "ai_alias_description_node.h"
26 #include "ai_event_description.h"
27 #include "ai_event_description.h"
30 #include "nel/misc/types_nl.h"
31 #include "nel/misc/common.h"
32 #include "nel/misc/stream.h"
35 #include <map>
36 #include <vector>
37 #include <string>
40 class CAIActions
42 public:
43 class CArg
45 public:
46 CArg(): _type(TypeInt), _i(0) {}
47 CArg(const CArg &other): _type(TypeInt), _i(0) { *this=other; }
49 #ifdef NL_COMP_VC6
50 CArg(sint arg): _type(TypeInt), _i(arg) {}
51 CArg(uint arg): _type(TypeInt), _i(arg) {}
52 #endif
53 CArg(bool arg): _type(TypeBool),_b(arg) {}
54 CArg(sint32 arg): _type(TypeInt), _i(arg) {}
55 CArg(uint32 arg): _type(TypeInt), _i(arg) {}
56 CArg(float arg): _type(TypeFloat), _f(arg) {}
57 CArg(double arg): _type(TypeFloat), _f((float)arg) {}
58 CArg(const char *arg): _type(TypeString) { _s=arg; }
59 CArg(const std::string &arg): _type(TypeString) { _s=arg; }
60 CArg(const CAIAliasDescriptionNode *arg): _type(TypeAliasTree) { _a=const_cast<CAIAliasDescriptionNode *>(arg); } // ->copyAliasDescriptionNode(); }
61 CArg(const CAIEventDescription *arg): _type(TypeEventTree) { _e=const_cast<CAIEventDescription *>(arg); }
63 ~CArg() {}
65 #ifdef NL_COMP_VC6
66 bool get(sint &arg) const { if (_type!=TypeInt) return false; arg=_i; return true; }
67 bool get(uint &arg) const { if (_type!=TypeInt) return false; arg=_i; return true; }
68 #endif
69 bool get(bool &arg) const { if (_type!=TypeBool)return false; arg=_b; return true; }
70 bool get(sint32 &arg) const { if (_type!=TypeInt) return false; arg=_i; return true; }
71 bool get(uint32 &arg) const { if (_type!=TypeInt) return false; arg=_i; return true; }
72 bool get(float &arg) const { if (_type!=TypeFloat) return false; arg=_f; return true; }
73 bool get(double &arg) const { if (_type!=TypeFloat) return false; arg=_f; return true; }
74 bool get(std::string &arg) const { if (_type!=TypeString) return false; arg=_s; return true; }
75 bool get(CAIAliasDescriptionNode *&arg) const { if (_type!=TypeAliasTree) return false; arg=_a; return true; }
76 bool get(CAIEventDescription::TSmartPtr &arg) const { if (_type!=TypeEventTree) return false; arg=_e; return true; }
78 const CArg &operator =(const CArg &other)
80 _type = other._type;
81 switch(other._type)
83 case TypeString: _s=other._s; break;
84 case TypeBool: _b=other._b; break;
85 case TypeInt: _i=other._i; break;
86 case TypeFloat: _f=other._f; break;
87 case TypeAliasTree: _a=other._a; break; //->copyAliasDescriptionNode(); break;
88 case TypeEventTree: _e=other._e; break;
90 return *this;
93 std::string toString() const
95 switch(_type)
97 case TypeString: return NLMISC::toString(_s);
98 case TypeBool: return NLMISC::toString(_b);
99 case TypeInt: return NLMISC::toString(_i);
100 case TypeFloat: return NLMISC::toString(_f);
101 // case TypeAliasTree: return _a->treeToString();
102 // case TypeEventTree: return _e->toString();
103 default: break;
105 return "<Invalid Argument Type>";
108 void serial(NLMISC::IStream &f)
110 f.serialEnum(_type);
111 switch(_type)
113 case TypeString: f.serial(_s); break;
114 case TypeBool: f.serial(_b); break;
115 case TypeInt: f.serial(_i); break;
116 case TypeFloat: f.serial(_f); break;
117 // case TypeAliasTree: f.serial(_a); break;
118 // case TypeEventTree: f.serial(_e); break;
119 default: break;
123 void pushToPdr(CPersistentDataRecord& pdr) const
125 switch(_type)
127 case TypeString: pdr.push(pdr.addString("string"),_s); break;
128 case TypeBool: pdr.push(pdr.addString("bool"),_b?(sint32)1:(sint32)0); break;
129 case TypeInt: pdr.push(pdr.addString("int"),_i); break;
130 case TypeFloat: pdr.push(pdr.addString("float"),_f); break;
131 case TypeAliasTree:
132 pdr.pushStructBegin(pdr.addString("aliasNodeTree"));
133 _a->pushToPdr(pdr);
134 pdr.pushStructEnd(pdr.addString("aliasNodeTree"));
135 break;
136 case TypeEventTree:
137 pdr.pushStructBegin(pdr.addString("eventHandler"));
138 _e->pushToPdr(pdr);
139 pdr.pushStructEnd(pdr.addString("eventHandler"));
140 break;
144 void popFromPdr(CPersistentDataRecord& pdr)
146 uint16 token= pdr.peekNextToken();
147 const std::string& tokenName= pdr.peekNextTokenName();
149 if (pdr.isStartOfStruct())
151 if (tokenName=="aliasNodeTree")
153 _type = TypeAliasTree;
154 pdr.popStructBegin(token);
155 _a= CAIAliasDescriptionNode::popFromPdr(pdr);
156 pdr.popStructEnd(token);
157 return;
159 if (tokenName=="eventHandler")
161 _type = TypeEventTree;
162 pdr.popStructBegin(token);
163 _e= CAIEventDescription::popFromPdr(pdr);
164 pdr.popStructEnd(token);
165 return;
167 WARN("Found unexpected clause in PDR: "+tokenName);
168 pdr.skipData();
170 else
172 if (tokenName=="string")
174 _type = TypeString;
175 _s= pdr.popNextArg(token).asString();
176 return;
178 if (tokenName=="bool")
180 _type = TypeBool;
181 _b= pdr.popNextArg(token).asSint()!=0;
182 return;
184 if (tokenName=="int")
186 _type = TypeInt;
187 _i= (sint32) pdr.popNextArg(token).asSint();
188 return;
190 if (tokenName=="float")
192 _type = TypeFloat;
193 _f = pdr.popNextArg(token).asFloat();
194 return;
197 WARN("Found unexpected value in PDR: "+tokenName);
198 pdr.skipStruct();
202 // a kind of serial used to generate messages from AIDS to AIS
203 void serialToString(std::string &s) throw()
205 s+=char(_type);
206 switch(_type)
208 case TypeString:
209 s+=_s+char(0);
210 break;
212 case TypeBool:
213 s+=_b ? char(1) : char(0);
214 break;
216 case TypeInt:
217 s+=NLMISC::toString("%*s",sizeof(sint32),"");
218 ((sint32*)&(s[s.size()]))[-1]=_i;
219 break;
221 case TypeFloat:
222 s+=NLMISC::toString("%*s",sizeof(float),"");
223 ((float*)&(s[s.size()]))[-1]=_f;
224 break;
226 case TypeAliasTree:
227 // TODO: LOADS OF WORK HERE!!!
228 // count the nodes
229 // build string table
230 // sort string table by size
231 // compact string table by removing strings that match tail end of existing strings
232 // - use an output buffer - containing all existing strings (directly in output string?)
233 // - a buffer index containing indices where strings end (start is implicit :o)
234 // - a heap of node indices, sorted by heapEntry->_name.size()
235 // - a vector of string start pointers corresponding to the nodes
236 // resize s to accomodate arriving data
237 // write node count
238 // write string buffer size
239 // write the nodes
240 // write string buffer
242 break;
244 case TypeEventTree:
245 // TODO: LOADS OF WORK HERE TOO!!!
246 break;
250 // a kind of serial used to decrypt messages from AIDS to AIS
251 static CArg serialFromString(std::string &data,uint &index) throw()
253 // first get hold of the type (a single char)
254 if (data.size()-index<1)
256 nlwarning("Unexpected end of input data in serialFromString()");
257 return CArg();
259 TType type=(TType)data[index++];
261 // now grab the value
262 switch(type)
264 case TypeString: // strings are stored in asciiz
266 char *str=&data[index];
267 for(;data[index]!=0;++index)
269 if (index>=data.size())
271 nlwarning("Unexpected end of input data in serialFromString()");
272 index=(uint)data.size()+1;
273 return CArg();
276 return CArg(str);
279 case TypeBool: // bool are stored directly on one char
280 index+=1;
281 if (index>data.size())
283 nlwarning("Unexpected end of input data in serialFromString()");
284 index=(uint)data.size()+1;
285 return CArg();
287 return CArg(bool(data[index] == 1));
289 case TypeInt: // ints are stored drectly as binary (beware of byte order!!!)
290 index+=sizeof(sint32);
291 if (index>data.size())
293 nlwarning("Unexpected end of input data in serialFromString()");
294 index=(uint)data.size()+1;
295 return CArg();
297 return CArg(((sint32 *)&data[index])[-1]);
299 case TypeFloat: // floats are stored directly as binary (beware of byte order!!!)
300 index+=sizeof(float);
301 if (index>data.size())
303 nlwarning("Unexpected end of input data in serialFromString()");
304 index=(uint)data.size()+1;
305 return CArg();
307 return CArg(((float *)&data[index])[-1]);
309 case TypeAliasTree:
310 // TODO: LOADS OF WORK HERE!!!
311 // return CArg(((float *)&data[index])[-1]);
312 break;
314 case TypeEventTree:
315 // TODO: LOADS OF WORK HERE!!!
316 // return CArg(((float *)&data[index])[-1]);
317 break;
319 nlwarning("Unexpected type in serialFromString()");
320 index=(uint)data.size()+1;
321 return CArg();
324 private:
325 enum TType { TypeString, TypeInt, TypeFloat, TypeBool, TypeAliasTree, TypeEventTree } _type;
326 bool _b;
327 sint32 _i;
328 float _f;
329 std::string _s;
330 CAIAliasDescriptionNode *_a;
331 CAIEventDescription::TSmartPtr _e;
333 // I've had to re-code strdup() here as the default one doesn't use the
334 // same memory manager as free() and so causes crashes in debug mode
335 static char *strdup(const char *src)
337 // calculate strlen() - *NOTE: i must be signed for use in copy (below)
338 sint i;
339 for (i=0;src[i];++i);
340 // allocate memory
341 char *result=(char *)malloc(i+1);
342 if (result==NULL)
343 return NULL;
344 // copy string into new buffer
345 for (;i>=0;i--)
346 result[i]=src[i];
347 return result;
352 class IExecutor
354 public:
355 virtual ~IExecutor() {}
357 virtual void openFile(const std::string &fileName) {}
358 virtual void closeFile(const std::string &fileName) {}
359 virtual void begin(uint32 contextAlias) =0;
360 virtual void end(uint32 contextAlias) =0;
361 virtual void execute(uint64 action,const std::vector <CArg> &args)=0;
364 static void init(IExecutor *executor) { _init=true; _executor=executor;}
365 static IExecutor* getExecuter() { return _init?_executor:0;}
366 static void release() { _init=false; }
368 static void openFile(const std::string &fileName);
369 static void closeFile(const std::string &fileName);
370 static void begin(uint32 contextAlias);
371 static void end(uint32 contextAlias);
373 static void execute(const std::string &action,const std::vector<CArg> &args);
374 static void execute(const std::string &action,const std::vector<std::string> &args);
375 static void execute(const std::string &action,const std::vector<int> &args);
376 static void execute(const std::string &action,const std::vector<double> &args);
377 static void execute(const std::string &action);
379 static void exec(const std::string &action)
381 std::vector<CArg> args;
382 execute(action,args);
384 template <class T0>
385 static void exec(const std::string &action,const T0 &arg0)
387 std::vector<CArg> args;
388 args.push_back(CArg(arg0));
389 execute(action,args);
391 template <class T0,class T1>
392 static void exec(const std::string &action,const T0 &arg0,const T1 &arg1)
394 std::vector<CArg> args;
395 args.push_back(CArg(arg0));
396 args.push_back(CArg(arg1));
397 execute(action,args);
399 template <class T0,class T1,class T2>
400 static void exec(const std::string &action,const T0 &arg0,const T1 &arg1,const T2 &arg2)
402 std::vector<CArg> args;
403 args.push_back(CArg(arg0));
404 args.push_back(CArg(arg1));
405 args.push_back(CArg(arg2));
406 execute(action,args);
408 template <class T0,class T1,class T2,class T3>
409 static void exec(const std::string &action,const T0 &arg0,const T1 &arg1,const T2 &arg2,const T3 &arg3)
411 std::vector<CArg> args;
412 args.push_back(CArg(arg0));
413 args.push_back(CArg(arg1));
414 args.push_back(CArg(arg2));
415 args.push_back(CArg(arg3));
416 execute(action,args);
418 template <class T0,class T1,class T2,class T3,class T4>
419 static void exec(const std::string &action,const T0 &arg0,const T1 &arg1,const T2 &arg2,const T3 &arg3,const T4 &arg4)
421 std::vector<CArg> args;
422 args.push_back(CArg(arg0));
423 args.push_back(CArg(arg1));
424 args.push_back(CArg(arg2));
425 args.push_back(CArg(arg3));
426 args.push_back(CArg(arg4));
427 execute(action,args);
429 template <class T0,class T1,class T2,class T3,class T4,class T5>
430 static void exec(const std::string &action,const T0 &arg0,const T1 &arg1,const T2 &arg2,const T3 &arg3,const T4 &arg4,const T5 &arg5)
432 std::vector<CArg> args;
433 args.push_back(CArg(arg0));
434 args.push_back(CArg(arg1));
435 args.push_back(CArg(arg2));
436 args.push_back(CArg(arg3));
437 args.push_back(CArg(arg4));
438 args.push_back(CArg(arg5));
439 execute(action,args);
441 template <class T0,class T1,class T2,class T3,class T4,class T5,class T6>
442 static void exec(const std::string &action,const T0 &arg0,const T1 &arg1,const T2 &arg2,const T3 &arg3,const T4 &arg4,const T5 &arg5, const T6 &arg6)
444 std::vector<CArg> args;
445 args.push_back(CArg(arg0));
446 args.push_back(CArg(arg1));
447 args.push_back(CArg(arg2));
448 args.push_back(CArg(arg3));
449 args.push_back(CArg(arg4));
450 args.push_back(CArg(arg5));
451 args.push_back(CArg(arg6));
452 execute(action,args);
454 private:
455 static bool _init;
456 static IExecutor *_executor;
459 #endif