source: src/mlx/gui/pirep.py@ 846:d11ea8564da8

Last change on this file since 846:d11ea8564da8 was 846:d11ea8564da8, checked in by István Váradi <ivaradi@…>, 7 years ago

The values are checked and the OK button is updated accordingly (re #307)

File size: 50.8 KB
RevLine 
[220]1
2from common import *
[845]3from dcdata import getTable
4from info import FlightInfo
5from flight import comboModel
[220]6
[236]7from mlx.pirep import PIREP
[846]8from mlx.flight import Flight
[220]9from mlx.const import *
10
11import time
[845]12import re
[220]13
14#------------------------------------------------------------------------------
15
[300]16## @package mlx.gui.pirep
17#
[845]18# The detailed PIREP viewer and editor windows.
[300]19#
20# The \ref PIREPViewer class is a dialog displaying all information found in a
21# PIREP. It consists of three tabs. The Data tab displays the simple,
22# itemizable data. The Comments & defects tab contains the flight comments and
23# defects, while the Log tab contains the flight log collected by the
24# \ref mlx.logger.Logger "logger".
25
26#------------------------------------------------------------------------------
27
[220]28class PIREPViewer(gtk.Dialog):
29 """The dialog for PIREP viewing."""
30 @staticmethod
31 def createFrame(label):
32 """Create a frame with the given label.
33
34 The frame will contain an alignment to properly distance the
35 insides. The alignment will contain a VBox to contain the real
[831]36 contents.
[220]37
38 The function returns a tuple with the following items:
39 - the frame,
40 - the inner VBox."""
41 frame = gtk.Frame(label = label)
42
43 alignment = gtk.Alignment(xalign = 0.0, yalign = 0.0,
44 xscale = 1.0, yscale = 1.0)
45 frame.add(alignment)
46 alignment.set_padding(padding_top = 4, padding_bottom = 4,
47 padding_left = 4, padding_right = 4)
48 box = gtk.VBox()
49 alignment.add(box)
[831]50
[220]51 return (frame, box)
52
53 @staticmethod
[845]54 def getLabel(text, extraText = ""):
[220]55 """Get a bold label with the given text."""
[845]56 label = gtk.Label("<b>" + text + "</b>" + extraText)
[220]57 label.set_use_markup(True)
58 label.set_alignment(0.0, 0.5)
59 return label
60
61 @staticmethod
62 def getDataLabel(width = None, xAlignment = 0.0):
63 """Get a bold label with the given text."""
64 label = gtk.Label()
65 if width is not None:
66 label.set_width_chars(width)
67 label.set_alignment(xAlignment, 0.5)
68 return label
69
70 @staticmethod
[845]71 def getTextWindow(heightRequest = 40, editable = False):
[220]72 """Get a scrollable text window.
[831]73
[220]74 Returns a tuple of the following items:
75 - the window,
76 - the text view."""
77 scrolledWindow = gtk.ScrolledWindow()
78 scrolledWindow.set_shadow_type(SHADOW_IN)
79 scrolledWindow.set_policy(POLICY_AUTOMATIC, POLICY_AUTOMATIC)
80
81 textView = gtk.TextView()
82 textView.set_wrap_mode(WRAP_WORD)
[845]83 textView.set_editable(editable)
84 textView.set_cursor_visible(editable)
[220]85 textView.set_size_request(-1, heightRequest)
86 scrolledWindow.add(textView)
87
88 return (scrolledWindow, textView)
89
90 @staticmethod
91 def tableAttach(table, column, row, labelText, width = None,
92 dataLabelXAlignment = 0.0):
93 """Attach a labeled data to the given column and row of the
[831]94 table.
95
[220]96 If width is given, that will be the width of the data
97 label.
98
99 Returns the data label attached."""
100 dataBox = gtk.HBox()
101 table.attach(dataBox, column, column+1, row, row+1)
[831]102
[220]103 dataLabel = PIREPViewer.addLabeledData(dataBox, labelText,
104 width = width)
105 dataLabel.set_alignment(dataLabelXAlignment, 0.5)
106
107 return dataLabel
108
109 @staticmethod
110 def addLabeledData(hBox, labelText, width = None, dataPadding = 8):
111 """Add a label and a data label to the given HBox.
[831]112
[845]113 Returns the data label."""
[220]114 label = PIREPViewer.getLabel(labelText)
115 hBox.pack_start(label, False, False, 0)
[831]116
[220]117 dataLabel = PIREPViewer.getDataLabel(width = width)
118 hBox.pack_start(dataLabel, False, False, dataPadding)
119
120 return dataLabel
121
122 @staticmethod
[845]123 def addHFiller(hBox, width = 8):
124 """Add a filler to the given horizontal box."""
125 filler = gtk.Alignment(xalign = 0.0, yalign = 0.0,
126 xscale = 1.0, yscale = 1.0)
127 filler.set_size_request(width, -1)
128 hBox.pack_start(filler, False, False, 0)
129
130 @staticmethod
[220]131 def addVFiller(vBox, height = 4):
[238]132 """Add a filler to the given vertical box."""
133 filler = gtk.Alignment(xalign = 0.0, yalign = 0.0,
134 xscale = 1.0, yscale = 1.0)
[220]135 filler.set_size_request(-1, height)
136 vBox.pack_start(filler, False, False, 0)
[831]137
[220]138 @staticmethod
139 def timestamp2text(label, timestamp):
140 """Convert the given timestamp into a text containing the hour
141 and minute in UTC and put that text into the given label."""
142 tm = time.gmtime(timestamp)
143 label.set_text("%02d:%02d" % (tm.tm_hour, tm.tm_min))
144
145 def __init__(self, gui):
146 """Construct the PIREP viewer."""
147 super(PIREPViewer, self).__init__(title = WINDOW_TITLE_BASE +
148 " - " +
149 xstr("pirepView_title"),
150 parent = gui.mainWindow)
[831]151
[220]152 self.set_resizable(False)
153
154 self._gui = gui
[831]155
[220]156 contentArea = self.get_content_area()
[221]157
158 self._notebook = gtk.Notebook()
159 contentArea.pack_start(self._notebook, False, False, 4)
[831]160
[220]161 dataTab = self._buildDataTab()
[221]162 label = gtk.Label(xstr("pirepView_tab_data"))
163 label.set_use_underline(True)
164 label.set_tooltip_text(xstr("pirepView_tab_data_tooltip"))
165 self._notebook.append_page(dataTab, label)
[831]166
[221]167 commentsTab = self._buildCommentsTab()
168 label = gtk.Label(xstr("pirepView_tab_comments"))
169 label.set_use_underline(True)
170 label.set_tooltip_text(xstr("pirepView_tab_comments_tooltip"))
171 self._notebook.append_page(commentsTab, label)
[831]172
[221]173 logTab = self._buildLogTab()
174 label = gtk.Label(xstr("pirepView_tab_log"))
175 label.set_use_underline(True)
176 label.set_tooltip_text(xstr("pirepView_tab_log_tooltip"))
177 self._notebook.append_page(logTab, label)
[224]178
179 self._okButton = self.add_button(xstr("button_ok"), RESPONSETYPE_OK)
180 self._okButton.set_can_default(True)
[831]181
[220]182 def setPIREP(self, pirep):
183 """Setup the data in the dialog from the given PIREP."""
184 bookedFlight = pirep.bookedFlight
185
186 self._callsign.set_text(bookedFlight.callsign)
187 self._tailNumber.set_text(bookedFlight.tailNumber)
188 aircraftType = xstr("aircraft_" + icaoCodes[bookedFlight.aircraftType].lower())
189 self._aircraftType.set_text(aircraftType)
[831]190
[220]191 self._departureICAO.set_text(bookedFlight.departureICAO)
192 self._departureTime.set_text("%02d:%02d" % \
193 (bookedFlight.departureTime.hour,
194 bookedFlight.departureTime.minute))
195
196 self._arrivalICAO.set_text(bookedFlight.arrivalICAO)
197 self._arrivalTime.set_text("%02d:%02d" % \
198 (bookedFlight.arrivalTime.hour,
199 bookedFlight.arrivalTime.minute))
200
201 self._numPassengers.set_text(str(bookedFlight.numPassengers))
202 self._numCrew.set_text(str(bookedFlight.numCrew))
203 self._bagWeight.set_text(str(bookedFlight.bagWeight))
204 self._cargoWeight.set_text(str(bookedFlight.cargoWeight))
205 self._mailWeight.set_text(str(bookedFlight.mailWeight))
[831]206
[220]207 self._route.get_buffer().set_text(bookedFlight.route)
208
209 self._filedCruiseLevel.set_text("FL" + str(pirep.filedCruiseAltitude/100))
210
211 if pirep.cruiseAltitude != pirep.filedCruiseAltitude:
212 self._modifiedCruiseLevel.set_text("FL" + str(pirep.cruiseAltitude/100))
213 else:
214 self._modifiedCruiseLevel.set_text("-")
215
216 self._userRoute.get_buffer().set_text(pirep.route)
217
218 self._departureMETAR.get_buffer().set_text(pirep.departureMETAR)
219
220 self._arrivalMETAR.get_buffer().set_text(pirep.arrivalMETAR)
221 self._departureRunway.set_text(pirep.departureRunway)
222 self._sid.set_text(pirep.sid)
223
224 self._star.set_text("-" if pirep.star is None else pirep.star)
225 self._transition.set_text("-" if pirep.transition is None else pirep.transition)
226 self._approachType.set_text(pirep.approachType)
227 self._arrivalRunway.set_text(pirep.arrivalRunway)
228
229 PIREPViewer.timestamp2text(self._blockTimeStart, pirep.blockTimeStart)
230 PIREPViewer.timestamp2text(self._blockTimeEnd, pirep.blockTimeEnd)
231 PIREPViewer.timestamp2text(self._flightTimeStart, pirep.flightTimeStart)
232 PIREPViewer.timestamp2text(self._flightTimeEnd, pirep.flightTimeEnd)
[831]233
[220]234 self._flownDistance.set_text("%.1f" % (pirep.flownDistance,))
235 self._fuelUsed.set_text("%.0f" % (pirep.fuelUsed,))
236
237 rating = pirep.rating
238 if rating<0:
239 self._rating.set_markup('<b><span foreground="red">NO GO</span></b>')
240 else:
241 self._rating.set_text("%.1f %%" % (rating,))
242
[303]243 self._flownNumCrew.set_text("%d" % (pirep.numCrew,))
244 self._flownNumPassengers.set_text("%d" % (pirep.numPassengers,))
245 self._flownBagWeight.set_text("%.0f" % (pirep.bagWeight,))
[223]246 self._flownCargoWeight.set_text("%.0f" % (pirep.cargoWeight,))
[303]247 self._flownMailWeight.set_text("%.0f" % (pirep.mailWeight,))
[831]248 self._flightType.set_text(xstr("flighttype_" +
[220]249 flightType2string(pirep.flightType)))
250 self._online.set_text(xstr("pirepView_" +
251 ("yes" if pirep.online else "no")))
252
253 delayCodes = ""
254 for code in pirep.delayCodes:
255 if delayCodes: delayCodes += ", "
[437]256 delayCodes += code
[831]257
258 self._delayCodes.get_buffer().set_text(delayCodes)
[221]259
260 self._comments.get_buffer().set_text(pirep.comments)
261 self._flightDefects.get_buffer().set_text(pirep.flightDefects)
262
263 logBuffer = self._log.get_buffer()
264 logBuffer.set_text("")
[225]265 lineIndex = 0
[221]266 for (timeStr, line) in pirep.logLines:
[225]267 isFault = lineIndex in pirep.faultLineIndexes
[226]268 appendTextBuffer(logBuffer,
269 formatFlightLogLine(timeStr, line),
270 isFault = isFault)
[225]271 lineIndex += 1
[221]272
273 self._notebook.set_current_page(0)
[224]274 self._okButton.grab_default()
[220]275
276 def _buildDataTab(self):
277 """Build the data tab of the viewer."""
278 table = gtk.Table(1, 2)
279 table.set_row_spacings(4)
280 table.set_col_spacings(16)
281 table.set_homogeneous(True)
282
283 box1 = gtk.VBox()
284 table.attach(box1, 0, 1, 0, 1)
[831]285
[220]286 box2 = gtk.VBox()
287 table.attach(box2, 1, 2, 0, 1)
[831]288
[220]289 flightFrame = self._buildFlightFrame()
290 box1.pack_start(flightFrame, False, False, 4)
291
292 routeFrame = self._buildRouteFrame()
293 box1.pack_start(routeFrame, False, False, 4)
294
295 departureFrame = self._buildDepartureFrame()
296 box2.pack_start(departureFrame, True, True, 4)
297
298 arrivalFrame = self._buildArrivalFrame()
299 box2.pack_start(arrivalFrame, True, True, 4)
300
301 statisticsFrame = self._buildStatisticsFrame()
302 box2.pack_start(statisticsFrame, False, False, 4)
303
304 miscellaneousFrame = self._buildMiscellaneousFrame()
305 box1.pack_start(miscellaneousFrame, False, False, 4)
306
307 return table
308
309 def _buildFlightFrame(self):
310 """Build the frame for the flight data."""
[831]311
[220]312 (frame, mainBox) = PIREPViewer.createFrame(xstr("pirepView_frame_flight"))
[831]313
[220]314 dataBox = gtk.HBox()
315 mainBox.pack_start(dataBox, False, False, 0)
[831]316
[220]317 self._callsign = \
318 PIREPViewer.addLabeledData(dataBox,
319 xstr("pirepView_callsign"),
320 width = 8)
321
322 self._tailNumber = \
323 PIREPViewer.addLabeledData(dataBox,
324 xstr("pirepView_tailNumber"),
325 width = 7)
326
327 PIREPViewer.addVFiller(mainBox)
328
329 dataBox = gtk.HBox()
330 mainBox.pack_start(dataBox, False, False, 0)
331
332 self._aircraftType = \
333 PIREPViewer.addLabeledData(dataBox,
334 xstr("pirepView_aircraftType"),
335 width = 25)
336
337 PIREPViewer.addVFiller(mainBox)
338
339 table = gtk.Table(3, 2)
340 mainBox.pack_start(table, False, False, 0)
341 table.set_row_spacings(4)
[831]342 table.set_col_spacings(8)
[220]343
344 self._departureICAO = \
345 PIREPViewer.tableAttach(table, 0, 0,
346 xstr("pirepView_departure"),
347 width = 5)
348
349 self._departureTime = \
350 PIREPViewer.tableAttach(table, 1, 0,
351 xstr("pirepView_departure_time"),
352 width = 6)
353
354 self._arrivalICAO = \
355 PIREPViewer.tableAttach(table, 0, 1,
356 xstr("pirepView_arrival"),
357 width = 5)
358
359 self._arrivalTime = \
360 PIREPViewer.tableAttach(table, 1, 1,
361 xstr("pirepView_arrival_time"),
362 width = 6)
363
364 table = gtk.Table(3, 2)
365 mainBox.pack_start(table, False, False, 0)
366 table.set_row_spacings(4)
[831]367 table.set_col_spacings(8)
[220]368
369 self._numPassengers = \
370 PIREPViewer.tableAttach(table, 0, 0,
371 xstr("pirepView_numPassengers"),
372 width = 4)
373
374 self._numCrew = \
375 PIREPViewer.tableAttach(table, 1, 0,
376 xstr("pirepView_numCrew"),
377 width = 3)
378
379 self._bagWeight = \
[831]380 PIREPViewer.tableAttach(table, 0, 1,
[220]381 xstr("pirepView_bagWeight"),
382 width = 5)
383
384 self._cargoWeight = \
[831]385 PIREPViewer.tableAttach(table, 1, 1,
[220]386 xstr("pirepView_cargoWeight"),
387 width = 5)
388
389 self._mailWeight = \
[831]390 PIREPViewer.tableAttach(table, 2, 1,
[220]391 xstr("pirepView_mailWeight"),
392 width = 5)
[831]393
[220]394 PIREPViewer.addVFiller(mainBox)
395
396 mainBox.pack_start(PIREPViewer.getLabel(xstr("pirepView_route")),
397 False, False, 0)
[831]398
[220]399 (routeWindow, self._route) = PIREPViewer.getTextWindow()
400 mainBox.pack_start(routeWindow, False, False, 0)
401
402 return frame
403
404 def _buildRouteFrame(self):
405 """Build the frame for the user-specified route and flight
406 level."""
[831]407
[220]408 (frame, mainBox) = PIREPViewer.createFrame(xstr("pirepView_frame_route"))
409
410 levelBox = gtk.HBox()
411 mainBox.pack_start(levelBox, False, False, 0)
[831]412
[220]413 self._filedCruiseLevel = \
[831]414 PIREPViewer.addLabeledData(levelBox,
[220]415 xstr("pirepView_filedCruiseLevel"),
416 width = 6)
417
418 self._modifiedCruiseLevel = \
419 PIREPViewer.addLabeledData(levelBox,
420 xstr("pirepView_modifiedCruiseLevel"),
421 width = 6)
422
423 PIREPViewer.addVFiller(mainBox)
424
425 (routeWindow, self._userRoute) = PIREPViewer.getTextWindow()
426 mainBox.pack_start(routeWindow, False, False, 0)
427
428 return frame
429
430 def _buildDepartureFrame(self):
[831]431 """Build the frame for the departure data."""
[220]432 (frame, mainBox) = PIREPViewer.createFrame(xstr("pirepView_frame_departure"))
433
434 mainBox.pack_start(PIREPViewer.getLabel("METAR:"),
435 False, False, 0)
436 (metarWindow, self._departureMETAR) = \
437 PIREPViewer.getTextWindow(heightRequest = -1)
438 mainBox.pack_start(metarWindow, True, True, 0)
439
440 PIREPViewer.addVFiller(mainBox)
441
442 dataBox = gtk.HBox()
443 mainBox.pack_start(dataBox, False, False, 0)
[831]444
[220]445 self._departureRunway = \
446 PIREPViewer.addLabeledData(dataBox,
447 xstr("pirepView_runway"),
448 width = 5)
449
450 self._sid = \
451 PIREPViewer.addLabeledData(dataBox,
452 xstr("pirepView_sid"),
453 width = 12)
454
455 return frame
[831]456
[220]457 def _buildArrivalFrame(self):
[831]458 """Build the frame for the arrival data."""
[220]459 (frame, mainBox) = PIREPViewer.createFrame(xstr("pirepView_frame_arrival"))
460
461 mainBox.pack_start(PIREPViewer.getLabel("METAR:"),
462 False, False, 0)
463 (metarWindow, self._arrivalMETAR) = \
464 PIREPViewer.getTextWindow(heightRequest = -1)
465 mainBox.pack_start(metarWindow, True, True, 0)
466
467 PIREPViewer.addVFiller(mainBox)
468
469 table = gtk.Table(2, 2)
470 mainBox.pack_start(table, False, False, 0)
471 table.set_row_spacings(4)
[831]472 table.set_col_spacings(8)
[220]473
474 self._star = \
475 PIREPViewer.tableAttach(table, 0, 0,
476 xstr("pirepView_star"),
477 width = 12)
478
479 self._transition = \
480 PIREPViewer.tableAttach(table, 1, 0,
481 xstr("pirepView_transition"),
482 width = 12)
[831]483
[220]484 self._approachType = \
485 PIREPViewer.tableAttach(table, 0, 1,
486 xstr("pirepView_approachType"),
487 width = 7)
[831]488
[220]489 self._arrivalRunway = \
[831]490 PIREPViewer.tableAttach(table, 1, 1,
[220]491 xstr("pirepView_runway"),
492 width = 5)
[831]493
[220]494 return frame
495
496 def _buildStatisticsFrame(self):
[831]497 """Build the frame for the statistics data."""
[220]498 (frame, mainBox) = PIREPViewer.createFrame(xstr("pirepView_frame_statistics"))
499
500 table = gtk.Table(4, 2)
501 mainBox.pack_start(table, False, False, 0)
502 table.set_row_spacings(4)
503 table.set_col_spacings(8)
[221]504 table.set_homogeneous(False)
[831]505
[220]506 self._blockTimeStart = \
507 PIREPViewer.tableAttach(table, 0, 0,
508 xstr("pirepView_blockTimeStart"),
509 width = 6)
[831]510
[220]511 self._blockTimeEnd = \
512 PIREPViewer.tableAttach(table, 1, 0,
513 xstr("pirepView_blockTimeEnd"),
514 width = 8)
515
516 self._flightTimeStart = \
517 PIREPViewer.tableAttach(table, 0, 1,
518 xstr("pirepView_flightTimeStart"),
519 width = 6)
[831]520
[220]521 self._flightTimeEnd = \
[831]522 PIREPViewer.tableAttach(table, 1, 1,
[220]523 xstr("pirepView_flightTimeEnd"),
524 width = 6)
525
526 self._flownDistance = \
527 PIREPViewer.tableAttach(table, 0, 2,
528 xstr("pirepView_flownDistance"),
529 width = 8)
[831]530
[220]531 self._fuelUsed = \
532 PIREPViewer.tableAttach(table, 1, 2,
533 xstr("pirepView_fuelUsed"),
534 width = 6)
[831]535
[220]536 self._rating = \
537 PIREPViewer.tableAttach(table, 0, 3,
538 xstr("pirepView_rating"),
539 width = 7)
540 return frame
541
542 def _buildMiscellaneousFrame(self):
[831]543 """Build the frame for the miscellaneous data."""
[220]544 (frame, mainBox) = PIREPViewer.createFrame(xstr("pirepView_frame_miscellaneous"))
[303]545
546 table = gtk.Table(3, 2)
547 mainBox.pack_start(table, False, False, 0)
548 table.set_row_spacings(4)
[831]549 table.set_col_spacings(8)
550
[303]551 self._flownNumPassengers = \
552 PIREPViewer.tableAttach(table, 0, 0,
553 xstr("pirepView_numPassengers"),
554 width = 4)
555
556 self._flownNumCrew = \
557 PIREPViewer.tableAttach(table, 1, 0,
558 xstr("pirepView_numCrew"),
559 width = 3)
560
561 self._flownBagWeight = \
562 PIREPViewer.tableAttach(table, 0, 1,
563 xstr("pirepView_bagWeight"),
564 width = 5)
565
[223]566 self._flownCargoWeight = \
[303]567 PIREPViewer.tableAttach(table, 1, 1,
568 xstr("pirepView_cargoWeight"),
569 width = 6)
570
571 self._flownMailWeight = \
572 PIREPViewer.tableAttach(table, 2, 1,
573 xstr("pirepView_mailWeight"),
574 width = 5)
[223]575
[220]576 self._flightType = \
[303]577 PIREPViewer.tableAttach(table, 0, 2,
578 xstr("pirepView_flightType"),
579 width = 15)
[831]580
[220]581 self._online = \
[303]582 PIREPViewer.tableAttach(table, 1, 2,
583 xstr("pirepView_online"),
584 width = 5)
[220]585
586 PIREPViewer.addVFiller(mainBox)
587
588 mainBox.pack_start(PIREPViewer.getLabel(xstr("pirepView_delayCodes")),
589 False, False, 0)
[831]590
[220]591 (textWindow, self._delayCodes) = PIREPViewer.getTextWindow()
592 mainBox.pack_start(textWindow, False, False, 0)
593
[831]594 return frame
[220]595
[221]596 def _buildCommentsTab(self):
597 """Build the tab with the comments and flight defects."""
598 table = gtk.Table(2, 1)
599 table.set_col_spacings(16)
600
601 (frame, commentsBox) = \
602 PIREPViewer.createFrame(xstr("pirepView_comments"))
603 table.attach(frame, 0, 1, 0, 1)
604
605 (commentsWindow, self._comments) = \
606 PIREPViewer.getTextWindow(heightRequest = -1)
607 commentsBox.pack_start(commentsWindow, True, True, 0)
608
609 (frame, flightDefectsBox) = \
610 PIREPViewer.createFrame(xstr("pirepView_flightDefects"))
611 table.attach(frame, 1, 2, 0, 1)
612
613 (flightDefectsWindow, self._flightDefects) = \
614 PIREPViewer.getTextWindow(heightRequest = -1)
615 flightDefectsBox.pack_start(flightDefectsWindow, True, True, 0)
[831]616
[221]617 return table
618
619 def _buildLogTab(self):
620 """Build the log tab."""
621 mainBox = gtk.VBox()
622
623 (logWindow, self._log) = PIREPViewer.getTextWindow(heightRequest = -1)
[226]624 addFaultTag(self._log.get_buffer())
[221]625 mainBox.pack_start(logWindow, True, True, 0)
[831]626
[221]627 return mainBox
[831]628
[220]629#------------------------------------------------------------------------------
[845]630
631class PIREPEditor(gtk.Dialog):
632 """A PIREP editor dialog."""
633 _delayCodeRE = re.compile("([0-9]{2,3})( \([^\)]*\))")
634
635 @staticmethod
636 def tableAttachWidget(table, column, row, labelText, widget):
637 """Attach the given widget with the given label to the given table.
638
639 The label will got to cell (column, row), the widget to cell
640 (column+1, row)."""
641 label = gtk.Label("<b>" + labelText + "</b>")
642 label.set_use_markup(True)
643 alignment = gtk.Alignment(xalign = 0.0, yalign = 0.5,
644 xscale = 0.0, yscale = 0.0)
645 alignment.add(label)
646 table.attach(alignment, column, column + 1, row, row + 1)
647
648 table.attach(widget, column + 1, column + 2, row, row + 1)
649
650 @staticmethod
651 def tableAttachSpinButton(table, column, row, labelText, maxValue,
652 minValue = 0, stepIncrement = 1,
653 pageIncrement = 10, numeric = True,
654 width = 3):
655 """Attach a spin button with the given label to the given table.
656
657 The label will got to cell (column, row), the spin button to cell
658 (column+1, row)."""
659 button = gtk.SpinButton()
660 button.set_range(min = minValue, max = maxValue)
661 button.set_increments(step = stepIncrement, page = pageIncrement)
662 button.set_numeric(True)
663 button.set_width_chars(width)
664 button.set_alignment(1.0)
665
666 PIREPEditor.tableAttachWidget(table, column, row, labelText, button)
667
668 return button
669
670 @staticmethod
671 def tableAttachTimeEntry(table, column, row, labelText):
672 """Attach a time entry widget with the given label to the given table.
673
674 The label will got to cell (column, row), the spin button to cell
675 (column+1, row)."""
676 entry = TimeEntry()
677 entry.set_width_chars(5)
678 entry.set_alignment(1.0)
679
680 PIREPEditor.tableAttachWidget(table, column, row, labelText, entry)
681
682 return entry
683
684 def __init__(self, gui):
685 """Construct the PIREP viewer."""
686 super(PIREPEditor, self).__init__(title = WINDOW_TITLE_BASE +
687 " - " +
688 xstr("pirepEdit_title"),
689 parent = gui.mainWindow)
690
691 self.set_resizable(False)
692
693 self._gui = gui
694
[846]695 self._pirep = None
696
[845]697 contentArea = self.get_content_area()
698
699 self._notebook = gtk.Notebook()
700 contentArea.pack_start(self._notebook, False, False, 4)
701
702 dataTab = self._buildDataTab()
703 label = gtk.Label(xstr("pirepView_tab_data"))
704 label.set_use_underline(True)
705 label.set_tooltip_text(xstr("pirepView_tab_data_tooltip"))
706 self._notebook.append_page(dataTab, label)
707
708 self._flightInfo = self._buildCommentsTab()
709 label = gtk.Label(xstr("pirepView_tab_comments"))
710 label.set_use_underline(True)
711 label.set_tooltip_text(xstr("pirepView_tab_comments_tooltip"))
712 self._notebook.append_page(self._flightInfo, label)
713
714 logTab = self._buildLogTab()
715 label = gtk.Label(xstr("pirepView_tab_log"))
716 label.set_use_underline(True)
717 label.set_tooltip_text(xstr("pirepView_tab_log_tooltip"))
718 self._notebook.append_page(logTab, label)
719
[846]720 self.add_button(xstr("button_cancel"), RESPONSETYPE_CANCEL)
721
[845]722 self._okButton = self.add_button(xstr("button_ok"), RESPONSETYPE_OK)
723 self._okButton.set_can_default(True)
724
725 def setPIREP(self, pirep):
726 """Setup the data in the dialog from the given PIREP."""
[846]727 self._pirep = pirep
728
[845]729 bookedFlight = pirep.bookedFlight
730
731 self._callsign.set_text(bookedFlight.callsign)
732 self._tailNumber.set_text(bookedFlight.tailNumber)
733 aircraftType = xstr("aircraft_" + icaoCodes[bookedFlight.aircraftType].lower())
734 self._aircraftType.set_text(aircraftType)
735
736 self._departureICAO.set_text(bookedFlight.departureICAO)
737 self._departureTime.set_text("%02d:%02d" % \
738 (bookedFlight.departureTime.hour,
739 bookedFlight.departureTime.minute))
740
741 self._arrivalICAO.set_text(bookedFlight.arrivalICAO)
742 self._arrivalTime.set_text("%02d:%02d" % \
743 (bookedFlight.arrivalTime.hour,
744 bookedFlight.arrivalTime.minute))
745
746 self._numPassengers.set_text(str(bookedFlight.numPassengers))
747 self._numCrew.set_text(str(bookedFlight.numCrew))
748 self._bagWeight.set_text(str(bookedFlight.bagWeight))
749 self._cargoWeight.set_text(str(bookedFlight.cargoWeight))
750 self._mailWeight.set_text(str(bookedFlight.mailWeight))
751
752 self._route.get_buffer().set_text(bookedFlight.route)
753
754 self._filedCruiseLevel.set_value(pirep.filedCruiseAltitude/100)
755 self._modifiedCruiseLevel.set_value(pirep.cruiseAltitude/100)
756
757 self._userRoute.get_buffer().set_text(pirep.route)
758
759 self._departureMETAR.get_buffer().set_text(pirep.departureMETAR)
760
761 self._arrivalMETAR.get_buffer().set_text(pirep.arrivalMETAR)
762 self._departureRunway.set_text(pirep.departureRunway)
763 self._sid.get_child().set_text(pirep.sid)
764
765 if not pirep.star:
766 self._star.set_active(0)
767 else:
768 self._star.get_child().set_text(pirep.star)
769
770 if not pirep.transition:
771 self._transition.set_active(0)
772 else:
773 self._transition.get_child().set_text(pirep.transition)
774 self._approachType.set_text(pirep.approachType)
775 self._arrivalRunway.set_text(pirep.arrivalRunway)
776
777 self._blockTimeStart.setTimestamp(pirep.blockTimeStart)
778 self._blockTimeEnd.setTimestamp(pirep.blockTimeEnd)
779 self._flightTimeStart.setTimestamp(pirep.flightTimeStart)
780 self._flightTimeEnd.setTimestamp(pirep.flightTimeEnd)
781
782 self._flownDistance.set_text("%.1f" % (pirep.flownDistance,))
783 self._fuelUsed.set_value(int(pirep.fuelUsed))
784
785 rating = pirep.rating
786 if rating<0:
787 self._rating.set_markup('<b><span foreground="red">NO GO</span></b>')
788 else:
789 self._rating.set_text("%.1f %%" % (rating,))
790
791 self._flownNumCrew.set_value(pirep.numCrew)
792 self._flownNumPassengers.set_value(pirep.numPassengers)
793 self._flownBagWeight.set_value(pirep.bagWeight)
794 self._flownCargoWeight.set_value(pirep.cargoWeight)
795 self._flownMailWeight.set_value(pirep.mailWeight)
796 self._flightType.set_active(flightType2index(pirep.flightType))
797 self._online.set_active(pirep.online)
798
799 self._flightInfo.reset()
800 self._flightInfo.enable(bookedFlight.aircraftType)
801
802 delayCodes = ""
803 for code in pirep.delayCodes:
804 if delayCodes: delayCodes += ", "
805 delayCodes += code
806 m = PIREPEditor._delayCodeRE.match(code)
807 if m:
808 self._flightInfo.activateDelayCode(m.group(1))
809
810 self._delayCodes.get_buffer().set_text(delayCodes)
811
812 self._flightInfo.comments = pirep.comments
813 if pirep.flightDefects.find("<br/></b>")!=-1:
814 flightDefects = pirep.flightDefects.split("<br/></b>")
815 caption = flightDefects[0]
816 index = 0
817 for defect in flightDefects[1:]:
818 if defect.find("<b>")!=-1:
819 (explanation, nextCaption) = defect.split("<b>")
820 else:
821 explanation = defect
822 nextCaption = None
823 self._flightInfo.addFault(index, caption)
824 self._flightInfo.setExplanation(index, explanation)
825 index += 1
826 caption = nextCaption
827
828 # self._comments.get_buffer().set_text(pirep.comments)
829 # self._flightDefects.get_buffer().set_text(pirep.flightDefects)
830
831 logBuffer = self._log.get_buffer()
832 logBuffer.set_text("")
833 lineIndex = 0
834 for (timeStr, line) in pirep.logLines:
835 isFault = lineIndex in pirep.faultLineIndexes
836 appendTextBuffer(logBuffer,
837 formatFlightLogLine(timeStr, line),
838 isFault = isFault)
839 lineIndex += 1
840
841 self._notebook.set_current_page(0)
842 self._okButton.grab_default()
843
[846]844 self._updateButtons()
845
846 def delayCodesChanged(self):
847 """Called when the delay codes have changed."""
848 self._updateButtons()
849
850 def commentsChanged(self):
851 """Called when the comments have changed."""
852 self._updateButtons()
853
854 def faultExplanationsChanged(self):
855 """Called when the fault explanations have changed."""
856 self._updateButtons()
857
[845]858 def _buildDataTab(self):
859 """Build the data tab of the viewer."""
860 table = gtk.Table(1, 2)
861 table.set_row_spacings(4)
862 table.set_col_spacings(16)
863 table.set_homogeneous(True)
864
865 box1 = gtk.VBox()
866 table.attach(box1, 0, 1, 0, 1)
867
868 box2 = gtk.VBox()
869 table.attach(box2, 1, 2, 0, 1)
870
871 flightFrame = self._buildFlightFrame()
872 box1.pack_start(flightFrame, False, False, 4)
873
874 routeFrame = self._buildRouteFrame()
875 box1.pack_start(routeFrame, False, False, 4)
876
877 departureFrame = self._buildDepartureFrame()
878 box2.pack_start(departureFrame, True, True, 4)
879
880 arrivalFrame = self._buildArrivalFrame()
881 box2.pack_start(arrivalFrame, True, True, 4)
882
883 statisticsFrame = self._buildStatisticsFrame()
884 box2.pack_start(statisticsFrame, False, False, 4)
885
886 miscellaneousFrame = self._buildMiscellaneousFrame()
887 box1.pack_start(miscellaneousFrame, False, False, 4)
888
889 return table
890
891 def _buildFlightFrame(self):
892 """Build the frame for the flight data."""
893
894 (frame, mainBox) = PIREPViewer.createFrame(xstr("pirepView_frame_flight"))
895
896 dataBox = gtk.HBox()
897 mainBox.pack_start(dataBox, False, False, 0)
898
899 self._callsign = \
900 PIREPViewer.addLabeledData(dataBox,
901 xstr("pirepView_callsign"),
902 width = 8)
903
904 self._tailNumber = \
905 PIREPViewer.addLabeledData(dataBox,
906 xstr("pirepView_tailNumber"),
907 width = 7)
908
909 PIREPViewer.addVFiller(mainBox)
910
911 dataBox = gtk.HBox()
912 mainBox.pack_start(dataBox, False, False, 0)
913
914 self._aircraftType = \
915 PIREPViewer.addLabeledData(dataBox,
916 xstr("pirepView_aircraftType"),
917 width = 25)
918
919 PIREPViewer.addVFiller(mainBox)
920
921 table = gtk.Table(3, 2)
922 mainBox.pack_start(table, False, False, 0)
923 table.set_row_spacings(4)
924 table.set_col_spacings(8)
925
926 self._departureICAO = \
927 PIREPViewer.tableAttach(table, 0, 0,
928 xstr("pirepView_departure"),
929 width = 5)
930
931 self._departureTime = \
932 PIREPViewer.tableAttach(table, 1, 0,
933 xstr("pirepView_departure_time"),
934 width = 6)
935
936 self._arrivalICAO = \
937 PIREPViewer.tableAttach(table, 0, 1,
938 xstr("pirepView_arrival"),
939 width = 5)
940
941 self._arrivalTime = \
942 PIREPViewer.tableAttach(table, 1, 1,
943 xstr("pirepView_arrival_time"),
944 width = 6)
945
946 table = gtk.Table(3, 2)
947 mainBox.pack_start(table, False, False, 0)
948 table.set_row_spacings(4)
949 table.set_col_spacings(8)
950
951 self._numPassengers = \
952 PIREPViewer.tableAttach(table, 0, 0,
953 xstr("pirepView_numPassengers"),
954 width = 4)
955 self._numCrew = \
956 PIREPViewer.tableAttach(table, 1, 0,
957 xstr("pirepView_numCrew"),
958 width = 3)
959
960 self._bagWeight = \
961 PIREPViewer.tableAttach(table, 0, 1,
962 xstr("pirepView_bagWeight"),
963 width = 5)
964
965 self._cargoWeight = \
966 PIREPViewer.tableAttach(table, 1, 1,
967 xstr("pirepView_cargoWeight"),
968 width = 5)
969
970 self._mailWeight = \
971 PIREPViewer.tableAttach(table, 2, 1,
972 xstr("pirepView_mailWeight"),
973 width = 5)
974
975 PIREPViewer.addVFiller(mainBox)
976
977 mainBox.pack_start(PIREPViewer.getLabel(xstr("pirepView_route")),
978 False, False, 0)
979
980 (routeWindow, self._route) = PIREPViewer.getTextWindow()
981 mainBox.pack_start(routeWindow, False, False, 0)
982
983 return frame
984
985 def _buildRouteFrame(self):
986 """Build the frame for the user-specified route and flight
987 level."""
988
989 (frame, mainBox) = PIREPViewer.createFrame(xstr("pirepView_frame_route"))
990
991 levelBox = gtk.HBox()
992 mainBox.pack_start(levelBox, False, False, 0)
993
994 label = PIREPViewer.getLabel(xstr("pirepView_filedCruiseLevel"),
995 xstr("pirepEdit_FL"))
996 levelBox.pack_start(label, False, False, 0)
997
998 self._filedCruiseLevel = gtk.SpinButton()
999 self._filedCruiseLevel.set_increments(step = 10, page = 100)
1000 self._filedCruiseLevel.set_range(min = 0, max = 500)
1001 #self._filedCruiseLevel.set_tooltip_text(xstr("route_level_tooltip"))
1002 self._filedCruiseLevel.set_numeric(True)
[846]1003 self._filedCruiseLevel.connect("value-changed", self._updateButtons)
[845]1004
1005 levelBox.pack_start(self._filedCruiseLevel, False, False, 0)
1006
1007 PIREPViewer.addHFiller(levelBox)
1008
1009 label = PIREPViewer.getLabel(xstr("pirepView_modifiedCruiseLevel"),
1010 xstr("pirepEdit_FL"))
1011 levelBox.pack_start(label, False, False, 0)
1012
1013 self._modifiedCruiseLevel = gtk.SpinButton()
1014 self._modifiedCruiseLevel.set_increments(step = 10, page = 100)
1015 self._modifiedCruiseLevel.set_range(min = 0, max = 500)
1016 #self._modifiedCruiseLevel.set_tooltip_text(xstr("route_level_tooltip"))
1017 self._modifiedCruiseLevel.set_numeric(True)
[846]1018 self._modifiedCruiseLevel.connect("value-changed", self._updateButtons)
[845]1019
1020 levelBox.pack_start(self._modifiedCruiseLevel, False, False, 0)
1021
1022 PIREPViewer.addVFiller(mainBox)
1023
1024 (routeWindow, self._userRoute) = \
1025 PIREPViewer.getTextWindow(editable = True)
1026 mainBox.pack_start(routeWindow, False, False, 0)
[846]1027 self._userRoute.get_buffer().connect("changed", self._updateButtons)
[845]1028
1029 return frame
1030
1031 def _buildDepartureFrame(self):
1032 """Build the frame for the departure data."""
1033 (frame, mainBox) = PIREPViewer.createFrame(xstr("pirepView_frame_departure"))
1034
1035 mainBox.pack_start(PIREPViewer.getLabel("METAR:"),
1036 False, False, 0)
1037 (metarWindow, self._departureMETAR) = \
1038 PIREPViewer.getTextWindow(heightRequest = -1,
1039 editable = True)
[846]1040 self._departureMETAR.get_buffer().connect("changed", self._updateButtons)
[845]1041 mainBox.pack_start(metarWindow, True, True, 0)
1042
1043 PIREPViewer.addVFiller(mainBox)
1044
1045 dataBox = gtk.HBox()
1046 mainBox.pack_start(dataBox, False, False, 0)
1047
1048 label = gtk.Label("<b>" + xstr("pirepView_runway") + "</b>")
1049 label.set_use_markup(True)
1050 dataBox.pack_start(label, False, False, 0)
1051
1052 # FIXME: quite the same as the runway entry boxes in the wizard
1053 self._departureRunway = gtk.Entry()
1054 self._departureRunway.set_width_chars(5)
1055 self._departureRunway.set_tooltip_text(xstr("takeoff_runway_tooltip"))
1056 self._departureRunway.connect("changed", self._upperChanged)
1057 dataBox.pack_start(self._departureRunway, False, False, 8)
1058
1059 label = gtk.Label("<b>" + xstr("pirepView_sid") + "</b>")
1060 label.set_use_markup(True)
1061 dataBox.pack_start(label, False, False, 0)
1062
1063 # FIXME: quite the same as the SID combo box in
1064 # the flight wizard
1065 if pygobject:
1066 self._sid = gtk.ComboBox.new_with_model_and_entry(comboModel)
1067 else:
1068 self._sid = gtk.ComboBoxEntry(comboModel)
1069
1070 self._sid.set_entry_text_column(0)
1071 self._sid.get_child().set_width_chars(10)
1072 self._sid.set_tooltip_text(xstr("takeoff_sid_tooltip"))
1073 self._sid.connect("changed", self._upperChangedComboBox)
1074
1075 dataBox.pack_start(self._sid, False, False, 8)
1076
1077 return frame
1078
1079 def _buildArrivalFrame(self):
1080 """Build the frame for the arrival data."""
1081 (frame, mainBox) = PIREPViewer.createFrame(xstr("pirepView_frame_arrival"))
1082
1083 mainBox.pack_start(PIREPViewer.getLabel("METAR:"),
1084 False, False, 0)
1085 (metarWindow, self._arrivalMETAR) = \
1086 PIREPViewer.getTextWindow(heightRequest = -1,
1087 editable = True)
[846]1088 self._arrivalMETAR.get_buffer().connect("changed", self._updateButtons)
[845]1089 mainBox.pack_start(metarWindow, True, True, 0)
1090
1091 PIREPViewer.addVFiller(mainBox)
1092
1093 table = gtk.Table(2, 4)
1094 mainBox.pack_start(table, False, False, 0)
1095 table.set_row_spacings(4)
1096 table.set_col_spacings(8)
1097
1098 # FIXME: quite the same as in the wizard
1099 if pygobject:
1100 self._star = gtk.ComboBox.new_with_model_and_entry(comboModel)
1101 else:
1102 self._star = gtk.ComboBoxEntry(comboModel)
1103
1104 self._star.set_entry_text_column(0)
1105 self._star.get_child().set_width_chars(10)
1106 self._star.set_tooltip_text(xstr("landing_star_tooltip"))
1107 self._star.connect("changed", self._upperChangedComboBox)
1108
1109 PIREPEditor.tableAttachWidget(table, 0, 0,
1110 xstr("pirepView_star"),
1111 self._star)
1112
1113 # FIXME: quite the same as in the wizard
1114 if pygobject:
1115 self._transition = gtk.ComboBox.new_with_model_and_entry(comboModel)
1116 else:
1117 self._transition = gtk.ComboBoxEntry(comboModel)
1118
1119 self._transition.set_entry_text_column(0)
1120 self._transition.get_child().set_width_chars(10)
1121 self._transition.set_tooltip_text(xstr("landing_transition_tooltip"))
1122 self._transition.connect("changed", self._upperChangedComboBox)
1123
1124 PIREPEditor.tableAttachWidget(table, 2, 0,
1125 xstr("pirepView_transition"),
1126 self._transition)
1127
1128
1129 # FIXME: quite the same as in the wizard
1130 self._approachType = gtk.Entry()
1131 self._approachType.set_width_chars(10)
1132 self._approachType.set_tooltip_text(xstr("landing_approach_tooltip"))
1133 self._approachType.connect("changed", self._upperChanged)
1134
1135 PIREPEditor.tableAttachWidget(table, 0, 1,
1136 xstr("pirepView_approachType"),
1137 self._approachType)
1138
1139 # FIXME: quite the same as in the wizard
1140 self._arrivalRunway = gtk.Entry()
1141 self._arrivalRunway.set_width_chars(10)
1142 self._arrivalRunway.set_tooltip_text(xstr("landing_runway_tooltip"))
1143 self._arrivalRunway.connect("changed", self._upperChanged)
1144
1145 PIREPEditor.tableAttachWidget(table, 2, 1,
1146 xstr("pirepView_runway"),
1147 self._arrivalRunway)
1148
1149 return frame
1150
1151 def _buildStatisticsFrame(self):
1152 """Build the frame for the statistics data."""
1153 (frame, mainBox) = PIREPViewer.createFrame(xstr("pirepView_frame_statistics"))
1154
1155 table = gtk.Table(4, 4)
1156 mainBox.pack_start(table, False, False, 0)
1157 table.set_row_spacings(4)
1158 table.set_col_spacings(8)
1159 table.set_homogeneous(False)
1160
1161 self._blockTimeStart = \
1162 PIREPEditor.tableAttachTimeEntry(table, 0, 0,
1163 xstr("pirepView_blockTimeStart"))
[846]1164 self._blockTimeStart.connect("changed", self._updateButtons)
[845]1165
1166 self._blockTimeEnd = \
1167 PIREPEditor.tableAttachTimeEntry(table, 2, 0,
1168 xstr("pirepView_blockTimeEnd"))
[846]1169 self._blockTimeEnd.connect("changed", self._updateButtons)
[845]1170
1171 self._flightTimeStart = \
1172 PIREPEditor.tableAttachTimeEntry(table, 0, 1,
1173 xstr("pirepView_flightTimeStart"))
[846]1174 self._flightTimeStart.connect("changed", self._updateButtons)
[845]1175
1176 self._flightTimeEnd = \
1177 PIREPEditor.tableAttachTimeEntry(table, 2, 1,
1178 xstr("pirepView_flightTimeEnd"))
[846]1179 self._flightTimeEnd.connect("changed", self._updateButtons)
[845]1180
1181 self._flownDistance = PIREPViewer.getDataLabel(width = 3)
1182 PIREPEditor.tableAttachWidget(table, 0, 2,
1183 xstr("pirepView_flownDistance"),
1184 self._flownDistance)
1185
1186 self._fuelUsed = \
1187 PIREPEditor.tableAttachSpinButton(table, 2, 2,
1188 xstr("pirepView_fuelUsed"),
1189 1000000)
[846]1190 self._fuelUsed.connect("value-changed", self._updateButtons)
[845]1191
1192 self._rating = PIREPViewer.getDataLabel(width = 3)
1193 PIREPEditor.tableAttachWidget(table, 0, 3,
1194 xstr("pirepView_rating"),
1195 self._rating)
1196 return frame
1197
1198 def _buildMiscellaneousFrame(self):
1199 """Build the frame for the miscellaneous data."""
1200 (frame, mainBox) = PIREPViewer.createFrame(xstr("pirepView_frame_miscellaneous"))
1201
1202 table = gtk.Table(6, 2)
1203 mainBox.pack_start(table, False, False, 0)
1204 table.set_row_spacings(4)
1205 table.set_col_spacings(8)
1206 table.set_homogeneous(False)
1207
1208 self._flownNumPassengers = \
1209 PIREPEditor.tableAttachSpinButton(table, 0, 0,
1210 xstr("pirepView_numPassengers"),
1211 300)
[846]1212 self._flownNumPassengers.connect("value-changed", self._updateButtons)
[845]1213
1214 self._flownNumCrew = \
1215 PIREPEditor.tableAttachSpinButton(table, 2, 0,
1216 xstr("pirepView_numCrew"),
1217 10)
[846]1218 self._flownNumCrew.connect("value-changed", self._updateButtons)
[845]1219
1220 self._flownBagWeight = \
1221 PIREPEditor.tableAttachSpinButton(table, 0, 1,
1222 xstr("pirepView_bagWeight"),
1223 100000, width = 6)
1224
1225 self._flownCargoWeight = \
1226 PIREPEditor.tableAttachSpinButton(table, 2, 1,
1227 xstr("pirepView_cargoWeight"),
1228 100000, width = 6)
1229
1230 self._flownMailWeight = \
1231 PIREPEditor.tableAttachSpinButton(table, 4, 1,
1232 xstr("pirepView_mailWeight"),
1233 100000, width = 6)
1234
1235 self._flightType = createFlightTypeComboBox()
1236 PIREPEditor.tableAttachWidget(table, 0, 2,
1237 xstr("pirepView_flightType"),
1238 self._flightType)
1239
1240 self._online = gtk.CheckButton(xstr("pirepView_online"))
1241 table.attach(self._online, 2, 3, 2, 3)
1242
1243 PIREPViewer.addVFiller(mainBox)
1244
1245 mainBox.pack_start(PIREPViewer.getLabel(xstr("pirepView_delayCodes")),
1246 False, False, 0)
1247
1248 (textWindow, self._delayCodes) = PIREPViewer.getTextWindow()
1249 mainBox.pack_start(textWindow, False, False, 0)
1250
1251 return frame
1252
1253 def _buildCommentsTab(self):
1254 """Build the tab with the comments and flight defects."""
[846]1255 return FlightInfo(self._gui, callbackObject = self)
[845]1256
1257 def _buildLogTab(self):
1258 """Build the log tab."""
1259 mainBox = gtk.VBox()
1260
1261 (logWindow, self._log) = PIREPViewer.getTextWindow(heightRequest = -1)
1262 addFaultTag(self._log.get_buffer())
1263 mainBox.pack_start(logWindow, True, True, 0)
1264
1265 return mainBox
1266
1267 def _upperChanged(self, entry, arg = None):
1268 """Called when the value of some entry widget has changed and the value
1269 should be converted to uppercase."""
1270 entry.set_text(entry.get_text().upper())
[846]1271 self._updateButtons()
[845]1272 #self._valueChanged(entry, arg)
1273
1274 def _upperChangedComboBox(self, comboBox):
1275 """Called for combo box widgets that must be converted to uppercase."""
1276 entry = comboBox.get_child()
1277 if comboBox.get_active()==-1:
1278 entry.set_text(entry.get_text().upper())
[846]1279 self._updateButtons()
[845]1280 #self._valueChanged(entry)
1281
[846]1282 def _updateButtons(self, *kwargs):
1283 """Update the activity state of the buttons."""
1284 pirep = self._pirep
1285 bookedFlight = pirep.bookedFlight
1286
1287 departureMinutes = \
1288 bookedFlight.departureTime.hour*60 + bookedFlight.departureTime.minute
1289 departureDifference = abs(Flight.getMinutesDifference(self._blockTimeStart.minutes,
1290 departureMinutes))
1291 flightStartDifference = \
1292 Flight.getMinutesDifference(self._flightTimeStart.minutes,
1293 self._blockTimeStart.minutes)
1294 arrivalMinutes = \
1295 bookedFlight.arrivalTime.hour*60 + bookedFlight.arrivalTime.minute
1296 arrivalDifference = abs(Flight.getMinutesDifference(self._blockTimeEnd.minutes,
1297 arrivalMinutes))
1298 flightEndDifference = \
1299 Flight.getMinutesDifference(self._blockTimeEnd.minutes,
1300 self._flightTimeEnd.minutes)
1301
1302 timesOK = self._flightInfo.hasComments or \
1303 self._flightInfo.hasDelayCode or \
1304 (departureDifference<=Flight.TIME_ERROR_DIFFERENCE and
1305 arrivalDifference<=Flight.TIME_ERROR_DIFFERENCE and
1306 flightStartDifference>=0 and flightStartDifference<30 and
1307 flightEndDifference>=0 and flightEndDifference<30)
1308
1309 text = self._sid.get_child().get_text()
1310 sid = text if self._sid.get_active()!=0 and text and text!="N/A" \
1311 else None
1312
1313 text = self._star.get_child().get_text()
1314 star = text if self._star.get_active()!=0 and text and text!="N/A" \
1315 else None
1316
1317 text = self._transition.get_child().get_text()
1318 transition = text if self._transition.get_active()!=0 \
1319 and text and text!="N/A" else None
1320
1321
1322 buffer = self._userRoute.get_buffer()
1323 route = buffer.get_text(buffer.get_start_iter(),
1324 buffer.get_end_iter(), True)
1325
1326 self._okButton.set_sensitive(timesOK and
1327 self._flightInfo.faultsFullyExplained and
1328 self._flownNumPassengers.get_value_as_int()>0 and
1329 self._flownNumCrew.get_value_as_int()>2 and
1330 self._fuelUsed.get_value_as_int()>0 and
1331 self._departureRunway.get_text_length()>0 and
1332 self._arrivalRunway.get_text_length()>0 and
1333 self._departureMETAR.get_buffer().get_char_count()>0 and
1334 self._arrivalMETAR.get_buffer().get_char_count()>0 and
1335 self._filedCruiseLevel.get_value_as_int()>=50 and
1336 self._modifiedCruiseLevel.get_value_as_int()>=50 and
1337 sid is not None and (star is not None or
1338 transition is not None) and route!="" and
1339 self._approachType.get_text()!="")
1340
[845]1341#------------------------------------------------------------------------------
Note: See TracBrowser for help on using the repository browser.