mirror of
https://github.com/TES3MP/openmw-tes3mp.git
synced 2025-03-03 20:49:41 +00:00
[Server] Add possibility to use previous state of data in events
This commit is contained in:
parent
7deff7a42a
commit
d0eef7c98e
3 changed files with 56 additions and 16 deletions
|
@ -400,13 +400,13 @@ PacketPreInit::PluginContainer Networking::getPluginListSample()
|
||||||
while (true)
|
while (true)
|
||||||
{
|
{
|
||||||
unsigned field = 0;
|
unsigned field = 0;
|
||||||
auto name = luaState.getEventCtrl().Call<CoreEvent::ON_REQUEST_PLUGIN_LIST, string>(id, field++);
|
auto name = luaState.getEventCtrl().Call<CoreEvent::ON_REQUEST_PLUGIN_LIST, false, string>(id, field++);
|
||||||
if (name.empty())
|
if (name.empty())
|
||||||
break;
|
break;
|
||||||
PacketPreInit::HashList hashList;
|
PacketPreInit::HashList hashList;
|
||||||
while (true)
|
while (true)
|
||||||
{
|
{
|
||||||
auto hash = luaState.getEventCtrl().Call<CoreEvent::ON_REQUEST_PLUGIN_LIST, string>(id, field++);
|
auto hash = luaState.getEventCtrl().Call<CoreEvent::ON_REQUEST_PLUGIN_LIST, false, string>(id, field++);
|
||||||
if (hash.empty())
|
if (hash.empty())
|
||||||
break;
|
break;
|
||||||
hashList.push_back((unsigned)stoul(hash));
|
hashList.push_back((unsigned)stoul(hash));
|
||||||
|
|
|
@ -13,7 +13,7 @@ void EventController::Init(LuaState &lua)
|
||||||
|
|
||||||
eventsTable["register"] = [&lua](int event, sol::function func, sol::this_environment te) {
|
eventsTable["register"] = [&lua](int event, sol::function func, sol::this_environment te) {
|
||||||
sol::environment& env = te;
|
sol::environment& env = te;
|
||||||
lua.getEventCtrl().registerEvent(event, env, func);
|
lua.getEventCtrl().registerEvent(event, env, func, false);
|
||||||
};
|
};
|
||||||
eventsTable["stop"] = [&lua](int event) {
|
eventsTable["stop"] = [&lua](int event) {
|
||||||
lua.getEventCtrl().stop(event);
|
lua.getEventCtrl().stop(event);
|
||||||
|
@ -112,11 +112,11 @@ EventController::EventController(LuaState *luaCtrl)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void EventController::registerEvent(int event, sol::environment &env, sol::function& func)
|
void EventController::registerEvent(int event, sol::environment &env, sol::function& func, bool needsOldState)
|
||||||
{
|
{
|
||||||
auto iter = events.find(event);
|
auto iter = events.find(event);
|
||||||
if (iter != events.end())
|
if (iter != events.end())
|
||||||
iter->second.push(env, func);
|
iter->second.push(env, func, needsOldState);
|
||||||
}
|
}
|
||||||
|
|
||||||
void EventController::stop(int event)
|
void EventController::stop(int event)
|
||||||
|
@ -146,12 +146,12 @@ void EventController::raiseEvent(Event id, sol::table data, const string &module
|
||||||
if (!moduleName.empty())
|
if (!moduleName.empty())
|
||||||
{
|
{
|
||||||
auto f = std::find_if(iter->second.begin(), iter->second.end(), [&moduleName](const auto &item){
|
auto f = std::find_if(iter->second.begin(), iter->second.end(), [&moduleName](const auto &item){
|
||||||
return item.first["ModuleName"]["name"] == moduleName;
|
return item.env["ModuleName"]["name"] == moduleName;
|
||||||
});
|
});
|
||||||
if (f != iter->second.end())
|
if (f != iter->second.end())
|
||||||
f->second.call(data); // call only specified mod
|
f->fn.call(data); // call only specified mod
|
||||||
}
|
}
|
||||||
iter->second.call(CallbackCollection::type_tag<void>(), data); // call all registered events with this id
|
iter->second.call(CallbackCollection::type_tag<void>(), false, data); // call all registered events with this id
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
cerr << "Event with id: " << id << " is not registered" << endl;
|
cerr << "Event with id: " << id << " is not registered" << endl;
|
||||||
|
|
|
@ -79,13 +79,21 @@ namespace CoreEvent
|
||||||
class CallbackCollection // todo: add sort by dependencies
|
class CallbackCollection // todo: add sort by dependencies
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
typedef std::vector<std::pair<sol::environment, sol::function>> Container;
|
struct CBType
|
||||||
|
{
|
||||||
|
sol::environment env;
|
||||||
|
sol::function fn;
|
||||||
|
bool needsOldState;
|
||||||
|
CBType(sol::environment _env, sol::function _fn, bool _needsOldState): env(_env), fn(_fn), needsOldState(_needsOldState) {}
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef std::vector<CBType> Container;
|
||||||
typedef Container::iterator Iterator;
|
typedef Container::iterator Iterator;
|
||||||
typedef Container::const_iterator CIterator;
|
typedef Container::const_iterator CIterator;
|
||||||
|
|
||||||
template<typename> struct type_tag {};
|
template<typename> struct type_tag {};
|
||||||
|
|
||||||
void push(sol::environment &env, sol::function &func) { functions.emplace_back(env, func); }
|
void push(sol::environment &env, sol::function &func, bool needsOldState) { functions.emplace_back(env, func, needsOldState); }
|
||||||
CIterator begin() const { return functions.begin(); }
|
CIterator begin() const { return functions.begin(); }
|
||||||
CIterator end() const { return functions.end(); }
|
CIterator end() const { return functions.end(); }
|
||||||
|
|
||||||
|
@ -93,6 +101,30 @@ public:
|
||||||
bool isStoped() const {return _stop;}
|
bool isStoped() const {return _stop;}
|
||||||
CIterator stopedAt() const { return lastCalled; }
|
CIterator stopedAt() const { return lastCalled; }
|
||||||
|
|
||||||
|
template<typename... Args, typename OldData>
|
||||||
|
void callWOld(const OldData &oldData, Args&&... args)
|
||||||
|
{
|
||||||
|
lastCalled = functions.end();
|
||||||
|
_stop = false;
|
||||||
|
for (CIterator iter = functions.begin(); iter != functions.end(); ++iter)
|
||||||
|
{
|
||||||
|
if (!_stop)
|
||||||
|
{
|
||||||
|
if (!iter->needsOldState)
|
||||||
|
{
|
||||||
|
iter->fn.call(std::forward<Args>(args)...);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
iter->fn.call(std::forward<Args>(args)..., oldData);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
lastCalled = iter;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
template<typename... Args>
|
template<typename... Args>
|
||||||
void call(type_tag<void>, Args&&... args)
|
void call(type_tag<void>, Args&&... args)
|
||||||
{
|
{
|
||||||
|
@ -101,14 +133,13 @@ public:
|
||||||
for (CIterator iter = functions.begin(); iter != functions.end(); ++iter)
|
for (CIterator iter = functions.begin(); iter != functions.end(); ++iter)
|
||||||
{
|
{
|
||||||
if (!_stop)
|
if (!_stop)
|
||||||
iter->second.call(std::forward<Args>(args)...);
|
iter->fn.call(std::forward<Args>(args)...);
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
lastCalled = iter;
|
lastCalled = iter;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
template<typename R, typename... Args>
|
template<typename R, typename... Args>
|
||||||
|
@ -121,7 +152,7 @@ public:
|
||||||
for (CIterator iter = functions.begin(); iter != functions.end(); ++iter)
|
for (CIterator iter = functions.begin(); iter != functions.end(); ++iter)
|
||||||
{
|
{
|
||||||
if (!_stop)
|
if (!_stop)
|
||||||
ret = iter->second.call(std::forward<Args>(args)...);
|
ret = iter->fn.call(std::forward<Args>(args)...);
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
lastCalled = iter;
|
lastCalled = iter;
|
||||||
|
@ -145,16 +176,25 @@ public:
|
||||||
explicit EventController(LuaState *luaCtrl);
|
explicit EventController(LuaState *luaCtrl);
|
||||||
typedef std::unordered_map<int, CallbackCollection> Container;
|
typedef std::unordered_map<int, CallbackCollection> Container;
|
||||||
|
|
||||||
void registerEvent(int event, sol::environment &env, sol::function& func);
|
void registerEvent(int event, sol::environment &env, sol::function& func, bool needsOldState);
|
||||||
CallbackCollection& GetEvents(Event event);
|
CallbackCollection& GetEvents(Event event);
|
||||||
Event createEvent();
|
Event createEvent();
|
||||||
void raiseEvent(Event id, sol::table data, const std::string &moduleName = "");
|
void raiseEvent(Event id, sol::table data, const std::string &moduleName = "");
|
||||||
void stop(int event);
|
void stop(int event);
|
||||||
|
|
||||||
template<Event event, typename R = void, typename... Args>
|
template<Event event, bool canProvideOldState = false, typename R = void, typename... Args>
|
||||||
R Call(Args&&... args)
|
R Call(Args&&... args)
|
||||||
{
|
{
|
||||||
return events.at(event).call(CallbackCollection::type_tag<R>{}, std::forward<Args>(args)...);
|
if(canProvideOldState)
|
||||||
|
events.at(event).callWOld(std::forward<Args>(args)...);
|
||||||
|
else
|
||||||
|
return events.at(event).call(CallbackCollection::type_tag<R>{}, std::forward<Args>(args)...);
|
||||||
|
}
|
||||||
|
|
||||||
|
template<Event event, bool canProvideOldState = false, typename R = void>
|
||||||
|
R Call()
|
||||||
|
{
|
||||||
|
return events.at(event).call(CallbackCollection::type_tag<R>{});
|
||||||
}
|
}
|
||||||
private:
|
private:
|
||||||
Container events;
|
Container events;
|
||||||
|
|
Loading…
Reference in a new issue