Skip to content

LabL

The lab

Small experiments. Each starts with a hypothesis and ends with what I learned, including the ones that failed.

05experiments

ActiveFeb 2026

High-Frequency Cursor Physics via gsap.quickTo

Investigating performance differences between requestAnimationFrame mouse interpolation vs GSAP quickTo single-tween pipes.

GSAP 3TypeScriptPerformance APIDOM

Hypothesis

Standard GSAP to() tweens invoked on every mousemove event cause memory churn and trigger unnecessary tween allocations. Reusing a single gsap.quickTo instance should eliminate garbage collection pauses.

Result

Tested cursor tracking with 10,000 synthetic mouse events. Standard gsap.to created thousands of temporary tween objects per minute. Using gsap.quickTo(target, property, { duration: 0.1 }) created a single long-lived tween that smoothly interpolated high-frequency mouse coordinates with zero layout thrashing.

  • gsap.quickTo is significantly more memory-efficient for continuous 60fps tracking than recreating tweens.
  • Must always gate custom cursor instantiation with @media (hover: hover) and (pointer: fine) to avoid breaking mobile touch interactions.
ExperimentJan 2026

Procedural Skybox Fog Shader for WebGL

Evaluating GLSL distance fog functions that blend horizon lines seamlessly into dynamic background skies.

Three.jsGLSLWebGLShaderMaterial

Hypothesis

A custom fragment shader calculating exp2 depth fog with a vertical horizon gradient can simulate realistic atmospheric haze with negligible fragment shader overhead.

Result

Implemented a custom shader material applied to a skydome mesh in Three.js. The shader interpolates between a daylight zenith color, a sunset orange horizon tint, and a deep obsidian night value based on a normalized solar elevation parameter.

  • Exponential squared fog (exp2(-density * depth * depth)) looks significantly more natural than linear fog for low-poly horizons.
  • Uniform updates must be throttled during camera movements to avoid CPU-to-GPU bus bottlenecks.
FailedSep 2025

CSS Houdini Paint Worklet for Animated Brutalist Shards

Attempting to generate animated geometric refraction shards using CSS Paint Worklets instead of DOM elements.

CSS HoudiniPaint APIJavaScript

Hypothesis

Rendering background shards off the main thread via CSS Houdini Paint API would reduce DOM node count to zero while enabling 60fps procedural animations.

Result

Created a paint worklet script to draw fractured glass polygons onto a canvas background. While performance was fast in Chromium, browser support in Safari and Firefox remained non-existent, and passing dynamic scroll progress uniforms to the worklet caused inconsistent repaint triggers.

  • CSS Houdini Paint API remains poorly supported across Safari/WebKit and Firefox, making it unsuitable for cross-browser production.
  • A lightweight SVG polygon overlay or controlled GSAP DOM pool provides much more predictable rendering and full browser compatibility.
ActiveAug 2025

ScrollTrigger Normalization on Mobile WebKit

Diagnosing and fixing the iOS Safari URL bar resize jumping issue during ScrollTrigger pinned timelines.

GSAP ScrollTriggerMobile WebKitTouch Events

Hypothesis

Using ScrollTrigger.normalizeScroll(true) prevents mobile browser address bar collapse from re-evaluating viewport heights and triggering infinite resize loops.

Result

Mobile browsers dynamically hide the address bar on scroll, changing window.innerHeight and causing ScrollTrigger to recompute start/end positions mid-animation. Enabling touch normalization locks the scroll container and prevents jarring visual jumps.

  • Always wrap GSAP animations in gsap.context() for idempotent cleanup during Next.js client-side route transitions.
  • Skip smooth scroll libraries on touch devices; native inertial scrolling provides the best input responsiveness.
PrototypeJun 2025

Multi-Octave 3D Simplex Cave Generator

Prototyping volumetric 3D noise carve-outs for subterranean cave systems in voxel worlds.

Simplex NoiseThree.jsVoxel EngineWeb Workers

Hypothesis

Evaluating 3D Simplex noise thresholding where noise(x, y, z) > 0.4 hollows out stone blocks into natural subterranean tunnels.

Result

Implemented a 3D noise sample pass over a 16x64x16 chunk column. While tunnel shapes were organic and interesting, calculating 3D noise per block in vanilla JavaScript on the main thread introduced 40ms frame drops during rapid movement.

  • 3D noise computation is an order of magnitude more expensive than 2D heightmap sampling.
  • Volumetric terrain generation must be offloaded to Web Workers or compiled to WebAssembly to maintain interactive frame rates.