package dell_Fence;
|
import java.awt.Color;
|
import java.awt.Dimension;
|
import java.awt.Font;
|
import java.awt.Graphics;
|
import java.awt.Graphics2D;
|
import java.awt.Image;
|
import java.awt.Point;
|
import java.awt.RenderingHints;
|
import java.awt.event.ComponentAdapter;
|
import java.awt.event.ComponentEvent;
|
import java.awt.event.MouseAdapter;
|
import java.awt.event.MouseEvent;
|
import java.awt.event.MouseWheelEvent;
|
import java.awt.geom.Point2D;
|
import java.util.Vector;
|
import javax.swing.ImageIcon;
|
import javax.swing.JPanel;
|
|
import targets.Mapdata;
|
|
public class MapCanvas extends JPanel {
|
private static final long serialVersionUID = 1L;
|
|
private final FenceDrawerFrame parentFrame;
|
private Mapdata mapData;
|
private Image mapImage;
|
private double scale = 1.0;
|
private int offsetX = 0;
|
private int offsetY = 0;
|
private Point dragOrigin;
|
private boolean isDrawingMode = false;
|
private Point2D.Double currentMousePointInMap = new Point2D.Double(0, 0);
|
private Point currentMouseScreenPoint = new Point(0, 0);
|
private boolean isDragging = false;
|
|
public MapCanvas(FenceDrawerFrame parentFrame, Mapdata mapData) {
|
this.parentFrame = parentFrame;
|
this.mapData = mapData;
|
loadMapImage();
|
setPreferredSize(new Dimension(800, 500));
|
|
initEventHandlers();
|
}
|
|
private void initEventHandlers() {
|
addMouseListener(new MouseAdapter() {
|
@Override
|
public void mousePressed(MouseEvent e) {
|
handleMousePress(e);
|
}
|
|
@Override
|
public void mouseReleased(MouseEvent e) {
|
isDragging = false;
|
}
|
|
// Ìí¼ÓË«»÷ʼþ´¦Àí
|
@Override
|
public void mouseClicked(MouseEvent e) {
|
if (e.getClickCount() == 2) { // Ë«»÷ʼþ
|
handleDoubleClick(e);
|
}
|
}
|
});
|
|
addMouseMotionListener(new MouseAdapter() {
|
@Override
|
public void mouseDragged(MouseEvent e) {
|
handleMouseDrag(e);
|
}
|
|
@Override
|
public void mouseMoved(MouseEvent e) {
|
handleMouseMove(e);
|
}
|
});
|
|
addMouseWheelListener(this::handleMouseWheel);
|
|
addComponentListener(new ComponentAdapter() {
|
@Override
|
public void componentResized(ComponentEvent e) {
|
centerMap();
|
}
|
});
|
}
|
|
// ´¦ÀíË«»÷ʼþ
|
private void handleDoubleClick(MouseEvent e) {
|
if (isDrawingMode && parentFrame.isDrawing) {
|
int currentShape = parentFrame.currentShape;
|
Vector<Point2D.Double> drawingPoints = parentFrame.drawingPoints;
|
|
// ¶à±ßÐλò¶à¶ÎÏßË«»÷Íê³É»æÖÆ
|
if (currentShape == 0 || currentShape == 1) {
|
// ¶à±ßÐÎÐèÒªÖÁÉÙ3¸öµã£¬¶à¶ÎÏßÖÁÉÙ2¸öµã
|
if ((currentShape == 0 && drawingPoints.size() >= 3) ||
|
(currentShape == 1 && drawingPoints.size() >= 2)) {
|
|
// ´¥·¢Íê³É»æÖÆ
|
parentFrame.finishDrawing();
|
}
|
}
|
}
|
}
|
|
private void handleMousePress(MouseEvent e) {
|
if (isDrawingMode && parentFrame.isDrawing) {
|
int currentShape = parentFrame.currentShape;
|
Vector<Point2D.Double> drawingPoints = parentFrame.drawingPoints;
|
|
// ¾ØÐÎ/Ô²ÐÎÌØÊâ´¦Àí£¨Ö»ÐèÒª2¸öµã£©
|
if (currentShape == 2 || currentShape == 3) {
|
if (drawingPoints.size() == 0) {
|
Point2D.Double mapPoint = screenToMap(e.getPoint());
|
drawingPoints.add(mapPoint);
|
repaint();
|
return;
|
} else if (drawingPoints.size() == 1) {
|
Point2D.Double mapPoint = screenToMap(e.getPoint());
|
drawingPoints.add(mapPoint);
|
repaint();
|
parentFrame.finishDrawing();
|
return;
|
}
|
}
|
|
// ¶à±ßÐκͶà¶ÎÏß´¦Àí£¨Ìí¼Óµã£©
|
if (currentShape == 0 || currentShape == 1) {
|
Point2D.Double mapPoint = screenToMap(e.getPoint());
|
drawingPoints.add(mapPoint);
|
repaint();
|
}
|
} else {
|
dragOrigin = e.getPoint();
|
isDragging = true;
|
}
|
}
|
|
private void handleMouseDrag(MouseEvent e) {
|
if (isDragging && !isDrawingMode) {
|
Point current = e.getPoint();
|
offsetX += current.x - dragOrigin.x;
|
offsetY += current.y - dragOrigin.y;
|
dragOrigin = current;
|
repaint();
|
}
|
}
|
|
private void handleMouseMove(MouseEvent e) {
|
currentMouseScreenPoint = e.getPoint();
|
currentMousePointInMap = screenToMap(currentMouseScreenPoint);
|
updateCoordLabel();
|
repaint();
|
}
|
|
private void handleMouseWheel(MouseWheelEvent e) {
|
int rotation = e.getWheelRotation();
|
double zoomFactor = 1.1;
|
|
double mapX = (e.getX() - offsetX) / scale;
|
double mapY = (e.getY() - offsetY) / scale;
|
|
if (rotation < 0 && scale < 5.0) {
|
scale *= zoomFactor;
|
} else if (rotation > 0 && scale > 0.2) {
|
scale /= zoomFactor;
|
} else {
|
return;
|
}
|
|
offsetX = (int) (e.getX() - mapX * scale);
|
offsetY = (int) (e.getY() - mapY * scale);
|
|
repaint();
|
}
|
|
// ¾ÓÖеØÍ¼
|
private void centerMap() {
|
if (mapImage == null) return;
|
int panelWidth = getWidth();
|
int panelHeight = getHeight();
|
int imgWidth = (int)(mapImage.getWidth(null) * scale);
|
int imgHeight = (int)(mapImage.getHeight(null) * scale);
|
offsetX = (panelWidth - imgWidth) / 2;
|
offsetY = (panelHeight - imgHeight) / 2;
|
repaint();
|
}
|
|
// ÆÁÄ»×ø±êתµØÍ¼×ø±ê
|
private Point2D.Double screenToMap(Point screenPoint) {
|
return new Point2D.Double(
|
(screenPoint.x - offsetX) / scale,
|
(screenPoint.y - offsetY) / scale
|
);
|
}
|
|
// µØÍ¼×ø±êתÆÁÄ»×ø±ê
|
private Point mapToScreen(Point2D.Double mapPoint) {
|
return new Point(
|
(int) (mapPoint.x * scale + offsetX),
|
(int) (mapPoint.y * scale + offsetY)
|
);
|
}
|
|
private void loadMapImage() {
|
String imagePath = "systemfile/imagemap/" + mapData.getMapNameDetaile();
|
mapImage = new ImageIcon(imagePath).getImage();
|
}
|
|
public void setDrawingMode(boolean drawingMode) {
|
isDrawingMode = drawingMode;
|
}
|
|
public void setDrawingPoints(Vector<Point2D.Double> points) {
|
// ÉèÖûæÖƵ㼯ºÏ
|
}
|
|
private void updateCoordLabel() {
|
parentFrame.getCoordLabel().setText(String.format("X: %.2f, Y: %.2f",
|
currentMousePointInMap.x, currentMousePointInMap.y));
|
}
|
|
@Override
|
protected void paintComponent(Graphics g) {
|
super.paintComponent(g);
|
Graphics2D g2d = (Graphics2D) g;
|
|
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
|
RenderingHints.VALUE_ANTIALIAS_ON);
|
|
// »æÖƵØÍ¼
|
if (mapImage != null) {
|
int width = (int) (mapImage.getWidth(null) * scale);
|
int height = (int) (mapImage.getHeight(null) * scale);
|
g2d.drawImage(mapImage, offsetX, offsetY, width, height, this);
|
}
|
|
// »æÖÆÐÎ×´
|
drawShapes(g2d);
|
|
// »æÖÆ×´Ì¬ÐÅÏ¢
|
drawStatusInfo(g2d);
|
}
|
|
private void drawShapes(Graphics2D g2d) {
|
Vector<Point2D.Double> drawingPoints = parentFrame.drawingPoints;
|
int currentShape = parentFrame.currentShape;
|
boolean isDrawing = parentFrame.isDrawing;
|
|
// »æÖÆÒѱ£´æµÄµã
|
if (!drawingPoints.isEmpty()) {
|
g2d.setColor(Color.RED);
|
for (Point2D.Double mapPoint : drawingPoints) {
|
Point screenPoint = mapToScreen(mapPoint);
|
g2d.fillOval(screenPoint.x - 5, screenPoint.y - 5, 10, 10);
|
// ÔÚµãÅÔ±ßÏÔÊ¾×ø±ê (X, Y)
|
String coordText = String.format("(%.0f, %.0f)", mapPoint.x, mapPoint.y);
|
g2d.setColor(Color.BLACK);
|
g2d.drawString(coordText, screenPoint.x + 8, screenPoint.y - 8);
|
g2d.setColor(Color.RED);
|
}
|
|
if (currentShape == 0) { // ¶à±ßÐÎ
|
if (drawingPoints.size() > 1) {
|
Point prev = mapToScreen(drawingPoints.get(0));
|
for (int i = 1; i < drawingPoints.size(); i++) {
|
Point current = mapToScreen(drawingPoints.get(i));
|
g2d.drawLine(prev.x, prev.y, current.x, current.y);
|
prev = current;
|
}
|
// ¶à±ßÐαպÏ
|
if (drawingPoints.size() > 2) {
|
Point first = mapToScreen(drawingPoints.get(0));
|
Point last = mapToScreen(drawingPoints.get(drawingPoints.size()-1));
|
g2d.drawLine(last.x, last.y, first.x, first.y);
|
}
|
}
|
}
|
// ÐÂÔö£º¶à¶ÎÏß»æÖÆÂß¼
|
else if (currentShape == 1) {
|
if (drawingPoints.size() > 1) {
|
Point prev = mapToScreen(drawingPoints.get(0));
|
for (int i = 1; i < drawingPoints.size(); i++) {
|
Point current = mapToScreen(drawingPoints.get(i));
|
g2d.drawLine(prev.x, prev.y, current.x, current.y);
|
prev = current;
|
}
|
}
|
}
|
else if (currentShape == 2 && drawingPoints.size() == 2) { // ¾ØÐÎ
|
Point p1 = mapToScreen(drawingPoints.get(0));
|
Point p2 = mapToScreen(drawingPoints.get(1));
|
int x = Math.min(p1.x, p2.x);
|
int y = Math.min(p1.y, p2.y);
|
int width = Math.abs(p1.x - p2.x);
|
int height = Math.abs(p1.y - p2.y);
|
g2d.drawRect(x, y, width, height);
|
} else if (currentShape == 3 && drawingPoints.size() == 2) { // Ô²ÐÎ
|
Point center = mapToScreen(drawingPoints.get(0));
|
Point edge = mapToScreen(drawingPoints.get(1));
|
int radius = (int) center.distance(edge);
|
g2d.drawOval(center.x - radius, center.y - radius, 2 * radius, 2 * radius);
|
}
|
}
|
|
// »æÖƶ¯Ì¬¸¨ÖúÏß
|
if (isDrawing && isDrawingMode) {
|
g2d.setColor(Color.BLUE);
|
|
if (currentShape == 0) { // ¶à±ßÐθ¨ÖúÏß
|
if (!drawingPoints.isEmpty()) {
|
Point lastPoint = mapToScreen(drawingPoints.lastElement());
|
g2d.drawLine(lastPoint.x, lastPoint.y,
|
currentMouseScreenPoint.x, currentMouseScreenPoint.y);
|
}
|
}
|
// ÐÂÔö£º¶à¶ÎÏ߸¨ÖúÏß
|
else if (currentShape == 1) {
|
if (!drawingPoints.isEmpty()) {
|
Point lastPoint = mapToScreen(drawingPoints.lastElement());
|
g2d.drawLine(lastPoint.x, lastPoint.y,
|
currentMouseScreenPoint.x, currentMouseScreenPoint.y);
|
}
|
}
|
else if (currentShape == 2) { // ¾ØÐθ¨ÖúÏß
|
if (!drawingPoints.isEmpty()) {
|
Point startPoint = mapToScreen(drawingPoints.get(0));
|
int x = Math.min(startPoint.x, currentMouseScreenPoint.x);
|
int y = Math.min(startPoint.y, currentMouseScreenPoint.y);
|
int width = Math.abs(startPoint.x - currentMouseScreenPoint.x);
|
int height = Math.abs(startPoint.y - currentMouseScreenPoint.y);
|
|
g2d.drawRect(x, y, width, height);
|
|
g2d.setColor(new Color(0, 255, 0, 150));
|
g2d.drawLine(startPoint.x, startPoint.y,
|
currentMouseScreenPoint.x, currentMouseScreenPoint.y);
|
}
|
}
|
else if (currentShape == 3) { // Ô²Ðθ¨ÖúÏß
|
if (!drawingPoints.isEmpty()) {
|
Point startPoint = mapToScreen(drawingPoints.get(0));
|
double dx = startPoint.x - currentMouseScreenPoint.x;
|
double dy = startPoint.y - currentMouseScreenPoint.y;
|
int radius = (int) Math.sqrt(dx * dx + dy * dy);
|
|
g2d.drawOval(startPoint.x - radius, startPoint.y - radius,
|
2 * radius, 2 * radius);
|
|
g2d.setColor(new Color(0, 255, 0, 150));
|
g2d.drawLine(startPoint.x, startPoint.y,
|
currentMouseScreenPoint.x, currentMouseScreenPoint.y);
|
}
|
}
|
}
|
}
|
|
private void drawStatusInfo(Graphics2D g2d) {
|
int panelHeight = getHeight();
|
g2d.setColor(Color.BLACK);
|
g2d.setFont(new Font("Arial", Font.BOLD, 14));
|
|
// »æÖƱÈÀý³ß
|
String scaleText = String.format(parentFrame.getMessage("SCALE") + ": %.1f", scale);
|
g2d.drawString(scaleText, 20, panelHeight - 20);
|
|
// »æÖÆ»æÖÆ×´Ì¬
|
if (isDrawingMode) {
|
g2d.setColor(Color.BLUE);
|
g2d.drawString(parentFrame.getMessage("DRAWING_STATUS"), 20, panelHeight - 40);
|
|
// ÐÂÔö£ºÏÔʾ˫»÷Íê³ÉÌáʾ
|
int currentShape = parentFrame.currentShape;
|
if (parentFrame.isDrawing && (currentShape == 0 || currentShape == 1)) {
|
g2d.drawString(parentFrame.getMessage("DOUBLE_CLICK_TO_FINISH"), 20, panelHeight - 60);
|
}
|
}
|
}
|
}
|