vant的pullRefresh 刷新中高度问题
在手机小屏下拉刷新,内容的高度没问题
但在ipad这种大屏的显示就出现问题了,有部分被遮住了
因为我的项目使用了postcss-px-to-viewport转化单位,其实内容高度也进行了单位转换,也没有毛病
既然高度没问题,那肯定是定位之类的位置不对,导致一部分被遮住,然后我看到了上面的绝对定位,但是又没有top值😓
然后我把loading的状态设置为true来调试,发现是van-pull-refresh__track这个节点的内联样式translate3d(0,50px, 0)控制位置的。
那么问题就知道了,这个内联样式是vant组件内部算的,而且是px,因为postcss-px-to-viewport不能转换行内样式的单位
那就看看源码(点击查看)是怎么处理的吧
const trackStyle = {
transitionDuration: `${state.duration}ms`,
transform: state.distance
? `translate3d(0,${state.distance}px, 0)`
: '',
};
确实是根据设置的距离的值做的,接下来就看他touchEnd做了什么就可以了
因为这个问题就是手松开之后,组件的
translateY位置不对
const onTouchEnd = () => {
if (reachTop && touch.deltaY.value && isTouchable()) {
state.duration = +props.animationDuration;
if (state.status === 'loosing') {
// 松手后就是刷新中,就是在这个地方设置了展示内容的一个高度
setStatus(+props.headHeight, true);
emit('update:modelValue', true);
// ensure value change can be watched
nextTick(() => emit('refresh'));
} else {
setStatus(0);
}
}
};
// ...
const setStatus = (distance: number, isLoading?: boolean) => {
const pullDistance = +(props.pullDistance || props.headHeight);
state.distance = distance;
if (isLoading) {
state.status = 'loading';
} else if (distance === 0) {
state.status = 'normal';
} else if (distance < pullDistance) {
state.status = 'pulling';
} else {
state.status = 'loosing';
}
emit('change', {
status: state.status,
distance,
});
};
由此可见,在touchEnd的时候通过setStatus方法把props.headHeight(默认50)的值作为Y轴偏移的距离
解决办法
所以,根据当前设备的宽高(根据UI设计稿或者你自己的适配方案)去计算高度,设置headHeight的值,单位是px哈
其实我记录的时候
UI还没设计,但是375下我感觉vant默认的50px挺合适的,所以就定义了750的时候设置headHeight为100
<template>
<div>
<PullRefresh :head-height="changeUiPx(100)" success-text="刷新成功" v-bind="$attrs">
<slot></slot>
</PullRefresh>
</div>
</template>
<script lang="ts" setup>
import { PullRefresh } from 'vant';
import { changeUiPx } from '/@/utils';
</script>
<style lang="less" scoped></style>
我自己写了一个转换我们设计稿(宽750)单位的工具函数
import { useWindowSize } from '@vant/use';
/**
* @author: gauharchan
* @description 设计稿像素转换
* @param {number} value 设计稿实际的值
*/
export const changeUiPx = (value: number) => {
const { width, height } = useWindowSize();
const vmin = Math.min(width.value, height.value);
return (vmin * value) / 750;
};