Enforce minimum client_mapblock_limit depending on view range

This commit is contained in:
sfan5 2025-03-01 00:16:18 +01:00
parent 24c1230c7b
commit 062207e696
3 changed files with 35 additions and 15 deletions

View file

@ -1998,7 +1998,9 @@ max_out_chat_queue_size (Maximum size of the outgoing chat queue) int 20 -1 3276
client_unload_unused_data_timeout (Mapblock unload timeout) float 600.0 0.0
# Maximum number of mapblocks for client to be kept in memory.
# Set to -1 for unlimited amount.
# Note that there is an internal dynamic minimum number of blocks that
# won't be deleted, depending on the current view range.
# Set to -1 for no limit.
client_mapblock_limit (Mapblock limit) int 7500 -1 2147483647
# Maximum number of blocks that are simultaneously sent per client.

View file

@ -446,20 +446,43 @@ void Client::step(float dtime)
/*
Run Map's timers and unload unused data
*/
const float map_timer_and_unload_dtime = 5.25;
constexpr float map_timer_and_unload_dtime = 5.25f;
constexpr s32 mapblock_limit_enforce_distance = 200;
if(m_map_timer_and_unload_interval.step(dtime, map_timer_and_unload_dtime)) {
std::vector<v3s16> deleted_blocks;
// Determine actual block limit to use
const s32 configured_limit = g_settings->getS32("client_mapblock_limit");
s32 mapblock_limit;
if (configured_limit < 0) {
mapblock_limit = -1;
} else {
s32 view_range = g_settings->getS16("viewing_range");
// Up to a certain limit we want to guarantee that the client can keep
// a full 360° view loaded in memory without blocks vanishing behind
// the players back.
// We use a sphere volume to approximate this. In practice far less
// blocks will be needed due to occlusion/culling.
float blocks_range = ceilf(std::min(mapblock_limit_enforce_distance, view_range)
/ (float) MAP_BLOCKSIZE);
mapblock_limit = (4.f/3.f) * M_PI * powf(blocks_range, 3);
assert(mapblock_limit > 0);
mapblock_limit = std::max(mapblock_limit, configured_limit);
if (mapblock_limit > std::max(configured_limit, m_mapblock_limit_logged)) {
infostream << "Client: using block limit of " << mapblock_limit
<< " rather than configured " << configured_limit
<< " due to view range." << std::endl;
m_mapblock_limit_logged = mapblock_limit;
}
}
m_env.getMap().timerUpdate(map_timer_and_unload_dtime,
std::max(g_settings->getFloat("client_unload_unused_data_timeout"), 0.0f),
g_settings->getS32("client_mapblock_limit"),
&deleted_blocks);
mapblock_limit, &deleted_blocks);
/*
Send info to server
NOTE: This loop is intentionally iterated the way it is.
*/
// Send info to server
std::vector<v3s16>::iterator i = deleted_blocks.begin();
auto i = deleted_blocks.begin();
std::vector<v3s16> sendlist;
for(;;) {
if(sendlist.size() == 255 || i == deleted_blocks.end()) {

View file

@ -486,23 +486,18 @@ private:
u8 m_server_ser_ver;
// Used version of the protocol with server
// Values smaller than 25 only mean they are smaller than 25,
// and aren't accurate. We simply just don't know, because
// the server didn't send the version back then.
// If 0, server init hasn't been received yet.
u16 m_proto_ver = 0;
bool m_update_wielded_item = false;
Inventory *m_inventory_from_server = nullptr;
float m_inventory_from_server_age = 0.0f;
s32 m_mapblock_limit_logged = 0;
PacketCounter m_packetcounter;
// Block mesh animation parameters
float m_animation_time = 0.0f;
int m_crack_level = -1;
v3s16 m_crack_pos;
// 0 <= m_daynight_i < DAYNIGHT_CACHE_COUNT
//s32 m_daynight_i;
//u32 m_daynight_ratio;
std::queue<std::wstring> m_out_chat_queue;
u32 m_last_chat_message_sent;
float m_chat_message_allowance = 5.0f;