H5仿探探左右滑动效果Vue.js

 效果图:

 

效果图:GIF

 

说明 H5仿探探左右滑动效果

<template>
  <div class="slide">
    <div
      class="slide_item"
      v-for="(item,index) in listArr"
      :key="index"
      :style="[initCSS(index),Transform(index)]"
      @touchstart.stop.prevent.capture="touchStart($event,index)"
      @touchmove.stop.prevent.capture="touchMove($event,index)"
      @touchend.stop.prevent.capture="touchEnd(index)"
      v-show="item.show"
    >
      <span class="title">第{{item.index + 1}}个</span>
      <span class="text">仿探探左右滑动效果/初始化50个</span>
      <span class="text">只支持移动端</span>

    
    </div>
  </div>
</template>
<script>
export default {
  name: "slide",
  data() {
    return {
      listArr: [],
      /*记录x y轴*/
      x: {
        start: 0,
        move: 0,
        end: 0
      },
      y: {
        start: 0,
        move: 0,
        end: 0
      },
      /*下标*/
      currentIndex: 0,
      /*宽度宽度*/
      winWidth: 0,
      /*xy位移*/
      displacement: {
        x: 0,
        y: 0
      },
      /*滑动*/
      swipering: false,
      /*滑动中*/
      slideing: false,
    };
  },
  mounted() {
    this.init();
  },
  methods: {
    init() {
      /* 测试数据*/
      for (let index = 0; index < 50; index++) {
        var data = {
            index: index,
            show: true,
            x: 0,
            y: 0,
            opacity: index < 3 ? 1 : 0
        };

        this.listArr.push(data);
      }
      this.winWidth = document.documentElement.clientWidth;
    },
    initCSS(index) {
      let css = {};
      css["z-index"] = index;
      css["transform"] = `translate3d(0,0,${(this.currentIndex - index) *
        50}px)`;
      css["transitionDuration"] =   "0ms";

      return css;
    },
    Transform(index) {
      let css = {};
      if (!this.swipering) {
        css["transitionDuration"] = "300ms";
      } else {
        css["transitionDuration"] = "0ms";
      }
      if (index === this.currentIndex) {
        css["transform"] = `translate3d(${this.listArr[index].x}px,${
          this.listArr[index].y
        }px,${(this.currentIndex - index) * 50}px)`;
      }

      css['opacity'] = this.listArr[index].opacity;
      return css;
    },
    touchStart(e) {
      if(this.slideing) return;
      this.swipering = true;
      this.x.start = e.touches[0].pageX;
      this.y.start = e.touches[0].pageY;
    },
    // 滑动计算
    touchMove(e, index) {
      if(this.slideing) return;
      if(this.listArr.length == index + 1){
         return;
      }
      this.x.move = e.touches[0].pageX;
      this.y.move = e.touches[0].pageY;

      this.displacement.x, (this.listArr[index].x = this.x.move - this.x.start);
      this.displacement.y, (this.listArr[index].y = this.y.move - this.y.start);
      
    },
    // 滑动结束判断是否超过一定值
    touchEnd(index) {
      this.swipering = false;
      if(this.listArr.length == index + 1){
         return;
      }
      if (
        this.listArr[index].x > 0 &&
        this.listArr[index].x > this.winWidth / 2 - this.winWidth / 4.5
      ) {
        this.touchEndNext(index);
      } else if (
        this.listArr[index].x < 0 &&
        this.listArr[index].x < -this.winWidth / 2 + this.winWidth / 4.5
      ) {
        this.touchEndNext(index);
      } else {
        this.listArr[index].x = 0;
        this.listArr[index].y = 0;
        this.slideing = false;
      }
    },
    touchEndNext(index) {
      this.slideing = true;
      this.listArr[index].x = this.listArr[index].x * 3;
      this.listArr[index].y = this.listArr[index].y * 3;
      var a = setTimeout(() => {
        this.$set(this.listArr[index], "show", false);
        this.$nextTick(() => {
          this.currentIndex++;
          if(index + 3 < this.listArr.length){
            this.$set(this.listArr[index + 3], "opacity", 1);
          }
          this.slideing = false
          a;
        });
      }, 300);
    }
  }
};
</script>

.slide {
  position: relative;
  width: 95%;
  height: 500px;
  perspective: 1000px;
  perspective-origin: 50% 150%;
  transform-style: preserve-3d;
}
.slide .slide_item {
  transform-style: preserve-3d;
  display: flex;
  width: 100%;
  height: 100%;
  border-radius: 20px;
  position: absolute;
  z-index: 30;
  background: #fff;
  display: flex;
  justify-content: center;
  align-items: center;
  text-align: center;
  /* opacity: 0; */
  /* display: none; */
  text-align: center;
  font-size: 30px;
  line-height: 1;
  transform: translate3d(0px, 0px, 0px) rotate(0deg);
  box-shadow: 0 10px 15px 0 rgba(0, 0, 0, 0.15);
  transition: 300ms;
  opacity: 0;
  flex-direction: column;
}
.slide .slide_item .title{
   font-size: 50px;
}
.slide .slide_item .text{
  font-size: 16px;
  margin-top: 10px;
}

由于csdn没有vue格式代码插入所以分成三段展示

Uniapp 是一个使用 Vue.js 开发所有前端应用的框架,能够编译到 iOS、Android、H5、以及各种小程序等多个平台。在 Uniapp 中实现仿探探左右滑动效果,可以通过内置的 `<scroll-view>` 组件来实现基本的滑动功能,配合 CSS 的 transform 属性来实现滑动动画效果。 基本步骤如下: 1. 使用 `<scroll-view>` 组件设置一个可滚动的视图区域,并设置其 `scroll-x` 属性为 `true`,以允许水平滚动。 2. 在 `<scroll-view>` 中放置多个可以左右滑动的卡片,每个卡片可以是一个单独的 `<view>` 组件。 3. 为每个卡片设置一个固定宽度,并通过 CSS 设置其在屏幕外的位置,当卡片滑动到屏幕内时,使用 CSS 的 `transform` 属性来移动卡片。 4. 当卡片滑动到屏幕边缘时,监听滑动事件,以实现自动左右滑动效果。 5. 为卡片添加点击事件,实现类似于探探的点击喜欢或不喜欢的功能。 下面是一个简单的代码示例: ```html <template> <view> <scroll-view class="scroll-view" scroll-x="true" @scroll="handleScroll" @touchend="handleTouchEnd"> <view class="card" v-for="(item, index) in cardList" :key="index" :style="{ transform: `translateX(${-100 * index}%)` }"> <!-- 卡片内容 --> </view> </scroll-view> </view> </template> <script> export default { data() { return { cardList: ['card1', 'card2', 'card3', 'card4'] // 卡片数组 }; }, methods: { handleScroll(e) { // 处理滚动事件 }, handleTouchEnd(e) { // 处理手指松开事件,可以实现自动滑动 // 计算滑动距离和速度,决定滑动到下一卡片还是返回 } } }; </script> <style> .scroll-view { white-space: nowrap; overflow: auto; } .card { display: inline-block; width: 100%; height: 100%; vertical-align: top; transition: transform 0.3s ease; } </style> ```
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值