{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "steps",
  "title": "Steps",
  "description": "Where the user is in an ordered flow: horizontal, vertical or compact, with errors.",
  "registryDependencies": [
    "@ikas/collapse",
    "@ikas/step-kit",
    "@ikas/swap-text",
    "@ikas/utils"
  ],
  "files": [
    {
      "path": "registry/ikas/steps.tsx",
      "content": "\"use client\"\n\nimport * as React from \"react\"\n\nimport { cn } from \"@/lib/utils\"\nimport { Collapse } from \"@/components/ikas/collapse\"\nimport { SwapText } from \"@/components/ikas/swap-text\"\nimport { StepConnector, StepMarker, markerWidth, useStepMarkerShape, useStepTravel, type StepMarkerShape, type StepStatus } from \"@/components/ikas/step-kit\"\n\ntype StepsItem = {\n  id: string\n  label: string\n  /** Shown under the current step (vertical), or in the caption on narrow screens. One sentence. */\n  description?: React.ReactNode\n  /** Set while the step failed. Turns the marker red and replaces the description. */\n  error?: React.ReactNode\n}\n\ntype StepsProps = Omit<React.ComponentProps<\"div\">, \"children\"> & {\n  steps: StepsItem[]\n  /** Index of the current step. `steps.length` means every step is done. */\n  current: number\n  /** horizontal for wizards (3–6 steps), vertical for long flows with descriptions, compact for a wizard's header. */\n  orientation?: \"horizontal\" | \"vertical\" | \"compact\"\n  /** diamond (default), circle, square or pill. Defaults to the StepMarkerProvider's. */\n  marker?: StepMarkerShape\n  /** Shown under the current step in the vertical layout, e.g. its primary button. */\n  actions?: React.ReactNode\n  /** Accessible name of the list. */\n  label?: string\n  /** Announced and shown when every step is done. */\n  completeLabel?: string\n}\n\nconst pad = (n: number) => String(n).padStart(2, \"0\")\n\n/**\n * Where the user is in an ordered flow. Jumping over several steps fills the connectors one after\n * another; the current step's halo lands last. Announces each change politely.\n */\nfunction Steps({\n  steps,\n  current,\n  orientation = \"horizontal\",\n  marker,\n  actions,\n  label = \"Adımlar\",\n  completeLabel = \"Tüm adımlar tamamlandı\",\n  className,\n  style,\n  ...props\n}: StepsProps) {\n  const shape = useStepMarkerShape(marker)\n  const travel = useStepTravel(current)\n  const n = steps.length\n  if (n === 0) return null\n  const done = current >= n\n  const at = Math.min(current, n - 1)\n  const statusOf = (i: number): StepStatus => (i < current ? \"done\" : i === current ? (steps[i].error ? \"error\" : \"current\") : \"upcoming\")\n  const markerDelay = (i: number) => (statusOf(i) === \"done\" ? travel.delay(i) : travel.landing)\n  const announce = done ? completeLabel : `${n} adımdan ${current + 1}. adım: ${steps[at].label}${steps[at].error ? \", hata\" : \"\"}`\n  const vars = { \"--marker-w\": `${markerWidth(shape, orientation === \"compact\" ? \"sm\" : \"default\")}px`, ...style } as React.CSSProperties\n  const srStatus = (i: number) => ({ done: \", tamamlandı\", error: \", hata\", current: \", şu anki adım\", upcoming: \"\", blocked: \"\" })[statusOf(i)]\n\n  const live = (\n    <span role=\"status\" aria-live=\"polite\" className=\"sr-only\">\n      {announce}\n    </span>\n  )\n\n  if (orientation === \"compact\") {\n    return (\n      <div data-slot=\"steps\" data-orientation=\"compact\" className={cn(\"flex flex-col gap-2.5\", className)} style={vars} {...props}>\n        <div\n          role=\"progressbar\"\n          aria-label={label}\n          aria-valuemin={1}\n          aria-valuemax={n}\n          aria-valuenow={at + 1}\n          aria-valuetext={announce}\n          className=\"flex items-center\"\n        >\n          {steps.map((step, i) => (\n            <React.Fragment key={step.id}>\n              <StepMarker status={statusOf(i)} shape={shape} size=\"sm\" delay={markerDelay(i)} />\n              {i < n - 1 && <StepConnector filled={i < current} delay={travel.delay(i)} className=\"mx-1.5 flex-1\" />}\n            </React.Fragment>\n          ))}\n        </div>\n        <div className=\"flex items-baseline justify-between gap-3 text-[12.5px] text-muted-foreground\">\n          <span className=\"tabular-nums\">\n            Adım <span className=\"font-medium text-foreground\">{done ? n : at + 1}</span> / {n}\n          </span>\n          <SwapText direction={travel.forward ? 1 : -1} className=\"truncate font-medium text-foreground\">\n            {done ? completeLabel : steps[at].label}\n          </SwapText>\n        </div>\n        {live}\n      </div>\n    )\n  }\n\n  if (orientation === \"vertical\") {\n    return (\n      <div data-slot=\"steps\" data-orientation=\"vertical\" className={cn(\"flex flex-col\", className)} style={vars} {...props}>\n        <ol aria-label={label} className=\"flex flex-col\">\n          {steps.map((step, i) => {\n            const status = statusOf(i)\n            const isCurrent = i === current\n            return (\n              <li\n                key={step.id}\n                data-status={status}\n                aria-current={isCurrent ? \"step\" : undefined}\n                className=\"relative grid grid-cols-[var(--marker-w)_minmax(0,1fr)] gap-x-3.5 pb-[18px] last:pb-0\"\n              >\n                {i < n - 1 && (\n                  <StepConnector\n                    orientation=\"vertical\"\n                    filled={i < current}\n                    delay={travel.delay(i)}\n                    className=\"absolute top-[30px] bottom-1 left-[calc(var(--marker-w)/2-0.75px)]\"\n                  />\n                )}\n                <StepMarker status={status} index={i + 1} shape={shape} delay={markerDelay(i)} />\n                <div className=\"flex min-w-0 flex-col pt-[3px]\">\n                  <span\n                    className={cn(\n                      \"text-sm transition-colors duration-200 ease-out\",\n                      status === \"upcoming\" ? \"text-muted-foreground\" : \"font-medium text-foreground\"\n                    )}\n                  >\n                    {step.label}\n                    <span className=\"sr-only\">{srStatus(i)}</span>\n                  </span>\n                  <Collapse open={isCurrent && !!(step.error || step.description || actions)}>\n                    <div className=\"flex flex-col gap-2 pt-1\">\n                      {(step.error || step.description) && (\n                        <SwapText swapKey={step.error ? \"error\" : \"description\"} className={cn(\"text-[13px]\", step.error ? \"text-red-subtle-foreground\" : \"text-muted-foreground\")}>\n                          <span role={step.error ? \"alert\" : undefined}>{step.error ?? step.description}</span>\n                        </SwapText>\n                      )}\n                      {actions && <div className=\"flex flex-wrap gap-2 pt-1\">{actions}</div>}\n                    </div>\n                  </Collapse>\n                </div>\n              </li>\n            )\n          })}\n        </ol>\n        {live}\n      </div>\n    )\n  }\n\n  return (\n    <div data-slot=\"steps\" data-orientation=\"horizontal\" className={cn(\"@container flex flex-col gap-3\", className)} style={vars} {...props}>\n      <ol aria-label={label} className=\"grid\" style={{ gridTemplateColumns: `repeat(${n}, minmax(0, 1fr))` }}>\n        {steps.map((step, i) => {\n          const status = statusOf(i)\n          return (\n            <li\n              key={step.id}\n              data-status={status}\n              aria-current={i === current ? \"step\" : undefined}\n              className=\"relative flex min-w-0 flex-col items-start gap-2.5 pr-2.5 last:pr-0\"\n            >\n              {i < n - 1 && (\n                <StepConnector filled={i < current} delay={travel.delay(i)} className=\"absolute top-[12.25px] right-2.5 left-[calc(var(--marker-w)+12px)]\" />\n              )}\n              <StepMarker status={status} index={i + 1} shape={shape} delay={markerDelay(i)} />\n              <span className=\"flex min-w-0 max-w-full flex-col gap-px @max-md:sr-only\">\n                <span\n                  className={cn(\n                    \"truncate text-[13px] transition-colors duration-200 ease-out\",\n                    status === \"upcoming\" ? \"text-muted-foreground\" : status === \"error\" ? \"font-medium text-red-subtle-foreground\" : \"font-medium text-foreground\"\n                  )}\n                >\n                  {step.label}\n                </span>\n                <span className=\"font-mono text-[11px] text-muted-foreground tabular-nums\">{pad(i + 1)}</span>\n                <span className=\"sr-only\">{srStatus(i)}</span>\n              </span>\n            </li>\n          )\n        })}\n      </ol>\n      {/* Narrow containers drop the labels under the markers and name the current step here instead. */}\n      <div aria-hidden className=\"hidden text-[13px] @max-md:block\">\n        <SwapText direction={travel.forward ? 1 : -1} swapKey={done ? \"done\" : `${at}:${steps[at].error ? \"e\" : \"\"}`}>\n          {done ? (\n            <span className=\"font-medium\">{completeLabel}</span>\n          ) : (\n            <span>\n              <span className=\"font-medium\">\n                {pad(at + 1)} · {steps[at].label}\n              </span>{\" \"}\n              <span className=\"text-muted-foreground\">{steps[at].error ?? steps[at].description}</span>\n            </span>\n          )}\n        </SwapText>\n      </div>\n      {live}\n    </div>\n  )\n}\n\nexport { Steps, type StepsItem, type StepsProps }\n",
      "type": "registry:component",
      "target": "@components/ikas/steps.tsx"
    }
  ],
  "docs": "https://builders.ikas.com/tr/docs/app-development/ui-kit/components/steps",
  "categories": [
    "navigation",
    "motion"
  ],
  "type": "registry:component"
}