canvasparticles-js 3.2.21 → 3.3.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +49 -21
- package/canvasParticles.js +60 -43
- package/canvasParticles.mjs +60 -43
- package/package.json +43 -43
package/README.md
CHANGED
|
@@ -102,7 +102,7 @@ Add a `<script>` element in the `<head>` to import `CanvasParticles`.
|
|
|
102
102
|
|
|
103
103
|
```html
|
|
104
104
|
<head>
|
|
105
|
-
<script src="https://cdn.jsdelivr.net/npm/canvasparticles-js
|
|
105
|
+
<script src="https://cdn.jsdelivr.net/npm/canvasparticles-js/canvasParticles.min.js" defer></script>
|
|
106
106
|
</head>
|
|
107
107
|
```
|
|
108
108
|
|
|
@@ -127,24 +127,6 @@ particles.start()
|
|
|
127
127
|
particles.stop()
|
|
128
128
|
```
|
|
129
129
|
|
|
130
|
-
### Update options on the fly
|
|
131
|
-
|
|
132
|
-
```js
|
|
133
|
-
const particles = new CanvasParticles(selector, options)
|
|
134
|
-
|
|
135
|
-
// Required usage of setter for options.background and options.particles.color
|
|
136
|
-
particles.setBackground('red')
|
|
137
|
-
particles.setParticleColor('hsl(149, 100%, 50%)')
|
|
138
|
-
|
|
139
|
-
// Changing options.particles.ppm or options.particles.max requires a reset
|
|
140
|
-
particles.options.particles.ppm = 100
|
|
141
|
-
particles.options.particles.max = 300
|
|
142
|
-
particles.newParticles() // required reset
|
|
143
|
-
|
|
144
|
-
// All other options can be updated on the fly
|
|
145
|
-
particles.options.gravity.repulsive = 1
|
|
146
|
-
```
|
|
147
|
-
|
|
148
130
|
## Options
|
|
149
131
|
|
|
150
132
|
Configuration options for the particles and their behavior.<br>
|
|
@@ -263,17 +245,62 @@ const options = {
|
|
|
263
245
|
|
|
264
246
|
</details>
|
|
265
247
|
|
|
266
|
-
|
|
248
|
+
### Update options on the fly
|
|
249
|
+
|
|
250
|
+
**Note:** The new option values are not validated, except for the options with a setter. Assigning invalid values will lead to unexpected behavior and system errors.
|
|
251
|
+
|
|
252
|
+
#### Using setter
|
|
253
|
+
|
|
254
|
+
These options require dedicated setters to ensure proper integration.
|
|
255
|
+
|
|
256
|
+
- options.background
|
|
257
|
+
- options.mouse.connectDistMult
|
|
258
|
+
- options.particles.color
|
|
259
|
+
|
|
260
|
+
```js
|
|
261
|
+
const particles = new CanvasParticles(selector, options)
|
|
262
|
+
|
|
263
|
+
// Use the setters to update these specific options
|
|
264
|
+
particles.setBackground('red')
|
|
265
|
+
particles.setMouseConnectDistMult(0.8)
|
|
266
|
+
particles.setParticleColor('hsl(149, 100%, 50%)')
|
|
267
|
+
```
|
|
268
|
+
|
|
269
|
+
#### Requires particle reset
|
|
270
|
+
|
|
271
|
+
After being updated, these options must call `newParticles()` to apply the changes:
|
|
272
|
+
|
|
273
|
+
- options.particles.ppm
|
|
274
|
+
- options.particles.max
|
|
275
|
+
|
|
276
|
+
```js
|
|
277
|
+
particles.options.particles.ppm = 100
|
|
278
|
+
particles.options.particles.max = 300
|
|
279
|
+
particles.newParticles() // Required reset to apply changes
|
|
280
|
+
```
|
|
281
|
+
|
|
282
|
+
#### Other
|
|
283
|
+
|
|
284
|
+
**All** other options can be updated by modifying the `options` object properties, with changes taking immediate effect.
|
|
285
|
+
|
|
286
|
+
```js
|
|
287
|
+
particles.options.mouse.interactionType = 0
|
|
288
|
+
particles.options.particles.connectDist = 200
|
|
289
|
+
particles.options.gravity.repulsive = 1
|
|
290
|
+
```
|
|
291
|
+
|
|
292
|
+
## One pager example
|
|
267
293
|
|
|
268
294
|
```html
|
|
269
295
|
<!DOCTYPE html>
|
|
270
296
|
<html lang="en">
|
|
271
297
|
<head>
|
|
272
298
|
<meta charset="utf-8" />
|
|
273
|
-
<script src="./canvasParticles.js" defer></script>
|
|
274
299
|
<style>
|
|
275
300
|
#canvas-particles {
|
|
276
301
|
position: absolute;
|
|
302
|
+
top: 0;
|
|
303
|
+
left: 0;
|
|
277
304
|
width: 100%;
|
|
278
305
|
height: 100%;
|
|
279
306
|
z-index: -1;
|
|
@@ -284,6 +311,7 @@ const options = {
|
|
|
284
311
|
<body>
|
|
285
312
|
<canvas id="canvas-particles"></canvas>
|
|
286
313
|
|
|
314
|
+
<script src="https://cdn.jsdelivr.net/npm/canvasparticles-js/canvasParticles.min.js"></script>
|
|
287
315
|
<script>
|
|
288
316
|
const selector = '#canvas-particles'
|
|
289
317
|
const options = {
|
package/canvasParticles.js
CHANGED
|
@@ -2,7 +2,10 @@
|
|
|
2
2
|
// https://github.com/Khoeckman/canvasParticles/blob/main/LICENSE
|
|
3
3
|
|
|
4
4
|
class CanvasParticles {
|
|
5
|
-
static version = '3.
|
|
5
|
+
static version = '3.3.4'
|
|
6
|
+
|
|
7
|
+
animating = false
|
|
8
|
+
particles = []
|
|
6
9
|
|
|
7
10
|
/**
|
|
8
11
|
* Creates a new CanvasParticles instance.
|
|
@@ -19,7 +22,6 @@ class CanvasParticles {
|
|
|
19
22
|
// Get 2d drawing functions
|
|
20
23
|
this.ctx = this.canvas.getContext('2d')
|
|
21
24
|
|
|
22
|
-
this.animating = false
|
|
23
25
|
this.formatOptions(options)
|
|
24
26
|
|
|
25
27
|
// Event handling
|
|
@@ -62,7 +64,6 @@ class CanvasParticles {
|
|
|
62
64
|
if (isNaN(this.options.framesPerUpdate)) this.options.framesPerUpdate = 1
|
|
63
65
|
|
|
64
66
|
if (isNaN(this.options.mouse.interactionType)) this.options.mouse.interactionType = 1
|
|
65
|
-
if (isNaN(this.options.mouse.connectDistMult)) this.options.mouse.connectDistMult = 2 / 3
|
|
66
67
|
if (isNaN(this.options.mouse.distRatio)) this.options.mouse.distRatio = 2 / 3
|
|
67
68
|
|
|
68
69
|
if (isNaN(this.options.particles.ppm)) this.options.particles.ppm = 100
|
|
@@ -77,11 +78,8 @@ class CanvasParticles {
|
|
|
77
78
|
if (isNaN(this.options.gravity.pulling)) this.options.gravity.pulling = 0
|
|
78
79
|
if (isNaN(this.options.gravity.friction)) this.options.gravity.friction = 0.9
|
|
79
80
|
|
|
80
|
-
// Transform distance multiplier to absolute distance
|
|
81
|
-
this.options.mouse.connectDist = this.options.particles.connectDist * this.options.mouse.connectDistMult
|
|
82
|
-
delete this.options.mouse.connectDistMult
|
|
83
|
-
|
|
84
81
|
this.setBackground(this.options.background)
|
|
82
|
+
this.setMouseConnectDistMult(this.options.mouse.connectDistMult)
|
|
85
83
|
this.setParticleColor(this.options.particles.color)
|
|
86
84
|
}
|
|
87
85
|
|
|
@@ -113,10 +111,14 @@ class CanvasParticles {
|
|
|
113
111
|
|
|
114
112
|
// Amount of particles to be created
|
|
115
113
|
const particles = Math.floor((this.options.particles.ppm * this.width * this.height) / 1000000)
|
|
116
|
-
this.
|
|
114
|
+
this.particleCount = Math.min(this.options.particles.max, particles)
|
|
115
|
+
|
|
116
|
+
if (!isFinite(this.particleCount)) throw new RangeError('number of particles must be finite. check `options.particles.ppm`')
|
|
117
|
+
|
|
118
|
+
if (this.options.resetOnResize || this.particles.length === 0) this.newParticles()
|
|
119
|
+
else this.matchParticleCount()
|
|
117
120
|
|
|
118
|
-
|
|
119
|
-
else this.matchParticlesAmount()
|
|
121
|
+
this.updateParticleBounds()
|
|
120
122
|
}
|
|
121
123
|
|
|
122
124
|
/**
|
|
@@ -124,22 +126,21 @@ class CanvasParticles {
|
|
|
124
126
|
* The amount of new particles will match 'options.particles.ppm'
|
|
125
127
|
* */
|
|
126
128
|
newParticles = () => {
|
|
127
|
-
if (this.len === Infinity) throw new RangeError('cannot create an infinite amount of particles')
|
|
128
129
|
this.particles = []
|
|
129
|
-
for (let i = 0; i < this.
|
|
130
|
+
for (let i = 0; i < this.particleCount; i++) this.createParticle()
|
|
130
131
|
}
|
|
131
132
|
|
|
132
133
|
/**
|
|
133
|
-
* When resizing, add or remove some particles.
|
|
134
|
-
* The final amount of particles will match 'options.particles.ppm'
|
|
134
|
+
* When resizing, add or remove some particles so that the final amount of particles will match 'options.particles.ppm'
|
|
135
135
|
* */
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
this.
|
|
139
|
-
while (this.len > this.particles.length) this.createParticle()
|
|
136
|
+
matchParticleCount = () => {
|
|
137
|
+
this.particles = this.particles.slice(0, this.particleCount)
|
|
138
|
+
while (this.particleCount > this.particles.length) this.createParticle()
|
|
140
139
|
}
|
|
141
140
|
|
|
142
|
-
createParticle =
|
|
141
|
+
createParticle = (posX, posY, dir, speed, size) => {
|
|
142
|
+
size = size || 0.5 + Math.random() ** 5 * 2 * this.options.particles.relSize
|
|
143
|
+
|
|
143
144
|
this.particles.push({
|
|
144
145
|
posX: posX - this.offX || Math.random() * this.width, // Logical position in pixels
|
|
145
146
|
posY: posY - this.offY || Math.random() * this.height, // Logical position in pixels
|
|
@@ -151,17 +152,22 @@ class CanvasParticles {
|
|
|
151
152
|
offY: 0, // Vertical distance from drawn to logical position in pixels
|
|
152
153
|
dir: dir || Math.random() * 2 * Math.PI, // Direction in radians
|
|
153
154
|
speed: speed || (0.5 + Math.random() * 0.5) * this.options.particles.relSpeed, // Velocity in pixels per update
|
|
154
|
-
size
|
|
155
|
+
size, // Ray in pixels of the particle
|
|
155
156
|
})
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
157
|
+
this.updateParticleBounds()
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
updateParticleBounds = () => {
|
|
161
|
+
this.particles.map(
|
|
162
|
+
particle =>
|
|
163
|
+
// Within these bounds the particle is considered visible
|
|
164
|
+
(particle.bounds = {
|
|
165
|
+
top: -particle.size,
|
|
166
|
+
right: this.canvas.width + particle.size,
|
|
167
|
+
bottom: this.canvas.height + particle.size,
|
|
168
|
+
left: -particle.size,
|
|
169
|
+
})
|
|
170
|
+
)
|
|
165
171
|
}
|
|
166
172
|
|
|
167
173
|
/**
|
|
@@ -169,7 +175,7 @@ class CanvasParticles {
|
|
|
169
175
|
* Is executed once every 'options.framesPerUpdate' frames.
|
|
170
176
|
* */
|
|
171
177
|
update = () => {
|
|
172
|
-
const len = this.
|
|
178
|
+
const len = this.particleCount
|
|
173
179
|
const enabledRepulsive = this.options.gravity.repulsive !== 0
|
|
174
180
|
const enabledPulling = this.options.gravity.pulling !== 0
|
|
175
181
|
const gravRepulsiveMult = this.options.particles.connectDist * this.options.gravity.repulsive
|
|
@@ -267,7 +273,7 @@ class CanvasParticles {
|
|
|
267
273
|
* @returns {number} x - The horizontal grid position (0, 1, or 2).
|
|
268
274
|
* @returns {number} y - The vertical grid position (0, 1, or 2).
|
|
269
275
|
*/
|
|
270
|
-
gridPos =
|
|
276
|
+
gridPos = particle => {
|
|
271
277
|
return {
|
|
272
278
|
x: (particle.x >= particle.bounds.left) + (particle.x > particle.bounds.right),
|
|
273
279
|
y: (particle.y >= particle.bounds.top) + (particle.y > particle.bounds.bottom),
|
|
@@ -280,7 +286,7 @@ class CanvasParticles {
|
|
|
280
286
|
* @param {Object} particleB - Second particle with {gridPos, isVisible}.
|
|
281
287
|
* @returns {boolean} - True if the line crosses the visible center, false otherwise.
|
|
282
288
|
*/
|
|
283
|
-
isLineVisible
|
|
289
|
+
isLineVisible(particleA, particleB) {
|
|
284
290
|
// Visible if either particle is in the center
|
|
285
291
|
if (particleA.isVisible || particleB.isVisible) return true
|
|
286
292
|
|
|
@@ -316,7 +322,7 @@ class CanvasParticles {
|
|
|
316
322
|
}
|
|
317
323
|
}
|
|
318
324
|
|
|
319
|
-
const len = this.
|
|
325
|
+
const len = this.particleCount
|
|
320
326
|
const drawAll = this.options.particles.connectDist >= Math.min(this.canvas.width, this.canvas.height)
|
|
321
327
|
|
|
322
328
|
const maxWorkPerParticle = this.options.particles.connectDist * this.options.particles.maxWork
|
|
@@ -397,6 +403,16 @@ class CanvasParticles {
|
|
|
397
403
|
if (typeof background === 'string') this.canvas.style.background = this.options.background = background
|
|
398
404
|
}
|
|
399
405
|
|
|
406
|
+
/**
|
|
407
|
+
* Transform distance multiplier to absolute distance
|
|
408
|
+
* @param {float} connectDistMult - The maximum distance for the mouse to interact with the particles.
|
|
409
|
+
* The value is multiplied by particles.connectDistance
|
|
410
|
+
* @example 0.8 connectDistMult * 150 particles.connectDistance = 120 pixels
|
|
411
|
+
*/
|
|
412
|
+
setMouseConnectDistMult = connectDistMult => {
|
|
413
|
+
this.options.mouse.connectDist = this.options.particles.connectDist * (isNaN(connectDistMult) ? 2 / 3 : connectDistMult)
|
|
414
|
+
}
|
|
415
|
+
|
|
400
416
|
/**
|
|
401
417
|
* Format particle color and opacity
|
|
402
418
|
* @param {string} color - The color of the particles and their connections. Can be any CSS supported color format.
|
|
@@ -407,19 +423,20 @@ class CanvasParticles {
|
|
|
407
423
|
if (this.ctx.fillStyle[0] === '#') {
|
|
408
424
|
this.options.particles.opacity = { value: 255, hex: 'ff' }
|
|
409
425
|
this.options.particles.color = this.ctx.fillStyle
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
const value = ~~(this.ctx.fillStyle.split(',').at(-1).slice(1, -1) * 255)
|
|
426
|
+
return
|
|
427
|
+
}
|
|
413
428
|
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
hex: value.toString(16),
|
|
417
|
-
}
|
|
429
|
+
// Example: extract 0.25 from rgba(136, 244, 255, 0.25) and convert to range 0x00 to 0xff and store as a 2 char string
|
|
430
|
+
const value = ~~(this.ctx.fillStyle.split(',').at(-1).slice(1, -1) * 255)
|
|
418
431
|
|
|
419
|
-
|
|
420
|
-
|
|
421
|
-
|
|
432
|
+
this.options.particles.opacity = {
|
|
433
|
+
value: value,
|
|
434
|
+
hex: value.toString(16),
|
|
422
435
|
}
|
|
436
|
+
|
|
437
|
+
// Example: extract 136, 244 and 255 from rgba(136, 244, 255, 0.25) and convert to '#001122' format
|
|
438
|
+
this.ctx.fillStyle = this.ctx.fillStyle.split(',').slice(0, -1).join(',') + ', 1)'
|
|
439
|
+
this.options.particles.color = this.ctx.fillStyle
|
|
423
440
|
}
|
|
424
441
|
}
|
|
425
442
|
|
package/canvasParticles.mjs
CHANGED
|
@@ -2,7 +2,10 @@
|
|
|
2
2
|
// https://github.com/Khoeckman/canvasParticles/blob/main/LICENSE
|
|
3
3
|
|
|
4
4
|
export default class CanvasParticles {
|
|
5
|
-
static version = '3.
|
|
5
|
+
static version = '3.3.4'
|
|
6
|
+
|
|
7
|
+
animating = false
|
|
8
|
+
particles = []
|
|
6
9
|
|
|
7
10
|
/**
|
|
8
11
|
* Creates a new CanvasParticles instance.
|
|
@@ -19,7 +22,6 @@ export default class CanvasParticles {
|
|
|
19
22
|
// Get 2d drawing functions
|
|
20
23
|
this.ctx = this.canvas.getContext('2d')
|
|
21
24
|
|
|
22
|
-
this.animating = false
|
|
23
25
|
this.formatOptions(options)
|
|
24
26
|
|
|
25
27
|
// Event handling
|
|
@@ -62,7 +64,6 @@ export default class CanvasParticles {
|
|
|
62
64
|
if (isNaN(this.options.framesPerUpdate)) this.options.framesPerUpdate = 1
|
|
63
65
|
|
|
64
66
|
if (isNaN(this.options.mouse.interactionType)) this.options.mouse.interactionType = 1
|
|
65
|
-
if (isNaN(this.options.mouse.connectDistMult)) this.options.mouse.connectDistMult = 2 / 3
|
|
66
67
|
if (isNaN(this.options.mouse.distRatio)) this.options.mouse.distRatio = 2 / 3
|
|
67
68
|
|
|
68
69
|
if (isNaN(this.options.particles.ppm)) this.options.particles.ppm = 100
|
|
@@ -77,11 +78,8 @@ export default class CanvasParticles {
|
|
|
77
78
|
if (isNaN(this.options.gravity.pulling)) this.options.gravity.pulling = 0
|
|
78
79
|
if (isNaN(this.options.gravity.friction)) this.options.gravity.friction = 0.9
|
|
79
80
|
|
|
80
|
-
// Transform distance multiplier to absolute distance
|
|
81
|
-
this.options.mouse.connectDist = this.options.particles.connectDist * this.options.mouse.connectDistMult
|
|
82
|
-
delete this.options.mouse.connectDistMult
|
|
83
|
-
|
|
84
81
|
this.setBackground(this.options.background)
|
|
82
|
+
this.setMouseConnectDistMult(this.options.mouse.connectDistMult)
|
|
85
83
|
this.setParticleColor(this.options.particles.color)
|
|
86
84
|
}
|
|
87
85
|
|
|
@@ -113,10 +111,14 @@ export default class CanvasParticles {
|
|
|
113
111
|
|
|
114
112
|
// Amount of particles to be created
|
|
115
113
|
const particles = Math.floor((this.options.particles.ppm * this.width * this.height) / 1000000)
|
|
116
|
-
this.
|
|
114
|
+
this.particleCount = Math.min(this.options.particles.max, particles)
|
|
115
|
+
|
|
116
|
+
if (!isFinite(this.particleCount)) throw new RangeError('number of particles must be finite. check `options.particles.ppm`')
|
|
117
|
+
|
|
118
|
+
if (this.options.resetOnResize || this.particles.length === 0) this.newParticles()
|
|
119
|
+
else this.matchParticleCount()
|
|
117
120
|
|
|
118
|
-
|
|
119
|
-
else this.matchParticlesAmount()
|
|
121
|
+
this.updateParticleBounds()
|
|
120
122
|
}
|
|
121
123
|
|
|
122
124
|
/**
|
|
@@ -124,22 +126,21 @@ export default class CanvasParticles {
|
|
|
124
126
|
* The amount of new particles will match 'options.particles.ppm'
|
|
125
127
|
* */
|
|
126
128
|
newParticles = () => {
|
|
127
|
-
if (this.len === Infinity) throw new RangeError('cannot create an infinite amount of particles')
|
|
128
129
|
this.particles = []
|
|
129
|
-
for (let i = 0; i < this.
|
|
130
|
+
for (let i = 0; i < this.particleCount; i++) this.createParticle()
|
|
130
131
|
}
|
|
131
132
|
|
|
132
133
|
/**
|
|
133
|
-
* When resizing, add or remove some particles.
|
|
134
|
-
* The final amount of particles will match 'options.particles.ppm'
|
|
134
|
+
* When resizing, add or remove some particles so that the final amount of particles will match 'options.particles.ppm'
|
|
135
135
|
* */
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
this.
|
|
139
|
-
while (this.len > this.particles.length) this.createParticle()
|
|
136
|
+
matchParticleCount = () => {
|
|
137
|
+
this.particles = this.particles.slice(0, this.particleCount)
|
|
138
|
+
while (this.particleCount > this.particles.length) this.createParticle()
|
|
140
139
|
}
|
|
141
140
|
|
|
142
|
-
createParticle =
|
|
141
|
+
createParticle = (posX, posY, dir, speed, size) => {
|
|
142
|
+
size = size || 0.5 + Math.random() ** 5 * 2 * this.options.particles.relSize
|
|
143
|
+
|
|
143
144
|
this.particles.push({
|
|
144
145
|
posX: posX - this.offX || Math.random() * this.width, // Logical position in pixels
|
|
145
146
|
posY: posY - this.offY || Math.random() * this.height, // Logical position in pixels
|
|
@@ -151,17 +152,22 @@ export default class CanvasParticles {
|
|
|
151
152
|
offY: 0, // Vertical distance from drawn to logical position in pixels
|
|
152
153
|
dir: dir || Math.random() * 2 * Math.PI, // Direction in radians
|
|
153
154
|
speed: speed || (0.5 + Math.random() * 0.5) * this.options.particles.relSpeed, // Velocity in pixels per update
|
|
154
|
-
size
|
|
155
|
+
size, // Ray in pixels of the particle
|
|
155
156
|
})
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
157
|
+
this.updateParticleBounds()
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
updateParticleBounds = () => {
|
|
161
|
+
this.particles.map(
|
|
162
|
+
particle =>
|
|
163
|
+
// Within these bounds the particle is considered visible
|
|
164
|
+
(particle.bounds = {
|
|
165
|
+
top: -particle.size,
|
|
166
|
+
right: this.canvas.width + particle.size,
|
|
167
|
+
bottom: this.canvas.height + particle.size,
|
|
168
|
+
left: -particle.size,
|
|
169
|
+
})
|
|
170
|
+
)
|
|
165
171
|
}
|
|
166
172
|
|
|
167
173
|
/**
|
|
@@ -169,7 +175,7 @@ export default class CanvasParticles {
|
|
|
169
175
|
* Is executed once every 'options.framesPerUpdate' frames.
|
|
170
176
|
* */
|
|
171
177
|
update = () => {
|
|
172
|
-
const len = this.
|
|
178
|
+
const len = this.particleCount
|
|
173
179
|
const enabledRepulsive = this.options.gravity.repulsive !== 0
|
|
174
180
|
const enabledPulling = this.options.gravity.pulling !== 0
|
|
175
181
|
const gravRepulsiveMult = this.options.particles.connectDist * this.options.gravity.repulsive
|
|
@@ -267,7 +273,7 @@ export default class CanvasParticles {
|
|
|
267
273
|
* @returns {number} x - The horizontal grid position (0, 1, or 2).
|
|
268
274
|
* @returns {number} y - The vertical grid position (0, 1, or 2).
|
|
269
275
|
*/
|
|
270
|
-
gridPos =
|
|
276
|
+
gridPos = particle => {
|
|
271
277
|
return {
|
|
272
278
|
x: (particle.x >= particle.bounds.left) + (particle.x > particle.bounds.right),
|
|
273
279
|
y: (particle.y >= particle.bounds.top) + (particle.y > particle.bounds.bottom),
|
|
@@ -280,7 +286,7 @@ export default class CanvasParticles {
|
|
|
280
286
|
* @param {Object} particleB - Second particle with {gridPos, isVisible}.
|
|
281
287
|
* @returns {boolean} - True if the line crosses the visible center, false otherwise.
|
|
282
288
|
*/
|
|
283
|
-
isLineVisible
|
|
289
|
+
isLineVisible(particleA, particleB) {
|
|
284
290
|
// Visible if either particle is in the center
|
|
285
291
|
if (particleA.isVisible || particleB.isVisible) return true
|
|
286
292
|
|
|
@@ -316,7 +322,7 @@ export default class CanvasParticles {
|
|
|
316
322
|
}
|
|
317
323
|
}
|
|
318
324
|
|
|
319
|
-
const len = this.
|
|
325
|
+
const len = this.particleCount
|
|
320
326
|
const drawAll = this.options.particles.connectDist >= Math.min(this.canvas.width, this.canvas.height)
|
|
321
327
|
|
|
322
328
|
const maxWorkPerParticle = this.options.particles.connectDist * this.options.particles.maxWork
|
|
@@ -397,6 +403,16 @@ export default class CanvasParticles {
|
|
|
397
403
|
if (typeof background === 'string') this.canvas.style.background = this.options.background = background
|
|
398
404
|
}
|
|
399
405
|
|
|
406
|
+
/**
|
|
407
|
+
* Transform distance multiplier to absolute distance
|
|
408
|
+
* @param {float} connectDistMult - The maximum distance for the mouse to interact with the particles.
|
|
409
|
+
* The value is multiplied by particles.connectDistance
|
|
410
|
+
* @example 0.8 connectDistMult * 150 particles.connectDistance = 120 pixels
|
|
411
|
+
*/
|
|
412
|
+
setMouseConnectDistMult = connectDistMult => {
|
|
413
|
+
this.options.mouse.connectDist = this.options.particles.connectDist * (isNaN(connectDistMult) ? 2 / 3 : connectDistMult)
|
|
414
|
+
}
|
|
415
|
+
|
|
400
416
|
/**
|
|
401
417
|
* Format particle color and opacity
|
|
402
418
|
* @param {string} color - The color of the particles and their connections. Can be any CSS supported color format.
|
|
@@ -407,18 +423,19 @@ export default class CanvasParticles {
|
|
|
407
423
|
if (this.ctx.fillStyle[0] === '#') {
|
|
408
424
|
this.options.particles.opacity = { value: 255, hex: 'ff' }
|
|
409
425
|
this.options.particles.color = this.ctx.fillStyle
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
const value = ~~(this.ctx.fillStyle.split(',').at(-1).slice(1, -1) * 255)
|
|
426
|
+
return
|
|
427
|
+
}
|
|
413
428
|
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
hex: value.toString(16),
|
|
417
|
-
}
|
|
429
|
+
// Example: extract 0.25 from rgba(136, 244, 255, 0.25) and convert to range 0x00 to 0xff and store as a 2 char string
|
|
430
|
+
const value = ~~(this.ctx.fillStyle.split(',').at(-1).slice(1, -1) * 255)
|
|
418
431
|
|
|
419
|
-
|
|
420
|
-
|
|
421
|
-
|
|
432
|
+
this.options.particles.opacity = {
|
|
433
|
+
value: value,
|
|
434
|
+
hex: value.toString(16),
|
|
422
435
|
}
|
|
436
|
+
|
|
437
|
+
// Example: extract 136, 244 and 255 from rgba(136, 244, 255, 0.25) and convert to '#001122' format
|
|
438
|
+
this.ctx.fillStyle = this.ctx.fillStyle.split(',').slice(0, -1).join(',') + ', 1)'
|
|
439
|
+
this.options.particles.color = this.ctx.fillStyle
|
|
423
440
|
}
|
|
424
441
|
}
|
package/package.json
CHANGED
|
@@ -1,43 +1,43 @@
|
|
|
1
|
-
{
|
|
2
|
-
"name": "canvasparticles-js",
|
|
3
|
-
"version": "3.
|
|
4
|
-
"description": "In an HTML canvas, a bunch of floating particles connected with lines when they approach eachother. Creating a fun and interactive background.",
|
|
5
|
-
"main": "canvasParticles.js",
|
|
6
|
-
"type": "module",
|
|
7
|
-
"repository": {
|
|
8
|
-
"type": "git",
|
|
9
|
-
"url": "git+https://github.com/Khoeckman/canvasParticles.git"
|
|
10
|
-
},
|
|
11
|
-
"keywords": [
|
|
12
|
-
"front-end",
|
|
13
|
-
"frontend",
|
|
14
|
-
"canvas",
|
|
15
|
-
"particle",
|
|
16
|
-
"particles",
|
|
17
|
-
"jsparticles",
|
|
18
|
-
"js-particles",
|
|
19
|
-
"particles.js",
|
|
20
|
-
"particles-js",
|
|
21
|
-
"xparticles",
|
|
22
|
-
"background",
|
|
23
|
-
"animation",
|
|
24
|
-
"animated",
|
|
25
|
-
"interactive",
|
|
26
|
-
"interaction",
|
|
27
|
-
"web",
|
|
28
|
-
"webdesign",
|
|
29
|
-
"web-design",
|
|
30
|
-
"javascript",
|
|
31
|
-
"js",
|
|
32
|
-
"ecmascript",
|
|
33
|
-
"module",
|
|
34
|
-
"html5",
|
|
35
|
-
"html"
|
|
36
|
-
],
|
|
37
|
-
"author": "Kyle Hoeckman",
|
|
38
|
-
"license": "MIT",
|
|
39
|
-
"bugs": {
|
|
40
|
-
"url": "https://github.com/Khoeckman/canvasParticles/issues"
|
|
41
|
-
},
|
|
42
|
-
"homepage": "http://kylehoeckman.great-site.net/canvas-particles/"
|
|
43
|
-
}
|
|
1
|
+
{
|
|
2
|
+
"name": "canvasparticles-js",
|
|
3
|
+
"version": "3.3.4",
|
|
4
|
+
"description": "In an HTML canvas, a bunch of floating particles connected with lines when they approach eachother. Creating a fun and interactive background.",
|
|
5
|
+
"main": "canvasParticles.js",
|
|
6
|
+
"type": "module",
|
|
7
|
+
"repository": {
|
|
8
|
+
"type": "git",
|
|
9
|
+
"url": "git+https://github.com/Khoeckman/canvasParticles.git"
|
|
10
|
+
},
|
|
11
|
+
"keywords": [
|
|
12
|
+
"front-end",
|
|
13
|
+
"frontend",
|
|
14
|
+
"canvas",
|
|
15
|
+
"particle",
|
|
16
|
+
"particles",
|
|
17
|
+
"jsparticles",
|
|
18
|
+
"js-particles",
|
|
19
|
+
"particles.js",
|
|
20
|
+
"particles-js",
|
|
21
|
+
"xparticles",
|
|
22
|
+
"background",
|
|
23
|
+
"animation",
|
|
24
|
+
"animated",
|
|
25
|
+
"interactive",
|
|
26
|
+
"interaction",
|
|
27
|
+
"web",
|
|
28
|
+
"webdesign",
|
|
29
|
+
"web-design",
|
|
30
|
+
"javascript",
|
|
31
|
+
"js",
|
|
32
|
+
"ecmascript",
|
|
33
|
+
"module",
|
|
34
|
+
"html5",
|
|
35
|
+
"html"
|
|
36
|
+
],
|
|
37
|
+
"author": "Kyle Hoeckman",
|
|
38
|
+
"license": "MIT",
|
|
39
|
+
"bugs": {
|
|
40
|
+
"url": "https://github.com/Khoeckman/canvasParticles/issues"
|
|
41
|
+
},
|
|
42
|
+
"homepage": "http://kylehoeckman.great-site.net/canvas-particles/"
|
|
43
|
+
}
|