b2nil / taro-ui-vue3

采用 Vue 3.0 重写的 Taro UI 组件库
https://b2nil.github.io/taro-ui-vue3/
MIT License
160 stars 51 forks source link

AtCalendar 组件滑动切换月份,意外回到上个月份 #55

Closed whyour closed 3 years ago

whyour commented 3 years ago

问题描述

当切换月份时,在monthChange方法中修改页面中的变量,触发页面重新渲染,这时会又跳到刚才切换之前的月份

版本信息

v1.0.0-alpha.12

涉及的平台

weapp

错误信息

代码

<at-calendar @monthChange="monthChange" />
<view class="part-loading" v-if="partLoading">
  <at-activity-indicator></at-activity-indicator>
</view>
const partLoading = ref(false)

const monthChange = (value) => {
  partLoading.value = true
}
b2nil commented 3 years ago

已定位问题,AtCalendarBody 中,Swiper 没有动态绑定 current 导致。

vue.h(components.Swiper, vue.mergeProps(animationEndOrFinish, {
   class: 'main__body',
   circular: true,
   vertical: props.isVertical,
   skipHiddenItemLayout: true,
   current: 1, // <- 应该改为: currentSwiperIndex.value
   onChange: handleChange,
   onTouchMove: handleSwipeTouchMove,
   onTouchEnd: handleSwipeTouchEnd,
   onTouchStart: handleSwipeTouchStart
}),

会在下一个版本中修复。

whyour commented 3 years ago

我看react版也没绑,current应该是swiper自己变的吧。如果monthChange的时候不修改partLoading就没问题

b2nil commented 3 years ago

你可以试试 react 版本存在这个问题吗?

b2nil commented 3 years ago

把 taro-ui-vue3/dist/index.umd.js 中 AtCalendarBody 中相应的地方按照上面改一下,的确可以修复问题。具体是哪个逻辑,或者 Swiper 组件的问题,后续再研究一下。

b2nil commented 3 years ago

@whyour 单独用 Swiper 复现了一下这个问题, 的确就是因为 Swipercurrent 参数绑定了 1 导致的。

current 参数的作用是定位滑块,页面首次渲染后,滑块定位在 index 为 1 的滑块位置。在不重新渲染页面的情况下,左右滑动不受影响。

在页面重新渲染后,虽然 onChange 中获取到的 current 值是相应变化的,但如果不动态绑定 current 的值,Swiper 视图一定会返回 index 为 1 的滑块位置。

<swiper
   circular
   vertical
   :current="1"   // <- currentSwiperIndex
   @change="handleChange"
>
   <swiper-item>
       <view class='demo-text-1'>1</view>
   </swiper-item>
   <swiper-item>
       <view class='demo-text-2'>2</view>
   </swiper-item>
   <swiper-item>
       <view class='demo-text-3'>3</view>
   </swiper-item>
</swiper>
<view
   class="part-loading"
   v-if="partLoading"
>
   <at-activity-indicator></at-activity-indicator>
</view>
const partLoading = ref(false)
const currentSwiperIndex = ref(1)

function handleChange(e) {
  const { current, source } = e.detail
  if (source === 'touch') {
     console.log(current)
     // currentSwiperIndex.value = current
     partLoading.value = !partLoading.value  // 触发页面重新渲染
  }
}
whyour commented 3 years ago

你可以试试 react 版本存在这个问题吗?

react版本也有问题,但不知道是不是同一个问题。react版本滑动第一次没问题,第二次swipercurrent会变成 -1,日历面板成白板了

b2nil commented 3 years ago

你可以试试 react 版本存在这个问题吗?

react版本也有问题,但不知道是不是同一个问题。react版本滑动第一次没问题,第二次swipercurrent会变成 -1,日历面板成白板了

ReactVue 2.0Vue 3.0 这三个版本的的 Taro UI 都存在同样的问题。React 版本因为缺乏维护,问题更多。

whyour commented 3 years ago

你可以试试 react 版本存在这个问题吗?

react版本也有问题,但不知道是不是同一个问题。react版本滑动第一次没问题,第二次swipercurrent会变成 -1,日历面板成白板了

ReactVue 2.0Vue 3.0 这三个版本的的 Taro UI 都存在同样的问题。React 版本因为缺乏维护,问题更多。

是的,所以我React都写完了,又转向Vue 3.0了,没人维护很尴尬

b2nil commented 3 years ago

已发 alpha.13