import type { DomainProperty } from '@api-client/core/modeling/DomainProperty.js'
import { type CountryConfig, DEFAULT_COUNTRY_CONFIG } from '@api-client/core/modeling/definitions/Country.js'
import { bound } from '../../decorators/bound.js'
import { html, TemplateResult } from 'lit'
import { SemanticType } from '@api-client/core/modeling/Semantics.js'
import { renderHelp } from '../../help/render.js'
import { TaxonomyDialog } from './TaxonomyDialog.js'

import '../../md/chip/ui-chip-set.js'
import '../../md/chip/ui-chip.js'

/**
 * A class that generates a dialog that allows the user to configure the taxonomy of a Country annotated association.
 */
export class CountryTaxonomy extends TaxonomyDialog<CountryConfig> {
  static override title = `Configure Country Taxonomy`

  constructor(public domainElement: DomainProperty) {
    let config: CountryConfig
    const semantic = domainElement.semantics.find((s) => s.id === SemanticType.Country)
    if (semantic && semantic.config) {
      config = structuredClone(semantic.config)
    } else {
      config = {}
    }
    super(config)
  }

  protected override formCallback(event: Event): Promise<void> {
    const semantic = this.domainElement.semantics.find((s) => s.id === SemanticType.Country)
    if (semantic) {
      semantic.config = this.config
    } else {
      this.domainElement.semantics.push({
        id: SemanticType.Country,
        config: this.config,
      })
    }
    this.domainElement.domain.notifyChange()
    return super.formCallback(event)
  }

  protected handleAllowedCountriesChange(event: Event): void {
    const input = event.target as HTMLInputElement
    const value = input.value.trim()
    if (value) {
      const countries = this.config?.allowedCountries ?? DEFAULT_COUNTRY_CONFIG.allowedCountries ?? []
      if (!countries.includes(value)) {
        countries.push(value)
        this.config = { ...this.config, allowedCountries: countries }
        this.requestUpdate()
      }
      input.value = ''
    }
  }

  protected handleRemoveAllowedCountry(event: Event): void {
    const chip = event.currentTarget as HTMLElement
    const index = parseInt(chip.dataset.index || '-1', 10)
    if (index >= 0 && this.config?.allowedCountries) {
      this.config.allowedCountries.splice(index, 1)
      this.requestUpdate()
    }
  }

  protected handleDisallowedCountriesChange(event: Event): void {
    const input = event.target as HTMLInputElement
    const value = input.value.trim()
    if (value) {
      const countries = this.config?.disallowedCountries ?? DEFAULT_COUNTRY_CONFIG.disallowedCountries ?? []
      if (!countries.includes(value)) {
        countries.push(value)
        this.config = { ...this.config, disallowedCountries: countries }
        this.requestUpdate()
      }
      input.value = ''
    }
  }

  protected handleRemoveDisallowedCountry(event: Event): void {
    const chip = event.currentTarget as HTMLElement
    const index = parseInt(chip.dataset.index || '-1', 10)
    if (index >= 0 && this.config?.disallowedCountries) {
      this.config.disallowedCountries.splice(index, 1)
      this.requestUpdate()
    }
  }

  @bound
  render(): TemplateResult {
    return html`
      <div class="input-group">
        ${this.renderFormatSelect()} ${this.renderAllowedCountries()} ${this.renderDisallowedCountries()}
      </div>
    `
  }

  protected renderFormatSelect(): TemplateResult {
    const value = this.config?.format ?? DEFAULT_COUNTRY_CONFIG.format
    return html`
      <div class="row">
        <ui-select
          label="Country format"
          class="input"
          name="format"
          .value="${value as string}"
          @change="${this.handleSelectChange}"
        >
          <ui-option value="ISO_3166_Alpha_2">
            <div>ISO 3166 Alpha-2 (Recommended)</div>
            <div slot="supporting-text">Store as ISO 3166 Alpha-2 (e.g., US)</div>
          </ui-option>
          <ui-option value="ISO_3166_Alpha_3">
            <div>ISO 3166 Alpha-3</div>
            <div slot="supporting-text">Store as ISO 3166 Alpha-3 (e.g., USA)</div>
          </ui-option>
          <ui-option value="Name">
            <div>Name</div>
            <div slot="supporting-text">Store as country name (e.g., United States)</div>
          </ui-option>
        </ui-select>
        ${renderHelp('taxonomy', 'country:format')}
      </div>
    `
  }

  protected renderAllowedCountries(): TemplateResult {
    const value = this.config?.allowedCountries ?? DEFAULT_COUNTRY_CONFIG.allowedCountries
    const chips = (value || []).map(
      (country, index) =>
        html`<ui-chip type="input" removable data-index="${index}" @remove="${this.handleRemoveAllowedCountry}"
          >${country}</ui-chip
        >`
    )
    return html`
      <div class="row input-row">
        <div class="input chips-input">
          <ui-outlined-text-field
            class="input"
            name="allowedCountries"
            label="Allowed Countries"
            @change="${this.handleAllowedCountriesChange}"
            supportingText="Add a country and press Enter to add it to the list. Use the selected format."
          ></ui-outlined-text-field>
          <ui-chip-set>${chips}</ui-chip-set>
        </div>
        ${renderHelp('taxonomy', 'country:allowedCountries')}
      </div>
    `
  }

  protected renderDisallowedCountries(): TemplateResult {
    const value = this.config?.disallowedCountries ?? DEFAULT_COUNTRY_CONFIG.disallowedCountries
    const chips = (value || []).map(
      (country, index) =>
        html`<ui-chip type="input" removable data-index="${index}" @remove="${this.handleRemoveDisallowedCountry}"
          >${country}</ui-chip
        >`
    )
    return html`
      <div class="row input-row">
        <div class="input chips-input">
          <ui-outlined-text-field
            class="input"
            name="disallowedCountries"
            label="Disallowed Countries"
            @change="${this.handleDisallowedCountriesChange}"
            supportingText="Add a country and press Enter to add it to the list. Use the selected format."
          ></ui-outlined-text-field>
          <ui-chip-set>${chips}</ui-chip-set>
        </div>
        ${renderHelp('taxonomy', 'country:disallowedCountries')}
      </div>
    `
  }
}
