import { ITEM_TYPES } from "../constants.js"
import { Grammar } from "../grammar.js"
import { CARACS } from "../rdd-carac.js"
import { RdDTimestamp } from "../time/rdd-timestamp.js"
import { TMRUtility } from "../tmr-utility.js"
import { ROLL_TYPE_MEDITATION } from "./roll-constants.mjs"
import { PART_CARAC } from "./roll-part-carac.mjs"
import { PART_COMP } from "./roll-part-comp.mjs"
import { RollPartSelect } from "./roll-part-select.mjs"
import { ROLLDIALOG_SECTION, RollPart } from "./roll-part.mjs"

export const PART_MEDITATION = "meditation"

const COMPORTEMENTS = ['isComportement', 'isHeure', 'isPurification', 'isVeture']

export class RollPartMeditation extends RollPartSelect {

  get code() { return PART_MEDITATION }
  get section() { return ROLLDIALOG_SECTION.CHOIX }

  get rollTypes() { return [ROLL_TYPE_MEDITATION] }
  isValid(rollData) { return rollData.active.actor.isPersonnage() && rollData.active.actor.isHautRevant() }
  visible(rollData) { return RollPart.isRollType(rollData, ROLL_TYPE_MEDITATION) }

  store(rollData, targetData) {
    const current = this.getCurrent(rollData)
    this.setSaved(targetData, {
      key: current.key,
      isComportement: current.isComportement,
      isHeure: current.isHeure,
      isPurification: current.isPurification,
      isVeture: current.isVeture
    })
  }

  loadRefs(rollData) {
    const refs = this.getRefs(rollData)
    const actor = rollData.active.actor
    refs.meditations = actor.itemTypes[ITEM_TYPES.meditation]
      .map(it => RollPartMeditation.$extractMeditation(it, actor))

    if (refs.meditations.length > 0) {
      this.$selectMeditation(rollData)
      this.$selectConditionMeditation(rollData)
      const selected = this.getSelected(rollData)
      const current = this.getCurrent(rollData)
      COMPORTEMENTS.filter(it => selected[it]).forEach(it => current[it] = selected[it])
    }
  }

  choices(refs) { return refs.meditations }

  static $extractMeditation(meditation, actor) {
    return {
      key: meditation.id,
      label: meditation.name,
      meditation: meditation,
      comp: actor.getCompetence(meditation.system.competence)
    }
  }

  prepareContext(rollData) {
    this.getCurrent(rollData).value = this.getMalusConditions(rollData)
  }

  getMalusConditions(rollData) {
    const current = this.getCurrent(rollData)
    const conditionsManquantes = COMPORTEMENTS.filter(it => !current[it]).length
    return -2 * conditionsManquantes
  }

  getMalusEchecs(rollData) {
    return this.getCurrent(rollData).meditation?.system.malus ?? 0
  }

  getAjustements(rollData) {
    const malus = this.getMalusEchecs(rollData)
    const malusEchecs = malus == 0 ? [] : [{ label: "Méditation", value: malus }]
    const malusConditions = { label: "Conditions", value: this.getMalusConditions(rollData) }
    return [malusConditions, ...malusEchecs]
  }

  $selectMeditation(rollData, key) {
    const previous = this.getCurrent(rollData)
    const current = this.selectByKey(rollData, key, 0)
    if (current.key != previous.key) {
      this.$selectConditionMeditation(rollData)
    }
  }

  $selectConditionMeditation(rollData) {
    const current = this.getCurrent(rollData)
    if (current.meditation){
      current.heureMonde = RdDTimestamp.getWorldTime().heure
      current.heureMeditation = RdDTimestamp.findHeure(current.meditation.system.heure)?.heure
      current.isHeure = current.heureMeditation == current.heureMonde
      current.isTMR = Grammar.equalsInsensitive(current.meditation.system.tmr, TMRUtility.getTMRType(rollData.active.actor.system.reve.tmrpos.coord))
    }
  }

  async _onRender(rollDialog, context, options) {

    const selectMeditation = rollDialog.element.querySelector(`roll-section[name="${this.code}"] select[name="select-meditation"]`)
    selectMeditation?.addEventListener("change", e => {
      const selectOptions = e.currentTarget.options
      const index = selectOptions.selectedIndex
      this.$selectMeditation(rollDialog.rollData, selectOptions[index]?.value)
      rollDialog.render()
    })

    COMPORTEMENTS.forEach(it => this.setupListenerCondition(rollDialog, it))
  }

  setupListenerCondition(rollDialog, inputName) {
    const checkbox = rollDialog.element.querySelector(`roll-section[name="${this.code}"] input[name="${inputName}"]`)
    checkbox?.addEventListener("change", e => {
      const current = this.getCurrent(rollDialog.rollData)
      current[inputName] = e.currentTarget.checked
      rollDialog.render()
    })
  }

  impactOtherPart(part, rollData) {
    if (this.visible(rollData)) {
      const current = this.getCurrent(rollData)
      switch (part.code) {
        case PART_CARAC: return part.filterCaracs(rollData, [CARACS.INTELLECT])
        case PART_COMP: return part.filterComps(rollData, [current.comp?.name])
      }
    }
    return undefined
  }
}
