/// <summary> /// Calls function with connection's script state. /// </summary> /// <param name="conn"></param> /// <param name="functionName"></param> public void Call(ChannelConnection conn, string functionName) { var NL = conn.ScriptState.NL; Melua.lua_getglobal(NL, functionName); if (Melua.lua_isnil(NL, -1)) { Log.Error("ScriptManager.Call: Function '{0}' not found.", functionName); return; } var result = Melua.lua_resume(NL, 0); // Log error if result is not success or yield if (result != 0 && result != Melua.LUA_YIELD) { Log.Error("ScriptManager.Call: Error while executing '{0}' for {1}.\n{2}", functionName, conn.Account.Name, Melua.lua_tostring(NL, -1)); result = 0; // Set to 0 to close dialog on error } // Close dialog if end of function was reached if (result == 0) { Send.ZC_DIALOG_CLOSE(conn); conn.ScriptState.CurrentNpc = null; } }
/// <summary> /// Calls function with connection's script state. /// </summary> /// <param name="conn"></param> /// <param name="functionName"></param> /// <param name="arguments"></param> public ScriptCallResult Call(ChannelConnection conn, string functionName, params object[] arguments) { if (conn.ScriptState.LuaThread != null) { Log.Warning("ScriptManager.Call: A previous thread wasn't closed for user '{0}'.", conn.Account.Name); } // Prepare thread conn.ScriptState.LuaThread = this.GetNewThread(conn.ScriptState); var NL = conn.ScriptState.LuaThread.L; var top = Melua.lua_gettop(_gL); // Get function Melua.lua_getglobal(NL, functionName); if (Melua.lua_isnil(NL, -1)) { conn.ScriptState.Reset(); return(new ScriptCallResult(ScriptCallResultType.NotFound)); } // Push all arguments var argc = arguments?.Length ?? 0; if (argc != 0) { PushArguments(NL, arguments); } // Execute the function with the arguments var funcResult = Melua.lua_resume(NL, argc); // If result is not a success or yield, an error occurred. if (funcResult != 0 && funcResult != Melua.LUA_YIELD) { conn.ScriptState.Reset(); var errorMessage = string.Format("Error while executing '{0}' for user '{1}': {2}", functionName, conn.Account.Name, Melua.lua_tostring(NL, -1)); return(new ScriptCallResult(ScriptCallResultType.Error, errorMessage)); } // We currently don't expect functions called this way to yield if (funcResult == Melua.LUA_YIELD) { Log.Warning("ScriptManager.Call: Script function '{0}' yielded for user '{1}', a behavior that's currently not handled.", functionName, conn.Account.Name); } conn.ScriptState.Reset(); return(new ScriptCallResult(ScriptCallResultType.Success)); }
/// <summary> /// Calls function with connection's script state. /// </summary> /// <param name="conn"></param> /// <param name="functionName"></param> public void Call(ChannelConnection conn, string functionName) { if (conn.ScriptState.LuaThread != null) { Log.Warning("ScriptManager.Call: A previous thread wasn't closed for user '{0}'.", conn.Account.Name); } // Get function name, use oneliner for localized, single-line // dialogues. if (this.IsOneLiner(functionName)) { functionName = "npc_oneliner"; } // Prepare thread conn.ScriptState.LuaThread = this.GetNewThread(conn.ScriptState); var NL = conn.ScriptState.LuaThread.L; var top = Melua.lua_gettop(GL); // Get function Melua.lua_getglobal(NL, functionName); if (Melua.lua_isnil(NL, -1)) { Log.Error("ScriptManager.Call: Function '{0}' not found.", functionName); return; } // Run var result = Melua.lua_resume(NL, 0); // Log error if result is not success or yield if (result != 0 && result != Melua.LUA_YIELD) { Log.Error("ScriptManager.Call: Error while executing '{0}' for {1}.\n{2}", functionName, conn.Account.Name, Melua.lua_tostring(NL, -1)); result = 0; // Set to 0 to close dialog on error } // Close dialog if end of function was reached if (result == 0) { Send.ZC_DIALOG_CLOSE(conn); conn.ScriptState.Reset(); } }