cecc7f4cbb
## 日期条 → 可展开日历 首页那条七天日期带下面加了「展开整月」。展开后是整月网格(有安排的 日子带绿点),点任意一天,任务卡跟着切到那天。收起来还是七天,默认 不拉日历接口。 这块原来是计划页的「日历」tab,现在从计划页整个摘掉了——「哪天要做 什么」和「今天要做什么」本来就是一件事,分在两个 tab 里只是让人多点 两下。日历样式(.cal-* / .day-detail / .dd-*)跟着从 plan.wxss 搬到 home.wxss,plan.wxss 里没留死规则。 ## 任务卡下面挂当天的计划节点和提醒 day-plan 接口本来就返回 plan_nodes / reminders / tasks 三份。这里只取 前两份,任务列表仍然走 /tasks——因为 /tasks 会补生成当天任务而 day-plan 不会,拿它的 tasks 覆盖列表会让今天的任务凭空少掉。 ## 「接下来」卡 30 天计划里最近 3 个还没做的节点,日期显示成「今天/明天/3 天后」而不是 7月31日。带完成度进度条,右上角「完整计划」进计划页。 计划页降级成二级页之后,这张卡是它在首页的唯一露出;没有它,计划这个 功能对用户来说就等于消失了。 ## AI 计划入口 AI 页快捷区加了「生成养护计划」,直达 /pages/plan/plan?tab=aiPlan。 没有把这个表单搬进 AI 聊天页:它要渲染 extracted 四宫格和可勾选的任务 节点,塞进聊天流意味着同一个页面维护两套完全不同的渲染,收益只是少跳 一次。原本要解决的是「计划页降级后 AI 计划找不到了」,一个入口就够了。 顺带:iconfont 补了 up / down 两个 chevron(展开收起用)。 联调验证(本地 9090,新建幼犬档案): day-plan 今天 → plan_nodes=['确认免疫与驱虫计划'] plan → completion_pct=0,4 个节点,date 字段齐全 接下来筛出 → 07-29 确认免疫与驱虫计划 / 08-01 观察饮水与排便 / 08-05 体重趋势检查 calendar → 2026-7,today=29,tasked_days=[29] day-plan 未来日 → 08-01、08-05 各自返回对应节点 Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
48 lines
2.0 KiB
Plaintext
48 lines
2.0 KiB
Plaintext
/* 整页聊天:上面滚动区自适应,下面输入区固定,中间不留空 */
|
|
.chat-scroll{flex:1;min-height:0}
|
|
.chat-body{padding:var(--sp-3) var(--pad-x) var(--sp-5)}
|
|
.chat-bottom{height:1rpx}
|
|
|
|
.row{display:flex;align-items:flex-start;gap:var(--sp-2);margin-bottom:var(--sp-4)}
|
|
.row-user{justify-content:flex-end}
|
|
.ai-avatar{
|
|
width:60rpx;height:60rpx;border-radius:var(--r-sm);flex:none;margin-top:4rpx;
|
|
display:flex;align-items:center;justify-content:center;
|
|
background:var(--cta);color:#fff;
|
|
}
|
|
.bubble{
|
|
max-width:76%;border-radius:var(--r-md);padding:var(--sp-3) var(--sp-4);
|
|
font-size:var(--fs-md);line-height:1.62;word-break:break-word;
|
|
}
|
|
.bubble-ai{background:#fff;box-shadow:var(--sd-1);border-top-left-radius:var(--r-xs)}
|
|
.bubble-user{background:var(--primary-soft);color:var(--primary-ink);border-top-right-radius:var(--r-xs)}
|
|
/* 打字光标 */
|
|
.caret{color:var(--primary);animation:blink .9s steps(1) infinite}
|
|
@keyframes blink{50%{opacity:0}}
|
|
|
|
/* 底部输入区 */
|
|
.dock{
|
|
flex:none;background:rgba(255,255,255,.94);
|
|
backdrop-filter:blur(28rpx);-webkit-backdrop-filter:blur(28rpx);
|
|
border-top:1rpx solid var(--line);
|
|
padding:var(--sp-3) var(--pad-x) calc(var(--sp-3) + env(safe-area-inset-bottom));
|
|
}
|
|
.presets{white-space:nowrap;margin-bottom:var(--sp-3)}
|
|
.preset{
|
|
display:inline-block;height:var(--h-sm);line-height:var(--h-sm);padding:0 var(--sp-4);
|
|
margin-right:var(--sp-2);border-radius:var(--r-full);border:1rpx solid var(--line);
|
|
background:#fff;color:var(--text-2);font-size:var(--fs-sm);
|
|
}
|
|
.input-row{display:flex;align-items:center;gap:var(--sp-3)}
|
|
.input-row .input{flex:1;background:var(--surface-2)}
|
|
.send{
|
|
width:88rpx;height:88rpx;border-radius:var(--r-md);flex:none;
|
|
display:flex;align-items:center;justify-content:center;
|
|
background:var(--line);color:#fff;transition:.16s ease;
|
|
}
|
|
.send.on{background:var(--cta)}
|
|
.preset-go{
|
|
display:inline-flex;align-items:center;gap:6rpx;
|
|
background:var(--primary-soft);color:var(--primary-dark);border-color:var(--primary-line);
|
|
}
|