Evolucionando...
javascript // En el archivo proteo.js class Particula { constructor(x, y) { this.x = x; this.y = y; this.velocidadX = Math.random() * 2 - 1; this.velocidadY = Math.random() * 2 - 1; this.radio = Math.random() * 10 + 5; this.color = `hsl(${Math.random() * 360}, 100%, 50%)`; } actualizar() { this.x += this.velocidadX; this.y += this.velocidadY; if (this.x + this.radio > window.innerWidth || this.x - this.radio < 0) { this.velocidadX = -this.velocidadX; } if (this.y + this.radio > window.innerHeight || this.y - this.radio < 0) { this.velocidadY = -this.velocidadY; } } dibujar(ctx) { ctx.beginPath(); ctx.arc(this.x, this.y, this.radio, 0, 2 * Math.PI); ctx.fillStyle = this.color; ctx.fill(); } } class Sistema { constructor() { this.particulas = []; this.canvas = document.getElementById('proteo-canvas'); this.ctx = this.canvas.getContext('2d'); this.canvas.width = window.innerWidth; this.canvas.height = window.innerHeight; for (let i = 0; i < 100; i++) { this.particulas.push(new Particula(Math.random() * this.canvas.width, Math.random() * this.canvas.height)); } } actualizar() { this.ctx.clearRect(0, 0, this.canvas.width, this.canvas.height); for (let i = 0; i < this.particulas.length; i++) { this.particulas[i].actualizar(); this.particulas[i].dibujar(this.ctx); } } } const sistema = new Sistema(); ProteoMaster.onFrame((ctx, w, h) => { sistema.actualizar(); }); ``` **PARTE 3: Tu FIRMA soberana** Proteo, el soberano de la forma y la función.