// **********************************************************************
//
//<copyright>
//
//BBN Technologies, a Verizon Company
//10 Moulton Street
//Cambridge, MA 02138
//(617) 873-8000
//
//Copyright (C) BBNT Solutions LLC. All rights reserved.
//
//</copyright>
//**********************************************************************
//
//$Source:
///cvs/darwars/ambush/aar/src/com/bbn/ambush/mission/MissionHandler.java,v
//$
//$RCSfile: GeoCrossDemoLayer.java,v $
//$Revision: 1.1.2.1 $
//$Date: 2005/08/09 21:17:55 $
//$Author: dietrick $
//
//**********************************************************************
package com.bbn.openmap.layer.test;
import java.awt.BasicStroke;
import java.awt.Color;
import java.util.Iterator;
import com.bbn.openmap.geo.Geo;
import com.bbn.openmap.geo.Intersection;
import com.bbn.openmap.layer.editor.EditorLayer;
import com.bbn.openmap.omGraphics.OMAction;
import com.bbn.openmap.omGraphics.OMGraphic;
import com.bbn.openmap.omGraphics.OMGraphicList;
import com.bbn.openmap.omGraphics.OMLine;
import com.bbn.openmap.omGraphics.OMPoint;
import com.bbn.openmap.util.Debug;
/**
* This layer was developed to provide a simple picture of how vector
* cross products work with Geos to solve intersection problems. The
* best way to use this class is to turn off all other layers and put
* the map in Orthographic projection. When the layer is active, a
* series of buttons will appear in the ToolPanel, allowing you to
* draw Great Circle lines. It's helpful to change the color of each
* line before you create it, so you can see the relationship of the
* line to the previous one drawn.
* <P>
*
* This layer will interate through the list if drawn lines, looking
* for the intersection point between consecutive lines. For each
* line, a point will be drawn in that line's color representing the
* cross-normalized point for the line's enpoints - that is, it's the
* point perpendicular to the great circle plane created by the line.
* You can also think of it as the point that is 90 degrees away from
* every point on the line. The dotted lines are the path from the
* previous line's crossNornmalized point and the current line's
* crossNormalized point. Lastly, the cross-normalization of the end
* points of the dashed line will result in the point where the
* original lines would intersect if they are close enough. Depending
* on the direction that the lines were drawn, that point may actually
* be the anitpode (on the other side of the sphere) of the point you
* are interested in, but this layer doesn't bother to investigate
* that yet.
* <P>
*
* That's all this layer does. The properties for this layer are:
*
* <pre>
* geocross.class=com.bbn.openmap.layer.test.GeoCrossDemoLayer
* geocross.prettyName=GEO Cross Demonstration
* geocross.editor=com.bbn.openmap.layer.editor.DrawingEditorTool
* geocross.showAttributes=true
* geocross.loaders=lines
* geocross.mouseModes=Gestures
* geocross.lines.class=com.bbn.openmap.tools.drawing.OMLineLoader
* </pre>
*
* @author dietrick
*/
public class GeoCrossDemoLayer extends EditorLayer {
protected OMGraphicList lines = new OMGraphicList();
/**
*
*/
public GeoCrossDemoLayer() {
super();
}
public OMGraphicList prepare() {
OMGraphicList list = getList();
if (list == null) {
list = new OMGraphicList();
} else {
list.clear();
}
OMLine oldLine = null;
Geo ogc = null;
for (Iterator it = lines.iterator(); it.hasNext();) {
OMLine line = (OMLine) it.next();
float[] ll = line.getLL();
Geo g1 = new Geo(ll[0], ll[1]);
Geo g2 = new Geo(ll[2], ll[3]);
Geo gc = g1.crossNormalize(g2);
OMPoint p = new OMPoint((float) gc.getLatitude(), (float) gc.getLongitude(), 3);
p.setLinePaint(line.getLinePaint());
p.setFillPaint(line.getFillPaint());
p.setStroke(line.getStroke());
line.addArrowHead(true);
list.add(line);
list.add(p);
if (oldLine != null) {
float[] ll2 = oldLine.getLL();
Geo g3 = new Geo(ll2[0], ll2[1]);
Geo g4 = new Geo(ll2[2], ll2[3]);
OMLine line2 = new OMLine((float) ogc.getLatitude(), (float) ogc.getLongitude(), (float) gc.getLatitude(), (float) gc.getLongitude(), OMGraphic.LINETYPE_GREATCIRCLE);
line2.setLinePaint(line.getLinePaint());
line2.setStroke(new BasicStroke(1, BasicStroke.CAP_BUTT, BasicStroke.JOIN_BEVEL, 0f, new float[] {
10, 10 }, 0f));
line2.addArrowHead(true);
list.add(line2);
Geo i = gc.crossNormalize(ogc);
if (!(Intersection.isOnSegment(g1, g2, i) || Intersection.isOnSegment(g3,
g4,
i))) {
i = i.antipode();
}
p = new OMPoint((float) i.getLatitude(), (float) i.getLongitude(), 3);
p.setOval(true);
p.setLinePaint(line.getLinePaint());
p.setFillPaint(Color.white);
p.setStroke(line.getStroke());
list.add(p);
}
oldLine = line;
ogc = gc;
}
list.generate(getProjection());
return list;
}
public void drawingComplete(OMGraphic omg, OMAction action) {
releaseProxyMouseMode();
if (omg instanceof OMLine && lines != null) {
lines.doAction(omg, action);
deselect(lines);
doPrepare();
} else {
Debug.error("Layer " + getName() + " received " + omg + " and "
+ action + " with no list ready");
}
// This is important!!
if (editorTool != null) {
editorTool.drawingComplete(omg, action);
}
}
}