JinShan_uniapp/components/custom-back-header.vue
2025-08-12 09:33:22 +08:00

150 lines
2.8 KiB
Vue

<template>
<!-- 自定义顶部返回栏 -->
<view class="custom-back-header" :style="headerStyle">
<!-- 返回按钮 -->
<view class="back-btn" @click="handleBack">
<slot name="icon">
<!-- 默认返回图标 -->
<view class="icon"></view>
</slot>
<text v-if="showText" class="text">{{ backText }}</text>
</view>
<!-- 标题插槽 -->
<view class="title">
<slot>{{ title }}</slot>
</view>
<!-- 右侧插槽 -->
<view class="right-slot">
<slot name="right"></slot>
</view>
</view>
</template>
<script>
export default {
props: {
// 标题文字
title: {
type: String,
default: ''
},
// 是否显示返回文字
showText: {
type: Boolean,
default: true
},
// 返回按钮文字
backText: {
type: String,
default: '返回'
},
// 背景颜色
bgColor: {
type: String,
default: '#ffffff'
},
// 文字颜色
color: {
type: String,
default: '#333333'
},
// 是否沉浸式(占位)
immersive: {
type: Boolean,
default: true
},
// 指定返回目标路径
targetPath: {
type: String,
default: ''
}
},
computed: {
headerStyle() {
return {
backgroundColor: this.bgColor,
color: this.color,
paddingTop: this.immersive ? 'var(--status-bar-height)' : '0'
};
}
},
methods: {
handleBack() {
if (this.$listeners.back) {
// 如果有自定义back事件则触发
this.$emit('back');
return;
}
const pages = getCurrentPages();
// 指定目标页面返回
if (this.targetPath) {
const target = pages.find(page =>
page.route === this.targetPath.replace(/^\//, '')
);
if (target) {
const delta = pages.length - pages.indexOf(target) - 1;
uni.navigateBack({ delta });
} else {
uni.redirectTo({ url: this.targetPath });
}
return;
}
// 默认返回逻辑
if (pages.length >= 2) {
uni.navigateBack();
} else {
uni.switchTab({ url: '/pages/index/index' });
}
}
}
};
</script>
<style scoped>
.custom-back-header {
display: flex;
align-items: center;
height: 44px;
padding: 0 15px;
position: relative;
z-index: 999;
}
.back-btn {
display: flex;
align-items: center;
padding: 5px 10px 5px 0;
margin-right: 10px;
}
.icon {
font-size: 20px;
margin-right: 5px;
}
.text {
font-size: 16px;
}
.title {
flex: 1;
text-align: center;
font-size: 17px;
font-weight: bold;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
.right-slot {
min-width: 60px;
display: flex;
justify-content: flex-end;
}
</style>