]> git.mxchange.org Git - flightgear.git/blob - src/Cockpit/hud_gaug.cxx
Merge commit 'refs/merge-requests/1552' of git@gitorious.org:fg/flightgear into next
[flightgear.git] / src / Cockpit / hud_gaug.cxx
1 #include "hud.hxx"
2
3 #ifdef USE_HUD_TextList
4 #define textString(x, y, text, digit)  TextString(text, x , y ,digit)
5 #else
6 #define textString(x, y, text, digit)  puDrawString(guiFnt, text, x, y)
7 #endif
8
9 FLTFNPTR get_func(const char *name);   // FIXME
10
11 gauge_instr::gauge_instr(const SGPropertyNode *node) :
12     instr_scale(
13             node->getIntValue("x"),
14             node->getIntValue("y"),
15             node->getIntValue("width"),
16             node->getIntValue("height"),
17             0 /*load_fn*/,
18             node->getIntValue("options"),
19             node->getFloatValue("maxValue") - node->getFloatValue("minValue"), // Always shows span?
20             node->getFloatValue("maxValue"),
21             node->getFloatValue("minValue"),
22             node->getFloatValue("disp_scaling"),
23             node->getIntValue("major_divs"),
24             node->getIntValue("minor_divs"),
25             node->getIntValue("modulator"), // "rollover"
26             0, /* hud.cxx: static int dp_shoing = 0; */    // FIXME
27             node->getBoolValue("working", true))
28 {
29     SG_LOG(SG_INPUT, SG_BULK, "Done reading gauge instrument "
30             << node->getStringValue("name", "[unnamed]"));
31
32     set_data_source(get_func(node->getStringValue("loadfn")));
33 }
34
35
36 // As implemented, draw only correctly draws a horizontal or vertical
37 // scale. It should contain a variation that permits clock type displays.
38 // Now is supports "tickless" displays such as control surface indicators.
39 // This routine should be worked over before using. Current value would be
40 // fetched and not used if not commented out. Clearly that is intollerable.
41
42 void gauge_instr::draw(void)
43 {
44     float marker_xs, marker_xe;
45     float marker_ys, marker_ye;
46     int text_x, text_y;
47     int width, height, bottom_4;
48     int lenstr;
49     int i;
50     char TextScale[80];
51     bool condition;
52     int disp_val = 0;
53     float vmin = min_val();
54     float vmax = max_val();
55     POINT mid_scr = get_centroid();
56     float cur_value = get_value();
57     RECT  scrn_rect = get_location();
58     UINT options = get_options();
59
60     width = scrn_rect.left + scrn_rect.right;
61     height = scrn_rect.top + scrn_rect.bottom;
62     bottom_4 = scrn_rect.bottom / 4;
63
64     // Draw the basic markings for the scale...
65     if (huds_vert(options)) { // Vertical scale
66         // Bottom tick bar
67         drawOneLine(scrn_rect.left, scrn_rect.top, width, scrn_rect.top);
68
69         // Top tick bar
70         drawOneLine( scrn_rect.left, height, width, height);
71
72         marker_xs = scrn_rect.left;
73         marker_xe = width;
74
75         if (huds_left(options)) { // Read left, so line down right side
76             drawOneLine(width, scrn_rect.top, width, height);
77             marker_xs  = marker_xe - scrn_rect.right / 3.0;   // Adjust tick
78         }
79
80         if (huds_right(options)) {     // Read  right, so down left sides
81             drawOneLine(scrn_rect.left, scrn_rect.top, scrn_rect.left, height);
82             marker_xe = scrn_rect.left + scrn_rect.right / 3.0;   // Adjust tick
83         }
84
85         // At this point marker x_start and x_end values are transposed.
86         // To keep this from confusing things they are now interchanged.
87         if (huds_both(options)) {
88             marker_ye = marker_xs;
89             marker_xs = marker_xe;
90             marker_xe = marker_ye;
91         }
92
93         // Work through from bottom to top of scale. Calculating where to put
94         // minor and major ticks.
95
96         if (!huds_noticks(options)) {    // If not no ticks...:)
97             // Calculate x marker offsets
98             int last = (int)vmax + 1;    // float_to_int(vmax)+1;
99             i = (int)vmin; //float_to_int(vmin);
100
101             for (; i < last; i++) {
102                 // Calculate the location of this tick
103                 marker_ys = scrn_rect.top + (i - vmin) * factor()/* +.5f*/;
104
105                 // We compute marker_ys even though we don't know if we will use
106                 // either major or minor divisions. Simpler.
107
108                 if (div_min()) {                  // Minor tick marks
109                     if (!(i % (int)div_min())) {
110                         if (huds_left(options) && huds_right(options)) {
111                             drawOneLine(scrn_rect.left, marker_ys, marker_xs - 3, marker_ys);
112                             drawOneLine(marker_xe + 3, marker_ys, width, marker_ys);
113
114                         } else if (huds_left(options)) {
115                             drawOneLine(marker_xs + 3, marker_ys, marker_xe, marker_ys);
116                         } else {
117                             drawOneLine(marker_xs, marker_ys, marker_xe - 3, marker_ys);
118                         }
119                     }
120                 }
121
122                 // Now we work on the major divisions. Since these are also labeled
123                 // and no labels are drawn otherwise, we label inside this if
124                 // statement.
125
126                 if (div_max()) {                  // Major tick mark
127                     if (!(i % (int)div_max())) {
128                         if (huds_left(options) && huds_right(options)) {
129                             drawOneLine(scrn_rect.left, marker_ys, marker_xs, marker_ys);
130                             drawOneLine(marker_xe, marker_ys, width, marker_ys);
131                         } else {
132                             drawOneLine(marker_xs, marker_ys, marker_xe, marker_ys);
133                         }
134
135                         if (!huds_notext(options)) {
136                             disp_val = i;
137                             sprintf(TextScale, "%d",
138                                     float_to_int(disp_val * data_scaling()/*+.5*/));
139
140                             lenstr = getStringWidth(TextScale);
141
142                             if (huds_left(options) && huds_right(options)) {
143                                 text_x = mid_scr.x -  lenstr/2 ;
144
145                             } else if (huds_left(options)) {
146                                 text_x = float_to_int(marker_xs - lenstr);
147                             } else {
148                                 text_x = float_to_int(marker_xe - lenstr);
149                             }
150                             // Now we know where to put the text.
151                             text_y = float_to_int(marker_ys);
152                             textString(text_x, text_y, TextScale, 0);
153                         }
154                     }
155                 }
156             }
157         }
158
159         // Now that the scale is drawn, we draw in the pointer(s). Since labels
160         // have been drawn, text_x and text_y may be recycled. This is used
161         // with the marker start stops to produce a pointer for each side reading
162
163         text_y = scrn_rect.top + float_to_int((cur_value - vmin) * factor() /*+.5f*/);
164         //    text_x = marker_xs - scrn_rect.left;
165
166         if (huds_right(options)) {
167             glBegin(GL_LINE_STRIP);
168             glVertex2f(scrn_rect.left, text_y + 5);
169             glVertex2f(float_to_int(marker_xe), text_y);
170             glVertex2f(scrn_rect.left, text_y - 5);
171             glEnd();
172         }
173         if (huds_left(options)) {
174             glBegin(GL_LINE_STRIP);
175             glVertex2f(width, text_y + 5);
176             glVertex2f(float_to_int(marker_xs), text_y);
177             glVertex2f(width, text_y - 5);
178             glEnd();
179         }
180         // End if VERTICAL SCALE TYPE
181
182     } else {                             // Horizontal scale by default
183         // left tick bar
184         drawOneLine(scrn_rect.left, scrn_rect.top, scrn_rect.left, height);
185
186         // right tick bar
187         drawOneLine(width, scrn_rect.top, width, height );
188
189         marker_ys = scrn_rect.top;                       // Starting point for
190         marker_ye = height;                              // tick y location calcs
191         marker_xs = scrn_rect.left + (cur_value - vmin) * factor() /*+ .5f*/;
192
193         if (huds_top(options)) {
194             // Bottom box line
195             drawOneLine(scrn_rect.left, scrn_rect.top, width, scrn_rect.top);
196
197             marker_ye = scrn_rect.top + scrn_rect.bottom / 2.0;   // Tick point adjust
198             // Bottom arrow
199             glBegin(GL_LINE_STRIP);
200             glVertex2f(marker_xs - bottom_4, scrn_rect.top);
201             glVertex2f(marker_xs, marker_ye);
202             glVertex2f(marker_xs + bottom_4, scrn_rect.top);
203             glEnd();
204         }
205
206         if (huds_bottom(options)) {
207             // Top box line
208             drawOneLine(scrn_rect.left, height, width, height);
209             // Tick point adjust
210             marker_ys = height - scrn_rect.bottom  / 2.0;
211
212             // Top arrow
213             glBegin(GL_LINE_STRIP);
214             glVertex2f(marker_xs + bottom_4, height);
215             glVertex2f(marker_xs, marker_ys );
216             glVertex2f(marker_xs - bottom_4, height);
217             glEnd();
218         }
219
220
221         int last = (int)vmax + 1; //float_to_int(vmax)+1;
222         i = (int)vmin; //float_to_int(vmin);
223         for (; i <last ; i++) {
224             condition = true;
225             if (!modulo() && i < min_val())
226                     condition = false;
227
228             if (condition) {
229                 marker_xs = scrn_rect.left + (i - vmin) * factor()/* +.5f*/;
230                 //        marker_xs = scrn_rect.left + (int)((i - vmin) * factor() + .5f);
231                 if (div_min()) {
232                     if (!(i % (int)div_min())) {
233                         // draw in ticks only if they aren't too close to the edge.
234                         if (((marker_xs + 5) > scrn_rect.left)
235                                || ((marker_xs - 5) < (width))) {
236
237                             if (huds_both(options)) {
238                                 drawOneLine(marker_xs, scrn_rect.top, marker_xs, marker_ys - 4);
239                                 drawOneLine(marker_xs, marker_ye + 4, marker_xs, height);
240
241                             } else if (huds_top(options)) {
242                                 drawOneLine(marker_xs, marker_ys, marker_xs, marker_ye - 4);
243                             } else {
244                                 drawOneLine(marker_xs, marker_ys + 4, marker_xs, marker_ye);
245                             }
246                         }
247                     }
248                 }
249
250                 if (div_max()) {
251                     if (!(i % (int)div_max())) {
252                         if (modulo()) {
253                             if (disp_val < 0) {
254                                 while (disp_val < 0)
255                                     disp_val += modulo();
256                             }
257                             disp_val = i % (int)modulo();
258                         } else {
259                             disp_val = i;
260                         }
261                         sprintf(TextScale, "%d",
262                                 float_to_int(disp_val * data_scaling()/* +.5*/));
263                         lenstr = getStringWidth(TextScale);
264
265                         // Draw major ticks and text only if far enough from the edge.
266                         if (((marker_xs - 10) > scrn_rect.left)
267                                 && ((marker_xs + 10) < width)) {
268                             if (huds_both(options)) {
269                                 drawOneLine(marker_xs, scrn_rect.top, marker_xs, marker_ys);
270                                 drawOneLine(marker_xs, marker_ye, marker_xs, height);
271
272                                 if (!huds_notext(options))
273                                     textString(marker_xs - lenstr, marker_ys + 4, TextScale, 0);
274
275                             } else {
276                                 drawOneLine(marker_xs, marker_ys, marker_xs, marker_ye);
277
278                                 if (!huds_notext(options)) {
279                                     if (huds_top(options))
280                                         textString(marker_xs - lenstr, height - 10, TextScale, 0);
281                                     else
282                                         textString(marker_xs - lenstr, scrn_rect.top, TextScale, 0);
283                                 }
284                             }
285                         }
286                     }
287                 }
288             }
289         }
290     }
291 }
292
293