mirror of
https://github.com/luanti-org/luanti.git
synced 2025-07-27 17:28:41 +00:00
Add callback on_mapblocks_changed
This commit is contained in:
parent
7701e70dc9
commit
5c248c2d7d
10 changed files with 141 additions and 6 deletions
|
@ -121,3 +121,12 @@ void warn_if_field_exists(lua_State *L, int table,
|
|||
|
||||
size_t write_array_slice_float(lua_State *L, int table_index, float *data,
|
||||
v3u16 data_size, v3u16 slice_offset, v3u16 slice_size);
|
||||
|
||||
// This must match the implementation in builtin/game/misc_s.lua
|
||||
// Note that this returns a floating point result as Lua integers are 32-bit
|
||||
inline lua_Number hash_node_position(v3s16 pos)
|
||||
{
|
||||
return (((s64)pos.Z + 0x8000L) << 32)
|
||||
| (((s64)pos.Y + 0x8000L) << 16)
|
||||
| ((s64)pos.X + 0x8000L);
|
||||
}
|
||||
|
|
|
@ -299,3 +299,36 @@ void ScriptApiEnv::on_liquid_transformed(
|
|||
|
||||
runCallbacks(2, RUN_CALLBACKS_MODE_FIRST);
|
||||
}
|
||||
|
||||
void ScriptApiEnv::on_mapblocks_changed(const std::unordered_set<v3s16> &set)
|
||||
{
|
||||
SCRIPTAPI_PRECHECKHEADER
|
||||
|
||||
// Get core.registered_on_mapblocks_changed
|
||||
lua_getglobal(L, "core");
|
||||
lua_getfield(L, -1, "registered_on_mapblocks_changed");
|
||||
luaL_checktype(L, -1, LUA_TTABLE);
|
||||
lua_remove(L, -2);
|
||||
|
||||
// Convert the set to a set of position hashes
|
||||
lua_createtable(L, 0, set.size());
|
||||
for(const v3s16 &p : set) {
|
||||
lua_pushnumber(L, hash_node_position(p));
|
||||
lua_pushboolean(L, true);
|
||||
lua_rawset(L, -3);
|
||||
}
|
||||
lua_pushinteger(L, set.size());
|
||||
|
||||
runCallbacks(2, RUN_CALLBACKS_MODE_FIRST);
|
||||
}
|
||||
|
||||
bool ScriptApiEnv::has_on_mapblocks_changed()
|
||||
{
|
||||
SCRIPTAPI_PRECHECKHEADER
|
||||
|
||||
// Get core.registered_on_mapblocks_changed
|
||||
lua_getglobal(L, "core");
|
||||
lua_getfield(L, -1, "registered_on_mapblocks_changed");
|
||||
luaL_checktype(L, -1, LUA_TTABLE);
|
||||
return lua_objlen(L, -1) > 0;
|
||||
}
|
||||
|
|
|
@ -22,6 +22,7 @@ with this program; if not, write to the Free Software Foundation, Inc.,
|
|||
#include "cpp_api/s_base.h"
|
||||
#include "irr_v3d.h"
|
||||
#include "mapnode.h"
|
||||
#include <unordered_set>
|
||||
#include <vector>
|
||||
|
||||
class ServerEnvironment;
|
||||
|
@ -48,5 +49,11 @@ public:
|
|||
// Called after liquid transform changes
|
||||
void on_liquid_transformed(const std::vector<std::pair<v3s16, MapNode>> &list);
|
||||
|
||||
// Called after mapblock changes
|
||||
void on_mapblocks_changed(const std::unordered_set<v3s16> &set);
|
||||
|
||||
// Determines whether there are any on_mapblocks_changed callbacks
|
||||
bool has_on_mapblocks_changed();
|
||||
|
||||
void initializeEnvironment(ServerEnvironment *env);
|
||||
};
|
||||
|
|
|
@ -381,6 +381,18 @@ void ActiveBlockList::update(std::vector<PlayerSAO*> &active_players,
|
|||
m_list = std::move(newlist);
|
||||
}
|
||||
|
||||
/*
|
||||
OnMapblocksChangedReceiver
|
||||
*/
|
||||
|
||||
void OnMapblocksChangedReceiver::onMapEditEvent(const MapEditEvent &event)
|
||||
{
|
||||
assert(receiving);
|
||||
for (const v3s16 &p : event.modified_blocks) {
|
||||
modified_blocks.insert(p);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
ServerEnvironment
|
||||
*/
|
||||
|
@ -476,6 +488,11 @@ void ServerEnvironment::init()
|
|||
|
||||
m_player_database = openPlayerDatabase(player_backend_name, m_path_world, conf);
|
||||
m_auth_database = openAuthDatabase(auth_backend_name, m_path_world, conf);
|
||||
|
||||
if (m_map && m_script->has_on_mapblocks_changed()) {
|
||||
m_map->addEventReceiver(&m_on_mapblocks_changed_receiver);
|
||||
m_on_mapblocks_changed_receiver.receiving = true;
|
||||
}
|
||||
}
|
||||
|
||||
ServerEnvironment::~ServerEnvironment()
|
||||
|
@ -1570,6 +1587,14 @@ void ServerEnvironment::step(float dtime)
|
|||
// Send outdated detached inventories
|
||||
m_server->sendDetachedInventories(PEER_ID_INEXISTENT, true);
|
||||
|
||||
// Notify mods of modified mapblocks
|
||||
if (m_on_mapblocks_changed_receiver.receiving &&
|
||||
!m_on_mapblocks_changed_receiver.modified_blocks.empty()) {
|
||||
std::unordered_set<v3s16> modified_blocks;
|
||||
std::swap(modified_blocks, m_on_mapblocks_changed_receiver.modified_blocks);
|
||||
m_script->on_mapblocks_changed(modified_blocks);
|
||||
}
|
||||
|
||||
const auto end_time = porting::getTimeUs();
|
||||
m_step_time_counter->increment(end_time - start_time);
|
||||
}
|
||||
|
|
|
@ -21,7 +21,7 @@ with this program; if not, write to the Free Software Foundation, Inc.,
|
|||
|
||||
#include "activeobject.h"
|
||||
#include "environment.h"
|
||||
#include "mapnode.h"
|
||||
#include "map.h"
|
||||
#include "settings.h"
|
||||
#include "server/activeobjectmgr.h"
|
||||
#include "util/numeric.h"
|
||||
|
@ -30,9 +30,7 @@ with this program; if not, write to the Free Software Foundation, Inc.,
|
|||
#include <random>
|
||||
|
||||
class IGameDef;
|
||||
class ServerMap;
|
||||
struct GameParams;
|
||||
class MapBlock;
|
||||
class RemotePlayer;
|
||||
class PlayerDatabase;
|
||||
class AuthDatabase;
|
||||
|
@ -193,6 +191,16 @@ public:
|
|||
std::set<v3s16> m_forceloaded_list;
|
||||
};
|
||||
|
||||
/*
|
||||
ServerEnvironment::m_on_mapblocks_changed_receiver
|
||||
*/
|
||||
struct OnMapblocksChangedReceiver : public MapEventReceiver {
|
||||
std::unordered_set<v3s16> modified_blocks;
|
||||
bool receiving = false;
|
||||
|
||||
void onMapEditEvent(const MapEditEvent &event) override;
|
||||
};
|
||||
|
||||
/*
|
||||
Operation mode for ServerEnvironment::clearObjects()
|
||||
*/
|
||||
|
@ -455,6 +463,8 @@ private:
|
|||
Server *m_server;
|
||||
// Active Object Manager
|
||||
server::ActiveObjectMgr m_ao_manager;
|
||||
// on_mapblocks_changed map event receiver
|
||||
OnMapblocksChangedReceiver m_on_mapblocks_changed_receiver;
|
||||
// World path
|
||||
const std::string m_path_world;
|
||||
// Outgoing network message buffer for active objects
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue