Files
im-uniapp/components/hrm/detailPanels/leave.vue
砂糖 d1eb3d61cf feat(审批): 新增审批中心页面及功能优化
- 新增审批中心页面,包含待审批任务列表展示和筛选功能
- 优化各审批类型详情页,增加项目信息展示和弹窗查看功能
- 在报销、用印、请假、出差详情页添加项目信息展示区域和详情弹窗
- 调整消息中心CC列表,增加未读状态红点标识
- 更新tabbar配置,新增审批入口图标和路由
- 优化部分页面交互细节和样式调整
2026-02-05 15:52:09 +08:00

270 lines
7.9 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<template>
<view class="leave-detail-container">
<!-- 请假类型 - 单独行+类型图标 -->
<view class="detail-item single-item">
<text class="item-icon icon-type"></text>
<view class="item-label">请假类型</view>
<view class="item-value">{{ detail.leaveType || '无' }}</view>
</view>
<view class="detail-item single-item">
<text class="item-icon icon-type"></text>
<view class="item-label">请假时间</view>
<view class="item-value">{{ formatTime(detail.startTime) }} - {{ formatTime(detail.endTime) }}</view>
</view>
<!-- 请假时长 - 单独行+时钟图标 -->
<view class="detail-item single-item">
<text class="item-icon icon-hour"></text>
<view class="item-label">请假时长</view>
<view class="item-value">{{ detail.hours || '0' }} 小时</view>
</view>
<!-- 请假原因 - 单独行+备注图标适配多行文 -->
<view class="detail-item single-item reason-item">
<text class="item-icon icon-reason"></text>
<view class="item-label">请假原因</view>
<view class="item-value">{{ detail.reason || '无' }}</view>
</view>
<!-- 申请人 - 单独行+用户图标 -->
<view class="detail-item single-item">
<text class="item-icon icon-user"></text>
<view class="item-label">申请人</view>
<view class="item-value">{{ detail.createBy || '无' }}</view>
</view>
<!-- 申请时间 - 单独行+日历图标 -->
<view class="detail-item single-item">
<text class="item-icon icon-date"></text>
<view class="item-label">申请时间</view>
<view class="item-value">{{ formatTime(detail.createTime) || '无' }}</view>
</view>
<view class="detail-item single-item amount-item" @click="openPopup" v-if="detail.projectId">
<text class="item-icon icon-creator"></text>
<view class="item-label">项目名称</view>
<view class="item-value">{{ detail.projectName || '无' }}</view>
</view>
<view class="detail-item single-item amount-item" @click="openPopup" v-if="detail.projectId">
<text class="item-icon icon-creator"></text>
<view class="item-label">项目编号</view>
<view class="item-value">{{ detail.projectNum || '无' }}</view>
</view>
<view class="detail-item single-item amount-item" @click="openPopup" v-if="detail.projectId">
<text class="item-icon icon-creator"></text>
<view class="item-label">项目代号</view>
<view class="item-value">{{ detail.projectCode || '无' }}</view>
</view>
<uni-popup ref="popup" type="center">
<view class="detail-content" v-if="detail.projectId">
<view class="info-item">
<text class="info-label">项目名称</text>
<text class="info-value">{{ detail.projectName || '-' }}</text>
</view>
<view class="info-item">
<text class="info-label">项目编号</text>
<text class="info-value">{{ detail.projectNum || '-' }}</text>
</view>
<view class="info-item">
<text class="info-label">项目代号</text>
<text class="info-value">{{ detail.projectCode || '-' }}</text>
</view>
<view class="info-item">
<text class="info-label">项目类型</text>
<oa-dict-tag dict-type="sys_project_type" :value="detail.projectType" placeholder="-" />
</view>
<view class="info-item">
<text class="info-label">项目地址</text>
<text class="info-value">{{ detail.address || '-' }}</text>
</view>
<view class="info-item">
<text class="info-label">项目总金额</text>
<text class="info-value">{{ detail.funds || '-' }}</text>
</view>
<view class="info-item">
<text class="info-label">负责人</text>
<text class="info-value">{{ detail.functionary || '-' }}</text>
</view>
<view class="info-item">
<text class="info-label">备注</text>
<text class="info-value">{{ detail.remark || '-' }}</text>
</view>
</view>
</uni-popup>
</view>
</template>
<script>
import { getLeaveReq } from '@/api/hrm/leave'
export default {
props: {
bizId: {
type: String,
required: true
}
},
data() {
return {
detail: {}
}
},
watch: {
bizId: {
handler(newVal) {
if (!newVal) return;
getLeaveReq(newVal)
.then(res => {
this.detail = res.data || {};
console.log(this.detail);
})
.catch(err => {
console.error('获取请假详情失败:', err);
uni.showToast({
title: '获取详情失败',
icon: 'none',
duration: 2000
});
});
},
immediate: true
}
},
methods: {
formatTime(timeStr) {
if (!timeStr) return '';
const [datePart] = timeStr.split(' ');
return datePart;
},
openPopup() {
this.$refs.popup.open()
},
}
}
</script>
<style scoped>
/* 主容器 - 卡片化升级,柔和阴影+大圆角+合理内边距 */
.leave-detail-container {
background: #ffffff;
border-radius: 18rpx;
margin: 20rpx 16rpx;
box-shadow: 0 4rpx 16rpx rgba(0, 0, 0, 0.05);
box-sizing: border-box;
}
/* 基础项样式 - 统一flex布局、行高、间距 */
.detail-item {
display: flex;
align-items: flex-start;
line-height: 48rpx;
padding: 20rpx 0;
border-bottom: 1px solid #f9f9f9;
}
/* 最后一项移除下边框 */
.detail-item:last-child {
border-bottom: none;
}
/* 单独行项 - 基础适配 */
.single-item {
flex-direction: row;
}
/* 同行双项 - 核心布局 */
.double-item {
flex-direction: row;
justify-content: space-between;
}
/* 图标样式 - 统一尺寸/颜色,视觉点缀(主题色可自定义) */
.item-icon {
display: inline-block;
width: 32rpx;
height: 32rpx;
margin-right: 12rpx;
margin-top: 8rpx;
flex-shrink: 0;
background-size: 100% 100%;
background-repeat: no-repeat;
color: #409eff; /* 主题色,可替换为项目主色 */
}
/* 各字段专属图标使用Unicode图标无需额外引入直接替换即可 */
.icon-type { content: "\e645"; font-family: "iconfont"; }
.icon-time-start { content: "\e629"; font-family: "iconfont"; }
.icon-time-end { content: "\e62a"; font-family: "iconfont"; }
.icon-hour { content: "\e68f"; font-family: "iconfont"; }
.icon-reason { content: "\e614"; font-family: "iconfont"; }
.icon-user { content: "\e600"; font-family: "iconfont"; }
.icon-date { content: "\e637"; font-family: "iconfont"; }
/* 标签样式 - 固定宽度+右对齐,视觉规整 */
.item-label {
width: 160rpx;
font-size: 30rpx;
color: #909399;
font-weight: 500;
flex-shrink: 0;
}
/* 同行时间项的标签 - 适配窄宽度 */
.time-item .item-label {
width: 100rpx;
}
/* 内容值样式 - 弹性占比,适配多行文/长文本 */
.item-value {
flex: 1;
font-size: 30rpx;
color: #333333;
word-break: break-all;
}
/* 总金额突出 - 字体加粗+主题色,视觉重点 */
.amount-item .item-value {
color: #409eff;
font-weight: 600;
font-size: 32rpx;
}
/* 请假原因 - 适配多行文,增加行高 */
.reason-item .item-value {
line-height: 52rpx;
padding-top: 4rpx;
}
/* 同行时间项 - 各占近50%宽度,防止挤压 */
.time-item {
display: flex;
align-items: flex-start;
width: 48%;
}
/* 同行时间项分隔线 - 竖线分隔,提升辨识度 */
.split-line {
width: 1px;
height: 60rpx;
background-color: #f9f9f9;
margin: 8rpx 16rpx 0;
flex-shrink: 0;
}
.detail-content {
border: 1px solid #ccc; /* 边框 */
border-radius: 10px; /* 圆角 */
padding: 15px; /* 内边距 */
background-color: #f9f9f9; /* 背景色 */
}
.info-item {
display: flex; /* 使用 Flexbox 布局 */
justify-content: space-between; /* 在一行内均匀分布 */
margin-top: 10px; /* 上边距 */
}
.info-label {
color: #333; /* 标签颜色 */
font-weight: bold; /* 标签加粗 */
}
.info-value {
color: #666; /* 值的颜色 */
}
</style>