]> icculus.org git repositories - taylor/freespace2.git/blob - src/hud/hudartillery.cpp
use a better multi_sw_ok_to_commit() check
[taylor/freespace2.git] / src / hud / hudartillery.cpp
1 /*
2  * Copyright (C) Volition, Inc. 1999.  All rights reserved.
3  *
4  * All source code herein is the property of Volition, Inc. You may not sell 
5  * or otherwise commercially exploit the source or things you created based on
6  * the source.
7  */
8
9 /*
10  * $Logfile: /Freespace2/code/Hud/HudArtillery.cpp $
11  * $Revision$
12  * $Date$
13  * $Author$
14  *
15  *
16  * $Log$
17  * Revision 1.6  2005/10/01 22:04:58  taylor
18  * fix FS1 (de)briefing voices, the directory names are different in FS1
19  * hard code the table values so that the fs1.vp file isn't needed
20  * hard code a mission fix for sm2-08a since a have no idea how to fix it otherwise
21  * generally cleanup some FS1 code
22  * fix volume sliders in the options screen that never went all the way up
23  *
24  * Revision 1.5  2002/06/17 06:33:09  relnev
25  * ryan's struct patch for gcc 2.95
26  *
27  * Revision 1.4  2002/06/09 04:41:21  relnev
28  * added copyright header
29  *
30  * Revision 1.3  2002/05/07 03:16:45  theoddone33
31  * The Great Newline Fix
32  *
33  * Revision 1.2  2002/05/03 13:34:33  theoddone33
34  * More stuff compiles
35  *
36  * Revision 1.1.1.1  2002/05/03 03:28:09  root
37  * Initial import.
38  *  
39  * 
40  * 5     6/01/99 8:35p Dave
41  * Finished lockarm weapons. Added proper supercap weapons/damage. Added
42  * awacs-set-radius sexpression.
43  * 
44  * 4     4/28/99 11:36p Dave
45  * Tweaked up subspace missile strike a bit,
46  * 
47  * 3     4/28/99 11:13p Dave
48  * Temporary checkin of artillery code.
49  * 
50  * 2     4/20/99 6:39p Dave
51  * Almost done with artillery targeting. Added support for downloading
52  * images on the PXO screen.
53  * 
54  * 1     4/20/99 12:00a Dave
55  * 
56  * 
57  * $NoKeywords: $
58  */
59
60 #include "hudartillery.h"
61 #include "ai.h"
62 #include "player.h"
63 #include "2d.h"
64 #include "alphacolors.h"
65
66 // -----------------------------------------------------------------------------------------------------------------------
67 // ARTILLERY DEFINES/VARS
68 //
69
70
71 // -----------------------------------------------------------------------------------------------------------------------
72 // ARTILLERY FUNCTIONS
73 //
74
75 #include "linklist.h"
76 #include "timer.h"
77 #include "parselo.h"
78 #include "multi.h"
79 #include "fireballs.h"
80 #include "freespace.h"
81
82 // test code for subspace missile strike -------------------------------------------
83
84
85 int Ssm_info_count = 0;
86 ssm_info Ssm_info[MAX_SSM_TYPES];
87
88 // list of active/free strikes
89 ssm_strike Ssm_strikes[MAX_SSM_STRIKES];
90 ssm_strike Ssm_free_list;
91 ssm_strike Ssm_used_list;
92 int Num_ssm_strikes = 0;
93
94 // game init
95 void ssm_init()
96 {       
97 #ifndef MAKE_FS1
98         ssm_info bogus, *s;
99         char weapon_name[NAME_LENGTH+1] = "";
100
101         try {
102                 read_file_text("ssm.tbl");
103                 reset_parse();
104
105                 // parse the table
106                 Ssm_info_count = 0;
107                 while(!optional_string("#end")){
108                         // another ssm definition
109                         if(optional_string("$SSM:")){
110                                 // pointer to info struct
111                                 if(Ssm_info_count >= MAX_SSM_TYPES){
112                                         s = &bogus;
113                                 } else {
114                                         s = &Ssm_info[Ssm_info_count];
115                                 }
116
117                                 // name
118                                 stuff_string(s->name, F_NAME, NULL);
119
120                                 // stuff data
121                                 required_string("+Weapon:");
122                                 stuff_string(weapon_name, F_NAME, NULL);
123                                 required_string("+Count:");
124                                 stuff_int(&s->count);
125                                 required_string("+WarpRadius:");
126                                 stuff_float(&s->warp_radius);
127                                 required_string("+WarpTime:");
128                                 stuff_float(&s->warp_time);
129                                 required_string("+Radius:");
130                                 stuff_float(&s->radius);
131                                 required_string("+Offset:");
132                                 stuff_float(&s->offset);
133
134                                 // see if we have a valid weapon
135                                 s->weapon_info_index = -1;
136                                 s->weapon_info_index = weapon_name_lookup(weapon_name);
137                                 if(s->weapon_info_index >= 0){
138                                         // valid
139                                         Ssm_info_count++;
140                                 }
141                         }
142                 }
143         } catch (parse_error_t rval) {
144                 Error(LOCATION, "Unable to parse ssm.tbl!  Code = %i.\n", (int)rval);
145         }
146
147 #else
148         // not for FS1
149         Ssm_info_count = 0;
150 #endif
151 }
152
153 void ssm_get_random_start_pos(vector *out, vector *start, matrix *orient, int ssm_index)
154 {
155         vector temp;
156         ssm_info *s = &Ssm_info[ssm_index];
157
158         // get a random vector in the circle of the firing plane
159         vm_vec_random_in_circle(&temp, start, orient, s->radius, 1);
160
161         // offset it a bit
162         vm_vec_scale_add(out, &temp, &orient->v.fvec, s->offset);
163 }
164
165 // level init
166 void ssm_level_init()
167 {
168         int i;
169
170         Num_ssm_strikes = 0;
171         list_init( &Ssm_free_list );
172         list_init( &Ssm_used_list );
173
174         // Link all object slots into the free list
175         for (i=0; i<MAX_SSM_STRIKES; i++)       {
176                 list_append(&Ssm_free_list, &Ssm_strikes[i] );
177         }
178 }
179
180 // start a subspace missile effect
181 void ssm_create(vector *target, vector *start, int ssm_index, ssm_firing_info *override)
182 {       
183         ssm_strike *ssm;                
184         matrix dir;
185         int idx;
186
187         if (Num_ssm_strikes >= MAX_SSM_STRIKES ) {
188                 #ifndef NDEBUG
189                 mprintf(("Ssm creation failed - too many ssms!\n" ));
190                 #endif
191                 return;
192         }
193
194         // sanity
195         SDL_assert(target != NULL);
196         if(target == NULL){
197                 return;
198         }
199         SDL_assert(start != NULL);
200         if(start == NULL){
201                 return;
202         }
203         if((ssm_index < 0) || (ssm_index >= MAX_SSM_TYPES)){
204                 return;
205         }
206
207         // Find next available trail
208         ssm = GET_FIRST(&Ssm_free_list);
209         SDL_assert( ssm != &Ssm_free_list );            // shouldn't have the dummy element
210
211         // remove trailp from the free list
212         list_remove( &Ssm_free_list, ssm );
213         
214         // insert trailp onto the end of used list
215         list_append( &Ssm_used_list, ssm );
216
217         // increment counter
218         Num_ssm_strikes++;      
219
220         // Init the ssm data
221
222         // override in multiplayer
223         if(override != NULL){
224                 ssm->sinfo = *override;
225         }
226         // single player or the server
227         else {
228                 // forward orientation
229                 vector temp;
230                 vm_vec_sub(&temp, target, start);
231                 vm_vec_normalize(&temp);
232                 vm_vector_2_matrix(&dir, &temp, NULL, NULL);
233
234                 // stuff info
235                 ssm->sinfo.ssm_index = ssm_index;
236                 ssm->sinfo.target = *target;
237                 for(idx=0; idx<Ssm_info[ssm_index].count; idx++){
238                         ssm->sinfo.delay_stamp[idx] = timestamp(200 + (int)frand_range(-199.0f, 1000.0f));
239                         ssm_get_random_start_pos(&ssm->sinfo.start_pos[idx], start, &dir, ssm_index);
240                 }
241
242                 // if we're the server, send a packet
243                 if(MULTIPLAYER_MASTER){
244                         //
245                 }
246         }
247
248         // clear timestamps, handles, etc
249         for(idx=0; idx<MAX_SSM_COUNT; idx++){
250                 ssm->done_flags[idx] = 0;
251                 ssm->fireballs[idx] = -1;
252         }
253 }
254
255 // delete a finished ssm effect
256 void ssm_delete(ssm_strike *ssm)
257 {
258         // remove objp from the used list
259         list_remove( &Ssm_used_list, ssm );
260
261         // add objp to the end of the free
262         list_append( &Ssm_free_list, ssm );
263
264         // decrement counter
265         Num_ssm_strikes--;
266
267         nprintf(("General", "Recycling SSM, %d left", Num_ssm_strikes));
268 }
269
270 // process subspace missile stuff
271 void ssm_process()
272 {
273         int idx, finished;
274         ssm_strike *moveup, *next_one;
275         ssm_info *si;
276         
277         // process all strikes  
278         moveup=GET_FIRST(&Ssm_used_list);
279         while ( moveup!=END_OF_LIST(&Ssm_used_list) )   {               
280                 // get the type
281                 if(moveup->sinfo.ssm_index < 0){
282                         continue;
283                 }
284                 si = &Ssm_info[moveup->sinfo.ssm_index];
285
286                 // check all the individual missiles
287                 finished = 1;
288                 for(idx=0; idx<si->count; idx++){
289                         // if this guy is not marked as done
290                         if(!moveup->done_flags[idx]){
291                                 finished = 0;                           
292
293                                 // if he already has the fireball effect
294                                 if(moveup->fireballs[idx] >= 0){
295                                         // if the warp effect is half done, fire the missile
296                                         if((1.0f - fireball_lifeleft_percent(&Objects[moveup->fireballs[idx]])) >= 0.5f){
297                                                 // get an orientation
298                                                 vector temp;
299                                                 matrix orient;
300
301                                                 vm_vec_sub(&temp, &moveup->sinfo.target, &moveup->sinfo.start_pos[idx]);
302                                                 vm_vec_normalize(&temp);
303                                                 vm_vector_2_matrix(&orient, &temp, NULL, NULL);
304
305                                                 // fire the missile and flash the screen
306                                                 weapon_create(&moveup->sinfo.start_pos[idx], &orient, si->weapon_info_index, -1, 1, -1, 1);
307
308                                                 // this makes this particular missile done
309                                                 moveup->done_flags[idx] = 1;
310                                         }
311                                 } 
312                                 // maybe create his warpin effect
313                                 else if((moveup->sinfo.delay_stamp[idx] >= 0) && timestamp_elapsed(moveup->sinfo.delay_stamp[idx])){
314                                         // get an orientation
315                                         vector temp;
316                                         matrix orient;
317
318                                         vm_vec_sub(&temp, &moveup->sinfo.target, &moveup->sinfo.start_pos[idx]);
319                                         vm_vec_normalize(&temp);
320                                         vm_vector_2_matrix(&orient, &temp, NULL, NULL);
321                                         moveup->fireballs[idx] = fireball_create(&moveup->sinfo.start_pos[idx], FIREBALL_WARP_EFFECT, -1, si->warp_radius, 0, &vmd_zero_vector, si->warp_time, 0, &orient);
322                                 }
323                         }
324                 }
325                 if(finished){
326                         next_one = GET_NEXT(moveup);                    
327                         ssm_delete(moveup);                                                                                                                     
328                         moveup = next_one;
329                         continue;
330                 }
331                 
332                 moveup=GET_NEXT(moveup);
333         }       
334 }
335
336
337 // test code for subspace missile strike -------------------------------------------
338
339 // level init
340 void hud_init_artillery()
341 {
342 }
343
344 // update all hud artillery related stuff
345 void hud_artillery_update()
346 {
347 }
348
349 // render all hud artillery related stuff
350 void hud_artillery_render()
351 {
352         // render how long the player has been painting his target      
353         if((Player_ai != NULL) && (Player_ai->artillery_objnum >= 0)){
354                 gr_set_color_fast(&Color_bright_blue);
355                 gr_printf(10, 50, "%f", Player_ai->artillery_lock_time);
356         }
357 }
358