编辑代码

import javax.swing.*;
import java.awt.*;
import java.awt.geom.AffineTransform;
import java.awt.geom.Path2D;

public class RotatingTriangle extends JPanel {
    private Point[] triangleVertices1;
        private Point[] triangleVertices2;
            private Point rotationCenter = new Point(200, 200); // 旋转中心点
                private double angle1 = 0; // 第一个三角形的旋转角度
                    private double angle2 = 0; // 第二个三角形的旋转角度
                        private final int ROTATION_SPEED1 = 2; // 第一个三角形的旋转速度(度/帧)
                            private final int ROTATION_SPEED2 = 4; // 第二个三角形的旋转速度(度/帧) - 设为2倍
                                private final int sideLength = 100;
                                    private int currentVertexIndex = 0; // 当前使用的顶点索引(0,1,2)

                                        public RotatingTriangle() {
                                                // 初始化三角形顶点
                                                        triangleVertices1 = calculateTriangleVertices1(rotationCenter, sideLength);
                                                                triangleVertices2 = calculateTriangleVertices2(triangleVertices1[currentVertexIndex], sideLength);

                                                                        // 创建动画定时器
                                                                                Timer timer = new Timer(50, e -> {
                                                                                            angle1 = (angle1 + ROTATION_SPEED1) % 360;
                                                                                                        angle2 = (angle2 + ROTATION_SPEED2) % 360;

                                                                                                                    // 获取旋转后的顶点位置
                                                                                                                                Point rotatedVertex = getRotatedPoint(triangleVertices1[currentVertexIndex], rotationCenter, angle1);
                                                                                                                                            triangleVertices2 = calculateTriangleVertices2(rotatedVertex, sideLength);
                                                                                                                                                        
                                                                                                                                                                    // 获取旋转后的三角形1的所有顶点
                                                                                                                                                                                Point[] rotatedTriangle1 = new Point[3];
                                                                                                                                                                                            for (int i = 0; i < 3; i++) {
                                                                                                                                                                                                            rotatedTriangle1[i] = getRotatedPoint(triangleVertices1[i], rotationCenter, angle1);
                                                                                                                                                                                                                        }
                                                                                                                                                                                                                                    
                                                                                                                                                                                                                                                // 获取旋转后的三角形2的所有顶点
                                                                                                                                                                                                                                                            Point[] rotatedTriangle2 = new Point[3];
                                                                                                                                                                                                                                                                        for (int i = 0; i < 3; i++) {
                                                                                                                                                                                                                                                                                        rotatedTriangle2[i] = getRotatedPoint(triangleVertices2[i], rotatedVertex, angle2);
                                                                                                                                                                                                                                                                                                    }
                                                                                                                                                                                                                                                                                                                
                                                                                                                                                                                                                                                                                                                            // 检查非旋转顶点是否重合
                                                                                                                                                                                                                                                                                                                                        boolean shouldSwitch = false;
                                                                                                                                                                                                                                                                                                                                                    for (int i = 0; i < 3; i++) {
                                                                                                                                                                                                                                                                                                                                                                    if (i == currentVertexIndex) continue; // 跳过旋转顶点
                                                                                                                                                                                                                                                                                                                                                                                    for (int j = 0; j < 3; j++) {
                                                                                                                                                                                                                                                                                                                                                                                                        if (j == 0) continue; // 跳过旋转顶点
                                                                                                                                                                                                                                                                                                                                                                                                                            if (distance(rotatedTriangle1[i], rotatedTriangle2[j]) < 5) {
                                                                                                                                                                                                                                                                                                                                                                                                                                                    shouldSwitch = true;
                                                                                                                                                                                                                                                                                                                                                                                                                                                                            break;
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                }
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                }
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                if (shouldSwitch) break;
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            }
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    if (shouldSwitch) {
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    currentVertexIndex = (currentVertexIndex + 1) % 3; // 切换到下一个顶点
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    rotatedVertex = getRotatedPoint(triangleVertices1[currentVertexIndex], rotationCenter, angle1);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    triangleVertices2 = calculateTriangleVertices2(rotatedVertex, sideLength);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                }

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            repaint();
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    });
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            timer.start();
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                }

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    // 计算两点之间的距离
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        private double distance(Point p1, Point p2) {
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                return Math.sqrt(Math.pow(p1.x - p2.x, 2) + Math.pow(p1.y - p2.y, 2));
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    }

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        // 计算旋转后的点
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            private Point getRotatedPoint(Point original, Point center, double angleDegrees) {
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    double angleRad = Math.toRadians(angleDegrees);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            double sin = Math.sin(angleRad);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    double cos = Math.cos(angleRad);

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            // 平移点到原点
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    int translatedX = original.x - center.x;
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            int translatedY = original.y - center.y;

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    // 应用旋转
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            int rotatedX = (int)(translatedX * cos - translatedY * sin);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    int rotatedY = (int)(translatedX * sin + translatedY * cos);

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            // 平移回原位置
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    return new Point(rotatedX + center.x, rotatedY + center.y);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        }

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            @Override
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                protected void paintComponent(Graphics g) {
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        super.paintComponent(g);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                Graphics2D g2d = (Graphics2D) g;

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        // 启用抗锯齿
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        // 绘制第一个三角形
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                Path2D path1 = new Path2D.Double();
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        path1.moveTo(triangleVertices1[0].x, triangleVertices1[0].y);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                path1.lineTo(triangleVertices1[1].x, triangleVertices1[1].y);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        path1.lineTo(triangleVertices1[2].x, triangleVertices1[2].y);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                path1.closePath();

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        // 绘制第二个三角形
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                Path2D path2 = new Path2D.Double();
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        path2.moveTo(triangleVertices2[0].x, triangleVertices2[0].y);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                path2.lineTo(triangleVertices2[1].x, triangleVertices2[1].y);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        path2.lineTo(triangleVertices2[2].x, triangleVertices2[2].y);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                path2.closePath();

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        // 保存原始变换
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                AffineTransform oldTransform = g2d.getTransform();

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        // 应用第一个三角形的旋转变换
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                g2d.rotate(Math.toRadians(angle1), rotationCenter.x, rotationCenter.y);

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        // 绘制旋转后的第一个三角形
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                g2d.setColor(new Color(70, 130, 180, 150)); // 半透明钢蓝色
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        g2d.fill(path1);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                g2d.setColor(Color.BLUE);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        g2d.draw(path1);

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                // 恢复原始变换
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        g2d.setTransform(oldTransform);

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                // 应用第二个三角形的旋转变换(基于当前选定的顶点)
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        Point rotatedVertex = getRotatedPoint(triangleVertices1[currentVertexIndex], rotationCenter, angle1);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                g2d.rotate(Math.toRadians(angle2), rotatedVertex.x, rotatedVertex.y);

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        // 绘制旋转后的第二个三角形
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                g2d.setColor(new Color(180, 70, 130, 150)); // 不同颜色
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        g2d.fill(path2);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                g2d.setColor(Color.RED);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        g2d.draw(path2);

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                // 恢复原始变换
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        g2d.setTransform(oldTransform);

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                // 标记旋转中心(红色)
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        g2d.setColor(Color.RED);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                g2d.fillOval(rotationCenter.x-5, rotationCenter.y-5, 10, 10);

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        // 显示当前角度和旋转点
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                g2d.setColor(Color.BLACK);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        g2d.drawString("大三角形角度: " + (int)angle1 + "°", 10, 20);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                g2d.drawString("小三角形角度: " + (int)angle2 + "°", 10, 40);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        g2d.drawString("当前旋转点: 顶点" + (currentVertexIndex + 1), 10, 60);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            }

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                private Point[] calculateTriangleVertices1(Point center, int sideLength) {
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        Point[] vertices = new Point[3];
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                double height = (Math.sqrt(3) / 2) * sideLength;
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        vertices[0] = new Point(center.x, center.y - (int)(height * 2 / 3));
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                vertices[1] = new Point(center.x + sideLength / 2, center.y + (int)(height / 3));
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        vertices[2] = new Point(center.x - sideLength / 2, center.y + (int)(height / 3));
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                return vertices;
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    }

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        private Point[] calculateTriangleVertices2(Point vertex, int sideLength) {
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                Point[] vertices = new Point[3];
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        double height = (Math.sqrt(3) / 2) * sideLength;
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                vertices[0] = new Point(vertex.x, vertex.y);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        vertices[1] = new Point(vertex.x + sideLength / 2, vertex.y + (int)height);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                vertices[2] = new Point(vertex.x - sideLength / 2, vertex.y + (int)height);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        return vertices;
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            }

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                public static void main(String[] args) {
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        JFrame frame = new JFrame("双三角形旋转");
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        frame.setSize(400, 400);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                frame.add(new RotatingTriangle());
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        frame.setVisible(true);
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            }
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            }