基於vue監聽滾動事件實現錨點連結平滑滾動的方法,vue

來源:互聯網
上載者:User

基於vue監聽滾動事件實現錨點連結平滑滾動的方法,vue

基於vue監聽滾動事件,實現錨點連結平滑滾動

近日在做一個vue項目的餐飲模組,小編需要實現一個菜單列表顯示的功能(:左邊為菜單類別,右邊顯示相對應的菜品)

小編將此分為三個功能模組來實現(本來一張動畫就清晰明了,小編太笨,只得口述一下):

1.左邊點擊類別,右邊顯示相應類別的菜品列表(平滑滾動)
2.滾動右邊的捲軸,左邊對應的顯示當前樣式
3.若從別的頁面點擊菜品進來該頁面,則該菜品為指定效果

小編也是vue的初學者,在閱讀了大量的文章後,其中借鑒http://www.bkjia.com/article/110325.htm 該文章,收到了很多啟發後,結合我們的功能加以完善。小編的和借鑒的文章側重點不同,建議大家在看之前可以先看一下上面的,以便於梳理的更清楚。

:scrollTop(滾動之根本)

在初寫項目的嘗試過程中,小編一直改變的是document.body.scrollTop的值來實現滾動,但是後來逐漸發現很邪門,有時給其賦值並沒有作用,而且過程也很麻煩,又查閱了一些資料也沒有解決辦法,所以不得已放棄。

之後無意中看到:scrollTop, 便嘗試開始使用vue中的屬性直接進行綁定滾動的變數值,功能實現反而簡單了。下面詳細講述:

一、組件html結構:

結構布局很簡單,在此多說是想給大家講述清楚一點兒右邊菜品的結構,方便綁定:scrollTop屬性,小編就踩了這個坑...

注意看注釋::scrollTop 的位置改變菜品列表的scrollTop值,來實現相應的滾動

二、實現錨連結平滑滾動

該功能是參考之前博主的文章的,方法基本沒改什麼,簡單易懂,直接放代碼

jump(index){    const cateItem = document.querySelectorAll('.cate-item');    let total = cateItem[index].offsetTop;    let distance = this.container.scrollTop // 擷取到頂部的距離(this.container便是.cate-list,為了方便存起來了)    let step = total / 50;    this.isActive = index; // 菜單列表顯示當前樣式    const _this = this;    if (total > distance) {     smoothDown()    } else {     let newTotal = distance - total     step = newTotal / 50     smoothUp()    }    function smoothDown () {     if (distance < total) {     distance += step     _this.scrollTop = distance;     setTimeout(smoothDown, 10);     } else {     _this.scrollTop = total     }    }    function smoothUp () {     if (distance > total) {     distance -= step     _this.scrollTop = distance     setTimeout(smoothUp, 10)     } else {     _this.scrollTop = total     }    }     }

三、監聽滾動事件,修改錨點狀態

在vue中鉤子函數監聽菜品列表(this.container)的滾動事件,

 mounted(){   // 監聽scroll事件   const _this = this;   setTimeout(function(){    _this.currentStick();     const rightItem = document.querySelectorAll('.cate-item');    const catelist = document.querySelectorAll('.cate-list')[0];    var length = rightItem.length;    var height = rightItem[length-1].offsetHeight;    var scrollHeight = document.querySelectorAll('.cate-menu-wrapper')[0].offsetHeight;    // 設定最後一個類別菜品列表的高度(小於適配器高度的話與適配器等高),不然點擊錨點不能夠置頂    if(height < scrollHeight){     rightItem[length-1].style.height = scrollHeight+'px';    }     var arr =[];    rightItem.forEach(function(v, i){     arr.push({top: v.offsetTop, height: v.offsetHeight, index: i});    })    _this.itemVal = arr;     const cateList = document.querySelectorAll('.cate-list')[0];    cateList.addEventListener('scroll', _this.onScroll);    _this.container = cateList;   }, 500)  },

這裡寫的有點囉嗦了,設定setTimeout延遲是為了能夠擷取到元素(誰有好辦法快推薦給我),為了在滾動中能夠對應列表顯示錨點目前狀態,存了一個資料itemAll,存了該菜品類別地區的scrollTop,索引,高度。(囉嗦,太囉嗦了)

methods: { onScroll () {    var _this = this;    _this.itemVal.forEach(function(obj, i){     _this.scrollTop = _this.container.scrollTop;     if(_this.scrollTop >= obj.top && _this.scrollTop < (obj.top + obj.height-10)){      // scrollTop的移動位置要在類別的菜品列表中才顯示對應錨點的目前狀態      _this.isActive = obj.index;     }    })   },}

三、點擊菜品進入頁面,該菜品置頂的聯動效果(該功能其實有隱藏性的bug,我們項目已取消該功能)

currentStick(){     const {dishId} = this.$route.query;     const cateContent = document.querySelectorAll('.cate-content');     const _this = this;     cateContent.forEach(function(v, i){      if(v.id == dishId){       _this.scrollTop = v.offsetTop;       }     })   },

該功能用:scrollTop綁定的話便簡單了許多,之前用document.body.scrollTop 設定值一直沒有作用。

好了,基本上所有的代碼都帖出來了,說的應該也詳細吧(我儘力了),該方法感覺其實還是在操作dom元素和js,枉用vue。但是一時也沒有更好的辦法來實現。

以上就是本文的全部內容,希望對大家的學習有所協助,也希望大家多多支援幫客之家。

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.