import {
  customElement,
  type TemplateResult,
  state,
  html,
  property,
  css,
  cssManager,
} from '@design.estate/dees-element';
import * as domtools from '@design.estate/dees-domtools';
import { DeesInputBase } from '../dees-input-base/dees-input-base.js';
import * as ibantools from 'ibantools';
import { demoFunc } from './dees-input-iban.demo.js';
import { themeDefaultStyles } from '../../00theme.js';

@customElement('dees-input-iban')
export class DeesInputIban extends DeesInputBase<DeesInputIban> {
  // STATIC
  public static demo = demoFunc;
  public static demoGroup = 'Input';

  // INSTANCE
  @state()
  accessor enteredString: string = '';

  @state()
  accessor enteredIbanIsValid: boolean = false;

  @property({
    type: String,
  })
  accessor value = '';

  public static styles = [
    themeDefaultStyles,
    ...DeesInputBase.baseStyles,
    cssManager.defaultStyles,
    css`
      /* TODO: Migrate hardcoded values to --dees-* CSS variables */
      /* IBAN input specific styles can go here */
    `,
  ];

  public render(): TemplateResult {
    return html`
      <div class="input-wrapper">
        <dees-label .label=${this.label || 'IBAN'} .description=${this.description}></dees-label>
        <dees-input-text
          .value=${this.value}
          .disabled=${this.disabled}
          .required=${this.required}
          .placeholder=${'DE89 3704 0044 0532 0130 00'}
          @input=${(eventArg: InputEvent) => {
            this.validateIban(eventArg);
          }}
        ></dees-input-text>
      </div>
    `;
  }

  public firstUpdated(_changedProperties: Map<string | number | symbol, unknown>) {
    super.firstUpdated(_changedProperties);
    const deesInputText = this.shadowRoot.querySelector('dees-input-text') as any;
    if (deesInputText && deesInputText.changeSubject) {
      deesInputText.changeSubject.subscribe(() => {
        this.changeSubject.next(this);
      });
    }
  }

  public async validateIban(eventArg: InputEvent): Promise<void> {
    const inputElement: HTMLInputElement = eventArg.target as HTMLInputElement;
    let enteredString = inputElement?.value;
    enteredString = enteredString || '';
    if (this.enteredString !== enteredString) {
      this.enteredString = ibantools.friendlyFormatIBAN(enteredString) || '';
      if (inputElement) {
        inputElement.value = this.enteredString;
        this.value = this.enteredString;
        this.changeSubject.next(this);
      }
    }
    this.enteredIbanIsValid = ibantools.isValidIBAN(this.enteredString.replace(/ /g, ''));
    const deesInputText = this.shadowRoot.querySelector('dees-input-text');
    deesInputText.validationText = `IBAN is valid: ${this.enteredIbanIsValid}`;
  }

  public getValue(): string {
    return this.value;
  }

  public setValue(value: string): void {
    this.value = value;
    this.enteredString = ibantools.friendlyFormatIBAN(value) || '';
  }
}
