📄 spatialpanel.java
字号:
package jwo.jpss.spatial.gui; // Part of the spatial GUI package.
import jwo.jpss.spatial.*; // For spatial classes.
import javax.swing.*; // For Swing components.
import javax.swing.text.*; // For text output.
import java.awt.*; // For cursor handling.
import java.awt.event.*; // For mouse events.
import java.awt.geom.*; // For affine transformations.
// **************************************************************
/** Panel for displaying spatial objects.
* @author Jo Wood.
* @version 1.1, 21st October, 2001.
*/
// **************************************************************
public class SpatialPanel extends JPanel
{
// --------------- Object and Class Variables ----------------
private JTextComponent output; // Component to report messages.
private SpatialModel spModel; // Spatial model to display.
private AffineTransform trans, // Georef to pixel transformation.
iTrans; // Pixel to georef transformation.
private static final int BORDER_SIZE = 5;
// --------------------- Constructors ------------------------
/** Creates a panel for displaying the given spatial model.
* @param spModel Spatial model to display.
*/
public SpatialPanel(SpatialModel spModel)
{
this(spModel, new JTextField());
}
/** Creates a panel for displaying the given spatial model.
* Text output can be sent to the given text component.
* @param spModel Spatial model to display.
* @param output Component to display text output.
*/
public SpatialPanel(SpatialModel spModel, JTextComponent output)
{
super();
this.spModel = spModel;
this.output = output;
setCursor(new Cursor(Cursor.CROSSHAIR_CURSOR));
addMouseListener(new MouseClickMonitor());
addMouseMotionListener(new MouseMoveMonitor());
addComponentListener(new PanelSizeMonitor());
setPreferredSize(new Dimension(200,200));
setBorder(BorderFactory.createEtchedBorder());
}
// ----------------------- Methods ---------------------------
/** Calculates the transformations required to convert between
* pixel coordinates and georeferenced coordinates.
*/
public void calcTransformation()
{
// Scale spatial bounds to fit inside panel and flip Y axis.
int panelWidth = getWidth() - 2*BORDER_SIZE;
int panelHeight = getHeight() - 2*BORDER_SIZE;
trans = new AffineTransform();
iTrans = new AffineTransform();
Footprint fp = spModel.getBounds();
double scaling = Math.min(panelWidth/fp.getMERWidth(),
panelHeight/fp.getMERHeight());
float centreX = (float)(panelWidth - (fp.getMERWidth()*scaling))/2;
float centreY = (float)(panelHeight - (fp.getMERHeight()*scaling))/-2;
trans.translate(BORDER_SIZE+centreX,panelHeight+BORDER_SIZE+centreY);
trans.scale(scaling,-scaling);
trans.translate(-fp.getXOrigin(), -fp.getYOrigin());
iTrans.translate(fp.getXOrigin(),fp.getYOrigin());
iTrans.scale(1/scaling,-1/scaling);
iTrans.translate(-centreX-BORDER_SIZE,-centreY-panelHeight-BORDER_SIZE);
}
/** Sets the text component to display text output
* @param output Component to display text output.
*/
public void setOutput(JTextComponent output)
{
this.output = output;
}
// ---------------------- Accessor Methods --------------------
/** Reports the affine transformation required to convert
* georeferenced to pixel coordinates.
* @return Affine transformation to convert georeferenced
into pixel coordinates.
*/
public AffineTransform getGeoToPixel()
{
return trans;
}
/** Transforms the given footprint from georeferenced to pixel coords.
* @param fp Georeferenced coordinates to transform.
* @return Pixel coordinates of the given footprint.
*/
public Footprint getGeoToPixel(Footprint fp)
{
Point2D geo,pxl,geoMax,pxlMax;
geo = new Point2D.Float(fp.getXOrigin(),fp.getYOrigin());
pxl = new Point2D.Float();
trans.transform(geo,pxl);
if ((fp.getMERWidth()==0) && (fp.getMERHeight()==0))
return new Footprint((float)pxl.getX(),(float)pxl.getY());
else
{
geoMax = new Point2D.Float(fp.getXOrigin()+fp.getMERWidth(),
fp.getYOrigin()+fp.getMERHeight());
pxlMax = new Point2D.Float();
trans.transform(geoMax,pxlMax);
return new Footprint((float)pxl.getX(),(float)pxl.getY(),
(float)(pxlMax.getX()-pxl.getX()),
(float)(pxlMax.getY()-pxl.getY()));
}
}
/** Reports the affine transformation required to convert
* pixel to georeferenced coordinates.
* @return Affine transformation to convert pixel into
georeferenced coordinates.
*/
public AffineTransform getPixelToGeo()
{
return iTrans;
}
/** Transforms the given footprint from pixel to georeferenced coords.
* @param fp Pixel coordinates to transform.
* @return Georeferened coordinates of the given footprint.
*/
public Footprint getPixelToGeo(Footprint fp)
{
Point2D geo,pxl,geoMax,pxlMax;
geo = new Point2D.Float(fp.getXOrigin(),fp.getYOrigin());
pxl = new Point2D.Float();
iTrans.transform(geo,pxl);
if ((fp.getMERWidth()==0) && (fp.getMERHeight()==0))
return new Footprint((float)pxl.getX(),(float)pxl.getY());
else
{
geoMax = new Point2D.Float(fp.getXOrigin()+fp.getMERWidth(),
fp.getYOrigin()+fp.getMERHeight());
pxlMax = new Point2D.Float();
iTrans.transform(geoMax,pxlMax);
return new Footprint((float)pxl.getX(),(float)pxl.getY(),
(float)(pxlMax.getX()-pxl.getX()),
(float)(pxlMax.getY()-pxl.getY()));
}
}
// -------------------- Nested Classes -----------------------
/** Handles mouse clicks on the panel.
*/
private class MouseClickMonitor extends MouseAdapter
{
/** Handles a mouse click in the panel and reports the coordinates
* of the mouse when clicked.
* @param e Mouse event associated with the click.
*/
public void mousePressed(MouseEvent e)
{
Footprint fp = getPixelToGeo(new Footprint(e.getX(),e.getY()));
float attribute = spModel.getAttribute(fp);
if (attribute == SpatialModel.OUT_OF_BOUNDS)
output.setText("Out of bounds");
else
if (attribute == SpatialModel.NO_VALUE)
output.setText("No object here");
else
output.setText("Attribute "+attribute);
}
}
/** Handles mouse movement over the panel.
*/
private class MouseMoveMonitor extends MouseMotionAdapter
{
/** Handles mouse movement over the panel by reporting the
* coordinates of the current mouse position.
* @param e Mouse event associated with movement.
*/
public void mouseMoved(MouseEvent e)
{
Footprint fp = getPixelToGeo(new Footprint(e.getX(),e.getY()));
output.setText("Location "+fp.getXOrigin()+","+fp.getYOrigin());
}
}
/** Handles changes in the panel's status.
*/
private class PanelSizeMonitor extends ComponentAdapter
{
/** Handles panel resizing events by updating the pixel-georeference
* transformation to account for new panel dimensions.
* @param e Panel resizing event.
*/
public void componentResized(ComponentEvent e)
{
calcTransformation();
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -