Skip to content

Commit

Permalink
Update doc
Browse files Browse the repository at this point in the history
Co-authored-by: Cahil Foley <[email protected]>
  • Loading branch information
Tetramputechture and cahilfoley committed Sep 6, 2024
1 parent a029a5d commit ee7a8c7
Show file tree
Hide file tree
Showing 2 changed files with 58 additions and 26 deletions.
22 changes: 17 additions & 5 deletions packages/react-snowfall/src/SnowfallCanvas.ts
Original file line number Diff line number Diff line change
Expand Up @@ -68,22 +68,34 @@ export class SnowfallCanvas {
private render(framesPassed = 1) {
const { ctx, canvas, snowflakes } = this

if (!ctx || !canvas) return

const { offsetWidth, offsetHeight } = canvas

// Update the position of each snowflake
for (const snowflake of snowflakes) {
snowflake.update(offsetWidth, offsetHeight, framesPassed)
}

// Render them if the canvas is available
if (ctx) {
ctx.setTransform(1, 0, 0, 1, 0, 0)
ctx.clearRect(0, 0, offsetWidth, offsetHeight)
// Render the snowflakes
ctx.setTransform(1, 0, 0, 1, 0, 0)
ctx.clearRect(0, 0, offsetWidth, offsetHeight)

// If using images, draw each image individually
if (this.config.images && this.config.images.length > 0) {
for (const snowflake of snowflakes) {
snowflake.draw(ctx)
snowflake.drawImage(ctx)
}
return
}

// Not using images, draw circles in a single path
ctx.beginPath()
for (const snowflake of snowflakes) {
snowflake.drawCircle(ctx)
}
ctx.fillStyle = this.config.color!
ctx.fill()
}

private animationFrame: number | undefined
Expand Down
62 changes: 41 additions & 21 deletions packages/react-snowfall/src/Snowflake.ts
Original file line number Diff line number Diff line change
Expand Up @@ -212,29 +212,49 @@ class Snowflake {
return sizes[size] ?? image
}

public draw(ctx: CanvasRenderingContext2D): void {
/**
* Draws a circular snowflake to the canvas.
*
* This method should only be called if our config does not have images.
*
* This method assumes that a path has already been started on the canvas.
* `ctx.beginPath()` should be called before calling this method.
*
* After calling this method, the fillStyle should be set to the snowflake's
* color and `ctx.fill()` should be called to fill the snowflake.
*
* Calling `ctx.fill()` after multiple snowflakes have had `drawCircle` called
* will render all of the snowflakes since the last call to `ctx.beginPath()`.
*
* @param ctx The canvas context to draw to
*/
public drawCircle(ctx: CanvasRenderingContext2D): void {
ctx.moveTo(this.params.x, this.params.y)
ctx.arc(this.params.x, this.params.y, this.params.radius, 0, TWO_PI)
}

/**
* Draws an image-based snowflake to the canvas.
*
* This method should only be called if our config has images.
*
* @param ctx The canvas context to draw to
*/
public drawImage(ctx: CanvasRenderingContext2D): void {
const { x, y, rotation, radius } = this.params

if (this.image) {
const radian = (rotation * Math.PI) / 180
const cos = Math.cos(radian)
const sin = Math.sin(radian)

// Translate to the location that we will be drawing the snowflake, including any rotation that needs to be applied
// The arguments for setTransform are: a, b, c, d, e, f
// a (scaleX), b (skewY), c (skewX), d (scaleY), e (translateX), f (translateY)
ctx.setTransform(cos, sin, -sin, cos, x, y)

// Draw the image with the center of the image at the center of the current location
const image = this.getImageOffscreenCanvas(this.image, radius)
ctx.drawImage(image, -(radius / 2), -(radius / 2), radius, radius)
} else {
// Not using images so no need to use transforms, just draw an arc in the right location
ctx.beginPath()
ctx.arc(x, y, radius, 0, TWO_PI)
ctx.fillStyle = this.config.color
ctx.fill()
}
const radian = (rotation * Math.PI) / 180
const cos = Math.cos(radian)
const sin = Math.sin(radian)

// Translate to the location that we will be drawing the snowflake, including any rotation that needs to be applied
// The arguments for setTransform are: a, b, c, d, e, f
// a (scaleX), b (skewY), c (skewX), d (scaleY), e (translateX), f (translateY)
ctx.setTransform(cos, sin, -sin, cos, x, y)

// Draw the image with the center of the image at the center of the current location
const image = this.getImageOffscreenCanvas(this.image!, radius)
ctx.drawImage(image, -(radius / 2), -(radius / 2), radius, radius)
}
}

Expand Down

0 comments on commit ee7a8c7

Please sign in to comment.