uni-app滑动/点击切换tab组件,动态数据内容获取swiper动态高度

本文介绍了一个uni-app中用于滑动和点击切换tab的组件实现,组件包含一个可滚动的tab栏和一个swiper容器。当切换tab时,组件会动态调整swiper的高度以适应内容。在加载动态数据后,通过调用组件提供的接口`getElementHeight`来获取并设置swiper的高度,确保内容正确显示。此外,展示了如何在父组件中引入并使用该组件,以及如何响应tab切换事件。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

可以点击切换tab也可以滑动切换tab

1.定义一个tabbar.vue,代码如下

<template>
    <view class="tabs">
        <view style="position:fixed;z-index:20;">
            <scroll-view id="tab-bar" class="scroll-h" :scroll-x="true" :show-scrollbar="false" :scroll-into-view="scrollInto">
                <view style="" :class="{'tabCenter':tabBars.length<4}">
                    <view v-for="(tab,index) in tabBars" :key="tab.id" class="uni-tab-item" :id="tab.id"
                        :data-current="index" @click="ontabtap">
                        <text class="uni-tab-item-title"
                            :class="tabIndex==index ? 'uni-tab-item-title-active' : ''">{{tab.name}}<text v-if="tab.count">({{tab.count}})</text></text>
                        <view class="uni-tab-item-line" v-if="tabIndex==index"></view>
                    </view>
                </view>
            </scroll-view>
            <slot name="center"></slot>
        </view>
        <swiper :current="tabIndex" class="swiper-box" style="flex: 1;min-height:calc(100vh - 200rpx - 142rpx);margin-top:184rpx;" :duration="300" @animationfinish="ontabchange"
            :style="{height: swiperHeight+'px'}">
            <swiper-item class="swiper-item" v-for="(item,i) in tabBars">
                <scroll-view class="scroll-v" :class="'list'+(i+1)" enableBackToTop="true" scroll-y>
                    <slot name='list{{i+1}}'></slot>
                </scroll-view>
            </swiper-item>
        </swiper>
    </view>
</template>

<script>
    export default {
        props: {
            tabBars: {
                type: Array,
                default: () => {
                    return []
                }
            },
        },
        data() {
            return {
                tabIndex: 0,
                swiperHeight:0,
                scrollInto:'',
            };
        },
        watch:{
        },
        methods: {
            ontabtap(e) {
                let index = e.target.dataset.current || e.currentTarget.dataset.current;
                this.tabIndex = index;
                this.scrollInto = this.tabBars[index].id;
            },
            ontabchange(e){
                let index = e.detail.current;
                this.tabIndex = index;
                this.scrollInto = this.tabBars[index].id;
                this.$emit('changeTabbar',this.tabIndex)
            },
            //动态获取高度(swiper组件高度固定,动画获取数据需要动态获取高度)
            getElementHeight(element) {
                //一定要 this.$nextTick 完成之后在获取dom节点高度
                setTimeout(() => {
                    this.$nextTick(() => {
                        let query = uni.createSelectorQuery().in(this);
                        query.select(element).boundingClientRect(data => {
                            // console.log(111,data)
                            if (!data) { //如果没获取到,再调一次
                                this.getElementHeight('.list');
                            } else {
                                this.swiperHeight = data.height;
                                //关闭loading
                                this.$emit('closeLoading')
                            }
                        }).exec()
                    })
                }, 10)
            },
        }
    }
</script>

<style lang="scss" scoped>
    .tabs {
        flex: 1;
        flex-direction: column;
        overflow: hidden;
        height:100%;
        overflow-y: scroll;
        .scroll-h {
            width: 750rpx;
            /* #ifdef H5 */
            width: 100%;
            /* #endif */
            flex-direction: row;
            /* #ifndef APP-PLUS */
            white-space: nowrap;
            /* #endif */
            flex-wrap: nowrap;
            background-color: #fff;
        }

        .uni-tab-item {
            /* #ifndef APP-PLUS */
            display: inline-block;
            /* #endif */
            flex-wrap: nowrap;
            padding-left: 34rpx;
            padding-right: 34rpx;
        }

        .uni-tab-item-line {
            width: 54rpx;
            height: 6rpx;
            background: #1975F7;
            border-radius: 3rpx 3rpx 3rpx 3rpx;
            margin: 0 auto;
        }

        .uni-tab-item-title {
            color: #555;
            font-size: 30rpx;
            height: 60rpx;
            line-height: 60rpx;
            flex-wrap: nowrap;
            /* #ifndef APP-PLUS */
            white-space: nowrap;
            /* #endif */
        }

        .uni-tab-item-title-active {
            color: #1975F7;
        }

        .swiper-box {
            flex: 1;
        }

        .swiper-item {
            flex: 1;
            flex-direction: row;
        }

        .scroll-v {
            flex: 1;
            /* #ifndef MP-ALIPAY */
            flex-direction: column;
            /* #endif */
            width: 750rpx;
            width: 100%;
        }

        .tabCenter {
            display: flex;
            align-items: center;
            justify-content: center;
        }

    }
</style>

2.在界面引入,使用

//引入组件
import tabbarPage from '../components/tabbar/index.vue';
//使用
<tabbar-page :tabBars="tabBarLists" ref="tabBarPage" @changeTabbar="changeTabbar">			
	<template slot="list1"> //写对应界面的代码 </template>
	<template slot="list2">	//写对应界面的代码</template>
	<template slot="list3"> //写对应界面的代码</template>
</tabbar-page>

3.注意。如果切换界面对应的是动态数据,swiper因为高度固定,需要获取动态高度

数据请求到之后调用组件接口,代码如下

setTimeout(() => {
		this.$nextTick(() => {
			this.$refs.tabBarPage.getElementHeight('.list1')
		})
}, 10)


**uni-app滑动/点击切换tab组件,动态数据内容获取swiper动态高度**

**uni-app滑动/点击切换tab组件,动态数据内容获取swiper动态高度**

**uni-app滑动/点击切换tab组件,动态数据内容获取swiper动态高度**

**uni-app滑动/点击切换tab组件,动态数据内容获取swiper动态高度**

**uni-app滑动/点击切换tab组件,动态数据内容获取swiper动态高度**

**uni-app滑动/点击切换tab组件,动态数据内容获取swiper动态高度**

**uni-app滑动/点击切换tab组件,动态数据内容获取swiper动态高度**

**uni-app滑动/点击切换tab组件,动态数据内容获取swiper动态高度**

**uni-app滑动/点击切换tab组件,动态数据内容获取swiper动态高度**

**uni-app滑动/点击切换tab组件,动态数据内容获取swiper动态高度**

**uni-app滑动/点击切换tab组件,动态数据内容获取swiper动态高度**

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值