<script setup>
/**
 * SuggestSlotsDialog — « Trouver un créneau » : UI ÉPURÉE à divulgation progressive.
 *  1. Chips de compétence (1 clic) → fixe la durée PAR DÉFAUT (souvent liée au skill), ajustable.
 *  2. Adresse (autosuggest RQA — liste sous le champ, pas de menu).
 *  3. Les options (durée / date) + « Chercher » n'APPARAISSENT qu'une fois l'adresse choisie.
 * Le choix d'un créneau émet 'select' (créneau + adresse/coords/durée/skill) → l'appelant pré-remplit la création.
 * props.skills = [{ skill, dur, color }] fourni par le parent (réutilise ses compétences + couleurs).
 */
import { reactive, ref, watch } from 'vue'
import { Notify } from 'quasar'
import { suggestSlots } from 'src/api/dispatch'
import { useAddressSearch } from 'src/composables/useAddressSearch'
import OccupancyBands from 'src/components/shared/OccupancyBands.vue' // bandes d'occupation partagées (dénominateur filtré par compétence)

const props = defineProps({
  modelValue: { type: Boolean, default: false },
  skills: { type: Array, default: () => [] }, // [{ skill, dur, color }]
  // Pré-remplissage (appel client / réparation / soumission) : adresse + coords + compétence. L'agent n'a plus qu'à chercher.
  initialAddress: { type: String, default: '' },
  initialLat: { type: Number, default: null },
  initialLng: { type: Number, default: null },
  initialSkill: { type: String, default: '' },
})
const emit = defineEmits(['update:modelValue', 'select', 'plan-shifts'])

const { addrResults, addrLoading, searchAddr, selectAddr } = useAddressSearch()
const target = reactive({ address: '', latitude: null, longitude: null, ville: '' })
const skill = ref('')
const durationH = ref(1)
const urgent = ref(false) // urgence/réparation → ignore les blocs RÉSERVÉS (soft) : le tech redevient disponible pour ce créneau
const afterDate = ref(new Date().toLocaleDateString('en-CA', { timeZone: 'America/Toronto' }))
const loading = ref(false)
const slots = ref([])
const searched = ref(false)

// ── Occupation des ressources (bandes verticales) ────────────────────────────
// Panneau dépliable : la grille elle-même vit dans <OccupancyBands> (partagée). Ici on ne garde que
// l'état du panneau + le dernier `occ` (pour la légende/caption). Le composant se recharge seul.
const occOpen = ref(false)
const occ = ref(null)

// Reset à l'ouverture (formulaire propre à chaque fois) — puis pré-remplissage éventuel (adresse/coords/compétence du contexte appelant).
watch(() => props.modelValue, (o) => {
  if (!o) return
  target.address = props.initialAddress || ''; target.latitude = props.initialLat; target.longitude = props.initialLng
  skill.value = props.initialSkill || ''; durationH.value = 1; urgent.value = false
  slots.value = []; searched.value = false; addrResults.value = []; occ.value = null; occOpen.value = false
  // Adresse fournie SANS coords (ex. lieu de service texte) → lance l'autosuggest RQA pour que l'agent confirme d'un clic.
  if (props.initialAddress && props.initialLat == null) searchAddr(props.initialAddress)
})

function pickSkill (s) { skill.value = s.skill; durationH.value = s.dur || 1 } // 1 clic → skill + durée par défaut
// Clic sur une case-jour de l'occupation (émis par <OccupancyBands>) → cale la recherche sur ce jour (et lance si l'adresse est déjà choisie).
function onOccDay (cell) { if (!cell || cell.off) return; afterDate.value = cell.date; if (target.latitude != null) search() }
function occShort (iso) { const d = new Date(iso + 'T12:00:00'); return DOW[d.getDay()] + ' ' + iso.slice(8) }
function onAddrInput (v) { target.latitude = null; target.longitude = null; searchAddr(v) } // retape l'adresse → invalide les coords
function onPickAddr (a) { selectAddr(a, target); addrResults.value = [] }

