浏览了很多关于uniapp的自定义tabbar的文章,很多感觉都写的不详细,而且跨端能力都不怎么样,我自己研究整理了一下:
跨端支持:H5、app、微信小程序,
H5效果图如下:
微信小程序效果图如下:
app的效果图没有截取到,但应该是可行的。
目录结构如下:
page.json的配置如下:
{
"pages": [ //pages数组中第一项表示应用启动页,参考:https://uniapp.dcloud.io/collocation/pages
{
"path": "pages/index/index",
"style": {
"navigationBarTitleText": "首页"
}
},{
"path": "pages/dynamic/dynamic",
"style": {
"navigationBarTitleText": "发现"
}
},{
"path": "pages/release/release",
"style": {
"navigationBarTitleText": "发布"
}
},{
"path": "pages/friend/friend",
"style": {
"navigationBarTitleText": "朋友"
}
},{
"path": "pages/mine/mine",
"style": {
"navigationBarTitleText": "我的"
}
}
],
"globalStyle": {
"navigationBarTextStyle": "black",
"navigationBarTitleText": "uni-app",
"navigationBarBackgroundColor": "#F8F8F8",
"backgroundColor": "#F8F8F8"
},
"tabBar": {
"color": "#999999",
"selectedColor": "#66CCFF",
"borderStyle": "black",
"backgroundColor": "#ffffff",
"midButton": {
"text": "发布",
"pagePath": "pages/release/release",
"iconPath": "static/images/tabbar/release.png",
"selectedIconPath": "static/images/tabbar/release-select.png"
},
"list": [{
"pagePath": "pages/index/index",
"iconPath": "static/images/tabbar/index.png",
"selectedIconPath": "static/images/tabbar/index-select.png",
"text": "首页"
},{
"pagePath": "pages/dynamic/dynamic",
"iconPath": "static/images/tabbar/dynamic.png",
"selectedIconPath": "static/images/tabbar/dynamic-select.png",
"text": "发现"
},
// #ifndef APP-PLUS
{
"pagePath": "pages/release/release",
"iconPath": "static/images/tabbar/release.png",
"selectedIconPath": "static/images/tabbar/release-select.png",
"text": "发布"
},
// #endif
{
"pagePath": "pages/friend/friend",
"iconPath": "static/images/tabbar/friend.png",
"selectedIconPath": "static/images/tabbar/friend-select.png",
"text": "朋友"
},{
"pagePath": "pages/mine/mine",
"iconPath": "static/images/tabbar/mine.png",
"selectedIconPath": "static/images/tabbar/mine-select.png",
"text": "我的"
}]
}
}
注册全局组件tabbar在main.js文件中,配置如下:
import Vue from 'vue'
import App from './App'
import rwjTabbar from './components/rwj-tabbar.vue'
Vue.config.productionTip = false
//注册全局组件
Vue.component('rwj-tabbar', rwjTabbar);
App.mpType = 'app'
const app = new Vue({
...App
})
app.$mount()
rwj-tabbar.vue文件编写:
<template>
<view class="tabbar-container">
<block>
<view class="tabbar-item" v-for="(item,index) in tabbarList" :class="[item.centerItem ? ' center-item' : '']" @click="changeItem(item)">
<view class="item-top">
<image :src="currentItem==item.id?item.selectIcon:item.icon"></image>
</view>
<view class="item-bottom" :class="[currentItem==item.id ? 'item-active' : '']">
<text>{{item.text}}</text>
</view>
</view>
</block>
</view>
</template>
<script>
export default {
props:{
currentPage: {
type: Number,
default: 0
}
},
data() {
return {
currentItem: 0,
tabbarList: [
{
id: 0,
path: "/pages/index/index",
icon: "/static/images/tabbar/index.png",
selectIcon: "/static/images/tabbar/index-select.png",
text: "首页",
centerItem: false
},{
id: 1,
path: "/pages/dynamic/dynamic",
icon: "/static/images/tabbar/dynamic.png",
selectIcon: "/static/images/tabbar/dynamic-select.png",
text: "动态",
centerItem: false
},{
id: 2,
path: "/pages/release/release",
icon: "/static/images/tabbar/release.png",
selectIcon: "/static/images/tabbar/release-select.png",
text: "发布",
centerItem: true
},{
id: 3,
path: "/pages/friend/friend",
icon: "/static/images/tabbar/friend.png",
selectIcon: "/static/images/tabbar/friend-select.png",
text: "朋友",
centerItem: false
},{
id: 4,
path: "/pages/mine/mine",
icon: "/static/images/tabbar/mine.png",
selectIcon: "/static/images/tabbar/mine-select.png",
text: "我的",
centerItem: false
}
]
};
},
mounted(){
this.currentItem = this.currentPage;
uni.hideTabBar();
},
methods: {
changeItem(item){
let _this = this;
//_this.currentItem = item.id;
uni.switchTab({
url: item.path
});
}
}
}
</script>
<style>
view{
padding: 0;
margin: 0;
box-sizing: border-box;
}
.tabbar-container{
position: fixed;
bottom: 0;
left: 0;
width: 100%;
height: 110rpx;
box-shadow: 0 0 5px #999;
display: flex;
align-items: center;
padding: 5rpx 0;
color: #999999;
}
.tabbar-container .tabbar-item{
width: 20%;
height: 100rpx;
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
text-align: center;
}
.tabbar-container .item-active{
color: #66CCFF;
}
.tabbar-container .center-item{
display: block;
position: relative;
}
.tabbar-container .tabbar-item .item-top{
width: 70rpx;
height: 70rpx;
padding: 10rpx;
}
.tabbar-container .center-item .item-top{
flex-shrink: 0;
width: 100rpx;
height: 100rpx;
position: absolute;
top: -50rpx;
left: calc(50% - 50rpx);
border-radius: 50%;
box-shadow: 0 0 5px #999;
background-color: #ffffff;
}
.tabbar-container .tabbar-item .item-top image{
width: 100%;
height: 100%;
}
.tabbar-container .tabbar-item .item-bottom{
font-size: 28rpx;
width: 100%;
}
.tabbar-container .center-item .item-bottom{
position: absolute;
bottom: 5rpx;
}
</style>
index.vue文件中引入tabbar:
<!-- #ifndef APP-PLUS -->
<rwj-tabbar :current-page="0"></rwj-tabbar>
<!-- #endif -->
补充说明:
由于app端不支持uni.hideTabBar();,所以在app端不需要使用自定义组件,而且app端uniapp原生的就支持中间凸起,所以app是使用的原生的tabbar