1 | /********************************************************************** <BR>
|
---|
2 | This file is part of Crack dot Com's free source code release of
|
---|
3 | Golgotha. <a href="http://www.crack.com/golgotha_release"> <BR> for
|
---|
4 | information about compiling & licensing issues visit this URL</a>
|
---|
5 | <PRE> If that doesn't help, contact Jonathan Clark at
|
---|
6 | golgotha_source@usa.net (Subject should have "GOLG" in it)
|
---|
7 | ***********************************************************************/
|
---|
8 |
|
---|
9 | #include "g1_object.hh"
|
---|
10 | #include "math/num_type.hh"
|
---|
11 | #include "math/pi.hh"
|
---|
12 | #include "g1_rand.hh"
|
---|
13 | #include "objs/debris.hh"
|
---|
14 | #include "saver.hh"
|
---|
15 | #include "map.hh"
|
---|
16 | #include "g1_render.hh"
|
---|
17 | #include "object_definer.hh"
|
---|
18 | #include "dll/dll.hh"
|
---|
19 | #include "map_man.hh"
|
---|
20 | #include "math/pi.hh"
|
---|
21 | #include "draw_context.hh"
|
---|
22 | #include "r1_clip.hh"
|
---|
23 | #include "r1_api.hh"
|
---|
24 |
|
---|
25 | const i4_float FUNNEL_HEIGHT=7.0;
|
---|
26 | const i4_float FUNNEL_RADIUS=1.0;
|
---|
27 | const int DATA_VERSION=1;
|
---|
28 | const int MAX_VALS=256;
|
---|
29 | const i4_float RADIUS=0.01;
|
---|
30 | static i4_float rand_val[MAX_VALS];
|
---|
31 | static int rand_i;
|
---|
32 | inline i4_float fast_rand() { rand_i=(rand_i+1)&(MAX_VALS-1); return rand_val[rand_i]; }
|
---|
33 |
|
---|
34 | void g1_debris_init()
|
---|
35 | {
|
---|
36 | for (int i=0; i<MAX_VALS; i++)
|
---|
37 | rand_val[i] = g1_float_rand(i)*RADIUS;
|
---|
38 | rand_i=0;
|
---|
39 | }
|
---|
40 |
|
---|
41 | g1_object_definer<g1_debris_class> g1_debris_def("debris",
|
---|
42 | g1_object_definition_class::EDITOR_SELECTABLE,
|
---|
43 | g1_debris_init);
|
---|
44 |
|
---|
45 |
|
---|
46 | g1_debris_class::g1_debris_class(g1_object_type id, g1_loader_class *fp)
|
---|
47 | : g1_object_class(id, fp)
|
---|
48 | {
|
---|
49 | w16 ver,data_size;
|
---|
50 |
|
---|
51 | if (fp)
|
---|
52 | fp->get_version(ver,data_size);
|
---|
53 | else
|
---|
54 | ver = 0;
|
---|
55 |
|
---|
56 | switch (ver)
|
---|
57 | {
|
---|
58 | case DATA_VERSION:
|
---|
59 | break;
|
---|
60 | default:
|
---|
61 | break;
|
---|
62 | }
|
---|
63 | type = RING_CHUNKS;
|
---|
64 | rad = 0.5;
|
---|
65 | strength = 2.0;
|
---|
66 | }
|
---|
67 |
|
---|
68 | void g1_debris_class::save(g1_saver_class *fp)
|
---|
69 | {
|
---|
70 | g1_object_class::save(fp);
|
---|
71 | fp->start_version(DATA_VERSION);
|
---|
72 | fp->end_version();
|
---|
73 | }
|
---|
74 |
|
---|
75 | void g1_debris_class::setup(i4_float sx, i4_float sy, i4_float sz, int _type)
|
---|
76 | {
|
---|
77 | g1_map_class *map=g1_get_map();
|
---|
78 |
|
---|
79 | if (sx<1) sx=1;
|
---|
80 | if (sy<1) sy=1;
|
---|
81 | if (sx>map->width()-1) sx=map->width()-1;
|
---|
82 | if (sy>map->height()-1) sy=map->height()-1;
|
---|
83 |
|
---|
84 | x=lx=sx;
|
---|
85 | y=ly=sy;
|
---|
86 | h=lh=sz;
|
---|
87 | type = _type;
|
---|
88 |
|
---|
89 | int i;
|
---|
90 | switch (type)
|
---|
91 | {
|
---|
92 | case TORNADO:
|
---|
93 | for (i=0; i<MAX_DEBRIS; i++)
|
---|
94 | {
|
---|
95 | debris[i].x = g1_float_rand(i)*FUNNEL_RADIUS*2.0-FUNNEL_RADIUS;
|
---|
96 | debris[i].y = g1_float_rand(i+2)*FUNNEL_RADIUS*2.0-FUNNEL_RADIUS;
|
---|
97 | debris[i].z = g1_float_rand(i+4)*FUNNEL_HEIGHT;
|
---|
98 | ldebris[i] = debris[i];
|
---|
99 | }
|
---|
100 | break;
|
---|
101 | case RING_CHUNKS:
|
---|
102 | for (i=0; i<MAX_DEBRIS; i++)
|
---|
103 | {
|
---|
104 | debris[i].x = g1_float_rand(i+4)*rad*2.0-rad;
|
---|
105 | debris[i].y = g1_float_rand(i+6)*rad*2.0-rad;
|
---|
106 | debris[i].z = g1_float_rand(i+8)*strength;
|
---|
107 | ldebris[i] = debris[i];
|
---|
108 | }
|
---|
109 | break;
|
---|
110 | }
|
---|
111 | occupy_location();
|
---|
112 | request_think();
|
---|
113 | }
|
---|
114 |
|
---|
115 |
|
---|
116 | void g1_debris_class::think()
|
---|
117 | {
|
---|
118 | i4_float
|
---|
119 | spin_speed = 0.3,
|
---|
120 | cs = cos(spin_speed)*1.05,
|
---|
121 | sn = sin(spin_speed)*1.05;
|
---|
122 |
|
---|
123 | unoccupy_location();
|
---|
124 | int i;
|
---|
125 | switch (type)
|
---|
126 | {
|
---|
127 | case TORNADO:
|
---|
128 | for (i=0; i<MAX_DEBRIS; i++)
|
---|
129 | {
|
---|
130 | ldebris[i] = debris[i];
|
---|
131 | debris[i].z += 0.4;
|
---|
132 | debris[i].x = debris[i].x*cs - debris[i].y*sn + fast_rand();
|
---|
133 | debris[i].y = debris[i].x*sn + debris[i].y*cs + fast_rand();
|
---|
134 | if (debris[i].z>FUNNEL_HEIGHT)
|
---|
135 | {
|
---|
136 | debris[i].x = g1_float_rand(i+0)*2*FUNNEL_RADIUS-FUNNEL_RADIUS;
|
---|
137 | debris[i].y = g1_float_rand(i+1)*2*FUNNEL_RADIUS-FUNNEL_RADIUS;
|
---|
138 | debris[i].z = g1_float_rand(i+2)*0.3;
|
---|
139 | ldebris[i] = debris[i];
|
---|
140 | }
|
---|
141 | }
|
---|
142 | break;
|
---|
143 | case RING_CHUNKS:
|
---|
144 | rad += 0.2;
|
---|
145 | strength *= 0.94;
|
---|
146 | if (rad>10.0)
|
---|
147 | {
|
---|
148 | request_remove();
|
---|
149 | return;
|
---|
150 | }
|
---|
151 | for (i=0; i<MAX_DEBRIS; i++)
|
---|
152 | {
|
---|
153 | ldebris[i] = debris[i];
|
---|
154 | debris[i].z += 0.2;
|
---|
155 | if (debris[i].z>strength)
|
---|
156 | {
|
---|
157 | i4_float th = g1_float_rand(i+0)*2*i4_pi();
|
---|
158 | debris[i].x = cos(th)*rad;
|
---|
159 | debris[i].y = sin(th)*rad;
|
---|
160 | debris[i].z = g1_float_rand(i+8)*0.2;
|
---|
161 | ldebris[i] = debris[i];
|
---|
162 | }
|
---|
163 | }
|
---|
164 | break;
|
---|
165 | }
|
---|
166 | occupy_location();
|
---|
167 | request_think();
|
---|
168 | }
|
---|
169 |
|
---|
170 | void g1_debris_class::draw(g1_draw_context_class *context)
|
---|
171 | {
|
---|
172 | sw32 i,j;
|
---|
173 |
|
---|
174 | r1_render_api_class *r_api = g1_render.r_api;
|
---|
175 |
|
---|
176 | i4_transform_class tmp,trans = *context->transform;
|
---|
177 | r1_vert p, vert[3];
|
---|
178 | i4_3d_vector ip;
|
---|
179 |
|
---|
180 | vert[0].a=vert[1].a=vert[2].a = 1;
|
---|
181 | vert[0].r=vert[0].g=vert[0].b = 0;
|
---|
182 | vert[1].r=vert[1].g=vert[1].b = 0;
|
---|
183 | vert[2].r=vert[2].g=vert[2].b = 0;
|
---|
184 |
|
---|
185 | tmp.translate(x,y,h);
|
---|
186 | trans.multiply(tmp);
|
---|
187 |
|
---|
188 | i4_float tx[3],ty[3];
|
---|
189 | i4_bool ok;
|
---|
190 | i4_float fr=g1_render.frame_ratio;
|
---|
191 |
|
---|
192 | r_api->set_write_mode(R1_WRITE_COLOR | R1_COMPARE_W | R1_WRITE_W);
|
---|
193 | r_api->set_shading_mode(R1_COLORED_SHADING);
|
---|
194 | r_api->set_alpha_mode(R1_ALPHA_DISABLED);
|
---|
195 | r_api->disable_texture();
|
---|
196 | for (i=0; i<MAX_DEBRIS; i++)
|
---|
197 | {
|
---|
198 | ip.set((debris[i].x-ldebris[i].x)*fr + ldebris[i].x,
|
---|
199 | (debris[i].y-ldebris[i].y)*fr + ldebris[i].y,
|
---|
200 | (debris[i].z-ldebris[i].z)*fr + ldebris[i].z);
|
---|
201 | trans.transform(ip, *p.point());
|
---|
202 | if (!r1_calc_outcode(&p))
|
---|
203 | {
|
---|
204 | p.v.x *= g1_render.scale_x;
|
---|
205 | p.v.y *= g1_render.scale_y;
|
---|
206 | p.w = 1/p.v.z;
|
---|
207 | p.px = p.v.x * p.w;
|
---|
208 | p.py = p.v.y * p.w;
|
---|
209 | ok=i4_T;
|
---|
210 | tx[0] = p.px+fast_rand()-RADIUS/2; ty[0] = p.py-fast_rand();
|
---|
211 | tx[1] = p.px-fast_rand(); ty[1] = p.py+fast_rand();
|
---|
212 | tx[2] = p.px+fast_rand(); ty[2] = p.py+fast_rand();
|
---|
213 | for (j=0; j<3 && ok; j++)
|
---|
214 | {
|
---|
215 | if (tx[j]<=-1.0 || tx[j]>=1.0 || ty[j]<=-1.0 || ty[j]>=1.0)
|
---|
216 | ok = i4_F;
|
---|
217 | else
|
---|
218 | {
|
---|
219 | vert[j].w = p.w;
|
---|
220 | vert[j].v.x = p.v.x; vert[j].v.y = p.v.y; vert[j].v.z = p.v.z;
|
---|
221 |
|
---|
222 | vert[j].px = tx[j]*g1_render.center_x + g1_render.center_x;
|
---|
223 | vert[j].py = ty[j]*g1_render.center_y + g1_render.center_y;
|
---|
224 | }
|
---|
225 | }
|
---|
226 | if (ok)
|
---|
227 | r_api->render_poly(3,vert);
|
---|
228 | }
|
---|
229 | }
|
---|
230 | }
|
---|
231 |
|
---|