Package com.bbn.openmap.plugin

Source Code of com.bbn.openmap.plugin.UTMGridPlugIn

// **********************************************************************
//
// <copyright>
//
//  BBN Technologies
//  10 Moulton Street
//  Cambridge, MA 02138
//  (617) 873-8000
//
//  Copyright (C) BBNT Solutions LLC. All rights reserved.
//
// </copyright>
// **********************************************************************
//
// $Source: /cvs/distapps/openmap/src/openmap/com/bbn/openmap/plugin/UTMGridPlugIn.java,v $
// $RCSfile: UTMGridPlugIn.java,v $
// $Revision: 1.8.2.9 $
// $Date: 2008/02/27 02:10:21 $
// $Author: dietrick $
//
// **********************************************************************

package com.bbn.openmap.plugin;

import java.awt.Color;
import java.awt.Component;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.Paint;
import java.awt.Point;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.Iterator;
import java.util.Properties;
import java.util.Vector;

import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JComboBox;
import javax.swing.JLabel;
import javax.swing.JPanel;

import com.bbn.openmap.I18n;
import com.bbn.openmap.LatLonPoint;
import com.bbn.openmap.omGraphics.DrawingAttributes;
import com.bbn.openmap.omGraphics.OMColorChooser;
import com.bbn.openmap.omGraphics.OMGeometry;
import com.bbn.openmap.omGraphics.OMGeometryList;
import com.bbn.openmap.omGraphics.OMGraphic;
import com.bbn.openmap.omGraphics.OMGraphicList;
import com.bbn.openmap.omGraphics.OMLine;
import com.bbn.openmap.omGraphics.OMText;
import com.bbn.openmap.omGraphics.geom.BasicGeometry;
import com.bbn.openmap.omGraphics.geom.PolygonGeometry;
import com.bbn.openmap.omGraphics.geom.PolylineGeometry;
import com.bbn.openmap.proj.Ellipsoid;
import com.bbn.openmap.proj.Projection;
import com.bbn.openmap.proj.coords.MGRSPoint;
import com.bbn.openmap.proj.coords.UTMPoint;
import com.bbn.openmap.util.Debug;
import com.bbn.openmap.util.PaletteHelper;
import com.bbn.openmap.util.PropUtils;
import com.bbn.openmap.util.quadtree.QuadTree;

/**
* The UTMGridPlugIn renders UTM Zone areas, and renders a grid marking
* equal-distance areas around the center of the current projection. This
* distance grid only extends east-west for 500km in both directions from the
* center of the current zone because that is the extent of accuracy for those
* measurements - after that, you get too far away from the central meridian for
* the current UTM zone.
* <p>
*
* Currently, this plugin only draws 100km distance squares. Updates on the way.
* The plugin has the following properties that may be set:
* <p>
*
* <pre>
*  
*  
*    # Turn zone area labels on when zoomed in closer than 1:33M (true
*    # is default)
*    showZones=true
*    showLabels=true
*    # Color for UTM Zone area boundaries
*    utmGridColor=hex AARRGGBB value
*    # Color for the distance area grid lines
*    distanceGridColor= hex AARRGGBB value
*    labelCutoffScale=scale to start showing labels, default is 33000000
*    show100KmGrid=false
*    utmGridColor
*    distanceGridColor
*    distanceGridResolution=0 (not shown by default, 1 = 10000 meter grid, 5 is 1 meter grid)
*    mgrsLabels=false
*   
* </pre>
*/
public class UTMGridPlugIn extends OMGraphicHandlerPlugIn {

    protected boolean UTM_DEBUG = false;
    protected boolean UTM_DEBUG_VERBOSE = false;

    public final static int INTERVAL_100K = 100000;
    public final static float DEFAULT_UTM_LABEL_CUTOFF_SCALE = 33000000;

    protected boolean showZones = true;
    protected boolean showLabels = true;
    protected float labelCutoffScale = DEFAULT_UTM_LABEL_CUTOFF_SCALE;
    protected boolean show100kGrid = false;
    protected boolean labelsAsMGRS = false;
    /**
     * Resolution should be MGRS accuracy, 0 for none, 1-5 otherwise, where 1 =
     * 10000 meter grid, 5 is 1 meter grid.
     */
    protected int distanceGridResolution = 0;
    protected Paint utmGridPaint = Color.black;
    protected Paint distanceGridPaint = Color.black;

    /**
     * Used to hold OMText UTM zone labels.
     */
    protected QuadTree labelTree;
    /**
     * Used for UTM zone labels.
     */
    protected OMGraphicList labelList;
    /**
     * The vertical list of OMLines used for UTM zones.
     */
    protected OMGraphicList verticalList;
    /**
     * The horizontal list of OMLines used for UTM zones.
     */
    protected OMGraphicList horizontalList;

    public final static String ShowLabelsProperty = "showLabels";
    public final static String ShowZonesProperty = "showZones";
    public final static String LabelCutoffScaleProperty = "labelCutoffScale";
    public final static String Show100kGridProperty = "show100KmGrid";
    public final static String UTMGridColorProperty = "utmGridColor";
    public final static String DistanceGridColorProperty = "distanceGridColor";
    public final static String DistanceGridResolutionProperty = "distanceGridResolution";
    public final static String LabelsAsMGRSProperty = "mgrsLabels";

