Add some more hacks to make planet seem more realistic

Original 8f6ef3764f
Authored by Jeija on May 18, 2016
master
Evert 2018-03-20 18:38:23 +02:00
parent d88f1ce6ed
commit 102ac5b205
No known key found for this signature in database
GPG Key ID: 1688DA83D222D0B5
5 changed files with 106 additions and 23 deletions

View File

@ -159,6 +159,8 @@ void ClientMap::updateDrawList()
// No occlusion culling when free_move is on and camera is
// inside ground
bool occlusion_culling_enabled = true;
if (g_settings->getBool("planet_enable"))
occlusion_culling_enabled = false;
if (g_settings->getBool("free_move")) {
MapNode n = getNodeNoEx(cam_pos_nodes);
if (n.getContent() == CONTENT_IGNORE ||
@ -194,14 +196,52 @@ void ClientMap::updateDrawList()
if (block->mesh)
block->mesh->updateCameraOffset(m_camera_offset);
float range = 100000 * BS;
if (!m_control.range_all)
range = m_control.wanted_range * BS;
/*
* Planet: Since the planet is actually just a flat map that wraps around
* a seemingly spherical object, there are 9 possible minimal distances to
* the same mapblock, because the end of the map on one side is the beginning
* of the map on the other side again. Find the minimal distance from the player
* to this mapblock.
*/
if (block->mesh != NULL && g_settings->getBool("planet_enable")) {
// Round planet circumference up to even number of mapblocks, in nodes
int planet_circumference = ceil(g_settings->getU16("planet_radius") * M_PI) * 2 * MAP_BLOCKSIZE;
float mindist = (cam_pos_nodes - block->getPos() * MAP_BLOCKSIZE).getLength();
int offset_minimal_x = 0, offset_minimal_z = 0;
for (int wrapx = -1; wrapx <= 1; ++wrapx)
for (int wrapz = -1; wrapz <= 1; ++wrapz) {
float distx = cam_pos_nodes.X - (block->getPos().X * MAP_BLOCKSIZE + wrapx * planet_circumference);
float distz = cam_pos_nodes.Z - (block->getPos().Z * MAP_BLOCKSIZE + wrapz * planet_circumference);
float dist = sqrt(distx * distx + distz * distz);
if (dist < mindist) {
mindist = dist;
offset_minimal_x = wrapx * planet_circumference;
offset_minimal_z = wrapz * planet_circumference;
}
}
block->mesh->updatePlanetOffset(-v3s16(offset_minimal_x, 0, offset_minimal_z));
// No need to render blocks deeper inside the planet than its radius
// or on the other side of the planet
if (block->getPos().Y < -g_settings->getU16("planet_radius"))
continue;
if (mindist > planet_circumference / 4)
continue;
}
float d = 0.0;
if (!isBlockInSight(block->getPos(), camera_position,
camera_direction, camera_fov, range, &d))
continue;
if (!g_settings->getBool("planet_enable")) {
float range = 100000 * BS;
if (m_control.range_all == false)
range = m_control.wanted_range * BS;
if (!isBlockInSight(block->getPos(), camera_position,
camera_direction, camera_fov, range, &d))
continue;
}
blocks_in_range++;
@ -231,6 +271,20 @@ void ClientMap::updateDrawList()
d > m_control.wanted_range * BS)
continue;
// Planet: Make sure block inside of planet bounds
if (g_settings->getBool("planet_enable")) {
// Round planet circumference up to even number of mapblocks
int planet_circumference_blocks = ceil(g_settings->getU16("planet_radius") * M_PI) * 2;
if (block->getPos().X > planet_circumference_blocks / 2 - 1)
continue;
if (block->getPos().X < -planet_circumference_blocks / 2)
continue;
if (block->getPos().Z > planet_circumference_blocks / 2 - 1)
continue;
if (block->getPos().Z < -planet_circumference_blocks / 2)
continue;
}
// Add to set
block->refGrab();
m_drawlist[block->getPos()] = block;
@ -370,7 +424,7 @@ void ClientMap::renderMap(video::IVideoDriver* driver, s32 pass)
continue;
float d = 0.0;
if (!isBlockInSight(block->getPos(), camera_position,
if (!g_settings->getBool("planet_enable") && !isBlockInSight(block->getPos(), camera_position,
camera_direction, camera_fov, 100000 * BS, &d))
continue;

View File

@ -744,6 +744,7 @@ protected:
const ToolCapabilities &playeritem_toolcap, f32 dtime);
void updateFrame(ProfilerGraph *graph, RunStats *stats, f32 dtime,
const CameraOrientation &cam);
void handlePlanet();
void updateProfilerGraphs(ProfilerGraph *graph);
// Misc
@ -883,6 +884,7 @@ private:
bool m_invert_mouse = false;
bool m_first_loop_after_window_activation = false;
bool m_camera_offset_changed = false;
bool m_planet_warp_changed = false;
bool m_does_lost_focus_pause_game = false;
@ -1118,12 +1120,37 @@ void Game::run()
// Update if minimap has been disabled by the server
m_game_ui->m_flags.show_minimap &= client->shouldShowMinimap();
handlePlanet();
if (m_does_lost_focus_pause_game && !device->isWindowFocused() && !isMenuActive()) {
showPauseMenu();
}
}
}
void Game::handlePlanet() {
LocalPlayer *player = client->getEnv().getLocalPlayer();
// Quick hack: Teleport to other side of planet at planet edges
if (g_settings->getBool("planet_enable")) {
// Round planet circumference up to even number of blocks, value in x/z coordinates
int planet_circumference = ceil(g_settings->getU16("planet_radius") * M_PI) * BS * MAP_BLOCKSIZE * 2;
v3f playerpos = player->getPosition();
if (playerpos.X > planet_circumference / 2 - 0.5 * BS)
playerpos.X = -(float)planet_circumference / 2 - 0.5 * BS;
if (playerpos.X < -planet_circumference / 2 - 0.5 * BS)
playerpos.X = (float)planet_circumference / 2 - 0.5 * BS;
if (playerpos.Z > planet_circumference / 2 - 0.5 * BS)
playerpos.Z = -(float)planet_circumference / 2 - 0.5 * BS;
if (playerpos.Z < -planet_circumference / 2 - 0.5 * BS)
playerpos.Z = (float)planet_circumference / 2 - 0.5 * BS;
m_planet_warp_changed = player->getPosition() != playerpos;
player->setPosition(playerpos);
}
}
void Game::shutdown()
{
@ -3769,7 +3796,7 @@ void Game::updateFrame(ProfilerGraph *graph, RunStats *stats, f32 dtime,
v3f camera_direction = camera->getDirection();
if (runData.update_draw_list_timer >= 0.2
|| runData.update_draw_list_last_cam_dir.getDistanceFrom(camera_direction) > 0.2
|| m_camera_offset_changed) {
|| m_camera_offset_changed || m_planet_warp_changed) {
runData.update_draw_list_timer = 0;
client->getEnv().getClientMap().updateDrawList();
runData.update_draw_list_last_cam_dir = camera_direction;

View File

@ -690,20 +690,6 @@ void LocalPlayer::applyControl(float dtime, Environment *env)
incH * physics_override_speed * slip_factor);
accelerateVertical(speedV * physics_override_speed,
incV * physics_override_speed);
// Quick hack: Teleport to other side of planet at planet edges
if (g_settings->getBool("planet_enable")) {
float planet_circumference = g_settings->getU16("planet_radius") * MAP_BLOCKSIZE * BS * 2 * M_PI;
std::cout << "circumference: " << planet_circumference << ", X and Z " << m_position.X << " " << m_position.Z << std::endl;
if (m_position.X > planet_circumference / 2)
m_position.X = -(float)planet_circumference / 2;
if (m_position.X < -planet_circumference / 2)
m_position.X = (float)planet_circumference / 2;
if (m_position.Z > planet_circumference / 2)
m_position.Z = -(float)planet_circumference / 2;
if (m_position.Z < -planet_circumference / 2)
m_position.Z = (float)planet_circumference / 2;
}
}
v3s16 LocalPlayer::getStandingNodePos()

View File

@ -1022,7 +1022,8 @@ MapBlockMesh::MapBlockMesh(MeshMakeData *data, v3s16 camera_offset):
m_shdrsrc(data->m_client->getShaderSource()),
m_animation_force_timer(0), // force initial animation
m_last_crack(-1),
m_last_daynight_ratio((u32) -1)
m_last_daynight_ratio((u32) -1),
m_planet_offset(v3s16(0, 0, 0))
{
for (auto &m : m_mesh)
m = new scene::SMesh();
@ -1268,6 +1269,17 @@ MapBlockMesh::~MapBlockMesh()
delete m_minimap_mapblock;
}
void MapBlockMesh::updatePlanetOffset(v3s16 planet_offset) {
if (planet_offset != m_planet_offset) {
for (scene::IMesh *m : m_mesh) {
translateMesh(m, intToFloat(m_planet_offset - planet_offset, BS));
if (m_enable_vbo)
m->setDirty();
}
m_planet_offset = planet_offset;
}
}
bool MapBlockMesh::animate(bool faraway, float time, int crack,
u32 daynight_ratio)
{

View File

@ -133,6 +133,7 @@ public:
}
void updateCameraOffset(v3s16 camera_offset);
void updatePlanetOffset(v3s16 planet_offset);
private:
scene::IMesh *m_mesh[MAX_TILE_LAYERS];
@ -171,6 +172,9 @@ private:
// Camera offset info -> do we have to translate the mesh?
v3s16 m_camera_offset;
// Mesh offset that is caused by the map wrapping around when rendering in planet mode
v3s16 m_planet_offset;
};