+ (480 + lx.getBaseHuef() - min(clrConst*p.fz, 120)) % 360,
+ 100,
+ b);
+ }
+ }
+}
+
+class BoomEffect extends SCEffect {
+
+ final BasicParameter falloff = new BasicParameter("WIDTH", 0.5);
+ final BasicParameter speed = new BasicParameter("SPD", 0.5);
+ final BasicParameter bright = new BasicParameter("BRT", 1.0);
+ final BasicParameter sat = new BasicParameter("SAT", 0.2);
+ List<Layer> layers = new ArrayList<Layer>();
+
+ class Layer {
+ LinearEnvelope boom = new LinearEnvelope(-40, 500, 1300);
+
+ Layer() {
+ addModulator(boom);
+ trigger();
+ }
+
+ void trigger() {
+ float falloffv = falloffv();
+ boom.setRange(-100 / falloffv, 500 + 100/falloffv, 4000 - speed.getValuef() * 3300);
+ boom.trigger();
+ }
+
+ void doApply(int[] colors) {
+ float brightv = 100 * bright.getValuef();
+ float falloffv = falloffv();
+ float satv = sat.getValuef() * 100;
+ float huev = lx.getBaseHuef();
+ for (Point p : Point.list) {
+ colors[p.index] = blendColor(
+ colors[p.index],
+ color(huev, satv, constrain(brightv - falloffv*abs(boom.getValuef() - dist(2*p.fx, p.fy, 2*p.fz, 128, 128, 128)), 0, 100)),
+ ADD);
+ }
+ }
+ }
+
+ BoomEffect(GLucose glucose) {
+ super(glucose, true);
+ addParameter(falloff);
+ addParameter(speed);
+ addParameter(bright);
+ addParameter(sat);
+ }
+
+ public void onEnable() {
+ for (Layer l : layers) {
+ if (!l.boom.isRunning()) {
+ l.trigger();
+ return;
+ }
+ }
+ layers.add(new Layer());
+ }
+
+ private float falloffv() {
+ return 20 - 19 * falloff.getValuef();
+ }
+
+ public void onTrigger() {
+ onEnable();
+ }
+
+ public void doApply(int[] colors) {
+ for (Layer l : layers) {
+ if (l.boom.isRunning()) {
+ l.doApply(colors);
+ }