    public UTMGridPlugIn() {
        UTM_DEBUG = Debug.debugging("utmgrid");
        UTM_DEBUG_VERBOSE = Debug.debugging("utmgrid_verbose");
    }

    protected OMGeometryList createUTMZoneVerticalLines() {

        OMGeometryList verticalList = new OMGeometryList();
        float[] points = null;

        for (int lon = -180; lon < 180; lon += 6) {
            if (lon == 6) {
                points = new float[] { 56f, lon, -80f, lon };
            } else if (lon > 6 && lon < 42) {
                points = new float[] { 72f, lon, -80f, lon };
            } else {
                points = new float[] { 84f, lon, -80f, lon };
            }
            verticalList.add(new PolylineGeometry.LL(points, OMGraphic.DECIMAL_DEGREES, OMGraphic.LINETYPE_GREATCIRCLE));
        }

        points = new float[] { 72f, 6f, 64f, 6f };
        verticalList.add(new PolylineGeometry.LL(points, OMGraphic.DECIMAL_DEGREES, OMGraphic.LINETYPE_GREATCIRCLE));

        points = new float[] { 64f, 3f, 56f, 3f };
        verticalList.add(new PolylineGeometry.LL(points, OMGraphic.DECIMAL_DEGREES, OMGraphic.LINETYPE_GREATCIRCLE));

        points = new float[] { 84f, 9f, 72f, 9f };
        verticalList.add(new PolylineGeometry.LL(points, OMGraphic.DECIMAL_DEGREES, OMGraphic.LINETYPE_GREATCIRCLE));

        points = new float[] { 84f, 21f, 72f, 21f };
        verticalList.add(new PolylineGeometry.LL(points, OMGraphic.DECIMAL_DEGREES, OMGraphic.LINETYPE_GREATCIRCLE));

        points = new float[] { 84f, 33f, 72f, 33f };
        verticalList.add(new PolylineGeometry.LL(points, OMGraphic.DECIMAL_DEGREES, OMGraphic.LINETYPE_GREATCIRCLE));

        verticalList.setLinePaint(utmGridPaint);

        return verticalList;
    }

    protected OMGeometryList createUTMZoneHorizontalLines() {
        OMGeometryList horizontalList = new OMGeometryList();
        float[] points = null;

        for (float lat = -80f; lat <= 72f; lat += 8f) {
            points = new float[] { lat, -180f, lat, -90f, lat, 0f, lat, 90f,
                    lat, 180f };
            horizontalList.add(new PolylineGeometry.LL(points, OMGraphic.DECIMAL_DEGREES, OMGraphic.LINETYPE_RHUMB));
        }

        points = new float[] { 84f, -180f, 84f, -90f, 84f, 0f, 84f, 90f, 84f,
                180f };
        horizontalList.add(new PolylineGeometry.LL(points, OMGraphic.DECIMAL_DEGREES, OMGraphic.LINETYPE_RHUMB));

        horizontalList.setLinePaint(utmGridPaint);

        return horizontalList;
    }

    protected QuadTree createUTMZoneLabels() {

        QuadTree labelTree = new QuadTree();

        // Need to use MGRSPoint to get MGRS zone letters, the UTM
        // zone letters are N and S for the hemisphere, which isn't
        // very interesting.
        UTMPoint utm = new MGRSPoint();
        LatLonPoint llp = new LatLonPoint();
        float latitude;
        float longitude;

        for (int lat = -80; lat <= 72; lat += 8) {
            for (int lon = -180; lon < 180; lon += 6) {

                latitude = (float) lat;
                longitude = (float) lon;

                if (lat == 56 && lon == 6) {
                    longitude = 3f;
                } else if (lat == 72 && (lon > 0 && lon < 42)) {
                    continue;
                }
                llp.setLatLon(latitude, longitude);
                addLabel(llp, UTMPoint.LLtoUTM(llp, utm), labelTree);
            }
        }

        latitude = 72f;
        llp.setLatLon(latitude, 9f);
        addLabel(llp, UTMPoint.LLtoUTM(llp, utm), labelTree);
        llp.setLongitude(21f);
        addLabel(llp, UTMPoint.LLtoUTM(llp, utm), labelTree);
        llp.setLongitude(33f);
        addLabel(llp, UTMPoint.LLtoUTM(llp, utm), labelTree);

        return labelTree;
    }

