Fixes to CPU particles for performance and avoiding NaNs.
This commit is contained in:
parent
b17e71b6e5
commit
14494dddd0
|
@ -4066,35 +4066,37 @@ void RasterizerStorageGLES3::multimesh_allocate(RID p_multimesh, int p_instances
|
|||
|
||||
multimesh->data.resize(format_floats * p_instances);
|
||||
|
||||
float *dataptr = multimesh->data.ptrw();
|
||||
|
||||
for (int i = 0; i < p_instances * format_floats; i += format_floats) {
|
||||
|
||||
int color_from = 0;
|
||||
int custom_data_from = 0;
|
||||
|
||||
if (multimesh->transform_format == VS::MULTIMESH_TRANSFORM_2D) {
|
||||
multimesh->data.write[i + 0] = 1.0;
|
||||
multimesh->data.write[i + 1] = 0.0;
|
||||
multimesh->data.write[i + 2] = 0.0;
|
||||
multimesh->data.write[i + 3] = 0.0;
|
||||
multimesh->data.write[i + 4] = 0.0;
|
||||
multimesh->data.write[i + 5] = 1.0;
|
||||
multimesh->data.write[i + 6] = 0.0;
|
||||
multimesh->data.write[i + 7] = 0.0;
|
||||
dataptr[i + 0] = 1.0;
|
||||
dataptr[i + 1] = 0.0;
|
||||
dataptr[i + 2] = 0.0;
|
||||
dataptr[i + 3] = 0.0;
|
||||
dataptr[i + 4] = 0.0;
|
||||
dataptr[i + 5] = 1.0;
|
||||
dataptr[i + 6] = 0.0;
|
||||
dataptr[i + 7] = 0.0;
|
||||
color_from = 8;
|
||||
custom_data_from = 8;
|
||||
} else {
|
||||
multimesh->data.write[i + 0] = 1.0;
|
||||
multimesh->data.write[i + 1] = 0.0;
|
||||
multimesh->data.write[i + 2] = 0.0;
|
||||
multimesh->data.write[i + 3] = 0.0;
|
||||
multimesh->data.write[i + 4] = 0.0;
|
||||
multimesh->data.write[i + 5] = 1.0;
|
||||
multimesh->data.write[i + 6] = 0.0;
|
||||
multimesh->data.write[i + 7] = 0.0;
|
||||
multimesh->data.write[i + 8] = 0.0;
|
||||
multimesh->data.write[i + 9] = 0.0;
|
||||
multimesh->data.write[i + 10] = 1.0;
|
||||
multimesh->data.write[i + 11] = 0.0;
|
||||
dataptr[i + 0] = 1.0;
|
||||
dataptr[i + 1] = 0.0;
|
||||
dataptr[i + 2] = 0.0;
|
||||
dataptr[i + 3] = 0.0;
|
||||
dataptr[i + 4] = 0.0;
|
||||
dataptr[i + 5] = 1.0;
|
||||
dataptr[i + 6] = 0.0;
|
||||
dataptr[i + 7] = 0.0;
|
||||
dataptr[i + 8] = 0.0;
|
||||
dataptr[i + 9] = 0.0;
|
||||
dataptr[i + 10] = 1.0;
|
||||
dataptr[i + 11] = 0.0;
|
||||
color_from = 12;
|
||||
custom_data_from = 12;
|
||||
}
|
||||
|
@ -4109,14 +4111,14 @@ void RasterizerStorageGLES3::multimesh_allocate(RID p_multimesh, int p_instances
|
|||
} cu;
|
||||
|
||||
cu.colu = 0xFFFFFFFF;
|
||||
multimesh->data.write[i + color_from + 0] = cu.colf;
|
||||
dataptr[i + color_from + 0] = cu.colf;
|
||||
custom_data_from = color_from + 1;
|
||||
|
||||
} else if (multimesh->color_format == VS::MULTIMESH_COLOR_FLOAT) {
|
||||
multimesh->data.write[i + color_from + 0] = 1.0;
|
||||
multimesh->data.write[i + color_from + 1] = 1.0;
|
||||
multimesh->data.write[i + color_from + 2] = 1.0;
|
||||
multimesh->data.write[i + color_from + 3] = 1.0;
|
||||
dataptr[i + color_from + 0] = 1.0;
|
||||
dataptr[i + color_from + 1] = 1.0;
|
||||
dataptr[i + color_from + 2] = 1.0;
|
||||
dataptr[i + color_from + 3] = 1.0;
|
||||
custom_data_from = color_from + 4;
|
||||
}
|
||||
|
||||
|
@ -4130,13 +4132,13 @@ void RasterizerStorageGLES3::multimesh_allocate(RID p_multimesh, int p_instances
|
|||
} cu;
|
||||
|
||||
cu.colu = 0;
|
||||
multimesh->data.write[i + custom_data_from + 0] = cu.colf;
|
||||
dataptr[i + custom_data_from + 0] = cu.colf;
|
||||
|
||||
} else if (multimesh->custom_data_format == VS::MULTIMESH_CUSTOM_DATA_FLOAT) {
|
||||
multimesh->data.write[i + custom_data_from + 0] = 0.0;
|
||||
multimesh->data.write[i + custom_data_from + 1] = 0.0;
|
||||
multimesh->data.write[i + custom_data_from + 2] = 0.0;
|
||||
multimesh->data.write[i + custom_data_from + 3] = 0.0;
|
||||
dataptr[i + custom_data_from + 0] = 0.0;
|
||||
dataptr[i + custom_data_from + 1] = 0.0;
|
||||
dataptr[i + custom_data_from + 2] = 0.0;
|
||||
dataptr[i + custom_data_from + 3] = 0.0;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -592,7 +592,7 @@ void CPUParticles::_particles_process(float p_delta) {
|
|||
|
||||
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));
|
||||
direction_yz.z = direction_yz.z / Math::sqrt(direction_yz.z); //better uniform distribution
|
||||
direction_yz.z = direction_yz.z / MAX(0.0001, Math::sqrt(ABS(direction_yz.z))); //better uniform distribution
|
||||
Vector3 direction = Vector3(direction_xz.x * direction_yz.z, direction_yz.y, direction_xz.z * direction_yz.z);
|
||||
direction.normalize();
|
||||
p.velocity = direction * parameters[PARAM_INITIAL_LINEAR_VELOCITY] * Math::lerp(1.0f, float(Math::randf()), randomness[PARAM_INITIAL_LINEAR_VELOCITY]);
|
||||
|
@ -977,6 +977,8 @@ void CPUParticles::_update_particle_data_buffer() {
|
|||
|
||||
ptr += 17;
|
||||
}
|
||||
|
||||
can_update = true;
|
||||
}
|
||||
|
||||
#ifndef NO_THREADS
|
||||
|
@ -989,8 +991,10 @@ void CPUParticles::_update_render_thread() {
|
|||
#ifndef NO_THREADS
|
||||
update_mutex->lock();
|
||||
#endif
|
||||
|
||||
VS::get_singleton()->multimesh_set_as_bulk_array(multimesh, particle_data);
|
||||
if (can_update) {
|
||||
VS::get_singleton()->multimesh_set_as_bulk_array(multimesh, particle_data);
|
||||
can_update = false; //wait for next time
|
||||
}
|
||||
|
||||
#ifndef NO_THREADS
|
||||
update_mutex->unlock();
|
||||
|
@ -1061,6 +1065,8 @@ void CPUParticles::_notification(int p_what) {
|
|||
}
|
||||
}
|
||||
|
||||
bool processed = false;
|
||||
|
||||
if (time == 0 && pre_process_time > 0.0) {
|
||||
|
||||
float frame_time;
|
||||
|
@ -1073,6 +1079,7 @@ void CPUParticles::_notification(int p_what) {
|
|||
|
||||
while (todo >= 0) {
|
||||
_particles_process(frame_time);
|
||||
processed = true;
|
||||
todo -= frame_time;
|
||||
}
|
||||
}
|
||||
|
@ -1091,6 +1098,7 @@ void CPUParticles::_notification(int p_what) {
|
|||
|
||||
while (todo >= frame_time) {
|
||||
_particles_process(frame_time);
|
||||
processed = true;
|
||||
todo -= decr;
|
||||
}
|
||||
|
||||
|
@ -1098,9 +1106,12 @@ void CPUParticles::_notification(int p_what) {
|
|||
|
||||
} else {
|
||||
_particles_process(delta);
|
||||
processed = true;
|
||||
}
|
||||
|
||||
_update_particle_data_buffer();
|
||||
if (processed) {
|
||||
_update_particle_data_buffer();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1424,6 +1435,8 @@ CPUParticles::CPUParticles() {
|
|||
flags[i] = false;
|
||||
}
|
||||
|
||||
can_update = false;
|
||||
|
||||
set_color(Color(1, 1, 1, 1));
|
||||
|
||||
#ifndef NO_THREADS
|
||||
|
|
|
@ -142,6 +142,8 @@ private:
|
|||
int fixed_fps;
|
||||
bool fractional_delta;
|
||||
|
||||
volatile bool can_update;
|
||||
|
||||
DrawOrder draw_order;
|
||||
|
||||
Ref<Mesh> mesh;
|
||||
|
|
|
@ -308,7 +308,7 @@ void ParticlesMaterial::_update_shader() {
|
|||
code += " float angle2_rad = rand_from_seed_m1_p1(alt_seed) * spread_rad * (1.0 - flatness);\n";
|
||||
code += " vec3 direction_xz = vec3(sin(angle1_rad), 0, cos(angle1_rad));\n";
|
||||
code += " vec3 direction_yz = vec3(0, sin(angle2_rad), cos(angle2_rad));\n";
|
||||
code += " direction_yz.z = direction_yz.z / sqrt(direction_yz.z); // better uniform distribution\n";
|
||||
code += " direction_yz.z = direction_yz.z / max(0.0001,sqrt(abs(direction_yz.z))); // better uniform distribution\n";
|
||||
code += " vec3 direction = vec3(direction_xz.x * direction_yz.z, direction_yz.y, direction_xz.z * direction_yz.z);\n";
|
||||
code += " direction = normalize(direction);\n";
|
||||
code += " VELOCITY = direction * initial_linear_velocity * mix(1.0, rand_from_seed(alt_seed), initial_linear_velocity_random);\n";
|
||||
|
|
Loading…
Reference in New Issue