From: Keith Packard Date: Tue, 23 Jun 2015 03:08:05 +0000 (-0700) Subject: altosdroid: Select tracker by clicking on map X-Git-Tag: 1.6.0.3~14 X-Git-Url: https://git.gag.com/?p=fw%2Faltos;a=commitdiff_plain;h=0f56903774d9e8bb033dfc0af6945e8ddc1d3065 altosdroid: Select tracker by clicking on map This lets you pick a tracker from the map, rather than having to use the menu. Signed-off-by: Keith Packard --- diff --git a/altosdroid/Notebook b/altosdroid/Notebook index c0ba2098..6804aa5d 100644 --- a/altosdroid/Notebook +++ b/altosdroid/Notebook @@ -15,14 +15,6 @@ Desired AltosDroid feature list *) Monitor-idle mode - *) Select tracker by clicking map - - *) Auto select tracker after long delay - - *) Evaluate performance issues - - *) Merge offline/online maps into single tab with mode - *) Make voice responses depend on selected tab *) Monitor TeleMega igniters @@ -96,3 +88,19 @@ Completed features *) TeleBT battery voltage Done + + *) Evaluate performance issues + + Done. Offline maps were duplicating tabs at every redisplay. + + *) Merge offline/online maps into single tab with mode + + Done. + + *) Auto select tracker after long delay + + Done. + + *) Select tracker by clicking map + + Done. diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroid.java b/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroid.java index f6645105..c5da6d0e 100644 --- a/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroid.java +++ b/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroid.java @@ -18,10 +18,9 @@ package org.altusmetrum.AltosDroid; import java.lang.ref.WeakReference; -import java.util.ArrayList; -import java.util.Timer; -import java.util.TimerTask; import java.text.*; +import java.util.*; +import java.io.*; import android.app.Activity; import android.app.PendingIntent; @@ -248,11 +247,13 @@ public class AltosDroid extends FragmentActivity implements AltosUnitsListener { } } + int selected_serial = 0; int current_serial; long switch_time; void set_switch_time() { switch_time = System.currentTimeMillis(); + selected_serial = 0; } boolean registered_units_listener; @@ -262,6 +263,9 @@ public class AltosDroid extends FragmentActivity implements AltosUnitsListener { if (new_telemetry_state != null) telemetry_state = new_telemetry_state; + if (selected_serial != 0) + current_serial = selected_serial; + if (current_serial == 0) current_serial = telemetry_state.latest_serial; @@ -271,6 +275,7 @@ public class AltosDroid extends FragmentActivity implements AltosUnitsListener { } serials = telemetry_state.states.keySet().toArray(new Integer[0]); + Arrays.sort(serials); update_title(telemetry_state); @@ -282,7 +287,9 @@ public class AltosDroid extends FragmentActivity implements AltosUnitsListener { int age = state_age(state); if (age < 20) aged = false; - if (switch_time != 0 && (switch_time - state.received_time) > 0) + if (current_serial == selected_serial) + aged = false; + else if (switch_time != 0 && (switch_time - state.received_time) > 0) aged = true; } @@ -828,13 +835,26 @@ public class AltosDroid extends FragmentActivity implements AltosUnitsListener { void select_tracker(int serial) { int i; - for (i = 0; i < serials.length; i++) - if (serials[i] == serial) - break; - if (i == serials.length) + + AltosDebug.debug("select tracker %d\n", serial); + + if (serial == selected_serial) { + AltosDebug.debug("%d already selected\n", serial); return; + } + + if (serial != 0) { + for (i = 0; i < serials.length; i++) + if (serials[i] == serial) + break; - current_serial = serial; + if (i == serials.length) { + AltosDebug.debug("attempt to select unknown tracker %d\n", serial); + return; + } + } + + current_serial = selected_serial = serial; update_state(null); } @@ -933,15 +953,19 @@ public class AltosDroid extends FragmentActivity implements AltosUnitsListener { return true; case R.id.select_tracker: if (serials != null) { - String[] trackers = new String[serials.length]; + String[] trackers = new String[serials.length+1]; + trackers[0] = "Auto"; for (int i = 0; i < serials.length; i++) - trackers[i] = String.format("%d", serials[i]); + trackers[i+1] = String.format("%d", serials[i]); AlertDialog.Builder builder_serial = new AlertDialog.Builder(this); builder_serial.setTitle("Select a tracker"); builder_serial.setItems(trackers, new DialogInterface.OnClickListener() { public void onClick(DialogInterface dialog, int item) { - select_tracker(serials[item]); + if (item == 0) + select_tracker(0); + else + select_tracker(serials[item-1]); } }); AlertDialog alert_serial = builder_serial.create(); diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroidMapInterface.java b/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroidMapInterface.java index 681cd311..7aff1341 100644 --- a/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroidMapInterface.java +++ b/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroidMapInterface.java @@ -23,7 +23,7 @@ import android.location.Location; import org.altusmetrum.altoslib_7.*; public interface AltosDroidMapInterface { - public void onCreateView(int map_type); + public void onCreateView(AltosDroid altos_droid); public void set_visible(boolean visible); diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/AltosMapOffline.java b/altosdroid/src/org/altusmetrum/AltosDroid/AltosMapOffline.java index 3ff6ff25..12dd2f25 100644 --- a/altosdroid/src/org/altusmetrum/AltosDroid/AltosMapOffline.java +++ b/altosdroid/src/org/altusmetrum/AltosDroid/AltosMapOffline.java @@ -36,7 +36,9 @@ import android.util.*; class Rocket implements Comparable { AltosLatLon position; String name; + int serial; long last_packet; + boolean active; AltosMapOffline map_offline; void paint() { @@ -49,14 +51,18 @@ class Rocket implements Comparable { this.last_packet = last_packet; } - Rocket(String name, AltosMapOffline map_offline) { - this.name = name; - this.map_offline = map_offline; + void set_active(boolean active) { + this.active = active; } public int compareTo(Object o) { Rocket other = (Rocket) o; + if (active && !other.active) + return 1; + if (other.active && !active) + return -1; + long diff = last_packet - other.last_packet; if (diff > 0) @@ -65,12 +71,19 @@ class Rocket implements Comparable { return -1; return 0; } + + Rocket(int serial, AltosMapOffline map_offline) { + this.serial = serial; + this.name = String.format("%d", serial); + this.map_offline = map_offline; + } } public class AltosMapOffline extends View implements ScaleGestureDetector.OnScaleGestureListener, AltosMapInterface, AltosDroidMapInterface { ScaleGestureDetector scale_detector; boolean scaling; AltosMap map; + AltosDroid altos_droid; AltosLatLon here; AltosLatLon pad; @@ -236,6 +249,24 @@ public class AltosMapOffline extends View implements ScaleGestureDetector.OnScal public void set_zoom_label(String label) { } + public void select_object(AltosLatLon latlon) { + if (map.transform == null) + return; + for (Rocket rocket : sorted_rockets()) { + if (rocket.position == null) { + debug("rocket %d has no position\n", rocket.serial); + continue; + } + double distance = map.transform.hypot(latlon, rocket.position); + debug("check select %d distance %g width %d\n", rocket.serial, distance, rocket_bitmap.getWidth()); + if (distance < rocket_bitmap.getWidth() * 2.0) { + debug("selecting %d\n", rocket.serial); + altos_droid.select_tracker(rocket.serial); + break; + } + } + } + class Line { AltosLatLon a, b; @@ -295,16 +326,20 @@ public class AltosMapOffline extends View implements ScaleGestureDetector.OnScal } } + private Rocket[] sorted_rockets() { + Rocket[] rocket_array = rockets.values().toArray(new Rocket[0]); + + Arrays.sort(rocket_array); + return rocket_array; + } + private void draw_positions() { line.set_a(map.last_position); line.set_b(here); line.paint(); draw_bitmap(pad, pad_bitmap, pad_off_x, pad_off_y); - Rocket[] rocket_array = rockets.values().toArray(new Rocket[0]); - - Arrays.sort(rocket_array); - for (Rocket rocket : rocket_array) + for (Rocket rocket : sorted_rockets()) rocket.paint(); draw_bitmap(here, here_bitmap, here_off_x, here_off_y); } @@ -379,6 +414,8 @@ public class AltosMapOffline extends View implements ScaleGestureDetector.OnScal map.touch_start((int) event.getX(), (int) event.getY(), true); } else if (event.getAction() == MotionEvent.ACTION_MOVE) { map.touch_continue((int) event.getX(), (int) event.getY(), true); + } else if (event.getAction() == MotionEvent.ACTION_UP) { + map.touch_stop((int) event.getX(), (int) event.getY(), true); } return true; } @@ -425,11 +462,13 @@ public class AltosMapOffline extends View implements ScaleGestureDetector.OnScal if (rockets.containsKey(serial)) rocket = rockets.get(serial); else { - rocket = new Rocket(String.format("%d", serial), this); + rocket = new Rocket(serial, this); rockets.put(serial, rocket); } if (t_state.gps != null) rocket.set_position(new AltosLatLon(t_state.gps.lat, t_state.gps.lon), t_state.received_time); + if (state != null) + rocket.set_active(state.serial == serial); } } if (receiver != null) { @@ -437,9 +476,10 @@ public class AltosMapOffline extends View implements ScaleGestureDetector.OnScal } } - public void onCreateView(int map_type) { + public void onCreateView(AltosDroid altos_droid) { + this.altos_droid = altos_droid; map = new AltosMap(this); - map.set_maptype(map_type); + map.set_maptype(altos_droid.map_type); pad_bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.pad); /* arrow at the bottom of the launchpad image */ @@ -464,6 +504,7 @@ public class AltosMapOffline extends View implements ScaleGestureDetector.OnScal public AltosMapOffline(Context context, AttributeSet attrs) { super(context, attrs); + this.altos_droid = altos_droid; scale_detector = new ScaleGestureDetector(context, this); } } diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/AltosMapOnline.java b/altosdroid/src/org/altusmetrum/AltosDroid/AltosMapOnline.java index 9503a0bd..3f5f32be 100644 --- a/altosdroid/src/org/altusmetrum/AltosDroid/AltosMapOnline.java +++ b/altosdroid/src/org/altusmetrum/AltosDroid/AltosMapOnline.java @@ -121,7 +121,11 @@ public class AltosMapOnline implements AltosDroidMapInterface { private AltosLatLon my_position = null; private AltosLatLon target_position = null; - public void onCreateView(final int map_type) { + private AltosDroid altos_droid; + + public void onCreateView(AltosDroid altos_droid) { + this.altos_droid = altos_droid; + final int map_type = altos_droid.map_type; mMapFragment = new SupportMapFragment() { @Override public void onActivityCreated(Bundle savedInstanceState) { diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/TabMap.java b/altosdroid/src/org/altusmetrum/AltosDroid/TabMap.java index 9c39e105..cd59dfe7 100644 --- a/altosdroid/src/org/altusmetrum/AltosDroid/TabMap.java +++ b/altosdroid/src/org/altusmetrum/AltosDroid/TabMap.java @@ -57,14 +57,6 @@ public class TabMap extends AltosDroidTab { super.onCreate(savedInstanceState); } - private void make_offline_map() { - } - - private void make_online_map() { - map_online = new AltosMapOnline(view.getContext()); - map_online.onCreateView(altos_droid.map_type); - } - @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { view = inflater.inflate(R.layout.tab_map, container, false); @@ -77,9 +69,9 @@ public class TabMap extends AltosDroidTab { mReceiverLatitudeView = (TextView)view.findViewById(R.id.receiver_lat_value); mReceiverLongitudeView = (TextView)view.findViewById(R.id.receiver_lon_value); map_offline = (AltosMapOffline)view.findViewById(R.id.map_offline); - map_offline.onCreateView(altos_droid.map_type); + map_offline.onCreateView(altos_droid); map_online = new AltosMapOnline(view.getContext()); - map_online.onCreateView(altos_droid.map_type); + map_online.onCreateView(altos_droid); set_map_source(AltosDroidPreferences.map_source()); return view; } diff --git a/altoslib/AltosMap.java b/altoslib/AltosMap.java index adf52ab9..8d12a180 100644 --- a/altoslib/AltosMap.java +++ b/altoslib/AltosMap.java @@ -391,6 +391,10 @@ public class AltosMap implements AltosMapTileListener, AltosMapStoreListener { AltosPointInt drag_start; + boolean dragged; + + static final double drag_far = 20; + private void drag(int x, int y) { if (drag_start == null) return; @@ -398,6 +402,11 @@ public class AltosMap implements AltosMapTileListener, AltosMapStoreListener { int dx = x - drag_start.x; int dy = y - drag_start.y; + double distance = Math.hypot(dx, dy); + + if (distance > drag_far) + dragged = true; + if (transform == null) { debug("Transform not set in drag\n"); return; @@ -410,6 +419,12 @@ public class AltosMap implements AltosMapTileListener, AltosMapStoreListener { private void drag_start(int x, int y) { drag_start = new AltosPointInt(x, y); + dragged = false; + } + + private void drag_stop(int x, int y) { + if (!dragged) + map_interface.select_object (transform.screen_lat_lon(new AltosPointInt(x,y))); } private void line_start(int x, int y) { @@ -442,6 +457,12 @@ public class AltosMap implements AltosMapTileListener, AltosMapStoreListener { line(x, y); } + public void touch_stop(int x, int y, boolean is_drag) { + notice_user_input(); + if (is_drag) + drag_stop(x, y); + } + public AltosMap(AltosMapInterface map_interface) { this.map_interface = map_interface; cache = new AltosMapCache(map_interface); diff --git a/altoslib/AltosMapInterface.java b/altoslib/AltosMapInterface.java index e6cb5971..7e8dd236 100644 --- a/altoslib/AltosMapInterface.java +++ b/altoslib/AltosMapInterface.java @@ -42,4 +42,6 @@ public interface AltosMapInterface { public abstract void set_zoom_label(String label); public abstract void debug(String format, Object ... arguments); + + public abstract void select_object(AltosLatLon latlon); } diff --git a/altoslib/AltosMapTransform.java b/altoslib/AltosMapTransform.java index 30994ecb..11ed4eb9 100644 --- a/altoslib/AltosMapTransform.java +++ b/altoslib/AltosMapTransform.java @@ -51,6 +51,13 @@ public class AltosMapTransform { return new AltosPointDouble(screen.x + offset_x, screen.y + offset_y); } + public double hypot(AltosLatLon a, AltosLatLon b) { + AltosPointDouble a_pt = point(a); + AltosPointDouble b_pt = point(b); + + return Math.hypot(a_pt.x - b_pt.x, a_pt.y - b_pt.y); + } + public AltosLatLon screen_lat_lon(AltosPointInt screen) { return lat_lon(screen_point(screen)); } diff --git a/altosuilib/AltosUIMapNew.java b/altosuilib/AltosUIMapNew.java index 246222bc..8ac18296 100644 --- a/altosuilib/AltosUIMapNew.java +++ b/altosuilib/AltosUIMapNew.java @@ -358,10 +358,15 @@ public class AltosUIMapNew extends JComponent implements AltosFlightDisplay, Alt zoom_label.setText(label); } + public void select_object(AltosLatLon latlon) { + debug("select at %f,%f\n", latlon.lat, latlon.lon); + } + public void debug(String format, Object ... arguments) { System.out.printf(format, arguments); } + /* AltosFlightDisplay interface */ public void set_font() {