W3Cschool
恭喜您成為首批注冊(cè)用戶
獲得88經(jīng)驗(yàn)值獎(jiǎng)勵(lì)
了解如何使用tabs組件完成選項(xiàng)卡頁(yè)簽的布局,靈活組合組件,配置屬性,優(yōu)化性能
通過本節(jié),你將學(xué)會(huì):
選項(xiàng)卡
效果常見于傳統(tǒng)H5開發(fā)中,開發(fā)者一般使用div和js代碼
控制布局交互得以實(shí)現(xiàn)
在框架中,開發(fā)者也可以使用div組件
實(shí)現(xiàn)簡(jiǎn)單的效果,示例代碼如下:
<template>
<div class="tutorial-page">
<!-- div組件模擬選項(xiàng)卡功能 -->
<div class="div-tabs">
<!-- tabs的head部分 -->
<div class="div-tabbar">
<text onclick="showContent(1)">menu1</text>
<text onclick="showContent(2)">menu2</text>
<text onclick="showContent(3)">menu3</text>
</div>
<!-- tabs的body部分 -->
<div class="div-tabcontent">
<div class="div-tabcontent-section" show="{{type === 'content_1'}}">
<text>content1</text>
</div>
<div class="div-tabcontent-section" show="{{type === 'content_2'}}">
<text>content2</text>
</div>
<div class="div-tabcontent-section" show="{{type === 'content_3'}}">
<text>content3</text>
</div>
</div>
</div>
</div>
</template>
<script>
export default {
data: {
type: 'content_1'
},
showContent (num) {
this.type = 'content_' + num;
}
}
</script>
使用div組件
實(shí)現(xiàn)的選項(xiàng)卡
效果,功能還是有限,為了帶來最佳用戶體驗(yàn),建議使用框架提供的tabs組件
完成需求
tabs
中封裝了常見功能和效果:頁(yè)簽支持橫向滾動(dòng),支持手勢(shì)滑動(dòng)切換內(nèi)容頁(yè)等
tabs
內(nèi)部?jī)H支持子組件tab-bar
和tab-content
,也可以只包含一個(gè)子組件,使用說明如下:
tab-bar組件
用來包含所有頁(yè)簽的標(biāo)題,屬性mode
用來配置是否可滾動(dòng),詳情請(qǐng)參考文檔:組件 -> 容器組件 -> tab-bar
tab-content組件
用來包含所有頁(yè)簽的內(nèi)容,詳情請(qǐng)參考文檔:組件 -> 容器組件 -> tab-content
tab-bar組件
的第n個(gè)直接子節(jié)點(diǎn)對(duì)應(yīng)tab-content
中第n個(gè)直接子節(jié)點(diǎn),具有聯(lián)動(dòng)效果示例代碼如下:
<template>
<div class="tutorial-page">
<!-- tabs組件 -->
<tabs>
<tab-bar class="tab-bar">
<text>menu1</text>
<text>menu2</text>
<text>menu3</text>
</tab-bar>
<tab-content class="tab-content">
<div class="tab-content-section">
<text>content1</text>
</div>
<div class="tab-content-section">
<text>content2</text>
</div>
<div class="tab-content-section">
<text>content3</text>
</div>
</tab-content>
</tabs>
</div>
</template>
注意:
tabs
內(nèi)不能再嵌套tabs
,如有此類需求,請(qǐng)參考教程第一部分div組件模擬選項(xiàng)卡
為了更好的組織頁(yè)面代碼,提升代碼可維護(hù)性。開發(fā)者可以將頁(yè)簽內(nèi)容通過自定義子組件
來渲染
關(guān)于如何開發(fā)子組件請(qǐng)參考文檔:父子組件通信 ,本小節(jié)僅做簡(jiǎn)單引入使用
示例代碼如下:
<import name="tab-content-item" src="./tabitem"></import>
<template>
<div class="tutorial-page">
<tabs onchange="onChangeTabIndex">
<tab-bar class="tab-bar">
<text>menu1</text>
<text>menu2</text>
<text>menu3</text>
</tab-bar>
<tab-content class="tab-content">
<tab-content-item index="0" itemdata="{{list[0]}}" current-index="{{currentIndex}}"></tab-content-item>
<tab-content-item index="1" itemdata="{{list[1]}}" current-index="{{currentIndex}}"></tab-content-item>
<tab-content-item index="2" itemdata="{{list[2]}}" current-index="{{currentIndex}}"></tab-content-item>
</tab-content>
</tabs>
</div>
</template>
<script>
export default {
data: {
list: [
{title: "content1"},
{title: "content2"},
{title: "content3"}
],
currentIndex: 0
},
onChangeTabIndex (evt) {
this.currentIndex = evt.index
}
}
</script>
在tabitem.ux
文件中:
<template>
<div class="tab-section">
<text>{{itemdata.title}}</text>
</div>
</template>
<style>
.tab-section {
flex: 1;
flex-direction: column;
justify-content: center;
background-color: #ffffff;
margin: 10px;
}
.tab-section text {
color: #FF0000;
text-align: center;
}
</style>
<script>
export default {
props: [
'index',
'itemdata',
// 駝峰式在賦值時(shí)使用-連接
'currentIndex'
],
onInit () {
// 監(jiān)聽屬性變化
this.$watch('currentIndex', 'watchCurrentIndex')
},
/**
* 監(jiān)聽用戶選擇的索引,選中當(dāng)前時(shí)觸發(fā)業(yè)務(wù)邏輯
* @param newValue
* @param oldValue
*/
watchCurrentIndex (newValue, oldValue) {
if (parseInt(this.index) === this.currentIndex) {
console.info(`當(dāng)前用戶選擇了這個(gè)標(biāo)簽:${this.index}, ${newValue}, ${oldValue}`)
}
}
}
</script>
一個(gè)內(nèi)容豐富的選項(xiàng)卡
,通常會(huì)包含許多頁(yè)簽內(nèi)容。如新聞?lì)悜?yīng)用中,可能會(huì)包括:推薦、熱點(diǎn)、視頻、段子、汽車、社會(huì)、娛樂等
直接使用tabs
默認(rèn)會(huì)加載所有頁(yè)簽內(nèi)容,導(dǎo)致JS線程持續(xù)忙于渲染每個(gè)頁(yè)簽,無(wú)法響應(yīng)用戶點(diǎn)擊事件等,造成體驗(yàn)困擾
為了解決這類問題,開發(fā)者可以讓頁(yè)簽內(nèi)容在用戶點(diǎn)擊時(shí)延遲渲染(而不是整個(gè)頁(yè)面初始化時(shí)渲染),這項(xiàng)功能可以通過if指令
完成
示例代碼如下:
<template>
<div class="tutorial-page">
<tabs onchange="onChangeTabIndex">
<tab-bar class="tab-bar" mode="scrollable">
<text for="{{tabHeadList}}" class="{{currentIndex === $idx ? 'active' : ''}}" >{{$item.title}}</text>
</tab-bar>
<tab-content class="tab-content">
<div class="tab-content-section" for="{{tabHeadList}}">
<!-- 初始化時(shí),if為false,默認(rèn)不做渲染;點(diǎn)擊后改為true -->
<text if="{{ renderTabContent($idx) }}">{{$item.title}}</text>
</div>
</tab-content>
</tabs>
</div>
</template>
<style lang="less">
.tutorial-page {
flex-direction: column;
justify-content: center;
align-items: center;
.tab-bar text{
padding: 0 25px;
text-align: center;
font-size: 34px;
}
.tab-bar .active {
color: #FF0000;
}
.tab-content {
flex: 1;
background-color: #eeeeee;
.tab-content-section {
flex: 1;
margin: 10px;
background-color: #ffffff;
justify-content: center;
text {
text-align: center;
color: #FF0000;
}
}
}
}
</style>
<script>
export default {
data: {
tabHeadList: [
{title: "推薦"},
{title: "熱門"},
{title: "視頻"},
{title: "段子"},
{title: "汽車"},
{title: "社會(huì)"},
{title: "娛樂"},
{title: "軍事"},
{title: "體育"},
{title: "NBA"},
{title: "財(cái)經(jīng)"}
],
currentIndex: 0
},
onInit(){
// 加載第一個(gè)頁(yè)簽內(nèi)容
this.changeTabIndex(0)
},
changeTabIndex(index) {
const item = Object.assign({}, this.tabHeadList[index])
item.render = true
this.tabHeadList.splice(index, 1, item)
},
onChangeTabIndex (evt) {
this.currentIndex = evt.index
this.changeTabIndex(evt.index)
},
renderTabContent (index) {
return !!this.tabHeadList[index].render
}
}
</script>
tabs
內(nèi)部可以僅包含tab-bar
或者tab-content
假設(shè)開發(fā)者有如下需求:開發(fā)一個(gè)簡(jiǎn)化的社交主頁(yè),其中,用戶圖標(biāo)和搜索圖標(biāo)為跳轉(zhuǎn)按鈕,點(diǎn)擊跳轉(zhuǎn)頁(yè)面;聊天、發(fā)現(xiàn)、通訊錄為頁(yè)簽,與內(nèi)容頁(yè)聯(lián)動(dòng),效果如下:
由于tabs
僅支持子組件tab-bar
與tab-content
,且tab-bar
與tab-content
的直接子元素都被當(dāng)做頁(yè)簽或內(nèi)容頁(yè)。因此,僅使用tabs
無(wú)法實(shí)現(xiàn)兩個(gè)圖標(biāo)按鈕
所以開發(fā)者可以這樣實(shí)現(xiàn):
tabs
中,僅使用tab-content
,包含選項(xiàng)卡
的所有內(nèi)容頁(yè)tabs
外,使用div
包含選項(xiàng)卡
頁(yè)簽標(biāo)題及圖標(biāo)按鈕,模擬tab-bar
tabs
的index屬性
,監(jiān)聽tabs
的change事件
,實(shí)現(xiàn)頁(yè)簽與內(nèi)容頁(yè)的聯(lián)動(dòng)示例代碼如下:
<template>
<div class="tutorial-page">
<!-- 靈活使用tabs組件 -->
<div class="flexible-tabs">
<!-- 自定義tab-bar組件 -->
<div class="flexible-tabbar">
<image src="./img/user.png" onclick="routePage('personal')"></image>
<text class="{{currentIndex === 0 ? 'active' : ''}}" onclick="clickTabBar(0)">聊天</text>
<text class="{{currentIndex === 1 ? 'active' : ''}}" onclick="clickTabBar(1)">發(fā)現(xiàn)</text>
<text class="{{currentIndex === 2 ? 'active' : ''}}" onclick="clickTabBar(2)">通訊錄</text>
<image src="./img/search.png" onclick="routePage('search')"></image>
</div>
<!-- 監(jiān)聽change事件,觸發(fā)時(shí)動(dòng)態(tài)修改tabs的index屬性 -->
<tabs onchange="changeTabactive" index="{{currentIndex}}">
<tab-content class="flexible-tab-content">
<div class="tab-content-section">
<text>聊天</text>
</div>
<div class="tab-content-section">
<text>發(fā)現(xiàn)</text>
</div>
<div class="tab-content-section">
<text>通訊錄</text>
</div>
</tab-content>
</tabs>
</div>
</div>
</template>
<style lang="less">
.tutorial-page {
flex: 1;
.flexible-tabs {
flex: 1;
flex-direction: column;
.flexible-tabbar {
height: 100px;
padding: 0 30px;
background-color: #f1f1f1;
align-items: center;
text {
flex-grow: 1;
height: 100px;
margin: 0 30px;
text-align: center;
border: 0px solid #f1f1f1;
border-bottom-width: 5px;
}
image {
height: 50px;
width: 50px;
resize-mode: contain;
}
.active {
color: #0faeff;
border-bottom-color: #0faeff;
}
}
.flexible-tab-content {
flex: 1;
.tab-content-section {
flex: 1;
background-color: #ffffff;
justify-content: center;
}
}
}
}
</style>
<script>
import router from '@system.router'
export default {
data: {
currentIndex: 0
},
changeTabactive (evt) {
this.currentIndex = evt.index
},
clickTabBar (index) {
this.currentIndex = index
},
routePage (param) {
router.push({
uri: param
})
}
}
</script>
選項(xiàng)卡需求很常見,熟悉tabs組件的使用,有助于:提升用戶體驗(yàn)、減少加載時(shí)間、優(yōu)化頁(yè)面性能
Copyright©2021 w3cschool編程獅|閩ICP備15016281號(hào)-3|閩公網(wǎng)安備35020302033924號(hào)
違法和不良信息舉報(bào)電話:173-0602-2364|舉報(bào)郵箱:jubao@eeedong.com
掃描二維碼
下載編程獅App
編程獅公眾號(hào)
聯(lián)系方式:
更多建議: