X-Git-Url: https://harrygodden.com/git/?a=blobdiff_plain;f=vg_m.h;h=91071ffb163d1b38617679c938bf68a7ba5bc590;hb=17dc0afed8913ce7756e86f1c69da4ada8ceda79;hp=c753be797bc9e1da62b96c29ead2e8e800f7f0b9;hpb=76d234b7dc5e6500e8a54009b367e7620f11ef97;p=vg.git diff --git a/vg_m.h b/vg_m.h index c753be7..91071ff 100644 --- a/vg_m.h +++ b/vg_m.h @@ -32,6 +32,7 @@ #define VG_PIf 3.14159265358979323846264338327950288f #define VG_TAUf 6.28318530717958647692528676655900576f + /* * ----------------------------------------------------------------------------- * Section 0. Misc Operations @@ -106,6 +107,31 @@ static inline f32 vg_rad( f32 deg ) return deg * VG_PIf / 180.0f; } +/* angle to reach b from a */ +static f32 vg_angle_diff( f32 a, f32 b ){ + f32 d = fmod(b,VG_TAUf)-fmodf(a,VG_TAUf); + if( fabsf(d) > VG_PIf ) + d = -vg_signf(d) * (VG_TAUf - fabsf(d)); + + return d; +} + +/* + * quantize float to bit count + */ +static u32 vg_quantf( f32 a, u32 bits, f32 min, f32 max ){ + u32 mask = (0x1 << bits) - 1; + return vg_clampf((a - min) * ((f32)mask/(max-min)), 0.0f, mask ); +} + +/* + * un-quantize discreet to float + */ +static f32 vg_dequantf( u32 q, u32 bits, f32 min, f32 max ){ + u32 mask = (0x1 << bits) - 1; + return min + (f32)q * ((max-min) / (f32)mask); +} + /* * ----------------------------------------------------------------------------- * Section 2.a 2D Vectors @@ -514,6 +540,34 @@ static void v3_tangent_basis( v3f n, v3f tx, v3f ty ){ v3_cross( n, tx, ty ); } +/* + * Compute yaw and pitch based of a normalized vector representing forward + * forward: -z + * result -> (YAW,PITCH,0.0) + */ +static void v3_angles( v3f v, v3f out_angles ){ + float yaw = atan2f( v[0], -v[2] ), + pitch = atan2f( + -v[1], + sqrtf( + v[0]*v[0] + v[2]*v[2] + ) + ); + + out_angles[0] = yaw; + out_angles[1] = pitch; + out_angles[2] = 0.0f; +} + +/* + * Compute the forward vector from (YAW,PITCH,ROLL) + * forward: -z + */ +static void v3_angles_vector( v3f angles, v3f out_v ){ + out_v[0] = sinf( angles[0] ) * cosf( angles[1] ); + out_v[1] = -sinf( angles[1] ); + out_v[2] = -cosf( angles[0] ) * cosf( angles[1] ); +} /* * ----------------------------------------------------------------------------- @@ -673,6 +727,10 @@ static void q_mulv( v4f q, v3f v, v3f d ) v3_add( v1, v2, d ); } +static f32 q_dist( v4f q0, v4f q1 ){ + return acosf( 2.0f * v4_dot(q0,q1) -1.0f ); +} + /* * ----------------------------------------------------------------------------- * Section 4.a 2x2 matrices @@ -2215,8 +2273,7 @@ struct { } static vg_rand; -static void vg_rand_seed( unsigned long seed ) -{ +static void vg_rand_seed( unsigned long seed ) { /* set initial seeds to mt[STATE_VECTOR_LENGTH] using the generator * from Line 25 of Table 1 in: Donald Knuth, "The Art of Computer * Programming," Vol. 2 (2nd Ed.) pp.102. @@ -2231,8 +2288,7 @@ static void vg_rand_seed( unsigned long seed ) /* * Generates a pseudo-randomly generated long. */ -static u32 vg_randu32(void) -{ +static u32 vg_randu32(void) { u32 y; /* mag[x] = x * 0x9908b0df for x = 0,1 */ static u32 mag[2] = {0x0, 0x9908b0df}; @@ -2272,32 +2328,47 @@ static u32 vg_randu32(void) /* * Generates a pseudo-randomly generated f64 in the range [0..1]. */ -static inline f64 vg_randf64(void) -{ +static inline f64 vg_randf64(void){ return (f64)vg_randu32()/(f64)0xffffffff; } -static inline f64 vg_randf64_range( f64 min, f64 max ) -{ +static inline f64 vg_randf64_range( f64 min, f64 max ){ return vg_lerp( min, max, (f64)vg_randf64() ); } -static inline void vg_rand_dir( v3f dir ) -{ +static inline void vg_rand_dir( v3f dir ){ dir[0] = vg_randf64(); dir[1] = vg_randf64(); dir[2] = vg_randf64(); + /* warning: *could* be 0 length. + * very unlikely.. 1 in (2^32)^3. but its mathematically wrong. */ + v3_muls( dir, 2.0f, dir ); v3_sub( dir, (v3f){1.0f,1.0f,1.0f}, dir ); v3_normalize( dir ); } -static inline void vg_rand_sphere( v3f co ) -{ +static inline void vg_rand_sphere( v3f co ){ vg_rand_dir(co); v3_muls( co, cbrtf( vg_randf64() ), co ); } +static void vg_rand_disc( v2f co ){ + f32 a = vg_randf64() * VG_TAUf; + co[0] = sinf(a); + co[1] = cosf(a); + v2_muls( co, sqrtf( vg_randf64() ), co ); +} + +static void vg_rand_cone( v3f out_dir, f32 angle ){ + f32 r = sqrtf(vg_randf64()) * angle * 0.5f, + a = vg_randf64() * VG_TAUf; + + out_dir[0] = sinf(a) * sinf(r); + out_dir[1] = cosf(a) * sinf(r); + out_dir[2] = cosf(r); +} + #endif /* VG_M_H */