first commit

This commit is contained in:
2026-05-29 08:20:56 +01:00
commit 949299f58d
6368 changed files with 527176 additions and 0 deletions

View File

@@ -0,0 +1,102 @@
# `<PluginParameterSlider>`
Linear-slider primitive for a single `AudioFxPlugin` parameter.
Mirrors `<PluginParameterKnob>`'s a11y contract and exposes a native
`<input type="range">` for pointer drag while implementing the
mandated keyboard keymap directly so step semantics match the knob.
<!-- begin:auto-docs -->
_(no submodules)_
<!-- end:auto-docs -->
## Purpose
The `<PluginParameterSlider>` is the linear half of the generic
parameter-control surface. It is preferred over the knob when the
parameter is naturally horizontal — pan, dry/wet mix, threshold,
crossfeed — and when consumers want native touch / pointer drag
without an extra dependency.
The slider subscribes to the parameter via the Phase-1
`useParameter` hook, so per-block parameter updates flow to the UI at
the provider's configured `sampleRateHz`.
## Features
- Native `<input type="range">` for pointer & touch drag, with `step`
set to `(max - min) / 100` so drag granularity matches the keyboard
fine-step.
- `role="slider"`, `aria-valuemin`, `aria-valuemax`, `aria-valuenow`,
`aria-valuetext` (unit-aware via `formatAriaValueText`).
- Full keyboard keymap: `←`/`→`, `↑`/`↓`, `PageUp`/`PageDown`,
`Home`/`End`, `Shift` ×10, `Alt` ÷10. Identical semantics to the
knob.
- `orientation` prop (`"horizontal"` | `"vertical"`) reflected on the
wrapper as `data-orientation`.
- `data-parameter-id` for stylesheet targeting.
- CSS-class API only (`rax-slider`, `rax-slider__input`,
`rax-slider__label`, `rax-slider__readout`).
## Usage: Basic
```tsx
import { PluginParameterSlider } from "@suaveplan/react-audio/components/plugin-parameter-slider";
function MixSlider({ plugin }) {
const param = plugin.parameterIndex.get("mix")!;
return <PluginParameterSlider plugin={plugin} parameter={param} />;
}
```
## Usage: Advanced
```tsx
// Render a vertical pan slider with a themed wrapper.
function PanSlider({ plugin }) {
const param = plugin.parameterIndex.get("pan")!;
return (
<PluginParameterSlider
plugin={plugin}
parameter={param}
orientation="vertical"
label="PAN"
className="ring-1 ring-zinc-700 rounded-md p-2"
/>
);
}
```
## API Reference
### Props
- `plugin: AudioFxPlugin` — the plugin instance bound to the slider.
- `parameter: PluginParameter` — the declaration to render. MUST be
present in `plugin.parameterIndex`.
- `orientation?: "horizontal" | "vertical"` — visual layout hint;
defaults to `"horizontal"`.
- `label?: string` — optional visible label override; defaults to
`parameter.name`.
- `className?: string` — optional CSS class appended to the wrapper.
### Behaviour
- Pointer drags fire the native `onChange`, which delegates to
`plugin.setParameter`.
- Keyboard events bypass the native range step (which would default to
1 and produce mis-stepped values for parameters whose range is
smaller or larger than 100) and run through the shared
`resolveParameterKeyboardChange` resolver so step semantics match
the knob exactly.
- `Enter` is intentionally a no-op on the slider; consumers expecting
a type-edit affordance should use `<PluginParameterKnob>`.
## Implementation Notes
- The native `step` attribute is `(max - min) / 100`, falling back to
`0.0001` for degenerate `min === max` declarations. The keyboard
handler never reads the native step.
- The slider does not animate; pointer & keyboard interactions write
the parameter directly and the next provider sample reads it back.
- A `<label htmlFor>` link is used so click-to-focus on the label
works without any JavaScript wiring.