91超碰碰碰碰久久久久久综合_超碰av人澡人澡人澡人澡人掠_国产黄大片在线观看画质优化_txt小说免费全本

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

基于vue的tab-list類目切換商品列表組件的示例代碼

發布時間:2020-09-20 22:48:00 來源:腳本之家 閱讀:272 作者:小紅衣 欄目:web開發

在大多數電商場景中,頁面都會有類目切換加上商品列表的部分,頁面大概會長這樣

基于vue的tab-list類目切換商品列表組件的示例代碼

基于vue的tab-list類目切換商品列表組件的示例代碼

每次寫類似場景的時候,都需要去為類目商品列表寫很多邏輯,為了提高開發效率我決定將這一部分抽離成組件。

實現

1.樣式

所有tab欄的樣式和商品列表的樣式都提供插槽,供業務自己定制

2.變量

isTabFixed: false,//是否吸頂
tab: 1,//當前tab
page: 1,//當前頁數
listStatus: {
 finished: false,//是否已是最后一頁
 loading: false,//是否加載中
},
items: [],//商品數組
tabMap: [],//tab列表數組
cache:{},//緩存
listName: '',//商品列表名稱
tabName: '',//tab列表名稱
apiName: '',//api方法名稱
queryName: '',//api請求參數名稱

3.緩存設計

為了減少消耗,已經請求過的商品列表我都將他們緩存下來

_addCache(proList) {
 cache[this.tab] = {
 finished: this.listStatus.finished,
 page: this.page,
 list: proList,
 };
},

4.請求數據

_getList(type) {
 let data = {};
 data[this.queryName] = this.tab;
 data.page = this.page;
 this.$http[this.apiName](data)
 .then((res) => {
 this.listStatus.finished = !res.has_more;//更新是否是最后一頁的狀態
 this._handleData(res.items);//處理得到的商品列表
 })
 .catch((err) => {
 note(err.message || '出錯啦');
 });
},
_handleData(proList) {
 if (this.page === 1) {//表示是tab切換時請求的數據,所以直接將items的指向切換
 this.items = proList;
 } else {//因為是翻頁,所以需要把數據拼接
 this.items = this.items.concat(proList);
 }
 this.$store.setData(this.listName, this.items);//把數據更新給父組件
 this._addCache(this.items);//把數據加入緩存
},

5.操作

邏輯部分主要分兩塊:一是列表翻頁,二是tab相關

列表翻頁

這部分的邏輯比較簡單,主要分兩點

  1. 將page加一
  2. 請求數據
_loadmore() {
 this.page = this.page + 1;
 this._getList();
},

其實對于手機列表的上拉翻頁操作,還有很多的點要去注意,比如如何去避免連續請求等,由于我將這些交給了另一個專注列表渲染的組件,這里就不需要再去考慮這些操作。

tab相關

tab切換

tab切換的時候主要是兩點

  1. 切換tab的指向
  2. 切換items的指向
  • 已經加載過的列表從緩存中取
  • 沒有加載過的請求數據 然后還有兩個體驗上的點
  1. 視圖應該回到頂部
  2. 切換的時候應該獲取切換列表的第一頁數據
changeTab(id) {
 this.tab = id;
 this.$store.setData(this.tabName, this.tab);//將tab的指向同步給父組件
 this._scrollToTab();//視圖回到頂部
 if (cache[this.tab]) {
 const target = cache[this.tab];
 this.listStatus.finished = target.finished;
 this.page = target.page;
 this.items = target.list;
 this.$store.setData(this.listName, this.items);//將商品列表同步給父組件
 } else {
 this.page = 1;
 this._getList();
 }
},
//視圖回到頂部
_scrollToTab() {
 let scrollTop = document.documentElement.scrollTop || document.body.scrollTop;
 let productsTop = this.$refs.products.$el.offsetTop;//商品列表距離頂部的距離
 let topHeight = this.$refs.tabNav.offsetHeight;//tab欄的高度
 if (scrollTop > productsTop) {
 window.scrollTo(0, productsTop - topHeight);
 }
},

吸頂

在吸頂的時候,需要對tab欄的樣式做一些小小的變動,所以需要一個變量來知道是否吸頂了

handleNavFixed() {
 this.stickyTop = this.$store.getData('stickyTop') || 0;//吸頂的高度
 window.onscroll = (e) => {
 let top = document.documentElement.scrollTop || document.body.scrollTop;
 let tabHeight = this.$refs.tabNav.offsetTop - top - 1;
 if (tabHeight <= this.stickyTop && !this.isTabFixed) {//結合判斷為了避免重復計算
 this.isTabFixed = true;
 }
 if (tabHeight >= this.stickyTop && this.isTabFixed) {
 this.isTabFixed = false;
 }
 };
},

6.組件相關

作為一個組件,不同點在于需要做到的是可用性和通用性。 對于組件如何更好的得到父組件的值并把更新的值傳回父組件方面,是我在開發過程中的一個卡點,最后我用了一套基于vue的組件通行機制。這種通行機制的實現網上很多,這里就不詳細說了。通行機制主要有兩個功能

  • 各組件間可以互相調用方法
  • 各個組件都可以得到和更新父組件的數據

由于將tab列表都作為插槽傳入,所以初始數據并不需要關心,需要關心的只是更新數據。

對于不同的頁面,tab列表的名稱,tab定位的名稱,商品列表的名稱,接口的名稱,請求接口的參數都可以會不一樣,所以我在這里將這些項作為參數,在初始化這個組件的時候需要傳入

//組件部分
init(data = {}) {
 this.listStatus.finished = !data.hasMore;
 this.tabName = data.tabName;
 this.listName = data.listName;
 this.apiName = data.apiName;
 this.queryName = data.queryName;
 this.handleNavFixed();//判斷是否吸頂
},
//調用組件
this.$bus.emit('tab-list.init', {
 tabName: 'tab',
 listName: 'items',
 apiName: 'homeList',
 queryName: 'tab_id',
 hasMore: this.hasMore,
});

總結

以上所述是小編給大家介紹的基于vue的tab-list類目切換商品列表組件的示例代碼,希望對大家有所幫助!

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

昆山市| 淮安市| 江源县| 安塞县| 涡阳县| 武夷山市| 克什克腾旗| 资兴市| 灌云县| 丰原市| 松滋市| 武强县| 十堰市| 桐梓县| 乐亭县| 南靖县| 南城县| 东方市| 宣威市| 湟中县| 沙湾县| 连山| 申扎县| 黔南| 临邑县| 东台市| 青河县| 桑日县| 枞阳县| 新干县| 吉安县| 博乐市| 鄂州市| 两当县| 清丰县| 肃南| 宜昌市| 怀柔区| 天水市| 郧西县| 托里县|