uniapp自定义导航栏(setup语法糖)

小程序可以直接使用,app需要调整一下使用的参数,我一般也就用到状态栏高度

我一般直接封装成一个组件,然后父组件传过来自定义的高度、自定义样式 包括搜索等

1、新建一个js文件用来存放获取到的设备信息

export function getdeviceInfo() {
    const globalData = {
        statusBarHeight: 0, // 状态导航栏高度
        topHeight: 0, // 距离顶部高度
        navHeight: 0, // 总体高度
        windowHeight: 0, // 可使用窗口高度
        tabBarHight: 0, //底部导航栏高度
    };
    let systemInfo = uni.getSystemInfoSync()
    globalData.windowHeight = systemInfo.screenHeight
    // 底部导航栏
    globalData.tabBarHight = systemInfo.screenHeight - systemInfo.safeArea.bottom
    // 状态栏高度
    globalData.statusBarHeight = systemInfo.statusBarHeight
/*#ifdef MP*/
    let menuButtonInfo = uni.getMenuButtonBoundingClientRect()
// 胶囊距离顶部高度
    globalData.topHeight = menuButtonInfo.top
// 胶囊高度
    globalData.navHeight = menuButtonInfo.height
/*#endif*/
​
    return {
        globalData
    }
}

2、在main.js中引入并挂载

import { getdeviceInfo } from '@/common/deviceInfo.js'
app.config.globalProperties.$key = getdeviceInfo(); // 定义全局变量

3、vue文件

<template>
	<!-- 导航栏 -->
	<view class="header-box" :style="{height:navHeight+topHeight+30+'px'}">
		<view class="header-nav" :style="{height:navHeight+'px',marginTop:topHeight+'px'}">
			<view class="nav-back" :style="{marginLeft:rightWidth+'px'}">
				<u-icon name="arrow-left"></u-icon>
			</view>
			<text class="nav-title">
				标题
			</text>
		</view>
	</view>
</template>

<script setup>
	import {
		getCurrentInstance,
		ref
	} from 'vue'
	const {
		proxy
	} = getCurrentInstance();
	const {
		navHeight,
		topHeight,
		rightWidth
	} = toRefs(proxy.$key.globalData)
	console.log(rightWidth);
</script>

<style lang="scss" scoped>
	.header-box {
		overflow: hidden;
		box-sizing: border-box;
		background: linear-gradient(#f9dacd, #ffffff);

		.header-nav {
			text-align: center;
			display: flex;
			align-items: center;
			position: relative;

			.nav-title {
				position: absolute;
				top: 50%;
				left: 50%;
				transform: translate(-50%, -50%);
			}
		}
	}
</style>

4、封装成组件

子组件

<template>
    <!-- 导航栏 -->
    <view class="header-box" :style="{height:navHeight+topHeight+height+'px'}">
        <view class="header-nav" :style="{height:navHeight+'px',marginTop:topHeight+'px'}">
            <view class="nav-back" :style="{marginLeft:rightWidth+'px'}">
                <u-icon size="18" name="arrow-left"></u-icon>
            </view>
            <text class="nav-title">
                {{title}}
            </text>
        </view>
        <view v-if="isSearch" class="search-box" :style="{paddingLeft:rightWidth+'px',paddingRight:rightWidth+'px'}">
            <u-search placeholder="搜索商品名称" bgColor="#ffffff" :show-action="false" v-model="keyword" @search="confirm"></u-search>
        </view>
​
    </view>
    <!-- 占位 -->
    <view :style="{height:navHeight+topHeight+height+'px'}">
    </view>
</template>
​
<script setup>
    import {
        getCurrentInstance,
        ref
    } from 'vue'
    const {
        proxy
    } = getCurrentInstance();
    const {
        navHeight,
        topHeight,
        rightWidth,
        windowHeight
    } = toRefs(proxy.$key.globalData)
    const emit = defineEmits(['toSearch'])
    const keyword = ref('')
    const props = defineProps({
        height: {
            type: Number,
            default: 30
        },
        title: String,
        isSearch: Boolean
    })
    const confirm = () => {
        emit('toSearch', keyword.value)
    }
</script>
​
<style lang="scss" scoped>
    page {
        position: relative;
    }
​
    .header-box {
        width: 100%;
        position: fixed;
        top: 0;
        overflow: hidden;
        box-sizing: border-box;
        background: linear-gradient(#f9dacd, #ffffff);
​
        .header-nav {
            text-align: center;
            display: flex;
            align-items: center;
            position: relative;
​
            .nav-title {
                position: absolute;
                top: 50%;
                left: 50%;
                transform: translate(-50%, -50%);
            }
        }
​
        .search-box {
            margin-top: 20rpx;
        }
    }
</style>

父组件

<!-- 导航栏 -->
    <navBar title="标题" :height="60" :isSearch="true" @toSearch="toSearch" />
    
  • 24
    点赞
  • 16
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值