原来vue的slot可以这么玩转
栏目: JavaScript · 发布时间: 6年前
内容简介:vue的内容分发非常适合“固定部分+动态部分”的组件的场景,固定部分可以是结构固定,也可以是逻辑固定,比如下拉loading,下拉loading只是中间内容是动态的,而拉到底部都会触发拉取更多内容的操作,因此我们可以把下拉loading做成一个有slot的插件。“下拉加载更多”的场景在移动端相对来说出现得比较多。我们知道下拉触底都要监听触底事件,触底的操作也相同(去后台拉取数据),分页算法也相同,因此我们会想到把它做成一个组件,重用这些相同的地方,让其他地方可以共用这个组件,从而减少代码量。然而,下拉lo
vue的内容分发非常适合“固定部分+动态部分”的组件的场景,固定部分可以是结构固定,也可以是逻辑固定,比如下拉loading,下拉loading只是中间内容是动态的,而拉到底部都会触发拉取更多内容的操作,因此我们可以把下拉loading做成一个有slot的插件。
使用场景
“下拉加载更多”的场景在移动端相对来说出现得比较多。我们知道下拉触底都要监听触底事件,触底的操作也相同(去后台拉取数据),分页算法也相同,因此我们会想到把它做成一个组件,重用这些相同的地方,让其他地方可以共用这个组件,从而减少代码量。
然而,下拉loading并不是一个可以完全重用的组件,因为列表里面的内容不同,空白页(没有内容时)的内容也可能不同,如果要做成组件,那么就要考虑到这方面的“不同”,因此我们想到利用vue的内容分发slot来做。下面是本人在开发的时候做的一个下拉loading,大家可以参考下。
组件代码:
<template> <div> <slot name="list" v-if="total > 0"></slot> <slot name="empty" v-else></slot> </div> </template> <script> import Toast from 'lib/xl-toast' import Tool from 'tool/tool' export default { data() { return { page: 1, isLoading: false, busy: false, isFirstLoad: false } }, props: { pageSize: { default: 10 // 每页展示多少条数据 }, total: { default: 0 // 总共多少条记录 } }, computed: { totalPage() { return Math.ceil(this.total / this.pageSize) } }, created() { this.getList() }, mounted() { this.addScrollListener() }, methods: { addScrollListener() { // 添加监听滚动操作,用到函数防抖 this.scrollFn = Tool.throttle(this.onScroll, 30, 30) document.addEventListener('scroll', this.scrollFn, false) }, getList() { // 正在拉取数据或者没有数据了,则取消滚动监听 if(this.isLoading || this.isFirstLoad && (this.page > this.totalPage)) { document.removeEventListener('scroll', this.scrollFn, false) return } this.busy = true this.isLoading = true // 通知父组件去拉取更多数据 this.$emit("getList", this.page, () => { this.isFirstLoad = true this.isLoading = false this.page++ }, () => { Toast.show('网络错误,请稍后重试') this.total = 0 this.isLoading = false }) }, reset() { // 重新拉取数据 this.page = 1 this.total = 0 this.isLoading = false this.isFirstLoad = false this.addScrollListener() this.getList() }, onScroll() { // 到底拉取更多数据 if(Tool.touchBottom()) { this.getList() } } } } </script> 复制代码
总之,遇到一些有想对比较固定的部分,包括js操作或者结构固定,又有一些动态的部分,我们应该就应该考虑到使用:组件+slot。
意向不到的slot另类用法
我在做需求的时候,做了一个组件,该组件分为上下两个部分,这两个部分耦合度很高(不然我怎么把它当成一个组件呢哈哈哈),如下图所示:
本来C区域是一个组件,然后产品突然说,需要把这两个部分分开,把A移到C1的位置,C1移到A的位置(心里感觉到憋屈)。
这里我的第一个想法就是拆开来做成两个组件,但是问题来了,之前这两部分的耦合度很高,如果强制把它拆开成两个组件,那么这两个组件之间的交互必然会多很多。比如,C1改变了某个东西会影响到C2,那么C1需要触发事件通知父组件,父组件再调用C2的某个方法来更新状态。这种跨组件之间的通讯在组件之间频繁交互的情况下,将会是噩梦,而我这边却需要频繁的交互,所以如果把它拆分为两个组件,那么工作量和复杂度将会大大的增加。当然,你可以想到通过Event Hub的方式来实现两个组件之间的交互,但是根本问题还是没有实质性得得到解决。
那么,有什么方法可以做到不拆分成两个组件又能移动位置的方法呢,答案就是slot。以我的例子为例,把A和B作为C的内容分发,原来是这样的:
<A></A> <B></B> <C></C> 复制代码
改为slot以后是这样的
<C> <A slot="c1"></A> <B slot="c2"></B> </C> 复制代码
这样就能做到不把C模块拆分,又能调整位置了,以最小的代价完成需求~~。
总结
vue的slot不仅可以用来内容分发,还可以用来做位置调整。如果在需要拆分组件来做位置调整,又不想因为拆分耦合度很高的组件,可以考虑使用slot来进行位置调整。一点愚见,希望对大家有所帮助。
以上所述就是小编给大家介绍的《原来vue的slot可以这么玩转》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!
猜你喜欢:- 100人运维200个数据中心,可以吗?华为可以!
- Windows 上的应用程序在运行期间可以给自己改名(可以做 OTA 自我更新)
- c# – 为什么具有受保护修饰符的函数可以被覆盖并且可以在每个位置访问?
- 可以学习的电脑
- Kubernetes,原来可以如此简单
- go语言可以开发什么?
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
Effective Java 中文版
(美)Joshua Bloch / 潘爱民 / 机械工业出版社 / 2003-1 / 39.00元
本书介绍了在Java编程中57条极具实用价值的经验规则,这些经验规则涵盖了大多数开发人员每天所面临的问题的解决方案。通过对Java平台设计专家所使用的技术的全面描述,揭示了应该做什么,不应该做什么才能产生清晰、健壮的高效的代码。 本书中的每条规则都以简短、独立的小文章形式出现,这些小文章包含了详细而精确的建议,以及对语言中许多细微之处的深入分析,并通过例子代码加以进一步说明。贯穿全书的是通用......一起来看看 《Effective Java 中文版》 这本书的介绍吧!