<template>
  <div class="relative w-full">
    <van-swipe ref="swipeRef" class="overflow-hidden" :style="swiperStyle" @change="handleSwiperChange">
      <van-swipe-item v-for="(item, index) in thumbnails" :key="index">
        <img class="w-full h-full" :src="item.photoUrl">
      </van-swipe-item>
    </van-swipe>

    <div v-if="showThumbnails && thumbnails.length"
      class="absolute left-[12px] right-[12px] flex items-end flex-row flex-nowrap" :style="thumbnailBoxStyle">
      <div ref="thumbnailScrollRef" class="flex-auto h-full whitespace-nowrap" scroll-x="true" :scroll-left="scrollLeft"
        :scroll-with-animation="true" show-scrollbar="false">
        <div class="flex items-center gap-[10px]" v-if="thumbnails.length > 1">
          <div v-for="(thumb, index) in thumbnails" :key="index"
            :class="['shrink-0 text-center rounded-card border-solid overflow-hidden', index === active ? 'border-2 border-white ' : 'border border-[#171717]']"
            :id="`thumbnail-${index}`" @click="handleThumbnailClick(index)">
            <img class="w-[36px] h-[36px]" :src="thumb.photoUrl">
          </div>
        </div>
      </div>

      <div class="ml-[12px] bg-black/50 rounded-full p-[4px_8px] flex items-center" @click="handlePreviewClick">
        <Camera size="14" color="#fff" />
        <span class="mx-[4px] text-[10px] text-white align-center">
          {{ thumbnails.length }}
        </span>
        <ChevronRight size="14" color="#fff" />
      </div>
    </div>
  </div>
</template>

<script setup>
import { ref, computed, nextTick, watch } from "vue";
import { useRouter } from 'vue-router'
import { Camera, ChevronRight } from '@lucide/vue'
import { usePictureStore } from "@/store";

const pictureStore = usePictureStore();
const router = useRouter();

const props = defineProps({
  borderRadius: {
    type: [Number, String],
    default: 8,
  },
  images: {
    type: Array,
    default: () => [],
  },
  height: {
    type: [Number, String],
    default: 200,
  },
  showThumbnails: {
    type: Boolean,
    default: true,
  },
  thumbnailBottom: {
    type: [Number, String],
    default: 0,
  },
});

const swipeRef = ref(null);
const thumbnailScrollRef = ref(null);
const active = ref(0);
const scrollLeft = ref(0);

const borderRadiusStyle = computed(() => {
  const radius =
    typeof props.borderRadius === "number"
      ? `${props.borderRadius}px`
      : props.borderRadius;
  return {
    borderRadius: radius,
  };
});

const swiperStyle = computed(() => {
  const radius =
    typeof props.borderRadius === "number"
      ? `${props.borderRadius}px`
      : props.borderRadius;
  const swiperHeight =
    typeof props.height === "number" ? `${props.height}px` : props.height;
  return {
    borderRadius: radius,
    height: swiperHeight,
  };
});

const thumbnails = computed(() => Array.isArray(props.images) ? props.images : []);

const thumbnailBoxStyle = computed(() => {
  const bottom =
    typeof props.thumbnailBottom === "number"
      ? `${props.thumbnailBottom}px`
      : props.thumbnailBottom;
  return {
    bottom: bottom,
  };
});

const clampIndex = (index) => {
  const maxIndex = Math.max(thumbnails.value.length - 1, 0);
  const nextIndex = Number.isFinite(Number(index)) ? Number(index) : 0;
  return Math.min(Math.max(nextIndex, 0), maxIndex);
};

const setActiveIndex = (index, options = {}) => {
  const nextIndex = clampIndex(index);
  active.value = nextIndex;
  scrollToActiveItem(nextIndex);

  if (options.swipe !== false) {
    swipeRef.value?.swipeTo?.(nextIndex, {
      immediate: Boolean(options.immediate),
    });
  }
};

const handleThumbnailClick = (index) => {
  setActiveIndex(index);
};

const scrollToActiveItem = async (index) => {
  await nextTick();

  const itemWidth = 58;
  const containerWidth = 300;
  const targetScrollLeft = Math.max(
    0,
    index * itemWidth - containerWidth / 2 + itemWidth / 2,
  );

  scrollLeft.value = targetScrollLeft;

  const scrollEl = thumbnailScrollRef.value;
  const activeEl = scrollEl?.querySelector?.(`#thumbnail-${index}`);
  if (!scrollEl || !activeEl) return;

  const scrollRect = scrollEl.getBoundingClientRect();
  const activeRect = activeEl.getBoundingClientRect();
  const h5TargetScrollLeft =
    scrollEl.scrollLeft +
    activeRect.left - scrollRect.left -
    (scrollRect.width - activeRect.width) / 2;

  scrollEl.scrollTo?.({
    left: Math.max(0, h5TargetScrollLeft),
    behavior: "smooth",
  });
};

const handleSwiperChange = (index) => {
  setActiveIndex(index, { swipe: false });
};

watch(
  () => thumbnails.value.length,
  (length) => {
    if (!length) {
      active.value = 0;
      scrollLeft.value = 0;
      return;
    }

    const nextIndex = clampIndex(active.value);
    nextTick(() => {
      swipeRef.value?.resize?.();
      setActiveIndex(nextIndex, {
        immediate: true,
      });
    });
  },
);

const handlePreviewClick = () => {
  pictureStore.setPreviewImageData(thumbnails.value);

  router.push({ name: 'album' })
};
</script>
