static { Core.update.forEach( dt -> { Iterator<Particle> it = ALL.iterator(); while (it.hasNext()) { Particle p = it.next(); p.vel = p.vel.add(p.gra.multiply(dt)); p.pos = p.pos.add(p.vel.multiply(dt)); p.lifeTime -= dt; if (p.lifeTime < 0 || CubeMap.isSolid(p.pos)) { it.remove(); } } }); Sprite s = new Sprite("ball"); Core.render.onEvent( () -> { ALL.forEach( p -> { s.scale = new Vec2(p.size); s.color = p.color; Vec3 towardsSprite = p.pos.subtract(Window3D.pos); s.draw( p.pos.subtract(towardsSprite.cross(Window3D.UP).withLength(-s.scale.x / 2)), -towardsSprite.direction2() + Math.PI / 2, towardsSprite.direction() + Math.PI / 2); }); }); }
@Override public void createInner() { List<Particle> particles = new LinkedList(); for (int i = 0; i < 2500; i++) { particles.add( new Particle(Window3D.pos.add(Vec3.randomSquare(MAX_DIST)), Math.random() * .04 + .06)); } onUpdate( dt -> { Iterator<Particle> it = particles.iterator(); while (it.hasNext()) { Particle p = it.next(); p.pos = p.pos.add(Vec3.randomSquare(dt / 5).add(new Vec3(0, 0, -dt))); p.pos = Window3D.pos.add( p.pos .subtract(Window3D.pos) .perComponent(d -> (d + 3 * MAX_DIST) % (2 * MAX_DIST) - MAX_DIST)); } }); Sprite s = new Sprite("snowflake2"); Core.renderLayer(.2) .onEvent( () -> { glEnable(GL_TEXTURE_2D); s.getTexture().bind(); WHITE.glColor(); glBegin(GL_QUADS); particles.forEach( p -> { if (CubeMap.rayCastStream(p.pos, new Vec3(0, 0, 1)) .anyMatch(cd -> cd.c != null)) { return; } ; Vec3 towards = p.pos.subtract(Window3D.pos); Vec3 side = towards.cross(Window3D.UP).withLength(p.size / 2); Vec3 snowUp = towards.cross(side).withLength(p.size / 2); Graphics3D.drawQuadFastT( p.pos.add(side).add(snowUp), p.pos.subtract(side).add(snowUp), p.pos.subtract(side).subtract(snowUp), p.pos.add(side).subtract(snowUp)); }); glEnd(); }) .addChild(this); }
public static void explode(Vec3 pos, Color4 color) { addParticle( 200, () -> new Particle( pos, Vec3.randomCircle(15), new Vec3(0, 0, -40), Double.POSITIVE_INFINITY, .05, color)); }