From 5567c7da33666372c9c66e5669037c5e1bc3ff21 Mon Sep 17 00:00:00 2001 From: Relintai Date: Thu, 3 Mar 2022 17:57:59 +0100 Subject: [PATCH] Now the isometric mesher's walls get properly y sorted. --- .../isometric/terrain_2d_mesher_isometric.cpp | 127 +++++++++++------- meshers/terrain_2d_mesher.cpp | 22 +++ meshers/terrain_2d_mesher.h | 1 + world/default/terrain_2d_chunk_default.cpp | 10 +- world/jobs/terrain_2d_terrain_job.cpp | 2 + 5 files changed, 114 insertions(+), 48 deletions(-) diff --git a/meshers/isometric/terrain_2d_mesher_isometric.cpp b/meshers/isometric/terrain_2d_mesher_isometric.cpp index 4272c53..b018b2d 100644 --- a/meshers/isometric/terrain_2d_mesher_isometric.cpp +++ b/meshers/isometric/terrain_2d_mesher_isometric.cpp @@ -100,15 +100,18 @@ void Terrain2DMesherIsometric::mesh_base(Ref chunk) { int margin_start = chunk->get_margin_start(); //z_size + margin_start is fine, x, and z are in data space. - for (int y = margin_start; y < y_size + margin_start; ++y) { - for (int x = margin_start; x < x_size + margin_start; ++x) { + for (int dy = margin_start; dy < y_size + margin_start; ++dy) { + for (int dx = margin_start; dx < x_size + margin_start; ++dx) { int indexes[4] = { - chunk->get_data_index(x, y), - chunk->get_data_index(x + 1, y), - chunk->get_data_index(x, y + 1), - chunk->get_data_index(x + 1, y + 1) + chunk->get_data_index(dx, dy), + chunk->get_data_index(dx + 1, dy), + chunk->get_data_index(dx, dy + 1), + chunk->get_data_index(dx + 1, dy + 1) }; + int x = dx - margin_start; + int y = dy - margin_start; + uint8_t type = channel_type[indexes[0]]; if (type == 0) @@ -387,15 +390,18 @@ void Terrain2DMesherIsometric::mesh_walls(Ref chunk) { int margin_start = chunk->get_margin_start(); //z_size + margin_start is fine, x, and z are in data space. - for (int y = margin_start; y < y_size + margin_start; ++y) { - for (int x = margin_start; x < x_size + margin_start; ++x) { + for (int dy = margin_start; dy < y_size + margin_start; ++dy) { + for (int dx = margin_start; dx < x_size + margin_start; ++dx) { int indexes[4] = { - chunk->get_data_index(x, y), - chunk->get_data_index(x + 1, y), - chunk->get_data_index(x, y + 1), - chunk->get_data_index(x + 1, y + 1) + chunk->get_data_index(dx, dy), + chunk->get_data_index(dx + 1, dy), + chunk->get_data_index(dx, dy + 1), + chunk->get_data_index(dx + 1, dy + 1) }; + int x = dx - margin_start; + int y = dy - margin_start; + uint8_t type = channel_type[indexes[0]]; if (type == 0) @@ -460,31 +466,22 @@ void Terrain2DMesherIsometric::mesh_walls(Ref chunk) { } } - Vector2 verts_normal[] = { - Vector2(0, 0), - Vector2(cell_size_x, 0), - Vector2(0, cell_size_y), - Vector2(cell_size_x, cell_size_y) - }; - - // Note that +y is down! - Vector2 verts_wall[] = { - Vector2(0, -cell_size_y), - Vector2(cell_size_x, -cell_size_y), - Vector2(0, 0), - Vector2(cell_size_x, 0) - }; - - int vc = get_vertex_count(); - if ((flags & Terrain2DChunkDefault::FLAG_CHANNEL_WALL_HOLE) != 0) { continue; } - _mesh_transform = Transform2D(0, mesh_transform_terrain.xform(Vector2(x * cell_size_x, y * cell_size_y))); - if ((flags & Terrain2DChunkDefault::FLAG_CHANNEL_WALL_NORTH) != 0) { - Vector2 vert_start_offset = mesh_transform_terrain.xform(Vector2(cell_size_x, cell_size_y)); + int vc = get_vertex_count(); + + _mesh_transform = Transform2D(0, mesh_transform_terrain.xform(Vector2((x + 1) * cell_size_x, y * cell_size_y))); + + // Note that +y is down! + Vector2 verts_wall_north[] = { + Vector2(-cell_size_x, -cell_size_y), + Vector2(0, -cell_size_y), + Vector2(-cell_size_x, 0), + Vector2(0, 0) + }; for (int i = 0; i < 4; ++i) { if (use_lighting) { @@ -494,7 +491,7 @@ void Terrain2DMesherIsometric::mesh_walls(Ref chunk) { } add_uv(uvs[i]); - add_vertex(mesh_transform_wall_north.xform(verts_wall[i]) + vert_start_offset); + add_vertex(mesh_transform_wall_north.xform(verts_wall_north[i])); } add_indices(vc + 0); @@ -504,11 +501,24 @@ void Terrain2DMesherIsometric::mesh_walls(Ref chunk) { add_indices(vc + 2); add_indices(vc + 3); - vc += 4; + if ((chunk->get_build_flags() & Terrain2DChunkDefault::BUILD_FLAG_USE_LIGHTING) != 0) { + bake_colors(chunk); + } + + store_mesh(); } if ((flags & Terrain2DChunkDefault::FLAG_CHANNEL_WALL_WEST) != 0) { - Vector2 vert_start_offset = mesh_transform_terrain.xform(Vector2(cell_size_x, cell_size_y + cell_size_y)); + int vc = get_vertex_count(); + + _mesh_transform = Transform2D(0, mesh_transform_terrain.xform(Vector2(x * cell_size_x, (y + 1) * cell_size_y))); + + Vector2 verts_wall_west[] = { + Vector2(0, -cell_size_y), + Vector2(cell_size_x, -cell_size_y), + Vector2(0, 0), + Vector2(cell_size_x, 0) + }; for (int i = 0; i < 4; ++i) { if (use_lighting) { @@ -519,7 +529,8 @@ void Terrain2DMesherIsometric::mesh_walls(Ref chunk) { add_uv(uvs[i]); - add_vertex(mesh_transform_wall_west.xform(verts_wall[i]) + vert_start_offset); + //add_vertex(mesh_transform_wall_west.xform(verts_wall[i])); + add_vertex(mesh_transform_wall_west.xform(verts_wall_west[i])); } add_indices(vc + 0); @@ -529,11 +540,24 @@ void Terrain2DMesherIsometric::mesh_walls(Ref chunk) { add_indices(vc + 2); add_indices(vc + 3); - vc += 4; + if ((chunk->get_build_flags() & Terrain2DChunkDefault::BUILD_FLAG_USE_LIGHTING) != 0) { + bake_colors(chunk); + } + + store_mesh(); } if ((flags & Terrain2DChunkDefault::FLAG_CHANNEL_WALL_SOUTH) != 0) { - Vector2 vert_start_offset = mesh_transform_terrain.xform(Vector2(cell_size_x, cell_size_y + cell_size_y)); + int vc = get_vertex_count(); + + _mesh_transform = Transform2D(0, mesh_transform_terrain.xform(Vector2((x)*cell_size_x, (y + 1) * cell_size_y))); + + Vector2 verts_wall_south[] = { + Vector2(0, -cell_size_y), + Vector2(cell_size_x, -cell_size_y), + Vector2(0, 0), + Vector2(cell_size_x, 0) + }; for (int i = 0; i < 4; ++i) { if (use_lighting) { @@ -543,7 +567,8 @@ void Terrain2DMesherIsometric::mesh_walls(Ref chunk) { } add_uv(uvs[i]); - add_vertex(mesh_transform_wall_south.xform(verts_wall[i]) + vert_start_offset); + add_vertex(mesh_transform_wall_south.xform(verts_wall_south[i])); + //add_vertex((verts_wall_south[i])); } add_indices(vc + 0); @@ -553,11 +578,24 @@ void Terrain2DMesherIsometric::mesh_walls(Ref chunk) { add_indices(vc + 2); add_indices(vc + 3); - vc += 4; + if ((chunk->get_build_flags() & Terrain2DChunkDefault::BUILD_FLAG_USE_LIGHTING) != 0) { + bake_colors(chunk); + } + + store_mesh(); } if ((flags & Terrain2DChunkDefault::FLAG_CHANNEL_WALL_EAST) != 0) { - Vector2 vert_start_offset = mesh_transform_terrain.xform(Vector2(cell_size_x + cell_size_x, cell_size_y + cell_size_y)); + int vc = get_vertex_count(); + + _mesh_transform = Transform2D(0, mesh_transform_terrain.xform(Vector2((x + 1)*cell_size_x, (y ) * cell_size_y))); + + Vector2 verts_wall_east[] = { + Vector2(-cell_size_x, -cell_size_y), + Vector2(0, -cell_size_y), + Vector2(-cell_size_x, 0), + Vector2(0, 0) + }; for (int i = 0; i < 4; ++i) { if (use_lighting) { @@ -567,7 +605,8 @@ void Terrain2DMesherIsometric::mesh_walls(Ref chunk) { } add_uv(uvs[i]); - add_vertex(mesh_transform_wall_east.xform(verts_wall[i]) + vert_start_offset); + add_vertex(mesh_transform_wall_east.xform(verts_wall_east[i])); + //add_vertex((verts_wall_east[i])); } add_indices(vc + 0); @@ -577,10 +616,6 @@ void Terrain2DMesherIsometric::mesh_walls(Ref chunk) { add_indices(vc + 2); add_indices(vc + 3); - vc += 4; - } - - if (_vertices.size() > 0) { if ((chunk->get_build_flags() & Terrain2DChunkDefault::BUILD_FLAG_USE_LIGHTING) != 0) { bake_colors(chunk); } diff --git a/meshers/terrain_2d_mesher.cpp b/meshers/terrain_2d_mesher.cpp index df9dfdc..381efd4 100644 --- a/meshers/terrain_2d_mesher.cpp +++ b/meshers/terrain_2d_mesher.cpp @@ -492,6 +492,28 @@ void Terrain2DMesher::build_stored_mesh_into(const int index, RID mesh) { VS::get_singleton()->mesh_add_surface_from_arrays(mesh, VisualServer::PRIMITIVE_TRIANGLES, arr); } +AABB Terrain2DMesher::calculate_stored_mesh_aabb(const int index) { + ERR_FAIL_INDEX_V(index, _stored_meshes.size(), AABB()); + + const Terrain2DMesherStoredMesh &md = _stored_meshes[index]; + + if (md.vertices.size() == 0) { + //Nothing to do + return AABB(); + } + + AABB aabb; + + int len = md.vertices.size(); + aabb.position = Vector3(md.vertices[0].vertex.x, md.vertices[0].vertex.y, 0); + + for (int i = 0; i < len; i++) { + aabb.expand_to(Vector3(md.vertices[i].vertex.x, md.vertices[i].vertex.y, 0)); + } + + return aabb; +} + void Terrain2DMesher::reset() { _vertices.resize(0); _indices.resize(0); diff --git a/meshers/terrain_2d_mesher.h b/meshers/terrain_2d_mesher.h index 5b61681..73f2b63 100644 --- a/meshers/terrain_2d_mesher.h +++ b/meshers/terrain_2d_mesher.h @@ -157,6 +157,7 @@ public: Array build_stored_mesh(const int index); Transform2D get_stored_mesh_transform(const int index); void build_stored_mesh_into(const int index, RID mesh); + AABB calculate_stored_mesh_aabb(const int index); PoolVector get_vertices() const; void set_vertices(const PoolVector &values); diff --git a/world/default/terrain_2d_chunk_default.cpp b/world/default/terrain_2d_chunk_default.cpp index fb6180a..5869a79 100644 --- a/world/default/terrain_2d_chunk_default.cpp +++ b/world/default/terrain_2d_chunk_default.cpp @@ -698,10 +698,16 @@ void Terrain2DChunkDefault::_draw() { if (terrain_mesh_rid != RID()) { RID terrain_texture_rid = mesh_rid_get(MESH_INDEX_TERRAIN, MESH_TYPE_INDEX_TEXTURE_RID); - VisualServer::get_singleton()->canvas_item_set_transform(get_canvas_item(i), get_transform() * _mesh_transforms[i]); - VisualServer::get_singleton()->canvas_item_clear(get_canvas_item(i)); + Transform2D t = get_transform() * _mesh_transforms[i]; + + VisualServer::get_singleton()->canvas_item_set_transform(get_canvas_item(i), t); + + //if (i != 0) { + // VisualServer::get_singleton()->canvas_item_set_custom_rect(get_canvas_item(i), true, Rect2(t.xform(Vector2()), Vector2(128, 128))); + //} + //Note: the transform parameter is not implemented in gles2 VisualServer::get_singleton()->canvas_item_add_mesh(get_canvas_item(i), terrain_mesh_rid, Transform2D(), Color(1, 1, 1, 1), terrain_texture_rid, RID()); } diff --git a/world/jobs/terrain_2d_terrain_job.cpp b/world/jobs/terrain_2d_terrain_job.cpp index 31bf9a5..4ea9073 100644 --- a/world/jobs/terrain_2d_terrain_job.cpp +++ b/world/jobs/terrain_2d_terrain_job.cpp @@ -411,6 +411,8 @@ void Terrain2DTerrain2DJob::step_type_normal() { VS::get_singleton()->mesh_add_surface_from_arrays(mesh_rid, VisualServer::PRIMITIVE_TRIANGLES, arr); chunk->_mesh_transforms.write[i + 1] = _mesher->get_stored_mesh_transform(i); + //AABB aabb = _mesher->calculate_stored_mesh_aabb(i); + //VS::get_singleton()->mesh_set_custom_aabb(mesh_rid, aabb); } }