Vue3 H5、原生微信小程序与 UniApp 自定义 TabBar 实现详解

Vue3 H5、原生微信小程序与 UniApp 自定义 TabBar 实现详解

在移动端开发中,TabBar 是常见的导航组件之一。无论是 H5 页面、微信小程序还是跨平台框架 UniApp,都支持自定义 TabBar 的实现。本文将分别介绍如何在 Vue3 H5原生微信小程序UniApp(兼容 H5 和微信小程序) 中实现自定义 TabBar,并对比其差异。


✅ 一、Vue3 H5 自定义 TabBar 实现

📦1. 安装依赖

确保你已经创建了一个 Vue3 项目(使用 Vite 或 Vue CLI),无需额外安装依赖。

npm create vue@latest

📦2. 组件结构

components/CustomTabBar.vue
<template>
  <div class="tab-bar">
    <div 
      v-for="item in tabs" 
      :key="item.name"
      class="tab-item"
      :class="{ active: activeTab === item.name }"
      @click="switchTab(item)"
    >
      <img :src="activeTab === item.name ? item.activeIcon : item.icon" />
      <span>{{ item.label }}</span>
    </div>
  </div>
</template>

<script setup>
import { ref } from 'vue';

const props = defineProps({
  tabs: {
    type: Array,
    required: true
  }
});

const emit = defineEmits(['switch']);

const activeTab = ref(tabs[0].name);

function switchTab(item) {
  activeTab.value = item.name;
  emit('switch', item.name);
}
</script>

<style scoped>
.tab-bar {
  display: flex;
  justify-content: space-around;
  align-items: center;
  height: 60px;
  background-color: #fff;
  border-top: 1px solid #eee;
  position: fixed;
  bottom: 0;
  left: 0;
  right: 0;
}

.tab-item {
  text-align: center;
  color: #999;
}

.tab-item.active {
  color: #4CAF50;
}

.tab-item img {
  width: 24px;
  height: 24px;
}
</style>
使用示例:App.vue
<template>
  <div style="margin-bottom: 60px;">
    <!-- 页面内容 -->
    <component :is="currentView" />
  </div>
  <CustomTabBar 
    :tabs="tabs" 
    @switch="handleSwitch" 
  />
</template>

<script setup>
import CustomTabBar from './components/CustomTabBar.vue';
import Home from './views/Home.vue';
import Category from './views/Category.vue';
import Mine from './views/Mine.vue';

const currentView = ref('Home');

const tabs = [
  {
    name: 'Home',
    label: '首页',
    icon: '/icons/home.png',
    activeIcon: '/icons/home_active.png'
  },
  {
    name: 'Category',
    label: '分类',
    icon: '/icons/category.png',
    activeIcon: '/icons/category_active.png'
  },
  {
    name: 'Mine',
    label: '我的',
    icon: '/icons/mine.png',
    activeIcon: '/icons/mine_active.png'
  }
];

function handleSwitch(tabName) {
  currentView.value = tabName;
}
</script>

🧩二、原生微信小程序自定义 TabBar 实现

微信小程序默认提供了 tabBar 配置,但不支持动态修改或完全自定义样式。因此我们通常采用自定义 TabBar 方式。

📦1. 配置页面禁用默认 TabBar

app.json 中设置:

{
  "pages": ["pages/index/index", "pages/logs/logs"],
  "window": {
    "navigationBarTitleText": "Demo"
  },
  "style": "v2",
  "sitemapLocation": "sitemap.json"
}

📦2. 创建自定义 TabBar 组件

/components/custom-tabbar.js
Component({
  data: {
    activeTab: 'index',
    tabs: [
      {
        name: 'index',
        label: '首页',
        icon: '/images/icon_home.png',
        activeIcon: '/images/icon_home_active.png'
      },
      {
        name: 'logs',
        label: '日志',
        icon: '/images/icon_logs.png',
        activeIcon: '/images/icon_logs_active.png'
      }
    ]
  },
  methods: {
    switchTab(e) {
      const name = e.currentTarget.dataset.name;
      this.setData({ activeTab: name });
      wx.switchTab({
        url: `/pages/${name}/${name}`
      });
    }
  }
});
/components/custom-tabbar.wxml
<view class="tab-bar">
  <block wx:for="{{tabs}}" wx:key="name">
    <view 
      class="tab-item {{activeTab === item.name ? 'active' : ''}}"
      bindtap="switchTab"
      data-name="{{item.name}}"
    >
      <image src="{{activeTab === item.name ? item.activeIcon : item.icon}}" mode="aspectFit"></image>
      <text>{{item.label}}</text>
    </view>
  </block>
