diff options
Diffstat (limited to 'scene/3d')
-rw-r--r-- | scene/3d/arvr_nodes.cpp | 3 | ||||
-rw-r--r-- | scene/3d/audio_stream_player_3d.h | 2 | ||||
-rw-r--r-- | scene/3d/baked_lightmap.cpp | 20 | ||||
-rw-r--r-- | scene/3d/baked_lightmap.h | 4 | ||||
-rw-r--r-- | scene/3d/collision_object.cpp | 2 | ||||
-rw-r--r-- | scene/3d/collision_shape.cpp | 2 | ||||
-rw-r--r-- | scene/3d/cpu_particles.cpp | 28 | ||||
-rw-r--r-- | scene/3d/cpu_particles.h | 4 | ||||
-rw-r--r-- | scene/3d/gi_probe.cpp | 1 | ||||
-rw-r--r-- | scene/3d/light.cpp | 19 | ||||
-rw-r--r-- | scene/3d/light.h | 2 | ||||
-rw-r--r-- | scene/3d/navigation.cpp | 1 | ||||
-rw-r--r-- | scene/3d/particles.cpp | 3 | ||||
-rw-r--r-- | scene/3d/path.cpp | 2 | ||||
-rw-r--r-- | scene/3d/physics_body.cpp | 4 | ||||
-rw-r--r-- | scene/3d/remote_transform.cpp | 9 | ||||
-rw-r--r-- | scene/3d/remote_transform.h | 2 | ||||
-rw-r--r-- | scene/3d/soft_body.cpp | 3 | ||||
-rw-r--r-- | scene/3d/spatial.cpp | 2 | ||||
-rw-r--r-- | scene/3d/sprite_3d.cpp | 4 | ||||
-rw-r--r-- | scene/3d/visual_instance.cpp | 2 | ||||
-rw-r--r-- | scene/3d/voxel_light_baker.cpp | 75 | ||||
-rw-r--r-- | scene/3d/voxel_light_baker.h | 2 | ||||
-rw-r--r-- | scene/3d/world_environment.cpp | 2 |
24 files changed, 167 insertions, 31 deletions
diff --git a/scene/3d/arvr_nodes.cpp b/scene/3d/arvr_nodes.cpp index 95eec41fb2..263a2d8de6 100644 --- a/scene/3d/arvr_nodes.cpp +++ b/scene/3d/arvr_nodes.cpp @@ -61,7 +61,7 @@ String ARVRCamera::get_configuration_warning() const { // must be child node of ARVROrigin! ARVROrigin *origin = Object::cast_to<ARVROrigin>(get_parent()); if (origin == NULL) { - return TTR("ARVRCamera must have an ARVROrigin node as its parent"); + return TTR("ARVRCamera must have an ARVROrigin node as its parent."); }; return String(); @@ -264,6 +264,7 @@ void ARVRController::_bind_methods() { ClassDB::bind_method(D_METHOD("get_rumble"), &ARVRController::get_rumble); ClassDB::bind_method(D_METHOD("set_rumble", "rumble"), &ARVRController::set_rumble); ADD_PROPERTY(PropertyInfo(Variant::REAL, "rumble", PROPERTY_HINT_RANGE, "0.0,1.0,0.01"), "set_rumble", "get_rumble"); + ADD_PROPERTY_DEFAULT("rumble", 0.0); ClassDB::bind_method(D_METHOD("get_mesh"), &ARVRController::get_mesh); diff --git a/scene/3d/audio_stream_player_3d.h b/scene/3d/audio_stream_player_3d.h index 7a652ed65f..93954e758a 100644 --- a/scene/3d/audio_stream_player_3d.h +++ b/scene/3d/audio_stream_player_3d.h @@ -71,7 +71,7 @@ private: struct Output { AudioFilterSW filter; - AudioFilterSW::Processor filter_process[6]; + AudioFilterSW::Processor filter_process[8]; AudioFrame vol[4]; float filter_gain; float pitch_scale; diff --git a/scene/3d/baked_lightmap.cpp b/scene/3d/baked_lightmap.cpp index 2b12e78158..c5ff4dadbc 100644 --- a/scene/3d/baked_lightmap.cpp +++ b/scene/3d/baked_lightmap.cpp @@ -221,6 +221,15 @@ Vector3 BakedLightmap::get_extents() const { return extents; } +void BakedLightmap::set_bake_default_texels_per_unit(const float &p_bake_texels_per_unit) { + bake_default_texels_per_unit = p_bake_texels_per_unit; + update_gizmo(); +} + +float BakedLightmap::get_bake_default_texels_per_unit() const { + return bake_default_texels_per_unit; +} + void BakedLightmap::_find_meshes_and_lights(Node *p_at_node, List<PlotMesh> &plot_meshes, List<PlotLight> &plot_lights) { MeshInstance *mi = Object::cast_to<MeshInstance>(p_at_node); @@ -236,7 +245,7 @@ void BakedLightmap::_find_meshes_and_lights(Node *p_at_node, List<PlotMesh> &plo } } - if (all_have_uv2 && mesh->get_lightmap_size_hint() != Size2()) { + if (all_have_uv2) { //READY TO BAKE! size hint could be computed if not found, actually.. AABB aabb = mesh->get_aabb(); @@ -463,7 +472,7 @@ BakedLightmap::BakeError BakedLightmap::bake(Node *p_from_node, bool p_create_vi btd.text = RTR("Lighting Meshes: ") + mesh_name + " (" + itos(pmc) + "/" + itos(mesh_list.size()) + ")"; btd.pass = step; btd.last_step = 0; - err = baker.make_lightmap(E->get().local_xform, E->get().mesh, lm, _bake_time, &btd); + err = baker.make_lightmap(E->get().local_xform, E->get().mesh, bake_default_texels_per_unit, lm, _bake_time, &btd); if (err != OK) { bake_end_function(); if (err == ERR_SKIP) @@ -473,7 +482,7 @@ BakedLightmap::BakeError BakedLightmap::bake(Node *p_from_node, bool p_create_vi step += 100; } else { - err = baker.make_lightmap(E->get().local_xform, E->get().mesh, lm); + err = baker.make_lightmap(E->get().local_xform, E->get().mesh, bake_default_texels_per_unit, lm); } if (err == OK) { @@ -790,6 +799,9 @@ void BakedLightmap::_bind_methods() { ClassDB::bind_method(D_METHOD("set_extents", "extents"), &BakedLightmap::set_extents); ClassDB::bind_method(D_METHOD("get_extents"), &BakedLightmap::get_extents); + ClassDB::bind_method(D_METHOD("set_bake_default_texels_per_unit", "texels"), &BakedLightmap::set_bake_default_texels_per_unit); + ClassDB::bind_method(D_METHOD("get_bake_default_texels_per_unit"), &BakedLightmap::get_bake_default_texels_per_unit); + ClassDB::bind_method(D_METHOD("set_propagation", "propagation"), &BakedLightmap::set_propagation); ClassDB::bind_method(D_METHOD("get_propagation"), &BakedLightmap::get_propagation); @@ -814,6 +826,7 @@ void BakedLightmap::_bind_methods() { ADD_PROPERTY(PropertyInfo(Variant::REAL, "bake_energy", PROPERTY_HINT_RANGE, "0,32,0.01"), "set_energy", "get_energy"); ADD_PROPERTY(PropertyInfo(Variant::BOOL, "bake_hdr"), "set_hdr", "is_hdr"); ADD_PROPERTY(PropertyInfo(Variant::VECTOR3, "bake_extents"), "set_extents", "get_extents"); + ADD_PROPERTY(PropertyInfo(Variant::REAL, "bake_default_texels_per_unit"), "set_bake_default_texels_per_unit", "get_bake_default_texels_per_unit"); ADD_GROUP("Capture", "capture_"); ADD_PROPERTY(PropertyInfo(Variant::REAL, "capture_cell_size", PROPERTY_HINT_RANGE, "0.01,64,0.01"), "set_capture_cell_size", "get_capture_cell_size"); ADD_GROUP("Data", ""); @@ -836,6 +849,7 @@ void BakedLightmap::_bind_methods() { BakedLightmap::BakedLightmap() { extents = Vector3(10, 10, 10); + bake_default_texels_per_unit = 20; bake_cell_size = 0.25; capture_cell_size = 0.5; diff --git a/scene/3d/baked_lightmap.h b/scene/3d/baked_lightmap.h index bb3f84719a..3a9f4cf01d 100644 --- a/scene/3d/baked_lightmap.h +++ b/scene/3d/baked_lightmap.h @@ -119,6 +119,7 @@ private: float bake_cell_size; float capture_cell_size; Vector3 extents; + float bake_default_texels_per_unit; float propagation; float energy; BakeQuality bake_quality; @@ -178,6 +179,9 @@ public: void set_extents(const Vector3 &p_extents); Vector3 get_extents() const; + void set_bake_default_texels_per_unit(const float &p_bake_texels_per_unit); + float get_bake_default_texels_per_unit() const; + void set_propagation(float p_propagation); float get_propagation() const; diff --git a/scene/3d/collision_object.cpp b/scene/3d/collision_object.cpp index fc46cf5bdb..9d3e2983c4 100644 --- a/scene/3d/collision_object.cpp +++ b/scene/3d/collision_object.cpp @@ -371,7 +371,7 @@ String CollisionObject::get_configuration_warning() const { if (shapes.empty()) { if (warning == String()) { - warning += "\n"; + warning += "\n\n"; } warning += TTR("This node has no shape, so it can't collide or interact with other objects.\nConsider adding a CollisionShape or CollisionPolygon as a child to define its shape."); } diff --git a/scene/3d/collision_shape.cpp b/scene/3d/collision_shape.cpp index 219ea56681..2b030641eb 100644 --- a/scene/3d/collision_shape.cpp +++ b/scene/3d/collision_shape.cpp @@ -120,7 +120,7 @@ String CollisionShape::get_configuration_warning() const { } if (!shape.is_valid()) { - return TTR("A shape must be provided for CollisionShape to function. Please create a shape resource for it!"); + return TTR("A shape must be provided for CollisionShape to function. Please create a shape resource for it."); } if (shape->is_class("PlaneShape")) { diff --git a/scene/3d/cpu_particles.cpp b/scene/3d/cpu_particles.cpp index 6ede9c10ef..86b407b9e6 100644 --- a/scene/3d/cpu_particles.cpp +++ b/scene/3d/cpu_particles.cpp @@ -237,6 +237,16 @@ void CPUParticles::restart() { } } +void CPUParticles::set_direction(Vector3 p_direction) { + + direction = p_direction; +} + +Vector3 CPUParticles::get_direction() const { + + return direction; +} + void CPUParticles::set_spread(float p_spread) { spread = p_spread; @@ -604,13 +614,13 @@ void CPUParticles::_particles_process(float p_delta) { p.anim_offset_rand = Math::randf(); if (flags[FLAG_DISABLE_Z]) { - float angle1_rad = (Math::randf() * 2.0 - 1.0) * Math_PI * spread / 180.0; + float angle1_rad = Math::atan2(direction.y, direction.x) + (Math::randf() * 2.0 - 1.0) * Math_PI * spread / 180.0; Vector3 rot = Vector3(Math::cos(angle1_rad), Math::sin(angle1_rad), 0.0); p.velocity = rot * parameters[PARAM_INITIAL_LINEAR_VELOCITY] * Math::lerp(1.0f, float(Math::randf()), randomness[PARAM_INITIAL_LINEAR_VELOCITY]); } else { //initiate velocity spread in 3D - float angle1_rad = (Math::randf() * 2.0 - 1.0) * Math_PI * spread / 180.0; - float angle2_rad = (Math::randf() * 2.0 - 1.0) * (1.0 - flatness) * Math_PI * spread / 180.0; + float angle1_rad = Math::atan2(direction.x, direction.z) + (Math::randf() * 2.0 - 1.0) * Math_PI * spread / 180.0; + float angle2_rad = Math::atan2(direction.y, Math::abs(direction.z)) + (Math::randf() * 2.0 - 1.0) * (1.0 - flatness) * Math_PI * spread / 180.0; Vector3 direction_xz = Vector3(Math::sin(angle1_rad), 0, Math::cos(angle1_rad)); Vector3 direction_yz = Vector3(0, Math::sin(angle2_rad), Math::cos(angle2_rad)); @@ -633,7 +643,9 @@ void CPUParticles::_particles_process(float p_delta) { //do none } break; case EMISSION_SHAPE_SPHERE: { - p.transform.origin = Vector3(Math::randf() * 2.0 - 1.0, Math::randf() * 2.0 - 1.0, Math::randf() * 2.0 - 1.0).normalized() * emission_sphere_radius; + float s = 2.0 * Math::randf() - 1.0, t = 2.0 * Math_PI * Math::randf(); + float radius = emission_sphere_radius * Math::sqrt(1.0 - s * s); + p.transform.origin = Vector3(radius * Math::cos(t), radius * Math::sin(t), emission_sphere_radius * s); } break; case EMISSION_SHAPE_BOX: { p.transform.origin = Vector3(Math::randf() * 2.0 - 1.0, Math::randf() * 2.0 - 1.0, Math::randf() * 2.0 - 1.0) * emission_box_extents; @@ -1189,6 +1201,7 @@ void CPUParticles::convert_from_particles(Node *p_particles) { if (material.is_null()) return; + set_direction(material->get_direction()); set_spread(material->get_spread()); set_flatness(material->get_flatness()); @@ -1290,6 +1303,9 @@ void CPUParticles::_bind_methods() { //////////////////////////////// + ClassDB::bind_method(D_METHOD("set_direction", "direction"), &CPUParticles::set_direction); + ClassDB::bind_method(D_METHOD("get_direction"), &CPUParticles::get_direction); + ClassDB::bind_method(D_METHOD("set_spread", "degrees"), &CPUParticles::set_spread); ClassDB::bind_method(D_METHOD("get_spread"), &CPUParticles::get_spread); @@ -1350,7 +1366,8 @@ void CPUParticles::_bind_methods() { ADD_PROPERTYI(PropertyInfo(Variant::BOOL, "flag_align_y"), "set_particle_flag", "get_particle_flag", FLAG_ALIGN_Y_TO_VELOCITY); ADD_PROPERTYI(PropertyInfo(Variant::BOOL, "flag_rotate_y"), "set_particle_flag", "get_particle_flag", FLAG_ROTATE_Y); ADD_PROPERTYI(PropertyInfo(Variant::BOOL, "flag_disable_z"), "set_particle_flag", "get_particle_flag", FLAG_DISABLE_Z); - ADD_GROUP("Spread", ""); + ADD_GROUP("Direction", ""); + ADD_PROPERTY(PropertyInfo(Variant::VECTOR3, "direction"), "set_direction", "get_direction"); ADD_PROPERTY(PropertyInfo(Variant::REAL, "spread", PROPERTY_HINT_RANGE, "0,180,0.01"), "set_spread", "get_spread"); ADD_PROPERTY(PropertyInfo(Variant::REAL, "flatness", PROPERTY_HINT_RANGE, "0,1,0.01"), "set_flatness", "get_flatness"); ADD_GROUP("Gravity", ""); @@ -1460,6 +1477,7 @@ CPUParticles::CPUParticles() { set_draw_order(DRAW_ORDER_INDEX); set_speed_scale(1); + set_direction(Vector3(1, 0, 0)); set_spread(45); set_flatness(0); set_param(PARAM_INITIAL_LINEAR_VELOCITY, 0); diff --git a/scene/3d/cpu_particles.h b/scene/3d/cpu_particles.h index 6566792def..517df8490d 100644 --- a/scene/3d/cpu_particles.h +++ b/scene/3d/cpu_particles.h @@ -152,6 +152,7 @@ private: //////// + Vector3 direction; float spread; float flatness; @@ -231,6 +232,9 @@ public: /////////////////// + void set_direction(Vector3 p_direction); + Vector3 get_direction() const; + void set_spread(float p_spread); float get_spread() const; diff --git a/scene/3d/gi_probe.cpp b/scene/3d/gi_probe.cpp index 414e932f61..a04f156d80 100644 --- a/scene/3d/gi_probe.cpp +++ b/scene/3d/gi_probe.cpp @@ -571,4 +571,5 @@ GIProbe::GIProbe() { } GIProbe::~GIProbe() { + VS::get_singleton()->free(gi_probe); } diff --git a/scene/3d/light.cpp b/scene/3d/light.cpp index 2e64872616..4ef945ab8d 100644 --- a/scene/3d/light.cpp +++ b/scene/3d/light.cpp @@ -51,6 +51,7 @@ void Light::set_param(Param p_param, float p_value) { if (p_param == PARAM_SPOT_ANGLE) { _change_notify("spot_angle"); + update_configuration_warning(); } else if (p_param == PARAM_RANGE) { _change_notify("omni_range"); _change_notify("spot_range"); @@ -68,6 +69,10 @@ void Light::set_shadow(bool p_enable) { shadow = p_enable; VS::get_singleton()->light_set_shadow(light, p_enable); + + if (type == VisualServer::LIGHT_SPOT) { + update_configuration_warning(); + } } bool Light::has_shadow() const { @@ -465,6 +470,20 @@ OmniLight::OmniLight() : set_shadow_detail(SHADOW_DETAIL_HORIZONTAL); } +String SpotLight::get_configuration_warning() const { + String warning = Light::get_configuration_warning(); + + if (has_shadow() && get_param(PARAM_SPOT_ANGLE) >= 90.0) { + if (warning != String()) { + warning += "\n\n"; + } + + warning += TTR("A SpotLight with an angle wider than 90 degrees cannot cast shadows."); + } + + return warning; +} + void SpotLight::_bind_methods() { ADD_GROUP("Spot", "spot_"); diff --git a/scene/3d/light.h b/scene/3d/light.h index ddd5bc6b3a..5d365758b5 100644 --- a/scene/3d/light.h +++ b/scene/3d/light.h @@ -221,6 +221,8 @@ protected: static void _bind_methods(); public: + virtual String get_configuration_warning() const; + SpotLight() : Light(VisualServer::LIGHT_SPOT) {} }; diff --git a/scene/3d/navigation.cpp b/scene/3d/navigation.cpp index 612d91c6e1..12d562c0c6 100644 --- a/scene/3d/navigation.cpp +++ b/scene/3d/navigation.cpp @@ -90,7 +90,6 @@ void Navigation::_navmesh_link(int p_id) { if (!valid) { nm.polygons.pop_back(); ERR_CONTINUE(!valid); - continue; } p.center = center; diff --git a/scene/3d/particles.cpp b/scene/3d/particles.cpp index 2bcd0eaa46..a6ccdb5791 100644 --- a/scene/3d/particles.cpp +++ b/scene/3d/particles.cpp @@ -257,7 +257,7 @@ String Particles::get_configuration_warning() const { SpatialMaterial *spat = Object::cast_to<SpatialMaterial>(draw_passes[i]->surface_get_material(j).ptr()); anim_material_found = anim_material_found || (spat && spat->get_billboard_mode() == SpatialMaterial::BILLBOARD_PARTICLES); } - if (meshes_found && anim_material_found) break; + if (anim_material_found) break; } } @@ -411,6 +411,7 @@ Particles::Particles() { particles = VS::get_singleton()->particles_create(); set_base(particles); + one_shot = false; // Needed so that set_emitting doesn't access uninitialized values set_emitting(true); set_one_shot(false); set_amount(8); diff --git a/scene/3d/path.cpp b/scene/3d/path.cpp index 84078911cb..d55c795d38 100644 --- a/scene/3d/path.cpp +++ b/scene/3d/path.cpp @@ -270,7 +270,7 @@ String PathFollow::get_configuration_warning() const { } else { Path *path = Object::cast_to<Path>(get_parent()); if (path->get_curve().is_valid() && !path->get_curve()->is_up_vector_enabled() && rotation_mode == ROTATION_ORIENTED) { - return TTR("PathFollow ROTATION_ORIENTED requires \"Up Vector\" enabled in its parent Path's Curve resource."); + return TTR("PathFollow's ROTATION_ORIENTED requires \"Up Vector\" to be enabled in its parent Path's Curve resource."); } } diff --git a/scene/3d/physics_body.cpp b/scene/3d/physics_body.cpp index 3624e04434..2f8b2ecc5c 100644 --- a/scene/3d/physics_body.cpp +++ b/scene/3d/physics_body.cpp @@ -934,7 +934,7 @@ String RigidBody::get_configuration_warning() const { if ((get_mode() == MODE_RIGID || get_mode() == MODE_CHARACTER) && (ABS(t.basis.get_axis(0).length() - 1.0) > 0.05 || ABS(t.basis.get_axis(1).length() - 1.0) > 0.05 || ABS(t.basis.get_axis(2).length() - 1.0) > 0.05)) { if (warning != String()) { - warning += "\n"; + warning += "\n\n"; } warning += TTR("Size changes to RigidBody (in character or rigid modes) will be overridden by the physics engine when running.\nChange the size in children collision shapes instead."); } @@ -1470,7 +1470,7 @@ Vector3 KinematicCollision::get_remainder() const { return collision.remainder; } Object *KinematicCollision::get_local_shape() const { - ERR_FAIL_COND_V(!owner, NULL); + if (!owner) return NULL; uint32_t ownerid = owner->shape_find_owner(collision.local_shape); return owner->shape_owner_get_owner(ownerid); } diff --git a/scene/3d/remote_transform.cpp b/scene/3d/remote_transform.cpp index add77e0272..76b0b0c92f 100644 --- a/scene/3d/remote_transform.cpp +++ b/scene/3d/remote_transform.cpp @@ -105,7 +105,7 @@ void RemoteTransform::_notification(int p_what) { switch (p_what) { - case NOTIFICATION_READY: { + case NOTIFICATION_ENTER_TREE: { _update_cache(); @@ -174,10 +174,14 @@ bool RemoteTransform::get_update_scale() const { return update_remote_scale; } +void RemoteTransform::force_update_cache() { + _update_cache(); +} + String RemoteTransform::get_configuration_warning() const { if (!has_node(remote_node) || !Object::cast_to<Spatial>(get_node(remote_node))) { - return TTR("Path property must point to a valid Spatial node to work."); + return TTR("The \"Remote Path\" property must point to a valid Spatial or Spatial-derived node to work."); } return String(); @@ -187,6 +191,7 @@ void RemoteTransform::_bind_methods() { ClassDB::bind_method(D_METHOD("set_remote_node", "path"), &RemoteTransform::set_remote_node); ClassDB::bind_method(D_METHOD("get_remote_node"), &RemoteTransform::get_remote_node); + ClassDB::bind_method(D_METHOD("force_update_cache"), &RemoteTransform::force_update_cache); ClassDB::bind_method(D_METHOD("set_use_global_coordinates", "use_global_coordinates"), &RemoteTransform::set_use_global_coordinates); ClassDB::bind_method(D_METHOD("get_use_global_coordinates"), &RemoteTransform::get_use_global_coordinates); diff --git a/scene/3d/remote_transform.h b/scene/3d/remote_transform.h index b737a4f858..07e01284e5 100644 --- a/scene/3d/remote_transform.h +++ b/scene/3d/remote_transform.h @@ -68,6 +68,8 @@ public: void set_update_scale(const bool p_update); bool get_update_scale() const; + void force_update_cache(); + virtual String get_configuration_warning() const; RemoteTransform(); diff --git a/scene/3d/soft_body.cpp b/scene/3d/soft_body.cpp index a9d96292a1..386e127f8b 100644 --- a/scene/3d/soft_body.cpp +++ b/scene/3d/soft_body.cpp @@ -73,7 +73,7 @@ void SoftBodyVisualServerHandler::open() { } void SoftBodyVisualServerHandler::close() { - write_buffer = PoolVector<uint8_t>::Write(); + write_buffer.release(); } void SoftBodyVisualServerHandler::commit_changes() { @@ -712,6 +712,7 @@ SoftBody::SoftBody() : } SoftBody::~SoftBody() { + PhysicsServer::get_singleton()->free(physics_rid); } void SoftBody::reset_softbody_pin() { diff --git a/scene/3d/spatial.cpp b/scene/3d/spatial.cpp index efd418e3c7..1a41a31253 100644 --- a/scene/3d/spatial.cpp +++ b/scene/3d/spatial.cpp @@ -506,6 +506,8 @@ bool Spatial::is_set_as_toplevel() const { Ref<World> Spatial::get_world() const { ERR_FAIL_COND_V(!is_inside_world(), Ref<World>()); + ERR_FAIL_COND_V(!data.viewport, Ref<World>()); + return data.viewport->find_world(); } diff --git a/scene/3d/sprite_3d.cpp b/scene/3d/sprite_3d.cpp index 9f73484b6a..67c79d8b5a 100644 --- a/scene/3d/sprite_3d.cpp +++ b/scene/3d/sprite_3d.cpp @@ -254,7 +254,7 @@ Ref<TriangleMesh> SpriteBase3D::generate_triangle_mesh() const { facesw[j] = vtx; } - facesw = PoolVector<Vector3>::Write(); + facesw.release(); triangle_mesh = Ref<TriangleMesh>(memnew(TriangleMesh)); triangle_mesh->create(faces); @@ -1061,7 +1061,7 @@ StringName AnimatedSprite3D::get_animation() const { String AnimatedSprite3D::get_configuration_warning() const { if (frames.is_null()) { - return TTR("A SpriteFrames resource must be created or set in the 'Frames' property in order for AnimatedSprite3D to display frames."); + return TTR("A SpriteFrames resource must be created or set in the \"Frames\" property in order for AnimatedSprite3D to display frames."); } return String(); diff --git a/scene/3d/visual_instance.cpp b/scene/3d/visual_instance.cpp index 4bb4d18071..5141c84803 100644 --- a/scene/3d/visual_instance.cpp +++ b/scene/3d/visual_instance.cpp @@ -60,7 +60,7 @@ void VisualInstance::_notification(int p_what) { if (skeleton) VisualServer::get_singleton()->instance_attach_skeleton( instance, skeleton->get_skeleton() ); */ - + ERR_FAIL_COND(get_world().is_null()); VisualServer::get_singleton()->instance_set_scenario(instance, get_world()->get_scenario()); _update_visibility(); diff --git a/scene/3d/voxel_light_baker.cpp b/scene/3d/voxel_light_baker.cpp index 5fa8c43f9f..8e09930aed 100644 --- a/scene/3d/voxel_light_baker.cpp +++ b/scene/3d/voxel_light_baker.cpp @@ -1792,19 +1792,82 @@ void VoxelLightBaker::_lightmap_bake_point(uint32_t p_x, LightMap *p_line) { } } -Error VoxelLightBaker::make_lightmap(const Transform &p_xform, Ref<Mesh> &p_mesh, LightMapData &r_lightmap, bool (*p_bake_time_func)(void *, float, float), void *p_bake_time_ud) { +Error VoxelLightBaker::make_lightmap(const Transform &p_xform, Ref<Mesh> &p_mesh, float default_texels_per_unit, LightMapData &r_lightmap, bool (*p_bake_time_func)(void *, float, float), void *p_bake_time_ud) { //transfer light information to a lightmap Ref<Mesh> mesh = p_mesh; - int width = mesh->get_lightmap_size_hint().x; - int height = mesh->get_lightmap_size_hint().y; - //step 1 - create lightmap + int width; + int height; Vector<LightMap> lightmap; - lightmap.resize(width * height); - Transform xform = to_cell_space * p_xform; + if (mesh->get_lightmap_size_hint() == Size2()) { + double area = 0; + double uv_area = 0; + for (int i = 0; i < mesh->get_surface_count(); i++) { + Array arrays = mesh->surface_get_arrays(i); + PoolVector<Vector3> vertices = arrays[Mesh::ARRAY_VERTEX]; + PoolVector<Vector2> uv2 = arrays[Mesh::ARRAY_TEX_UV2]; + PoolVector<int> indices = arrays[Mesh::ARRAY_INDEX]; + + ERR_FAIL_COND_V(vertices.size() == 0, ERR_INVALID_PARAMETER); + ERR_FAIL_COND_V(uv2.size() == 0, ERR_INVALID_PARAMETER); + + int vc = vertices.size(); + PoolVector<Vector3>::Read vr = vertices.read(); + PoolVector<Vector2>::Read u2r = uv2.read(); + PoolVector<int>::Read ir; + int ic = 0; + + if (indices.size()) { + ic = indices.size(); + ir = indices.read(); + } + + int faces = ic ? ic / 3 : vc / 3; + for (int j = 0; j < faces; j++) { + Vector3 vertex[3]; + Vector2 uv[3]; + + for (int k = 0; k < 3; k++) { + int idx = ic ? ir[j * 3 + k] : j * 3 + k; + vertex[k] = xform.xform(vr[idx]); + uv[k] = u2r[idx]; + } + + Vector3 p1 = vertex[0]; + Vector3 p2 = vertex[1]; + Vector3 p3 = vertex[2]; + double a = p1.distance_to(p2); + double b = p2.distance_to(p3); + double c = p3.distance_to(p1); + double halfPerimeter = (a + b + c) / 2.0; + area += sqrt(halfPerimeter * (halfPerimeter - a) * (halfPerimeter - b) * (halfPerimeter - c)); + + Vector2 uv_p1 = uv[0]; + Vector2 uv_p2 = uv[1]; + Vector2 uv_p3 = uv[2]; + double uv_a = uv_p1.distance_to(uv_p2); + double uv_b = uv_p2.distance_to(uv_p3); + double uv_c = uv_p3.distance_to(uv_p1); + double uv_halfPerimeter = (uv_a + uv_b + uv_c) / 2.0; + uv_area += sqrt(uv_halfPerimeter * (uv_halfPerimeter - uv_a) * (uv_halfPerimeter - uv_b) * (uv_halfPerimeter - uv_c)); + } + } + + if (uv_area < 0.0001f) { + uv_area = 1.0; + } + + int pixels = (ceil((1.0 / sqrt(uv_area)) * sqrt(area * default_texels_per_unit))); + width = height = CLAMP(pixels, 2, 4096); + } else { + width = mesh->get_lightmap_size_hint().x; + height = mesh->get_lightmap_size_hint().y; + } + + lightmap.resize(width * height); //step 2 plot faces to lightmap for (int i = 0; i < mesh->get_surface_count(); i++) { diff --git a/scene/3d/voxel_light_baker.h b/scene/3d/voxel_light_baker.h index 295e099d47..2e2efc62ff 100644 --- a/scene/3d/voxel_light_baker.h +++ b/scene/3d/voxel_light_baker.h @@ -177,7 +177,7 @@ public: PoolVector<float> light; }; - Error make_lightmap(const Transform &p_xform, Ref<Mesh> &p_mesh, LightMapData &r_lightmap, bool (*p_bake_time_func)(void *, float, float) = NULL, void *p_bake_time_ud = NULL); + Error make_lightmap(const Transform &p_xform, Ref<Mesh> &p_mesh, float default_texels_per_unit, LightMapData &r_lightmap, bool (*p_bake_time_func)(void *, float, float) = NULL, void *p_bake_time_ud = NULL); PoolVector<int> create_gi_probe_data(); Ref<MultiMesh> create_debug_multimesh(DebugMode p_mode = DEBUG_ALBEDO); diff --git a/scene/3d/world_environment.cpp b/scene/3d/world_environment.cpp index 3cd43cbf5b..8d46b4161d 100644 --- a/scene/3d/world_environment.cpp +++ b/scene/3d/world_environment.cpp @@ -80,7 +80,7 @@ Ref<Environment> WorldEnvironment::get_environment() const { String WorldEnvironment::get_configuration_warning() const { if (!environment.is_valid()) { - return TTR("WorldEnvironment needs an Environment resource."); + return TTR("WorldEnvironment requires its \"Environment\" property to contain an Environment to have a visible effect."); } if (/*!is_visible_in_tree() ||*/ !is_inside_tree()) |