2 * Copyright © 2010 Keith Packard <keithp@keithp.com>
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; version 2 of the License.
8 * This program is distributed in the hope that it will be useful, but
9 * WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 * General Public License for more details.
13 * You should have received a copy of the GNU General Public License along
14 * with this program; if not, write to the Free Software Foundation, Inc.,
15 * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
21 import java.awt.event.*;
23 import javax.swing.event.*;
25 import java.util.concurrent.*;
26 import java.util.Arrays;
27 import org.altusmetrum.altoslib_5.*;
28 import org.altusmetrum.altosuilib_3.*;
30 public class AltosIdleMonitorUI extends AltosUIFrame implements AltosFlightDisplay, AltosIdleMonitorListener, DocumentListener {
34 AltosInfoTable flightInfo;
35 AltosFlightStatus flightStatus;
36 AltosIdleMonitor thread;
44 } catch (InterruptedException ie) {
59 public void font_size_changed(int font_size) {
60 pad.font_size_changed(font_size);
61 flightInfo.font_size_changed(font_size);
64 public void units_changed(boolean imperial_units) {
65 pad.units_changed(imperial_units);
66 flightInfo.units_changed(imperial_units);
69 AltosFlightStatusUpdate status_update;
71 public void show(AltosState state, AltosListenerState listener_state) {
72 status_update.saved_state = state;
74 pad.show(state, listener_state);
75 flightStatus.show(state, listener_state);
76 flightInfo.show(state, listener_state);
77 // } catch (Exception e) {
78 // System.out.print("Show exception " + e);
82 public void update(final AltosState state, final AltosListenerState listener_state) {
83 Runnable r = new Runnable() {
85 show(state, listener_state);
88 SwingUtilities.invokeLater(r);
92 AltosFreqList frequencies;
93 JTextField callsign_value;
95 /* DocumentListener interface methods */
96 public void changedUpdate(DocumentEvent e) {
97 if (callsign_value != null) {
98 String callsign = callsign_value.getText();
99 thread.set_callsign(callsign);
100 AltosUIPreferences.set_callsign(callsign);
104 public void insertUpdate(DocumentEvent e) {
108 public void removeUpdate(DocumentEvent e) {
114 public GridBagConstraints constraints (int x, int width, int fill) {
115 GridBagConstraints c = new GridBagConstraints();
116 Insets insets = new Insets(4, 4, 4, 4);
121 c.anchor = GridBagConstraints.CENTER;
123 c.anchor = GridBagConstraints.EAST;
125 c.anchor = GridBagConstraints.WEST;
132 public GridBagConstraints constraints(int x, int width) {
133 return constraints(x, width, GridBagConstraints.NONE);
136 void idle_exception(JFrame owner, Exception e) {
137 if (e instanceof FileNotFoundException) {
138 JOptionPane.showMessageDialog(owner,
139 ((FileNotFoundException) e).getMessage(),
140 "Cannot open target device",
141 JOptionPane.ERROR_MESSAGE);
142 } else if (e instanceof AltosSerialInUseException) {
143 JOptionPane.showMessageDialog(owner,
144 String.format("Device \"%s\" already in use",
145 device.toShortString()),
147 JOptionPane.ERROR_MESSAGE);
148 } else if (e instanceof IOException) {
149 IOException ee = (IOException) e;
150 JOptionPane.showMessageDialog(owner,
151 device.toShortString(),
152 ee.getLocalizedMessage(),
153 JOptionPane.ERROR_MESSAGE);
155 JOptionPane.showMessageDialog(owner,
156 String.format("Connection to \"%s\" failed",
157 device.toShortString()),
159 JOptionPane.ERROR_MESSAGE);
163 public AltosIdleMonitorUI(JFrame in_owner)
164 throws FileNotFoundException, TimeoutException, InterruptedException {
166 device = AltosDeviceUIDialog.show(in_owner, Altos.product_any);
168 if (!device.matchProduct(Altos.product_altimeter))
171 serial = device.getSerial();
175 link = new AltosSerial(device);
176 } catch (Exception ex) {
177 idle_exception(in_owner, ex);
181 bag = getContentPane();
182 bag.setLayout(new GridBagLayout());
184 setTitle(String.format("AltOS %s", device.toShortString()));
186 /* Stick frequency selector at top of table for telemetry monitoring */
187 if (remote && serial >= 0) {
189 frequencies = new AltosFreqList(AltosUIPreferences.frequency(serial));
190 frequencies.addActionListener(new ActionListener() {
191 public void actionPerformed(ActionEvent e) {
192 double frequency = frequencies.frequency();
193 thread.set_frequency(frequency);
194 AltosUIPreferences.set_frequency(device.getSerial(),
198 bag.add (frequencies, constraints(0, 1));
199 bag.add (new JLabel("Callsign:"), constraints(1, 1));
200 /* Add callsign configuration */
201 callsign_value = new JTextField(AltosUIPreferences.callsign());
202 callsign_value.getDocument().addDocumentListener(this);
203 callsign_value.setToolTipText("Callsign sent in packet mode");
204 bag.add(callsign_value, constraints(2, 1, GridBagConstraints.BOTH));
209 /* Flight status is always visible */
210 flightStatus = new AltosFlightStatus();
211 bag.add(flightStatus, constraints(0, 3, GridBagConstraints.HORIZONTAL));
214 /* The rest of the window uses a tabbed pane to
215 * show one of the alternate data views
217 pane = new JTabbedPane();
219 pad = new AltosPad();
220 pane.add("Launch Pad", pad);
222 flightInfo = new AltosInfoTable();
223 pane.add("Table", new JScrollPane(flightInfo));
225 /* Make the tabbed pane use the rest of the window space */
226 bag.add(pane, constraints(0, 3, GridBagConstraints.BOTH));
228 setDefaultCloseOperation(JFrame.DO_NOTHING_ON_CLOSE);
230 AltosUIPreferences.register_font_listener(this);
232 addWindowListener(new WindowAdapter() {
234 public void windowClosing(WindowEvent e) {
237 } catch (Exception ex) {
238 System.out.printf("Exception %s\n", ex.toString());
239 for (StackTraceElement el : ex.getStackTrace())
240 System.out.printf("%s\n", el.toString());
244 AltosUIPreferences.unregister_font_listener(AltosIdleMonitorUI.this);
251 thread = new AltosIdleMonitor((AltosIdleMonitorListener) this, link, (boolean) remote);
253 status_update = new AltosFlightStatusUpdate(flightStatus);
255 new javax.swing.Timer(100, status_update).start();