1
+ const canvas = document . querySelector ( 'canvas' ) ;
2
+ const c = canvas . getContext ( '2d' )
3
+
4
+ canvas . width = innerWidth
5
+ canvas . height = innerHeight
6
+
7
+
8
+ class Player {
9
+ constructor ( x , y , radius , color ) {
10
+ this . x = x
11
+ this . y = y
12
+
13
+ this . radius = radius
14
+ this . color = color
15
+ }
16
+ draw ( ) {
17
+ c . beginPath ( )
18
+ c . arc ( this . x , this . y , this . radius , 0 , Math . PI * 2 , false )
19
+ c . fillStyle = this . color
20
+ c . fill ( )
21
+ }
22
+ }
23
+
24
+ class Projectile {
25
+ constructor ( x , y , radius , color , velocity ) {
26
+ this . x = x
27
+ this . y = y
28
+ this . radius = radius
29
+ this . color = color
30
+ this . velocity = velocity
31
+ }
32
+ draw ( ) {
33
+ c . beginPath ( )
34
+ c . arc ( this . x , this . y , this . radius , 0 , Math . PI * 2 , false )
35
+ c . fillStyle = this . color
36
+ c . fill ( )
37
+ }
38
+ update ( ) {
39
+ this . draw ( )
40
+ this . x += this . velocity . x
41
+ this . y += this . velocity . y
42
+ }
43
+ }
44
+
45
+ class Enemy {
46
+ constructor ( x , y , radius , color , velocity ) {
47
+ this . x = x
48
+ this . y = y
49
+ this . radius = radius
50
+ this . color = color
51
+ this . velocity = velocity
52
+ }
53
+ draw ( ) {
54
+ c . beginPath ( )
55
+ c . arc ( this . x , this . y , this . radius , 0 , Math . PI * 2 , false )
56
+ c . fillStyle = this . color
57
+ c . fill ( )
58
+ }
59
+ update ( ) {
60
+ this . draw ( )
61
+ this . x += this . velocity . x
62
+ this . y += this . velocity . y
63
+ }
64
+ }
65
+
66
+ class Particle {
67
+ constructor ( x , y , radius , color , velocity ) {
68
+ this . x = x
69
+ this . y = y
70
+ this . radius = radius
71
+ this . color = color
72
+ this . velocity = velocity
73
+ this . alpha = 1
74
+ }
75
+ draw ( ) {
76
+ c . save ( )
77
+ c . globalAlpha = thid . alpha
78
+ c . beginPath ( )
79
+ c . arc ( this . x , this . y , this . radius , 0 , Math . PI * 2 , false )
80
+ c . fillStyle = this . color
81
+ c . fill ( )
82
+ c . restore ( )
83
+ }
84
+ update ( ) {
85
+ this . draw ( )
86
+ this . x += this . velocity . x
87
+ this . y += this . velocity . y
88
+ this . alpha -= 0.01
89
+ }
90
+ }
91
+ const x = canvas . width / 2
92
+ const y = canvas . height / 2
93
+
94
+ const player = new Player ( x , y , 30 , 'blue' )
95
+
96
+
97
+ // const projectile = new Projectile(canvas.width/2, canvas.height/2, 5, 'red', {x:1 ,y:1})
98
+ // const projectile2 = new Projectile(canvas.width/2, canvas.height/2, 5, 'green', {x:-1 ,y:-1})
99
+
100
+ const projectiles = [ ]
101
+ const enemies = [ ]
102
+ const particles = [ ]
103
+
104
+ function spawnEnemies ( ) {
105
+ setInterval ( ( ) => {
106
+ const radius = Math . random ( ) * ( 30 - 4 ) + 4
107
+
108
+ let x
109
+ let y
110
+
111
+ if ( Math . random ( ) < 0.5 ) {
112
+ x = Math . random ( ) < 0.5 ? 0 - radius : canvas . width + radius
113
+ y = Math . random ( ) * canvas . height
114
+ // y = Math.random() < 0.5 ? 0 - radius : canvas.height + radius
115
+ } else {
116
+ x = Math . random ( ) * canvas . width
117
+ y = Math . random ( ) < 0.5 ? 0 - radius : canvas . height + radius
118
+ }
119
+
120
+
121
+
122
+ const color = `hsl(${ Math . random ( ) * 360 } , 50%, 50%)`
123
+
124
+ const angle = Math . atan2 ( canvas . height / 2 - y , canvas . width / 2 - x )
125
+ const velocity = {
126
+ x :Math . cos ( angle ) * 4 ,
127
+ y :Math . sin ( angle ) * 4
128
+ }
129
+ enemies . push ( new Enemy ( x , y , radius , color , velocity ) )
130
+ } , 1000 )
131
+ }
132
+
133
+ console . log ( player )
134
+
135
+ let animationId
136
+ function Animate ( ) {
137
+ animationId = requestAnimationFrame ( Animate )
138
+ c . fillStyle = 'rgba(0, 0, 0, 0.1)'
139
+ c . fillRect ( 0 , 0 , canvas . width , canvas . height )
140
+ player . draw ( )
141
+ particles . forEach ( ( particle , index ) => {
142
+ if ( particle . alpha <= 0 ) {
143
+ particles . splice ( index , 1 )
144
+ } else {
145
+ particle . update ( )
146
+ }
147
+
148
+ } )
149
+ projectiles . forEach ( ( Projectile , index ) => {
150
+ Projectile . update ( )
151
+
152
+ //remove from edges of screen
153
+ // if(projectile.x + projectile.radius < 0 || projectile.x - projectile.radius > canvas.width || projectile.y + projectile.radius < 0 || projectile.y - projectile.radius > canvas.height){
154
+ // setTimeout(() =>{
155
+ // projectiles.splice(index, 1)
156
+ // }, 0)
157
+
158
+ // }
159
+ } )
160
+
161
+ enemies . forEach ( ( enemy , index ) => {
162
+ enemy . update ( )
163
+ const dist = Math . hypot ( player . x - enemy . x , player . y - enemy . y )
164
+ //end game
165
+ if ( dist - enemy . radius - player . radius < 1 ) {
166
+ cancelAnimationFrame ( animationId )
167
+ }
168
+ projectiles . forEach ( ( projectile , projectileIndex ) => {
169
+ const dist = Math . hypot ( projectile . x - enemy . x , projectile . y - enemy . y )
170
+
171
+ //when projectiles touch enemy
172
+ if ( dist - enemy . radius - projectile . radius < 1 ) {
173
+
174
+ //create explosions
175
+ for ( let i = 0 ; i < enemy . radius * 2 ; i ++ ) {
176
+ particles . push ( new Particle ( projectile . x , projectile . y , Math . random ( ) * 2 , enemy . color , { x :2 , y :2 } ) )
177
+ }
178
+
179
+ if ( enemy . radius - 10 > 10 ) {
180
+ enemy . radius -= 10
181
+ setTimeout ( ( ) => {
182
+ // enemies.splice(index ,1)
183
+ projectiles . splice ( projectileIndex , 1 )
184
+ } , 0 )
185
+ } else {
186
+ setTimeout ( ( ) => {
187
+ enemies . splice ( index , 1 )
188
+ projectiles . splice ( projectileIndex , 1 )
189
+ } , 0 )
190
+ }
191
+
192
+
193
+ }
194
+ } )
195
+ } )
196
+ // projectile.draw()
197
+ // projectile.update()
198
+ }
199
+
200
+ addEventListener ( 'click' , ( event ) => {
201
+ const angle = Math . atan2 ( event . clientY - canvas . height / 2 , event . clientX - canvas . width / 2 )
202
+ const velocity = {
203
+ x :Math . cos ( angle ) * 4 ,
204
+ y :Math . sin ( angle ) * 4
205
+ }
206
+ projectiles . push ( new Projectile ( canvas . width / 2 , canvas . height / 2 , 5 , 'red' , velocity ) )
207
+
208
+ } )
209
+ Animate ( )
210
+ spawnEnemies ( )
0 commit comments