]> git.mxchange.org Git - flightgear.git/blob - src/ATC/ATCdisplay.cxx
Improved tumbling behaviour -- the AI doesn't just freeze now, but
[flightgear.git] / src / ATC / ATCdisplay.cxx
1 // ATCdisplay.cxx - routines to display ATC output - graphically for now
2 //
3 // Written by David Luff, started October 2001.
4 //
5 // Copyright (C) 2001  David C Luff - david.luff@nottingham.ac.uk
6 //
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.
11 //
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.
16 //
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.
20
21 #ifdef HAVE_CONFIG_H
22 #  include <config.h>
23 #endif
24
25 #include <simgear/misc/props.hxx>
26
27 #include <Include/general.hxx>
28 #include <Main/fg_props.hxx>
29 #include <GUI/gui.h>
30
31 #include "ATCdisplay.hxx"
32
33
34 // Constructor
35 FGATCDisplay::FGATCDisplay() {
36         rep_msg = false;
37         change_msg_flag = false;
38         dsp_offset1 = 0;
39         dsp_offset2 = 0;
40 }
41
42
43 // Destructor
44 FGATCDisplay::~FGATCDisplay() {
45 }
46
47 void FGATCDisplay::init() {
48 }
49
50 void FGATCDisplay::bind() {
51 }
52
53 void FGATCDisplay::unbind() {
54 }
55
56 // update - this actually draws the visuals and should be called from the main Flightgear rendering loop.
57 void FGATCDisplay::update(double dt) {
58         
59         // These strings are used for temporary storage of the transmission string in order
60         // that the string we view only changes when the next repetition starts scrolling
61         // even though the master string (rep_msg_str) may change at any time.
62         static string msg1 = "";
63         static string msg2 = "";
64         
65         if( rep_msg || msgList.size() ) {
66                 //cout << "In FGATC::update()" << endl;
67                 SGPropertyNode *xsize_node = fgGetNode("/sim/startup/xsize");
68                 SGPropertyNode *ysize_node = fgGetNode("/sim/startup/ysize");
69                 int iwidth   = xsize_node->getIntValue();
70                 int iheight  = ysize_node->getIntValue();
71                 
72                 glMatrixMode( GL_PROJECTION );
73                 glPushMatrix();
74                 glLoadIdentity();
75                 gluOrtho2D( 0, iwidth, 0, iheight );
76                 glMatrixMode( GL_MODELVIEW );
77                 glPushMatrix();
78                 glLoadIdentity();
79                 
80                 glDisable( GL_DEPTH_TEST );
81                 glDisable( GL_LIGHTING );
82                 
83                 glColor3f( 0.9, 0.4, 0.2 );
84                 
85                 float fps = general.get_frame_rate();
86                 
87                 if(rep_msg) {
88                         //cout << "dsp_offset1 = " << dsp_offset1 << " dsp_offset2 = " << dsp_offset2 << endl;
89                         if(dsp_offset1 == 0) {
90                                 msg1 = rep_msg_str;
91                         }
92                         if(dsp_offset2 == 0) {
93                                 msg2 = rep_msg_str;
94                         }
95                         // Check for the situation where one offset is negative and the message is changed
96                         if(change_msg_flag) {
97                                 if(dsp_offset1 < 0) {
98                                         msg1 = rep_msg_str;
99                                 } else if(dsp_offset2 < 0) {
100                                         msg2 = rep_msg_str;
101                                 }
102                                 change_msg_flag = false;
103                         }
104                         
105                         //      guiFnt.drawString( rep_msg_str.c_str(),
106                         //          int(iwidth - guiFnt.getStringWidth(buf) - 10 - (int)dsp_offset),
107                         //          (iheight - 20) );
108                         guiFnt.drawString( msg1.c_str(),
109                         int(iwidth - 10 - dsp_offset1),
110                         (iheight - 20) );
111                         guiFnt.drawString( msg2.c_str(),
112                         int(iwidth - 10 - dsp_offset2),
113                         (iheight - 20) );
114                         
115                         // Try to scroll at a frame rate independent speed
116                         // 40 pixels/second looks about right for now
117                         if(dsp_offset1 >= dsp_offset2) {
118                                 dsp_offset1+=(40.0/fps);
119                                 dsp_offset2 = dsp_offset1 - (rep_msg_str.size() * 10) - 100;
120                                 if(dsp_offset1 > (iwidth + (rep_msg_str.size() * 10)))
121                                         dsp_offset1 = 0;
122                         } else {
123                                 dsp_offset2+=(40.0/fps);
124                                 dsp_offset1 = dsp_offset2 - (rep_msg_str.size() * 10) - 100;
125                                 if(dsp_offset2 > (iwidth + (rep_msg_str.size() * 10)))
126                                         dsp_offset2 = 0;
127                         }
128                         
129                 }
130                 
131                 if(msgList.size()) {
132                         //cout << "Attempting to render single message\n";
133                         // We have at least one non-repeating message to process
134                         if(fgGetBool("/ATC/display/scroll-single-messages")) {  // Scroll single messages across the screen.
135                                 msgList_itr = msgList.begin();
136                                 int i = 0;
137                                 while(msgList_itr != msgList.end()) {
138                                         atcMessage m = *msgList_itr;
139                                         //cout << "m.counter = " << m.counter << '\n';
140                                         if(m.dsp_offset > (iwidth + (m.msg.size() * 10))) {
141                                                 //cout << "Stopping single message\n";
142                                                 msgList_itr = msgList.erase(msgList_itr);
143                                         } else if(m.counter > m.start_count) {
144                                                 //cout << "Drawing single message\n";
145                                                 guiFnt.drawString( m.msg.c_str(),
146                                                 int(iwidth - 10 - m.dsp_offset),
147                                                 (iheight - 40) );
148                                                 m.counter += dt;
149                                                 m.dsp_offset += (80.0/fps);
150                                                 msgList[i] = m;
151                                                 ++msgList_itr;
152                                                 ++i;
153                                         } else {
154                                                 //cout << "Not yet started single message\n";
155                                                 m.counter += dt;
156                                                 msgList[i] = m;
157                                                 ++msgList_itr;
158                                                 ++i;
159                                         }
160                                 }
161                         } else {        // Display single messages for a short period of time.
162                                 msgList_itr = msgList.begin();
163                                 int i = 0;
164                                 while(msgList_itr != msgList.end()) {
165                                         atcMessage m = *msgList_itr;
166                                         //cout << "m.counter = " << m.counter << '\n';
167                                         if(m.counter > m.stop_count) {
168                                                 //cout << "Stopping single message\n";
169                                                 msgList_itr = msgList.erase(msgList_itr);
170                                         } else if(m.counter > m.start_count) {
171                                                 guiFnt.drawString( m.msg.c_str(),
172                                                 (iwidth - (m.msg.size() * 8))/2,
173                                                 //iwidth/2,
174                                                 (iheight - 40) );       // TODO - relate the distance in that the string is rendered to the string length.
175                                                 m.counter += dt;
176                                                 msgList[i] = m;
177                                                 ++msgList_itr;
178                                                 ++i;
179                                         } else {
180                                                 m.counter += dt;
181                                                 msgList[i] = m;
182                                                 ++msgList_itr;
183                                                 ++i;
184                                         }
185                                 }
186                         }
187                 }
188                 glEnable( GL_DEPTH_TEST );
189                 glEnable( GL_LIGHTING );
190                 glMatrixMode( GL_PROJECTION );
191                 glPopMatrix();
192                 glMatrixMode( GL_MODELVIEW );
193                 glPopMatrix();
194         }
195 }
196
197 void FGATCDisplay::RegisterSingleMessage(string msg, double delay) {
198         atcMessage m;
199         m.msg = msg;
200         m.repeating = false;
201         m.counter = 0.0;
202         m.start_count = delay;
203         m.stop_count = m.start_count + 5.0;             // Display for 5ish seconds for now - this might have to change eg. be related to length of message in future
204         //cout << "m.stop_count = " << m.stop_count << '\n';
205         m.id = 0;
206         m.dsp_offset = 0.0;
207         
208         msgList.push_back(m);
209         //cout << "Single message registered\n";
210 }
211
212 void FGATCDisplay::RegisterRepeatingMessage(string msg) {
213         rep_msg = true;
214         rep_msg_str = msg;
215         return;
216 }
217
218 void FGATCDisplay::ChangeRepeatingMessage(string newmsg) {
219         rep_msg_str = newmsg;
220         change_msg_flag = true;
221         return;
222 }
223
224 void FGATCDisplay::CancelRepeatingMessage() {
225         rep_msg = false;
226         rep_msg_str = "";
227         dsp_offset1 = 0;
228         dsp_offset2 = 0;
229         return;
230 }
231