update helpers/location to 'frosted' ui
[carveJwlIkooP6JGAAIwe30JlM.git] / world_audio.c
1 #include "audio.h"
2 #include "world_audio.h"
3
4 /* finds any active playing in world and fades them out, we can only do this
5 * while unloading */
6 void world_fadeout_audio( world_instance *world )
7 {
8 if( world->status != k_world_status_unloading ){
9 vg_fatal_error( "World status must be set to 'unloading', to fadeout"
10 " audio.\n" );
11 }
12
13 u8 world_id = (world - world_static.instances) + 1;
14
15 audio_lock();
16 for( u32 i=0; i<AUDIO_CHANNELS; i++ ){
17 audio_channel *ch = &vg_audio.channels[i];
18
19 if( ch->allocated && (ch->world_id == world_id) ){
20 ch = audio_channel_fadeout( ch, 1.0f );
21 }
22 }
23 audio_unlock();
24 }
25
26 /*
27 * Trace out a random point, near the player to try and determine water areas
28 */
29 enum audio_sprite_type world_audio_sample_sprite_random(v3f origin, v3f output)
30 {
31 v3f chance = { (vg_randf64(&vg.rand)-0.5f) * 30.0f,
32 8,
33 (vg_randf64(&vg.rand)-0.5f) * 30.0f };
34
35 v3f pos;
36 v3_add( chance, origin, pos );
37
38 ray_hit contact;
39 contact.dist = vg_minf( 16.0f, pos[1] );
40
41 world_instance *world = world_current_instance();
42
43 if( ray_world( world, pos, (v3f){0.0f,-1.0f,0.0f}, &contact,
44 k_material_flag_ghosts ) ){
45 struct world_surface *mat = ray_hit_surface( world, &contact );
46
47 if( mat->info.surface_prop == k_surface_prop_grass){
48 v3_copy( contact.pos, output );
49 return k_audio_sprite_type_grass;
50 }
51 else{
52 return k_audio_sprite_type_none;
53 }
54 }
55
56 output[0] = pos[0];
57 output[1] = 0.0f;
58 output[2] = pos[2];
59
60 float dist = fabsf(output[1] - origin[1]);
61
62 if( world->water.enabled && dist<=40.0f && !(world->info.flags&0x2) )
63 return k_audio_sprite_type_water;
64 else
65 return k_audio_sprite_type_none;
66 }
67
68 void world_audio_sample_distances( v3f co, int *index, float *value )
69 {
70 float inr3 = 0.57735027,
71 inr2 = 0.70710678118;
72
73 v3f sample_directions[] = {
74 { -1.0f, 0.0f, 0.0f },
75 { 1.0f, 0.0f, 0.0f },
76 { 0.0f, 0.0f, 1.0f },
77 { 0.0f, 0.0f, -1.0f },
78 { 0.0f, 1.0f, 0.0f },
79 { 0.0f, -1.0f, 0.0f },
80 { -inr3, inr3, inr3 },
81 { inr3, inr3, inr3 },
82 { -inr3, inr3, -inr3 },
83 { inr3, inr3, -inr3 },
84 { -inr2, 0.0f, inr2 },
85 { inr2, 0.0f, inr2 },
86 { -inr2, 0.0f, -inr2 },
87 { inr2, 0.0f, -inr2 },
88 };
89
90 static int si = 0;
91 static float distances[16];
92
93 ray_hit ray;
94 ray.dist = 5.0f;
95
96 v3f rc, rd, ro;
97 v3_copy( sample_directions[ si ], rd );
98 v3_add( co, (v3f){0.0f,1.5f,0.0f}, ro );
99 v3_copy( ro, rc );
100
101 float dist = 200.0f;
102
103 for( int i=0; i<10; i++ ){
104 if( ray_world( world_current_instance(), rc, rd, &ray,
105 k_material_flag_ghosts ) ){
106 dist = (float)i*5.0f + ray.dist;
107 break;
108 }
109 else{
110 v3_muladds( rc, rd, ray.dist, rc );
111 }
112 }
113
114 distances[si] = dist;
115
116 if( vg_audio.debug_ui && vg_lines.enabled ){
117 for( int i=0; i<14; i++ ){
118 if( distances[i] != 200.0f ){
119 u32 colours[] = { VG__RED, VG__BLUE, VG__GREEN,
120 VG__CYAN, VG__YELOW, VG__PINK,
121 VG__WHITE };
122
123 u32 colour = colours[i%7];
124
125 v3f p1;
126 v3_muladds( ro, sample_directions[i], distances[i], p1 );
127 vg_line( ro, p1, colour );
128 vg_line_point( p1, 0.1f, colour );
129 }
130 }
131 }
132
133 *index = si;
134 *value = dist;
135
136 si ++;
137 if( si >= 14 )
138 si = 0;
139 }