{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "adjustments-vertical",
  "type": "registry:component",
  "title": "adjustments-vertical",
  "description": "Animated adjustments-vertical icon for Angular",
  "author": "Aniket Pawar <pawaraniket508@gmail.com>",
  "registryDependencies": [],
  "dependencies": [],
  "files": [
    {
      "path": "packages/angular/src/icons/adjustments-vertical.ts",
      "type": "registry:component",
      "target": "~/src/app/components/heroicons-animated/adjustments-vertical.ts",
      "content": "import {\n  ChangeDetectionStrategy,\n  Component,\n  computed,\n  DestroyRef,\n  effect,\n  inject,\n  input,\n  signal,\n} from \"@angular/core\";\n\ntype VerticalStateKey =\n  | \"col1TopY2\"\n  | \"col1BottomY1\"\n  | \"col1KnobCY\"\n  | \"col2TopY2\"\n  | \"col2BottomY1\"\n  | \"col2KnobCY\"\n  | \"col3TopY2\"\n  | \"col3BottomY1\"\n  | \"col3KnobCY\";\n\ntype VerticalState = Record<VerticalStateKey, number>;\n\n@Component({\n  selector: \"hi-adjustments-vertical\",\n  standalone: true,\n  changeDetection: ChangeDetectionStrategy.OnPush,\n  host: {\n    \"[attr.aria-label]\": \"'adjustments-vertical'\",\n    role: \"img\",\n    \"(mouseenter)\": \"onMouseEnter()\",\n    \"(mouseleave)\": \"onMouseLeave()\",\n  },\n  template: `<svg\n    xmlns=\"http://www.w3.org/2000/svg\"\n    [attr.width]=\"size()\"\n    [attr.height]=\"size()\"\n    viewBox=\"0 0 24 24\"\n    fill=\"none\"\n    [attr.stroke]=\"color()\"\n    [attr.stroke-width]=\"strokeWidth()\"\n    stroke-linecap=\"round\"\n    stroke-linejoin=\"round\"\n    class=\"icon-svg\"\n  >\n    <line x1=\"6\" x2=\"6\" y1=\"3.75\" [attr.y2]=\"col1TopY2()\" />\n    <line x1=\"6\" x2=\"6\" [attr.y1]=\"col1BottomY1()\" y2=\"20.25\" />\n    <circle cx=\"6\" [attr.cy]=\"col1KnobCY()\" fill=\"none\" r=\"1.5\" />\n\n    <line x1=\"12\" x2=\"12\" y1=\"3.75\" [attr.y2]=\"col2TopY2()\" />\n    <line x1=\"12\" x2=\"12\" [attr.y1]=\"col2BottomY1()\" y2=\"20.25\" />\n    <circle cx=\"12\" [attr.cy]=\"col2KnobCY()\" fill=\"none\" r=\"1.5\" />\n\n    <line x1=\"18\" x2=\"18\" y1=\"3.75\" [attr.y2]=\"col3TopY2()\" />\n    <line x1=\"18\" x2=\"18\" [attr.y1]=\"col3BottomY1()\" y2=\"20.25\" />\n    <circle cx=\"18\" [attr.cy]=\"col3KnobCY()\" fill=\"none\" r=\"1.5\" />\n  </svg>`,\n  styles: [\n    `\n      :host {\n        display: inline-block;\n      }\n      .icon-svg {\n        transform-box: fill-box;\n        transform-origin: center;\n      }\n    `,\n  ],\n})\nexport class AdjustmentsVerticalIcon {\n  readonly color = input(\"currentColor\");\n  readonly size = input(28);\n  readonly strokeWidth = input(1.5);\n  readonly animate = input(false);\n\n  protected isHovered = signal(false);\n  protected shouldAnimate = computed(() => this.animate() || this.isHovered());\n\n  protected col1TopY2 = signal(13.5);\n  protected col1BottomY1 = signal(16.5);\n  protected col1KnobCY = signal(15);\n  protected col2TopY2 = signal(7.5);\n  protected col2BottomY1 = signal(10.5);\n  protected col2KnobCY = signal(9);\n  protected col3TopY2 = signal(13.5);\n  protected col3BottomY1 = signal(16.5);\n  protected col3KnobCY = signal(15);\n\n  private readonly DURATION_MS = 450;\n  private readonly NORMAL_STATE: VerticalState = {\n    col1TopY2: 13.5,\n    col1BottomY1: 16.5,\n    col1KnobCY: 15,\n    col2TopY2: 7.5,\n    col2BottomY1: 10.5,\n    col2KnobCY: 9,\n    col3TopY2: 13.5,\n    col3BottomY1: 16.5,\n    col3KnobCY: 15,\n  };\n  private readonly ANIMATE_STATE: VerticalState = {\n    col1TopY2: 10.5,\n    col1BottomY1: 13.5,\n    col1KnobCY: 12,\n    col2TopY2: 10.5,\n    col2BottomY1: 13.5,\n    col2KnobCY: 12,\n    col3TopY2: 10.5,\n    col3BottomY1: 13.5,\n    col3KnobCY: 12,\n  };\n\n  private rafId = 0;\n  private animationToken = 0;\n  private readonly destroyRef = inject(DestroyRef);\n\n  private readonly signalMap: Record<\n    VerticalStateKey,\n    ReturnType<typeof signal<number>>\n  > = {} as Record<VerticalStateKey, ReturnType<typeof signal<number>>>;\n\n  constructor() {\n    this.signalMap.col1TopY2 = this.col1TopY2;\n    this.signalMap.col1BottomY1 = this.col1BottomY1;\n    this.signalMap.col1KnobCY = this.col1KnobCY;\n    this.signalMap.col2TopY2 = this.col2TopY2;\n    this.signalMap.col2BottomY1 = this.col2BottomY1;\n    this.signalMap.col2KnobCY = this.col2KnobCY;\n    this.signalMap.col3TopY2 = this.col3TopY2;\n    this.signalMap.col3BottomY1 = this.col3BottomY1;\n    this.signalMap.col3KnobCY = this.col3KnobCY;\n\n    effect(() => {\n      this.runStateAnimation(this.shouldAnimate());\n    });\n    this.destroyRef.onDestroy(() => {\n      this.animationToken++;\n      if (this.rafId) {\n        cancelAnimationFrame(this.rafId);\n        this.rafId = 0;\n      }\n    });\n  }\n\n  private easeOutBack(progress: number): number {\n    const c1 = 1.701_58;\n    const c3 = c1 + 1;\n    const p = progress - 1;\n    return 1 + c3 * p * p * p + c1 * p * p;\n  }\n\n  private lerp(from: number, to: number, progress: number): number {\n    return from + (to - from) * progress;\n  }\n\n  private runStateAnimation(active: boolean) {\n    const target = active ? this.ANIMATE_STATE : this.NORMAL_STATE;\n    const stateKeys = Object.keys(this.NORMAL_STATE) as VerticalStateKey[];\n    const startValues = {} as VerticalState;\n    for (const key of stateKeys) {\n      startValues[key] = this.signalMap[key]();\n    }\n\n    const currentToken = ++this.animationToken;\n    if (this.rafId) {\n      cancelAnimationFrame(this.rafId);\n      this.rafId = 0;\n    }\n\n    const start = performance.now();\n    const tick = (now: number) => {\n      if (currentToken !== this.animationToken) {\n        return;\n      }\n      const rawProgress = Math.min((now - start) / this.DURATION_MS, 1);\n      const easedProgress = this.easeOutBack(rawProgress);\n\n      for (const key of stateKeys) {\n        this.signalMap[key].set(\n          this.lerp(startValues[key], target[key], easedProgress)\n        );\n      }\n\n      if (rawProgress < 1) {\n        this.rafId = requestAnimationFrame(tick);\n      } else {\n        this.rafId = 0;\n      }\n    };\n\n    this.rafId = requestAnimationFrame(tick);\n  }\n\n  onMouseEnter() {\n    this.isHovered.set(true);\n  }\n  onMouseLeave() {\n    this.isHovered.set(false);\n  }\n}\n"
    }
  ]
}
