From 9d995567bdd4c138e26c0b1059486b57bfedf12c Mon Sep 17 00:00:00 2001 From: unanmed <1319491857@qq.com> Date: Wed, 15 Feb 2023 21:15:33 +0800 Subject: [PATCH] =?UTF-8?q?=E5=AE=8C=E5=96=84=E7=B2=92=E5=AD=90?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/plugin/particle/particle.ts | 33 ++++++++++++++++++++++++++++++++- src/plugin/particle/render.ts | 21 ++++++--------------- src/plugin/webgl/matrix.ts | 1 - 3 files changed, 38 insertions(+), 17 deletions(-) diff --git a/src/plugin/particle/particle.ts b/src/plugin/particle/particle.ts index 6f3643c..32171a4 100644 --- a/src/plugin/particle/particle.ts +++ b/src/plugin/particle/particle.ts @@ -49,6 +49,10 @@ export class Particle { /** 需要渲染的粒子列表 */ list: ParticleOne[] = []; + /** 是否需要更新缓冲区数据 */ + needUpdateBuffer: boolean = false; + /** 当前缓存信息 */ + cache?: Float32Array; /** 是否需要更新 */ private needUpdate: boolean = false; @@ -175,6 +179,27 @@ export class Particle { this.list = particles; } + /** + * 获取粒子的Float32Array信息 + */ + getArrayInfo() { + if (!this.cache || this.needUpdateBuffer) { + const array = this.list; + const particleArray = new Float32Array( + array + .map(v => { + const [r, g, b, a] = v.color; + return [v.x, v.y, v.z, r, g, b, a, v.r, 0]; + }) + .flat() + ); + this.cache = particleArray; + return particleArray; + } else { + return this.cache; + } + } + /** * 每帧执行的粒子更新器 */ @@ -185,10 +210,12 @@ export class Particle { // check number if (this.list.length > this.density) { this.list.splice(this.density); + this.needUpdateBuffer = true; } else if (this.list.length < this.density) { this.list.push( ...this.generateNewParticles(this.density - this.list.length) ); + this.needUpdateBuffer = true; } // check radius @@ -198,6 +225,7 @@ export class Particle { this.list.forEach(v => { v.r += delta; }); + this.needUpdateBuffer = true; } } @@ -214,6 +242,7 @@ export class Particle { v.color[2] += b; v.color[3] += a; }); + this.needUpdateBuffer = true; } } @@ -228,6 +257,7 @@ export class Particle { v.y += y; v.z += z; }); + this.needUpdateBuffer = true; } } @@ -266,6 +296,7 @@ export class Particle { }) as ParticleColor; }); } + this.needUpdateBuffer = true; } } @@ -298,6 +329,6 @@ export class Particle { * 渲染这个粒子 */ private render() { - this.renderer?.render(this); + this.renderer?.render(); } } diff --git a/src/plugin/particle/render.ts b/src/plugin/particle/render.ts index 5fed02c..88fef18 100644 --- a/src/plugin/particle/render.ts +++ b/src/plugin/particle/render.ts @@ -202,15 +202,8 @@ export class Renderer { * 更新一个粒子的缓冲区数据 * @param array 粒子的粒子元素数组 */ - private updateOneParticleBufferData(array: ParticleOne[]) { - const particleArray = new Float32Array( - array - .map(v => { - const [r, g, b, a] = v.color; - return [v.x, v.y, v.z, r, g, b, a, v.r, 0]; - }) - .flat() - ); + private updateOneParticleBufferData(particle: Particle) { + const particleArray = particle.getArrayInfo(); this.gl.bufferData( this.gl.ARRAY_BUFFER, particleArray, @@ -240,7 +233,7 @@ export class Renderer { * @param particle 要渲染的粒子 */ private renderOne(particle: Particle) { - const arr = this.updateOneParticleBufferData(particle.list); + const arr = this.updateOneParticleBufferData(particle); const size = arr.BYTES_PER_ELEMENT; const { position, color, radius } = this.attribLocation; @@ -307,11 +300,9 @@ window.addEventListener('load', async () => { camera.lookAt([1, 1, 5], [0, 0, 0], [0, 1, 0]); camera.setPerspective(20, 1, 1, 100); - console.log(camera.view, camera.projection); - - particle.setColor([0.3, 0.6, 0.7, 0.7]); - particle.setRadius(3); - particle.setDensity(1000); + particle.setColor([0.3, 0.6, 0.7, 1.0]); + particle.setRadius(2); + particle.setDensity(5000); particle.setThreshold({ posX: 0.2, posY: 0.2, diff --git a/src/plugin/webgl/matrix.ts b/src/plugin/webgl/matrix.ts index 450ba03..de6c935 100644 --- a/src/plugin/webgl/matrix.ts +++ b/src/plugin/webgl/matrix.ts @@ -1,4 +1,3 @@ -import { cloneDeep } from 'lodash'; import { has } from '../utils'; export class Matrix extends Array {