import * as angleSliderMachine from "@zag-js/angle-slider";
import type { MachineInput } from "marko-zag";
import { cn } from "#lib/utils.ts";
import { stripOwnProps } from "#lib/native-attrs.ts";
import { angleSlider as styles } from "./classes.ts";

export type Input = MachineInput<"div", angleSliderMachine.Props> & {
  valueChange?: (value: number) => void;
};

<zag/api=() => angleSliderMachine from=input/>

<const/nativeAttrs=() =>
  stripOwnProps(angleSliderMachine.splitProps(input)[1], "class", "valueChange")
>

// Zag points the label's `for` at the hidden <input type="text">, but a type=hidden
// input is not a labelable element (html-validate valid-for). No replacement
// is needed: the thumb already carries role=slider and Zag wires
// aria-labelledby to this label's id there. Marko does not dedupe spread
// attrs, hence the explicit strip.
<const/labelProps=() => {
  const { for: _for, ...rest } = api().getLabelProps() as Record<string, unknown>;
  return rest;
}/>

<div
  ...nativeAttrs()
  ...api().getRootProps()
  data-slot="angle-slider"
  class=cn(styles.root, input.class)
>
  <label ...labelProps() data-slot="angle-slider-label" class=styles.label>
    Angle
  </label>
  <div
    ...api().getControlProps()
    data-slot="angle-slider-control"
    class=styles.control
  >
    <input type="text" ...api().getHiddenInputProps()>
    <div
      ...api().getThumbProps()
      data-slot="angle-slider-thumb"
      class=styles.thumb
    >
      <span data-slot="angle-slider-thumb-knob" class=styles.thumbKnob></span>
    </div>
  </div>
  <span
    ...api().getValueTextProps()
    data-slot="angle-slider-value-text"
    class=styles.valueText
  >
    ${api().value}&deg;
  </span>
</div>

<return=api>
