00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018 #include "Script.h"
00019 #include "../core/GameManager.h"
00020
00021
00022
00023
00024 u32 Script::mIDCount = 0;
00025
00026
00027 Script::Script(const std::string &name)
00028 : mName(name), mModule(NULL)
00029 {
00030 mID = mIDCount++;
00031
00032
00033 ScriptManager *scriptMgr = GameManager::Instance()->getScriptManager();
00034
00035
00036 mModule = scriptMgr->getEngine()->GetModule(mName.c_str(), asGM_ALWAYS_CREATE);
00037 mContext = scriptMgr->getEngine()->CreateContext();
00038 }
00039
00040
00041 Script::~Script()
00042 {
00043
00044 ScriptManager *scriptMgr = GameManager::Instance()->getScriptManager();
00045
00046
00047 if(mModule != NULL)
00048 scriptMgr->getEngine()->DiscardModule(mName.c_str());
00049
00050 mContext->Release();
00051 }
00052
00053
00054 Script* Script::refFactory(const std::string &name)
00055 {
00056 return new Script(name);
00057 }
00058
00059
00060 void Script::refAdd()
00061 {
00062 mRefCount++;
00063 }
00064
00065
00066 void Script::refRelease()
00067 {
00068 if(--mRefCount == 0)
00069 {
00070 if(!GameManager::Instance()->getScriptManager()->removeScript(this))
00071 delete this;
00072 }
00073 }
00074
00075
00076 u32 Script::getID() const
00077 {
00078 return mID;
00079 }
00080
00081
00082 const std::string& Script::getName() const
00083 {
00084 return mName;
00085 }
00086
00087
00088 asIScriptContext* Script::getContext() const
00089 {
00090 return mContext;
00091 }
00092
00093
00094 asIScriptModule* Script::getModule() const
00095 {
00096 return mModule;
00097 }
00098
00099
00100 bool Script::loadScript(const std::string &fileName)
00101 {
00102
00103 IFileSystem *fileSystem = GameManager::Instance()->getDevice()->getFileSystem();
00104 ScriptManager *scriptMgr = GameManager::Instance()->getScriptManager();
00105
00106
00107 if(mModule != NULL)
00108 {
00109 scriptMgr->getEngine()->DiscardModule(mName.c_str());
00110 mModule = NULL;
00111 }
00112
00113
00114 if(!fileSystem->existFile(fileName.c_str()))
00115 return false;
00116
00117
00118 mModule = scriptMgr->getEngine()->GetModule(mName.c_str(), asGM_ALWAYS_CREATE);
00119
00120
00121 IReadFile *file = fileSystem->createAndOpenFile(fileName.c_str());
00122
00123 long fSize = file->getSize();
00124 c8 * fBuffer = new c8[fSize+1];
00125 memset(fBuffer, 0, fSize+1);
00126
00127 file->read(fBuffer, fSize);
00128 file->drop();
00129
00130
00131 mModule->AddScriptSection("main", fBuffer);
00132 scriptMgr->addScriptSectionsToScript(this);
00133
00134
00135 int r = mModule->Build();
00136 if(r < 0)
00137 return false;
00138
00139
00140 delete[] fBuffer;
00141
00142 return true;
00143 }
00144
00145
00146 bool Script::unloadScript()
00147 {
00148 ScriptManager *scriptMgr = GameManager::Instance()->getScriptManager();
00149
00150 if(mModule != NULL)
00151 {
00152 scriptMgr->getEngine()->DiscardModule(mName.c_str());
00153 mModule = NULL;
00154 return true;
00155 }
00156
00157 return false;
00158 }
00159
00160
00161 bool Script::executeFunctionByName(const std::string &name, const std::string &args)
00162 {
00163
00164 if(mModule == NULL)
00165 return false;
00166
00167
00168 int functionID = mModule->GetFunctionIdByName(name.c_str());
00169
00170 if(functionID == asERROR || functionID == asMULTIPLE_FUNCTIONS || functionID == asNO_FUNCTION)
00171 return false;
00172
00173
00174 std::stringstream ss;
00175 ss << name << "(" << args << ");";
00176
00177 mModule->GetEngine()->ExecuteString(mName.c_str(), ss.str().c_str(), &mContext,
00178 asEXECSTRING_ONLY_PREPARE | asEXECSTRING_USE_MY_CONTEXT);
00179
00180
00181 int r = mContext->Execute();
00182 if(r == asEXECUTION_FINISHED)
00183 {
00184 return true;
00185 }
00186
00187 else return false;
00188 }
00189
00190
00191
00192 void bindScript(asIScriptEngine *engine)
00193 {
00194
00195 int r;
00196
00197
00198 r = engine->RegisterObjectType("Script", sizeof(Script), asOBJ_REF); assert(r >= 0);
00199
00200
00201 r = engine->RegisterObjectBehaviour("Script", asBEHAVE_FACTORY, "Script@ f(const string &)",
00202 asFUNCTION(Script::refFactory), asCALL_CDECL); assert(r >= 0);
00203 r = engine->RegisterObjectBehaviour("Script", asBEHAVE_ADDREF, "void f()",
00204 asMETHOD(Script, refAdd), asCALL_THISCALL); assert(r >= 0);
00205 r = engine->RegisterObjectBehaviour("Script", asBEHAVE_RELEASE, "void f()",
00206 asMETHOD(Script, refRelease), asCALL_THISCALL); assert(r >= 0);
00207
00208
00209 r = engine->RegisterObjectMethod("Script", "u32 getID()",
00210 asMETHOD(Script, getID), asCALL_THISCALL); (r >= 0);
00211 r = engine->RegisterObjectMethod("Script", "const string& getName()",
00212 asMETHOD(Script, getName), asCALL_THISCALL); assert(r >= 0);
00213
00214 r = engine->RegisterObjectMethod("Script", "bool loadScript(const string &)",
00215 asMETHOD(Script, loadScript), asCALL_THISCALL);assert(r >= 0);
00216 r = engine->RegisterObjectMethod("Script", "bool unloadScript()",
00217 asMETHOD(Script, unloadScript), asCALL_THISCALL);assert(r >= 0);
00218
00219 r = engine->RegisterObjectMethod("Script", "bool executeFunctionByName(const string &, const string &)",
00220 asMETHOD(Script, loadScript), asCALL_THISCALL);assert(r >= 0);
00221 }
00222
00223