better-scroll滑动组件的使用

<template>
  <div class="scroll-wrapper" ref="scroll">
    <slot></slot>
  </div>
</template>

<script setup lang="ts">
import BScrolls from "@better-scroll/core";
import { ref, onMounted, onUnmounted, watch, defineExpose } from "vue";

const props = defineProps({
  list: {
    type: Array,
    default: () => [],
  },
  scrollbar: {
    type: Boolean,
    default: false,
  },
  pullUp: {
    type: Boolean,
    default: false,
  },
  scrollX: {
    type: Boolean,
    default: false,
  },
  scrollY: {
    type: Boolean,
    default: false,
  },
  enabled: {
    type: Boolean,
    default: false,
  },
  beforeScroll: {
    type: Boolean,
    default: false,
  },
  probeType: {
    type: Number,
    default: 0,
  },
  refreshDelay: {
    type: Number,
    default: 20,
  },
  scrollToEndLimit: {
    type: Number,
    default: 50,
  },
  listenScroll: {
    type: Boolean,
    default: false,
  },
  bounce: {
    type: Boolean,
    default: true,
  },
  stopPropagation: {
    type: Boolean,
    default: true,
  },
  refreshStatus: {
    type: Boolean,
    default: true,
  },
});
interface Props {
  list: Array<any>;
  scrollbar: boolean;
  pullUp: boolean;
  scrollX: boolean;
  scrollY: boolean;
  enabled: boolean;
  beforeScroll: boolean;
  probeType: number;
  refreshDelay: number;
  scrollToEndLimit: number;
  listenScroll: boolean;
  bounce: boolean;
  stopPropagation: boolean;
  refreshStatus: boolean;
}
const emit = defineEmits(["scroll", "scrollToEnd", "beforeScroll"]);
let scroll = ref(null);
type bscorllType = {
  scrollTo: any;
  on: any;
  refresh: any;
  scrollToElement: any;
  stop: any;
  enable: any;
  disable: any;
  destroy: any;
  y: any;
  maxScrollY: any;
} | null;
let BScroll = ref<bscorllType>(null);

function initScroll() {
  if (!scroll.value) {
    return;
  }
  BScroll.value = new BScrolls(scroll.value, {
    click: true,
    disableMouse: false,
    disableTouch: false,
    scrollX: props.scrollX,
    scrollY: props.scrollY,
    probeType: props.probeType,
    scrollbar: props.scrollbar,
    bounce: props.bounce,
    stopPropagation: props.stopPropagation,
    enabled: props.enabled,
    // mouseWheel: true,
    // disableMouse: true,
    // disableTouch: true,
  });
  BScroll.value.scrollTo(0, 0, 800);
  console.log("BScroll.value", BScroll.value, props.enabled);
  if (props.listenScroll) {
    BScroll.value.on("scroll", scrollHandler);
  }
  if (props.pullUp) {
    BScroll.value.on("scrollEnd", scrollToEndHandler);
  }
  if (props.beforeScroll) {
    BScroll.value.on("beforeScrollStart", beforeScrollHandler);
  }
  BScroll.value.on("scrollEnd", scrollToEnd);
}

function refresh() {
  BScroll.value && BScroll.value.refresh();
}
function scrollTo(a: any, b: any) {
  console.log(a, b);

  BScroll.value && BScroll.value.scrollTo.apply(BScroll.value, arguments);
}
function scrollToElement() {
  BScroll.value &&
    BScroll.value.scrollToElement.apply(BScroll.value, arguments);
}
//立即停止当前运行的滚动动画
function stop() {
  BScroll.value && BScroll.value.stop();
}
//允许滚动
function enable() {
  BScroll.value && BScroll.value.enable();
}
//禁止滚动
function disable() {
  BScroll.value && BScroll.value.disable();
}
function destroy() {
  BScroll.value && BScroll.value.destroy();
  BScroll.value = null;
}
function scrollHandler(pos: any) {
  emit("scroll", pos);
}
function scrollToEndHandler() {
  if (
    BScroll.value &&
    BScroll.value.y <= BScroll.value.maxScrollY + props.scrollToEndLimit
  ) {
    emit("scrollToEnd");
  }
}
function beforeScrollHandler() {
  emit("beforeScroll");
}
function scrollToEnd() {
  // context.$emit("scrollEnd", position);
}
defineExpose({ refresh, scrollTo, destroy });
// function scrollToEnd(position) {
//   context.$emit("scrollEnd", position);
// }
onMounted(() => {
  setTimeout(() => {
    initScroll();
  }, props.refreshDelay);
});
onUnmounted(() => {
  destroy();
});
watch(
  props.list,
  (newValue, oldValue) => {
    // console.log("watch list", newValue, oldValue);
    setTimeout(() => {
      if (props.refreshStatus) {
        scrollTo(0, 0);
        refresh();
      }
    }, props.refreshDelay);
  },
  { immediate: true, deep: true }
);
// return {
//   scroll,
//   BScroll,
//   initScroll,
//   refresh,
//   scrollTo,
//   scrollToElement,
//   stop,
//   enable,
//   disable,
//   destroy,
//   scrollHandler,
//   scrollToEndHandler,
//   beforeScrollHandler,
//   scrollToEnd,
// };
// },
// };
</script>
<style>
.scroll-wrapper {
  position: relative;
}
</style>

单个页面组件内使用

 <ScrollView
    :listenScroll="true"
    class="scrollView"
    style="height: 720px; overflow: hidden"
    :refreshDelay="500"
    ref="shopListRef"
    :scrollY="true"
  >
    <div class="storeyList">
      <div
        v-for="(item, index) in modifyCardList"
        :key="index"
        class="listItem"
        @click="checkShopDetail(item)"
      >
        <div class="listContent">
          <img
            v-show="item && item.logoUrl"
            class="itemImg"
            :src="item.logoUrl ? 'static/offline' + item.logoUrl : ''"
            alt=""
          />
          <!-- <div class="listHeadTitle">花珑珠 赚珑珠</div>  :src="item.logoUrl ? 'static/offline' + item.logoUrl : ''" -->
        </div>

        <div class="listFont">
          <div class="fontLeft">{{ item.name }}</div>
          <div class="iconExplain">
            <img src="../assets/images/clothes.png" alt="" class="itemImg" />
            <!-- <img
                v-show="item && item.logoUrl"
                class="itemImg"
                :src="'static/offline' + item.logoUrl"
                alt=""
              /> -->
            <span style="font-size: 12px; color: #888888">{{
              item.floorName
            }}</span>
          </div>
        </div>
      </div>
    </div>
  </ScrollView>

上面是竖向滑动,比较简单,如果是横向滑动的话,尽量不要用flex布局,会互相影响,可能起不到横向滑动的作用

另外要注意:

 当这些滑动的数据需要进行筛选,重新显示的时候,为了观感,每次筛选之后都要位于数据最顶部,且往下滑不会没有限制,需要进行下面的操作

setTimeout(() => {
    shopListRef.value.scrollTo(0, 0);
    shopListRef.value.refresh();
  }, 200);

例子如下

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值