fix(security & perf): implement bearer session tokens, salted pbkdf2, object pooling and background caching
This commit is contained in:
+86
-29
@@ -1,10 +1,63 @@
|
||||
// Particle Object Pool to eliminate GC churn during large waves
|
||||
window.ParticlePool = class ParticlePool {
|
||||
constructor(initialCapacity = 150) {
|
||||
this.pool = [];
|
||||
for (let i = 0; i < initialCapacity; i++) {
|
||||
this.pool.push({
|
||||
x: 0,
|
||||
y: 0,
|
||||
vx: 0,
|
||||
vy: 0,
|
||||
color: '#ffffff',
|
||||
size: 3,
|
||||
life: 0,
|
||||
maxLife: 0
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
get(x, y, vx, vy, color = '#8bc34a', size = 3, life = 0.35) {
|
||||
const p = this.pool.length > 0 ? this.pool.pop() : { x: 0, y: 0, vx: 0, vy: 0, color: '#ffffff', size: 3, life: 0, maxLife: 0 };
|
||||
p.x = x;
|
||||
p.y = y;
|
||||
p.vx = vx;
|
||||
p.vy = vy;
|
||||
p.color = color;
|
||||
p.size = size;
|
||||
p.life = life;
|
||||
p.maxLife = life;
|
||||
return p;
|
||||
}
|
||||
|
||||
release(p) {
|
||||
if (!p) return;
|
||||
p.life = 0;
|
||||
this.pool.push(p);
|
||||
}
|
||||
|
||||
releaseAll(particles) {
|
||||
if (!Array.isArray(particles)) return;
|
||||
for (let i = 0; i < particles.length; i++) {
|
||||
this.release(particles[i]);
|
||||
}
|
||||
}
|
||||
|
||||
clear() {
|
||||
this.pool = [];
|
||||
}
|
||||
};
|
||||
|
||||
// Combat & Collision Resolution System (with Bowling Ricochet & Coin Drops)
|
||||
window.CombatSystem = class CombatSystem {
|
||||
constructor() {
|
||||
this.particlePool = new window.ParticlePool(150);
|
||||
this.particles = [];
|
||||
}
|
||||
|
||||
reset() {
|
||||
if (this.particlePool) {
|
||||
this.particlePool.releaseAll(this.particles);
|
||||
}
|
||||
this.particles = [];
|
||||
}
|
||||
|
||||
@@ -12,45 +65,50 @@ window.CombatSystem = class CombatSystem {
|
||||
for (let i = 0; i < count; i++) {
|
||||
const angle = Math.random() * Math.PI * 2;
|
||||
const speed = 40 + Math.random() * 80;
|
||||
this.particles.push({
|
||||
this.particles.push(this.particlePool.get(
|
||||
x,
|
||||
y,
|
||||
vx: Math.cos(angle) * speed,
|
||||
vy: Math.sin(angle) * speed,
|
||||
Math.cos(angle) * speed,
|
||||
Math.sin(angle) * speed,
|
||||
color,
|
||||
size: 3 + Math.random() * 3,
|
||||
life: 0.35,
|
||||
maxLife: 0.35
|
||||
});
|
||||
3 + Math.random() * 3,
|
||||
0.35
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
createExplosionParticles(x, y) {
|
||||
const colors = ['#ff5722', '#ff9800', '#ffeb3b', '#424242'];
|
||||
for (let i = 0; i < 35; i++) {
|
||||
const angle = Math.random() * Math.PI * 2;
|
||||
const speed = 50 + Math.random() * 200;
|
||||
const colors = ['#ff5722', '#ff9800', '#ffeb3b', '#424242'];
|
||||
this.particles.push({
|
||||
this.particles.push(this.particlePool.get(
|
||||
x,
|
||||
y,
|
||||
vx: Math.cos(angle) * speed,
|
||||
vy: Math.sin(angle) * speed,
|
||||
color: colors[Math.floor(Math.random() * colors.length)],
|
||||
size: 5 + Math.random() * 8,
|
||||
life: 0.65,
|
||||
maxLife: 0.65
|
||||
});
|
||||
Math.cos(angle) * speed,
|
||||
Math.sin(angle) * speed,
|
||||
colors[Math.floor(Math.random() * colors.length)],
|
||||
5 + Math.random() * 8,
|
||||
0.65
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
update(dt, gameState) {
|
||||
// 1. Update Particles
|
||||
for (const p of this.particles) {
|
||||
// 1. Update Particles in-place (eliminating GC allocations)
|
||||
let writeIdx = 0;
|
||||
for (let i = 0; i < this.particles.length; i++) {
|
||||
const p = this.particles[i];
|
||||
p.x += p.vx * dt;
|
||||
p.y += p.vy * dt;
|
||||
p.life -= dt;
|
||||
if (p.life > 0) {
|
||||
this.particles[writeIdx++] = p;
|
||||
} else {
|
||||
this.particlePool.release(p);
|
||||
}
|
||||
}
|
||||
this.particles = this.particles.filter(p => p.life > 0);
|
||||
this.particles.length = writeIdx;
|
||||
|
||||
// 2. Projectiles vs Zombies
|
||||
for (const proj of gameState.projectiles) {
|
||||
@@ -233,16 +291,15 @@ window.CombatSystem = class CombatSystem {
|
||||
// Tree of Wisdom Cheat: Daisies
|
||||
if (gameState.tree && gameState.tree.cheats && gameState.tree.cheats.daisies) {
|
||||
for (let i = 0; i < 6; i++) {
|
||||
this.particles.push({
|
||||
x: zombie.x + (Math.random() - 0.5) * 30,
|
||||
y: zombie.y + 10 + (Math.random() - 0.5) * 16,
|
||||
vx: 0,
|
||||
vy: -8,
|
||||
color: '#ffffff',
|
||||
size: 4,
|
||||
life: 2.5,
|
||||
maxLife: 2.5
|
||||
});
|
||||
this.particles.push(this.particlePool.get(
|
||||
zombie.x + (Math.random() - 0.5) * 30,
|
||||
zombie.y + 10 + (Math.random() - 0.5) * 16,
|
||||
0,
|
||||
-8,
|
||||
'#ffffff',
|
||||
4,
|
||||
2.5
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user