    protected QuadTree createMGRSZoneLabels() {

        QuadTree labelTree = new QuadTree();

        // Need to use MGRSPoint to get MGRS zone letters, the UTM
        // zone letters are N and S for the hemisphere, which isn't
        // very interesting.
        MGRSPoint mgrs = new MGRSPoint();
        LatLonPoint llp = new LatLonPoint();
        float latitude;
        float longitude;

        for (int lat = -80; lat <= 72; lat += 8) {
            for (int lon = -180; lon < 180; lon += 6) {

                latitude = (float) lat;
                longitude = (float) lon;

                if (lat == 56 && lon == 6) {
                    longitude = 3f;
                } else if (lat == 72 && (lon > 0 && lon < 42)) {
                    continue;
                }
                llp.setLatLon(latitude, longitude);
                addLabel(llp, MGRSPoint.LLtoMGRS(llp, mgrs), labelTree);
            }
        }

        latitude = 72f;
        llp.setLatLon(latitude, 9f);
        addLabel(llp, MGRSPoint.LLtoMGRS(llp, mgrs), labelTree);
        llp.setLongitude(21f);
        addLabel(llp, MGRSPoint.LLtoMGRS(llp, mgrs), labelTree);
        llp.setLongitude(33f);
        addLabel(llp, MGRSPoint.LLtoMGRS(llp, mgrs), labelTree);

        return labelTree;
    }

    protected void addLabel(LatLonPoint llp, UTMPoint utm, QuadTree labelTree) {
        float latitude = llp.getLatitude();
        float longitude = llp.getLongitude();
        labelTree.put(latitude,
                longitude,
                new OMText(latitude, longitude, 2, -2, utm.zone_number + ""
                        + utm.zone_letter, OMText.JUSTIFY_LEFT));
    }

    /**
     * Called to create 100km distance grid lines. Was originally designed to
     * accept different gridLineInterval distances, but has only been debugged
     * and tested for 100000.
     *
     * @param utm the UTMPoint of the center of the area to create lines for.
     */
    protected OMGraphicList createEquiDistanceLines(UTMPoint utm,
                                                    int gridLineInterval) {

        OMGraphicList list = new OMGraphicList();

        // Used to calculate the endpoints of the horizontal lines.
        UTMPoint utm1 = new UTMPoint(utm);
        UTMPoint utm2 = new UTMPoint(utm);
        LatLonPoint point1 = new LatLonPoint();
        LatLonPoint point2 = new LatLonPoint();

        // Used to calculate the pieces of the vertical lines.
        UTMPoint utmp = new UTMPoint(utm);
        LatLonPoint llp = new LatLonPoint();

        int i;
        OMLine line;
        BasicGeometry poly;

        float lat2;
        int endNorthing = (int) Math.floor(utm.northing / INTERVAL_100K) + 10;
        int startNorthing = (int) Math.floor(utm.northing / INTERVAL_100K) - 10;

        int numVertLines = 9;
        int numHorLines = endNorthing - startNorthing;

        float[][] vertPoints = new float[numVertLines][numHorLines * 2];

        if (UTM_DEBUG_VERBOSE) {
            Debug.output("Array is [" + vertPoints.length + "]["
                    + vertPoints[0].length + "]");
        }

        int coordCount = 0;
        boolean doPolys = true;

        utm1.easting = INTERVAL_100K;
        utm2.easting = 9 * INTERVAL_100K;

        // Horizontal lines
        for (i = startNorthing; i < endNorthing; i++) {
            utm1.northing = (float) i * gridLineInterval;
            utm2.northing = utm1.northing;
            utmp.northing = utm1.northing;

            if (doPolys) {
                for (int j = 0; j < numVertLines; j++) {
                    utmp.easting = (float) (j + 1) * gridLineInterval;
                    llp = utmp.toLatLonPoint(Ellipsoid.WGS_84, llp);

                    vertPoints[j][coordCount] = llp.getLatitude();
                    vertPoints[j][coordCount + 1] = llp.getLongitude();

                    if (UTM_DEBUG_VERBOSE) {
                        Debug.output("for vline " + j + ", point " + i
                                + ", easting: " + utmp.easting + ", northing: "
                                + utmp.northing + ", lat:"
                                + vertPoints[j][coordCount] + ", lon:"
                                + vertPoints[j][coordCount + 1]);
                    }
                }
                coordCount += 2;
            }

            point1 = utm1.toLatLonPoint(Ellipsoid.WGS_84, point1);
            point2 = utm2.toLatLonPoint(Ellipsoid.WGS_84, point2);

            lat2 = point1.getLatitude();

            if (lat2 < 84f) {
                line = new OMLine(point1.getLatitude(), point1.getLongitude(), point2.getLatitude(), point2.getLongitude(), OMGraphic.LINETYPE_GREATCIRCLE);
                line.setLinePaint(distanceGridPaint);
                list.add(line);
            }
        }

        if (doPolys) {
            OMGeometryList polys = new OMGeometryList();
            for (i = 0; i < vertPoints.length; i++) {
                if (UTM_DEBUG_VERBOSE) {
                    for (int k = 0; k < vertPoints[i].length; k += 2) {
                        System.out.println(" for poly " + i + ": lat = "
                                + vertPoints[i][k] + ", lon = "
                                + vertPoints[i][k + 1]);
                    }
                }
                poly = new PolylineGeometry.LL(vertPoints[i], OMGraphic.DECIMAL_DEGREES, OMGraphic.LINETYPE_GREATCIRCLE);
                polys.add(poly);
            }
            polys.setLinePaint(distanceGridPaint);
            list.add(polys);
        } else {

            // This doesn't seem to calculate the right
            // lines, although it looks like it should.

            if (UTM_DEBUG) {
                Debug.output("Doing vertical lines");
            }

            utm1.northing = startNorthing;
            utm2.northing = endNorthing;

            // Vertical lines
            for (i = 1; i <= 9; i++) {
                utm1.easting = i * 100000f;
                utm2.easting = i * 100000f;

                point1 = utm1.toLatLonPoint(Ellipsoid.WGS_84, point1);
                point2 = utm2.toLatLonPoint(Ellipsoid.WGS_84, point2);

                line = new OMLine(point1.getLatitude(), point1.getLongitude(), point2.getLatitude(), point2.getLongitude(), OMGraphic.LINETYPE_GREATCIRCLE);
                line.setLinePaint(distanceGridPaint);
                list.add(line);
            }
        }

        return list;
    }

