From 289c456428a6b4138a830470499b36f78ea441ee Mon Sep 17 00:00:00 2001 From: Relintai Date: Mon, 20 Apr 2020 01:01:24 +0200 Subject: [PATCH] Now VoxelChunkDefault can create area colliders aswell, liquids are created using these in the running game. (Only there because the editor needs raycasting.) Also fixed setting liquid visibility. --- world/default/voxel_chunk_default.cpp | 49 +++++++++++++++++++++++++-- world/default/voxel_chunk_default.h | 4 ++- 2 files changed, 50 insertions(+), 3 deletions(-) diff --git a/world/default/voxel_chunk_default.cpp b/world/default/voxel_chunk_default.cpp index 3c99ca9..2cca96f 100644 --- a/world/default/voxel_chunk_default.cpp +++ b/world/default/voxel_chunk_default.cpp @@ -604,6 +604,33 @@ void VoxelChunkDefault::create_colliders(const int mesh_index, const int layer_m _rids[mesh_index] = m; } +void VoxelChunkDefault::create_colliders_area(const int mesh_index, const int layer_mask) { + ERR_FAIL_COND(_voxel_world == Variant()); + + if (!_rids.has(mesh_index)) + _rids[mesh_index] = Dictionary(); + + Dictionary m = _rids[mesh_index]; + + ERR_FAIL_COND(m.has(MESH_TYPE_INDEX_AREA)); + ERR_FAIL_COND(m.has(MESH_TYPE_INDEX_SHAPE)); + + RID shape_rid = PhysicsServer::get_singleton()->shape_create(PhysicsServer::SHAPE_CONCAVE_POLYGON); + RID area_rid = PhysicsServer::get_singleton()->area_create(); + + PhysicsServer::get_singleton()->area_set_collision_layer(area_rid, layer_mask); + PhysicsServer::get_singleton()->area_set_collision_mask(area_rid, layer_mask); + + PhysicsServer::get_singleton()->area_add_shape(area_rid, shape_rid, get_transform()); + + if (get_voxel_world()->is_inside_world()) + PhysicsServer::get_singleton()->area_set_space(area_rid, get_voxel_world()->get_world()->get_space()); + + m[MESH_TYPE_INDEX_AREA] = area_rid; + m[MESH_TYPE_INDEX_SHAPE] = shape_rid; + + _rids[mesh_index] = m; +} void VoxelChunkDefault::free_colliders(const int mesh_index) { if (!_rids.has(mesh_index)) return; @@ -662,6 +689,13 @@ void VoxelChunkDefault::update_transforms() { if (rid != empty_rid) PhysicsServer::get_singleton()->body_set_state(rid, PhysicsServer::BODY_STATE_TRANSFORM, t); } + + if (d.has(MESH_TYPE_INDEX_AREA)) { + RID rid = d[MESH_TYPE_INDEX_AREA]; + + if (rid != empty_rid) + PhysicsServer::get_singleton()->area_set_shape_transform(rid, 0, t); + } } } @@ -801,6 +835,11 @@ void VoxelChunkDefault::_visibility_changed(bool visible) { for (int i = 0; i < _lod_num + 1; ++i) { RID rid = get_mesh_rid_index(MESH_INDEX_TERRARIN, MESH_TYPE_INDEX_MESH_INSTANCE, i); + if (rid != RID()) + VisualServer::get_singleton()->instance_set_visible(rid, false); + + rid = get_mesh_rid_index(MESH_INDEX_LIQUID, MESH_TYPE_INDEX_MESH_INSTANCE, i); + if (rid != RID()) VisualServer::get_singleton()->instance_set_visible(rid, false); } @@ -1145,8 +1184,14 @@ void VoxelChunkDefault::_build_phase(int phase) { } if (temp_arr_collider_liquid.size() != 0) { - if (!has_meshes(MESH_INDEX_LIQUID, MESH_TYPE_INDEX_BODY)) { - create_colliders(MESH_INDEX_LIQUID); + if (Engine::get_singleton()->is_editor_hint()) { + if (!has_meshes(MESH_INDEX_LIQUID, MESH_TYPE_INDEX_BODY)) { + create_colliders(MESH_INDEX_LIQUID); + } + } else { + if (!has_meshes(MESH_INDEX_LIQUID, MESH_TYPE_INDEX_AREA)) { + create_colliders_area(MESH_INDEX_LIQUID); + } } PhysicsServer::get_singleton()->shape_set_data(get_mesh_rid(MESH_INDEX_LIQUID, MESH_TYPE_INDEX_SHAPE), temp_arr_collider_liquid); diff --git a/world/default/voxel_chunk_default.h b/world/default/voxel_chunk_default.h index c7e53fe..1a97fb2 100644 --- a/world/default/voxel_chunk_default.h +++ b/world/default/voxel_chunk_default.h @@ -116,7 +116,8 @@ public: MESH_TYPE_INDEX_MESH = 0, MESH_TYPE_INDEX_MESH_INSTANCE, MESH_TYPE_INDEX_SHAPE, - MESH_TYPE_INDEX_BODY + MESH_TYPE_INDEX_BODY, + MESH_TYPE_INDEX_AREA, }; enum BuildFlags { @@ -197,6 +198,7 @@ public: void free_meshes(const int mesh_index); void create_colliders(const int mesh_index, const int layer_mask = 1); + void create_colliders_area(const int mesh_index, const int layer_mask = 1); void free_colliders(const int mesh_index); //Transform