diff --git a/docs/20260708/uni-app用户侧前端重建计划.md b/docs/20260708/uni-app用户侧前端重建计划.md index da284850..731dff43 100644 --- a/docs/20260708/uni-app用户侧前端重建计划.md +++ b/docs/20260708/uni-app用户侧前端重建计划.md @@ -224,6 +224,7 @@ mobile-uni/ - PC 成长激励和组织权限页已收口真实数据边界: 派专项必须输入真实员工手机号或 extPartyId,不再写入 `mobile-user`;无项目范围接口时只显示空态,不再展示假项目样例。 - `mobile-uni` 本地 dev 代理已对齐 portless:默认 `/dev-api -> https://wygj-api.localhost`,不再依赖裸 `8080`;真实浏览器登录链路已复跑通过。 - 员工今日页“今日安排”已优先回读真实 `/api/aihr/mobile/practice/assignments`;有待训练专项或每日三题时覆盖公开 home seed,真实浏览器已验证 `13900000998` 首页显示当天 daily 任务并可跳到练习页。 +- 员工今日页到练习页已补任务上下文传递:首页点“开始”会把当前 assignment 带到练习页,daily 任务高亮并提示填写,主管专项可直接启动,减少跳页后的二次选择。 ## 7. 风险 diff --git a/mobile-uni/src/pages/user/practice/index.vue b/mobile-uni/src/pages/user/practice/index.vue index 3c53b3df..2e0cd634 100644 --- a/mobile-uni/src/pages/user/practice/index.vue +++ b/mobile-uni/src/pages/user/practice/index.vue @@ -21,7 +21,7 @@ - + {{ item.source === 'daily' ? '每日三题' : '主管专项' }} {{ item.question || item.scenarioName }} @@ -174,6 +174,7 @@ type PracticeStatus = 'idle' | 'starting' | 'active' | 'submitting' | 'finished' const defaultScenarioId = 'complaint-water'; const defaultScenarioName = '投诉接待'; +const pendingAssignmentKey = 'aihr_pending_assignment_id'; const status = ref('idle'); const sessionId = ref(''); const roundIndex = ref(0); @@ -199,6 +200,7 @@ const drillAnswers = ref>({}); const assignmentLoading = ref(false); const answeringId = ref(null); const activeAssignmentId = ref(); +const highlightedAssignmentId = ref(null); const loggedIn = ref(false); const busy = computed(() => status.value === 'starting' || status.value === 'submitting'); const canStartPractice = computed(() => status.value === 'idle' || status.value === 'finished'); @@ -257,6 +259,7 @@ const clearPracticeData = () => { redFlagActive.value = false; answeringId.value = null; activeAssignmentId.value = undefined; + highlightedAssignmentId.value = null; }; const requireLogin = () => { @@ -297,6 +300,7 @@ const loadAssignments = async () => { try { assignments.value = await getPracticeAssignments(true); drillAnswers.value = Object.fromEntries(assignments.value.map((item) => [item.id, item.userAnswer || ''])); + consumePendingAssignment(); } catch (error) { handleError(error, '今日任务加载失败'); } finally { @@ -304,6 +308,25 @@ const loadAssignments = async () => { } }; +const consumePendingAssignment = () => { + const raw = uni.getStorageSync(pendingAssignmentKey); + if (!raw) return; + uni.removeStorageSync(pendingAssignmentKey); + const id = Number(raw); + if (!Number.isFinite(id)) return; + const item = assignments.value.find((row) => row.id === id); + if (!item) { + message.value = '首页任务已更新,请从列表选择'; + return; + } + highlightedAssignmentId.value = item.id; + if (item.source !== 'daily' && item.status === '待训练' && canStartPractice.value) { + startAssignment(item); + return; + } + message.value = item.source === 'daily' ? '已定位首页任务,请填写话术后提交' : '该任务已完成,请选择其他任务'; +}; + const submitDaily = async (item: PracticeAssignment) => { if (answeringId.value) return; const answer = (drillAnswers.value[item.id] || '').trim(); @@ -560,10 +583,16 @@ onShow(() => { .assignment-row { margin-top: 10px; padding: 12px; + border: 1px solid transparent; border-radius: 14px; background: #f8fafc; } +.assignment-row.highlighted { + border-color: #2563eb; + background: #eff6ff; +} + .assignment-badge { display: inline-flex; width: fit-content; diff --git a/mobile-uni/src/pages/user/today/index.vue b/mobile-uni/src/pages/user/today/index.vue index 09a270be..d1a45beb 100644 --- a/mobile-uni/src/pages/user/today/index.vue +++ b/mobile-uni/src/pages/user/today/index.vue @@ -117,6 +117,7 @@ const message = ref(''); const loggedIn = ref(false); const quickQuestions = ['催费话术', '投诉应对', '收费标准']; const pendingSopQueryKey = 'aihr_sop_pending_query'; +const pendingAssignmentKey = 'aihr_pending_assignment_id'; const iconFor = (title: string) => { if (title.includes('SOP') || title.includes('查')) return '/static/map-icons/ask.png'; @@ -218,6 +219,9 @@ const goLogin = () => { }; const openPrimarySchedule = () => { + if (primaryAssignment.value) { + uni.setStorageSync(pendingAssignmentKey, String(primaryAssignment.value.id)); + } uni.switchTab({ url: '/pages/user/practice/index' }); };