AltosSiteMap: add autoscroll and grabndrag scroll
[fw/altos] / ao-tools / altosui / AltosSiteMap.java
index 420bfc813ac8eae9d41dfd3033b8c9701cbdb800..1db839597f8e05f0ade863cfa4a03f3f160612c4 100644 (file)
@@ -21,6 +21,7 @@ import java.awt.*;
 import java.awt.image.*;
 import java.awt.event.*;
 import javax.swing.*;
+import javax.swing.event.MouseInputAdapter;
 import javax.imageio.ImageIO;
 import javax.swing.table.*;
 import java.io.*;
@@ -31,129 +32,64 @@ import java.lang.Math;
 import java.awt.geom.Point2D;
 import java.awt.geom.Line2D;
 
-public class AltosSiteMap extends JComponent implements AltosFlightDisplay {
-    double lat, lng;
-    int zoom;
-    double scale_x, scale_y;
-    Point2D.Double coord_pt;
-    Point2D.Double last_pt;
-
-    Graphics2D g2d;
-
-    private void setLocation(double new_lat, double new_lng) {
-        int new_zoom = 15;
-        lat = new_lat;
-        lng = new_lng;
-        zoom = new_zoom;
-        scale_x = 256/360.0 * Math.pow(2, zoom);
-        scale_y = 256/(2.0*Math.PI) * Math.pow(2, zoom);
-        coord_pt = pt(lat, lng, new Point2D.Double(0,0));
-        coord_pt.x = 320-coord_pt.x;
-        coord_pt.y = 320-coord_pt.y;
-        last_pt = null;
-
-        try {
-            File pngfile = new File(AltosPreferences.logdir(), 
-                                    FileCoord(lat, lng, zoom));
-            System.out.printf("Trying file %s\n", pngfile);
-            BufferedImage myPicture = ImageIO.read(pngfile);
-            picLabel.setIcon(new ImageIcon( myPicture ));
-            g2d = myPicture.createGraphics();
-        } catch (Exception e) { 
-            throw new RuntimeException(e);
-        };
-    }
-
-    private static double limit(double v, double lo, double hi) {
-        if (v < lo)
-            return lo;
-        if (hi < v)
-            return hi;
-        return v;
-    }
-
-    private static String FileCoord(double lat, double lng, int zoom) {
-        char chlat = lat < 0 ? 'S' : 'N';
-        char chlng = lng < 0 ? 'E' : 'W';
-        if (lat < 0) lat = -lat;
-        if (lng < 0) lng = -lng;
-        return String.format("map-%c%.3f,%c%.3f-%d.png",
-                chlat, lat, chlng, lng, zoom);
-    }
-
-
-    // based on google js
-    //  http://maps.gstatic.com/intl/en_us/mapfiles/api-3/2/10/main.js
-    // search for fromLatLngToPoint and fromPointToLatLng
-    private Point2D.Double pt(double lat, double lng) {
-        return pt(lat, lng, coord_pt);
-    }
-
-    private Point2D.Double pt(double lat, double lng, Point2D.Double centre) {
-        Point2D.Double res = new Point2D.Double();
-        double e;
-
-        res.x = centre.x + lng*scale_x;
-        e = limit(Math.sin(Math.toRadians(lat)),-(1-1.0E-15),1-1.0E-15);
-        res.y = centre.y + 0.5*Math.log((1+e)/(1-e))*-scale_y;
-        return res;
-    }
-
-
+public class AltosSiteMap extends JScrollPane implements AltosFlightDisplay {
     public void reset() {
-        // ?
+        // nothing
     }
-
-    static Color stateColors[] = {
-        Color.WHITE,  // startup
-        Color.WHITE,  // idle
-        Color.WHITE,  // pad
-        Color.RED,    // boost
-        Color.PINK,   // fast
-        Color.YELLOW, // coast
-        Color.CYAN,   // drogue
-        Color.BLUE,   // main
-        Color.BLACK   // landed
-    };
-
     public void show(AltosState state, int crc_errors) {
-        if (!state.gps_ready && state.pad_lat == 0 && state.pad_lon == 0)
-            return;
-        double plat = (int)(state.pad_lat*200)/200.0;
-        double plon = (int)(state.pad_lon*200)/200.0;
+        for (int x = 0; x < mapTiles.length; x++) {
+            mapTiles[x].show(state, crc_errors);
+        }
+    }
+  
+    AltosSiteMapTile [] mapTiles = new AltosSiteMapTile[9];
+
+    class GrabNDrag extends MouseInputAdapter {
+        private JComponent scroll;
+        private Point startPt = new Point();
 
-        if (last_pt == null) {
-            setLocation(plat, plon);
+        public GrabNDrag(JComponent parent) {
+            scroll = parent;
         }
 
-        Point2D.Double pt = pt(state.gps.lat, state.gps.lon);
-        if (last_pt != null && pt != last_pt) {
-            if (0 <= state.state && state.state < stateColors.length) {
-                g2d.setColor(stateColors[state.state]);
-            }
-            g2d.draw(new Line2D.Double(last_pt, pt));
+        public void mousePressed(MouseEvent e) {
+            startPt.setLocation(e.getPoint());
+        }
+        public void mouseDragged(MouseEvent e) {
+            int xd = e.getX() - startPt.x;
+            int yd = e.getY() - startPt.y;
+
+            Rectangle r = scroll.getVisibleRect();
+            r.x -= xd;
+            r.y -= yd;
+            scroll.scrollRectToVisible(r);
         }
-        last_pt = pt;
-        repaint();
     }
-   
-    JLabel picLabel = new JLabel();
 
     public AltosSiteMap() {
+        JComponent comp = new JComponent() {
+            GrabNDrag scroller = new GrabNDrag(this);
+            {
+                addMouseMotionListener(scroller);
+                addMouseListener(scroller);
+                setAutoscrolls(true);
+            }
+        };
+
         GridBagLayout layout = new GridBagLayout();
-        setLayout(layout);
+        comp.setLayout(layout);
 
         GridBagConstraints c = new GridBagConstraints();
-
-        c.gridx = 0; c.gridy = 0;
-        c.weightx = 1; c.weighty = 1;
         c.anchor = GridBagConstraints.CENTER;
         c.fill = GridBagConstraints.BOTH;
-        picLabel = new JLabel();
-        JScrollPane scrollPane = new JScrollPane(picLabel);
-        layout.setConstraints(scrollPane, c);
-        add(scrollPane);
 
+        for (int x = 0; x < 9; x++) {
+            c.gridx = x % 3; c.gridy = x / 3;
+            mapTiles[x] = new AltosSiteMapTile((x%3)-1, (x/3)-1);
+            layout.setConstraints(mapTiles[x], c);
+            comp.add(mapTiles[x]);
+        }
+        setViewportView(comp);
     }
 }