summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--doc/classes/CPUParticles2D.xml11
-rw-r--r--doc/classes/CPUParticles3D.xml13
-rw-r--r--doc/classes/ParticlesMaterial.xml13
-rw-r--r--scene/2d/cpu_particles_2d.cpp10
-rw-r--r--scene/2d/cpu_particles_2d.h1
-rw-r--r--scene/3d/cpu_particles_3d.cpp12
-rw-r--r--scene/3d/cpu_particles_3d.h1
-rw-r--r--scene/resources/particles_material.cpp15
-rw-r--r--scene/resources/particles_material.h1
9 files changed, 57 insertions, 20 deletions
diff --git a/doc/classes/CPUParticles2D.xml b/doc/classes/CPUParticles2D.xml
index 4a7ffe1536..dacdca1cee 100644
--- a/doc/classes/CPUParticles2D.xml
+++ b/doc/classes/CPUParticles2D.xml
@@ -313,18 +313,21 @@
All particles will be emitted from a single point.
</constant>
<constant name="EMISSION_SHAPE_SPHERE" value="1" enum="EmissionShape">
+ Particles will be emitted in the volume of a sphere flattened to two dimensions.
+ </constant>
+ <constant name="EMISSION_SHAPE_SPHERE_SURFACE" value="2" enum="EmissionShape">
Particles will be emitted on the surface of a sphere flattened to two dimensions.
</constant>
- <constant name="EMISSION_SHAPE_RECTANGLE" value="2" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_RECTANGLE" value="3" enum="EmissionShape">
Particles will be emitted in the area of a rectangle.
</constant>
- <constant name="EMISSION_SHAPE_POINTS" value="3" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_POINTS" value="4" enum="EmissionShape">
Particles will be emitted at a position chosen randomly among [member emission_points]. Particle color will be modulated by [member emission_colors].
</constant>
- <constant name="EMISSION_SHAPE_DIRECTED_POINTS" value="4" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_DIRECTED_POINTS" value="5" enum="EmissionShape">
Particles will be emitted at a position chosen randomly among [member emission_points]. Particle velocity and rotation will be set based on [member emission_normals]. Particle color will be modulated by [member emission_colors].
</constant>
- <constant name="EMISSION_SHAPE_MAX" value="5" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_MAX" value="6" enum="EmissionShape">
Represents the size of the [enum EmissionShape] enum.
</constant>
</constants>
diff --git a/doc/classes/CPUParticles3D.xml b/doc/classes/CPUParticles3D.xml
index 7152f67f48..f2a0040ed4 100644
--- a/doc/classes/CPUParticles3D.xml
+++ b/doc/classes/CPUParticles3D.xml
@@ -370,19 +370,22 @@
<constant name="EMISSION_SHAPE_SPHERE" value="1" enum="EmissionShape">
Particles will be emitted in the volume of a sphere.
</constant>
- <constant name="EMISSION_SHAPE_BOX" value="2" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_SPHERE_SURFACE" value="2" enum="EmissionShape">
+ Particles will be emitted on the surface of a sphere.
+ </constant>
+ <constant name="EMISSION_SHAPE_BOX" value="3" enum="EmissionShape">
Particles will be emitted in the volume of a box.
</constant>
- <constant name="EMISSION_SHAPE_POINTS" value="3" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_POINTS" value="4" enum="EmissionShape">
Particles will be emitted at a position chosen randomly among [member emission_points]. Particle color will be modulated by [member emission_colors].
</constant>
- <constant name="EMISSION_SHAPE_DIRECTED_POINTS" value="4" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_DIRECTED_POINTS" value="5" enum="EmissionShape">
Particles will be emitted at a position chosen randomly among [member emission_points]. Particle velocity and rotation will be set based on [member emission_normals]. Particle color will be modulated by [member emission_colors].
</constant>
- <constant name="EMISSION_SHAPE_RING" value="5" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_RING" value="6" enum="EmissionShape">
Particles will be emitted in a ring or cylinder.
</constant>
- <constant name="EMISSION_SHAPE_MAX" value="6" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_MAX" value="7" enum="EmissionShape">
Represents the size of the [enum EmissionShape] enum.
</constant>
</constants>
diff --git a/doc/classes/ParticlesMaterial.xml b/doc/classes/ParticlesMaterial.xml
index e05853e816..885bedbc04 100644
--- a/doc/classes/ParticlesMaterial.xml
+++ b/doc/classes/ParticlesMaterial.xml
@@ -325,19 +325,22 @@
<constant name="EMISSION_SHAPE_SPHERE" value="1" enum="EmissionShape">
Particles will be emitted in the volume of a sphere.
</constant>
- <constant name="EMISSION_SHAPE_BOX" value="2" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_SPHERE_SURFACE" value="2" enum="EmissionShape">
+ Particles will be emitted on the surface of a sphere.
+ </constant>
+ <constant name="EMISSION_SHAPE_BOX" value="3" enum="EmissionShape">
Particles will be emitted in the volume of a box.
</constant>
- <constant name="EMISSION_SHAPE_POINTS" value="3" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_POINTS" value="4" enum="EmissionShape">
Particles will be emitted at a position determined by sampling a random point on the [member emission_point_texture]. Particle color will be modulated by [member emission_color_texture].
</constant>
- <constant name="EMISSION_SHAPE_DIRECTED_POINTS" value="4" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_DIRECTED_POINTS" value="5" enum="EmissionShape">
Particles will be emitted at a position determined by sampling a random point on the [member emission_point_texture]. Particle velocity and rotation will be set based on [member emission_normal_texture]. Particle color will be modulated by [member emission_color_texture].
</constant>
- <constant name="EMISSION_SHAPE_RING" value="5" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_RING" value="6" enum="EmissionShape">
Particles will be emitted in a ring or cylinder.
</constant>
- <constant name="EMISSION_SHAPE_MAX" value="6" enum="EmissionShape">
+ <constant name="EMISSION_SHAPE_MAX" value="7" enum="EmissionShape">
Represents the size of the [enum EmissionShape] enum.
</constant>
<constant name="SUB_EMITTER_DISABLED" value="0" enum="SubEmitterMode">
diff --git a/scene/2d/cpu_particles_2d.cpp b/scene/2d/cpu_particles_2d.cpp
index cd2153b132..dd9df3c485 100644
--- a/scene/2d/cpu_particles_2d.cpp
+++ b/scene/2d/cpu_particles_2d.cpp
@@ -500,7 +500,7 @@ bool CPUParticles2D::get_split_scale() {
}
void CPUParticles2D::_validate_property(PropertyInfo &property) const {
- if (property.name == "emission_sphere_radius" && emission_shape != EMISSION_SHAPE_SPHERE) {
+ if (property.name == "emission_sphere_radius" && (emission_shape != EMISSION_SHAPE_SPHERE && emission_shape != EMISSION_SHAPE_SPHERE_SURFACE)) {
property.usage = PROPERTY_USAGE_NONE;
}
@@ -762,6 +762,11 @@ void CPUParticles2D::_particles_process(double p_delta) {
//do none
} break;
case EMISSION_SHAPE_SPHERE: {
+ real_t t = Math_TAU * Math::randf();
+ real_t radius = emission_sphere_radius * Math::randf();
+ p.transform[2] = Vector2(Math::cos(t), Math::sin(t)) * radius;
+ } break;
+ case EMISSION_SHAPE_SPHERE_SURFACE: {
real_t s = Math::randf(), t = Math_TAU * Math::randf();
real_t radius = emission_sphere_radius * Math::sqrt(1.0 - s * s);
p.transform[2] = Vector2(Math::cos(t), Math::sin(t)) * radius;
@@ -1357,7 +1362,7 @@ void CPUParticles2D::_bind_methods() {
ClassDB::bind_method(D_METHOD("convert_from_particles", "particles"), &CPUParticles2D::convert_from_particles);
ADD_GROUP("Emission Shape", "emission_");
- ADD_PROPERTY(PropertyInfo(Variant::INT, "emission_shape", PROPERTY_HINT_ENUM, "Point,Sphere,Box,Points,Directed Points", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_UPDATE_ALL_IF_MODIFIED), "set_emission_shape", "get_emission_shape");
+ ADD_PROPERTY(PropertyInfo(Variant::INT, "emission_shape", PROPERTY_HINT_ENUM, "Point,Sphere,Sphere Surface,Box,Points,Directed Points", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_UPDATE_ALL_IF_MODIFIED), "set_emission_shape", "get_emission_shape");
ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "emission_sphere_radius", PROPERTY_HINT_RANGE, "0.01,128,0.01"), "set_emission_sphere_radius", "get_emission_sphere_radius");
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "emission_rect_extents"), "set_emission_rect_extents", "get_emission_rect_extents");
ADD_PROPERTY(PropertyInfo(Variant::PACKED_VECTOR2_ARRAY, "emission_points"), "set_emission_points", "get_emission_points");
@@ -1447,6 +1452,7 @@ void CPUParticles2D::_bind_methods() {
BIND_ENUM_CONSTANT(EMISSION_SHAPE_POINT);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_SPHERE);
+ BIND_ENUM_CONSTANT(EMISSION_SHAPE_SPHERE_SURFACE);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_RECTANGLE);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_POINTS);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_DIRECTED_POINTS);
diff --git a/scene/2d/cpu_particles_2d.h b/scene/2d/cpu_particles_2d.h
index 8c8f161d74..7ae51e3966 100644
--- a/scene/2d/cpu_particles_2d.h
+++ b/scene/2d/cpu_particles_2d.h
@@ -69,6 +69,7 @@ public:
enum EmissionShape {
EMISSION_SHAPE_POINT,
EMISSION_SHAPE_SPHERE,
+ EMISSION_SHAPE_SPHERE_SURFACE,
EMISSION_SHAPE_RECTANGLE,
EMISSION_SHAPE_POINTS,
EMISSION_SHAPE_DIRECTED_POINTS,
diff --git a/scene/3d/cpu_particles_3d.cpp b/scene/3d/cpu_particles_3d.cpp
index ab28a83806..8c8596fc2e 100644
--- a/scene/3d/cpu_particles_3d.cpp
+++ b/scene/3d/cpu_particles_3d.cpp
@@ -508,7 +508,7 @@ bool CPUParticles3D::get_split_scale() {
}
void CPUParticles3D::_validate_property(PropertyInfo &property) const {
- if (property.name == "emission_sphere_radius" && emission_shape != EMISSION_SHAPE_SPHERE) {
+ if (property.name == "emission_sphere_radius" && (emission_shape != EMISSION_SHAPE_SPHERE && emission_shape != EMISSION_SHAPE_SPHERE_SURFACE)) {
property.usage = PROPERTY_USAGE_NONE;
}
@@ -804,6 +804,13 @@ void CPUParticles3D::_particles_process(double p_delta) {
case EMISSION_SHAPE_SPHERE: {
real_t s = 2.0 * Math::randf() - 1.0;
real_t t = Math_TAU * Math::randf();
+ real_t x = Math::randf();
+ real_t radius = emission_sphere_radius * Math::sqrt(1.0 - s * s);
+ p.transform.origin = Vector3(0, 0, 0).lerp(Vector3(radius * Math::cos(t), radius * Math::sin(t), emission_sphere_radius * s), x);
+ } break;
+ case EMISSION_SHAPE_SPHERE_SURFACE: {
+ real_t s = 2.0 * Math::randf() - 1.0;
+ real_t t = Math_TAU * Math::randf();
real_t 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;
@@ -1530,7 +1537,7 @@ void CPUParticles3D::_bind_methods() {
ClassDB::bind_method(D_METHOD("convert_from_particles", "particles"), &CPUParticles3D::convert_from_particles);
ADD_GROUP("Emission Shape", "emission_");
- ADD_PROPERTY(PropertyInfo(Variant::INT, "emission_shape", PROPERTY_HINT_ENUM, "Point,Sphere,Box,Points,Directed Points,Ring", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_UPDATE_ALL_IF_MODIFIED), "set_emission_shape", "get_emission_shape");
+ ADD_PROPERTY(PropertyInfo(Variant::INT, "emission_shape", PROPERTY_HINT_ENUM, "Point,Sphere,Sphere Surface,Box,Points,Directed Points,Ring", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_UPDATE_ALL_IF_MODIFIED), "set_emission_shape", "get_emission_shape");
ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "emission_sphere_radius", PROPERTY_HINT_RANGE, "0.01,128,0.01"), "set_emission_sphere_radius", "get_emission_sphere_radius");
ADD_PROPERTY(PropertyInfo(Variant::VECTOR3, "emission_box_extents"), "set_emission_box_extents", "get_emission_box_extents");
ADD_PROPERTY(PropertyInfo(Variant::PACKED_VECTOR3_ARRAY, "emission_points"), "set_emission_points", "get_emission_points");
@@ -1627,6 +1634,7 @@ void CPUParticles3D::_bind_methods() {
BIND_ENUM_CONSTANT(EMISSION_SHAPE_POINT);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_SPHERE);
+ BIND_ENUM_CONSTANT(EMISSION_SHAPE_SPHERE_SURFACE);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_BOX);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_POINTS);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_DIRECTED_POINTS);
diff --git a/scene/3d/cpu_particles_3d.h b/scene/3d/cpu_particles_3d.h
index 5eeb5e75d3..521b6c615e 100644
--- a/scene/3d/cpu_particles_3d.h
+++ b/scene/3d/cpu_particles_3d.h
@@ -71,6 +71,7 @@ public:
enum EmissionShape {
EMISSION_SHAPE_POINT,
EMISSION_SHAPE_SPHERE,
+ EMISSION_SHAPE_SPHERE_SURFACE,
EMISSION_SHAPE_BOX,
EMISSION_SHAPE_POINTS,
EMISSION_SHAPE_DIRECTED_POINTS,
diff --git a/scene/resources/particles_material.cpp b/scene/resources/particles_material.cpp
index 1ef2b3496f..01a0411545 100644
--- a/scene/resources/particles_material.cpp
+++ b/scene/resources/particles_material.cpp
@@ -190,6 +190,9 @@ void ParticlesMaterial::_update_shader() {
case EMISSION_SHAPE_SPHERE: {
code += "uniform float emission_sphere_radius;\n";
} break;
+ case EMISSION_SHAPE_SPHERE_SURFACE: {
+ code += "uniform float emission_sphere_radius;\n";
+ } break;
case EMISSION_SHAPE_BOX: {
code += "uniform vec3 emission_box_extents;\n";
} break;
@@ -398,6 +401,13 @@ void ParticlesMaterial::_update_shader() {
case EMISSION_SHAPE_SPHERE: {
code += " float s = rand_from_seed(alt_seed) * 2.0 - 1.0;\n";
code += " float t = rand_from_seed(alt_seed) * 2.0 * pi;\n";
+ code += " float p = rand_from_seed(alt_seed);\n";
+ code += " float radius = emission_sphere_radius * sqrt(1.0 - s * s);\n";
+ code += " TRANSFORM[3].xyz = mix(vec3(0.0, 0.0, 0.0), vec3(radius * cos(t), radius * sin(t), emission_sphere_radius * s), p);\n";
+ } break;
+ case EMISSION_SHAPE_SPHERE_SURFACE: {
+ code += " float s = rand_from_seed(alt_seed) * 2.0 - 1.0;\n";
+ code += " float t = rand_from_seed(alt_seed) * 2.0 * pi;\n";
code += " float radius = emission_sphere_radius * sqrt(1.0 - s * s);\n";
code += " TRANSFORM[3].xyz = vec3(radius * cos(t), radius * sin(t), emission_sphere_radius * s);\n";
} break;
@@ -1165,7 +1175,7 @@ RID ParticlesMaterial::get_shader_rid() const {
}
void ParticlesMaterial::_validate_property(PropertyInfo &property) const {
- if (property.name == "emission_sphere_radius" && emission_shape != EMISSION_SHAPE_SPHERE) {
+ if (property.name == "emission_sphere_radius" && (emission_shape != EMISSION_SHAPE_SPHERE && emission_shape != EMISSION_SHAPE_SPHERE_SURFACE)) {
property.usage = PROPERTY_USAGE_NONE;
}
@@ -1388,7 +1398,7 @@ void ParticlesMaterial::_bind_methods() {
ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "lifetime_randomness", PROPERTY_HINT_RANGE, "0,1,0.01"), "set_lifetime_randomness", "get_lifetime_randomness");
ADD_GROUP("Emission Shape", "emission_");
- ADD_PROPERTY(PropertyInfo(Variant::INT, "emission_shape", PROPERTY_HINT_ENUM, "Point,Sphere,Box,Points,Directed Points,Ring"), "set_emission_shape", "get_emission_shape");
+ ADD_PROPERTY(PropertyInfo(Variant::INT, "emission_shape", PROPERTY_HINT_ENUM, "Point,Sphere,Sphere Surface,Box,Points,Directed Points,Ring"), "set_emission_shape", "get_emission_shape");
ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "emission_sphere_radius", PROPERTY_HINT_RANGE, "0.01,128,0.01,or_greater"), "set_emission_sphere_radius", "get_emission_sphere_radius");
ADD_PROPERTY(PropertyInfo(Variant::VECTOR3, "emission_box_extents"), "set_emission_box_extents", "get_emission_box_extents");
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "emission_point_texture", PROPERTY_HINT_RESOURCE_TYPE, "Texture2D"), "set_emission_point_texture", "get_emission_point_texture");
@@ -1496,6 +1506,7 @@ void ParticlesMaterial::_bind_methods() {
BIND_ENUM_CONSTANT(EMISSION_SHAPE_POINT);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_SPHERE);
+ BIND_ENUM_CONSTANT(EMISSION_SHAPE_SPHERE_SURFACE);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_BOX);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_POINTS);
BIND_ENUM_CONSTANT(EMISSION_SHAPE_DIRECTED_POINTS);
diff --git a/scene/resources/particles_material.h b/scene/resources/particles_material.h
index fd00c58468..57da344ce0 100644
--- a/scene/resources/particles_material.h
+++ b/scene/resources/particles_material.h
@@ -73,6 +73,7 @@ public:
enum EmissionShape {
EMISSION_SHAPE_POINT,
EMISSION_SHAPE_SPHERE,
+ EMISSION_SHAPE_SPHERE_SURFACE,
EMISSION_SHAPE_BOX,
EMISSION_SHAPE_POINTS,
EMISSION_SHAPE_DIRECTED_POINTS,