]> git.mxchange.org Git - flightgear.git/blob - Simulator/Cockpit/hud_ladr.cxx
Initial revision.
[flightgear.git] / Simulator / Cockpit / hud_ladr.cxx
1 #ifdef HAVE_CONFIG_H
2 #  include <config.h>
3 #endif
4
5 #ifdef HAVE_WINDOWS_H
6 #  include <windows.h>
7 #endif
8 #include <stdlib.h>
9 #include <string.h>
10 #include <Aircraft/aircraft.hxx>
11 #include <Include/fg_constants.h>
12 #include <Math/fg_random.h>
13 #include <Math/mat3.h>
14 #include <Math/polar3d.hxx>
15 #include <Scenery/scenery.hxx>
16 #include <Time/fg_timer.hxx>
17
18
19 #include "hud.hxx"
20 //====================== Top of HudLadder Class =======================
21 HudLadder ::
22   HudLadder(  int       x,
23               int       y,
24               UINT      width,
25               UINT      height,
26               DBLFNPTR  ptch_source,
27               DBLFNPTR  roll_source,
28               double    span_units,
29               double    major_div,
30               double    minor_div,
31               UINT      screen_hole,
32               UINT      lbl_pos,
33               bool      working) :
34                dual_instr_item( x, y, width, height,
35                                 ptch_source,
36                                 roll_source,
37                                 working,
38                                 HUDS_RIGHT),
39                width_units    ( span_units   ),
40                div_units      ( major_div < 0? -major_div: major_div ),
41                minor_div      ( minor_div    ),
42                label_pos      ( lbl_pos      ),
43                scr_hole       ( screen_hole  ),
44                vmax           ( span_units/2 ),
45                vmin           ( -vmax        )
46 {
47   if( !width_units ) {
48     width_units = 45;
49     }
50   factor = (double)get_span() / (double) width_units;
51 }
52
53 HudLadder ::
54   ~HudLadder()
55 {
56 }
57
58 HudLadder ::
59   HudLadder( const HudLadder & image ) :
60         dual_instr_item( (dual_instr_item &) image),
61         width_units    ( image.width_units   ),
62         div_units      ( image.div_units     ),
63         label_pos      ( image.label_pos     ),
64         scr_hole       ( image.scr_hole      ),
65         vmax           ( image.vmax ),
66         vmin           ( image.vmin ),
67         factor         ( image.factor        )
68 {
69 }
70 HudLadder & HudLadder ::
71   operator = ( const HudLadder & rhs )
72 {
73   if( !(this == &rhs)) {
74     (dual_instr_item &)(*this) = (dual_instr_item &)rhs;
75     width_units  = rhs.width_units;
76     div_units    = rhs.div_units;
77     label_pos    = rhs.label_pos;
78     scr_hole     = rhs.scr_hole;
79     vmax         = rhs.vmax;
80     vmin         = rhs.vmin;
81     factor       = rhs.factor;
82     }
83   return *this;
84 }
85
86 //
87 //      Draws a climb ladder in the center of the HUD
88 //
89
90 void HudLadder :: draw( void )
91 {
92   double roll_value;
93   double pitch_value;
94   int    marker_y;
95   int    x_ini;
96   int    x_end;
97   int    y_ini;
98   int    y_end;
99   int    new_x_ini;
100   int    new_x_end;
101   int    new_y_ini;
102   int    new_y_end;
103   int    i;
104   POINT  centroid   = get_centroid();
105   RECT   box        = get_location();
106   int    scr_min    = box.top;
107   int    half_span  = box.right >> 1;
108   char   TextLadder[80];
109   int    condition;
110   int    label_length;
111   roll_value        = current_ch2();
112   GLfloat sinRoll   = sin( roll_value );
113   GLfloat cosRoll   = cos( roll_value );
114
115   pitch_value       = current_ch1() * RAD_TO_DEG;
116   vmin              = pitch_value - (double)width_units/2.0;
117   vmax              = pitch_value + (double)width_units/2.0;
118
119 // Box the target.
120   drawOneLine( centroid.x - 5, centroid.y,     centroid.x,     centroid.y + 5);
121   drawOneLine( centroid.x,     centroid.y + 5, centroid.x + 5, centroid.y);
122   drawOneLine( centroid.x + 5, centroid.y,     centroid.x,     centroid.y - 5);
123   drawOneLine( centroid.x,     centroid.y - 5, centroid.x - 5, centroid.y);
124
125   for( i=(int)vmin; i<=(int)vmax; i++ )  {  // Through integer pitch values...
126     condition = 1;
127     if( condition )      {
128       marker_y = centroid.y + (int)(((double)(i - pitch_value) * factor) + .5);
129       if( div_units ) {
130         if( !(i % div_units ))    {        //  At integral multiple of div
131           sprintf( TextLadder, "%d", i );
132           label_length = strlen( TextLadder );
133           if( scr_hole == 0 )           {
134             if( i ) {
135               x_ini = centroid.x - half_span;
136               }
137             else {                         // Make zero point wider on left
138               x_ini = centroid.x - half_span - 10;
139               }
140             y_ini = marker_y;
141             x_end = centroid.x + half_span;
142             y_end = marker_y;
143             new_x_ini = centroid.x + (int)(
144                        (x_ini - centroid.x) * cosRoll -
145                        (y_ini - centroid.y) * sinRoll);
146             new_y_ini = centroid.y + (int)(             \
147                        (x_ini - centroid.x) * sinRoll + \
148                        (y_ini - centroid.y) * cosRoll);
149             new_x_end = centroid.x + (int)(             \
150                        (x_end - centroid.x) * cosRoll - \
151                        (y_end - centroid.y) * sinRoll);
152             new_y_end = centroid.y + (int)(             \
153                        (x_end - centroid.x) * sinRoll + \
154                        (y_end - centroid.y) * cosRoll);
155
156             if( i >= 0 ) { // Above zero draw solid lines
157               drawOneLine( new_x_ini, new_y_ini, new_x_end, new_y_end );
158               }
159             else         { // Below zero draw dashed lines.
160               glEnable(GL_LINE_STIPPLE);
161               glLineStipple( 1, 0x00FF );
162               drawOneLine( new_x_ini, new_y_ini, new_x_end, new_y_end );
163               glDisable(GL_LINE_STIPPLE);
164               }
165             // Calculate the position of the left text and write it.
166             new_x_ini = centroid.x + (int)(
167                         (x_ini - 8 * label_length- 4 - centroid.x) * cosRoll -
168                         (y_ini - 4 ) * sinRoll);
169             new_y_ini = centroid.y + (int)(
170                         (x_ini - 8 * label_length- 4 - centroid.x) * sinRoll +
171                         (y_ini - 4 - centroid.y) * cosRoll);
172             strokeString( new_x_ini , new_y_ini ,
173                         TextLadder, GLUT_STROKE_ROMAN,
174                         roll_value );
175
176             // Calculate the position of the right text and write it.
177             new_x_end = centroid.x + (int)(                  \
178                        (x_end + 24 - 8 * label_length - centroid.x) * cosRoll - \
179                        (y_end -  4 - centroid.y) * sinRoll);
180             new_y_end = centroid.y + (int)(                  \
181                        (x_end + 24 - 8 * label_length - centroid.x) * sinRoll + \
182                        (y_end -  4 - centroid.y) * cosRoll);
183             strokeString( new_x_end,  new_y_end,
184                           TextLadder, GLUT_STROKE_ROMAN,
185                           roll_value );
186             }
187           else   {  // Draw ladder with space in the middle of the lines
188                     // Start by calculating the points and drawing the
189                     // left side lines.
190             if( i != 0 )  {
191               x_ini = centroid.x - half_span;
192               }
193             else          {
194               x_ini = centroid.x - half_span - 10;
195               }
196             y_ini = marker_y;
197             x_end = centroid.x - half_span + scr_hole/2;
198             y_end = marker_y;
199
200             new_x_end = centroid.x+  (int)(             \
201                         (x_end - centroid.x) * cosRoll -\
202                         (y_end - centroid.y) * sinRoll);
203             new_y_end = centroid.y+ (int)(              \
204                         (x_end - centroid.x) * sinRoll +\
205                         (y_end - centroid.y) * cosRoll);
206             new_x_ini = centroid.x + (int)(              \
207                         (x_ini - centroid.x) * cosRoll -\
208                         (y_ini - centroid.y) * sinRoll);
209             new_y_ini = centroid.y + (int)(             \
210                         (x_ini - centroid.x) * sinRoll +\
211                         (y_ini - centroid.y) * cosRoll);
212
213             if( i >= 0 )
214               {
215               drawOneLine( new_x_ini, new_y_ini, new_x_end, new_y_end );
216               }
217             else  {
218               glEnable(GL_LINE_STIPPLE);
219               glLineStipple( 1, 0x00FF );
220               drawOneLine( new_x_ini, new_y_ini, new_x_end, new_y_end );
221               glDisable(GL_LINE_STIPPLE);
222               }
223             // Now calculate the location of the left side label using
224             // the previously calculated start of the left side line.
225
226             x_ini = x_ini - (label_length + 32 + centroid.x);
227             if( i < 0) {
228               x_ini -= 8;
229               }
230             else {
231               if( i == 0 ) {
232                 x_ini += 20;
233                 }
234               }
235             y_ini = y_ini - ( 4 + centroid.y);
236
237             new_x_ini = centroid.x + (int)(x_ini * cosRoll - y_ini * sinRoll);
238             new_y_ini = centroid.y + (int)(x_ini * sinRoll + y_ini * cosRoll);
239             strokeString( new_x_ini , new_y_ini ,
240                           TextLadder, GLUT_STROKE_MONO_ROMAN,
241                           roll_value );
242
243             // Now calculate and draw the right side line location
244             x_ini = centroid.x + half_span - scr_hole/2;
245             y_ini = marker_y;
246             if( i != 0 )  {
247               x_end = centroid.x + half_span;
248               }
249             else          {
250               x_end = centroid.x + half_span + 10;
251               }
252             y_end = marker_y;
253
254             new_x_ini = centroid.x + (int)(         \
255                         (x_ini-centroid.x)*cosRoll -\
256                         (y_ini-centroid.y)*sinRoll);
257             new_y_ini = centroid.y + (int)(         \
258                         (x_ini-centroid.x)*sinRoll +\
259                         (y_ini-centroid.y)*cosRoll);
260             new_x_end = centroid.x + (int)(         \
261                         (x_end-centroid.x)*cosRoll -\
262                         (y_end-centroid.y)*sinRoll);
263             new_y_end = centroid.y +  (int)(        \
264                         (x_end-centroid.x)*sinRoll +\
265                         (y_end-centroid.y)*cosRoll);
266
267             if( i >= 0 )
268               {
269               drawOneLine( new_x_ini, new_y_ini, new_x_end, new_y_end );
270               }
271             else
272               {
273               glEnable(GL_LINE_STIPPLE);
274               glLineStipple( 1, 0x00FF );
275               drawOneLine( new_x_ini, new_y_ini, new_x_end, new_y_end );
276               glDisable(GL_LINE_STIPPLE);
277               }
278
279             // Calculate the location and draw the right side label
280             // using the end of the line as previously calculated.
281             x_end -= centroid.x + label_length - 24;
282             if( i < 0 ) {
283               x_end -= 8;
284               }
285             y_end  = marker_y - ( 4 + centroid.y);
286             new_x_end = centroid.x + (int)( (GLfloat)x_end * cosRoll -
287                                             (GLfloat)y_end * sinRoll);
288             new_y_end = centroid.y + (int)( (GLfloat)x_end * sinRoll +
289                                             (GLfloat)y_end * cosRoll);
290             strokeString( new_x_end,  new_y_end,
291                           TextLadder, GLUT_STROKE_MONO_ROMAN,
292                           roll_value );
293             }
294           }
295         }
296       }
297     }
298 }
299