This commit is contained in:
marzban-dev
2025-03-13 20:30:18 +03:30
parent 183c76e608
commit e69d681415
2 changed files with 99 additions and 17 deletions
@@ -58,7 +58,7 @@ const onInput = (e: any) => {
</NumberFieldIncrement>
<NumberFieldInput
@input="onInput"
class="field-sizing-content bg-transparent outline-none typo-label-md text-black"
class="field-sizing-content bg-transparent w-[30px] text-center outline-none typo-label-md text-black"
/>
<NumberFieldDecrement class="cursor-pointer">
<Icon name="ci:minus" class="**:stroke-slate-500 size-5" />
@@ -1,6 +1,9 @@
<script lang="ts" setup>
// types
import { Swiper, SwiperSlide } from "swiper/vue";
import type { SwiperClass } from "swiper/react";
type Props = {
selectedSlide: number;
slides: ProductImage[];
@@ -12,8 +15,19 @@ const props = defineProps<Props>();
const { slides, selectedSlide } = toRefs(props);
// emit
const emit = defineEmits(["update:selectedSlide"]);
// state
const swiper_instance = ref<SwiperClass | null>(null);
// methods
const onSwiper = (swiper: SwiperClass) => {
swiper_instance.value = swiper;
};
// computed
const selectedSlideDetail = computed(() => {
@@ -22,17 +36,22 @@ const selectedSlideDetail = computed(() => {
})!;
});
const emptySlidesCount = computed(() => {
return 3 - slides.value.length > 0 ? 3 - slides.value.length : 0;
});
// methods
const changeSlide = (id: number) => {
emit("update:selectedSlide", id);
};
</script>
<template>
<div class="flex flex-col relative gap-6">
<div
class="bg-white brightness-[97%] w-full relative aspect-square overflow-hidden rounded-200"
class="bg-white brightness-[97%] w-full relative aspect-square overflow-hidden rounded-[12px] md:rounded-200"
>
<Transition name="zoom" mode="out-in">
<img
@@ -43,24 +62,87 @@ const changeSlide = (id: number) => {
/>
</Transition>
</div>
<div class="flex items-center justify-between gap-6">
<div
@click="changeSlide(slide.id)"
v-for="slide in slides"
:class="
selectedSlide === slide.id
? '!ring-black'
: 'ring-transparent'
"
class="active:scale-95 hover:ring-slate-200 transition-all cursor-pointer brightness-[97%] bg-white aspect-square ring-2 ring-offset-4 rounded-200 w-full overflow-hidden relative"
:key="slide.id"
<div class="relative w-full">
<Swiper
:slides-per-view="3"
:space-between="20"
@swiper="onSwiper"
class="w-full"
>
<img
class="absolute object-cover size-full"
:src="slide.image"
:alt="String(slide.id)"
<SwiperSlide
class="py-4"
v-for="slide in slides"
:key="slide.id"
>
<div
@click="changeSlide(slide.id)"
:class="
selectedSlide === slide.id
? '!border-black'
: 'border-transparent'
"
class="active:scale-95 hover:border-slate-200 transition-all cursor-pointer brightness-[97%] bg-white aspect-square border-2 rounded-[12px] md:rounded-200 w-full overflow-hidden relative"
>
<img
class="absolute object-cover size-full"
:src="slide.image"
:alt="String(slide.id)"
/>
</div>
</SwiperSlide>
<SwiperSlide
v-if="emptySlidesCount > 0"
v-for="slide in emptySlidesCount"
:key="slide"
class="py-4"
>
<div class="brightness-[97%] bg-white aspect-square rounded-[12px] md:rounded-200 w-full" />
</SwiperSlide>
</Swiper>
<div
v-if="slides.length > 3"
@click="swiper_instance?.slidePrev()"
class="absolute z-20 -right-4 shadow-lg cursor-pointer shadow-black/10 bottom-[50%] translate-y-1/2 bg-white rounded-full size-10 xs:size-11.5 flex justify-center items-center"
>
<Icon
name="ci:arrow-right"
class="**:stroke-black size-5 xs:size-6"
:class="swiper_instance?.isBeginning ? '**:stroke-black/30' : ''"
/>
</div>
<div
v-if="slides.length > 3"
@click="swiper_instance?.slideNext()"
class="absolute z-20 -left-4 shadow-lg cursor-pointer shadow-black/10 bottom-[50%] translate-y-1/2 bg-white rounded-full size-10 xs:size-11.5 flex justify-center items-center"
>
<Icon
name="ci:arrow-left"
class="**:stroke-black size-5 xs:size-6"
:class="swiper_instance?.isEnd ? '**:stroke-black/30' : ''"
/>
</div>
</div>
<!-- <div class="grid grid-cols-3 gap-6">-->
<!-- <div-->
<!-- @click="changeSlide(slide.id)"-->
<!-- v-for="slide in slides"-->
<!-- :class="-->
<!-- selectedSlide === slide.id-->
<!-- ? '!ring-black'-->
<!-- : 'ring-transparent'-->
<!-- "-->
<!-- class="active:scale-95 hover:ring-slate-200 transition-all cursor-pointer brightness-[97%] bg-white aspect-square ring-2 ring-offset-4 rounded-[12px] md:rounded-200 w-full overflow-hidden relative"-->
<!-- :key="slide.id"-->
<!-- >-->
<!-- <img-->
<!-- class="absolute object-cover size-full"-->
<!-- :src="slide.image"-->
<!-- :alt="String(slide.id)"-->
<!-- />-->
<!-- </div>-->
<!-- </div>-->
</div>
</template>