This commit is contained in:
2026-07-25 21:54:02 +02:00
parent c62daa9c1c
commit d9dfff3339
6 changed files with 113 additions and 32 deletions

View File

@@ -6,7 +6,6 @@ include(cmake/CPM.cmake)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED TRUE)
set(CMAKE_POLICY_VERSION_MINIMUM 3.10)
add_definitions(-DLUA_USE_DLOPEN)
include(cmake/EnumOption.cmake)
if(EMSCRIPTEN)
@@ -34,9 +33,11 @@ if (${PLATFORM} STREQUAL "Desktop")
add_definitions(-D_CRT_SECURE_NO_WARNINGS)
include_directories(misc/windows)
set(EXTRA_LIBS ws2_32 winhttp)
add_definitions(-DLUA_DL_DLL=1)
elseif(UNIX)
find_library(pthread NAMES pthread)
set(EXTRA_LIBS pthread m)
add_definitions(-DLUA_USE_DLOPEN=1)
endif()
elseif (${PLATFORM} STREQUAL "Web")

View File

@@ -6,7 +6,7 @@
#include "../../../world/level/Level.h"
#include "../../../network/RakNetInstance.h"
#include "../../../network/ServerSideNetworkHandler.h"
#include "../../../network/packet/ChatPacket.h"
#include "../../../network/packet/MessagePacket.h"
#include "../../../platform/log.h"
#include "util/StringUtils.h"
@@ -76,7 +76,7 @@ void ConsoleScreen::execute()
if (minecraft->netCallback && minecraft->raknetInstance->isServer()) {
static_cast<ServerSideNetworkHandler*>(minecraft->netCallback)->displayGameMessage(_input);
} else if (minecraft->netCallback) {
ChatPacket chatPkt(_input);
MessagePacket chatPkt(_input.c_str());
minecraft->raknetInstance->send(chatPkt);
} else {
minecraft->gui.addMessage("<" + minecraft->player->name + "> " + _input);

View File

@@ -164,9 +164,13 @@ void ServerSideNetworkHandler::handle(const RakNet::RakNetGUID& source, ChatPack
if (packet->message[0] == '/') {
// This is a command
ChatPacket resp(minecraft->commandManager().execute(*minecraft, *player, Util::stringTrim(packet->message.substr(1))));
auto cmd = Util::stringTrim(packet->message.substr(1));
if (PluginsManager::get().emitCommands(cmd, LuaPlayer(source))) {
ChatPacket resp(minecraft->commandManager().execute(*minecraft, *player, cmd));
return sendPrivate(resp, source);
}
}
displayGameMessage("<" + player->name + "> " + packet->message);
PluginsManager::get().emit("Message", LuaPlayer(source), packet->message);
@@ -452,12 +456,18 @@ void ServerSideNetworkHandler::handle(const RakNet::RakNetGUID& source, MovePlay
// }
// }
PluginsManager::get().emit(
"PlayerMovement",
LuaPlayer(source),
packet->x, packet->y, packet->z, packet->yRot, packet->xRot, // newPos
player->x, player->y, player->z, player->yRot, player->xRot // oldPos
);
entity->xd = entity->yd = entity->zd = 0;
entity->lerpTo(packet->x, packet->y, packet->z, packet->yRot, packet->xRot, 3);
// broadcast this packet to other clients
redistributePacket(packet, source);
}
}

View File

@@ -5,49 +5,89 @@
#include <network/ServerSideNetworkHandler.h>
#include <world/entity/player/Player.h>
#include <client/Minecraft.h>
#include <network/packet/ChatPacket.h>
#include <network/packet/MovePlayerPacket.h>
#include <world/entity/player/Inventory.h>
class LuaPlayer {
public:
LuaPlayer(const RakNet::RakNetGUID source) : m_source(source) {}
std::string getNickname() {
Player* getPlayer() {
auto mc = PluginsManager::get().getMinecraft();
ServerSideNetworkHandler* ss = (ServerSideNetworkHandler*) mc->netCallback;
auto plr = ss->getPlayer(m_source);
return plr;
}
std::string getNickname() {
auto plr = getPlayer();
if (plr != nullptr) return plr->name;
return "";
}
float getX() {
auto mc = PluginsManager::get().getMinecraft();
ServerSideNetworkHandler* ss = (ServerSideNetworkHandler*) mc->netCallback;
std::tuple<float, float, float, float, float> getPos() {
auto plr = getPlayer();
if (plr != nullptr) return {plr->x, plr->y, plr->z, plr->yRot, plr->xRot};
auto plr = ss->getPlayer(m_source);
if (plr != nullptr) return plr->x;
return 0;
return {0, 0, 0, 0, 0};
}
float getY() {
void setPos(float x, float y, float z, float yRot, float xRot) {
auto plr = getPlayer();
if (plr == nullptr) return;
auto mc = PluginsManager::get().getMinecraft();
ServerSideNetworkHandler* ss = (ServerSideNetworkHandler*) mc->netCallback;
auto plr = ss->getPlayer(m_source);
if (plr != nullptr) return plr->y;
return 0;
// plr->x = x;
// plr->y = y;
// plr->z = z;
// plr->yRot = yRot;
// plr->xRot = xRot;
plr->xd = plr->yd = plr->zd = 0;
plr->lerpTo(x, y, z, yRot, xRot, 3);
MovePlayerPacket move(plr->entityId, x, y, z, yRot, xRot);
ss->sendPrivate(move, m_source);
}
float getZ() {
void sendMessage(std::string msg) {
auto mc = PluginsManager::get().getMinecraft();
ServerSideNetworkHandler* ss = (ServerSideNetworkHandler*) mc->netCallback;
ChatPacket packet(msg);
auto plr = ss->getPlayer(m_source);
if (plr != nullptr) return plr->z;
ss->sendPrivate(packet, m_source);
}
return 0;
void addItem(int id, int count, int auxValue) {
auto plr = getPlayer();
if (plr == nullptr) return;
plr->inventory->add(new ItemInstance(id, count, auxValue));
}
sol::table getInventory() {
auto plr = getPlayer();
if (plr == nullptr) return {};
sol::table inv = PluginsManager::get().getLua().create_table();
for (int i = Inventory::MAX_SELECTION_SIZE; i < plr->inventory->getContainerSize(); i++) {
auto itm = plr->inventory->getItem(i);
if (itm != NULL) {
inv[i - 8] = {itm->id, itm->count, itm->getAuxValue()};
} else {
inv[i - 8] = sol::lua_nil;
}
}
return inv;
}
private:
const RakNet::RakNetGUID m_source;

View File

@@ -8,7 +8,7 @@
namespace fs = std::filesystem;
void PluginsManager::init(Minecraft& minecraft) {
m_lua.open_libraries(sol::lib::base, sol::lib::package, sol::lib::string, sol::lib::math, sol::lib::table);
m_lua.open_libraries(sol::lib::base, sol::lib::package, sol::lib::string, sol::lib::math, sol::lib::table, sol::lib::io);
registerTypes();
m_minecraft = &minecraft;
@@ -19,10 +19,13 @@ void PluginsManager::registerTypes() {
// m_lua.set_function("subscribe", &PluginsManager::subscribe);
m_lua.set_function("subscribe", [this](std::string event, sol::protected_function func) {
// @note: why the .at() not working?
m_callbacks[event].push_back(func);
});
m_lua.set_function("addCommand", [this](std::string commandName, sol::function func) {
m_luaCommands[commandName].push_back(func);
});
m_lua.new_usertype<LuaServer>(
"Server",
"sendMessage", &LuaServer::sendServerMessage
@@ -31,9 +34,10 @@ void PluginsManager::registerTypes() {
m_lua.new_usertype<LuaPlayer>(
"Player",
"getNickname", &LuaPlayer::getNickname,
"getX", &LuaPlayer::getX,
"getY", &LuaPlayer::getY,
"getZ", &LuaPlayer::getZ
"getPos", &LuaPlayer::getPos,
"setPos", &LuaPlayer::setPos,
"sendMessage", &LuaPlayer::sendMessage,
"getInventory", &LuaPlayer::getInventory
);
m_lua["Server"] = &m_srv;
@@ -42,7 +46,13 @@ void PluginsManager::registerTypes() {
void PluginsManager::loadPlugins() {
std::string path = "plugins/";
for (const auto & entry : fs::directory_iterator(path)) {
if (fs::exists(path)) {
for (const auto& entry : fs::directory_iterator(path)) {
if (!fs::is_directory(entry.path().string())) {
m_lua.script_file(entry.path().string());
}
}
} else {
std::filesystem::create_directory(path);
}
}

View File

@@ -20,6 +20,8 @@ public:
void loadPlugins();
sol::state& getLua() { return m_lua; }
// @ai @note maybe we should rewrite it...
// problem that i dont know how to pass args in sol::function dynamically
// so i used ai
@@ -40,9 +42,27 @@ public:
}
}
template<typename... Args>
int emitCommands(std::string event, Args&&... args) {
auto it = m_luaCommands.find(event);
if (it == m_luaCommands.end()) return 1;
for (auto& callback : it->second) {
sol::protected_function_result result = callback(std::forward<Args>(args)...);
if (!result.valid()) {
sol::error err = result;
std::cout << err.what() << std::endl;
}
}
return 0;
}
Minecraft* getMinecraft() { return m_minecraft; }
private:
std::unordered_map<std::string, std::vector<sol::function>> m_callbacks;
std::unordered_map<std::string, std::vector<sol::function>> m_luaCommands;
LuaServer m_srv;
sol::state m_lua;