uni-app
App端内置了一个基于 weex 改进的原生渲染引擎,提供了原生渲染能力。
在App端,如果使用vue页面,则使用webview渲染;如果使用nvue页面(native vue的缩写),则使用原生渲染。
list是app端nvue专用组件,详细介绍在官网https://uniapp.dcloud.io/component/list?id=list
1、下拉刷新和触底加载
<refresh>
组件为容器提供下拉刷新功能,
<refresh>
提供两个事件=》
pullingdown:被下拉时触发;refresh :被下拉完成时触发(理解为touchend 时)
<list>提供一个事件,和一个属性设定触底加载的距离
loadmore:列表滚动到底部将会立即触发这个事件,你可以在这个事件的处理函数中加载下一页的列表项。 如果未触发,请检查是否设置了loadmoreoffset的值,建议此值设置大于0;
loadmoreoffset:触发 loadmore 事件所需要的垂直偏移距离(设备屏幕底部与 list 底部之间的距离);
<template>
<view class="list">
<!-- list组件必须显示的指定宽高,或者使用定位方式 -->
<list class="list" loadmoreoffset="10" @loadmore="loadMore" ref="list">
<refresh
:display="refreshing ? 'show' : 'hide'"
@refresh="onrefresh"
@pullingdown="onpullingdown"
@click="reFresh">
<view class="loading-more">
<loading-indicator style="margin-right:15px;"></loading-indicator>
<text class="loading-more-text">{{refreshText}}</text>
</view>
</refresh>
<cell v-for="(item,index) in list"
:key="index"
:ref="'cell'+index">
<view class="cell">
<text>{{item}}</text>
</view>
</cell>
<cell v-if="list.length>8 && !noData">
<view class="loading-more">
<loading-indicator style="margin-right:15px;"></loading-indicator>
<text class="loading-more-text">加载中...</text>
</view>
</cell>
<cell v-if="noData">
<view class="loading-more">
<text class="loading-more-text">没有更多数据了</text>
</view>
</cell>
</list>
<view class="top" style="bottom: 150px;" @click="reLoad">
<text>刷新</text>
</view>
<view class="top" @click="clickTop()">
<view style="background-color: pink;" @click.stop="toTop(1,$event)">
<text>toTop</text>
</view>
</view>
</view>
</template>
<script>
//只在nvue 页面有该模块
const dom = weex.requireModule('dom')
export default {
data() {
return {
list: [1, 2, 3, 4, 5, 6,7,8],
noData:false,
refreshText:'',
loading:false,
refreshing:false
}
},
methods: {
//开始下拉时
onpullingdown(e){
//当正在刷新的时候直接返回
if(this.refreshing){
return;
}
if (Math.abs(e.pullingDistance) > Math.abs(e.viewHeight)) {
//当下拉的距离大于fresh组件的高度
this.refreshText = "释放立即刷新";
} else {
this.refreshText = "下拉可以刷新";
}
},
onrefresh(){
if(this.loading){
//当正在调用接口获取数据时,此时的下拉不做任何操作
return;
}
this.refreshText="正在刷新...";
//刷新数据
//模拟接口延迟
this.loading = true;
this.refreshing = true;
//刷新成功
setTimeout(()=>{
this.list = [1,2,3,4,5,6,7,8];
this.loading = false;
this.refreshing = false;
this.loadErr = false;
},300);
//模拟刷新失败
// setTimeout(()=>{
// this.loading = false;
// this.refreshText = '刷新失败,点击重试';
// this.loadErr = true;
// },300);
},
reFresh(){
if(!this.loadErr){
return;
}
this.refreshText="正在刷新...";
setTimeout(()=>{
this.list = [1,2,3,4,5,6,7,8];
this.loading = false;
this.refreshing = false;
this.loadErr = false;
},300);
},
loadMore(){
let data = [];
let v = this.list[this.list.length-1];
if(v==200){
this.noData = true;
return;
}
for(let i = 0;i<4;i++){
v++;
data.push(v);
}
//模拟接口返回时间延迟
setTimeout(()=>{
this.list = this.list.concat(data);
},300);
},
reLoad(){
//当屏幕已经向下滚动,此时刷新,如果数据超过一屏,此时滚动条不会自动置顶
this.list = [1,2,3,4,5,7,8,9];
this.scrollElement(0);
},
toTop(params,e){
//nvue下阻止事件冒泡的方法
e.stopPropagation()
this.scrollElement(0);
},
//滚动到某一个元素
scrollElement(index){
if (this.$refs['cell'+index]) {
//滑动到顶部
let el = this.$refs['cell'+index][0];
dom && dom.scrollToElement(el, {
// animated:false //滚动的动画,默认有
});
}
},
clickTop(e){
uni.showToast({
title:'事件冒泡了'
})
}
}
}
</script>
<style>
.list{
position: absolute;
top:0;
bottom: 0;
left:0;
right: 0;
/* #ifndef APP-PLUS */
display: flex;
flex-direction: column;
/* #endif */
}
.cell {
padding-left: 20px;
padding-top: 40px;
padding-right: 20px;
padding-bottom: 40px;
background-color: #F9D7EA;
margin-top: 15px;
}
.loading-more {
align-items: center;
justify-content: center;
padding-top: 14px;
padding-bottom: 14px;
text-align: center;
flex-direction: row;
width:750rpx;
}
.loading-more-text {
font-size: 28upx;
color: #999;
}
.top{
position: fixed;
right:5px;
background-color: #FFFFFF;
bottom:50px;
width:80px;
height: 80px;
border-radius: 50%;
box-shadow: 0 1px 20px 0 rgba(195, 195, 195, 0.5);
align-items: center;
justify-content: center;
}
</style>
注:如果上拉加载数据后,再下拉刷新,然后无法再触发loadmore事件时,请重置loadmore
loadMore(e) {
//loadmore 事件中重置
this.$refs["list"].resetLoadmore();
//下一页操作
...
}
如果下拉刷新的组件不回弹回去,试试延迟设置hide