import {
  ChangeDetectionStrategy,
  Component,
  ViewEncapsulation,
  computed,
  effect,
  inject,
  input,
  untracked,
} from '@angular/core';
import { toSignal } from '@angular/core/rxjs-interop';
import { FormControl, ReactiveFormsModule } from '@angular/forms';
import { DateRangeValue, RangeDatepickerComponent } from '@isa/ui/datepicker';
import { DateRangeFilterInput, FilterService } from '../../core';
import { InputType } from '../../types';

@Component({
  selector: 'filter-datepicker-range-input',
  templateUrl: './datepicker-range-input.component.html',
  styleUrls: ['./datepicker-range-input.component.scss'],
  changeDetection: ChangeDetectionStrategy.OnPush,
  encapsulation: ViewEncapsulation.None,
  standalone: true,
  imports: [RangeDatepickerComponent, ReactiveFormsModule],
  host: { '[class]': "['filter-datepicker-range-input']" },
})
export class DatepickerRangeInputComponent {
  readonly filterService = inject(FilterService);
  inputKey = input.required<string>();

  datepicker = new FormControl<DateRangeValue | undefined>(undefined);
  valueChanges = toSignal(this.datepicker.valueChanges);

  input = computed<DateRangeFilterInput>(() => {
    const inputs = this.filterService.inputs();
    const input = inputs.find(
      (input) =>
        input.key === this.inputKey() && input.type === InputType.DateRange,
    ) as DateRangeFilterInput;

    if (!input) {
      throw new Error(`Input not found for key: ${this.inputKey()}`);
    }

    return input;
  });

  datepickerMin = computed<Date | undefined>(() => {
    const inp = this.input();
    return inp.minStart ? new Date(inp.minStart) : undefined;
  });

  datepickerMax = computed<Date | undefined>(() => {
    const inp = this.input();
    return inp.maxStop ? new Date(inp.maxStop) : undefined;
  });

  constructor() {
    effect(() => {
      const input = this.input();
      const startDate = input.start ? new Date(input.start) : undefined;
      const stopDate = input.stop ? new Date(input.stop) : undefined;

      this.datepicker.patchValue([startDate, stopDate]);
      this.datepicker.updateValueAndValidity();
    });

    effect(() => {
      this.valueChanges();
      untracked(() => {
        const startDate = this.datepicker?.value?.[0];
        const stopDate = this.datepicker?.value?.[1];

        const start = startDate?.toISOString();
        const stop = stopDate?.toISOString();

        const controlEqualsInput =
          this.input().start === start && this.input().stop === stop;

        if (!controlEqualsInput) {
          this.filterService.setInputDateRangeValue(
            this.inputKey(),
            start,
            stop,
          );
        }
      });
    });
  }
}
