Vue支持搜索与筛选的用户列表实现流程介绍
1. 常规风格的示例工程开发
首先新建一个名为 normal.html 的测试文件,在HTML文件的head标签中引入Vue框架并设置常规的模板字段如下:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Document</title> <script src="https://unpkg.com/vue@next"></script> <style> .container { margin: 50px; } .content { margin: 20px; } </style> </head> <body> <div id="Application"></div> <script> const App = Vue.createApp({ }) App.mount('#Application') </script> </body> </html>
为了方便逻辑的演示,我们先不添加样式,先从逻辑上梳理这样一个简单页面应用的开发思路。
第一步,设计页面的根组件的数据框架,分析页面的功能需求,主要有三个:能够渲染用户列表、能够根据输入的关键字进行检索。因此,我们至少需要三个响应式的数据:用户列表数据、性别筛选字段和关键词字段。
定义 组件的data选项如下:
data() { return { //性别筛选字段 sexFilter : -1, //展示的用户列表数据 showDatas : [], //搜索的关键词 sarchKey : "" } }
上面定义的属性中,sexFilter 字段的取值可以是 -1、0或1 。 -1表示全部,0表示性别男,1表示性别女。
第二步,思考页面需要支持的行为,首先从网络上请求用户数据,将其渲染到页面上(使用延时函数来模拟这一过程),要支持性别筛选功能,需要定义一个筛选函数来完成,同样要实现关键词检索功能,也需要定义一个检索函数。
定义组件的methods选项如下:
methods: { //获取用户数据 queryAllData() { this.showDatas = mock }, //进行性别筛选 filterData() { if(this.sexFilter == -1) { this.showDatas = mock }else { this.showDatas = mock.filter((data) => { return data.sex == this.sexFilter }) } }, //进行关键词检索 searchData() { if(this.searchKey.length == 0) { this.showDatas = mock }else { this.showDatas = mock.filter((data) => { //名称中包含输入的关键词则表示匹配成功 return data.name.indexOf(this.searchKey) != -1 }) } } }
对上面的代码进行汇总,mock变量是本地定义的模拟数据,方便我们测试效果,代码如下:
let mock = [ { name : "小王", sex : 0 }, { name : "小红", sex : 1 }, { name : "小李", sex : 1 }, { name : "小张", sex : 0 } ]
定义好了功能函数,我们需要在合适的时机对其进行调用,queryAllData 方法可以在组件挂载时调用来获取数据,当页面挂载后,延时3秒会获取到测试的模拟数据,代码如下:
mounted() { //模拟请求过程 setTimeout(() => { this.queryAllData }, 3000); },
对于性别筛选和关键词检索功能,可以监听对应的属性,当这些属性发生变化时,进行筛选或检索行为。定义组件的watch选项如下:
watch: { sexFilter(oldValue,newValue) { this.filterData() }, searchKey(oldValue,newValue) { this.searchData() } }
至此,我们编写完成当前页面应用的所有逻辑代码。还有第三步需要做,将页面渲染所需的HTML框架搭建完成,示例代码如下:
<div id="Application"> <div class="container"> <div class="content"> <input type="radio" :value="-1" v-model="sexFilter"/>全部 <input type="radio" :value="0" v-model="sexFilter"/>男 <input type="radio" :value="1" v-model="sexFilter"/>女 </div> <div class="content">搜索:<input type="text" v-model="searchKey" /></div> <div class="content"> <table border="1" width="300px"> <tr> <th>姓名</th> <th>性别</th> </tr> <tr v-for="(data, index) in showDatas"> <td>{{data.name}}</td> <td>{{data.sex == 0 ? '男' : '女'}}</td> </tr> </table> </div> </div> </div>
运行代码,可以看到一个支持筛选和检索的用户列表应用以及完成了,效果如下图所示:
2. 使用组合式API重构用户列表页面
在上一节中我们实现了完整的用户列表页面。深入分析我们编写的代码,可以发现需要关注的逻辑点十分分散,例如用户的性别筛选是一个独立的功能,要实现这样一个功能,需要先在data选项中定义属性,之后在methods选项中定义功能方法,最后在watch选项中监听属性,实现筛选功能。这些逻辑点的分离使得代码的可读性变差,并且随着项目的迭代,页面的功能可能会越来越复杂,对于后续此组建的维护者来说,扩展会变得更加困难。
Vue3提供的组合式API的开发风格可以很好的解决这个问题,我们可以将逻辑都梳理在setup方法中,相同的逻辑点聚合性更强,更易阅读和扩展。
使用组合式API重写后的完整代码如下:
let mock = [ { name:"小王", sex:0 },{ name:"小红", sex:1 },{ name:"小李", sex:1 },{ name:"小张", sex:0 } ] const App = Vue.createApp({ setup() { // 用户列表 const showDatas = Vue.ref([]) const queryAllData = () => { // 模拟请求过程 setTimeout(()=>{ showDatas.value = mock }, 3000); } // 组件挂载是请求数据 Vue.onMounted(queryAllData) let sexFilter = Vue.ref(-1) let searchKey = Vue.ref("") let filterData = () => { if (sexFilter.value == -1) { showDatas.value = mock } else { showDatas.value = mock.filter((data)=>{ return data.sex == sexFilter.value }) } } searchData = () => { if (searchKey.value.length == 0) { showDatas.value = mock } else { showDatas.value = mock.filter((data)=>{ return data.name.search(searchKey.value) != -1 }) } } // 添加侦听 Vue.watch(sexFilter, filterData) Vue.watch(searchKey, searchData) return { showDatas, searchKey, sexFilter } }, template: ` <div class="container"> <div class="content"> <input type="radio" :value="-1" v-model="sexFilter"/>全部 <input type="radio" :value="0" v-model="sexFilter"/>男 <input type="radio" :value="1" v-model="sexFilter"/>女 </div> <div class="content">搜索:<input type="text" v-model="searchKey" /></div> <div class="content"> <table border="1" width="300px"> <tr> <th>姓名</th> <th>性别</th> </tr> <tr v-for="(data, index) in showDatas"> <td>{{data.name}}</td> <td>{{data.sex == 0 ? '男' : '女'}}</td> </tr> </table> </div> </div> ` }) App.mount("#Application")
在使用组合式API编写代码时,特别要注意,对于需要使用的响应式数据,要使用 ref 方法或 reactive方法进行包装。
3. 优化用户列表页面
在上一节中我们通过组合式API重写了用户列表页面,但是现在页面筛选和搜索功能都比较生硬,在本节,我们尝试给他添加一些动画效果。
首先要实现列表动画效果,需要对定义的组件模板结果做一下改动,示例代码如下:
template: ` <div class="container"> <div class="content"> <input type="radio" :value="-1" v-model="sexFliter"/>全部 <input type="radio" :value="0" v-model="sexFliter"/>男 <input type="radio" :value="1" v-model="sexFliter"/>女 </div> <div class="content">搜索:<input type="text" v-model="searchKey" /></div> <div class="content"> <div class="tab" width="300px"> <div> <div class="item">姓名</div> <div class="item">性别</div> </div> <transition-group name="list"> <div v-for="(data, index) in showDatas" :key="data.name"> <div class="item">{{data.name}}</div> <div class="item">{{data.sex == 0 ? '男' : '女'}}</div> </div> </transition-group> </div> </div> </div> `
对应的,定义CSS样式与动画样式如下:
.container { margin: 50px; } .content { margin: 20px; } .tab { width: 300px; position: absolute; } .item { border: gray 1px solid; width: 148px; text-align: center; transition: all 0.8s ease; display: inline-block; } .list-enter-active { transition: all 1s ease; } .list-enter-from, .list-leave-to { opacity: 0; } .list-move { transition: transform 1s ease; } .list-leave-active { position: absolute; transition: all 1s ease; }
现在运行代码,可以看到当对用户列表进行筛选、搜索时,列表的变化以及有了动画过渡效果:
到此这篇关于Vue支持搜索与筛选的用户列表实现流程介绍的文章就介绍到这了,更多相关Vue用户列表内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!
相关文章
解决Electron store的commit和dispatch不好用问题
这篇文章主要介绍了解决Electron store的commit和dispatch不好用问题,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教2023-01-01vue button的@click方法无效钩子函数没有执行问题
这篇文章主要介绍了vue button的@click方法无效钩子函数没有执行问题及解决,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教2022-03-03使用axios发送post请求,将JSON数据改为form类型的示例
今天小编就为大家分享一篇使用axios发送post请求,将JSON数据改为form类型的示例,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧2019-10-10vue.nextTick()与setTimeout的区别及说明
这篇文章主要介绍了vue.nextTick()与setTimeout的区别及说明,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教2024-03-03
最新评论