通过 Swiper 组件实现了游戏列表的轮播展示,根据设备类型动态调整每页显示的游戏数量和布局,并且为每个游戏项添加了点击事件以跳转到详细页面。

展示效果:
在这里插入图片描述

1.安装依赖:(我安装的是"swiper": “^11.1.12”,)

npm i swiper

2.template代码:

<template>
  <div>
    <!-- tab -->
    <div class="tab-search">
      <div class="itemBox overflow-x-scroll flex items-center justify-start ">
        <div class="tab-search-item " :class="{ actived: isActive === item.id }" v-for="item in tabList" :key="item.id"
          @click="changeTab(item)">

          <i class="iconfont" :class="item.icon"></i>
          <!-- <span>{{ $t(`${item.langTitle}`) }}</span> -->
          <span>{{ item.name }}</span>
        </div>
      </div>
      <div class="search-icon">
        <van-icon name="search" color="#0FE1A9" />
      </div>
    </div>
    <!-- 内容 -->
    <div class="content">
      <div class="gameList" v-for="(i, idx) in filtersList" :key="i.typeName">
        <div class="titleContent">
          <div class="title">
            <i class="iconfont text-45 fontColor pr-10" :class="i.icon" />
            <span class="text-28 ">{{ i.typeName }}</span>
            <div class="Rtp bg-fff-5 text-fff px-20 ml-20 text-20" v-if="!isMobile">
              <i class="iconfont icon-lightning text-fff mr-5"></i>
              <span class=" ">RTP até </span>
              <span class="text-ffee92 ml-5">{{ i.hot }}</span>
            </div>
          </div>
          <div class="switch">
            <div class="mais">{{ $t('More') }}</div>
            <div class="arrow_left" @click="prevSlide(idx)">
              <!-- <i class="iconfont icon-cha"></i> -->
              <van-icon name="arrow-left" size="14" color="#4D4F54" />
            </div>
            <div class="arrow_right" @click="nextSlide(idx)" :disabled="disabledEnd">
              <!-- <i class="iconfont icon-jinbi"></i> -->
              <van-icon name="arrow" size="14" color="#4D4F54" />
            </div>
          </div>
        </div>
        <div class="centerDiv" v-if="isMobile">
          <!-- <van-icon name="sort" /> -->
          <i class="iconfont icon-lightning text-fff"></i>
          <span>RTP até </span>
          <span>{{ i.hot }}</span>
        </div>
        <div class="list">
          <!-- :autoplay="swiperOption.autoplay"  ref="mySwiper"
        @swiper="onSwiper" -->
          <Swiper :ref="`mySwiper${idx}`" @swiper="onSwiper(idx, $event)" :autoplay="false" :modules="modules"
            :slides-per-view="isMobile ? 4 : 7" :grid="{
              fill: 'row',
              rows: 3,
            }" :spaceBetween="isMobile ? 6 : 50" :prevent-clicks-propagation="false" class="wrap">

            <SwiperSlide v-for="(item, index) in i.data" :key="index" class="swiper-slide chart"
              @click="handleDetail(item)">
              <!-- {{ item }} -->
              <div class=" relative ">

                <img :src="`${domain.picture}${item.gameIcon}`" alt="" />
                <div
                  class="absolute top-0 left-0 w-60 h-35 rounded-r-40px  text-24  text-fff bg-gradient-to-b from-[#FF0F47] to-[#FFAB96] content-center pl-7 shasowYy">
                  Top</div>
                <div
                  class="absolute top-2 right-2 w-31 h-31 leading-31 bg-[rgba(113,113,113,0.71)]  content-center text-center rounded-50%">
                  <i class="iconfont icon-xingxing  fontSize14 text-fff"
                    :class="{ 'text-gradient ': isLike == true }"></i>
                </div>
              </div>
            </SwiperSlide>
          </Swiper>

        </div>
      </div>
      <div v-if="!filtersList.length" class="text-center mt-30">暂无数据</div>
    </div>
  </div>
</template>

3.js代码

import { computed, onMounted, ref } from "vue";
import { Swiper, SwiperSlide } from "swiper/vue";
import "swiper/css";
import "swiper/css/grid";
import { Autoplay, Grid } from "swiper/modules";
let isActive = ref(0);
let disabledEnd = ref(false);
const swiperRefs = ref([]);
// 切换tab数据过滤
const filtersList = computed(() => {
  if (isActive.value === 0) {
    return dataList.value.filter(item => item.hasOwnProperty('data'))
  } else {
    return dataList.value.filter(item => item.type === isActive.value && item.hasOwnProperty('data'))
  }
})
const changeTab = (e) => {
  isActive.value = e.id

}
// 添加一个用于存储每个swiper当前页码的数组
const currentPages = ref(Array(dataList.value.length).fill(0));
// 监听 swiper 组件的回调函数,同时存储每个swiper的引用
const onSwiper = (index, swiper) => {

  swiperRefs.value[index] = swiper;

  swiper.on('slideChange', () => {
    // 更新当前页码
    currentPages.value[index] = swiper.activeIndex;
    console.log(swiper);

  });
};
// 检查是否在第一页的函数
const isAtFirstPage = (index) => {
  return currentPages.value[index] === 0;
};

const isEndPcPage = (index) => {
  return (swiperRefs.value[index].slides.length - 12) / 2
}
// 上一页滑动函数
const prevSlide = (index) => {
  const swiperInstance = swiperRefs.value[index];
  if (swiperInstance.slides && swiperInstance.slides.length < 12) {
    showToast({
      message: '没有更多数据',
      position: 'center',
    });
    console.log('没有更多数据');
    return
  }

   if(swiperInstance.activeIndex===0 ){
    console.log("已经是第一页了",swiperInstance);
    showToast({
      message: '已是第一页',
      position: 'center',
    });
  } else if (!isAtFirstPage(index) && swiperInstance) {
    swiperInstance.slidePrev();
    console.log("上一页", swiperInstance,isAtFirstPage(index));
  }else{
    console.log("已经是第一页了");
    showToast({
      message: '已是第一页',
      position: 'center',
    });
  }

};
// 切换到下一张幻灯片
const nextSlide = (index) => {
  const swiperInstance = swiperRefs.value[index];
  if (swiperInstance.slides.length < 12) {
    showToast({
      message: '没有更多数据',
      position: 'center',
    });
    return false;
  }
  if (swiperInstance.activeIndex >= isEndPcPage(index) && !isMobile) {
    showToast({
      message: '已是最后一页',
      position: 'center',
    });
    console.log('已经是最后一张了');
    return false;
  }
  if(swiperInstance.activeIndex  >=((swiperInstance.slides.length - 12) / 3)){ //3代表列 12代表每一页个数
    showToast({
      message: '已是最后一页',
      position: 'center',
    });
  }
   else if (!(swiperInstance.activeIndex >= ((swiperInstance.slides.length - 12) / 3)) && swiperInstance) {
    swiperRefs.value[index].slideNext();
  }else {
    disabledEnd.value = true;
    showToast({
      message: '已是最后一页',
      position: 'center',
    });
  }
};
Logo

魔乐社区(Modelers.cn) 是一个中立、公益的人工智能社区,提供人工智能工具、模型、数据的托管、展示与应用协同服务,为人工智能开发及爱好者搭建开放的学习交流平台。社区通过理事会方式运作,由全产业链共同建设、共同运营、共同享有,推动国产AI生态繁荣发展。

更多推荐