</view>
/components/custom-tabbar.wxss
.tab-bar {
  display: flex;
  justify-content: space-around;
  align-items: center;
  height: 50px;
  background-color: white;
  border-top: 1px solid #eee;
  position: fixed;
  bottom: 0;
  left: 0;
  right: 0;
}

.tab-item {
  text-align: center;
  color: #999;
}

.tab-item.active {
  color: #4CAF50;
}

.tab-item image {
  width: 24px;
  height: 24px;
}

📦3. 在页面中引入组件

/pages/index/index.json
{
  "usingComponents": {
    "custom-tabbar": "/components/custom-tabbar"
  }
}
/pages/index/index.wxml
<view style="margin-bottom: 50px;">
  <!-- 页面内容 -->
</view>
<custom-tabbar />

🎨三、UniApp 实现微信小程序 + H5 自定义 TabBar

UniApp 支持多端编译,我们可以编写一套代码适配多个平台。

📦1. 创建自定义 TabBar 组件

/components/custom-tabbar.vue
<template>
  <view class="tab-bar">
    <view 
      v-for="item in tabs" 
      :key="item.name"
      class="tab-item"
      :class="{ active: activeTab === item.name }"
      @click="switchTab(item)"
    >
      <image :src="activeTab === item.name ? item.activeIcon : item.icon" mode="aspectFit" />
      <text>{{ item.label }}</text>
    </view>
  </view>
</template>

<script setup>
import { ref } from 'vue';

const props = defineProps({
  tabs: {
    type: Array,
    required: true
  }
});

const emit = defineEmits(['switch']);

const activeTab = ref(tabs[0].name);

function switchTab(item) {
  activeTab.value = item.name;
  emit('switch', item.name);
}
</script>

<style lang="scss">
.tab-bar {
  display: flex;
  justify-content: space-around;
  align-items: center;
  height: 50px;
  background-color: white;
  border-top: 1px solid #eee;
  position: fixed;
  bottom: 0;
  left: 0;
  right: 0;
}

.tab-item {
  text-align: center;
  color: #999;
}

.tab-item.active {
  color: #4CAF50;
}

.tab-item image {
  width: 24px;
  height: 24px;
}
</style>
</style>

📦2. 页面中使用组件

/pages/index/index.vue
<template>
  <view style="margin-bottom: 50px;">
    <!-- 页面内容 -->
  </view>
  <custom-tabbar 
    :tabs="tabs" 
    @switch="handleSwitch" 
  />
</template>

<script setup>
import CustomTabBar from '@/components/custom-tabbar.vue';

const tabs = [
  {
    name: 'home',
    label: '首页',
    icon: require('@/static/icons/home.png'),
    activeIcon: require('@/static/icons/home_active.png')
  },
  {
    name: 'mine',
    label: '我的',
    icon: require('@/static/icons/mine.png'),
    activeIcon: require('@/static/icons/mine_active.png')
  }
];

function handleSwitch(name) {
  uni.switchTab({
    url: `/pages/${name}/${name}`
  });
}
</script>

📦3. 配置页面为 TabBar 页面

pages.json 中配置:

{
  "pages": [
    {
      "path": "pages/index/index",
      "style": {
        "navigationBarTitleText": "首页"
      }
    },
    {
      "path": "pages/mine/mine",
      "style": {
        "navigationBarTitleText": "我的"
      }
    }
  ],
  "globalStyle": {
    "navigationStyle": "custom"
  }
}

注意:navigationStyle: "custom" 表示隐藏原生导航栏,以便自定义 TabBar 正常显示。


四、总结

平台是否支持原生 TabBar是否支持自定义实现方式
Vue3 H5Vue 组件
微信小程序自定义组件
UniApp✅(需配置)多端组件
  • Vue3 H5:使用 Vue3 的响应式系统和组件化开发,实现灵活。
  • 微信小程序:通过自定义组件实现,注意生命周期与 API 调用。
  • UniApp:利用 Vue3 语法结合 UniApp 的多端能力,一套代码运行多个平台。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值