import java.text.*;
import java.util.prefs.*;
import java.util.concurrent.*;
+import org.altusmetrum.AltosLib.*;
public class AltosIgniteUI
- extends JDialog
+ extends AltosDialog
implements ActionListener
{
AltosDevice device;
- AltosIgnite ignite;
JFrame owner;
JLabel label;
JRadioButton apogee;
JToggleButton arm;
JButton fire;
javax.swing.Timer timer;
+ JButton close;
int apogee_status;
int main_status;
int time_remaining;
boolean timer_running;
+ LinkedBlockingQueue<String> command_queue;
+
+ class IgniteHandler implements Runnable {
+ AltosIgnite ignite;
+ JFrame owner;
+
+ void send_exception(Exception e) {
+ final Exception f_e = e;
+ Runnable r = new Runnable() {
+ public void run() {
+ ignite_exception(f_e);
+ }
+ };
+ SwingUtilities.invokeLater(r);
+ }
+
+ public void run () {
+ try {
+ AltosSerial serial = new AltosSerial(device);
+ serial.set_frame(owner);
+ ignite = new AltosIgnite(serial,
+ !device.matchProduct(Altos.product_altimeter));
+
+ } catch (Exception e) {
+ send_exception(e);
+ return;
+ }
+
+ for (;;) {
+ Runnable r;
+
+ try {
+ String command = command_queue.take();
+ String reply = null;
+
+ if (command.equals("get_status")) {
+ apogee_status = ignite.status(AltosIgnite.Apogee);
+ main_status = ignite.status(AltosIgnite.Main);
+ reply = "status";
+ } else if (command.equals("main")) {
+ ignite.fire(AltosIgnite.Main);
+ reply = "fired";
+ } else if (command.equals("apogee")) {
+ ignite.fire(AltosIgnite.Apogee);
+ reply = "fired";
+ } else if (command.equals("quit")) {
+ ignite.close();
+ break;
+ } else {
+ throw new ParseException(String.format("invalid command %s", command), 0);
+ }
+ final String f_reply = reply;
+ r = new Runnable() {
+ public void run() {
+ ignite_reply(f_reply);
+ }
+ };
+ SwingUtilities.invokeLater(r);
+ } catch (Exception e) {
+ send_exception(e);
+ }
+ }
+ }
+
+ public IgniteHandler(JFrame in_owner) {
+ owner = in_owner;
+ }
+ }
+
+ void ignite_exception(Exception e) {
+ if (e instanceof FileNotFoundException) {
+ JOptionPane.showMessageDialog(owner,
+ ((FileNotFoundException) e).getMessage(),
+ "Cannot open target device",
+ JOptionPane.ERROR_MESSAGE);
+ } else if (e instanceof AltosSerialInUseException) {
+ JOptionPane.showMessageDialog(owner,
+ String.format("Device \"%s\" already in use",
+ device.toShortString()),
+ "Device in use",
+ JOptionPane.ERROR_MESSAGE);
+ } else if (e instanceof IOException) {
+ IOException ee = (IOException) e;
+ JOptionPane.showMessageDialog(owner,
+ device.toShortString(),
+ ee.getLocalizedMessage(),
+ JOptionPane.ERROR_MESSAGE);
+ } else {
+ JOptionPane.showMessageDialog(owner,
+ String.format("Connection to \"%s\" failed",
+ device.toShortString()),
+ "Connection Failed",
+ JOptionPane.ERROR_MESSAGE);
+ }
+ close();
+ }
+
+ void ignite_reply(String reply) {
+ if (reply.equals("status")) {
+ set_ignite_status();
+ } else if (reply.equals("fired")) {
+ fired();
+ }
+ }
+
void set_arm_text() {
if (arm.isSelected())
arm.setText(String.format("%d", time_remaining));
stop_timer();
}
- void get_ignite_status() throws InterruptedException, TimeoutException {
- apogee_status = ignite.status(AltosIgnite.Apogee);
- main_status = ignite.status(AltosIgnite.Main);
+ void send_command(String command) {
+ try {
+ command_queue.put(command);
+ } catch (Exception ex) {
+ ignite_exception(ex);
+ }
+ }
+
+ boolean getting_status = false;
+
+ boolean visible = false;
+ void set_ignite_status() {
+ getting_status = false;
+ apogee_status_label.setText(String.format("\"%s\"", AltosIgnite.status_string(apogee_status)));
+ main_status_label.setText(String.format("\"%s\"", AltosIgnite.status_string(main_status)));
+ if (!visible) {
+ visible = true;
+ setVisible(true);
+ }
+ }
+
+ void poll_ignite_status() {
+ if (!getting_status) {
+ getting_status = true;
+ send_command("get_status");
+ }
}
- void set_ignite_status() throws InterruptedException, TimeoutException {
- get_ignite_status();
- apogee_status_label.setText(String.format("\"%s\"", ignite.status_string(apogee_status)));
- main_status_label.setText(String.format("\"%s\"", ignite.status_string(main_status)));
+ boolean firing = false;
+
+ void start_fire(String which) {
+ if (!firing) {
+ firing = true;
+ send_command(which);
+ }
+ }
+
+ void fired() {
+ firing = false;
+ cancel();
}
void close() {
+ send_command("quit");
timer.stop();
setVisible(false);
- ignite.close();
- }
-
- void abort() {
- close();
- JOptionPane.showMessageDialog(owner,
- String.format("Connection to \"%s\" failed",
- device.toShortString()),
- "Connection Failed",
- JOptionPane.ERROR_MESSAGE);
+ dispose();
}
void tick_timer() {
else
set_arm_text();
}
- try {
- set_ignite_status();
- } catch (InterruptedException ie) {
- abort();
- } catch (TimeoutException te) {
- abort();
- }
+ poll_ignite_status();
}
void fire() {
if (arm.isEnabled() && arm.isSelected() && time_remaining > 0) {
- int igniter = AltosIgnite.None;
+ String igniter = "none";
if (apogee.isSelected() && !main.isSelected())
- igniter = AltosIgnite.Apogee;
+ igniter = "apogee";
else if (main.isSelected() && !apogee.isSelected())
- igniter = AltosIgnite.Main;
- ignite.fire(igniter);
+ igniter = "main";
+ send_command(igniter);
cancel();
}
}
}
private boolean open() {
- device = AltosDeviceDialog.show(owner, AltosDevice.product_any);
+ command_queue = new LinkedBlockingQueue<String>();
+
+ device = AltosDeviceDialog.show(owner, Altos.product_any);
if (device != null) {
- try {
- ignite = new AltosIgnite(device);
+ IgniteHandler handler = new IgniteHandler(owner);
+ Thread t = new Thread(handler);
+ t.start();
return true;
- } catch (FileNotFoundException ee) {
- JOptionPane.showMessageDialog(owner,
- String.format("Cannot open device \"%s\"",
- device.toShortString()),
- "Cannot open target device",
- JOptionPane.ERROR_MESSAGE);
- } catch (AltosSerialInUseException si) {
- JOptionPane.showMessageDialog(owner,
- String.format("Device \"%s\" already in use",
- device.toShortString()),
- "Device in use",
- JOptionPane.ERROR_MESSAGE);
- } catch (IOException ee) {
- JOptionPane.showMessageDialog(owner,
- device.toShortString(),
- ee.getLocalizedMessage(),
- JOptionPane.ERROR_MESSAGE);
- }
}
return false;
}
c.fill = GridBagConstraints.NONE;
c.anchor = GridBagConstraints.CENTER;
c.insets = i;
- c.weightx = 1;
- c.weighty = 1;
+ c.weightx = 0;
+ c.weighty = 0;
c.gridx = 0;
c.gridy = 0;
main_status_label = new JLabel();
pane.add(main_status_label, c);
- try {
- set_ignite_status();
- } catch (InterruptedException ie) {
- abort();
- return;
- } catch (TimeoutException te) {
- abort();
- return;
- }
-
c.gridx = 0;
c.gridy = 3;
c.gridwidth = 1;
fire.addActionListener(this);
fire.setActionCommand("fire");
+ c.gridx = 0;
+ c.gridy = 4;
+ c.gridwidth = 2;
+ c.anchor = GridBagConstraints.CENTER;
+ close = new JButton ("Close");
+ pane.add(close, c);
+ close.addActionListener(this);
+ close.setActionCommand("close");
+
pack();
setLocationRelativeTo(owner);
- setVisible(true);
addWindowListener(new ConfigListener(this));
}