FS2_Open
Open source remastering of the Freespace 2 engine
missionscreencommon.cpp
Go to the documentation of this file.
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 the
6  * source.
7  *
8 */
9 
10 
11 
12 
13 #include <limits.h> // this is need even when not building debug!!
14 
15 #include "anim/animplay.h"
16 #include "cmdline/cmdline.h"
17 #include "cutscene/cutscenes.h"
18 #include "cutscene/movie.h"
19 #include "gamehelp/contexthelp.h"
21 #include "gamesnd/eventmusic.h"
22 #include "gamesnd/gamesnd.h"
23 #include "globalincs/linklist.h"
24 #include "graphics/2d.h"
26 #include "hud/hudwingmanstatus.h"
27 #include "io/key.h"
28 #include "io/mouse.h"
29 #include "io/timer.h"
30 #include "lighting/lighting.h"
31 #include "missionui/chatbox.h"
32 #include "missionui/missionbrief.h"
36 #include "network/multi.h"
37 #include "network/multi_endgame.h"
38 #include "network/multimsgs.h"
40 #include "network/multiutil.h"
41 #include "palman/palman.h"
42 #include "parse/sexp.h"
43 #include "popup/popup.h"
44 #include "render/3d.h"
45 #include "ship/ship.h"
46 #include "ui/uidefs.h"
47 #include "weapon/weapon.h"
48 
50 // Game Globals
52 
54 
55 // Dependent on when mouse button goes up
57 
59 
60 // Timers used to flash buttons after timeouts
61 #define MSC_FLASH_AFTER_TIME 60000 // time before flashing a button
62 #define MSC_FLASH_INTERVAL 200 // time between flashes
63 int Flash_timer; // timestamp used to start flashing
64 int Flash_toggle; // timestamp used to toggle flashing
65 int Flash_bright; // state of button to flash
66 
68 // Global to modulde
72 static int InterfacePaletteBitmap = -1; // PCX file that holds the interface palette
75 
76 loadout_data Player_loadout; // what the ship and weapon loadout is... used since we want to use the
77  // same loadout if the mission is played again
78 
79 //wss_unit Wss_slots[MAX_WSS_SLOTS]; // slot data struct
80 //int Wl_pool[MAX_WEAPON_TYPES]; // weapon pool
81 //int Ss_pool[MAX_SHIP_CLASSES]; // ship pool
82 //int Wss_num_wings; // number of player wings
83 
88 
90 int *Wl_pool = NULL;
91 int *Ss_pool = NULL;
93 
95 // Externs
97 extern void ss_set_team_pointers(int team);
98 extern void ss_reset_team_pointers();
99 extern void wl_set_team_pointers(int team);
100 extern void wl_reset_team_pointers();
101 extern int anim_timer_start;
102 extern void ss_reset_selected_ship();
103 
105 // UI
108 
110  { // UGH
111  { // GR_640
112  brief_common_buttons("CB_00", 7, 3, 37, 7, 0),
113  brief_common_buttons("CB_01", 7, 19, 37, 23, 1),
114  brief_common_buttons("CB_02", 7, 35, 37, 39, 2),
115  brief_common_buttons("CB_05", 571, 425, 572, 413, 5),
116  brief_common_buttons("CB_06", 533, 425, 500, 440, 6),
117  brief_common_buttons("CB_07", 533, 455, 479, 464, 7),
118  },
119  { // GR_1024
120  brief_common_buttons("2_CB_00", 12, 5, 59, 12, 0),
121  brief_common_buttons("2_CB_01", 12, 31, 59, 37, 1),
122  brief_common_buttons("2_CB_02", 12, 56, 59, 62, 2),
123  brief_common_buttons("2_CB_05", 914, 681, 937, 671, 5),
124  brief_common_buttons("2_CB_06", 854, 681, 822, 704, 6),
125  brief_common_buttons("2_CB_07", 854, 724, 800, 743, 7),
126  }
127  },
128  { // UGH
129  { // GR_640
130  brief_common_buttons("CB_00", 7, 3, 37, 7, 0),
131  brief_common_buttons("CB_01", 7, 19, 37, 23, 1),
132  brief_common_buttons("CB_02", 7, 35, 37, 39, 2),
133  brief_common_buttons("CB_05", 571, 425, 572, 413, 5),
134  brief_common_buttons("CB_06", 533, 425, 500, 440, 6),
135  brief_common_buttons("CB_07", 533, 455, 479, 464, 7),
136  },
137  { // GR_1024
138  brief_common_buttons("2_CB_00", 12, 5, 59, 12, 0),
139  brief_common_buttons("2_CB_01", 12, 31, 59, 37, 1),
140  brief_common_buttons("2_CB_02", 12, 56, 59, 62, 2),
141  brief_common_buttons("2_CB_05", 914, 681, 937, 671, 5),
142  brief_common_buttons("2_CB_06", 854, 681, 822, 704, 6),
143  brief_common_buttons("2_CB_07", 854, 724, 800, 743, 7),
144  }
145  },
146  { // UGH
147  { // GR_640
148  brief_common_buttons("CB_00", 7, 3, 37, 7, 0),
149  brief_common_buttons("CB_01", 7, 19, 37, 23, 1),
150  brief_common_buttons("CB_02", 7, 35, 37, 39, 2),
151  brief_common_buttons("CB_05", 571, 425, 572, 413, 5),
152  brief_common_buttons("CB_06", 533, 425, 500, 440, 6),
153  brief_common_buttons("CB_07", 533, 455, 479, 464, 7),
154  },
155  { // GR_1024
156  brief_common_buttons("2_CB_00", 12, 5, 59, 12, 0),
157  brief_common_buttons("2_CB_01", 12, 31, 59, 37, 1),
158  brief_common_buttons("2_CB_02", 12, 56, 59, 62, 2),
159  brief_common_buttons("2_CB_05", 914, 681, 937, 671, 5),
160  brief_common_buttons("2_CB_06", 854, 681, 822, 704, 6),
161  brief_common_buttons("2_CB_07", 854, 724, 800, 743, 7),
162  }
163  }
164 };
165 
166 #define COMMON_BRIEFING_BUTTON 0
167 #define COMMON_SS_BUTTON 1
168 #define COMMON_WEAPON_BUTTON 2
169 #define COMMON_COMMIT_BUTTON 3
170 #define COMMON_HELP_BUTTON 4
171 #define COMMON_OPTIONS_BUTTON 5
172 
173 int Background_playing; // Flag to indicate background animation is playing
174 static anim *Background_anim; // Ids for the anim data that is loaded
175 
176 // value for which Team_data entry to use
178 
179 // Ids for the instance of the anim that is playing
180 //static anim_instance *Background_anim_instance;
181 
184 
185 // prototypes
186 int wss_slots_all_empty();
187 
188 // Display the no ships selected error
190 {
191  popup(PF_USE_AFFIRMATIVE_ICON, 1, POPUP_OK, XSTR( "At least one ship must be selected before proceeding to weapons loadout", 460));
192 }
193 
194 // Check the status of the buttons common to the loadout screens
196 {
197  int i;
198  UI_BUTTON *b;
199 
200  for ( i = 0; i < NUM_COMMON_BUTTONS; i++ ) {
201  b = &Common_buttons[Current_screen-1][gr_screen.res][i].button;
202  if ( b->pressed() ) {
203 
204  common_button_do(i);
205  }
206  }
207 
208 /*
209  // AL 11-23-97: let a joystick button press commit
210  if ( joy_down_count(0) || joy_down_count(1) ) {
211  Commit_pressed = 1;
212  }
213 */
214 
215 }
216 
217 // -------------------------------------------------------------------
218 // common_redraw_pressed_buttons()
219 //
220 // Redraw any common buttons that are pressed down. This function is needed
221 // since we sometimes need to draw pressed buttons last to ensure the entire
222 // button gets drawn (and not overlapped by other buttons)
223 //
225 {
226  int i;
227  UI_BUTTON *b;
228 
229  for ( i = 0; i < NUM_COMMON_BUTTONS; i++ ) {
230  b = &Common_buttons[Current_screen-1][gr_screen.res][i].button;
231  if ( b->button_down() ) {
232  b->draw_forced(2);
233  }
234  }
235 }
236 
238 {
239  UI_BUTTON *b;
240  int i;
241 
242  for ( i = 0; i < NUM_COMMON_BUTTONS; i++ ) {
243  b = &Common_buttons[Current_screen-1][gr_screen.res][i].button;
244  b->set_bmaps(Common_buttons[Current_screen-1][gr_screen.res][i].filename);
245  }
246 }
247 
249 {
250  UI_BUTTON *b;
251  int i;
252 
253  for ( i = 0; i < NUM_COMMON_BUTTONS; i++ ) {
254  b = &Common_buttons[Current_screen-1][gr_screen.res][i].button;
255  b->create( ui_window, "", Common_buttons[Current_screen-1][gr_screen.res][i].x, Common_buttons[Current_screen-1][gr_screen.res][i].y, 60, 30, 0, 1);
256  // set up callback for when a mouse first goes over a button
258  b->set_bmaps(Common_buttons[Current_screen-1][gr_screen.res][i].filename);
259  b->link_hotspot(Common_buttons[Current_screen-1][gr_screen.res][i].hotspot);
260  }
261 
262  // add some text
264  ui_window->add_XSTR("Ship Selection", 1067, Common_buttons[Current_screen-1][gr_screen.res][COMMON_SS_BUTTON].xt, Common_buttons[Current_screen-1][gr_screen.res][COMMON_SS_BUTTON].yt, &Common_buttons[Current_screen-1][gr_screen.res][COMMON_SS_BUTTON].button, UI_XSTR_COLOR_GREEN);
265  ui_window->add_XSTR("Weapon Loadout", 1068, Common_buttons[Current_screen-1][gr_screen.res][COMMON_WEAPON_BUTTON].xt, Common_buttons[Current_screen-1][gr_screen.res][COMMON_WEAPON_BUTTON].yt, &Common_buttons[Current_screen-1][gr_screen.res][COMMON_WEAPON_BUTTON].button, UI_XSTR_COLOR_GREEN);
266  ui_window->add_XSTR("Commit", 1062, Common_buttons[Current_screen-1][gr_screen.res][COMMON_COMMIT_BUTTON].xt, Common_buttons[Current_screen-1][gr_screen.res][COMMON_COMMIT_BUTTON].yt, &Common_buttons[Current_screen-1][gr_screen.res][COMMON_COMMIT_BUTTON].button, UI_XSTR_COLOR_PINK);
267  ui_window->add_XSTR("Help", 928, Common_buttons[Current_screen-1][gr_screen.res][COMMON_HELP_BUTTON].xt, Common_buttons[Current_screen-1][gr_screen.res][COMMON_HELP_BUTTON].yt, &Common_buttons[Current_screen-1][gr_screen.res][COMMON_HELP_BUTTON].button, UI_XSTR_COLOR_GREEN);
269 
271 
275 
276  // for scramble or training missions, disable the ship/weapon selection regions
277  if ( brief_only_allow_briefing() ) {
280  }
281 }
282 
283 // Try to load background bitmaps as appropriate
284 int mission_ui_background_load(const char *custom_background, const char *single_background, const char *multi_background)
285 {
286  int background_bitmap = -1;
287 
288  if (custom_background && (*custom_background != '\0'))
289  {
290  background_bitmap = bm_load(custom_background);
291  if (background_bitmap < 0)
292  mprintf(("Failed to load custom background bitmap %s!\n", custom_background));
293  }
294 
295  // if special background failed to load, or if no special background was supplied, load the standard bitmap
296  if (background_bitmap < 0)
297  {
298  if (multi_background && (Game_mode & GM_MULTIPLAYER))
299  background_bitmap = bm_load(multi_background);
300  else
301  background_bitmap = bm_load(single_background);
302  }
303 
304  // return what we've got
305  return background_bitmap;
306 }
307 
308 void set_active_ui(UI_WINDOW *ui_window)
309 {
310  Active_ui_window = ui_window;
311 }
312 
313 void common_music_init(int score_index)
314 {
316  return;
317  }
318 
319  if ( score_index >= NUM_SCORES ) {
320  Int3();
321  return;
322  }
323 
324  if ( Mission_music[score_index] < 0 ) {
325  if ( Num_music_files > 0 ) {
326  Mission_music[score_index] = 0;
327  nprintf(("Sound","No briefing music is selected, so play first briefing track: %s\n",Spooled_music[Mission_music[score_index]].name));
328  } else {
329  return;
330  }
331  }
332 
334  // Use this id to trigger the start of music playing on the briefing screen
336 }
337 
339 {
341  return;
342  }
343 
344  // Use this id to trigger the start of music playing on the briefing screen
348  }
349 }
350 
352 {
354  return;
355  }
356 
357  if ( Num_music_files <= 0 )
358  return;
359 
360  briefing_stop_music(true);
361 }
362 
363 int common_num_cutscenes_valid(int movie_type)
364 {
365  int num_valid_cutscenes = 0;
366 
367  for (uint i = 0; i < The_mission.cutscenes.size(); i++) {
368  if (movie_type == The_mission.cutscenes[i].type) {
369  if (!eval_sexp( The_mission.cutscenes[i].formula )) {
370  continue;
371  }
372 
373  num_valid_cutscenes++;
374  }
375  }
376 
377  return num_valid_cutscenes;
378 }
379 
380 void common_maybe_play_cutscene(int movie_type, bool restart_music, int music)
381 {
382  bool music_off = false;
383 
384  for (uint i = 0; i < The_mission.cutscenes.size(); i++) {
385  if (movie_type == The_mission.cutscenes[i].type) {
386  if (!eval_sexp( The_mission.cutscenes[i].formula )) {
387  continue;
388  }
389 
390  if ( strlen(The_mission.cutscenes[i].filename) ) {
392  music_off = true;
393  movie_play( The_mission.cutscenes[i].filename ); //Play the movie!
395  }
396  }
397  }
398 
399  if (music_off && restart_music) {
400  common_music_init(music);
401  }
402 }
403 
404 // function that sets the current palette to the interface palette. This function
405 // needs to be followed by common_free_interface_palette() to restore the game palette.
407 {
408  static char buf[MAX_FILENAME_LEN + 1] = {0};
409 
410  if (!filename)
411  filename = NOX("palette01");
412 
413  Assert(strlen(filename) <= MAX_FILENAME_LEN);
414  if ( (InterfacePaletteBitmap != -1) && !stricmp(filename, buf) )
415  return; // already set to this palette
416 
417  strcpy_s(buf, filename);
418 
419  // unload the interface bitmap from memory
420  if (InterfacePaletteBitmap != -1) {
421  bm_release(InterfacePaletteBitmap);
422  InterfacePaletteBitmap = -1;
423  }
424 
425  // ugh - we don't need this anymore
426  /*
427  InterfacePaletteBitmap = bm_load(filename);
428  if (InterfacePaletteBitmap < 0) {
429  Error(LOCATION, "Could not load in \"%s\"!", filename);
430  }
431  */
432 
433 #ifndef HARDWARE_ONLY
434  palette_use_bm_palette(InterfacePaletteBitmap);
435 #endif
436 }
437 
438 // release the interface palette .pcx file, and restore the game palette
440 {
441  // unload the interface bitmap from memory
442  if (InterfacePaletteBitmap != -1) {
443  bm_release(InterfacePaletteBitmap);
444  InterfacePaletteBitmap = -1;
445  }
446 
447  // restore the normal game palette
449 }
450 
451 // Init timers used for flashing buttons
453 {
455  Flash_toggle = 1;
456  Flash_bright = 0;
457 }
458 
459 // determine if we should draw a button as bright
461 {
465  Flash_bright ^= 1;
466  }
467  }
468 
469  return Flash_bright;
470 }
471 
472 // set the necessary pointers
474 {
475  Assert( (team >= 0) && (team < MAX_TVT_TEAMS) );
476 
477  Wss_slots = Wss_slots_teams[team];
480 
481  ss_set_team_pointers(team);
482  wl_set_team_pointers(team);
483 }
484 
485 // reset the necessary pointers to defaults
487 {
490 
491  // these are done last so that we can make use of the Assert()'s in the above
492  // functions to make sure the screens are exited and this is safe
493  Wss_slots = NULL;
494  Ss_pool = NULL;
495  Wl_pool = NULL;
496 }
497 
498 // common_select_init() will load in animations and bitmaps that are common to the
499 // briefing/ship select/weapon select screens. The global Common_select_inited is set
500 // after this function is called once, and is only cleared when common_select_close()
501 // is called. This prevents multiple loadings of animations/bitmaps.
502 //
503 // This function also sets the palette based on the file palette01.pcx
505 {
506  if ( Common_select_inited ) {
507  nprintf(("Alan","common_select_init() returning without doing anything\n"));
508  return;
509  }
510 
511  nprintf(("Alan","entering common_select_init()\n"));
512 
513  // No anims are playing
514  Background_playing = 0;
515  Background_anim = NULL;
516 
518 
519  // load in the icons for the wing slots
520  load_wing_icons(NOX("iconwing01"));
521 
523 
524  Commit_pressed = 0;
525 
527 
528  // this handles the case where the player played a multiplayer game but now is in single player (in one instance
529  // of FreeSpace)
530  if(!(Game_mode & GM_MULTIPLAYER)){
531  chatbox_close();
532  }
533 
534  // get the value of the team
535  Common_team = 0; // assume the first team -- we'll change this value if we need to
536 
537  if ( (Game_mode & GM_MULTIPLAYER) && IS_MISSION_MULTI_TEAMS )
539 
541 
545 
546  if ( Game_mode & GM_MULTIPLAYER ) {
548  }
549 
550  // restore loadout from Player_loadout if this is the same mission as the one previously played
551  if ( !(Game_mode & GM_MULTIPLAYER) ) {
552  if ( !stricmp(Player_loadout.filename, Game_current_mission_filename) ) {
556  }
557  }
558 
560 
561  Drop_icon_mflag = 0;
562  Drop_on_wing_mflag = 0;
563 
564  //init colors
565  gr_init_alphacolor(&Icon_colors[ICON_FRAME_NORMAL], 32, 128, 128, 255);
566  gr_init_alphacolor(&Icon_colors[ICON_FRAME_HOT], 48, 160, 160, 255);
567  gr_init_alphacolor(&Icon_colors[ICON_FRAME_SELECTED], 64, 192, 192, 255);
568  gr_init_alphacolor(&Icon_colors[ICON_FRAME_PLAYER], 192, 128, 64, 255);
569  gr_init_alphacolor(&Icon_colors[ICON_FRAME_DISABLED], 175, 175, 175, 255);
570  gr_init_alphacolor(&Icon_colors[ICON_FRAME_DISABLED_HIGH], 100, 100, 100, 255);
571  //init shaders
572  gr_create_shader(&Icon_shaders[ICON_FRAME_NORMAL], 32, 128, 128, 255);
573  gr_create_shader(&Icon_shaders[ICON_FRAME_HOT], 48, 160, 160, 255);
574  gr_create_shader(&Icon_shaders[ICON_FRAME_SELECTED], 64, 192, 192, 255);
575  gr_create_shader(&Icon_shaders[ICON_FRAME_PLAYER], 192, 128, 64, 255);
576  gr_create_shader(&Icon_shaders[ICON_FRAME_DISABLED], 175, 175, 175, 255);
577  gr_create_shader(&Icon_shaders[ICON_FRAME_DISABLED_HIGH], 100, 100, 100, 255);
578 }
579 
581 {
582  int i;
583  UI_BUTTON *b;
584 
585  for ( i = 0; i < NUM_COMMON_BUTTONS; i++ ) {
586  b = &Common_buttons[Current_screen-1][gr_screen.res][i].button;
587  b->reset_status();
588  }
589 
590  switch(Current_screen) {
591  case ON_BRIEFING_SELECT:
593  break;
594  case ON_SHIP_SELECT:
596  break;
597  case ON_WEAPON_SELECT:
599  break;
600  }
601 }
602 
603 // common_select_do() is called once per loop in the interface screens and is used
604 // for drawing and changing the common animations and blitting common bitmaps.
605 int common_select_do(float frametime)
606 {
607  int k, new_k;
608 
609 
611  Common_buttons[0][gr_screen.res][COMMON_HELP_BUTTON].button.reset_status();
612  Common_buttons[1][gr_screen.res][COMMON_HELP_BUTTON].button.reset_status();
613  Common_buttons[2][gr_screen.res][COMMON_HELP_BUTTON].button.reset_status();
614  Active_ui_window->set_ignore_gadgets(1);
615  } else {
616  Active_ui_window->set_ignore_gadgets(0);
617  }
618 
619  k = chatbox_process();
620 
621  if ( Game_mode & GM_NORMAL ) {
622  new_k = Active_ui_window->process(k);
623  } else {
624  new_k = Active_ui_window->process(k, 0);
625  }
626 
627  if ( (k > 0) || (new_k > 0) || B1_JUST_RELEASED ) {
632  Active_ui_window->set_ignore_gadgets(0);
633  k = 0;
634  new_k = 0;
635  }
636  }
637 
638  // test for mouse buttons, must be done after Active_ui_window->process()
639  // has been called to work properly
640  //
641  Drop_icon_mflag = 0;
642  Drop_on_wing_mflag = 0;
645 
646  // if the left mouse button was released...
647  if ( B1_RELEASED ) {
648  Drop_icon_mflag = 1;
649  Drop_on_wing_mflag = 1;
650  }
651 
652  // if the left mouse button was pressed...
653  if ( B1_PRESSED ) {
655  }
656 
657  // basically a "click", only check for the click here to avoid action-on-over on briefing map
658  if ( B1_JUST_PRESSED ) {
660  }
661 
662  // reset timers for flashing buttons if key pressed
663  if ( (k>0) || (new_k>0) ) {
665  }
666 
667  common_music_do();
668 
669  /*
670  if ( Background_playing ) {
671 
672  if ( Background_anim_instance->frame_num == BUTTON_SLIDE_IN_FRAME ) {
673  gamesnd_play_iface(SND_BTN_SLIDE);
674  }
675 
676  if ( Background_anim_instance->frame_num == Background_anim_instance->stop_at ) {
677  // Free up the big honking background animation, since we won't be playing it again
678  anim_release_render_instance(Background_anim_instance);
679  anim_free(Background_anim);
680 
681  Background_playing = 0;
682  Current_screen = Next_screen = ON_BRIEFING_SELECT;
683  }
684  }
685  */
686 
687  if ( Current_screen != Next_screen ) {
688  switch( Next_screen ) {
689  case ON_BRIEFING_SELECT:
691  break;
692 
693  case ON_SHIP_SELECT:
694  // go to the specialized multiplayer team/ship select screen
697  }
698  // go to the normal ship select screen
699  else {
701  }
702  break;
703 
704  case ON_WEAPON_SELECT:
705  if ( !wss_slots_all_empty() ) {
707  } else {
709  }
710  break;
711  } // end switch
712  }
713 
714  return new_k;
715 }
716 
717 // -------------------------------------------------------------------------------------
718 // common_render()
719 //
720 void common_render(float frametime)
721 {
722  if ( !Background_playing ) {
725  gr_bitmap(0, 0, GR_RESIZE_MENU);
726  }
727 
728  anim_render_all(0, frametime);
729  anim_render_all(ON_SHIP_SELECT, frametime);
730 }
731 
732 // -------------------------------------------------------------------------------------
733 // common_render_selected_screen_button()
734 //
735 // A very ugly piece of special purpose code. This is used to draw the pressed button
736 // frame for whatever stage of the briefing/ship select/weapons loadout we are on.
737 //
739 {
740  Common_buttons[Next_screen-1][gr_screen.res][Next_screen-1].button.draw_forced(2);
741 }
742 
743 // -------------------------------------------------------------------------------------
744 // common_button_do() do the button action for the specified pressed button
745 //
747 {
748  if ( i == COMMON_COMMIT_BUTTON ) {
749  Commit_pressed = 1;
750  return;
751  }
752 
753  if ( Background_playing )
754  return;
755 
756  switch ( i ) {
757 
762  }
763  break;
764 
766  if ( Current_screen != ON_WEAPON_SELECT ) {
767  if ( !wss_slots_all_empty() ) {
770  } else {
772  }
773  }
774  break;
775 
776  case COMMON_SS_BUTTON:
777  if ( Current_screen != ON_SHIP_SELECT ) {
780  }
781  break;
782 
786  break;
787 
788  case COMMON_HELP_BUTTON:
791  break;
792 
793  } // end switch
794 }
795 
796 // common_check_keys() will check for keypresses common to all the interface screens.
797 void common_check_keys(int k)
798 {
799  switch (k) {
800 
801  case KEY_ESC: {
802 
804  if ( brief_get_closeup_icon() != NULL ) {
806  break;
807  }
808  }
809 
810  // prompt the host of a multiplayer game
813  } else {
814  // go through the single player quit process
815  // return to the main menu
816 /*
817  int return_to_menu, pf_flags;
818  pf_flags = PF_USE_AFFIRMATIVE_ICON|PF_USE_NEGATIVE_ICON;
819  return_to_menu = popup(pf_flags, 2, POPUP_NO, POPUP_YES, XSTR( "Do you want to return to the Main Hall?\n(Your campaign position will be saved)", -1));
820  if ( return_to_menu == 1 ) {
821  gameseq_post_event(GS_EVENT_MAIN_MENU);
822  }
823 */
825  }
826  break;
827  }
828 
829  case KEY_CTRLED + KEY_ENTER:
830  Commit_pressed = 1;
831  break;
832 
833  case KEY_B:
836  }
837  break;
838 
839  case KEY_W:
840  if ( brief_only_allow_briefing() ) {
842  break;
843  }
844 
846  if ( !wss_slots_all_empty() ) {
848  } else {
850  }
851  }
852 
853  break;
854 
855  case KEY_S:
856 
857  if ( brief_only_allow_briefing() ) {
859  break;
860  }
861 
864  }
865 
866  break;
867 
868  case KEY_SHIFTED+KEY_TAB:
869 
870  if ( brief_only_allow_briefing() ) {
872  break;
873  }
874 
875  if ( !Background_playing ) {
876  switch ( Current_screen ) {
877  case ON_BRIEFING_SELECT:
878  if ( !wss_slots_all_empty() ) {
880  } else {
882  }
883  break;
884 
885  case ON_SHIP_SELECT:
887  break;
888 
889  case ON_WEAPON_SELECT:
891  break;
892  default:
893  Int3();
894  break;
895  } // end switch
896  }
897 
898  break;
899 
900  case KEY_TAB:
901 
902  if ( brief_only_allow_briefing() ) {
904  break;
905  }
906 
907  if ( !Background_playing ) {
908  switch ( Current_screen ) {
909  case ON_BRIEFING_SELECT:
911  break;
912 
913  case ON_SHIP_SELECT:
914  if ( !wss_slots_all_empty() ) {
916  } else {
918  }
919  break;
920 
921  case ON_WEAPON_SELECT:
923  break;
924  default:
925  Int3();
926  break;
927  } // end switch
928  }
929 
930  break;
931 
932  case KEY_P:
933  if ( Anim_paused )
934  Anim_paused = 0;
935  else
936  Anim_paused = 1;
937  break;
938  } // end switch
939 }
940 
941 // common_select_close() will release the memory for animations and bitmaps that
942 // were loaded in common_select_init(). This function will abort if the Common_select_inited
943 // flag is not set. The last thing common_select_close() does in clear the Common_select_inited
944 // flag.
945 //
946 // weapon_select_close() and ship_select_close() are both called, since common_select_close()
947 // is the function that is called the interface screens are finally exited.
949 {
950  if ( !Common_select_inited ) {
951  nprintf(("Alan","common_select_close() returning without doing anything\n"));
952  return;
953  }
954 
955  nprintf(("Alan","entering common_select_close()\n"));
956 
957  // catch open anims that weapon_select_init_team() opened when not in weapon_select - taylor
958  // *** not the same as weapon_select_close() ***
960 
962 
964  multi_ts_close();
965  }
966 
968  brief_close();
969 
971 
972  // release the bitmpas that were previously extracted from anim files
974 
975  // Release any instances that may still exist
977 
978  // free the anim's that were loaded into memory
979  /*
980  if ( Background_anim ) {
981  anim_free(Background_anim);
982  Background_anim = NULL;
983  }
984  */
985 
987 
989 
991 }
992 
993 // ------------------------------------------------------------------------
994 // load_wing_icons() creates the bitmaps for wing icons
995 //
997 {
998  int first_frame, num_frames;
999 
1000  first_frame = bm_load_animation(filename, &num_frames);
1001  if ( first_frame == -1 ) {
1002  Error(LOCATION, "Could not load icons from %s\n", filename);
1003  return;
1004  }
1005 
1006  Wing_slot_disabled_bitmap = first_frame;
1007  Wing_slot_empty_bitmap = first_frame + 1;
1008 // Wing_slot_player_empty_bitmap = first_frame + 2;
1009 }
1010 
1011 // ------------------------------------------------------------------------
1012 // common_scroll_up_pressed()
1013 //
1014 int common_scroll_up_pressed(int *start, int size, int max_show)
1015 {
1016  // check if we even need to scroll at all
1017  if ( size <= max_show ) {
1018  return 0;
1019  }
1020 
1021  if ( (size - *start) > max_show ) {
1022  *start += 1;
1023  return 1;
1024  }
1025  return 0;
1026 }
1027 
1028 // ------------------------------------------------------------------------
1029 // common_scroll_down_pressed()
1030 //
1031 int common_scroll_down_pressed(int *start, int size, int max_show)
1032 {
1033  // check if we even need to scroll at all
1034  if ( size <= max_show ) {
1035  return 0;
1036  }
1037 
1038  if ( *start > 0 ) {
1039  *start -= 1;
1040  return 1;
1041  }
1042  return 0;
1043 }
1044 
1045 // NEWSTUFF BEGIN
1046 
1047 // save ship selection loadout to the Player_loadout struct
1049 {
1050  int i,j;
1051 
1052  Assert( (Ss_pool != NULL) && (Wl_pool != NULL) && (Wss_slots != NULL) );
1053 
1054  // save the ship pool
1055  for ( i = 0; i < MAX_SHIP_CLASSES; i++ ) {
1056  Player_loadout.ship_pool[i] = Ss_pool[i];
1057  }
1058 
1059  // save the weapons pool
1060  for ( i = 0; i < MAX_WEAPON_TYPES; i++ ) {
1061  Player_loadout.weapon_pool[i] = Wl_pool[i];
1062  }
1063 
1064  // save the ship class / weapons for each slot
1065  for ( i = 0; i < MAX_WSS_SLOTS; i++ ) {
1066  Player_loadout.unit_data[i].ship_class = Wss_slots[i].ship_class;
1067 
1068  for ( j = 0; j < MAX_SHIP_WEAPONS; j++ ) {
1069  Player_loadout.unit_data[i].wep[j] = Wss_slots[i].wep[j];
1070  Player_loadout.unit_data[i].wep_count[j] = Wss_slots[i].wep_count[j];
1071  }
1072  }
1073 }
1074 
1075 // restore ship/weapons loadout from the Player_loadout struct
1077 {
1078  int i,j;
1079  wss_unit *slot;
1080 
1081  Assert( (Ss_pool != NULL) && (Wl_pool != NULL) && (Wss_slots != NULL) );
1082 
1083  // only restore if mission hasn't changed
1084  if ( stricmp(Player_loadout.last_modified, The_mission.modified) ) {
1085  return;
1086  }
1087 
1088  // first we generate a pool of ships and weapons used the last time this mission was played. We also generate a pool of what is
1089  // available in this mission.
1090  int last_loadout_ships[MAX_SHIP_CLASSES];
1091  int this_loadout_ships[MAX_SHIP_CLASSES];
1092 
1093  int last_loadout_weapons[MAX_WEAPON_TYPES];
1094  int this_loadout_weapons[MAX_WEAPON_TYPES];
1095 
1096  // zero all pools
1097  for (i = 0; i < MAX_SHIP_CLASSES; i++) {
1098  last_loadout_ships[i] = 0;
1099  this_loadout_ships[i] = 0;
1100  }
1101  for (i = 0; i < MAX_WEAPON_TYPES; i++) {
1102  last_loadout_weapons[i] = 0;
1103  this_loadout_weapons[i] = 0;
1104  }
1105 
1106  // record the ship classes / weapons used last time
1107  for ( i = 0; i < MAX_WSS_SLOTS; i++ ) {
1108  slot = &Player_loadout.unit_data[i];
1109  if ((slot->ship_class >= 0) && (slot->ship_class < static_cast<int>(Ship_info.size()))) {
1110  ++last_loadout_ships[slot->ship_class];
1111 
1112  for ( j = 0; j < MAX_SHIP_WEAPONS; j++ ) {
1113  if ((slot->wep[j] >= 0) && (slot->wep[j] < Num_weapon_types)) {
1114  last_loadout_weapons[slot->wep[j]] += slot->wep_count[j];
1115  }
1116  }
1117  }
1118  }
1119 
1120  // record the ships classes / weapons used by the player and wingmen. We don't include the amount in the pools yet
1121  for ( i = 0; i < MAX_WSS_SLOTS; i++ ) {
1122  if ((Wss_slots[i].ship_class >= 0) && (Wss_slots[i].ship_class < static_cast<int>(Ship_info.size()))) {
1123  ++this_loadout_ships[Wss_slots[i].ship_class];
1124 
1125  for ( j = 0; j < MAX_SHIP_WEAPONS; j++ ) {
1126  if ((Wss_slots[i].wep[j] >= 0) && (Wss_slots[i].wep[j] < Num_weapon_types)) {
1127  this_loadout_weapons[Wss_slots[i].wep[j]] += Wss_slots[i].wep_count[j];
1128  }
1129  }
1130  }
1131  }
1132 
1133  // now compare the two, adding in what was left in the pools. If there are less of a ship or weapon class in the mission now
1134  // than there were last time, we can't restore and must abort.
1135  for (i = 0; i < static_cast<int>(Ship_info.size()); i++) {
1136  if (Ss_pool[i] >= 1) {
1137  this_loadout_ships[i] += Ss_pool[i];
1138  }
1139  if ( this_loadout_ships[i] < last_loadout_ships[i]) {
1140  return;
1141  }
1142  }
1143 
1144  for (i = 0; i < Num_weapon_types; i++) {
1145  if (Wl_pool[i] >= 1) {
1146  this_loadout_weapons[i] += Wl_pool[i];
1147  }
1148  if ( this_loadout_weapons[i] < last_loadout_weapons[i]) {
1149  return;
1150  }
1151  }
1152 
1153  // go through the slots and restore the previous runthrough's loadout. Also remove that ship from total of ships in this mission
1154  for ( i = 0; i < MAX_WSS_SLOTS; i++ ) {
1155  slot = &Player_loadout.unit_data[i];
1156 
1157  if ((slot->ship_class >= 0) && (slot->ship_class < static_cast<int>(Ship_info.size()))) {
1158  --this_loadout_ships[slot->ship_class];
1159  Assertion((this_loadout_ships[slot->ship_class] >= 0), "Attempting to restore the previous missions loadout has resulted in an invalid number of ships available");
1160 
1161  }
1162  // restore the ship class for each slot
1163  Wss_slots[i].ship_class = slot->ship_class;
1164 
1165  for ( j = 0; j < MAX_SHIP_WEAPONS; j++ ) {
1166  if ((slot->ship_class >= 0) && (slot->wep[j] >= 0) && (slot->wep[j] < Num_weapon_types)) {
1167  this_loadout_weapons[slot->wep[j]] -= slot->wep_count[j];
1168  Assertion((this_loadout_weapons[slot->wep[j]] >= 0), "Attempting to restore the previous missions loadout has resulted in an invalid number of weapons available");
1169  }
1170 
1171  Wss_slots[i].wep[j]= slot->wep[j];
1172  Wss_slots[i].wep_count[j] = slot->wep_count[j];
1173  }
1174  }
1175 
1176  // restore the ship pool
1177  for ( i = 0; i < static_cast<int>(Ship_info.size()); i++ ) {
1178  Ss_pool[i] = this_loadout_ships[i];
1179  }
1180 
1181  // restore the weapons pool
1182  for ( i = 0; i < Num_weapon_types; i++ ) {
1183  Wl_pool[i] = this_loadout_weapons[i];
1184  }
1185 }
1186 
1187 // Do a direct restore of the Player_loadout ship/weapon data to the wings
1189 {
1190  int i, j;
1191  wing *wp;
1192  wss_unit *slot;
1193 
1194  // only restore if mission hasn't changed
1195  if ( stricmp(Player_loadout.last_modified, The_mission.modified) ) {
1196  return;
1197  }
1198 
1199  // niffiwan: if Starting_wings[] has missing wings, Player_loadout.unit_data
1200  // skips the missing wings. Use a new variable to track the number of valid
1201  // wings in Starting_wings[], otherwise mission can crash on restart
1202  int valid_wing_index = -1;
1203 
1204  for ( i = 0; i < MAX_WING_BLOCKS; i++ ) {
1205 
1206  if ( Starting_wings[i] < 0 )
1207  continue;
1208 
1209  valid_wing_index++;
1210  wp = &Wings[Starting_wings[i]];
1211 
1212  // If this wing is still on the arrival list, then update the parse objects
1213  if ( wp->ship_index[0] == -1 ) {
1214  p_object *p_objp;
1215  j=0;
1216  for ( p_objp = GET_FIRST(&Ship_arrival_list); p_objp != END_OF_LIST(&Ship_arrival_list); p_objp = GET_NEXT(p_objp) ) {
1217  if ( p_objp->wingnum == WING_INDEX(wp) ) {
1218  // niffiwan: don't overrun the array
1219  if (j >= MAX_WING_SLOTS) {
1220  Warning(LOCATION, "Starting Wing '%s' has more than 'MAX_WING_SLOTS' ships\n", Starting_wing_names[i]);
1221  break;
1222  }
1223  slot = &Player_loadout.unit_data[valid_wing_index*MAX_WING_SLOTS+j];
1224  p_objp->ship_class = slot->ship_class;
1225  wl_update_parse_object_weapons(p_objp, slot);
1226  j++;
1227  }
1228  }
1229  } else {
1230  int k;
1231  int cleanup_ship_index[MAX_WING_SLOTS];
1232  ship *shipp;
1233 
1234  for ( k = 0; k < MAX_WING_SLOTS; k++ ) {
1235  cleanup_ship_index[k] = -1;
1236  }
1237 
1238  // This wing is already created, so directly update the ships
1239  for ( j = 0; j < MAX_WING_SLOTS; j++ ) {
1240  if ( wp->ship_index[j] == -1 ) { // if this is an invalid ship, move on
1241  continue;
1242  }
1243 
1244  slot = &Player_loadout.unit_data[valid_wing_index*MAX_WING_SLOTS+j];
1245  shipp = &Ships[wp->ship_index[j]];
1246  if ( shipp->ship_info_index != slot->ship_class ) {
1247 
1248  if ( slot->ship_class == -1 ) {
1249  cleanup_ship_index[j] = wp->ship_index[j];
1251  obj_delete(shipp->objnum);
1253  continue;
1254  } else {
1255  change_ship_type(wp->ship_index[j], slot->ship_class);
1256  }
1257  }
1258  wl_bash_ship_weapons(&Ships[wp->ship_index[j]].weapons, slot);
1259  }
1260 
1261  for ( k = 0; k < MAX_WING_SLOTS; k++ ) {
1262  if ( cleanup_ship_index[k] != -1 ) {
1263  ship_wing_cleanup( cleanup_ship_index[k], wp );
1264  }
1265  }
1266 
1267  }
1268  } // end for
1269 }
1271 {
1272  int i;
1273 
1274  Assert( Wss_slots != NULL );
1275 
1276  for ( i = 0; i < MAX_WSS_SLOTS; i++ ) {
1277  if ( Wss_slots[i].ship_class >= 0 )
1278  break;
1279  }
1280 
1281  if ( i == MAX_WSS_SLOTS )
1282  return 1;
1283  else
1284  return 0;
1285 }
1286 
1287 // determine the mode (WSS_...) based on slot/list index values
1288 int wss_get_mode(int from_slot, int from_list, int to_slot, int to_list, int wl_ship_slot)
1289 {
1290  int mode, to_slot_empty=0;
1291 
1292  Assert( Wss_slots != NULL );
1293 
1294  if ( wl_ship_slot >= 0 ) {
1295  // weapons loadout
1296  if ( to_slot >= 0 ) {
1297  if ( Wss_slots[wl_ship_slot].wep_count[to_slot] == 0 ) {
1298  to_slot_empty = 1;
1299  }
1300  }
1301  } else {
1302  // ship select
1303  if ( to_slot >= 0 ) {
1304  if ( Wss_slots[to_slot].ship_class == -1 ){
1305  to_slot_empty = 1;
1306  }
1307  }
1308  }
1309 
1310  // determine mode
1311  if ( from_slot >= 0 && to_slot >= 0 ) {
1312  mode = WSS_SWAP_SLOT_SLOT;
1313  } else if ( from_slot >= 0 && to_list >= 0 ) {
1314  mode = WSS_DUMP_TO_LIST;
1315  } else if ( (from_list >= 0) && (to_slot >= 0) && (to_slot_empty) ) {
1316  mode = WSS_GRAB_FROM_LIST;
1317  } else if ( (from_list >= 0) && (to_slot >= 0) && (!to_slot_empty) ) {
1318  mode = WSS_SWAP_LIST_SLOT;
1319  } else {
1320  mode = -1; // no changes required
1321  }
1322 
1323  return mode;
1324 }
1325 
1326 // store all the unit data and pool data
1327 int store_wss_data(ubyte *block, int max_size, int sound,int player_index)
1328 {
1329  int j, i,offset=0;
1330  short player_id;
1331  short ishort;
1332 
1333  // this function assumes that the data is going to be used over the network
1334  // so make a non-network version of this function if needed
1336  Assert( (Ss_pool != NULL) && (Wl_pool != NULL) && (Wss_slots != NULL) );
1337 
1338  if ( !(Game_mode & GM_MULTIPLAYER) )
1339  return 0;
1340 
1341 
1342  // write the ship pool
1343  for ( i = 0; i < static_cast<int>(Ship_info.size()); i++ ) {
1344  if ( Ss_pool[i] > 0 ) {
1345  block[offset++] = (ubyte)i;
1346  Assert( Ss_pool[i] < UCHAR_MAX );
1347 
1348  // take care of sign issues
1349  if(Ss_pool[i] == -1){
1350  block[offset++] = 0xff;
1351  } else {
1352  block[offset++] = (ubyte)Ss_pool[i];
1353  }
1354  }
1355  }
1356 
1357  block[offset++] = 0xff; // signals start of weapons pool
1358 
1359  // write the weapon pool
1360  for ( i = 0; i < Num_weapon_types; i++ ) {
1361  if ( Wl_pool[i] > 0 ) {
1362  block[offset++] = (ubyte)i;
1363  ishort = INTEL_SHORT( (short)Wl_pool[i] );
1364  memcpy(block+offset, &ishort, sizeof(short));
1365  offset += sizeof(short);
1366  }
1367  }
1368 
1369  // write the unit data
1370 
1371  block[offset++] = 0xff; // signals start of unit data
1372 
1373  for ( i=0; i<MAX_WSS_SLOTS; i++ ) {
1374  Assert( Wss_slots[i].ship_class < UCHAR_MAX );
1375  if(Wss_slots[i].ship_class == -1){
1376  block[offset++] = 0xff;
1377  } else {
1378  block[offset++] = (ubyte)(Wss_slots[i].ship_class);
1379  }
1380  for ( j = 0; j < MAX_SHIP_WEAPONS; j++ ) {
1381  // take care of sign issues
1382  Assert( Wss_slots[i].wep[j] < UCHAR_MAX );
1383  if(Wss_slots[i].wep[j] == -1){
1384  block[offset++] = 0xff;
1385  } else {
1386  block[offset++] = (ubyte)(Wss_slots[i].wep[j]);
1387  }
1388 
1389  Assert( Wss_slots[i].wep_count[j] < SHRT_MAX );
1390  ishort = INTEL_SHORT( (short)Wss_slots[i].wep_count[j] );
1391 
1392  memcpy(&(block[offset]), &(ishort), sizeof(short) );
1393  offset += sizeof(short);
1394  }
1395 
1396  // mwa -- old way below -- too much space
1397  //memcpy(block+offset, &Wss_slots[i], sizeof(wss_unit));
1398  //offset += sizeof(wss_unit);
1399  }
1400 
1401  // any sound index
1402  if(sound == -1){
1403  block[offset++] = 0xff;
1404  } else {
1405  block[offset++] = (ubyte)sound;
1406  }
1407 
1408  // add a netplayer address to identify who should play the sound
1409  player_id = -1;
1410 
1411  if(player_index != -1){
1412  player_id = Net_players[player_index].player_id;
1413  }
1414 
1415  player_id = INTEL_SHORT( player_id );
1416  memcpy(block+offset,&player_id,sizeof(player_id));
1417  offset += sizeof(player_id);
1418 
1419  Assert( offset < max_size );
1420  return offset;
1421 }
1422 
1424 {
1425  int i, j, sanity, offset=0;
1426  ubyte b1, b2,sound;
1427  short ishort;
1428  short player_id;
1429 
1430  // this function assumes that the data is going to be used over the network
1431  // so make a non-network version of this function if needed
1433  Assert( (Ss_pool != NULL) && (Wl_pool != NULL) && (Wss_slots != NULL) );
1434 
1435  if ( !(Game_mode & GM_MULTIPLAYER) )
1436  return 0;
1437 
1438  // restore ship pool
1439  sanity=0;
1440  memset(Ss_pool, 0, MAX_SHIP_CLASSES*sizeof(int));
1441  for (;;) {
1442  if ( sanity++ > MAX_SHIP_CLASSES ) {
1443  Int3();
1444  break;
1445  }
1446 
1447  b1 = block[offset++];
1448  if ( b1 == 0xff ) {
1449  break;
1450  }
1451 
1452  // take care of sign issues
1453  b2 = block[offset++];
1454  if(b2 == 0xff){
1455  Ss_pool[b1] = -1;
1456  } else {
1457  Ss_pool[b1] = b2;
1458  }
1459  }
1460 
1461  // restore weapons pool
1462  sanity=0;
1463  memset(Wl_pool, 0, MAX_WEAPON_TYPES*sizeof(int));
1464  for (;;) {
1465  if ( sanity++ > MAX_WEAPON_TYPES ) {
1466  Int3();
1467  break;
1468  }
1469 
1470  b1 = block[offset++];
1471  if ( b1 == 0xff ) {
1472  break;
1473  }
1474 
1475  memcpy(&ishort, block+offset, sizeof(short));
1476  offset += sizeof(short);
1477  Wl_pool[b1] = INTEL_SHORT( ishort );
1478  }
1479 
1480  for ( i=0; i<MAX_WSS_SLOTS; i++ ) {
1481  if(block[offset] == 0xff){
1482  Wss_slots[i].ship_class = -1;
1483  } else {
1484  Wss_slots[i].ship_class = block[offset];
1485  }
1486  offset++;
1487  for ( j = 0; j < MAX_SHIP_WEAPONS; j++ ) {
1488  // take care of sign issues
1489  if(block[offset] == 0xff){
1490  Wss_slots[i].wep[j] = -1;
1491  offset++;
1492  } else {
1493  Wss_slots[i].wep[j] = (int)(block[offset++]);
1494  }
1495 
1496  memcpy( &ishort, &(block[offset]), sizeof(short) );
1497  ishort = INTEL_SHORT( ishort );
1498  Wss_slots[i].wep_count[j] = (int)ishort;
1499  offset += sizeof(short);
1500  }
1501 
1502  // mwa -- old way below
1503  //memcpy(&Wss_slots[i], block+offset, sizeof(wss_unit));
1504  //offset += sizeof(wss_unit);
1505  }
1506 
1507  // read in the sound data
1508  sound = block[offset++]; // the sound index
1509 
1510  // read in the player address
1511  memcpy(&player_id,block+offset,sizeof(player_id));
1512  player_id = INTEL_SHORT( player_id );
1513  offset += sizeof(short);
1514 
1515  // determine if I'm the guy who should be playing the sound
1516  if((Net_player != NULL) && (Net_player->player_id == player_id)){
1517  // play the sound
1518  if(sound != 0xff){
1519  gamesnd_play_iface((int)sound);
1520  }
1521  }
1522 
1523  if(!(Game_mode & GM_MULTIPLAYER)){
1525  }
1526 
1527  return offset;
1528 }
1529 
1530 void draw_model_icon(int model_id, int flags, float closeup_zoom, int x, int y, int w, int h, const ship_info *sip, int resize_mode, const vec3d *closeup_pos)
1531 {
1532  matrix object_orient = IDENTITY_MATRIX;
1533  angles rot_angles = {0.0f,0.0f,0.0f};
1534  float zoom = closeup_zoom * 2.5f;
1535 
1536  if(sip == NULL)
1537  {
1538  //Assume it's a weapon
1539  rot_angles.h = -(PI_2);
1540  }
1541  else if(sip->model_icon_angles.p != 0.0f || sip->model_icon_angles.b != 0.0f || sip->model_icon_angles.h != 0.0f)
1542  {
1543  // If non-zero model_icon_angles exists, always use that
1544  rot_angles = sip->model_icon_angles;
1545  }
1546  else if(sip->flags & SIF_SMALL_SHIP)
1547  {
1548  rot_angles.p = -(PI_2);
1549  }
1550  else if((sip->max_speed <= 0.0f) && !(sip->flags & SIF_CARGO))
1551  {
1552  //Probably an installation or Knossos
1553  rot_angles.h = PI;
1554  }
1555  else
1556  {
1557  //Probably a capship
1558  rot_angles.h = PI_2;
1559  }
1560  vm_angles_2_matrix(&object_orient, &rot_angles);
1561 
1562  gr_set_clip(x, y, w, h, resize_mode);
1563  g3_start_frame(1);
1564  if(sip != NULL)
1565  {
1567 
1568  if (!Cmdline_nohtl) {
1570  }
1571  }
1572  else
1573  {
1574  polymodel *pm = model_get(model_id);
1575  bsp_info *bs = NULL; //tehe
1576  for(int i = 0; i < pm->n_models; i++)
1577  {
1578  if(!pm->submodel[i].is_thruster)
1579  {
1580  bs = &pm->submodel[i];
1581  break;
1582  }
1583  }
1584 
1585  if(bs == NULL)
1586  {
1587  bs = &pm->submodel[0];
1588  }
1589 
1590  vec3d weap_closeup = *closeup_pos;
1591  float y_closeup;
1592  float tm_zoom = closeup_zoom;
1593 
1594  //Find the center of teh submodel
1595  weap_closeup.xyz.x = -(bs->min.xyz.z + (bs->max.xyz.z - bs->min.xyz.z)/2.0f);
1596  weap_closeup.xyz.y = -(bs->min.xyz.y + (bs->max.xyz.y - bs->min.xyz.y)/2.0f);
1597  //weap_closeup.xyz.z = (weap_closeup.xyz.x/tanf(zoom / 2.0f));
1598  weap_closeup.xyz.z = -(bs->rad/tanf(tm_zoom/2.0f));
1599 
1600  y_closeup = -(weap_closeup.xyz.y/tanf(tm_zoom / 2.0f));
1601  if(y_closeup < weap_closeup.xyz.z)
1602  {
1603  weap_closeup.xyz.z = y_closeup;
1604  }
1605  if(bs->min.xyz.x < weap_closeup.xyz.z)
1606  {
1607  weap_closeup.xyz.z = bs->min.xyz.x;
1608  }
1609  g3_set_view_matrix( &weap_closeup, &vmd_identity_matrix, tm_zoom);
1610 
1611  if (!Cmdline_nohtl) {
1612  gr_set_proj_matrix(0.5f*Proj_fov, gr_screen.clip_aspect, 0.05f, 1000.0f);
1613  }
1614  }
1615 
1616  model_render_params render_info;
1617  render_info.set_detail_level_lock(0);
1618 
1619  if (!Cmdline_nohtl) {
1621  }
1622 
1623  if(!(flags & MR_NO_LIGHTING))
1624  {
1625  light_reset();
1626  vec3d light_dir = vmd_zero_vector;
1627  light_dir.xyz.x = -0.5;
1628  light_dir.xyz.y = 2.0f;
1629  light_dir.xyz.z = -2.0f;
1630  light_add_directional(&light_dir, 0.65f, 1.0f, 1.0f, 1.0f);
1631  light_rotate_all();
1632  }
1633 
1634  Glowpoint_override = true;
1635  model_clear_instance(model_id);
1636 
1637  render_info.set_flags(flags);
1638  model_render_immediate(&render_info, model_id, &object_orient, &vmd_zero_vector);
1639  Glowpoint_override = false;
1640 
1641  if (!Cmdline_nohtl)
1642  {
1645  }
1646 
1647 
1648  g3_end_frame();
1649  gr_reset_clip();
1650 }
1651 
1652 void light_set_all_relevent();
1653 void draw_model_rotating(model_render_params *render_info, int model_id, int x1, int y1, int x2, int y2, float *rotation_buffer, vec3d *closeup_pos, float closeup_zoom, float rev_rate, int flags, int resize_mode, int effect)
1654 {
1655  //WMC - Can't draw a non-model
1656  if (model_id < 0)
1657  return;
1658 
1659  float time = (timer_get_milliseconds()-anim_timer_start)/1000.0f;
1660  angles rot_angles, view_angles;
1661  matrix model_orient;
1662 
1663  if (effect == 2) { // FS2 Effect; Phase 0 Expand scanline, Phase 1 scan the grid and wireframe, Phase 2 scan up and reveal the ship, Phase 3 tilt the camera, Phase 4 start rotating the ship
1664  // rotate the ship as much as required for this frame
1665  if (time >= 3.6f) // Phase 4
1666  *rotation_buffer += PI2 * flFrametime / rev_rate;
1667  else
1668  *rotation_buffer = PI; // No rotation before Phase 4
1669  while (*rotation_buffer > PI2){
1670  *rotation_buffer -= PI2;
1671  }
1672 
1673  view_angles.p = -PI_2;
1674 
1675  if (time >= 3.0f) { // Phase 3
1676  if (time >= 3.6f) { // done tilting
1677  view_angles.p = -0.6f;
1678  } else {
1679  view_angles.p = (PI_2-0.6f)*(time-3.0f)*1.66667f - PI_2; // Phase 3 Tilt animation
1680  }
1681  }
1682 
1683  view_angles.b = 0.0f;
1684  view_angles.h = 0.0f;
1685  vm_angles_2_matrix(&model_orient, &view_angles);
1686  rot_angles.p = 0.0f;
1687  rot_angles.b = 0.0f;
1688  rot_angles.h = *rotation_buffer;
1689  vm_rotate_matrix_by_angles(&model_orient, &rot_angles);
1690  gr_set_clip(x1, y1, x2, y2, resize_mode);
1691  vec3d wire_normal,ship_normal,plane_point;
1692 
1693  // Clip the wireframe below the scanline
1694  wire_normal.xyz.x = 0.0f;
1695  wire_normal.xyz.y = 1.0f;
1696  wire_normal.xyz.z = 0.0f;
1697 
1698  // Clip the ship above the scanline
1699  ship_normal.xyz.x = 0.0f;
1700  ship_normal.xyz.y = -1.0f;
1701  ship_normal.xyz.z = 0.0f;
1702  polymodel *pm = model_get(model_id);
1703 
1704  //Make the clipping plane
1705  float clip = -pm->rad*0.7f;
1706  if (time < 1.5f && time >= 0.5f) // Phase 1 Move down
1707  clip = pm->rad*(time-1.0f)*1.4f;
1708 
1709  if (time >= 1.5f)
1710  clip = pm->rad*(time-2.0f)*(-1.4f); // Phase 2 Move up
1711 
1712  vm_vec_scale_sub(&plane_point,&vmd_zero_vector,&wire_normal,clip);
1713 
1714  g3_start_frame(1);
1715  if ( (closeup_pos != NULL) && (vm_vec_mag(closeup_pos) > 0.0f) ) {
1716  g3_set_view_matrix(closeup_pos, &vmd_identity_matrix, closeup_zoom);
1717  } else {
1718  vec3d pos = { { { 0.0f, 0.0f, -(pm->rad * 1.5f) } } };
1719  g3_set_view_matrix(&pos, &vmd_identity_matrix, closeup_zoom);
1720  }
1721 
1724 
1725  vec3d start, stop;
1726  float size = pm->rad*0.7f;
1727  float start_scale = MIN(time,0.5f)*2.5f;
1728  float offset = size*0.5f*MIN(MAX(time-3.0f,0.0f),0.6f)*1.66667f;
1729 
1731 
1732  if (time < 0.5f) { // Do the expanding scanline in phase 0
1733  gr_set_color(0,255,0);
1734  start.xyz.x = size*start_scale;
1735  start.xyz.y = 0.0f;
1736  start.xyz.z = -clip;
1737  stop.xyz.x = -size*start_scale;
1738  stop.xyz.y = 0.0f;
1739  stop.xyz.z = -clip;
1740  g3_draw_htl_line(&start,&stop);
1741  }
1742  g3_done_instance(true);
1743 
1744  gr_zbuffer_set(GR_ZBUFF_NONE); // Turn off Depthbuffer so we don't get gridlines over the ship or a disappearing scanline
1745  Glowpoint_use_depth_buffer = false; // Since we don't have one
1746  if (time >= 0.5f) { // Phase 1 onward draw the grid
1747  int i;
1748  start.xyz.y = -offset;
1749  start.xyz.z = size+offset*0.5f;
1750  stop.xyz.y = -offset;
1751  stop.xyz.z = -size+offset*0.5f;
1752  gr_set_color(0,200,0);
1754 
1755  if (time < 1.5f) {
1756  stop.xyz.z = -clip;
1757  }
1758 
1759  for (i = -3; i < 4; i++) {
1760  start.xyz.x = stop.xyz.x = size*0.333f*i;
1761  g3_draw_htl_line(&start,&stop);
1762  }
1763 
1764  start.xyz.x = size;
1765  stop.xyz.x = -size;
1766 
1767  for (i = 3; i > -4; i--) {
1768  start.xyz.z = stop.xyz.z = size*0.333f*i+offset*0.5f;
1769  if ((time < 1.5f) && (start.xyz.z <= -clip))
1770  break;
1771  g3_draw_htl_line(&start,&stop);
1772  }
1773 
1774  g3_done_instance(true);
1775 
1776  // lighting for techroom
1777  light_reset();
1778  vec3d light_dir = vmd_zero_vector;
1779  light_dir.xyz.y = 1.0f;
1780  light_dir.xyz.x = 0.0000001f;
1781  light_add_directional(&light_dir, 0.65f, 1.0f, 1.0f, 1.0f);
1782  light_rotate_all();
1783  // lighting for techroom
1784 
1785  // render the ships
1786  model_clear_instance(model_id);
1787  render_info->set_detail_level_lock(0);
1788 
1789  gr_zbuffer_set(true);
1791  {
1794 
1795  gr_reset_clip();
1796 
1797  model_render_params shadow_render_info;
1798 
1799  shadow_render_info.set_detail_level_lock(0);
1800  shadow_render_info.set_flags(flags | MR_NO_TEXTURING | MR_NO_LIGHTING);
1801 
1802  if ( flags & MR_IS_MISSILE ) {
1803  shadows_start_render(&Eye_matrix, &Eye_position, Proj_fov, gr_screen.clip_aspect, -closeup_pos->xyz.z + pm->rad, -closeup_pos->xyz.z + pm->rad + 20.0f, -closeup_pos->xyz.z + pm->rad + 200.0f, -closeup_pos->xyz.z + pm->rad + 1000.0f);
1804  } else {
1805  shadows_start_render(&Eye_matrix, &Eye_position, Proj_fov, gr_screen.clip_aspect, -closeup_pos->xyz.z + pm->rad, -closeup_pos->xyz.z + pm->rad + 200.0f, -closeup_pos->xyz.z + pm->rad + 2000.0f, -closeup_pos->xyz.z + pm->rad + 10000.0f);
1806  }
1807 
1808  model_render_immediate(&shadow_render_info, model_id, &model_orient, &vmd_zero_vector);
1810 
1811  gr_set_clip(x1, y1, x2, y2, resize_mode);
1812 
1815  }
1816  gr_zbuffer_set(false);
1817  gr_set_color(80,49,160);
1818  render_info->set_color(80, 49, 160);
1819 
1821 
1822  if ( (time < 2.5f) && (time >= 0.5f) ) { // Phase 1 and 2 render the wireframe
1823  if (time >= 1.5f) // Just clip the wireframe after Phase 1
1824  render_info->set_clip_plane(plane_point,wire_normal);
1825 
1827 
1828  model_render_immediate(render_info, model_id, &model_orient, &vmd_zero_vector);
1829  }
1830 
1831  if (time >= 1.5f) { // Render the ship in Phase 2 onwards
1832  render_info->set_clip_plane(plane_point,ship_normal);
1833  render_info->set_flags(flags);
1834 
1835  model_render_immediate(render_info, model_id, &model_orient, &vmd_zero_vector);
1836  }
1837 
1838  if (time < 2.5f) { // Render the scanline in Phase 1 and 2
1839  gr_set_color(0,255,0);
1840  start.xyz.x = size*1.25f;
1841  start.xyz.y = 0.0f;
1842  start.xyz.z = -clip;
1843  stop.xyz.x = -size*1.25f;
1844  stop.xyz.y = 0.0f;
1845  stop.xyz.z = -clip;
1847  g3_draw_htl_line(&start,&stop);
1848  g3_done_instance(true);
1849  }
1850  }
1851 
1852  gr_zbuffer_set(GR_ZBUFF_FULL); // Turn off depthbuffer again
1853 
1854  batch_render_all();
1855  Glowpoint_use_depth_buffer = true; // Back to normal
1856 
1859  g3_end_frame();
1860  gr_reset_clip();
1861 
1862  } else {
1863  // rotate the ship as much as required for this frame
1864  *rotation_buffer += PI2 * flFrametime / rev_rate;
1865  while (*rotation_buffer > PI2){
1866  *rotation_buffer -= PI2;
1867  }
1868 
1869  view_angles.p = -0.6f;
1870  view_angles.b = 0.0f;
1871  view_angles.h = 0.0f;
1872  vm_angles_2_matrix(&model_orient, &view_angles);
1873 
1874  rot_angles.p = 0.0f;
1875  rot_angles.b = 0.0f;
1876  rot_angles.h = *rotation_buffer;
1877  vm_rotate_matrix_by_angles(&model_orient, &rot_angles);
1878 
1879  g3_start_frame(1);
1880 
1881  polymodel *pm = model_get(model_id);
1882 
1883  // render the wodel
1884  if ( (closeup_pos != NULL) && (vm_vec_mag(closeup_pos) > 0.0f) ) {
1885  g3_set_view_matrix(closeup_pos, &vmd_identity_matrix, closeup_zoom);
1886  } else {
1887  vec3d pos = { { { 0.0f, 0.0f, -(pm->rad * 1.5f) } } };
1888  g3_set_view_matrix(&pos, &vmd_identity_matrix, closeup_zoom);
1889  }
1890 
1891  // lighting for techroom
1892  light_reset();
1893  vec3d light_dir = vmd_zero_vector;
1894  light_dir.xyz.y = 1.0f;
1895  light_add_directional(&light_dir, 0.65f, 1.0f, 1.0f, 1.0f);
1896  light_rotate_all();
1897  // lighting for techroom
1898 
1899  model_clear_instance(model_id);
1900 
1901  render_info->set_detail_level_lock(0);
1902 
1904  {
1905  if ( flags & MR_IS_MISSILE ) {
1906  shadows_start_render(&Eye_matrix, &Eye_position, Proj_fov, gr_screen.clip_aspect, -closeup_pos->xyz.z + pm->rad, -closeup_pos->xyz.z + pm->rad + 20.0f, -closeup_pos->xyz.z + pm->rad + 200.0f, -closeup_pos->xyz.z + pm->rad + 1000.0f);
1907  } else {
1908  shadows_start_render(&Eye_matrix, &Eye_position, Proj_fov, gr_screen.clip_aspect, -closeup_pos->xyz.z + pm->rad, -closeup_pos->xyz.z + pm->rad + 200.0f, -closeup_pos->xyz.z + pm->rad + 2000.0f, -closeup_pos->xyz.z + pm->rad + 10000.0f);
1909  }
1910 
1911  model_render_params shadow_render_info;
1912 
1913  shadow_render_info.set_flags(flags | MR_NO_TEXTURING | MR_NO_LIGHTING);
1914  shadow_render_info.set_detail_level_lock(0);
1915 
1916  model_render_immediate(&shadow_render_info, model_id, &model_orient, &vmd_zero_vector);
1918  }
1919 
1920  gr_set_clip(x1, y1, x2, y2, resize_mode);
1921 
1924 
1925  gr_set_color(0,128,0);
1926 
1927  if (effect == 1) { // FS1 effect
1928  render_info->set_animated_effect(ANIMATED_SHADER_LOADOUTSELECT_FS1, MIN(time*0.5f,2.0f));
1929  render_info->set_flags(flags);
1930  } else {
1931  render_info->set_flags(flags);
1932  }
1933 
1934  model_render_immediate(render_info, model_id, &model_orient, &vmd_zero_vector);
1935 
1936  batch_render_all();
1937 
1940  g3_end_frame();
1941  gr_reset_clip();
1942  }
1943 }
1944 
1945 // NEWSTUFF END
void light_add_directional(const vec3d *dir, float intensity, float r, float g, float b, float spec_r, float spec_g, float spec_b, bool specular)
Definition: lighting.cpp:209
vec3d max
Definition: model.h:343
void ship_wing_cleanup(int shipnum, wing *wingp)
Definition: ship.cpp:7640
int Common_select_inited
int Flash_timer
Definition: sound.cpp:39
#define COMMON_BRIEFING_BUTTON
#define MAX_FILENAME_LEN
Definition: pstypes.h:324
void set_highlight_action(void(*_user_function)(void))
Definition: button.cpp:375
void hud_set_wingman_status_none(int wing_index, int wing_pos)
#define gr_zbuffer_set
Definition: 2d.h:817
char Starting_wing_names[MAX_STARTING_WINGS][NAME_LENGTH]
Definition: ship.cpp:139
bsp_info * submodel
Definition: model.h:764
int timestamp(int delta_ms)
Definition: timer.cpp:226
wing Wings[MAX_WINGS]
Definition: ship.cpp:128
int i
Definition: multi_pxo.cpp:466
char wing_status_wing_pos
Definition: ship.h:553
float p
Definition: pstypes.h:111
void add_XSTR(char *string, int _xstr_id, int _x, int _y, UI_GADGET *_assoc, int _color_type, int _font_id=-1)
Definition: window.cpp:476
#define NUM_SCORES
Definition: eventmusic.h:50
#define MR_SHOW_OUTLINE_HTL
Definition: model.h:885
void reset_status()
Definition: button.cpp:78
#define MIN(a, b)
Definition: pstypes.h:296
float Proj_fov
Definition: 3dsetup.cpp:31
void briefing_load_music(char *fname)
vec3d min
Definition: model.h:342
void wss_save_loadout()
int Cmdline_freespace_no_music
Definition: cmdline.cpp:271
int objnum
Definition: ship.h:537
int Game_mode
Definition: systemvars.cpp:24
GLfloat GLfloat GLfloat GLfloat h
Definition: Glext.h:7280
int Mission_music[NUM_SCORES]
Definition: eventmusic.cpp:253
#define COMMON_OPTIONS_BUTTON
#define ON_SHIP_SELECT
Definition: missionbrief.h:19
brief_common_buttons Common_buttons[3][GR_NUM_RESOLUTIONS][NUM_COMMON_BUTTONS]
char Game_current_mission_filename[MAX_FILENAME_LEN]
Definition: fredstubs.cpp:26
polymodel * model_get(int model_num)
Definition: modelread.cpp:3134
ship_weapon weapons
Definition: ship.h:658
#define GR_RESIZE_MENU
Definition: 2d.h:684
net_player * Net_player
Definition: multi.cpp:94
float vm_vec_mag(const vec3d *v)
Definition: vecmat.cpp:325
#define gr_end_view_matrix
Definition: 2d.h:896
void draw_model_icon(int model_id, int flags, float closeup_zoom, int x, int y, int w, int h, const ship_info *sip, int resize_mode, const vec3d *closeup_pos)
#define IS_MISSION_MULTI_TEAMS
Definition: missionparse.h:96
float flFrametime
Definition: fredstubs.cpp:22
bool Glowpoint_override
Definition: systemvars.cpp:75
int Current_screen
char wing_status_wing_index
Definition: ship.h:552
void common_show_no_ship_error()
matrix * vm_angles_2_matrix(matrix *m, const angles *a)
Definition: vecmat.cpp:752
int Anim_paused
Definition: animplay.cpp:34
int Briefing_overlay_id
void vm_rotate_matrix_by_angles(matrix *orient, const angles *tangles)
Definition: vecmat.cpp:1338
angles model_icon_angles
Definition: ship.h:1339
void ship_add_exited_ship(ship *sp, int reason)
Definition: ship.cpp:5298
void _cdecl void void _cdecl void _cdecl Warning(char *filename, int line, SCP_FORMAT_STRING const char *format,...) SCP_FORMAT_STRING_ARGS(3
void unload_wing_icons()
Assert(pm!=NULL)
#define MSC_FLASH_INTERVAL
#define MR_NO_POLYS
Definition: model.h:866
Definition: pstypes.h:88
char filename[MAX_FILENAME_LEN]
#define GR_NUM_RESOLUTIONS
Definition: 2d.h:651
#define mprintf(args)
Definition: pstypes.h:238
int Wss_num_wings_teams[MAX_TVT_TEAMS]
void gr_init_alphacolor(color *clr, int r, int g, int b, int alpha, int type)
Definition: 2d.cpp:1173
general failure sound for any event
Definition: gamesnd.h:297
int weapon_pool[MAX_WEAPON_TYPES]
Definition: 2d.h:95
matrix Eye_matrix
Definition: 3dsetup.cpp:26
help pressed
Definition: gamesnd.h:293
int res
Definition: 2d.h:370
#define SIF_CARGO
Definition: ship.h:884
void set_flags(uint flags)
void ss_set_team_pointers(int team)
#define MR_NO_LIGHTING
Definition: model.h:867
#define GR_ZBUFF_FULL
Definition: 2d.h:675
struct vec3d::@225::@227 xyz
CButton * team
void wl_bash_ship_weapons(ship_weapon *swp, wss_unit *slot)
void model_render_immediate(model_render_params *render_info, int model_num, matrix *orient, vec3d *pos, int render, bool sort)
GLclampf f
Definition: Glext.h:7097
#define INTEL_SHORT(x)
Definition: pstypes.h:389
#define ANIMATED_SHADER_LOADOUTSELECT_FS2
#define GR_ZBUFF_NONE
Definition: 2d.h:672
#define SEF_PLAYER_DELETED
Definition: ship.h:849
#define Assertion(expr, msg,...)
Definition: clang.h:41
Definition: 2d.h:82
int brief_only_allow_briefing()
void common_check_buttons()
int Ss_pool_teams[MAX_TVT_TEAMS][MAX_SHIP_CLASSES]
#define GR_MAYBE_CLEAR_RES(bmap)
Definition: 2d.h:639
void common_music_close()
#define MAX_WSS_SLOTS
int ship_class
Definition: missionparse.h:351
Definition: ship.h:1516
void set_detail_level_lock(int detail_level_lock)
int restore_wss_data(ubyte *block)
int common_scroll_up_pressed(int *start, int size, int max_show)
GLenum mode
Definition: Glext.h:5794
int Background_playing
int Ship_select_overlay_id
void help_overlay_set_state(int overlay_id, int resolution_index, int state)
void set_ignore_gadgets(int state)
Definition: window.cpp:471
void weapon_select_close_team()
void ss_synch_interface()
void common_buttons_maybe_reload(UI_WINDOW *ui_window)
Definition: ui.h:195
void set_active_ui(UI_WINDOW *ui_window)
void gr_set_bitmap(int bitmap_num, int alphablend_mode, int bitblt_mode, float alpha)
Definition: 2d.cpp:2105
GLsizeiptr size
Definition: Glext.h:5496
#define Int3()
Definition: pstypes.h:292
void ss_reset_team_pointers()
void anim_release_all_instances(int screen_id)
Free all anim instances that are on the anim_render_list.
Definition: animplay.cpp:567
#define WSS_GRAB_FROM_LIST
#define COMMON_WEAPON_REGION
void multi_ts_common_init()
ship * shipp
Definition: lua.cpp:9162
int Mouse_down_last_frame
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition: Glext.h:7308
int bm_release(int handle, int clear_render_targets)
Frees both a bitmap's data and it's associated slot.
Definition: bmpman.cpp:2603
#define gr_end_proj_matrix
Definition: 2d.h:894
void common_button_do(int i)
void ss_reset_selected_ship()
#define B1_JUST_RELEASED
Definition: uidefs.h:50
int bm_load_animation(const char *real_filename, int *nframes, int *fps, int *keyframe, int can_drop_frames, int dir_type)
Loads a bitmap sequance so we can draw with it.
Definition: bmpman.cpp:1420
void wl_update_parse_object_weapons(p_object *pobjp, wss_unit *slot)
void shadows_end_render()
Definition: shadows.cpp:386
int wep_count[MAX_SHIP_WEAPONS]
#define ON_BRIEFING_SELECT
Definition: missionbrief.h:18
#define MAX_WING_SLOTS
void brief_close()
void g3_done_instance(bool set_api=false)
Definition: 3dsetup.cpp:341
void gr_set_color(int r, int g, int b)
Definition: 2d.cpp:1188
#define B1_JUST_PRESSED
Definition: uidefs.h:49
void common_reset_buttons()
void common_set_interface_palette(char *filename)
void common_flash_button_init()
__inline void gr_set_clip(int x, int y, int w, int h, int resize_mode=GR_RESIZE_FULL)
Definition: 2d.h:741
void draw_forced(int frame_num)
Definition: button.cpp:104
int * Wl_pool
#define gr_set_view_matrix
Definition: 2d.h:895
int Num_music_files
Definition: eventmusic.cpp:250
typedef int(SCP_EXT_CALLCONV *SCPDLL_PFVERSION)(SCPDLL_Version *)
#define gr_reset_clip
Definition: 2d.h:745
UI_WINDOW * Active_ui_window
matrix shadows_start_render(matrix *eye_orient, vec3d *eye_pos, float fov, float aspect, float veryneardist, float neardist, float middist, float fardist)
Definition: shadows.cpp:349
void skip_first_highlight_callback()
Definition: button.cpp:414
int set_bmaps(char *ani_filename, int nframes=3, int start_frame=1)
Definition: gadget.cpp:71
GLintptr offset
Definition: Glext.h:5497
void g3_start_instance_angles(const vec3d *pos, const angles *orient)
Definition: 3dsetup.cpp:317
void batch_render_all(int stream_buffer)
Definition: grbatch.cpp:1124
int Cmdline_nohtl
Definition: cmdline.cpp:438
const float PI2
Definition: pstypes.h:305
net_player_info p_info
Definition: multi.h:473
#define gr_set_proj_matrix
Definition: 2d.h:893
void common_free_interface_palette()
#define NUM_ICON_FRAMES
void common_redraw_pressed_buttons()
int common_select_do(float frametime)
#define MAX_SHIP_WEAPONS
Definition: globals.h:64
void common_maybe_play_cutscene(int movie_type, bool restart_music, int music)
unsigned int uint
Definition: pstypes.h:64
#define nprintf(args)
Definition: pstypes.h:239
#define GM_MULTIPLAYER
Definition: systemvars.h:18
float clip_aspect
Definition: 2d.h:372
#define MR_NO_TEXTURING
Definition: model.h:868
#define MAX_SHIP_CLASSES
Definition: globals.h:48
int flags
Definition: ship.h:1227
void g3_set_view_matrix(const vec3d *view_pos, const matrix *view_matrix, float zoom)
Definition: 3dsetup.cpp:152
void model_clear_instance(int model_num)
Definition: modelread.cpp:4624
#define SIF_SMALL_SHIP
Definition: ship.h:943
char * filename
void weapon_select_common_init()
int pressed()
Definition: button.cpp:325
Switching to a new screen, but not commit.
Definition: gamesnd.h:292
#define KEY_SHIFTED
Definition: key.h:62
int Commit_pressed
#define MAX_WEAPON_TYPES
Definition: globals.h:73
#define COMMON_SS_REGION
int Brief_mouse_up_flag
#define ICON_FRAME_DISABLED_HIGH
float Max_draw_distance
Definition: 2d.cpp:85
#define KEY_W
Definition: key.h:104
int anim_timer_start
wss_unit unit_data[MAX_WSS_SLOTS]
#define KEY_ENTER
Definition: key.h:125
void weapon_select_close()
void light_set_all_relevent()
Definition: lighting.cpp:644
#define ANIMATED_SHADER_LOADOUTSELECT_FS1
void common_select_init()
short player_id
Definition: multi.h:460
void common_set_team_pointers(int team)
vec3d closeup_pos
Definition: ship.h:1327
#define ICON_FRAME_DISABLED
int wss_get_mode(int from_slot, int from_list, int to_slot, int to_list, int wl_ship_slot)
Definition: ship.h:534
#define B1_RELEASED
Definition: uidefs.h:48
#define MAX_WING_BLOCKS
void multi_ts_close()
void anim_render_all(int screen_id, float frametime)
Display the frames for the currently playing anims.
Definition: animplay.cpp:67
void set_color(color &clr)
int Briefing_music_begin_timestamp
#define KEY_P
Definition: key.h:97
int common_num_cutscenes_valid(int movie_type)
void common_check_keys(int k)
void common_render_selected_screen_button()
void vm_vec_scale_sub(vec3d *dest, const vec3d *src1, const vec3d *src2, float k)
Definition: vecmat.cpp:275
void ship_select_common_init()
int Cmdline_shadow_quality
Definition: cmdline.cpp:344
GLint GLint GLint GLint GLint x
Definition: Glext.h:5182
int Drop_on_wing_mflag
bool Glowpoint_use_depth_buffer
Definition: systemvars.cpp:76
unsigned char ubyte
Definition: pstypes.h:62
shader Icon_shaders[NUM_ICON_FRAMES]
int Wing_slot_disabled_bitmap
SCP_vector< mission_cutscene > cutscenes
Definition: missionparse.h:170
const char * XSTR(const char *str, int index)
Definition: localize.cpp:851
char modified[DATE_TIME_LENGTH]
Definition: missionparse.h:135
void wl_set_team_pointers(int team)
#define NOX(s)
Definition: pstypes.h:473
void briefing_stop_music(bool fade)
GLuint start
Definition: Gl.h:1502
float rad
Definition: model.h:340
void common_music_do()
#define KEY_F1
Definition: key.h:143
void _cdecl void void _cdecl Error(const char *filename, int line, SCP_FORMAT_STRING const char *format,...) SCP_FORMAT_STRING_ARGS(3
void briefing_start_music()
float max_speed
Definition: ship.h:1230
void ship_select_close()
GLbitfield flags
Definition: Glext.h:6722
menu_music Spooled_music[MAX_SPOOLED_MUSIC]
Definition: eventmusic.cpp:249
int Num_weapon_types
Definition: weapons.cpp:105
void set_hotkey(int keycode)
Definition: gadget.cpp:280
int Starting_wings[MAX_STARTING_WINGS]
Definition: ship.cpp:132
int Common_team
GLuint const GLchar * name
Definition: Glext.h:5608
#define B1_PRESSED
Definition: uidefs.h:47
wss_unit * Wss_slots
#define IDENTITY_MATRIX
Definition: vecmat.h:64
void common_buttons_init(UI_WINDOW *ui_window)
#define ICON_FRAME_SELECTED
vec3d Eye_position
Definition: 3dsetup.cpp:27
int bm_load(const char *real_filename)
Loads a bitmap so we can draw with it later.
Definition: bmpman.cpp:1119
int multi_quit_game(int prompt, int notify_code, int err_code, int wsa_error)
GLboolean GLboolean GLboolean b
Definition: Glext.h:5781
ship Ships[MAX_SHIPS]
Definition: ship.cpp:122
void wss_direct_restore_loadout()
#define KEY_B
Definition: key.h:83
void chatbox_close()
Definition: chatbox.cpp:634
#define NUM_COMMON_BUTTONS
#define WING_INDEX(wingp)
Definition: ship.h:1601
int Wss_num_wings
int common_scroll_down_pressed(int *start, int size, int max_show)
brief_icon * brief_get_closeup_icon()
void obj_delete(int objnum)
Definition: object.cpp:522
color Icon_colors[NUM_ICON_FRAMES]
void link_hotspot(int num)
Definition: gadget.cpp:50
void common_select_close()
struct sound sound
void create(UI_WINDOW *wnd, char *_text, int _x, int _y, int _w, int _h, int do_repeat=0, int ignore_focus=0)
Definition: button.cpp:26
#define KEY_ESC
Definition: key.h:124
int wep[MAX_SHIP_WEAPONS]
GLubyte GLubyte GLubyte GLubyte w
Definition: Glext.h:5679
int Weapon_select_overlay_id
void draw_model_rotating(model_render_params *render_info, int model_id, int x1, int y1, int x2, int y2, float *rotation_buffer, vec3d *closeup_pos, float closeup_zoom, float rev_rate, int flags, int resize_mode, int effect)
#define ON_WEAPON_SELECT
Definition: missionbrief.h:20
press briefing, ship selection or weapons bar (top-left)
Definition: gamesnd.h:291
float rad
Definition: model.h:757
int n_models
Definition: model.h:744
#define UI_XSTR_COLOR_PINK
Definition: ui.h:161
int Flash_bright
int button_down()
Definition: button.cpp:363
void palette_use_bm_palette(int n)
Definition: palman.cpp:578
int Next_screen
void wss_maybe_restore_loadout()
loadout_data Player_loadout
int eval_sexp(int cur_node, int referenced_node)
Definition: sexp.cpp:22894
#define ICON_FRAME_HOT
#define g3_end_frame()
Definition: 3d.h:49
int Wing_slot_empty_bitmap
Definition: ui.h:584
screen gr_screen
Definition: 2d.cpp:46
int Flash_toggle
float Min_draw_distance
Definition: 2d.cpp:84
#define COMMON_WEAPON_BUTTON
#define KEY_F2
Definition: key.h:144
void palette_restore_palette()
Definition: palman.cpp:588
int store_wss_data(ubyte *block, int max_size, int sound, int player_index)
int ship_info_index
Definition: ship.h:539
void light_reset()
Definition: lighting.cpp:150
#define ICON_FRAME_PLAYER
#define MR_IS_MISSILE
Definition: model.h:872
#define WSS_SWAP_SLOT_SLOT
SCP_vector< ship_info > Ship_info
Definition: ship.cpp:164
#define LOCATION
Definition: pstypes.h:245
void common_play_highlight_sound()
Definition: gamesnd.cpp:1151
int Wl_pool_teams[MAX_TVT_TEAMS][MAX_WEAPON_TYPES]
#define BRIEFING_MUSIC_DELAY
Definition: missionbrief.h:42
#define timestamp_elapsed(stamp)
Definition: timer.h:102
int * Ss_pool
#define COMMON_SS_BUTTON
#define PI
Definition: pstypes.h:303
int is_thruster
Definition: model.h:355
hull_check pos
Definition: lua.cpp:5050
int chatbox_process(int key_in)
Definition: chatbox.cpp:575
#define PROMPT_ALL
Definition: multi_endgame.h:29
#define WSS_SWAP_LIST_SLOT
int Brief_background_bitmap
bool movie_play(char *name)
Definition: movie.cpp:72
#define KEY_CTRLED
Definition: key.h:64
wss_unit Wss_slots_teams[MAX_TVT_TEAMS][MAX_WSS_SLOTS]
#define KEY_TAB
Definition: key.h:127
void change_ship_type(int n, int ship_type, int by_sexp)
Definition: ship.cpp:9983
#define MAX_TVT_TEAMS
Definition: globals.h:57
void set_clip_plane(vec3d &pos, vec3d &normal)
void gr_bitmap(int _x, int _y, int resize_mode)
Definition: 2d.cpp:1303
void cutscene_mark_viewable(char *filename)
Definition: cutscenes.cpp:126
p_object Ship_arrival_list
const float PI_2
Definition: pstypes.h:307
#define UI_XSTR_COLOR_GREEN
Definition: ui.h:160
void set_animated_effect(int effect_num, float timer)
void brief_turn_off_closeup_icon()
int mission_ui_background_load(const char *custom_background, const char *single_background, const char *multi_background)
int ship_index[MAX_SHIPS_PER_WING]
Definition: ship.h:1531
polymodel * pm
Definition: lua.cpp:1598
void gr_create_shader(shader *shade, ubyte r, ubyte g, ubyte b, ubyte c)
Definition: 2d.cpp:1211
#define MAX(a, b)
Definition: pstypes.h:299
void load_wing_icons(char *filename)
#define COMMON_HELP_BUTTON
#define GM_NORMAL
Definition: systemvars.h:19
void wl_synch_interface()
void launch_context_help()
void gamesnd_play_iface(int n)
Definition: gamesnd.cpp:260
mission The_mission
void disable()
Definition: gadget.cpp:432
#define COMMON_BRIEFING_REGION
float h
Definition: pstypes.h:111
void common_render(float frametime)
void wl_reset_team_pointers()
#define KEY_S
Definition: key.h:100
vec3d vmd_zero_vector
Definition: vecmat.cpp:24
void common_reset_team_pointers()
int common_flash_bright()
#define wp(p)
Definition: modelsinc.h:69
int process(int key_in=-1, int process_mouse=1)
Definition: window.cpp:401
net_player Net_players[MAX_PLAYERS]
Definition: multi.cpp:93
int timer_get_milliseconds()
Definition: timer.cpp:150
void gameseq_post_event(int event)
#define stricmp(s1, s2)
Definition: config.h:271
int ship_pool[MAX_SHIP_CLASSES]
matrix vmd_identity_matrix
Definition: vecmat.cpp:28
#define COMMON_COMMIT_BUTTON
int help_overlay_active(int overlay_id)
void light_rotate_all()
Definition: lighting.cpp:585
void common_music_init(int score_index)
#define ICON_FRAME_NORMAL
#define WSS_DUMP_TO_LIST
float b
Definition: pstypes.h:111
GLint y
Definition: Gl.h:1505
#define g3_start_frame(zbuffer_flag)
Definition: 3d.h:39
char last_modified[DATE_TIME_LENGTH]
int wss_slots_all_empty()
int Drop_icon_mflag
#define strcpy_s(...)
Definition: safe_strings.h:67
#define MSC_FLASH_AFTER_TIME
void g3_draw_htl_line(const vec3d *start, const vec3d *end)
Definition: 3ddraw.cpp:1975