    /**
     * Create a list of rectangles representing equal areas of MGRS coordinates
     * around a lat/lon location. The rectangles are laid out on the MGRS grid,
     * their size determined by the accuracy limitation given, which reflects
     * how many digits are provided in a MGRS coordinate. Uses WGS 84 ellipsoid.
     *
     * @param llp the lat/lon point of concern.
     * @param accuracy the number of digits for northing and easting values of a
     *        MGRS coordinate, which implicitly translates to meters - 5 (1
     *        meter) to 1 (10,000 meter).
     * @param numRects the number of rectangles in each direction from the llp
     *        to create.
     */
    protected OMGeometryList createMGRSRectangles(LatLonPoint llp,
                                                  int accuracy, int numRects) {
        return createMGRSRectangles(llp, accuracy, numRects, Ellipsoid.WGS_84);
    }

    /**
     * Create a list of rectangles representing equal areas of MGRS coordinates
     * around a lat/lon location. The rectangles are laid out on the MGRS grid,
     * their size determined by the accuracy limitation given, which reflects
     * how many digits are provided in a MGRS coordinate.
     *
     * @param llp the lat/lon point of concern.
     * @param accuracy the number of digits for northing and easting values of a
     *        MGRS coordinate, which implicitly translates to meters - 5 (1
     *        meter) to 1 (10,000 meter).
     * @param numRects the number of rectangles in each direction from the llp
     *        to create.
     * @param ellipsoid the ellipsoid to use.
     */
    protected OMGeometryList createMGRSRectangles(LatLonPoint llp,
                                                  int accuracy, int numRects,
                                                  Ellipsoid ellipsoid) {
        MGRSPoint mgrs = new MGRSPoint();
        mgrs.setAccuracy(accuracy);
        MGRSPoint.LLtoMGRS(llp, ellipsoid, mgrs);

        float accuracyBonus = 100000f / (float) Math.pow(10, accuracy);

        OMGeometryList list = new OMGeometryList();

        for (float i = -numRects * accuracyBonus; i < numRects * accuracyBonus; i += accuracyBonus) {
            for (float j = -numRects * accuracyBonus; j < numRects
                    * accuracyBonus; j += accuracyBonus) {
                if (Debug.debugging("utmdistancegrid")) {
                    System.out.print(".");
                }
                list.add(createMGRSRectangle(mgrs,
                        i,
                        j,
                        accuracyBonus,
                        ellipsoid));
            }
            if (Debug.debugging("utmdistancegrid")) {
                System.out.println("");
            }
        }

        return list;
    }

    /**
     * Create a polygon representing an equi-distant area, at a meters offset
     * with a meters interval.
     *
     * @param mgrsBasePoint the center point of interest that has been
     *        normalized for the units of the rectangle (meters, km, etc).
     * @param voffset vertical offset in meters, normalized for units, for
     *        entire polygon.
     * @param hoffset horizontal offset in meters, normalized for units, for
     *        entire polygon.
     * @param interval edge length of rectangle polygon in meters, normalized
     *        for units.
     * @param ellipsoid Ellipsoid for coordinate translation.
     */
    protected OMGeometry createMGRSRectangle(MGRSPoint mgrsBasePoint,
                                             float voffset, float hoffset,
                                             float interval, Ellipsoid ellipsoid) {

        float[] llpoints = new float[10];

        float easting = mgrsBasePoint.easting + hoffset;
        float northing = mgrsBasePoint.northing + voffset;
        int zone_number = mgrsBasePoint.zone_number;
        char zone_letter = mgrsBasePoint.zone_letter;

        LatLonPoint llp1 = new LatLonPoint();
        MGRSPoint.MGRStoLL(ellipsoid,
                northing,
                easting,
                zone_number,
                zone_letter,
                llp1);
        llpoints[0] = llp1.getLatitude();
        llpoints[1] = llp1.getLongitude();
        llpoints[8] = llp1.getLatitude();
        llpoints[9] = llp1.getLongitude();

        MGRSPoint.MGRStoLL(ellipsoid,
                northing,
                easting + interval,
                zone_number,
                zone_letter,
                llp1);
        llpoints[2] = llp1.getLatitude();
        llpoints[3] = llp1.getLongitude();

        MGRSPoint.MGRStoLL(ellipsoid,
                northing + interval,
                easting + interval,
                zone_number,
                zone_letter,
                llp1);
        llpoints[4] = llp1.getLatitude();
        llpoints[5] = llp1.getLongitude();

        MGRSPoint.MGRStoLL(ellipsoid,
                northing + interval,
                easting,
                zone_number,
                zone_letter,
                llp1);
        llpoints[6] = llp1.getLatitude();
        llpoints[7] = llp1.getLongitude();

        MGRSPoint mgrs = new MGRSPoint(northing, easting, zone_number, zone_letter);
        mgrs.resolve(mgrsBasePoint.getAccuracy());
        // MGRSPoint.MGRStoLL(mgrs, ellipsoid, llp1);
        String mgrsString = mgrs.getMGRS();

        if (Debug.debugging("utmgriddetail"))
            Debug.output(" - assigning " + mgrsString + " to poly with "
                    + mgrs.getAccuracy());

        PolygonGeometry poly = new PolygonGeometry.LL(llpoints, OMGraphic.DECIMAL_DEGREES, (interval <= 1000 ? OMGraphic.LINETYPE_STRAIGHT
                : OMGraphic.LINETYPE_GREATCIRCLE));
        poly.setAppObject(mgrsString);
        return poly;
    }

