美文网首页我的Vue学习之路
Vue 如何实现一个底部导航栏组件

Vue 如何实现一个底部导航栏组件

作者: QYiZHong | 来源:发表于2018-11-04 12:00 被阅读601次

    演示效果

    演示效果

    可以看到父组件是知道我点击了底部TabBar的哪个item的。

    实现

    实现template 和style

    我用的布局工具是bootstrap,图标是阿里巴巴的iconfont

    <template>
        <div id="TabBar" class="tab-bar row">
            <div class="col-xs-4 tab-bar-item">
                <div class="row">
                    <i class="iconfont icon-daohangshouye"></i>
                </div>
                <div class="row">
                    <span>首页</span>
                </div>
            </div>
            <div class="col-xs-4 tab-bar-item">
                <div class="row">
                    <i class="iconfont icon-shangjia"></i>
                </div>
                <div class="row">
                    <span>商户</span>
                </div>
            </div>
            <div class="col-xs-4 tab-bar-item">
                <div class="row">
                    <i class="iconfont icon-huiyuan"></i>
                </div>
                <div class="row">
                    <span>我的</span>
                </div>
            </div>
        </div>
    </template>
    
    <style scoped>
        .tab-bar {
            background-color: white;
            height: 54px;
            border: 0 solid rgb(210, 210, 210);
            border-top-width: 1px;
            position: fixed;
            margin: auto;
            bottom: 0;
            width: 100%;
        }
    
        .tab-bar-item {
            height: 54px;
        }
    
        i {
            font-size: 25px;
        }
    </style>
    

    实现点击事件

    在每个tab-bar-item的div上添加@click绑定点击事件并且传递当前是哪个item,第一个item就可以传一个tag=0的参数。实现如下:

    <div class="col-xs-4 tab-bar-item" @click="didClickedItem(0)">
        <div class="row">
            <i class="iconfont icon-daohangshouye"></i>
        </div>
        <div class="row">
            <span>首页</span>
        </div>
    </div>
    
    didClickedItem: function (tag) {
                    if (tag === 0) {
    
                    } else if (tag === 1) {
    
                    } else if (tag === 2) {
                        
                    }
                }
    

    点击完肯定需要让那个item进入选中的状态,也就是变亮,可以通过v-bind:class去做。data存一个数组放bool变量,因为第一个item肯定默认点亮,所以数组第一个元素为true。每次点击别的item时先把数组元素全部置位false,然后把选中的item所对应的数组元素改为true就可以实现选中效果。实现如下:

    data: function () {
                return {
                    actives: [true, false, false]
                }
            }
    
    <div class="col-xs-4 tab-bar-item" @click="didClickedItem(0)" v-bind:class="{active: actives[0]}">
        <div class="row">
            <i class="iconfont icon-daohangshouye"></i>
        </div>
        <div class="row">
            <span>首页</span>
        </div>
    </div>
    
    didClickedItem: function (tag) {
                    this.actives = this.actives.map(function () {
                        return false;
                    });
                    this.actives[tag] = true;
                }
    
    .active {
            color: #1E90FF;
        }
    

    对外暴露方法

    选中一个item肯定需要让父组件知道你选了什么,所以肯定要对外暴露方法,这个方法在didClickedItem这个方法最后一行加一行代码即可

    # TabBar组件里
    this.$emit('select-item', tag);
    
    # 父组件使用方法
    <template>
      <div id="app">
        <div style="font-size: 20px">{{item}}</div>
        <TabBar @select-item="onClickTabBarItem"/>
      </div>
    </template>
    
    <script>
    import TabBar from './components/TabBar'
    
    export default {
        name: 'app',
        data: function () {
            return {
                item: 0
            }
        },
        components: {
            TabBar
        },
        methods: {
            onClickTabBarItem: function (tag) {
                this.item = tag;
            }
        }
    }
    </script>
    

    完整代码

    <template>
        <div id="TabBar" class="tab-bar row">
            <div class="col-xs-4 tab-bar-item" @click="didClickedItem(0)" v-bind:class="{active: actives[0]}">
                <div class="row">
                    <i class="iconfont icon-daohangshouye"></i>
                </div>
                <div class="row">
                    <span>首页</span>
                </div>
            </div>
            <div class="col-xs-4 tab-bar-item" @click="didClickedItem(1)" v-bind:class="{active: actives[1]}">
                <div class="row">
                    <i class="iconfont icon-shangjia"></i>
                </div>
                <div class="row">
                    <span>商户</span>
                </div>
            </div>
            <div class="col-xs-4 tab-bar-item" @click="didClickedItem(2)" v-bind:class="{active: actives[2]}">
                <div class="row">
                    <i class="iconfont icon-huiyuan"></i>
                </div>
                <div class="row">
                    <span>我的</span>
                </div>
            </div>
        </div>
    </template>
    
    <script>
        export default {
            name: "TabBar",
            props: {
    
            },
            data: function () {
                return {
                    actives: [true, false, false]
                }
            },
            methods: {
                didClickedItem: function (tag) {
                    if (tag === 0) {
                        this.actives = this.actives.map(function () {
                            return false;
                        });
                        this.actives[0] = true;
                    } else if (tag === 1) {
                        this.actives = this.actives.map(function () {
                            return false;
                        });
                        this.actives[1] = true;
                    } else if (tag === 2) {
                        this.actives = this.actives.map(function () {
                            return false;
                        });
                        this.actives[2] = true;
                    }
                    this.$emit('select-item', tag);
                }
            }
        }
    </script>
    
    <style scoped>
        .tab-bar {
            background-color: white;
            height: 54px;
            border: 0 solid rgb(210, 210, 210);
            border-top-width: 1px;
            position: fixed;
            margin: auto;
            bottom: 0;
            width: 100%;
        }
    
        .tab-bar-item {
            height: 54px;
        }
    
        .active {
            color: #1E90FF;
        }
    
        i {
            font-size: 25px;
        }
    </style>
    

    相关文章

      网友评论

        本文标题:Vue 如何实现一个底部导航栏组件

        本文链接:https://www.haomeiwen.com/subject/tierxqtx.html