<template>
  <aside
    :id="componentId"
    :class="twMerge(
      'relative flex h-full flex-col bg-m-bg',
      collapsed ? 'w-[72px]' : 'w-[232px]',
      sidebarClass,
    )"
    v-bind="$attrs"
  >
    <div :class="['px-[20px] py-[14px]', collapsed ? '' : 'mx-[10px] border-b-2 border-m-primary']">
      <slot
        v-if="collapsed"
        name="logo-collapsed"
      />
      <slot
        v-else
        name="logo"
      />
    </div>

    <nav class="flex-1 overflow-y-auto mb-4">
      <div
        v-for="(section, sectionIndex) in sections"
        :key="sectionIndex"
        :class="collapsed ? 'first:border-t-2 first:border-m-primary' : 'mx-[10px] border-t-2 border-m-primary first:border-t-0'"
      >
        <div
          v-if="section.label"
          :class="[
            'flex items-center gap-2 pt-2 pb-3',
            collapsed ? 'justify-center pt-[40px]' : '',
          ]"
        >
          <IconifyIcon
            v-if="section.icon"
            :icon="section.icon"
            :width="24"
            class="shrink-0 text-m-primary"
          />
          <span
            v-if="!collapsed"
            class="text-[15px] font-bold uppercase text-m-primary"
          >
            {{ section.label }}
          </span>
        </div>
        <ul>
          <li
            v-for="item in section.items"
            :key="item.to"
            :class="collapsed ? '' : 'text-black hover:bg-m-primary/10 hover:font-semibold hover:text-m-primary pt-1 pb-1'"
          >
            <NuxtLink
              :to="item.to"
              active-class="!text-m-primary font-semibold"
              :class="twMerge(
                'block truncate text-[15px] leading-[150%]',
                collapsed ? 'px-3 text-center' : 'pl-[32px]',
              )"
            >
              <span v-if="!collapsed">{{ item.label }}</span>
            </NuxtLink>
          </li>
        </ul>
      </div>
    </nav>

    <button
      type="button"
      :aria-label="collapsed ? 'Déplier le menu' : 'Plier le menu'"
      :class="twMerge(
        'absolute top-1/2 -translate-y-1/2 right-0 translate-x-1/2 z-10',
        'flex h-8 w-8 items-center justify-center rounded-full border border-m-border bg-white shadow-sm',
        'cursor-pointer transition-colors hover:bg-m-surface',
        toggleClass,
      )"
      @click="toggleCollapse"
    >
      <IconifyIcon
        :icon="collapsed ? 'mdi:chevron-right' : 'mdi:chevron-left'"
        :width="18"
      />
    </button>
  </aside>
</template>

<script setup lang="ts">
import {computed, ref, useId} from 'vue'
import {Icon as IconifyIcon} from '@iconify/vue'
import {twMerge} from 'tailwind-merge'

defineOptions({name: 'MalioSidebar', inheritAttrs: false})

export type SidebarItem = {
  label: string
  to: string
}

export type SidebarSection = {
  label?: string
  icon?: string
  items: SidebarItem[]
}

const props = withDefaults(defineProps<{
  sections: SidebarSection[]
  modelValue?: boolean
  id?: string
  sidebarClass?: string
  toggleClass?: string
}>(), {
  modelValue: undefined,
  id: '',
  sidebarClass: '',
  toggleClass: '',
})

const emit = defineEmits<{
  (e: 'update:modelValue', value: boolean): void
}>()

const generatedId = useId()
const componentId = computed(() => props.id || `malio-sidebar-${generatedId}`)

const isControlled = computed(() => props.modelValue !== undefined)
const localValue = ref(false)

const collapsed = computed(() =>
  isControlled.value ? props.modelValue! : localValue.value,
)

function toggleCollapse() {
  const newValue = !collapsed.value
  if (!isControlled.value) {
    localValue.value = newValue
  }
  emit('update:modelValue', newValue)
}
</script>