    /**
     * The getRectangle call is the main call into the PlugIn module. The module
     * is expected to fill the graphics list with objects that are within the
     * screen parameters passed.
     *
     * @param p projection of the screen, holding scale, center coords, height,
     *        width.
     */
    public OMGraphicList getRectangle(Projection p) {

        OMGraphicList list = getList();

        if (verticalList == null) {
            verticalList = createUTMZoneVerticalLines();
            horizontalList = createUTMZoneHorizontalLines();
            if (labelsAsMGRS) {
                labelTree = createMGRSZoneLabels();
            } else {
                labelTree = createUTMZoneLabels();
            }
        }

        list.clear();

        if (showZones) {
            list.add(verticalList);
            list.add(horizontalList);
        }

        LatLonPoint center = p.getCenter();
        UTMPoint utm = new UTMPoint(center);

        if (show100kGrid) {
            Debug.message("utmgrid", "Creating 100k distance lines...");

            OMGraphicList hunKLines = createEquiDistanceLines(utm, 100000);
            list.add(hunKLines);
        }

        if (distanceGridResolution > 0) {
            Debug.message("utmgrid", "Creating distance lines...");

            float decisionAid = 100000f / (float) Math.pow(10,
                    distanceGridResolution);
            float dglc = 30f * decisionAid; // distance grid label
            // cutoff
            // Debug.output("Basing decision to display labels on " +
            // dglc);

            int numberBasedForScale = (int) (p.getScale() / (2 * decisionAid));
            if (numberBasedForScale > 10) {
                numberBasedForScale = 10;
            }
            // Debug.output(numberBasedForScale + "");

            OMGeometryList geoList = createMGRSRectangles(center,
                    distanceGridResolution,
                    numberBasedForScale);

            if (showLabels && p.getScale() <= dglc) {
                Debug.message("utmgrid",
                        "Creating labels for distance lines ...");

                OMGraphicList textList = new OMGraphicList();
                LatLonPoint llp = new LatLonPoint();
                Point point = new Point();
                Iterator it = geoList.iterator();
                while (it.hasNext()) {
                    PolygonGeometry.LL pll = (PolygonGeometry.LL) it.next();
                    String labelString = (String) (pll).getAppObject();
                    if (labelString == null) {
                        continue;
                    }
                    float[] ll = pll.getLatLonArray();
                    llp.setLatLon(ll[0], ll[1], true);

                    p.forward(llp, point);

                    double x = point.getX();
                    double y = point.getY();
                    int buffer = 20;

                    // Lame attempt of testing whether the label is
                    // on-screen
                    if ((x > -buffer || x < p.getWidth() + buffer)
                            && (y > -buffer || y < p.getHeight() + buffer)) {

                        OMText label = new OMText(llp.getLatitude(), llp.getLongitude(), 4, -4, labelString, OMText.JUSTIFY_LEFT);
                        label.setLinePaint(distanceGridPaint);
                        textList.add(label);
                    }
                }
                list.add(textList);
            }

            geoList.setLinePaint(distanceGridPaint);
            list.add(geoList);
        }

        if (labelList != null) {
            labelList.clear();
        } else {
            labelList = new OMGraphicList();
        }

        if (showLabels && p.getScale() <= labelCutoffScale) {
            Debug.message("utmgrid", "Creating labels for map...");
            LatLonPoint ul = p.getUpperLeft();
            LatLonPoint lr = p.getLowerRight();

            Vector labels = labelTree.get(ul.getLatitude(),
                    ul.getLongitude(),
                    lr.getLatitude(),
                    lr.getLongitude());

            labelList.setTargets(labels);
            labelList.setLinePaint(getUTMGridPaint());
            list.add(labelList);
        }

        Debug.message("utmgrid", "Generating OMGraphics...");
        list.generate(p);
        Debug.message("utmgrid", "Done.");
        return list;
    } // end getRectangle

