mirror of
https://git.huckle.dev/Huckles-Minecraft-Archive/LCE-Revelations.git
synced 2026-09-23 12:23:06 +00:00
chunk additions
This commit is contained in:
@@ -103,6 +103,11 @@ typedef int(__stdcall *fn_fire_piston_extend)(int dimId, int x, int y, int z, in
|
||||
typedef int(__stdcall *fn_fire_piston_retract)(int dimId, int x, int y, int z, int direction);
|
||||
typedef int(__stdcall *fn_fire_command_preprocess)(int entityId, const char *cmdUtf8, int cmdByteLen, char *outBuf, int outBufSize, int *outLen);
|
||||
typedef int(__stdcall *fn_fire_block_from_to)(int dimId, int fromX, int fromY, int fromZ, int toX, int toY, int toZ, int face);
|
||||
typedef void(__stdcall *fn_set_chunk_callbacks)(void *isChunkLoaded, void *loadChunk, void *unloadChunk, void *getLoadedChunks, void *isChunkInUse, void *getChunkSnapshot, void *unloadChunkRequest, void *regenerateChunk, void *refreshChunk);
|
||||
typedef void(__stdcall *fn_set_block_info_callbacks)(void *getSkyLight, void *getBlockLight, void *getBiomeId, void *setBiomeId);
|
||||
typedef void(__stdcall *fn_set_world_entity_callbacks)(void *getWorldEntities);
|
||||
typedef void(__stdcall *fn_fire_chunk_load)(int dimId, int chunkX, int chunkZ, int isNewChunk);
|
||||
typedef int(__stdcall *fn_fire_chunk_unload)(int dimId, int chunkX, int chunkZ);
|
||||
|
||||
struct OpenContainerInfo
|
||||
{
|
||||
@@ -160,6 +165,11 @@ static fn_fire_piston_extend s_managedFirePistonExtend = nullptr;
|
||||
static fn_fire_piston_retract s_managedFirePistonRetract = nullptr;
|
||||
static fn_fire_command_preprocess s_managedFireCommandPreprocess = nullptr;
|
||||
static fn_fire_block_from_to s_managedFireBlockFromTo = nullptr;
|
||||
static fn_set_chunk_callbacks s_managedSetChunkCallbacks = nullptr;
|
||||
static fn_set_block_info_callbacks s_managedSetBlockInfoCallbacks = nullptr;
|
||||
static fn_set_world_entity_callbacks s_managedSetWorldEntityCallbacks = nullptr;
|
||||
static fn_fire_chunk_load s_managedFireChunkLoad = nullptr;
|
||||
static fn_fire_chunk_unload s_managedFireChunkUnload = nullptr;
|
||||
|
||||
static bool s_initialized = false;
|
||||
|
||||
@@ -242,6 +252,11 @@ void Initialize()
|
||||
{L"FirePistonRetract", (void **)&s_managedFirePistonRetract},
|
||||
{L"FireCommandPreprocess", (void **)&s_managedFireCommandPreprocess},
|
||||
{L"FireBlockFromTo", (void **)&s_managedFireBlockFromTo},
|
||||
{L"SetChunkCallbacks", (void **)&s_managedSetChunkCallbacks},
|
||||
{L"SetBlockInfoCallbacks", (void **)&s_managedSetBlockInfoCallbacks},
|
||||
{L"SetWorldEntityCallbacks", (void **)&s_managedSetWorldEntityCallbacks},
|
||||
{L"FireChunkLoad", (void **)&s_managedFireChunkLoad},
|
||||
{L"FireChunkUnload", (void **)&s_managedFireChunkUnload},
|
||||
};
|
||||
|
||||
bool ok = true;
|
||||
@@ -336,6 +351,26 @@ void Initialize()
|
||||
(void *)&NativeGetPassengerId,
|
||||
(void *)&NativeGetEntityInfo);
|
||||
|
||||
s_managedSetChunkCallbacks(
|
||||
(void *)&NativeIsChunkLoaded,
|
||||
(void *)&NativeLoadChunk,
|
||||
(void *)&NativeUnloadChunk,
|
||||
(void *)&NativeGetLoadedChunks,
|
||||
(void *)&NativeIsChunkInUse,
|
||||
(void *)&NativeGetChunkSnapshot,
|
||||
(void *)&NativeUnloadChunkRequest,
|
||||
(void *)&NativeRegenerateChunk,
|
||||
(void *)&NativeRefreshChunk);
|
||||
|
||||
s_managedSetBlockInfoCallbacks(
|
||||
(void *)&NativeGetSkyLight,
|
||||
(void *)&NativeGetBlockLight,
|
||||
(void *)&NativeGetBiomeId,
|
||||
(void *)&NativeSetBiomeId);
|
||||
|
||||
s_managedSetWorldEntityCallbacks(
|
||||
(void *)&NativeGetWorldEntities);
|
||||
|
||||
LogInfo("fourkit", "FourKit initialized successfully.");
|
||||
}
|
||||
|
||||
@@ -1014,4 +1049,18 @@ bool FireBlockFromTo(int dimId, int fromX, int fromY, int fromZ, int toX, int to
|
||||
return false;
|
||||
return s_managedFireBlockFromTo(dimId, fromX, fromY, fromZ, toX, toY, toZ, face) != 0;
|
||||
}
|
||||
|
||||
void FireChunkLoad(int dimId, int chunkX, int chunkZ, bool isNewChunk)
|
||||
{
|
||||
if (!s_initialized || !s_managedFireChunkLoad)
|
||||
return;
|
||||
s_managedFireChunkLoad(dimId, chunkX, chunkZ, isNewChunk ? 1 : 0);
|
||||
}
|
||||
|
||||
bool FireChunkUnload(int dimId, int chunkX, int chunkZ)
|
||||
{
|
||||
if (!s_initialized || !s_managedFireChunkUnload)
|
||||
return false;
|
||||
return s_managedFireChunkUnload(dimId, chunkX, chunkZ) != 0;
|
||||
}
|
||||
} // namespace FourKitBridge
|
||||
|
||||
@@ -105,6 +105,8 @@ namespace FourKitBridge
|
||||
bool FirePistonRetract(int dimId, int x, int y, int z, int direction);
|
||||
bool FireCommandPreprocess(int entityId, const std::wstring &commandLine, std::wstring &outCommand);
|
||||
bool FireBlockFromTo(int dimId, int fromX, int fromY, int fromZ, int toX, int toY, int toZ, int face);
|
||||
void FireChunkLoad(int dimId, int chunkX, int chunkZ, bool isNewChunk);
|
||||
bool FireChunkUnload(int dimId, int chunkX, int chunkZ);
|
||||
#else
|
||||
// Standalone build: every hook is an inline no-op. Cancellable hooks
|
||||
// return false so vanilla code paths run unmodified, AND every out
|
||||
@@ -211,5 +213,7 @@ namespace FourKitBridge
|
||||
inline bool FirePistonRetract(int, int, int, int, int) { return false; }
|
||||
inline bool FireCommandPreprocess(int, const std::wstring &commandLine, std::wstring &outCommand) { outCommand = commandLine; return false; }
|
||||
inline bool FireBlockFromTo(int, int, int, int, int, int, int, int) { return false; }
|
||||
inline void FireChunkLoad(int, int, int, bool) {}
|
||||
inline bool FireChunkUnload(int, int, int) { return false; }
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -13,6 +13,10 @@
|
||||
#include "../Minecraft.Client/ServerLevel.h"
|
||||
#include "../Minecraft.Client/ServerPlayer.h"
|
||||
#include "../Minecraft.Client/ServerPlayerGameMode.h"
|
||||
#include "../Minecraft.Client/ServerChunkCache.h"
|
||||
#include "../Minecraft.World/LevelChunk.h"
|
||||
#include "../Minecraft.World/Biome.h"
|
||||
#include "../Minecraft.World/LightLayer.h"
|
||||
#include "../Minecraft.Client/Windows64/Network/WinsockNetLayer.h"
|
||||
#include "../Minecraft.World/AbstractContainerMenu.h"
|
||||
#include "../Minecraft.World/AddGlobalEntityPacket.h"
|
||||
@@ -1268,4 +1272,232 @@ void __cdecl NativeGetEntityInfo(int entityId, double *outData)
|
||||
outData[4] = (double)entity->dimension;
|
||||
}
|
||||
|
||||
int __cdecl NativeGetWorldEntities(int dimId, int **outBuf)
|
||||
{
|
||||
*outBuf = nullptr;
|
||||
ServerLevel *level = GetLevel(dimId);
|
||||
if (!level)
|
||||
return 0;
|
||||
|
||||
EnterCriticalSection(&level->m_entitiesCS);
|
||||
int total = (int)level->entities.size();
|
||||
int *buf = (int *)CoTaskMemAlloc(total * 3 * sizeof(int));
|
||||
int count = 0;
|
||||
if (buf)
|
||||
{
|
||||
for (auto &entity : level->entities)
|
||||
{
|
||||
if (!entity)
|
||||
continue;
|
||||
int idx = count * 3;
|
||||
buf[idx] = entity->entityId;
|
||||
buf[idx + 1] = MapEntityType((int)entity->GetType());
|
||||
buf[idx + 2] = entity->instanceof(eTYPE_LIVINGENTITY) ? 1 : 0;
|
||||
count++;
|
||||
}
|
||||
}
|
||||
LeaveCriticalSection(&level->m_entitiesCS);
|
||||
*outBuf = buf;
|
||||
return count;
|
||||
}
|
||||
|
||||
int __cdecl NativeIsChunkLoaded(int dimId, int chunkX, int chunkZ)
|
||||
{
|
||||
ServerLevel *level = GetLevel(dimId);
|
||||
if (!level || !level->cache)
|
||||
return 0;
|
||||
return level->cache->hasChunk(chunkX, chunkZ) ? 1 : 0;
|
||||
}
|
||||
|
||||
int __cdecl NativeLoadChunk(int dimId, int chunkX, int chunkZ, int generate)
|
||||
{
|
||||
ServerLevel *level = GetLevel(dimId);
|
||||
if (!level || !level->cache)
|
||||
return 0;
|
||||
LevelChunk *chunk = level->cache->create(chunkX, chunkZ);
|
||||
return (chunk != nullptr) ? 1 : 0;
|
||||
}
|
||||
|
||||
int __cdecl NativeUnloadChunk(int dimId, int chunkX, int chunkZ, int save, int safe)
|
||||
{
|
||||
ServerLevel *level = GetLevel(dimId);
|
||||
if (!level || !level->cache)
|
||||
return 0;
|
||||
if (safe)
|
||||
{
|
||||
if (!level->cache->hasChunk(chunkX, chunkZ))
|
||||
return 0;
|
||||
LevelChunk *chunk = level->cache->getChunk(chunkX, chunkZ);
|
||||
if (chunk && chunk->containsPlayer())
|
||||
return 0;
|
||||
}
|
||||
level->cache->drop(chunkX, chunkZ);
|
||||
return 1;
|
||||
}
|
||||
|
||||
int __cdecl NativeGetLoadedChunks(int dimId, int **coordBuf)
|
||||
{
|
||||
// wow gay
|
||||
*coordBuf = nullptr;
|
||||
ServerLevel *level = GetLevel(dimId);
|
||||
if (!level || !level->cache)
|
||||
return 0;
|
||||
|
||||
std::vector<LevelChunk *> *list = level->cache->getLoadedChunkList();
|
||||
|
||||
if (!list)
|
||||
return 0;
|
||||
|
||||
|
||||
|
||||
int total = (int)list->size();
|
||||
int *buf = (int *)CoTaskMemAlloc(total * 2 * sizeof(int));
|
||||
int count = 0;
|
||||
|
||||
if (buf)
|
||||
{
|
||||
for (auto *chunk : *list)
|
||||
{
|
||||
if (chunk)
|
||||
{
|
||||
buf[count * 2] = chunk->x;
|
||||
buf[count * 2 + 1] = chunk->z;
|
||||
count++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
*coordBuf = buf;
|
||||
return count;
|
||||
}
|
||||
|
||||
int __cdecl NativeIsChunkInUse(int dimId, int chunkX, int chunkZ)
|
||||
{
|
||||
PlayerList *list = MinecraftServer::getPlayerList();
|
||||
if (!list)
|
||||
return 0;
|
||||
for (auto &p : list->players)
|
||||
{
|
||||
if (p && p->dimension == dimId)
|
||||
{
|
||||
int px = (int)floor(p->x) >> 4;
|
||||
int pz = (int)floor(p->z) >> 4;
|
||||
if (px == chunkX && pz == chunkZ)
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
void __cdecl NativeGetChunkSnapshot(int dimId, int chunkX, int chunkZ, int *blockIds, int *blockData, int *maxBlockY)
|
||||
{
|
||||
ServerLevel *level = GetLevel(dimId);
|
||||
if (!level || !level->cache)
|
||||
{
|
||||
memset(blockIds, 0, 16 * 128 * 16 * sizeof(int));
|
||||
memset(blockData, 0, 16 * 128 * 16 * sizeof(int));
|
||||
memset(maxBlockY, 0, 16 * 16 * sizeof(int));
|
||||
return;
|
||||
}
|
||||
if (!level->cache->hasChunk(chunkX, chunkZ))
|
||||
{
|
||||
memset(blockIds, 0, 16 * 128 * 16 * sizeof(int));
|
||||
memset(blockData, 0, 16 * 128 * 16 * sizeof(int));
|
||||
memset(maxBlockY, 0, 16 * 16 * sizeof(int));
|
||||
return;
|
||||
}
|
||||
LevelChunk *chunk = level->cache->getChunk(chunkX, chunkZ);
|
||||
if (!chunk)
|
||||
{
|
||||
memset(blockIds, 0, 16 * 128 * 16 * sizeof(int));
|
||||
memset(blockData, 0, 16 * 128 * 16 * sizeof(int));
|
||||
memset(maxBlockY, 0, 16 * 16 * sizeof(int));
|
||||
return;
|
||||
}
|
||||
for (int lx = 0; lx < 16; lx++)
|
||||
{
|
||||
for (int lz = 0; lz < 16; lz++)
|
||||
{
|
||||
int highest = 0;
|
||||
for (int ly = 0; ly < 128; ly++)
|
||||
{
|
||||
int idx = (lx * 128 * 16) + (ly * 16) + lz;
|
||||
blockIds[idx] = chunk->getTile(lx, ly, lz);
|
||||
blockData[idx] = chunk->getData(lx, ly, lz);
|
||||
if (blockIds[idx] != 0)
|
||||
highest = ly;
|
||||
}
|
||||
maxBlockY[lx * 16 + lz] = highest;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int __cdecl NativeUnloadChunkRequest(int dimId, int chunkX, int chunkZ, int safe)
|
||||
{
|
||||
ServerLevel *level = GetLevel(dimId);
|
||||
if (!level || !level->cache)
|
||||
return 0;
|
||||
if (safe)
|
||||
{
|
||||
if (!level->cache->hasChunk(chunkX, chunkZ))
|
||||
return 0;
|
||||
LevelChunk *chunk = level->cache->getChunk(chunkX, chunkZ);
|
||||
if (chunk && chunk->containsPlayer())
|
||||
return 0;
|
||||
}
|
||||
level->cache->drop(chunkX, chunkZ);
|
||||
return 1;
|
||||
}
|
||||
|
||||
int __cdecl NativeRegenerateChunk(int dimId, int chunkX, int chunkZ)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int __cdecl NativeRefreshChunk(int dimId, int chunkX, int chunkZ)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int __cdecl NativeGetSkyLight(int dimId, int x, int y, int z)
|
||||
{
|
||||
ServerLevel *level = GetLevel(dimId);
|
||||
if (!level)
|
||||
return 0;
|
||||
return level->getBrightness(LightLayer::Sky, x, y, z);
|
||||
}
|
||||
|
||||
int __cdecl NativeGetBlockLight(int dimId, int x, int y, int z)
|
||||
{
|
||||
ServerLevel *level = GetLevel(dimId);
|
||||
if (!level)
|
||||
return 0;
|
||||
return level->getBrightness(LightLayer::Block, x, y, z);
|
||||
}
|
||||
|
||||
int __cdecl NativeGetBiomeId(int dimId, int x, int z)
|
||||
{
|
||||
ServerLevel *level = GetLevel(dimId);
|
||||
if (!level)
|
||||
return 1;
|
||||
Biome *biome = level->getBiome(x, z);
|
||||
return biome ? biome->id : 1;
|
||||
}
|
||||
|
||||
void __cdecl NativeSetBiomeId(int dimId, int x, int z, int biomeId)
|
||||
{
|
||||
ServerLevel *level = GetLevel(dimId);
|
||||
if (!level)
|
||||
return;
|
||||
LevelChunk *chunk = level->getChunk(x >> 4, z >> 4);
|
||||
if (!chunk)
|
||||
return;
|
||||
byteArray biomes = chunk->getBiomes();
|
||||
if (biomes.data == nullptr)
|
||||
return;
|
||||
int lx = x & 0xf;
|
||||
int lz = z & 0xf;
|
||||
biomes.data[(lz << 4) | lx] = static_cast<unsigned char>(biomeId & 0xff);
|
||||
}
|
||||
|
||||
} // namespace FourKitBridge
|
||||
|
||||
@@ -78,4 +78,24 @@ namespace FourKitBridge
|
||||
int __cdecl NativeGetVehicleId(int entityId);
|
||||
int __cdecl NativeGetPassengerId(int entityId);
|
||||
void __cdecl NativeGetEntityInfo(int entityId, double *outData);
|
||||
|
||||
// chunk
|
||||
int __cdecl NativeIsChunkLoaded(int dimId, int chunkX, int chunkZ);
|
||||
int __cdecl NativeLoadChunk(int dimId, int chunkX, int chunkZ, int generate);
|
||||
int __cdecl NativeUnloadChunk(int dimId, int chunkX, int chunkZ, int save, int safe);
|
||||
int __cdecl NativeGetLoadedChunks(int dimId, int **coordBuf);
|
||||
int __cdecl NativeIsChunkInUse(int dimId, int chunkX, int chunkZ);
|
||||
void __cdecl NativeGetChunkSnapshot(int dimId, int chunkX, int chunkZ, int *blockIds, int *blockData, int *maxBlockY);
|
||||
int __cdecl NativeUnloadChunkRequest(int dimId, int chunkX, int chunkZ, int safe);
|
||||
int __cdecl NativeRegenerateChunk(int dimId, int chunkX, int chunkZ);
|
||||
int __cdecl NativeRefreshChunk(int dimId, int chunkX, int chunkZ);
|
||||
|
||||
// world entity bs
|
||||
int __cdecl NativeGetWorldEntities(int dimId, int **outBuf);
|
||||
|
||||
// block info (light, biome)
|
||||
int __cdecl NativeGetSkyLight(int dimId, int x, int y, int z);
|
||||
int __cdecl NativeGetBlockLight(int dimId, int x, int y, int z);
|
||||
int __cdecl NativeGetBiomeId(int dimId, int x, int z);
|
||||
void __cdecl NativeSetBiomeId(int dimId, int x, int z, int biomeId);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user