summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKeith Packard <keithp@keithp.com>2010-11-25 15:56:42 -0800
committerKeith Packard <keithp@keithp.com>2010-11-25 16:30:19 -0800
commit12fb7f0e70cd244475d84469f93283112478d1e1 (patch)
treeeaada3e2ea3534f3c8d7eae1dc77f1c83651cb36
parentb74cec6cd0bc043f53e9e28472765aa343136813 (diff)
altosui: Only call swing display functions from main thread.
Swing insists that all display functions be called from a single thread, and the flight window wasn't following this for display updates. Use SwingUtilities.invokeLater to make sure the flight UI updates happen in the right context. Fixes a UI freeze on Mac OS. Signed-off-by: Keith Packard <keithp@keithp.com>
-rw-r--r--altosui/AltosDisplayThread.java49
1 files changed, 40 insertions, 9 deletions
diff --git a/altosui/AltosDisplayThread.java b/altosui/AltosDisplayThread.java
index 3e719130..84abfae9 100644
--- a/altosui/AltosDisplayThread.java
+++ b/altosui/AltosDisplayThread.java
@@ -38,11 +38,45 @@ public class AltosDisplayThread extends Thread {
int crc_errors;
AltosFlightDisplay display;
- synchronized void show(AltosState state, int crc_errors) {
+ void show_internal(AltosState state, int crc_errors) {
if (state != null)
display.show(state, crc_errors);
}
+ void show_safely(AltosState in_state, int in_crc_errors) {
+ final AltosState state = in_state;
+ final int crc_errors = in_crc_errors;
+ Runnable r = new Runnable() {
+ public void run() {
+ try {
+ show_internal(state, crc_errors);
+ } catch (Exception ex) {
+ }
+ }
+ };
+ SwingUtilities.invokeLater(r);
+ }
+
+ void reading_error_internal(String name) {
+ JOptionPane.showMessageDialog(parent,
+ String.format("Error reading from \"%s\"", name),
+ "Telemetry Read Error",
+ JOptionPane.ERROR_MESSAGE);
+ }
+
+ void reading_error_safely(String in_name) {
+ final String name = in_name;
+ Runnable r = new Runnable() {
+ public void run() {
+ try {
+ reading_error_internal(name);
+ } catch (Exception ex) {
+ }
+ }
+ };
+ SwingUtilities.invokeLater(r);
+ }
+
class IdleThread extends Thread {
boolean started;
@@ -102,7 +136,7 @@ public class AltosDisplayThread extends Thread {
++reported_landing;
if (state.state != Altos.ao_flight_landed) {
state.state = Altos.ao_flight_landed;
- show(state, 0);
+ show_safely(state, 0);
}
}
}
@@ -202,7 +236,6 @@ public class AltosDisplayThread extends Thread {
idle_thread = new IdleThread();
- display.reset();
try {
for (;;) {
try {
@@ -212,23 +245,20 @@ public class AltosDisplayThread extends Thread {
old_state = state;
state = new AltosState(record, state);
reader.update(state);
- show(state, crc_errors);
+ show_safely(state, crc_errors);
told = tell(state, old_state);
idle_thread.notice(state, told);
} catch (ParseException pp) {
System.out.printf("Parse error: %d \"%s\"\n", pp.getErrorOffset(), pp.getMessage());
} catch (AltosCRCException ce) {
++crc_errors;
- show(state, crc_errors);
+ show_safely(state, crc_errors);
}
}
} catch (InterruptedException ee) {
interrupted = true;
} catch (IOException ie) {
- JOptionPane.showMessageDialog(parent,
- String.format("Error reading from \"%s\"", name),
- "Telemetry Read Error",
- JOptionPane.ERROR_MESSAGE);
+ reading_error_safely(name);
} finally {
if (!interrupted)
idle_thread.report(true);
@@ -245,5 +275,6 @@ public class AltosDisplayThread extends Thread {
voice = in_voice;
display = in_display;
reader = in_reader;
+ display.reset();
}
}