// 025 - Julia Morphism (experimental)
// 1:1 Original algorithm engine source
function createJuliaMorph() {
const SAMPLES = 50;
return {
setup() {
},
render(context, timeState, params) {
const { ctx, width, height } = context;
const t = timeState.time * Number(params.speed || 0.4);
const maxIter = Number(params.maxIter || 24);
const cr = -0.8 + 0.15 * Math.cos(t * 0.7);
const ci = 0.156 + 0.15 * Math.sin(t * 0.7);
const stepX = width / SAMPLES;
const stepY = height / SAMPLES;
ctx.fillStyle = "#08090d";
ctx.fillRect(0, 0, width, height);
for (let y = 0; y < SAMPLES; y++) {
const zy0 = y / SAMPLES * 2.8 - 1.4;
for (let x = 0; x < SAMPLES; x++) {
const zx0 = x / SAMPLES * 2.8 - 1.4;
let zx = zx0;
let zy = zy0;
let iter = 0;
while (zx * zx + zy * zy < 4 && iter < maxIter) {
const tempX = zx * zx - zy * zy + cr;
zy = 2 * zx * zy + ci;
zx = tempX;
iter++;
}
if (iter < maxIter) {
const smoothIter = iter + 1 - Math.log(Math.log(Math.sqrt(zx * zx + zy * zy))) / Math.log(2);
const hue = (smoothIter * 14 + t * 20) % 360;
const px = x * stepX;
const py = y * stepY;
ctx.fillStyle = hsla(hue, 85, 60, 0.75);
ctx.fillRect(px, py, stepX + 0.5, stepY + 0.5);
}
}
}
}
};
}
// Default parameters from content metadata
const defaultParams = [
{
"key": "speed",
"label": "Morph Velocity",
"type": "range",
"min": 0.1,
"max": 1.5,
"step": 0.05,
"defaultValue": 0.4,
"description": "Parameter space orbit speed"
},
{
"key": "maxIter",
"label": "Max Iterations",
"type": "range",
"min": 10,
"max": 50,
"step": 2,
"defaultValue": 24,
"description": "Fractal escape depth"
}
];
if (!window.__art_instances) window.__art_instances = {};
if (!window.__art_instances['julia-morph']) {
const inst = typeof createJuliaMorph === 'function' ? createJuliaMorph() : null;
if (inst && inst.setup) {
inst.setup({ ctx, width, height, dpr: 1, aspectRatio: width / height }, defaultParams);
}
window.__art_instances['julia-morph'] = inst;
}
const instance = window.__art_instances['julia-morph'];
if (instance && instance.render) {
instance.render(
{ ctx, width, height, dpr: 1, aspectRatio: width / height },
{ time, deltaTime: dt, frameCount: Math.floor(time * 60), fps: 60 },
defaultParams
);
}