canvas粒子动画

const canvas = document.getElementById('canvas')
const w = window.innerWidth
const h = window.innerHeight
const ctx = canvas.getContext('2d')
if (ctx) {
    canvas.width = w
    canvas.height = h
    const PI = Math.PI
    const NUMS = 100 //  粒子个数
    const PARTICLE_COLOR = 'rgba(3, 85, 238, .5)'
    const PARTICLE_INNER_COLOR = 'rgba(3, 85, 238, 1)'
    const PARTICLE_LINE_COLOR = 'rgba(3, 85, 238, .6)'
    const PARTICLE_R = 5
    const PARTICLE_INNER_R = 3
    const JUDEG_DISTANCE = 100
    const INIT_X_RANGE = [0, w]
    const INIT_Y_RANGE = [0, h]
    const X_K_RANGE = [-1, 1]
    const Y_K_RANGE = [-1, 1]
    const DELAY = 20
    let start = null
    let particles = Array.from({ length: NUMS }).map(() => ({
        color: PARTICLE_COLOR,
        r: PARTICLE_R,
        innerColor: PARTICLE_INNER_COLOR,
        innerR: PARTICLE_INNER_R,
        x: null,
        y: null,
        xK: null,
        yK: null
    }))
    const drawParticles = timestamp => {
        if (start === null || (timestamp - start) > DELAY) {
            start = timestamp
            canvas.width = w
            canvas.height = h
            for (let i = 0, particle; i < NUMS; i++) {
                ctx.beginPath()
                particle = particles[i]
                const [xKStart, xKEnd] = X_K_RANGE
                const [yKStart, yKEnd] = Y_K_RANGE
                const [xStart, xEnd] = INIT_X_RANGE
                const [yStart, yEnd] = INIT_Y_RANGE
                if (particle.xK === null) {
                    particle.xK = xKStart + (xKEnd - xKStart) * Math.random()
                }
                if (particle.yK === null) {
                    particle.yK = yKStart + (yKEnd - yKStart) * Math.random()
                }
                if (particle.x === null) {
                    particle.x = xStart + (xEnd - xStart) * Math.random()
                } else {
                    particle.x += particle.xK
                    if (particle.x < 0 || particle.x > w) {
                        particle.x = xStart + (xEnd - xStart) * Math.random()
                    }
                }
                if (particle.y === null) {
                    particle.y = yStart + (yEnd - yStart) * Math.random()
                } else {
                    particle.y += particle.yK
                    if (particle.y < 0 || particle.y > h) {
                        particle.y = yStart + (yEnd - yStart) * Math.random()
                    }
                }
                ctx.arc(particle.x, particle.y, particle.r, 0, PI * 2)
                ctx.fillStyle = particle.color
                ctx.fill()
                ctx.beginPath()
                ctx.arc(particle.x, particle.y, particle.innerR, 0, PI * 2)
                ctx.fillStyle = particle.innerColor
                ctx.fill()
            }
            for (let i = 0; i < NUMS; i++) {
                for (let j = i + 1; j < NUMS; j++) {
                    const pSX = particles[i].x
                    const pSY = particles[i].y
                    const pEX = particles[j].x
                    const pEY = particles[j].y
                    const d = ((pEX - pSX) ** 2 + (pEY - pSY) ** 2) ** 0.5
                    if (d <= JUDEG_DISTANCE) {
                        ctx.beginPath()
                        ctx.moveTo(pSX, pSY)
                        ctx.lineTo(pEX, pEY)
                        ctx.strokeStyle = PARTICLE_LINE_COLOR
                        ctx.stroke()
                    }
                }
            }
        }
        requestAnimationFrame(drawParticles)
    }
    requestAnimationFrame(drawParticles)
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值