Files
jindengchen-ai-report/cool-unix/pages/dailyreport/detail.uvue
2025-11-13 10:36:23 +08:00

223 lines
6.8 KiB
Plaintext
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>
<cl-page title="日报详情">
<view v-if="loading" class="flex justify-center items-center py-20">
<cl-loading />
</view>
<view v-else-if="report" class="p-4">
<!-- 头部信息 -->
<view class="mb-6">
<view class="flex justify-between items-center mb-2">
<text class="text-2xl font-bold">{{ formatDate(report.reportDate) }}</text>
<cl-tag :type="report.status === 1 ? 'success' : 'warning'">
{{ report.status === 1 ? '已提交' : '草稿' }}
</cl-tag>
</view>
<text class="text-sm text-gray-500">
{{ report.inputType === 1 ? "🎤 语音输入" : "⌨️ 文字输入" }} ·
{{ report.submitTime ? ('提交于 ' + formatDateTime(report.submitTime)) : ('创建于 ' + formatDateTime(report.createTime)) }}
</text>
</view>
<!-- 最终日报内容 -->
<view class="mb-6">
<text class="text-base font-bold mb-3 block">📝 日报内容</text>
<view class="p-4 bg-white rounded-lg shadow-sm">
<text class="text-sm text-gray-800">{{ report.userEditedContent || "暂无内容" }}</text>
</view>
</view>
<!-- 折叠面板查看原始内容和AI生成内容 -->
<cl-collapse v-model="activeNames">
<!-- 原始内容 -->
<cl-collapse-item v-if="report.originalText" name="original" title="📄 原始输入内容">
<view class="p-3 bg-gray-50 rounded">
<text class="text-sm text-gray-700">{{ report.originalText }}</text>
</view>
</cl-collapse-item>
<!-- AI格式化内容 -->
<cl-collapse-item v-if="report.aiFormattedContent" name="ai" title="🤖 AI生成内容">
<view class="p-3 bg-blue-50 rounded">
<text class="text-sm text-gray-800">{{ report.aiFormattedContent }}</text>
</view>
</cl-collapse-item>
</cl-collapse>
<!-- 操作按钮 -->
<view class="flex gap-3 mt-6">
<cl-button type="primary" size="large" :flex="1" @tap="editReport">
编辑日报
</cl-button>
<cl-button v-if="report.status === 0" type="success" size="large" :flex="1" @tap="submitReport" :loading="isSubmitting">
{{ isSubmitting ? "提交中..." : "提交日报" }}
</cl-button>
</view>
</view>
<view v-else class="flex flex-col items-center justify-center py-20">
<text class="text-6xl mb-4">📝</text>
<text class="text-gray-400 text-base">日报不存在</text>
<cl-button type="primary" size="small" class="mt-4" @tap="router.back()">
返回列表
</cl-button>
</view>
</cl-page>
</template>
<script setup lang="ts">
import { ref } from "vue";
import { request, router, useStore } from "@/cool";
import { useUi } from "@/uni_modules/cool-ui";
import { onLoad } from "@dcloudio/uni-app";
const ui = useUi();
const { user } = useStore();
// 日报数据
const report = ref<any>(null);
const loading = ref(true);
const isSubmitting = ref(false);
// 折叠面板展开项
const activeNames = ref<string[]>([]);
// 用户ID从登录状态获取
const userId = ref(0);
// 路由参数onLoad 中获取)
const reportId = ref("");
const reportDateParam = ref("");
onLoad(async (options: any) => {
// 读取路由参数
reportId.value = (options?.id ?? "").toString();
reportDateParam.value = (options?.date ?? "").toString();
// 刷新用户信息
if (user.token) {
try { await user.get(); } catch (e) { console.error("【日报详情】获取用户信息失败:", e); }
}
// 获取当前登录用户ID
if (user.info.value && user.info.value.id) {
userId.value = user.info.value.id;
} else {
ui.showToast({ message: "请先登录", type: "error" });
setTimeout(() => { router.to("/pages/user/login"); }, 1000);
loading.value = false;
return;
}
if (reportId.value) {
await loadReportDetail();
} else if (reportDateParam.value) {
await loadReportDetailByDateFallback();
} else {
loading.value = false;
}
});
// 加载日报详情按ID
async function loadReportDetail() {
loading.value = true;
try {
const res = await request({
url: "/app/dailyreport/report/detail",
method: "GET",
params: { id: reportId.value, userId: userId.value }
});
if (res) { report.value = res; return; }
await loadReportDetailByDateFallback();
} catch (error: any) {
console.error("加载日报详情失败:", error);
await loadReportDetailByDateFallback();
} finally {
loading.value = false;
}
}
// 按日期回退查询
async function loadReportDetailByDateFallback() {
if (!reportDateParam.value) return;
loading.value = true;
try {
const res = await request({
url: "/app/dailyreport/report/myReports",
method: "GET",
params: {
userId: userId.value,
startDate: reportDateParam.value,
endDate: reportDateParam.value
}
});
if (Array.isArray(res) && res.length > 0) {
report.value = res[0];
}
} catch (error: any) {
console.error("按日期加载日报失败:", error);
} finally {
loading.value = false;
}
}
// 编辑日报
function editReport() {
const id = reportId.value || report.value?.id;
if (id) {
router.to(`/pages/dailyreport/submit?id=${id}`);
} else if (reportDateParam.value) {
router.to(`/pages/dailyreport/submit?date=${reportDateParam.value}`);
} else {
ui.showToast({ message: "无有效日报标识", type: "warn" });
}
}
// 提交日报(草稿转提交)
async function submitReport() {
if (!report.value) return;
isSubmitting.value = true;
try {
await request({
url: "/app/dailyreport/report/submit",
method: "POST",
data: {
userId: userId.value,
reportDate: report.value.reportDate,
originalText: report.value.originalText,
aiFormattedContent: report.value.aiFormattedContent,
userEditedContent: report.value.userEditedContent,
inputType: report.value.inputType
}
});
ui.showToast({ message: "日报提交成功", type: "success" });
setTimeout(() => { loadReportDetail(); }, 500);
} catch (error: any) {
console.error("提交日报失败:", error);
ui.showToast({ message: "提交失败: " + (error.message || "未知错误"), type: "error" });
} finally {
isSubmitting.value = false;
}
}
// 工具:日期与时间格式化
function formatDate(dateStr: string) {
if (!dateStr) return "";
const d = new Date(dateStr);
const y = d.getFullYear();
const m = String(d.getMonth() + 1).padStart(2, "0");
const dd = String(d.getDate()).padStart(2, "0");
return `${y}-${m}-${dd}`;
}
function formatDateTime(timeStr: string) {
if (!timeStr) return "";
const date = new Date(timeStr);
const y = date.getFullYear();
const m = String(date.getMonth() + 1).padStart(2, "0");
const d = String(date.getDate()).padStart(2, "0");
const hh = String(date.getHours()).padStart(2, "0");
const mm = String(date.getMinutes()).padStart(2, "0");
return `${y}-${m}-${d} ${hh}:${mm}`;
}
</script>