diff options
| author | Rémi Verschelde <rverschelde@gmail.com> | 2017-12-16 14:28:25 +0100 | 
|---|---|---|
| committer | GitHub <noreply@github.com> | 2017-12-16 14:28:25 +0100 | 
| commit | 1c18943e97940fa89dbc61ad3c733f29f65b9743 (patch) | |
| tree | b4cb2c77563fbba62e8ce7c05c771970b6957c8e | |
| parent | 0f188461c5690e29fc7bce7c5aa080a7ebe44219 (diff) | |
| parent | 641c6de16049f48ffc38162803aa3440b8bf1437 (diff) | |
Merge pull request #14330 from matrem/particles_spread
Spread should be in degree (see documentation, and flag_disable_z case)
| -rw-r--r-- | scene/3d/particles.cpp | 34 | 
1 files changed, 23 insertions, 11 deletions
diff --git a/scene/3d/particles.cpp b/scene/3d/particles.cpp index 821f1a5a78..b445ccc5a9 100644 --- a/scene/3d/particles.cpp +++ b/scene/3d/particles.cpp @@ -598,6 +598,11 @@ void ParticlesMaterial::_update_shader() {  	code += "}\n";  	code += "\n"; +	code += "float rand_from_seed_m1_p1(inout uint seed) {\n"; +	code += "	return rand_from_seed(seed)*2.0-1.0;\n"; +	code += "}\n"; +	code += "\n"; +  	//improve seed quality  	code += "uint hash(uint x) {\n";  	code += "	x = ((x >> uint(16)) ^ x) * uint(73244475);\n"; @@ -614,6 +619,8 @@ void ParticlesMaterial::_update_shader() {  	code += "	float scale_rand = rand_from_seed(alt_seed);\n";  	code += "	float hue_rot_rand = rand_from_seed(alt_seed);\n";  	code += "	float anim_offset_rand = rand_from_seed(alt_seed);\n"; +	code += "	float pi = 3.14159;\n"; +	code += "	float degree_to_rad = pi / 180.0;\n";  	code += "\n";  	if (emission_shape >= EMISSION_SHAPE_POINTS) { @@ -638,23 +645,28 @@ void ParticlesMaterial::_update_shader() {  	else  		code += "		float tex_anim_offset = 0.0;\n"; +	code += "		float spread_rad = spread*degree_to_rad;\n"; +  	if (flags[FLAG_DISABLE_Z]) { -		code += "		float angle1 = (rand_from_seed(alt_seed)*2.0-1.0)*spread/180.0*3.1416;\n"; -		code += "		vec3 rot = vec3( cos(angle1), sin(angle1),0.0 );\n"; +		code += "		float angle1_rad = rand_from_seed_m1_p1(alt_seed)*spread_rad;\n"; +		code += "		vec3 rot = vec3( cos(angle1_rad), sin(angle1_rad),0.0 );\n";  		code += "		VELOCITY = rot*initial_linear_velocity*mix(1.0, rand_from_seed(alt_seed), initial_linear_velocity_random);\n";  	} else {  		//initiate velocity spread in 3D -		code += "		float angle1 = rand_from_seed(alt_seed)*spread*3.1416;\n"; -		code += "		float angle2 = rand_from_seed(alt_seed)*20.0*3.1416; // make it more random like\n"; -		code += "		vec3 rot_xz = vec3( sin(angle1), 0.0, cos(angle1) );\n"; -		code += "		vec3 rot = vec3( cos(angle2)*rot_xz.x,sin(angle2)*rot_xz.x, rot_xz.z);\n"; -		code += "		VELOCITY = rot*initial_linear_velocity*mix(1.0, rand_from_seed(alt_seed), initial_linear_velocity_random);\n"; +		code += "		float angle1_rad = rand_from_seed_m1_p1(alt_seed)*spread_rad;\n"; +		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 += "		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";  	}  	code += "		float base_angle = (initial_angle+tex_angle)*mix(1.0,angle_rand,initial_angle_random);\n"; -	code += "		CUSTOM.x = base_angle*3.1416/180.0;\n"; //angle +	code += "		CUSTOM.x = base_angle*degree_to_rad;\n"; //angle  	code += "		CUSTOM.y = 0.0;\n"; //phase  	code += "		CUSTOM.z = (anim_offset+tex_anim_offset)*mix(1.0,anim_offset_rand,anim_offset_random);\n"; //animation offset (0-1)  	switch (emission_shape) { @@ -777,7 +789,7 @@ void ParticlesMaterial::_update_shader() {  		code += "		float orbit_amount = (orbit_velocity+tex_orbit_velocity)*mix(1.0,rand_from_seed(alt_seed),orbit_velocity_random);\n";  		code += "		if (orbit_amount!=0.0) {\n"; -		code += "		     float ang = orbit_amount * DELTA * 3.1416 * 2.0;\n"; +		code += "		     float ang = orbit_amount * DELTA * pi * 2.0;\n";  		code += "		     mat2 rot = mat2(vec2(cos(ang),-sin(ang)),vec2(sin(ang),cos(ang)));\n";  		code += "		     TRANSFORM[3].xy-=diff.xy;\n";  		code += "		     TRANSFORM[3].xy+=rot * diff.xy;\n"; @@ -800,7 +812,7 @@ void ParticlesMaterial::_update_shader() {  	code += "		}\n";  	code += "		float base_angle = (initial_angle+tex_angle)*mix(1.0,angle_rand,initial_angle_random);\n";  	code += "		base_angle += CUSTOM.y*LIFETIME*(angular_velocity+tex_angular_velocity)*mix(1.0,rand_from_seed(alt_seed)*2.0-1.0,angular_velocity_random);\n"; -	code += "		CUSTOM.x = base_angle*3.1416/180.0;\n"; //angle +	code += "		CUSTOM.x = base_angle*degree_to_rad;\n"; //angle  	code += "		CUSTOM.z = (anim_offset+tex_anim_offset)*mix(1.0,anim_offset_rand,anim_offset_random)+CUSTOM.y*(anim_speed+tex_anim_speed)*mix(1.0,rand_from_seed(alt_seed),anim_speed_random);\n"; //angle  	if (flags[FLAG_ANIM_LOOP]) {  		code += "		CUSTOM.z = mod(CUSTOM.z,1.0);\n"; //loop @@ -821,7 +833,7 @@ void ParticlesMaterial::_update_shader() {  	else  		code += "	float tex_hue_variation = 0.0;\n"; -	code += "	float hue_rot_angle = (hue_variation+tex_hue_variation)*3.1416*2.0*mix(1.0,hue_rot_rand*2.0-1.0,hue_variation_random);\n"; +	code += "	float hue_rot_angle = (hue_variation+tex_hue_variation)*pi*2.0*mix(1.0,hue_rot_rand*2.0-1.0,hue_variation_random);\n";  	code += "	float hue_rot_c = cos(hue_rot_angle);\n";  	code += "	float hue_rot_s = sin(hue_rot_angle);\n";  	code += "	mat4 hue_rot_mat = mat4( vec4(0.299,  0.587,  0.114, 0.0),\n";  |