export declare const VERTEX_SHADER = "\nuniform float uTime;\nvarying vec2 vUv;\n\nvoid main() {\n  vUv = uv;\n  gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0);\n}\n";
export declare const FRAGMENT_SHADER = "\n\nvec3 mod289_3(vec3 x) { return x - floor(x * (1.0 / 289.0)) * 289.0; }\nvec4 mod289_4(vec4 x) { return x - floor(x * (1.0 / 289.0)) * 289.0; }\nvec4 permute(vec4 x) { return mod289_4(((x * 34.0) + 10.0) * x); }\nvec4 taylorInvSqrt(vec4 r) { return 1.79284291400159 - 0.85373472095314 * r; }\n\nfloat snoise(vec3 v) {\n  const vec2 C = vec2(1.0/6.0, 1.0/3.0);\n  const vec4 D = vec4(0.0, 0.5, 1.0, 2.0);\n\n  vec3 i  = floor(v + dot(v, C.yyy));\n  vec3 x0 = v - i + dot(i, C.xxx);\n\n  vec3 g = step(x0.yzx, x0.xyz);\n  vec3 l = 1.0 - g;\n  vec3 i1 = min(g.xyz, l.zxy);\n  vec3 i2 = max(g.xyz, l.zxy);\n\n  vec3 x1 = x0 - i1 + C.xxx;\n  vec3 x2 = x0 - i2 + C.yyy;\n  vec3 x3 = x0 - D.yyy;\n\n  i = mod289_3(i);\n  vec4 p = permute(permute(permute(\n            i.z + vec4(0.0, i1.z, i2.z, 1.0))\n          + i.y + vec4(0.0, i1.y, i2.y, 1.0))\n          + i.x + vec4(0.0, i1.x, i2.x, 1.0));\n\n  float n_ = 0.142857142857;\n  vec3  ns = n_ * D.wyz - D.xzx;\n\n  vec4 j = p - 49.0 * floor(p * ns.z * ns.z);\n\n  vec4 x_ = floor(j * ns.z);\n  vec4 y_ = floor(j - 7.0 * x_);\n\n  vec4 x = x_ * ns.x + ns.yyyy;\n  vec4 y = y_ * ns.x + ns.yyyy;\n  vec4 h = 1.0 - abs(x) - abs(y);\n\n  vec4 b0 = vec4(x.xy, y.xy);\n  vec4 b1 = vec4(x.zw, y.zw);\n\n  vec4 s0 = floor(b0) * 2.0 + 1.0;\n  vec4 s1 = floor(b1) * 2.0 + 1.0;\n  vec4 sh = -step(h, vec4(0.0));\n\n  vec4 a0 = b0.xzyw + s0.xzyw * sh.xxyy;\n  vec4 a1 = b1.xzyw + s1.xzyw * sh.zzww;\n\n  vec3 p0 = vec3(a0.xy, h.x);\n  vec3 p1 = vec3(a0.zw, h.y);\n  vec3 p2 = vec3(a1.xy, h.z);\n  vec3 p3 = vec3(a1.zw, h.w);\n\n  vec4 norm = taylorInvSqrt(vec4(dot(p0,p0), dot(p1,p1), dot(p2,p2), dot(p3,p3)));\n  p0 *= norm.x;\n  p1 *= norm.y;\n  p2 *= norm.z;\n  p3 *= norm.w;\n\n  vec4 m = max(0.5 - vec4(dot(x0,x0), dot(x1,x1), dot(x2,x2), dot(x3,x3)), 0.0);\n  m = m * m;\n  return 105.0 * dot(m * m, vec4(dot(p0,x0), dot(p1,x1), dot(p2,x2), dot(p3,x3)));\n}\n\n// Fractional Brownian Motion: stacked octaves of simplex noise\nfloat fbm(vec3 p) {\n  float value = 0.0;\n  float amplitude = 0.5;\n  float frequency = 1.0;\n  for (int i = 0; i < 4; i++) {\n    value += amplitude * snoise(p * frequency);\n    amplitude *= 0.5;\n    frequency *= 2.0;\n  }\n  return value;\n}\n\n\nuniform float uTime;\nuniform float uAnimation;\nuniform float uInputVolume;\nuniform float uOutputVolume;\nuniform vec3  uColorA;\nuniform vec3  uColorB;\nuniform float uPhaseT;\nuniform float uErrorFlash;\nuniform float uPressed;\nuniform float uOpacity;\nuniform float uVariant;        // 0 = metal, 1 = aurora\n\nconst vec3 ERROR_COLOR = vec3(0.85, 0.18, 0.18);\nconst float PI = 3.14159265358979323846;\n\nvarying vec2 vUv;\n\n// =============================================================================\n// METAL look \u2014 smooth chrome-like sphere with strong specular + depth shading.\n// Apple Siri / Vision Pro adjacent.\n// =============================================================================\nvec4 metalLook(vec2 uv, float r, vec3 cA, vec3 cB, float drive) {\n  // Two octaves of noise for surface variation\n  float n  = fbm(vec3(uv * 1.4, uAnimation * 0.18)) * 0.5 + 0.5;\n  float n2 = fbm(vec3(uv * 2.6 + 4.7, uAnimation * 0.10)) * 0.5 + 0.5;\n\n  // Vertical light bias \u2014 top brighter than bottom (3D illusion)\n  float topLight = smoothstep(-1.0, 1.0, uv.y * 0.6 + 0.4);\n  float mixT = clamp(n * 0.55 + topLight * 0.45 + n2 * 0.08, 0.0, 1.0);\n\n  // Light cream color for the highlight band \u2014 gives the chrome look.\n  // Brightens cA toward white for the upper portion of the sphere.\n  vec3 highlightTone = mix(cA, vec3(0.95, 0.92, 0.98), 0.55);\n  vec3 deepTone      = mix(cB, vec3(0.04, 0.02, 0.10), 0.55);\n\n  // 4-stop ramp: cream highlight \u2192 cA \u2192 cB \u2192 deep core\n  vec3 base;\n  if (mixT > 0.66) {\n    base = mix(cA, highlightTone, (mixT - 0.66) / 0.34);\n  } else if (mixT > 0.33) {\n    base = mix(cB, cA, (mixT - 0.33) / 0.33);\n  } else {\n    base = mix(deepTone, cB, mixT / 0.33);\n  }\n\n  // Specular: tight bright spot top-left\n  vec2 specCenter = vec2(-0.35, 0.45);\n  float spec = smoothstep(0.45, 0.0, length(uv - specCenter));\n  base += vec3(1.0) * spec * 0.32;\n\n  // Bottom shadow for depth\n  float shadow = smoothstep(0.3, 1.0, -uv.y) * 0.35;\n  base = mix(base, base * 0.55, shadow);\n\n  // Inner glow on audio\n  float glow = (1.0 - r) * (1.0 - r);\n  base += cA * drive * glow * 0.5;\n\n  return vec4(base, 1.0);\n}\n\n// =============================================================================\n// AURORA look \u2014 soft layered ribbons drifting across a translucent disc.\n// Northern-lights aesthetic. Calm, atmospheric.\n// =============================================================================\nvec4 auroraLook(vec2 uv, float r, vec3 cA, vec3 cB, float drive) {\n  float t = uAnimation * 0.25;\n\n  // Disc base \u2014 deep, translucent. cB darkened.\n  vec3 baseColor = mix(cB * 0.25, cB * 0.55, smoothstep(1.0, 0.0, r));\n\n  // Three drifting ribbons at different y-offsets, angles, and speeds.\n  // Each ribbon is a horizontally-stretched soft band whose vertical position\n  // oscillates with time + noise.\n\n  // Ribbon 1 \u2014 upper, primary color\n  float y1 = uv.y - (sin(t * 0.7 + uv.x * 1.5) * 0.18) - 0.15;\n  float band1 = exp(-pow(y1 / 0.18, 2.0));\n  float n1 = fbm(vec3(uv.x * 2.0 + t, uv.y * 0.8, t * 0.4)) * 0.5 + 0.5;\n  vec3 ribbon1 = cA * band1 * n1 * 1.4;\n\n  // Ribbon 2 \u2014 middle, accent color (cooler \u2014 shift cA toward cyan)\n  vec3 cool = mix(cA, vec3(0.36, 0.83, 1.0), 0.45);\n  float y2 = uv.y - (sin(t * 0.55 + uv.x * 2.2 + 1.7) * 0.22) + 0.05;\n  float band2 = exp(-pow(y2 / 0.14, 2.0));\n  float n2 = fbm(vec3(uv.x * 2.6 + t * 0.6 + 3.1, uv.y * 0.6, t * 0.3)) * 0.5 + 0.5;\n  vec3 ribbon2 = cool * band2 * n2 * 1.0;\n\n  // Ribbon 3 \u2014 lower, warm accent (shift cA toward pink)\n  vec3 warm = mix(cA, vec3(1.0, 0.49, 0.83), 0.55);\n  float y3 = uv.y - (sin(t * 0.4 + uv.x * 1.8 + 4.2) * 0.18) + 0.30;\n  float band3 = exp(-pow(y3 / 0.16, 2.0));\n  float n3 = fbm(vec3(uv.x * 2.2 + t * 0.45 + 7.9, uv.y * 0.7, t * 0.35)) * 0.5 + 0.5;\n  vec3 ribbon3 = warm * band3 * n3 * 0.85;\n\n  // Stack ribbons additively over the disc\n  vec3 base = baseColor + ribbon1 + ribbon2 + ribbon3;\n\n  // Audio drive intensifies all ribbons + brightens center\n  base += (ribbon1 + ribbon2 + ribbon3) * drive * 0.6;\n  float glow = (1.0 - r) * (1.0 - r);\n  base += cA * drive * glow * 0.35;\n\n  // Subtle inner rim accent for legibility against dark backgrounds\n  float rim = smoothstep(0.82, 0.98, r);\n  base += cA * rim * 0.22;\n\n  return vec4(base, 1.0);\n}\n\nvoid main() {\n  vec2 uv = vUv * 2.0 - 1.0;\n  float r = length(uv);\n\n  // Discard fragments outside the unit circle so the canvas stays clean.\n  if (r > 1.0) {\n    gl_FragColor = vec4(0.0);\n    return;\n  }\n\n  // ---- Phase masks (0..1 for each phase) ---------------------------------\n  // uPhaseT smoothly interpolates between numeric phases:\n  // 0=idle, 1=listening, 2=thinking, 3=speaking, 4=error.\n  float isListening = clamp(1.0 - abs(uPhaseT - 1.0), 0.0, 1.0);\n  float isThinking  = clamp(1.0 - abs(uPhaseT - 2.0), 0.0, 1.0);\n  float isSpeaking  = clamp(1.0 - abs(uPhaseT - 3.0), 0.0, 1.0);\n\n  float inputDrive  = uInputVolume  * isListening;\n  float outputDrive = uOutputVolume * isSpeaking;\n  float thinkPulse  = isThinking * (0.5 + 0.5 * sin(uTime * 2.0));\n  float drive = max(inputDrive, max(outputDrive, thinkPulse * 0.4));\n\n  // ---- Resolve effective colors with error tint --------------------------\n  vec3 cA = mix(uColorA, ERROR_COLOR, uErrorFlash);\n  vec3 cB = mix(uColorB, ERROR_COLOR * 0.55, uErrorFlash * 0.7);\n\n  // ---- Pick variant ------------------------------------------------------\n  vec4 result;\n  if (uVariant > 0.5) {\n    result = auroraLook(uv, r, cA, cB, drive);\n  } else {\n    result = metalLook(uv, r, cA, cB, drive);\n  }\n\n  vec3 base = result.rgb;\n\n  // ---- Press: slight core brighten ---------------------------------------\n  base = mix(base, base * 1.18, uPressed * (1.0 - smoothstep(0.0, 0.55, r)));\n\n  // ---- Edge falloff: smooth alpha at the disc boundary -------------------\n  float alpha = smoothstep(1.0, 0.92, r);\n\n  gl_FragColor = vec4(base, alpha * uOpacity);\n}\n";