async function search () {
  if (target.latitude == null) return
  loading.value = true; searched.value = true
  try {
    slots.value = await suggestSlots({ duration_h: durationH.value, latitude: target.latitude, longitude: target.longitude, after_date: afterDate.value, limit: 8, skill: skill.value, ignoreReserved: urgent.value })
  } catch (e) { Notify.create({ type: 'negative', message: 'Recherche impossible : ' + (e.message || e), timeout: 4000 }); slots.value = [] }
  finally { loading.value = false }
}

function pick (s) {
  emit('select', { ...s, _address: target.address, _latitude: target.latitude, _longitude: target.longitude, _duration: durationH.value, _skill: skill.value })
  emit('update:modelValue', false)
}

// « Aucun créneau » → renvoie le parent (Planif) vers la timeline des techs (filtrée compétence) au jour cherché, pour CRÉER un quart.
function planShifts () { emit('plan-shifts', { skill: skill.value, date: afterDate.value }); emit('update:modelValue', false) }

const DOW = ['dim', 'lun', 'mar', 'mer', 'jeu', 'ven', 'sam']
function dayLabel (iso) { const d = new Date(iso + 'T12:00:00'); return DOW[d.getDay()] + ' ' + iso.slice(8) + '/' + iso.slice(5, 7) }
</script>

