pane.ts

webgpu-based path tracer

src/pane.ts

4.25 KB
import { Vec3 } from 'gl-matrix';
import { Pane } from 'tweakpane';

export const InitPane = (device: GPUDevice, UNIFORMS: any, uniformBuffer0: GPUBuffer) => {
  const container = document.getElementById("pane-container") as HTMLElement;
  const header = document.getElementById("pane-container-header") as HTMLElement;

  const pane = new Pane({
    container: container,
  });
  let offsetX = 0;
  let offsetY = 0;
  let isDragging = false;
  header.addEventListener('mousedown', (e) => {
    isDragging = true;
    offsetX = e.clientX - container.offsetLeft;
    offsetY = e.clientY - container.offsetTop;
    container.style.cursor = 'move';
  });
  document.addEventListener('mousemove', (e) => {
    if (isDragging) {
      let x = e.clientX - offsetX;
      let y = e.clientY - offsetY;

      const viewportWidth = window.innerWidth;
      const viewportHeight = window.innerHeight;

      const containerWidth = container.offsetWidth;
      const containerHeight = container.offsetHeight;

      const minX = 0;
      const maxX = viewportWidth - containerWidth;
      const minY = 0;
      const maxY = viewportHeight - containerHeight;

      x = Math.max(minX, Math.min(x, maxX));
      y = Math.max(minY, Math.min(y, maxY));

      container.style.left = `${x}px`;
      container.style.top = `${y}px`;
    }
  });
  document.addEventListener('mouseup', () => {
    isDragging = false;
    container.style.cursor = 'default';
  });

  //packed vars: samp_count, bounce, aperture, focal_length]
  let packed0 = new Float32Array([UNIFORMS.sample_count, UNIFORMS.bounce_count, UNIFORMS.aperture, UNIFORMS.focal_length])
  pane.addBinding(UNIFORMS, 'frameTimeMs', {
    readonly: true,
    label: "Frame Time ",
    view: 'number',
    min: 0,
    max: 120.00,
  });
  pane.addBinding(UNIFORMS, 'frameTimeMs', {
    readonly: true,
    label: "Frame Time Graph",
    view: 'graph',
    min: 0,
    max: 120.00,
  });
  const cameraFolder = pane.addFolder({ title: 'Camera' })
  cameraFolder.addBinding(UNIFORMS, 'thin_lens', {
    label: "Enable thin lens approx",
  }).on('change', (e) => {
    device.queue.writeBuffer(uniformBuffer0, 256, new Float32Array([e.value]));
    window.framecount = 0;
  });
  cameraFolder.addBinding(UNIFORMS, 'sample_count', {
    view: 'slider',
    type: 'number',
    label: 'Sample Count',
    min: 1,
    max: 5,
    value: 1,
    step: 1,
  }).on('change', (e) => {
    packed0[0] = e.value;
    device.queue.writeBuffer(uniformBuffer0, 236, packed0);
    window.framecount = 0;
  });
  cameraFolder.addBinding(UNIFORMS, 'bounce_count', {
    view: 'slider',
    type: 'number',
    label: 'Max Bounces',
    min: 1,
    max: 10,
    value: 1,
    step: 1,
  }).on('change', (e) => {
    packed0[1] = e.value;
    device.queue.writeBuffer(uniformBuffer0, 236, packed0);
    window.framecount = 0;
  });
  cameraFolder.addBinding(UNIFORMS, 'aperture', {
    view: 'slider',
    type: 'number',
    label: 'Aperture',
    min: 0.1,
    max: 1,
    value: 0.1,
  }).on('change', (e) => {
    packed0[2] = e.value;
    device.queue.writeBuffer(uniformBuffer0, 236, packed0);
    window.framecount = 0;
  });
  cameraFolder.addBinding(UNIFORMS, 'focal_length', {
    view: 'slider',
    type: 'number',
    label: 'Focal Length',
    min: 1,
    max: 200,
    value: 1,
  }).on('change', (e) => {
    packed0[3] = e.value;
    device.queue.writeBuffer(uniformBuffer0, 236, packed0);
    window.framecount = 0;
  });
  const dirFolder = pane.addFolder({ title: 'Environment' });
  dirFolder.addBinding(UNIFORMS, 'sun_angle', {
    label: 'Sun Angle',
    x: { min: -1, max: 1, step: 0.1 },
    y: { min: -1, max: 1, step: 0.1 },
    z: { min: -1, max: 1, step: 0.1 },
  }).on('change', () => {
    device.queue.writeBuffer(uniformBuffer0, 208, Vec3.fromValues(UNIFORMS.sun_angle.x, UNIFORMS.sun_angle.y, UNIFORMS.sun_angle.z));
    window.framecount = 0;
  });
  dirFolder.addBinding(UNIFORMS, 'sun_color', {
    color: { type: 'float' },
    picker: 'inline',
    label: 'Sun Color',
    x: { min: -1, max: 1, step: 0.1 },
    y: { min: -1, max: 1, step: 0.1 },
    z: { min: -1, max: 1, step: 0.1 },
  }).on('change', (e) => {
    device.queue.writeBuffer(uniformBuffer0, 224, Vec3.fromValues(e.value.r * UNIFORMS.scale, e.value.g * UNIFORMS.scale, e.value.b * UNIFORMS.scale));
    window.framecount = 0;
  });
}