source: trunk/src/nrEngine/ScriptEngine.cpp @ 46

Revision 46, 9.8 KB checked in by art, 12 years ago (diff)
  • Include changes in *.cpp due to the directory structure change
  • Plugin build fixes (now plugins are build without preinstalling of the engine)
  • ToDo?: Uninstall do not remove the lib*.so files
RevLine 
[1]1/***************************************************************************
2 *                                                                         *
3 *   (c) Art Tevs, MPI Informatik Saarbruecken                             *
4 *       mailto: <tevs@mpi-sb.mpg.de>                                      *
5 *                                                                         *
6 *   This program is free software; you can redistribute it and/or modify  *
7 *   it under the terms of the GNU General Public License as published by  *
8 *   the Free Software Foundation; either version 2 of the License, or     *
9 *   (at your option) any later version.                                   *
10 *                                                                         *
11 ***************************************************************************/
12
13
14//----------------------------------------------------------------------------------
15// Includes
16//----------------------------------------------------------------------------------
[46]17#include <nrEngine/ScriptEngine.h>
18#include <nrEngine/Log.h>
19#include <nrEngine/events/EngineEvent.h>
20#include <nrEngine/EventManager.h>
21#include <nrEngine/VariadicArgument.h>
22#include <nrEngine/IScript.h>
[1]23
24namespace nrEngine{
25
26        //----------------------------------------------------------------------------------
27        ScriptFunctionDec(scriptLoad, ScriptEngine)
28        {
29                // check parameter count
30                if (args.size() < 2){
31                        return ScriptResult(std::string("Not valid parameter count! Parameters (name, filename)"));
32                }
33
34                // get parameters
35                IResourcePtr ptr = Engine::sScriptEngine()->load(args[1], args[2]);
36
37                if (ptr.isNull())
38                {
39                        return ScriptResult(std::string("Can not load script ") + args[1] + " from file " + args[2]);
40                }
41
42                return ScriptResult();
43        }
44
45        //----------------------------------------------------------------------------------
46        ScriptFunctionDec(scriptRun, ScriptEngine)
47        {
48                // check parameter count
49                if (args.size() < 1){
50                        return ScriptResult(std::string("Not valid parameter count! Parameters (name [, runonce = true [, immediate = false]])"));
51                }
52
53                // get parameters
54                try{
55                        const std::string& name = args[1];
56                        bool once = true;
[22]57                        if (args.size() > 2) once = boost::lexical_cast<bool>(args[2]);
[1]58                        bool force = false;
[22]59                        if (args.size() > 3) force = boost::lexical_cast<bool>(args[3]);
[1]60
61                        // run
62                        if (!Engine::sScriptEngine()->execute(name, once, force))
63                                return ScriptResult(std::string("Can not execute script ") + name);
64                }catch(boost::bad_lexical_cast s){
65                        return ScriptResult(std::string("Wrong parameter value! "));
66                }
67               
68                return ScriptResult();
69        }
70
71        //----------------------------------------------------------------------------------
[23]72        ScriptFunctionDec(scriptLoadAndRun, ScriptEngine)
73        {
74                // check parameter count
75                if (args.size() < 2){
76                        return ScriptResult(std::string("Not valid parameter count! Parameters (name, filename)"));
77                }
78
79                // get name and filename
80                const std::string& name = args[1];
81                const std::string& fileName = args[2];
82               
83                // create argument for calling
84                std::vector<std::string> arg;
85                arg.push_back(args[0]);
86                arg.push_back(name);
87                arg.push_back(fileName);
88               
89                // call load method
90                ScriptResult res = scriptLoad(arg, param);
91               
92                // create arguments for run method
93                arg.pop_back();
94               
95                // call run if load was successfull
96                if (res.size() == 0) res = scriptRun(arg, param);
97               
98                return res;
99        }
100
101        //----------------------------------------------------------------------------------
[1]102        ScriptFunctionDec(scriptCall, ScriptEngine)
103        {
104                // check parameter count
105                if (args.size() < 2){
106                        return ScriptResult(std::string("Not valid parameter count! Parameters (name, funcname, [, param1, ..., paramn])"));
107                }
[22]108               
109                IScript::ArgumentList ar;
110                       
111                // we get parameters, so extract them
112                if (args.size() >= 3 )
113                {
114                        for (uint32 i=3; i < args.size(); i++)
115                        {
116                                // get value
117                                std::string param = args[i];
118                               
119                                // check if it contains ':' character
120                                std::string::size_type pos = param.find(':');
121                                if (pos == std::string::npos)
122                                {
123                                        char msg[4096];
124                                        sprintf(msg, "ScriptEngine: Parameter %s does not contain type information", param.c_str());
125                                        return ScriptResult(std::string(msg));
126                                }
127                               
128                                // split on that character
129                                std::string type = param.substr(pos + 1);
130                                std::string value = param.substr(0, pos);
[1]131       
[22]132                                // store them
133                                ar.push_back(std::pair<std::string, std::string>(type, value));
134                        } 
135                }
[1]136
137                // get resource
138                ResourcePtr<IScript> ptr = Engine::sResourceManager()->getByName(args[1]);
139                if (ptr.isNull())
140                        return ScriptResult(std::string("Can not find script ") + args[1]);
141
142                // now prepare arguments
143                ptr->setArguments(args[2], ar);
144                ScriptResult res;
145                ptr->call(args[2]);
146               
147                // call a specific function
148                return res;
149        }
150       
151        //----------------------------------------------------------------------------------
152        ScriptEngine::ScriptEngine(){
153                mDatabase["scriptLoad"].first = scriptLoad;
154                mDatabase["scriptRun"].first = scriptRun;
155                mDatabase["scriptExecute"].first = scriptRun;
156                mDatabase["scriptCall"].first = scriptCall;
[23]157                mDatabase["scriptLoadAndRun"].first = scriptLoadAndRun;
[1]158        }
159
160        //----------------------------------------------------------------------------------
161        ScriptEngine::~ScriptEngine(){
162
163                // empty the database
164                mDatabase.clear();
165
166        }
167
168        //----------------------------------------------------------------------------------
169        Result ScriptEngine::add(const std::string& name, ScriptFunctor func, const std::vector<ScriptParam>& param)
170        {
171                // first check whenever such function already registered
172                if (isRegistered(name))
173                        return SCRIPT_FUNCTION_REGISTERED;
174
175                // now add the function to the database
176                mDatabase[name].first = func;
177                mDatabase[name].second = param;
178
179                // some statistical information
180                NR_Log(Log::LOG_ENGINE, Log::LL_DEBUG, "ScriptEngine: New function \"%s\" registered", name.c_str());
181
182                // emit a new event
183                SharedPtr<Event> msg(new ScriptRegisterFunctionEvent(name, func));
184                Engine::sEventManager()->emitSystem(msg);
185               
186                return OK;
187        }
188
189        //----------------------------------------------------------------------------------
190        Result ScriptEngine::add(const std::string& name, ScriptFunctor func, const VarArg& v){
191
192                // get the elements and store them in vector
193                std::vector<ScriptParam> p;
194                v.convert<ScriptParam>(p);
195
196                // OK
197                return add(name, func, p);
198        }
199
200        //----------------------------------------------------------------------------------
201        Result ScriptEngine::del(const std::string& name)
202        {
203                // get the function
204                FunctionDatabase::iterator it = mDatabase.find(name);
205                if (it == mDatabase.end()) return SCRIPT_FUNCTION_NOT_REGISTERED;
206
207                mDatabase.erase(it);
208
209                // some statistical information
210                NR_Log(Log::LOG_ENGINE, Log::LL_DEBUG, "ScriptEngine: Function \"%s\" was removed", name.c_str());
211
212                // emit a new event
213                SharedPtr<Event> msg(new ScriptRemoveFunctionEvent(name));
214                Engine::sEventManager()->emitSystem(msg);
215
216                return OK;
217        }
218
219        //----------------------------------------------------------------------------------
220        ScriptResult ScriptEngine::call(const std::string& name, const std::vector<std::string>& args)
221        {
222                // if no such function was found
223                FunctionDatabase::iterator f = get(name);
224                if (f == mDatabase.end()){
225                        NR_Log(Log::LOG_ENGINE, Log::LL_WARNING, "ScriptEngine: Function \"%s\" was not found!", name.c_str());
226                        return ScriptResult();
227                }
[25]228               
229                // debug information
230                std::string msg;
231                for (unsigned int i=1; i < args.size(); i++) msg += std::string(" ") + args[i];
232                NR_Log(Log::LOG_ENGINE, Log::LL_DEBUG, "ScriptEngine: Call \"%s (%s)\" function!", name.c_str(), msg.c_str());
[1]233
234                // call the function
235                return ((*f).second).first(args, (*f).second.second);
236        }
237
238        //----------------------------------------------------------------------------------
239        bool ScriptEngine::isRegistered(const std::string& name)
240        {
241                // search for that name in the database
242                FunctionDatabase::const_iterator it = mDatabase.find(name);
243                return it != mDatabase.end();
244        }
245
246        //----------------------------------------------------------------------------------
247        ScriptEngine::FunctionDatabase::iterator ScriptEngine::get(const std::string& name)
248        {
249                // search for that name in the database
250                FunctionDatabase::iterator it = mDatabase.find(name);
251
252                return it;
253        }
254
255        //------------------------------------------------------------------------
256        ResourcePtr<IScript> ScriptEngine::load(const std::string& name, const std::string& file)
257        {
258                // try to load the resource and check for the error code
259                ResourcePtr<IScript> plg = Engine::sResourceManager()->loadResource(name, "Scripts", file);
260
261                if (plg.isNull()){
262                        NR_Log(Log::LOG_ENGINE, Log::LL_ERROR, "Can not load the script %s from %s", name.c_str(), file.c_str());
263                }
264                return plg;
265        }
266
267
268        //------------------------------------------------------------------------
269        Result ScriptEngine::execute(const std::string& name, bool runOnce, bool immediate)
270        {
271                // get the pointer to the script resource
272                ResourcePtr<IScript> scr = Engine::sResourceManager()->getByName(name);
273                return _execute(scr, runOnce, immediate);               
274        }
275
276        //------------------------------------------------------------------------
277        Result ScriptEngine::execute(const std::string& name, const std::string& fileName, bool runOnce, bool immediate)
278        {
279                ResourcePtr<IScript> scr = load(name, fileName);
280                return _execute(scr, runOnce, immediate);
281        }
282
283        //------------------------------------------------------------------------
284        Result ScriptEngine::_execute(const ResourcePtr<IScript>& ptr, bool runOnce, bool immediate)
285        {
286                if (ptr.isNull()) return RES_NOT_FOUND;
287                if (immediate) return ptr->forceExecute(runOnce);
288                return ptr->execute(runOnce);
289        }
290
291        //------------------------------------------------------------------------
292        const std::string& ScriptEngine::getFunction(uint32 index, ScriptFunctor& functor)
293        {
294                NR_ASSERT(index < getFunctionCount());
295                FunctionDatabase::const_iterator it = mDatabase.begin();
296                for (uint32 i = 0; i < index; i++, it++){}
297
298                functor = it->second.first;
299                return it->first;
300        }
301
302};
303
Note: See TracBrowser for help on using the repository browser.