<template>
  <q-dialog :model-value="modelValue" @update:model-value="v => emit('update:modelValue', v)">
    <q-card style="width:500px;max-width:95vw">
      <q-card-section class="row items-center q-pb-none">
        <q-icon name="event_available" color="primary" size="24px" class="q-mr-sm" />
        <div class="text-h6">Trouver un créneau</div>
        <q-space /><q-btn flat round dense icon="close" @click="emit('update:modelValue', false)" />
      </q-card-section>

      <q-card-section class="q-gutter-sm">
        <!-- 1. Type de job (1 clic) → fixe la durée par défaut -->
        <div v-if="skills.length" class="row items-center q-gutter-xs">
          <span v-for="s in skills" :key="s.skill" class="ss-chip" :class="{ on: skill === s.skill }"
                :style="skill === s.skill ? { background: s.color, borderColor: s.color, color: '#fff' } : { borderColor: s.color, color: s.color }"
                @click="pickSkill(s)">{{ s.skill }}</span>
        </div>

        <!-- 1b. Occupation des ressources (dépliable) — qui a de la place pour la compétence choisie, sur 7 jours -->
        <q-expansion-item v-model="occOpen" dense switch-toggle-side class="ss-occ-exp"
                          icon="bar_chart" :label="skill ? 'Occupation — « ' + skill + ' »' : 'Occupation des ressources'"
                          :caption="occ ? (occ.techs.length + ' ressource' + (occ.techs.length > 1 ? 's' : '') + ' · dès ' + occShort(afterDate)) : 'Voir la charge par tech'">
          <div class="q-pt-xs">
            <OccupancyBands :skill="skill" :after-date="afterDate" :days="7" :active="occOpen" @day="onOccDay" @loaded="v => occ = v" />
          </div>
        </q-expansion-item>

        <!-- 2. Adresse — autosuggest RQA (liste sous le champ) -->
        <q-input dense outlined v-model="target.address" label="Adresse du client" clearable autofocus
                 :loading="addrLoading" @update:model-value="onAddrInput">
          <template #prepend><q-icon name="place" /></template>
          <template #append><q-icon v-if="target.latitude != null" name="check_circle" color="positive" /></template>
        </q-input>
        <q-list v-if="addrResults.length" dense bordered class="ss-addr-list">
          <q-item v-for="(a, i) in addrResults" :key="i" clickable @click="onPickAddr(a)">
            <q-item-section avatar style="min-width:26px"><q-icon name="place" size="16px" color="grey-6" /></q-item-section>
            <q-item-section>{{ a.address_full }}</q-item-section>
          </q-item>
        </q-list>

        <!-- 3. Options révélées SEULEMENT quand l'adresse est choisie -->
        <template v-if="target.latitude != null">
          <div class="row items-center q-gutter-sm">
            <q-input dense outlined type="number" v-model.number="durationH" label="Durée (h)" :min="0.5" :max="8" :step="0.5" style="width:110px">
              <template #prepend><q-icon name="schedule" size="18px" /></template>
            </q-input>
            <q-input dense outlined type="date" v-model="afterDate" label="Dès le" class="col" />
          </div>
          <q-toggle v-model="urgent" dense size="sm" color="deep-orange-7" label="Urgence / réparation — utiliser aussi les techs réservés" class="q-mb-xs"><q-tooltip>Ignore les blocs « Réservé » (soft) : un tech réservé pour un projet redevient offert pour une réparation/urgence.</q-tooltip></q-toggle>
          <q-btn unelevated color="primary" icon="search" label="Chercher des créneaux" class="full-width" :loading="loading" @click="search" no-caps />
        </template>
        <div v-else class="text-caption text-grey-6 q-pt-xs">Choisis d'abord une adresse ci-dessus.</div>
      </q-card-section>

      <q-separator v-if="searched" />
      <q-card-section v-if="searched" style="max-height:44vh;overflow:auto" class="q-pt-sm">
        <div v-if="loading" class="text-center q-pa-md"><q-spinner size="26px" color="primary" /></div>
        <div v-else-if="!slots.length" class="text-center q-pa-md">
          <div class="text-grey-6 q-mb-sm">Aucun créneau{{ skill ? ' pour « ' + skill + ' »' : '' }} — vérifie qu'un tech qualifié a un <b>quart</b> sur ces jours (les créneaux suivent les quarts réels ; week-ends réservés aux réparations), ou élargis la date.</div>
          <q-btn unelevated no-caps size="sm" color="teal-8" icon="event" :label="skill ? 'Planifier des quarts pour « ' + skill + ' »' : 'Planifier des quarts'" @click="planShifts">
            <q-tooltip>Ouvre la Planification (timeline des techs {{ skill ? 'de « ' + skill + ' »' : '' }}, au {{ afterDate }}) pour créer un quart → des créneaux apparaîtront.</q-tooltip>
          </q-btn>
        </div>
        <q-list v-else separator>
          <q-item v-for="(s, i) in slots" :key="i" clickable @click="pick(s)" class="rounded-borders">
            <q-item-section avatar><q-avatar size="34px" color="blue-grey-1" text-color="blue-grey-8" class="text-weight-bold" style="font-size:12px">{{ dayLabel(s.date).slice(0, 3) }}</q-avatar></q-item-section>
            <q-item-section>
              <q-item-label class="text-weight-medium">{{ dayLabel(s.date) }} · {{ s.start_time }}–{{ s.end_time }}</q-item-label>
              <q-item-label caption>{{ s.tech_name }}<span v-if="s.travel_min"> · 🚗 {{ s.travel_min }} min<span v-if="s.distance_km"> ({{ s.distance_km }} km)</span></span></q-item-label>
            </q-item-section>
            <q-item-section side><q-icon name="chevron_right" color="primary" /></q-item-section>
          </q-item>
        </q-list>
      </q-card-section>
    </q-card>
  </q-dialog>
</template>

<style scoped>
.ss-chip { display: inline-flex; align-items: center; padding: 3px 11px; border: 1.5px solid #cbd5e1; border-radius: 14px; font-size: 12.5px; font-weight: 600; cursor: pointer; user-select: none; background: #fff; text-transform: capitalize; }
.ss-addr-list { border-radius: 6px; max-height: 168px; overflow-y: auto; }
.ss-occ-exp { border: 1px solid #e2e8f0; border-radius: 8px; }
</style>