    public Component getGUI() {
        JPanel panel = new JPanel();

        GridBagLayout gridbag = new GridBagLayout();
        GridBagConstraints c = new GridBagConstraints();
        panel.setLayout(gridbag);

        JCheckBox setZonesButton = new JCheckBox(i18n.get(UTMGridPlugIn.class,
                "setZonesButton",
                "Show UTM Zone Grid"), showZones);
        setZonesButton.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent ae) {
                JCheckBox button = (JCheckBox) ae.getSource();
                showZones = button.isSelected();
                doPrepare();
            }
        });
        c.gridy = 0;
        c.anchor = GridBagConstraints.WEST;
        gridbag.setConstraints(setZonesButton, c);
        panel.add(setZonesButton);

        JCheckBox set100kGridButton = new JCheckBox(i18n.get(UTMGridPlugIn.class,
                "set100kGridButton",
                "Show 100Km Distance Grid"), show100kGrid);
        set100kGridButton.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent ae) {
                JCheckBox button = (JCheckBox) ae.getSource();
                show100kGrid = button.isSelected();
                doPrepare();
            }
        });

        c.gridy = 1;
        gridbag.setConstraints(set100kGridButton, c);
        panel.add(set100kGridButton);

        JCheckBox setLabelsButton = new JCheckBox(i18n.get(UTMGridPlugIn.class,
                "setLabelsButton",
                "Show Zone Labels"), showLabels);
        setLabelsButton.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent ae) {
                JCheckBox button = (JCheckBox) ae.getSource();
                showLabels = button.isSelected();
                doPrepare();
            }
        });
        c.gridy = 2;
        gridbag.setConstraints(setLabelsButton, c);
        panel.add(setLabelsButton);

        JPanel resPanel = PaletteHelper.createPaletteJPanel(i18n.get(UTMGridPlugIn.class,
                "resPanel",
                "Distance Grid Units"));

        String[] resStrings = {
                i18n.get(UTMGridPlugIn.class, "resStrings.noGrid", " No Grid "),
                i18n.get(UTMGridPlugIn.class,
                        "resStrings.10000m",
                        " 10,000 meter   "),
                i18n.get(UTMGridPlugIn.class,
                        "resStrings.1000m",
                        " 1000 meter "),
                i18n.get(UTMGridPlugIn.class, "resStrings.100m", " 100 meter "),
                i18n.get(UTMGridPlugIn.class, "resStrings.10m", " 10 meter "),
                i18n.get(UTMGridPlugIn.class, "resStrings.1m", " 1 meter ") };

        JComboBox resList = new JComboBox(resStrings);
        resList.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                JComboBox jcb = (JComboBox) e.getSource();
                setDistanceGridResolution(jcb.getSelectedIndex());
                doPrepare();
            }
        });
        resList.setSelectedIndex(getDistanceGridResolution());

        resPanel.add(resList);

        c.gridy = 3;
        c.anchor = GridBagConstraints.CENTER;
        gridbag.setConstraints(resPanel, c);
        panel.add(resPanel);

        JButton utmGridColorButton = new JButton(DrawingAttributes.getIconForPaint(getUTMGridPaint(),
                true));
        utmGridColorButton.setContentAreaFilled(false);
        utmGridColorButton.setBorder(null);
        utmGridColorButton.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent ae) {
                Color tmpPaint = getNewPaint((Component) ae.getSource(),
                        i18n.get(UTMGridPlugIn.class,
                                "utmGridColorChooser",
                                "Choose UTM Grid Color"),
                        (Color) getUTMGridPaint());
                if (tmpPaint != null) {
                    setUTMGridPaint(tmpPaint);
                    ((JButton) ae.getSource()).setIcon(DrawingAttributes.getIconForPaint(tmpPaint,
                            true));
                    doPrepare();
                }
            }
        });

        JLabel utmGridLabel = new JLabel(i18n.get(UTMGridPlugIn.class,
                "utmGridColorButton",
                "Set UTM Grid Color"));

        JPanel utmGridPanel = new JPanel();
        utmGridPanel.add(utmGridColorButton);
        utmGridPanel.add(utmGridLabel);

        c.gridy = 4;
        c.anchor = GridBagConstraints.WEST;
        gridbag.setConstraints(utmGridPanel, c);
        panel.add(utmGridPanel);

        JButton distGridColorButton = new JButton(DrawingAttributes.getIconForPaint(getDistanceGridPaint(),
                true));
        distGridColorButton.setContentAreaFilled(false);
        distGridColorButton.setBorder(null);
        distGridColorButton.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent ae) {
                Color tmpPaint = getNewPaint((Component) ae.getSource(),
                        i18n.get(UTMGridPlugIn.class,
                                "distanceGridColorChooser",
                                "Choose Distance Grid Color"),
                        (Color) getDistanceGridPaint());
                if (tmpPaint != null) {
                    setDistanceGridPaint(tmpPaint);
                    ((JButton) ae.getSource()).setIcon(DrawingAttributes.getIconForPaint(tmpPaint,
                            true));
                    doPrepare();
                }
            }
        });
        JLabel distanceGridLabel = new JLabel(i18n.get(UTMGridPlugIn.class,
                "distGridColorButton",
                "Set Distance Grid Color"));
        JPanel distGridPanel = new JPanel();
        distGridPanel.add(distGridColorButton);
        distGridPanel.add(distanceGridLabel);
        c.gridy = 5;
        gridbag.setConstraints(distGridPanel, c);
        panel.add(distGridPanel);

        return panel;
    }

    /**
     * A convenience method to get a color from a JColorChooser. Null will be
     * returned if the JColorChooser lock is in place, or if something else is
     * done where the JColorChooser would normally return null.
     *
     * @param source the source component for the JColorChooser.
     * @param title the String to label the JColorChooser window.
     * @param startingColor the color to give to the JColorChooser to start
     *        with. Returned if the cancel button is pressed.
     * @return Color chosen from the JColorChooser, null if lock for chooser
     *         can't be sequired.
     */
    protected Color getNewPaint(Component source, String title,
                                Color startingColor) {
        Color newPaint = null;
        if (getLock()) {
            newPaint = OMColorChooser.showDialog(source, title, startingColor);
            releaseLock();
        }
        return newPaint;
    }

    /**
     * A lock to use to limit the number of JColorChoosers that can pop up for a
     * given DrawingAttributes GUI.
     */
    private boolean colorChooserLock = false;

    /**
     * Get the lock to use a JColorChooser. Returns true if you got the lock,
     * false if you didn't.
     */
    protected synchronized boolean getLock() {
        if (colorChooserLock == false) {
            colorChooserLock = true;
            return colorChooserLock;
        } else {
            return false;
        }
    }

    /**
     * Release the lock on the JColorChooser.
     */
    protected synchronized void releaseLock() {
        colorChooserLock = false;
    }

    public void setProperties(String prefix, Properties props) {
        super.setProperties(prefix, props);
        prefix = PropUtils.getScopedPropertyPrefix(prefix);

        showLabels = PropUtils.booleanFromProperties(props, prefix
                + ShowLabelsProperty, showLabels);
        showZones = PropUtils.booleanFromProperties(props, prefix
                + ShowZonesProperty, showZones);
        show100kGrid = PropUtils.booleanFromProperties(props, prefix
                + Show100kGridProperty, show100kGrid);
        labelCutoffScale = PropUtils.floatFromProperties(props, prefix
                + LabelCutoffScaleProperty, labelCutoffScale);
        utmGridPaint = PropUtils.parseColorFromProperties(props, prefix
                + UTMGridColorProperty, utmGridPaint);
        distanceGridPaint = PropUtils.parseColorFromProperties(props, prefix
                + DistanceGridColorProperty, distanceGridPaint);
        setDistanceGridResolution(PropUtils.intFromProperties(props, prefix
                + DistanceGridResolutionProperty, distanceGridResolution));
        labelsAsMGRS = PropUtils.booleanFromProperties(props, prefix
                + LabelsAsMGRSProperty, labelsAsMGRS);
    }

    public Properties getProperties(Properties props) {
        props = super.getProperties(props);

        String prefix = PropUtils.getScopedPropertyPrefix(this);
        props.put(prefix + ShowLabelsProperty, Boolean.toString(showLabels));
        props.put(prefix + ShowZonesProperty, new Boolean(showZones).toString());
        props.put(prefix + LabelCutoffScaleProperty,
                Float.toString(labelCutoffScale));
        props.put(prefix + Show100kGridProperty, Boolean.toString(show100kGrid));
        props.put(prefix + UTMGridColorProperty,
                Integer.toHexString(((Color) utmGridPaint).getRGB()));
        props.put(prefix + DistanceGridColorProperty,
                Integer.toHexString(((Color) distanceGridPaint).getRGB()));
        props.put(prefix + DistanceGridResolutionProperty,
                Integer.toString(distanceGridResolution));
        props.put(prefix + LabelsAsMGRSProperty, Boolean.toString(labelsAsMGRS));
        return props;
    }

    public Properties getPropertyInfo(Properties props) {
        props = super.getPropertyInfo(props);
        String interString;

        interString = i18n.get(UTMGridPlugIn.class,
                ShowZonesProperty,
                I18n.TOOLTIP,
                "Show UTM Zone Grid Lines.");
        props.put(ShowZonesProperty, interString);
        interString = i18n.get(UTMGridPlugIn.class,
                ShowZonesProperty,
                ShowZonesProperty);
        props.put(ShowZonesProperty + LabelEditorProperty, interString);
        props.put(ShowZonesProperty + ScopedEditorProperty,
                "com.bbn.openmap.util.propertyEditor.YesNoPropertyEditor");

        interString = i18n.get(UTMGridPlugIn.class,
                UTMGridColorProperty,
                I18n.TOOLTIP,
                "Color for UTM Zone Grid lines.");
        props.put(UTMGridColorProperty, interString);
        interString = i18n.get(UTMGridPlugIn.class,
                UTMGridColorProperty,
                UTMGridColorProperty);
        props.put(UTMGridColorProperty + LabelEditorProperty, interString);
        props.put(UTMGridColorProperty + ScopedEditorProperty,
                "com.bbn.openmap.util.propertyEditor.ColorPropertyEditor");

        interString = i18n.get(UTMGridPlugIn.class,
                ShowLabelsProperty,
                I18n.TOOLTIP,
                "Show Labels for Grid Lines");
        props.put(ShowLabelsProperty, interString);
        interString = i18n.get(UTMGridPlugIn.class,
                ShowLabelsProperty,
                ShowLabelsProperty);
        props.put(ShowLabelsProperty + LabelEditorProperty, interString);
        props.put(ShowLabelsProperty + ScopedEditorProperty,
                "com.bbn.openmap.util.propertyEditor.YesNoPropertyEditor");

        interString = i18n.get(UTMGridPlugIn.class,
                Show100kGridProperty,
                I18n.TOOLTIP,
                "Show 100Km Distance Grid Lines");
        props.put(Show100kGridProperty, interString);
        interString = i18n.get(UTMGridPlugIn.class,
                Show100kGridProperty,
                Show100kGridProperty);
        props.put(Show100kGridProperty + LabelEditorProperty, interString);
        props.put(Show100kGridProperty + ScopedEditorProperty,
                "com.bbn.openmap.util.propertyEditor.YesNoPropertyEditor");

        interString = i18n.get(UTMGridPlugIn.class,
                DistanceGridColorProperty,
                I18n.TOOLTIP,
                "Color for Equal-Distance Grid Lines.");
        props.put(DistanceGridColorProperty, interString);
        interString = i18n.get(UTMGridPlugIn.class,
                DistanceGridColorProperty,
                DistanceGridColorProperty);
        props.put(DistanceGridColorProperty + LabelEditorProperty, interString);
        props.put(DistanceGridColorProperty + ScopedEditorProperty,
                "com.bbn.openmap.util.propertyEditor.ColorPropertyEditor");

        interString = i18n.get(UTMGridPlugIn.class,
                DistanceGridResolutionProperty,
                I18n.TOOLTIP,
                "Meter Resolution for Distance Grid Lines (0-5)");
        props.put(DistanceGridResolutionProperty, interString);
        interString = i18n.get(UTMGridPlugIn.class,
                DistanceGridResolutionProperty,
                DistanceGridResolutionProperty);
        props.put(DistanceGridResolutionProperty + LabelEditorProperty,
                interString);

        PropUtils.setI18NPropertyInfo(i18n,
                props,
                UTMGridPlugIn.class,
                LabelsAsMGRSProperty,
                "Labels as MGRS",
                "Flag to display labels in MGRS notation, or UTM.",
                "com.bbn.openmap.util.propertyEditor.YesNoPropertyEditor");

        props.put(initPropertiesProperty, ShowZonesProperty + " "
                + UTMGridColorProperty + " " + Show100kGridProperty + " "
                + ShowLabelsProperty + " " + DistanceGridResolutionProperty
                + " " + DistanceGridColorProperty + " " + LabelsAsMGRSProperty);
        return props;
    }

    public void setShowZones(boolean value) {
        showZones = value;
    }

    public boolean isShowZones() {
        return showZones;
    }

    public void setShowLabels(boolean value) {
        showLabels = value;
    }

    public boolean isShowLabels() {
        return showLabels;
    }

    public void setLabelCutoffScale(float value) {
        labelCutoffScale = value;
    }

    public float getLabelCutoffScale() {
        return labelCutoffScale;
    }

    public void setShow100kGrid(boolean value) {
        show100kGrid = value;
    }

    public boolean isShow100kGrid() {
        return show100kGrid;
    }

    /**
     * Resolution should be MGRS accuracy, 0 for none, 1-5 otherwise, where 1 =
     * 10000 meter grid, 5 is 1 meter grid.
     */
    public void setDistanceGridResolution(int value) {
        distanceGridResolution = value;
        if (distanceGridResolution < 0
                || distanceGridResolution > MGRSPoint.ACCURACY_1_METER) {
            distanceGridResolution = 0;
        }
    }

    public int getDistanceGridResolution() {
        return distanceGridResolution;
    }

    public void setUTMGridPaint(Paint value) {
        utmGridPaint = value;

        if (verticalList != null) {
            verticalList.setLinePaint(getUTMGridPaint());
            horizontalList.setLinePaint(getUTMGridPaint());
        }
    }

    public Paint getUTMGridPaint() {
        return utmGridPaint;
    }

    public void setDistanceGridPaint(Paint value) {
        distanceGridPaint = value;
    }

    public Paint getDistanceGridPaint() {
        return distanceGridPaint;
    }
}
TOP

Related Classes of com.bbn.openmap.plugin.UTMGridPlugIn

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.