<template>
  <q-dialog
    :model-value="editor !== undefined"
    persistent
    transition-show="scale"
    transition-hide="scale"
  >
    <q-card>
      <div class="column">
        <div class="col" align="right" style="position: sticky; top: 0; z-index: 999">
          <q-btn round color="negative" icon="close" dense rounded @click="editDone(false)" />
        </div>
        <div class="col" style="margin: 0; padding: 0; margin-top: -2.4em">
          <edit-event v-model="editor" @done="editDone" />
        </div>
      </div>
    </q-card>
  </q-dialog>
  <div class="q-pa-md">
    <q-card style="height: 70vh; max-width: 1800px" class="q-pa-md">
      <div class="scroll" ref="scrollDiv" style="height: 100%">
        <q-infinite-scroll :offset="250" @load="load">
          <q-list>
            <q-item id="bbb">
              <q-btn label="Ältere Veranstaltungen laden" @click="load(-1)" />
            </q-item>
            <template v-for="(events, index) in agendas" :key="index">
              <q-separator />
              <q-item-label overline>{{ index }}</q-item-label>
              <q-item v-for="(event, idx) in events" :key="idx"
                ><event-slot :model-value="event" />{{ idx }}</q-item
              >
            </template>
          </q-list>
          <template #loading>
            <div class="row justify-center q-my-md">
              <q-spinner-dots color="primary" size="40px" />
            </div>
          </template>
        </q-infinite-scroll>
      </div>
    </q-card>
  </div>
</template>

<script lang="ts">
import { computed, defineComponent, onBeforeMount, ref } from 'vue';
import { useEventStore } from '../../store';
import { date } from 'quasar';
import EditEvent from '../management/EditEvent.vue';
import EventSlot from '../overview/slots/EventSlot.vue';

export default defineComponent({
  name: 'ListView',
  components: { EditEvent, EventSlot },

  setup() {
    interface Agendas {
      [index: string]: FG.Event[];
    }

    const store = useEventStore();

    const editor = ref<FG.Event | undefined>(undefined);
    const events = ref<FG.Event[]>([]);
    const scrollDiv = ref<Element>();

    const agendas = computed<Agendas>(() => {
      const ag = {} as Agendas;
      events.value?.forEach((event) => {
        const day = date.formatDate(event.start, 'YYYYMMDD');

        if (!ag[day]) {
          ag[day] = [];
        }
        ag[day].push(event);
      });
      return ag;
    });

    onBeforeMount(async () => {
      //await loadAgendas();
    });

    async function edit(id: number) {
      editor.value = await store.getEvent(id);
    }

    function editDone(changed: boolean) {
      //if (changed) void loadAgendas();
      editor.value = undefined;
    }

    async function load(index: number, done?: (stop: boolean) => void) {
      const start = new Date();
      if (index < 0) {
        const { result } = await store.getEvents({ to: start, limit: 5, descending: true });
        events.value.unshift(...result);
        if (done) done(false);
      } else {
        const len = events.value.length;
        const { result } = await store.getEvents({
          from: start,
          offset: (index - 1) * 10,
          limit: 10,
        });
        if (len == events.value.push(...result)) {
          if (done) return done(true);
        } else if (done) done(false);
      }
      if (index <= 1) {
        window.setTimeout(() => {
          (<Element>scrollDiv.value).scrollTop = document.getElementById('bbb')?.scrollHeight || 0;
        }, 150);
      }
    }

    async function remove(id: number) {
      if (await store.removeEvent(id)) {
        // Successfull removed
        for (const idx in agendas.value) {
          const i = agendas.value[idx].findIndex((event) => event.id === id);
          if (i !== -1) {
            agendas.value[idx].splice(i, 1);
            break;
          }
        }
      } else {
        // Not found, this means our eventa are outdated
      }
    }

    function asMonth(value: string) {
      if (value) {
        return date.formatDate(new Date(value), 'MMMM', {
          months: [
            'Januar',
            'Februar',
            'März',
            'April',
            'Mai',
            'Juni',
            'Juli',
            'August',
            'September',
            'Oktober',
            'November',
            'Dezember',
          ],
        });
      }
    }

    function asYear(value: string) {
      if (value) {
        return date.formatDate(new Date(value), 'YYYY');
      }
    }

    return {
      agendas,
      asYear,
      asMonth,
      edit,
      editor,
      scrollDiv,
      editDone,
      load,
      remove,
    };
  },
});
</script>

<style>
@import '@quasar/quasar-ui-qcalendar/dist/index.css';

/* Fill full height of card */
.q-calendar-agenda__pane {
  height: 100%;
}

/* Same as Qcard */
.q-calendar {
  --calendar-background-dark: --q-dark;
}
</style>
