1 // hud.cxx -- hud defines and prototypes
3 // Written by Michele America, started September 1997.
5 // Copyright (C) 1997 Michele F. America - micheleamerica@geocities.com
7 // This program is free software; you can redistribute it and/or
8 // modify it under the terms of the GNU General Public License as
9 // published by the Free Software Foundation; either version 2 of the
10 // License, or (at your option) any later version.
12 // This program is distributed in the hope that it will be useful, but
13 // WITHOUT ANY WARRANTY; without even the implied warranty of
14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 // General Public License for more details.
17 // You should have received a copy of the GNU General Public License
18 // along with this program; if not, write to the Free Software
19 // Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22 // (Log is kept at end of this file)
38 # include <values.h> // for MAXINT
41 #include <Aircraft/aircraft.h>
42 #include <Debug/fg_debug.h>
43 #include <Include/fg_constants.h>
44 #include <Main/options.hxx>
45 #include <Math/fg_random.h>
46 #include <Math/mat3.h>
47 #include <Math/polar3d.hxx>
48 #include <Scenery/scenery.hxx>
49 #include <Time/fg_timer.hxx>
50 #include <Weather/weather.h>
52 #if defined ( __sun__ ) || defined ( __sgi )
54 extern void *memmove(void *, const void *, size_t);
62 // The following routines obtain information concerntin the aircraft's
63 // current state and return it to calling instrument display routines.
64 // They should eventually be member functions of the aircraft.
67 deque< instr_item * > HUD_deque;
73 locRECT( UINT left, UINT top, UINT right, UINT bottom);
74 RECT get_rect(void) { return rect;}
77 locRECT :: locRECT( UINT left, UINT top, UINT right, UINT bottom)
87 void drawOneLine( UINT x1, UINT y1, UINT x2, UINT y2)
95 void drawOneLine( RECT &rect)
98 glVertex2f(rect.left, rect.top);
99 glVertex2f(rect.right, rect.bottom);
104 // The following code deals with painting the "instrument" on the display
106 /* textString - Bitmap font string */
108 void textString( int x, int y, char *msg, void *font ){
111 glutBitmapCharacter(font, *msg);
116 /* strokeString - Stroke font string */
118 void strokeString(int x, int y, char *msg, void *font, float theta)
124 glRotatef(theta * RAD_TO_DEG, 0.0, 0.0, 1.0);
125 xx = (int)(x * cos(theta) + y * sin( theta ));
126 yy = (int)(y * cos(theta) - x * sin( theta ));
127 glTranslatef( xx, yy, 0);
128 glScalef(.1, .1, 0.0);
130 glutStrokeCharacter(font, *msg);
136 //========================= End of Class Implementations===================
139 // Constructs a HUD object and then adds in instruments. At the present
140 // the instruments are hard coded into the routine. Ultimately these need
141 // to be defined by the aircraft's instrumentation records so that the
142 // display for a Piper Cub doesn't show the speed range of a North American
143 // mustange and the engine readouts of a B36!
148 int fgHUDInit( fgAIRCRAFT * /* current_aircraft */ )
153 fgPrintf( FG_COCKPIT, FG_INFO, "Initializing current aircraft HUD\n" );
155 HUD_deque.erase( HUD_deque.begin(), HUD_deque.end()); // empty the HUD deque
160 // For now lets just hardcode the hud here.
161 // In the future, hud information has to come from the same place
162 // aircraft information came from.
164 // fgHUDSetTimeMode( hud, NIGHT );
165 // fgHUDSetBrightness( hud, BRT_LIGHT );
172 HIptr = (instr_item *) new fgTBI_instr( 270, 100, 60, 10 );
175 case 1: // Artificial Horizon
176 HIptr = (instr_item *) new HudLadder( 240, 195, 120, 180 );
180 HIptr = (instr_item *) new hud_card( 130,
185 HUDS_LEFT | HUDS_VERT,
196 case 3: // Radio Altimeter
197 HIptr = (instr_item *) new hud_card( 420,
202 HUDS_LEFT | HUDS_VERT,
212 case 4: // GYRO COMPASS
213 HIptr = (instr_item *) new hud_card( 200,
229 HIptr = (instr_item *) new hud_card( 460,
234 HUDS_RIGHT | HUDS_VERT,
245 HIptr = (instr_item *) new guage_instr( 250, // x
249 get_aileronval, // data source
250 HUDS_BOTTOM | HUDS_NOTEXT,
257 HIptr = (instr_item *) new guage_instr( 170, // x
261 get_elevatorval, // data source
262 HUDS_RIGHT | HUDS_VERT | HUDS_NOTEXT,
263 -100.0, // Scale data
269 HIptr = (instr_item *) new guage_instr( 250, // x
273 get_rudderval, // data source
274 HUDS_TOP | HUDS_NOTEXT,
281 HIptr = (instr_item *) new guage_instr( 100, // x
285 get_throttleval, // data source
286 HUDS_VERT | HUDS_RIGHT | HUDS_NOTEXT,
292 case 10: // Digital KIAS
293 HIptr = (instr_item *) new instr_label ( 110,
309 case 11: // Digital Rate of Climb
310 HIptr = (instr_item *) new instr_label ( 110,
326 case 12: // Roll indication diagnostic
327 HIptr = (instr_item *) new instr_label ( 110,
343 case 13: // Angle of attack diagnostic
344 HIptr = (instr_item *) new instr_label ( 440,
361 HIptr = (instr_item *) new instr_label ( 440,
378 HIptr = (instr_item *) new instr_label ( 440,
395 HIptr = (instr_item *) new instr_label( 440,
412 HIptr = (instr_item *) new instr_label( 440,
429 HIptr = (instr_item *) new instr_label( 440,
447 HIptr = (instr_item *) new instr_label( 10,
464 switch( current_options.get_tris_or_culled() ) {
466 HIptr = (instr_item *) new instr_label( 10,
482 HIptr = (instr_item *) new instr_label( 10,
501 HIptr = (instr_item *) new instr_label( 10,
520 if( HIptr ) { // Anything to install?
521 HUD_deque.insert( HUD_deque.begin(), HIptr);
527 return 0; // For now. Later we may use this for an error code.
530 int fgHUDInit2( fgAIRCRAFT * /* current_aircraft */ )
535 fgPrintf( FG_COCKPIT, FG_INFO, "Initializing current aircraft HUD\n" );
537 HUD_deque.erase( HUD_deque.begin(), HUD_deque.end()); // empty the HUD deque
542 // For now lets just hardcode the hud here.
543 // In the future, hud information has to come from the same place
544 // aircraft information came from.
546 // fgHUDSetTimeMode( hud, NIGHT );
547 // fgHUDSetBrightness( hud, BRT_LIGHT );
555 HIptr = (instr_item *) new fgTBI_instr( 270, 100, 60, 10 );
558 case 1: // Artificial Horizon
559 HIptr = (instr_item *) new HudLadder( 240, 195, 120, 180 );
563 HIptr = (instr_item *) new hud_card( 130,
568 HUDS_LEFT | HUDS_VERT,
579 case 3: // Radio Altimeter
580 HIptr = (instr_item *) new hud_card( 420,
585 HUDS_LEFT | HUDS_VERT,
595 case 4: // GYRO COMPASS
596 HIptr = (instr_item *) new hud_card( 200,
612 HIptr = (instr_item *) new hud_card( 460,
617 HUDS_RIGHT | HUDS_VERT,
628 HIptr = (instr_item *) new guage_instr( 250, // x
632 get_aileronval, // data source
633 HUDS_BOTTOM | HUDS_NOTEXT,
640 HIptr = (instr_item *) new guage_instr( 170, // x
644 get_elevatorval, // data source
645 HUDS_RIGHT | HUDS_VERT | HUDS_NOTEXT,
646 -100.0, // Scale data
652 HIptr = (instr_item *) new guage_instr( 250, // x
656 get_rudderval, // data source
657 HUDS_TOP | HUDS_NOTEXT,
664 HIptr = (instr_item *) new guage_instr( 100, // x
668 get_throttleval, // data source
669 HUDS_VERT | HUDS_RIGHT | HUDS_NOTEXT,
675 case 10: // Digital KIAS
676 HIptr = (instr_item *) new instr_label ( 110,
692 case 11: // Digital Rate of Climb
693 HIptr = (instr_item *) new instr_label ( 110,
709 case 12: // Roll indication diagnostic
710 HIptr = (instr_item *) new instr_label ( 110,
726 case 13: // Angle of attack diagnostic
727 HIptr = (instr_item *) new instr_label ( 440,
744 HIptr = (instr_item *) new instr_label ( 440,
761 HIptr = (instr_item *) new instr_label ( 440,
778 HIptr = (instr_item *) new instr_label( 440,
795 HIptr = (instr_item *) new instr_label( 440,
812 HIptr = (instr_item *) new instr_label( 440,
830 HIptr = (instr_item *) new instr_label( 10,
847 switch( current_options.get_tris_or_culled() ) {
849 HIptr = (instr_item *) new instr_label( 10,
865 HIptr = (instr_item *) new instr_label( 10,
884 HIptr = (instr_item *) new instr_label( 10,
903 if( HIptr ) { // Anything to install?
904 HUD_deque.insert( HUD_deque.begin(), HIptr);
910 return 0; // For now. Later we may use this for an error code.
913 int global_day_night_switch = DAY;
915 void HUD_brightkey( bool incr_bright )
917 instr_item *pHUDInstr = HUD_deque[0];
918 int brightness = pHUDInstr->get_brightness();
920 if( current_options.get_hud_status() ) {
922 switch (brightness) {
924 current_options.set_hud_status(0);
928 brightness = BRT_LIGHT;
932 brightness = BRT_MEDIUM;
936 brightness = BRT_DARK;
940 brightness = BRT_BLACK;
944 switch (brightness) {
946 brightness = BRT_MEDIUM;
950 brightness = BRT_DARK;
954 brightness = BRT_BLACK;
959 current_options.set_hud_status(0);
964 current_options.set_hud_status(1);
966 if( DAY == global_day_night_switch ) {
967 brightness = BRT_BLACK;
970 brightness = BRT_DARK;
971 global_day_night_switch = DAY;
975 if( NIGHT == global_day_night_switch ) {
976 brightness = BRT_DARK;
979 brightness = BRT_MEDIUM;
980 global_day_night_switch = NIGHT;
984 pHUDInstr->SetBrightness( brightness );
989 // Performs a once around the list of calls to instruments installed in
990 // the HUD object with requests for redraw. Kinda. It will when this is
993 void fgUpdateHUD( void ) {
996 // int day_night_sw = current_aircraft.controls->day_night_switch;
997 int day_night_sw = global_day_night_switch;
998 int hud_displays = HUD_deque.size();
999 instr_item *pHUDInstr;
1001 if( !hud_displays ) { // Trust everyone, but ALWAYS cut the cards!
1005 pHUDInstr = HUD_deque[0];
1006 brightness = pHUDInstr->get_brightness();
1007 // brightness = HUD_deque.at(0)->get_brightness();
1009 glMatrixMode(GL_PROJECTION);
1013 gluOrtho2D(0, 640, 0, 480);
1014 glMatrixMode(GL_MODELVIEW);
1018 glColor3f(1.0, 1.0, 1.0);
1021 glDisable(GL_DEPTH_TEST);
1022 glDisable(GL_LIGHTING);
1026 deque < instr_item * > :: iterator current;
1027 deque < instr_item * > :: iterator last;
1029 current = HUD_deque.begin();
1030 last = HUD_deque.end();
1031 while ( current != last ) {
1032 pHUDInstr = *current;
1035 // for( i = hud_displays; i; --i) { // Draw everything
1036 // if( HUD_deque.at(i)->enabled()) {
1037 // pHUDInstr = HUD_deque[i - 1];
1038 if( pHUDInstr->enabled()) {
1039 // We should to respond to a dial instead
1040 // or as well to the of time of day. Of
1041 // course, we have no dial!
1042 if( day_night_sw == DAY) {
1043 switch (brightness) {
1045 glColor3f (0.1, 0.9, 0.1);
1049 glColor3f (0.1, 0.7, 0.0);
1053 glColor3f (0.0, 0.5, 0.0);
1057 glColor3f( 0.0, 0.0, 0.0);
1064 if( day_night_sw == NIGHT) {
1065 switch (brightness) {
1067 glColor3f (0.9, 0.1, 0.1);
1071 glColor3f (0.7, 0.0, 0.1);
1076 glColor3f (0.5, 0.0, 0.0);
1079 else { // Just in case default
1080 glColor3f (0.1, 0.9, 0.1);
1083 // fgPrintf( FG_COCKPIT, FG_DEBUG, "HUD Code %d Status %d\n",
1084 // hud->code, hud->status );
1086 // HUD_deque.at(i)->draw(); // Responsible for broken or fixed variants.
1087 // No broken displays honored just now.
1091 glEnable(GL_DEPTH_TEST);
1092 glEnable(GL_LIGHTING);
1093 glMatrixMode(GL_PROJECTION);
1095 glMatrixMode(GL_MODELVIEW);
1100 // Revision 1.22 1998/09/29 14:56:31 curt
1101 // c++-ified comments.
1103 // Revision 1.21 1998/09/29 02:01:07 curt
1104 // Added a "rate of climb" indicator.
1106 // Revision 1.20 1998/08/24 20:05:16 curt
1107 // Added a second minimalistic HUD.
1108 // Added code to display the number of triangles rendered.
1110 // Revision 1.19 1998/07/30 23:44:05 curt
1111 // Tweaks for sgi building.
1113 // Revision 1.18 1998/07/20 12:47:55 curt
1114 // Replace the hud rendering for loop (which linearly searches the the hud
1115 // list to find the entry with the proper position) with a simple linear
1116 // traversal using an "iterator."
1118 // Revision 1.17 1998/07/13 21:28:02 curt
1119 // Converted the aoa scale to a radio altimeter.
1121 // Revision 1.16 1998/07/13 21:00:47 curt
1122 // Integrated Charlies latest HUD updates.
1123 // Wrote access functions for current fgOPTIONS.
1125 // Revision 1.15 1998/07/08 14:41:08 curt
1126 // Renamed polar3d.h to polar3d.hxx
1128 // Revision 1.14 1998/07/06 21:31:20 curt
1129 // Removed an extraneous ^M.
1131 // Revision 1.13 1998/07/03 13:16:28 curt
1132 // Added Charlie Hotchkiss's HUD updates and improvementes.
1134 // Revision 1.11 1998/06/05 18:17:10 curt
1135 // Added the declaration of memmove needed by the stl which apparently
1136 // solaris only defines for cc compilations and not for c++ (__STDC__)
1138 // Revision 1.10 1998/05/17 16:58:12 curt
1139 // Added a View Frustum Culling ratio display to the hud.
1141 // Revision 1.9 1998/05/16 13:04:14 curt
1142 // New updates from Charlie Hotchkiss.
1144 // Revision 1.8 1998/05/13 18:27:54 curt
1145 // Added an fov to hud display.
1147 // Revision 1.7 1998/05/11 18:13:11 curt
1148 // Complete C++ rewrite of all cockpit code by Charlie Hotchkiss.
1150 // Revision 1.22 1998/04/18 04:14:02 curt
1151 // Moved fg_debug.c to it's own library.
1153 // Revision 1.21 1998/04/03 21:55:28 curt
1154 // Converting to Gnu autoconf system.
1157 // Revision 1.20 1998/03/09 22:48:40 curt
1158 // Minor "formatting" tweaks.
1160 // Revision 1.19 1998/02/23 20:18:28 curt
1161 // Incorporated Michele America's hud changes.
1163 // Revision 1.18 1998/02/21 14:53:10 curt
1164 // Added Charlie's HUD changes.
1166 // Revision 1.17 1998/02/20 00:16:21 curt
1167 // Thursday's tweaks.
1169 // Revision 1.16 1998/02/19 13:05:49 curt
1170 // Incorporated some HUD tweaks from Michelle America.
1171 // Tweaked the sky's sunset/rise colors.
1172 // Other misc. tweaks.
1174 // Revision 1.15 1998/02/16 13:38:39 curt
1175 // Integrated changes from Charlie Hotchkiss.
1177 // Revision 1.14 1998/02/12 21:59:41 curt
1178 // Incorporated code changes contributed by Charlie Hotchkiss
1179 // <chotchkiss@namg.us.anritsu.com>
1181 // Revision 1.12 1998/02/09 15:07:48 curt
1184 // Revision 1.11 1998/02/07 15:29:34 curt
1185 // Incorporated HUD changes and struct/typedef changes from Charlie Hotchkiss
1186 // <chotchkiss@namg.us.anritsu.com>
1188 // Revision 1.10 1998/02/03 23:20:14 curt
1189 // Lots of little tweaks to fix various consistency problems discovered by
1190 // Solaris' CC. Fixed a bug in fg_debug.c with how the fgPrintf() wrapper
1191 // passed arguments along to the real printf(). Also incorporated HUD changes
1192 // by Michele America.
1194 // Revision 1.9 1998/01/31 00:43:04 curt
1195 // Added MetroWorks patches from Carmen Volpe.
1197 // Revision 1.8 1998/01/27 00:47:51 curt
1198 // Incorporated Paul Bleisch's <bleisch@chromatic.com> new debug message
1199 // system and commandline/config file processing code.
1201 // Revision 1.7 1998/01/19 18:40:20 curt
1202 // Tons of little changes to clean up the code and to remove fatal errors
1203 // when building with the c++ compiler.
1205 // Revision 1.6 1997/12/15 23:54:34 curt
1206 // Add xgl wrappers for debugging.
1207 // Generate terrain normals on the fly.
1209 // Revision 1.5 1997/12/10 22:37:39 curt
1210 // Prepended "fg" on the name of all global structures that didn't have it yet.
1211 // i.e. "struct WEATHER {}" became "struct fgWEATHER {}"
1213 // Revision 1.4 1997/09/23 00:29:32 curt
1214 // Tweaks to get things to compile with gcc-win32.
1216 // Revision 1.3 1997/09/05 14:17:26 curt
1217 // More tweaking with stars.
1219 // Revision 1.2 1997/09/04 02:17:30 curt
1222 // Revision 1.1 1997/08/29 18:03:22 curt
1223 // Initial revision.