File size: 5,275 Bytes
f79888b
 
 
 
 
5a59d0c
f79888b
5a59d0c
 
 
 
 
f79888b
 
 
5a59d0c
 
f79888b
5a59d0c
 
f79888b
5a59d0c
 
 
 
 
 
 
 
 
 
f79888b
5a59d0c
 
 
 
 
 
 
824c1ab
5a59d0c
 
 
 
 
f79888b
5a59d0c
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
f79888b
5a59d0c
 
 
f79888b
 
5a59d0c
 
 
 
 
 
 
 
 
b79cc65
5a59d0c
 
 
 
 
 
 
b79cc65
 
5a59d0c
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
b79cc65
 
5a59d0c
 
 
 
b79cc65
5a59d0c
 
 
 
 
 
 
 
 
 
f79888b
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Balls in Rotating Hexagon</title>
    <style>
        canvas {
            border: 1px solid black;
            display: block;
            margin: auto;
        }
    </style>
</head>
<body>
    <canvas id="myCanvas" width="800" height="600"></canvas>

    <script>
        const canvas = document.getElementById('myCanvas');
        const ctx = canvas.getContext('2d');

        // Ball class
        class Ball {
            constructor(x, y, radius, color) {
                this.x = x;
                this.y = y;
                this.radius = radius;
                this.color = color;
                this.vx = Math.random() * 2 - 1;
                this.vy = Math.random() * 2 - 1;
            }

            draw() {
                ctx.beginPath();
                ctx.arc(this.x, this.y, this.radius, 0, Math.PI*2);
                ctx.fillStyle = this.color;
                ctx.fill();
                ctx.closePath();
            }

            move() {
                this.x += this.vx;
                this.y += this.vy;
                this.vy += 0.05; // gravity
            }

            collideWithWall(hexagon) {
                const vertices = hexagon.vertices;
                for (let i = 0; i < vertices.length; i++) {
                    const p1 = vertices[i];
                    const p2 = vertices[(i + 1) % vertices.length];
                    if (this.lineCircle(p1.x, p1.y, p2.x, p2.y, this.x, this.y, this.radius)) {
                        const normal = {x: p2.y - p1.y, y: p1.x - p2.x};
                        const distance = Math.sqrt(normal.x * normal.x + normal.y * normal.y);
                        normal.x /= distance;
                        normal.y /= distance;
                        
                        const dotProduct = this.vx * normal.x + this.vy * normal.y;
                        this.vx -= 2 * dotProduct * normal.x;
                        this.vy -= 2 * dotProduct * normal.y;
                        // Move the ball outside the wall to avoid sticking
                        this.x += this.vx;
                        this.y += this.vy;
                        return;
                    }
                }
            }

            lineCircle(x1, y1, x2, y2, cx, cy, r) {
                const lineLength = Math.sqrt((x2 - x1) * (x2 - x1) + (y2 - y1) * (y2 - y1));
                const dot = (((cx - x1) * (x2 - x1)) + ((cy - y1) * (y2 - y1))) / Math.pow(lineLength, 2);
                const closestX = x1 + (dot * (x2 - x1));
                const closestY = y1 + (dot * (y2 - y1));
                if (this.distance(closestX, closestY, x1, y1) > lineLength || this.distance(closestX, closestY, x2, y2) > lineLength) {
                    return false;
                }
                const distance = this.distance(closestX, closestY, cx, cy);
                return distance <= r;
            }

            distance(x1, y1, x2, y2) {
                return Math.sqrt((x2 - x1) * (x2 - x1) + (y2 - y1) * (y2 - y1));
            }
        }

        // Hexagon class
        class Hexagon {
            constructor(centerX, centerY, radius) {
                this.centerX = centerX;
                this.centerY = centerY;
                this.radius = radius;
                this.rotation = 0;
                this.vertices = this.calculateVertices();
            }

            calculateVertices() {
                const vertices = [];
                for (let i = 0; i < 6; i++) {
                    const angle = Math.PI / 3 * i + this.rotation;
                    vertices.push({
                        x: this.centerX + this.radius * Math.cos(angle),
                        y: this.centerY + this.radius * Math.sin(angle)
                    });
                }
                return vertices;
            }

            draw() {
                ctx.beginPath();
                for (let vertex of this.vertices) {
                    ctx.lineTo(vertex.x, vertex.y);
                }
                ctx.closePath();
                ctx.strokeStyle = "black";
                ctx.stroke();
            }

            update() {
                this.rotation += 0.01;
                this.vertices = this.calculateVertices();
            }
        }

        const hexagon = new Hexagon(canvas.width / 2, canvas.height / 2, 200);
        const balls = [];
        const colors = ["red", "blue", "green", "yellow", "purple", "orange", "pink", "brown", "cyan", "magenta"];

        for (let i = 0; i < 10; i++) {
            const x = canvas.width / 2 + Math.random() * 100 - 50;
            const y = canvas.height / 2 + Math.random() * 100 - 50;
            balls.push(new Ball(x, y, 10, colors[i]));
        }

        function animate() {
            ctx.clearRect(0, 0, canvas.width, canvas.height);
            hexagon.update();
            hexagon.draw();

            for (let ball of balls) {
                ball.move();
                ball.collideWithWall(hexagon);
                ball.draw();
            }

            requestAnimationFrame(animate);
        }

        animate();
    </script>
</body>
</html>