vue仿美團側邊菜單組件
阿新 • • 發佈:2019-01-19
日常 子類 () 內容 get 定時器 curd 類型 使用
這樣一個組件的話我們是經常都能看到的,也經常都會用到,日常積累
首先從我們的布局開始,布局當然是越簡單越好。我們是可以看到左邊一個列表,固定不變的,右邊是一個彈出菜單,菜單根據左邊的每一欄獲得不同的值,展示不同的內容,當然我這個gif圖做得比較垃圾。大概明白這個意思就好
那麽我看看這個布局怎麽做
<template> <div class="m-menu"> <dl class="nav" @mouseleave=‘mouseleave‘> //將方法綁定到父級 <dt>全部分類</dt> <dd> //這樣我們就能根據當前的type去循環 <i :class="item.type" />第一個<span class="arrow" /> </dd> </dl> // 上面這個就是我們看到的左側的菜單列表 <div> <template > // 這裏放右側的子類列表 <h4 >美食</h4> <span>燒烤</span> </template> </div> </div> </template>
布局就這樣兩塊兒就可以了,然後看下數據結構
data() { return {
kind:‘‘,
menu: [{ type: ‘food‘, name: ‘美食‘, child:[{ // 這個child 就是我們右側子類菜單需要展示的title和列表數據 title:‘美食‘, child:[‘代金券‘,‘葡萄幹‘,‘火鍋‘,‘快餐‘,‘小吃‘] }] }, { type: ‘takeout‘, name: ‘外賣‘, child:[{ title:‘外賣‘, child:[‘幹鍋‘,‘快餐‘,‘中餐‘,‘小炒‘,‘湯品‘] }] }, { type: ‘hotel‘, name: ‘酒店‘, child:[{ title:‘酒店星級‘, child:[‘經濟型‘,‘舒適型‘,‘三星‘,‘四星‘,‘五星‘] }] }, { type: ‘hotel‘, name: ‘酒店‘, child:[{ title:‘酒店星級‘, child:[‘經濟型‘,‘舒適型‘,‘三星‘,‘四星‘,‘五星‘] }] }] } }
現在的話我們就可以去循環menu數據
<dd v-for=‘item in menu‘ :key=‘item.id‘> // 首先獲取到小圖標的type值 然後獲取name <i :class="item.type" />{{ item.name }} <span class="arrow" /> </dd>
緊接著我們得循環右側的菜單詳情
<div class="detail" v-if=‘kind‘ @mouseenter=‘sover‘ @mouseleave=‘sout‘> <template v-for="(item,index) in curdetail.child"> //curdetail 是我們遍歷鼠標移入的是哪個左側的item,然後添加 <h4 :key="index">{{ item.title }}</h4> <span v-for="list in item.child" :key="list.id">{{ list }}</span> </template> </div>
現在需要做的就是遍歷數組,這裏使用了原生的filter方法過濾數組
computed: { curdetail:function(){
return this.menu.filter((item)=>item.type === this.kind)[0] // 利用filter過濾了item數組,拿到type並添加到kind,這樣就拿到了側邊菜單的數據
} },
現在這個就成了,接下來需要實現鼠標移入移出了,首先鼠標離開的時候
我們先定義一個事件
methods: { mouseleave(){
let index = this;
index._timer=setTimout(()=>{
index.kind=‘‘ 鼠標離開的時候我們在200毫秒後清空kind,kind就是我們通過過濾獲取到右側菜單數據,這個方法是綁定到右側導航欄上的
},200)
}}
上面我們過濾了數組,現在我們需要將過濾的數組使用了,判斷鼠標移入的是哪個i
enter:function(e){ //鼠標移入 獲取當前 i上面的type值 然後賦值給kind this.kind=e.target.querySelector(‘i‘).className //這裏使用了target.querySelector這個原生dom選擇器 用來獲取當前i的className,然後賦給當前的kind },
接下來還要處理下鼠標移入子級後,不能讓子級菜單小時
sover:function(){ clearTimeout(this._timer) // 清除定時器 },sout:function(){ // 當鼠標離開的時候 清空kind值 this.kind=‘‘ }
,這樣一個側邊菜單組件完成,完整代碼如下
<template> <div class="m-menu"> <dl class="nav" @mouseleave="mouseleave"> <dt>全部分類</dt> <dd v-for="item in menu" :key="item.id" @mouseenter="enter" > <i :class="item.type" />{{ item.name }} <span class="arrow" /> </dd> </dl> <div v-if="kind" class="detail" @mouseenter="sover" @mouseleave="sout" > <template v-for="(item,index) in curdetail.child"> <h4 :key="index">{{ item.title }}</h4> <span v-for="list in item.child" :key="list.id">{{ list }}</span> </template> </div> </div> </template> <script> export default { data() { return { kind:‘‘, //鼠標移入類型 menu: [{ type: ‘food‘, name: ‘美食‘, child:[{ title:‘美食‘, child:[‘代金券‘,‘葡萄幹‘,‘火鍋‘,‘快餐‘,‘小吃‘] }] }, { type: ‘takeout‘, name: ‘外賣‘, child:[{ title:‘外賣‘, child:[‘幹鍋‘,‘快餐‘,‘中餐‘,‘小炒‘,‘湯品‘] }] }, { type: ‘hotel‘, name: ‘酒店‘, child:[{ title:‘酒店星級‘, child:[‘經濟型‘,‘舒適型‘,‘三星‘,‘四星‘,‘五星‘] }] }, { type: ‘hotel‘, name: ‘酒店‘, child:[{ title:‘酒店星級‘, child:[‘經濟型‘,‘舒適型‘,‘三星‘,‘四星‘,‘五星‘] }] }] } }, computed: { curdetail:function(){ //判斷當前數據 並遍歷 return this.menu.filter((item)=>item.type === this.kind)[0] // 用 filer過濾item數組,並拿到type 然後添加到kind } }, methods: { mouseleave:function(){ //鼠標離開的時候 let self = this; self._timer = setTimeout(() => { self.kind = ‘‘ }, 150); }, enter:function(e){ //鼠標移入 獲取當前 i上面的type值 然後賦值給kind this.kind=e.target.querySelector(‘i‘).className }, // 鼠標移入子級 sover:function(){ clearTimeout(this._timer) }, sout:function(){ this.kind=‘‘ } } } </script> <style scoped lang="scss"> @import "@/assets/css/index/index.scss"; </style>
vue仿美團側邊菜單組件