在上一篇中,我们用内置组件切了一张仿淘宝首页,主要了解到了uni-app内置组件的布局,我们在布局首页时,我们使用了uni-list这个组件,这是一个uni-app内置官方扩展组件,该组件长列表性能优化,多端兼容。

我们继续完善一下首页的商品列表模块

主要会从以下完善功能

  • 在线mock商品数据

  • 实现商品的上拉加载,下拉刷新

在线mock数据

首先我们在EazyMockopen in new window在线平台登陆,创建一个个人项目,然后我们在线创建一个接口

然后我们编辑mock数据

{
  "data": {
    pageIndex: function({
      _req
    }) {
      return _req.query.pageIndex
    },
    pageSize: function({
      _req
    }) {
      return _req.query.pageSize
    },
    "list|10": [{
      'url': "@image('200x100', '#50B347', '#FFF', 'Web技术学苑')",
      'desc': '@ctitle()',
      'prices': '@integer(100,1000)',
      'buys': '@integer(60,100)',
    }]
  }
}

在代码中我们需要将模拟的mock数据放置到数据中

// Content.vue
 ...
	methods: {
			queryGoods() {
				const {condation} = this;
				uni.request({
					url:"https://mock.mengxuegu.com/mock/63e0b9f41b8291742151c7a2/tabbao/goodslist",
					method:'GET',
					data: condation,
					success: (res) =>  {
						const {data: {data}} = res;
						this.shopData = this.shopData.concat(data.list)
					}
				})
			}
		},
		created() {
			this.queryGoods();
		}

看下预览效果,页面展示了10条数据

上拉加载

uni-app中实现上拉加载主要有两种方案,第一种的是使用内置组件scroll-view,另一种就是使用原生pages.json配置实现,我们需要注意scroll-view是区域滚动,并且scroll-viewopen in new window并不适合长列表

官方推荐上拉加载使用原生配置

首先我们必须在pages.json中对应的style中添加enablePullDownRefresh

{
  "pages": [
    {
			"path": "pages/index/index",
			"style": {
				"navigationBarTitleText": "仿淘宝网触屏版",
				"enablePullDownRefresh": true
			}
		}
  ]
}

只有对应路有页面新增enablePullDownRefreshopen in new window,对应路由页面才会触发下拉加载钩子

我们在主页面可以看到

  • 新增了两个方法onPullDownRefreshonReachBottom
<template>
	<view class="index-content">
		<Header></Header>
		<Content ref="content"></Content>
	</view>
</template>

<script>
	import Header from "./component/Header.vue";
	import Content from "./component/Content.vue";
	
	export default {
		components: {
			Header,
			Content
		},
		data() {
			return {
				
			}
		},
		onPullDownRefresh() {
			this.$refs.content.pullDownRefresh();
		},
		onReachBottom() {
			this.$refs.content.reachBottom();
		},
		onLoad() {
			console.log('index load')
			console.log(window)
		},
		onShow() {
			console.log('index on show')
		},
		methods: {
			
		}
	}
</script>

<style>
	
</style>

onPullDownRefresh在下拉时会触发这个钩子函数

onReachBottom触发底部时会触发这个函数

注意这两个钩子只能在主页里生效,并不能在content组件中生效,所以我们使用一个ref方式与子组件通信

Content组件中

...
methods: {
			queryGoods() {
				const { condation } = this;
				this.loadStatus = 0;
				uni.request({
					url:"https://mock.mengxuegu.com/mock/63e0b9f41b8291742151c7a2/tabbao/goodslist",
					method:'GET',
					data: condation,
					success: (res) =>  {
						const {data: {data}} = res;
						if (data.hasMore) {
							this.loadStatus = 3;
							this.shopData = this.shopData.concat(data.list)
						} else {
							this.loadStatus = 2;
						}
					}
				})
			},
      // 下拉刷新
			pullDownRefresh() {
				this.condation.pageIndex = 1;
				this.condation.pageSize = 10;
				this.shopData = [];
				this.queryGoods();
				// 停止loading
				uni.stopPullDownRefresh();
			},
      // 上拉触发底部加载
			reachBottom() {
				if (this.condation.pageIndex < 5) {
					this.condation.pageIndex +=1;
					this.queryGoods();
				}
			}
	},
  created() {
			this.queryGoods();
	}

我使用hasMore的标识模拟数据加载完毕,当hasMorefalse时就代表数据加载完毕

loadStatus0,1,2三个值代表加载状态

	<!--商品列表_start-->
		<uni-list class="shop-list" :border="false">
			<uni-list-item v-for="(item, index) in shopData" :key="index">
				<template slot="body">
					<view class="card-item-body">
						<image class="img" :src="item.url" mode="aspectFill"></image>
						<view class="card-item-body-desc">
							<text>{{item.desc}}</text>
						</view>
						<view>
							<text class="prise">¥{{item.prices}}</text>
							<text class="buys">{{item.buys}}+人已购买</text>
						</view>
					</view>
				</template>
			</uni-list-item>
			<view class="load-status">
				{{loadStatusText[loadStatus]}}
			</view>
		</uni-list>

最后的结果翻到最后一页时

pageIndex==5时,在线的mock接口将hasMore改成false

{
  "data": {
    pageIndex: function({
      _req
    }) {
      return _req.query.pageIndex
    },
    pageSize: function({
      _req
    }) {
      return _req.query.pageSize
    },
    hasMore: function({
      _req
    }) {
      if (_req.query.pageIndex * 1 >= 5) {
        return false
      }
      return true;
    },
    "list|10": [{
      'url': "@image('200x100', '#50B347', '#FFF','Web技术学苑')",
      'desc': '@ctitle()',
      'prices': '@integer(100,1000)',
      'buys': '@integer(60,100)',
    }]
  }
}

总结

  • 主要是完善首页商品列表,通过内置配置实现下拉刷新与上拉加载

  • pages.json中关键的配置enablePullDownRefresh,当它为true时会触发页面的onPullDownRefreshonReachBottom

  • EazyMock在线模拟了接口,实现假数据的填充

  • 本文示例code exampleopen in new window

扫二维码,关注公众号
专注前端技术,分享web技术
加作者微信
扫二维码 备注 【加群】
教你聊天恋爱,助力脱单
微信扫小程序二维码,助你寻他/她
专注前端技术,分享Web技术
微信扫小程序二维码,一起学习,一起进步
前端面试大全
海量前端面试经典题,助力前端面试