docs(oa): expand corner index design and plan to all five mobile lists.
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
1 parent
b2a30d78d8
commit
53e4a52b4f
4 files changed
+332
-54
No files matched your search
@@ -0,0 +1,247 @@
|
||||
# OA 五列表 · 折角序号 + 滚动分页加固 Implementation Plan
|
||||
|
||||
> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking.
|
||||
|
||||
**Goal:** 五个 OA 列表统一左上折角序号(方案 A),并加固触底滚动分页可触发性。
|
||||
|
||||
**Architecture:** `formatCornerIndex` 纯函数 + 全局 `.dd-card__corner` 样式;五页模板在 `.dd-card` 内插入折角并用累计 `list` 下标;`pages.json` 为五页补 `onReachBottomDistance`。分页数据逻辑已存在,不重写。
|
||||
|
||||
**Tech Stack:** uni-app(mobile-h5)、SCSS、Node assert
|
||||
|
||||
**Spec:** `docs/superpowers/specs/2026-08-13-oa-list-corner-index-pagination-design.md`
|
||||
**Demo:** `mobile-ui/zkxw-mobile-oa-mine-card-index-badge-demo.html`(A)
|
||||
**取代计划:** `docs/superpowers/plans/2026-08-13-oa-mine-card-corner-index.md`(仅 mine)
|
||||
|
||||
---
|
||||
|
||||
## File map
|
||||
|
||||
| 文件 | 职责 |
|
||||
|------|------|
|
||||
| Create: `mobile-h5/utils/oa-corner-index.js` | 序号文案 |
|
||||
| Create: `mobile-h5/utils/oa-corner-index.test.js` | 单测 |
|
||||
| Modify: `mobile-h5/styles/components/oa-task-list.scss` | 全局折角样式 |
|
||||
| Modify: `mobile-h5/pages.json` | 五页 `onReachBottomDistance: 80` |
|
||||
| Modify: `mobile-h5/pages/oa/{drafts,pending,done,mine,cc}/index.vue` | 折角 DOM + `cornerIndex` |
|
||||
|
||||
---
|
||||
|
||||
### Task 1: `formatCornerIndex`(TDD)
|
||||
|
||||
**Files:**
|
||||
- Create: `mobile-h5/utils/oa-corner-index.js`
|
||||
- Create: `mobile-h5/utils/oa-corner-index.test.js`
|
||||
|
||||
- [ ] **Step 1: 写失败单测**
|
||||
|
||||
```js
|
||||
// mobile-h5/utils/oa-corner-index.test.js
|
||||
import assert from 'node:assert/strict'
|
||||
import { formatCornerIndex } from './oa-corner-index.js'
|
||||
|
||||
assert.equal(formatCornerIndex(1), '01')
|
||||
assert.equal(formatCornerIndex(9), '09')
|
||||
assert.equal(formatCornerIndex(10), '10')
|
||||
assert.equal(formatCornerIndex(11), '11')
|
||||
assert.equal(formatCornerIndex(99), '99')
|
||||
assert.equal(formatCornerIndex(100), '100')
|
||||
|
||||
console.log('oa-corner-index: ok')
|
||||
```
|
||||
|
||||
- [ ] **Step 2: 跑测确认失败**
|
||||
|
||||
```bash
|
||||
cd mobile-h5 && node utils/oa-corner-index.test.js
|
||||
```
|
||||
|
||||
Expected: module not found / 失败。
|
||||
|
||||
- [ ] **Step 3: 实现**
|
||||
|
||||
```js
|
||||
// mobile-h5/utils/oa-corner-index.js
|
||||
/**
|
||||
* @param {number} n 从 1 起的序号
|
||||
* @returns {string}
|
||||
*/
|
||||
export function formatCornerIndex(n) {
|
||||
const num = Number(n)
|
||||
if (!Number.isFinite(num) || num < 1) return '01'
|
||||
const i = Math.floor(num)
|
||||
if (i < 10) return '0' + i
|
||||
return String(i)
|
||||
}
|
||||
```
|
||||
|
||||
- [ ] **Step 4: 跑测通过**
|
||||
|
||||
```bash
|
||||
cd mobile-h5 && node utils/oa-corner-index.test.js
|
||||
```
|
||||
|
||||
Expected: `oa-corner-index: ok`
|
||||
|
||||
- [ ] **Step 5: Commit**
|
||||
|
||||
```bash
|
||||
git add mobile-h5/utils/oa-corner-index.js mobile-h5/utils/oa-corner-index.test.js
|
||||
git commit -m "$(cat <<'EOF'
|
||||
feat(mobile-h5): add formatCornerIndex for OA list corner badges.
|
||||
|
||||
EOF
|
||||
)"
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### Task 2: 全局折角样式 + 触底距离
|
||||
|
||||
**Files:**
|
||||
- Modify: `mobile-h5/styles/components/oa-task-list.scss`
|
||||
- Modify: `mobile-h5/pages.json`
|
||||
|
||||
- [ ] **Step 1: 在 `oa-task-list.scss` 末尾追加**
|
||||
|
||||
```scss
|
||||
/* 钉钉风列表卡 · 左上折角序号(五中心共用) */
|
||||
.dd-card {
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.dd-card__corner {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
width: 0;
|
||||
height: 0;
|
||||
border-style: solid;
|
||||
border-width: 68rpx 68rpx 0 0;
|
||||
border-color: #0a9f6d transparent transparent transparent;
|
||||
pointer-events: none;
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
.dd-card__corner-num {
|
||||
position: absolute;
|
||||
top: -60rpx;
|
||||
left: 8rpx;
|
||||
font-size: 20rpx;
|
||||
font-weight: 800;
|
||||
line-height: 1;
|
||||
color: #fff;
|
||||
letter-spacing: -0.02em;
|
||||
}
|
||||
```
|
||||
|
||||
说明:`App.vue` 已 `@import` 本文件,无需改各页 scoped 重复写折角色。
|
||||
|
||||
- [ ] **Step 2: `pages.json` — 五页 style 增加触底距离**
|
||||
|
||||
对以下 path 的 `style` 对象各加一行 `"onReachBottomDistance": 80`(与现有 `enablePullDownRefresh` 并列):
|
||||
|
||||
- `pages/oa/drafts/index`
|
||||
- `pages/oa/pending/index`
|
||||
- `pages/oa/done/index`
|
||||
- `pages/oa/mine/index`
|
||||
- `pages/oa/cc/index`
|
||||
|
||||
- [ ] **Step 3: Commit**
|
||||
|
||||
```bash
|
||||
git add mobile-h5/styles/components/oa-task-list.scss mobile-h5/pages.json
|
||||
git commit -m "$(cat <<'EOF'
|
||||
feat(mobile-h5): add shared OA card corner styles and reach-bottom distance.
|
||||
|
||||
EOF
|
||||
)"
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### Task 3: 五页模板接入折角
|
||||
|
||||
**Files:**
|
||||
- Modify: `mobile-h5/pages/oa/drafts/index.vue`
|
||||
- Modify: `mobile-h5/pages/oa/pending/index.vue`
|
||||
- Modify: `mobile-h5/pages/oa/done/index.vue`
|
||||
- Modify: `mobile-h5/pages/oa/mine/index.vue`
|
||||
- Modify: `mobile-h5/pages/oa/cc/index.vue`
|
||||
|
||||
每页做相同三件事(草稿/待办/抄送的 `v-for` 在 row 上,折角仍放在内层 `.dd-card`)。
|
||||
|
||||
- [ ] **Step 1: `mine/index.vue`**
|
||||
|
||||
1. `v-for="(row, idx) in list"`
|
||||
2. 在 `.dd-card` 内最前插入:
|
||||
|
||||
```vue
|
||||
<view class="dd-card__corner" aria-hidden="true">
|
||||
<text class="dd-card__corner-num">{{ cornerIndex(idx) }}</text>
|
||||
</view>
|
||||
```
|
||||
|
||||
3. script:
|
||||
|
||||
```js
|
||||
import { formatCornerIndex } from '../../../utils/oa-corner-index.js'
|
||||
```
|
||||
|
||||
```js
|
||||
cornerIndex(idx) {
|
||||
return formatCornerIndex(Number(idx) + 1)
|
||||
},
|
||||
```
|
||||
|
||||
- [ ] **Step 2: `done/index.vue`** — 同 Step 1(结构与 mine 最接近)
|
||||
|
||||
- [ ] **Step 3: `drafts/index.vue`**
|
||||
|
||||
`v-for="(row, idx) in list"` 在 `.draft-row` 上;折角放进内层 `.dd-card` 开头;同样 import + `cornerIndex`。
|
||||
|
||||
- [ ] **Step 4: `pending/index.vue`** — 同 drafts(`.pending-row` + 内层 `.dd-card`)
|
||||
|
||||
- [ ] **Step 5: `cc/index.vue`** — 同 pending(管理多选行 + 内层 `.dd-card`)
|
||||
|
||||
- [ ] **Step 6: 手工验收**
|
||||
|
||||
| 页 | 路径 | 检查 |
|
||||
|----|------|------|
|
||||
| 草稿箱 | `/#/pages/oa/drafts/index` | 折角 + 触底 + 搜索重置 `01` |
|
||||
| 待办 | `/#/pages/oa/pending/index` | 同上;管理勾选不受折角影响 |
|
||||
| 已办 | `/#/pages/oa/done/index` | 同上 |
|
||||
| 我发起的 | `/#/pages/oa/mine/index` | 同上;长按仍可用 |
|
||||
| 抄送 | `/#/pages/oa/cc/index` | 同上;未读点仍可见 |
|
||||
|
||||
- [ ] **Step 7: Commit**
|
||||
|
||||
```bash
|
||||
git add \
|
||||
mobile-h5/pages/oa/drafts/index.vue \
|
||||
mobile-h5/pages/oa/pending/index.vue \
|
||||
mobile-h5/pages/oa/done/index.vue \
|
||||
mobile-h5/pages/oa/mine/index.vue \
|
||||
mobile-h5/pages/oa/cc/index.vue
|
||||
git commit -m "$(cat <<'EOF'
|
||||
feat(mobile-h5): show corner index on all five OA task list cards.
|
||||
|
||||
EOF
|
||||
)"
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Spec coverage
|
||||
|
||||
| Spec | Task |
|
||||
|------|------|
|
||||
| 折角样式 / `#0a9f6d` / 补零规则 | Task 1–2 |
|
||||
| 五页序号 | Task 3 |
|
||||
| 滚动分页保持 + 触底距离 | Task 2 Step 2 + 既有 `loadList` |
|
||||
| 搜索重置从 01 | 既有 reset + `idx` |
|
||||
| 管理多选不挡 | 折角在 card 内、`pointer-events: none` |
|
||||
|
||||
## Out of scope
|
||||
|
||||
- 金额角标、状态变色折角、后端改动、Web 端
|
||||
@@ -0,0 +1,5 @@
|
||||
# 我发起的 · 列表卡片折角序号 Implementation Plan(已升级)
|
||||
|
||||
> **已由** [`2026-08-13-oa-list-corner-index-pagination.md`](./2026-08-13-oa-list-corner-index-pagination.md) **替代。**
|
||||
>
|
||||
> 新计划覆盖五个 OA 列表的折角序号 + 触底距离加固。请勿按本文仅改 mine。
|
||||
@@ -0,0 +1,75 @@
|
||||
# OA 五列表 · 滚动分页 + 折角序号 Design
|
||||
|
||||
| 项 | 内容 |
|
||||
|----|------|
|
||||
| 日期 | 2026-08-13 |
|
||||
| 状态 | 已定稿(用户确认:五页统一) |
|
||||
| 范围 | `mobile-h5` 草稿箱 / 待办 / 已办 / 我发起的 / 抄送我的 |
|
||||
| Demo | `mobile-ui/zkxw-mobile-oa-mine-card-index-badge-demo.html`(方案 A) |
|
||||
| 替代 | 原 `2026-08-13-oa-mine-card-corner-index-design.md` 范围升级为本篇 |
|
||||
|
||||
## 背景
|
||||
|
||||
五页列表卡片均为钉钉风白卡片,需统一:
|
||||
|
||||
1. **触底滚动分页加载**(累计列表)
|
||||
2. **左上折角序号**(方案 A)
|
||||
|
||||
## 现状
|
||||
|
||||
五页均已实现 `PAGE_SIZE=10`、`onReachBottom`、`loadList(reset)` 累计拼接、`hasMore` / 「加载更多…」/「已经到底了」。本期以**核对与加固**为主,不为分页另起架构。
|
||||
|
||||
折角序号尚未落地。
|
||||
|
||||
## 目标
|
||||
|
||||
| 能力 | 要求 |
|
||||
|------|------|
|
||||
| 滚动分页 | 触底加载下一页;下拉刷新 / 搜索或筛选重置回到第 1 页并清空累计列表 |
|
||||
| 折角序号 | 左上品牌绿三角 + 白字序号;跨页连续;`01`…`09`,`10`/`11` 不补三位 |
|
||||
|
||||
## 非目标
|
||||
|
||||
- 金额角标、折角随状态变色
|
||||
- 新增分页/序号相关 API 字段
|
||||
- Web 管理端列表改造
|
||||
|
||||
## 决策
|
||||
|
||||
| 项 | 选定 |
|
||||
|----|------|
|
||||
| 折角样式 | 方案 A:`#0a9f6d` 直角三角 + 白色序号 |
|
||||
| 序号文案 | `formatCornerIndex(listIndex + 1)`;累计 `list` 下标,**勿**用已自增的 `page` 套公式 |
|
||||
| 样式放置 | 全局 `styles/components/oa-task-list.scss`(`App.vue` 已引入),五页共用 |
|
||||
| 工具函数 | `mobile-h5/utils/oa-corner-index.js` |
|
||||
| 分页 | 保持现有逻辑;五页 `pages.json` 统一补 `onReachBottomDistance: 80`(便于触底触发) |
|
||||
|
||||
## 分页规格(验收基线)
|
||||
|
||||
各页已有行为须保持:
|
||||
|
||||
- `reset=true`:`page=1`、清空/替换 `list`、重拉
|
||||
- `reset=false`:`concat`、`page++`(有数据时)
|
||||
- `hasMore = loaded < total && rows.length > 0`
|
||||
- 底栏:加载中「加载更多…」,无更多「已经到底了」
|
||||
|
||||
涉及页:`drafts` / `pending` / `done` / `mine` / `cc`。
|
||||
|
||||
## UI 规格(折角)
|
||||
|
||||
- `.dd-card`:`position: relative; overflow: hidden`
|
||||
- 折角:直角边约 `68rpx`(对齐 Demo 34px@375)
|
||||
- 数字:约 `20rpx`、字重 800、白色,贴折角内侧
|
||||
- 管理多选行(草稿/待办/抄送):折角在卡片上,不挡左侧勾选
|
||||
|
||||
## 验收
|
||||
|
||||
1. 五页均可触底加载;不足一页显示「已经到底了」
|
||||
2. 搜索/筛选/下拉刷新后序号从 `01` 重计
|
||||
3. 第 1~10 条为 `01`–`10`,第 11 条为 `11`
|
||||
4. 五页折角色一致;点击 / 长按 / 管理多选行为不变
|
||||
|
||||
## 参考
|
||||
|
||||
- Demo A:`mobile-ui/zkxw-mobile-oa-mine-card-index-badge-demo.html`
|
||||
- 分页语义:`docs/superpowers/specs/2026-08-11-oa-task-centers-pagination-design.md`
|
||||
@@ -1,56 +1,7 @@
|
||||
# 我发起的 · 列表卡片左上折角序号 Design
|
||||
# 原 mine-only 折角序号设计(已升级)
|
||||
|
||||
| 项 | 内容 |
|
||||
|----|------|
|
||||
| 日期 | 2026-08-13 |
|
||||
| 状态 | 已定稿(用户确认方案 A) |
|
||||
| 范围 | `mobile-h5`「我发起的」列表卡片左上角序号 |
|
||||
| Demo | `mobile-ui/zkxw-mobile-oa-mine-card-index-badge-demo.html`(方案 A) |
|
||||
> **已由** [`2026-08-13-oa-list-corner-index-pagination-design.md`](./2026-08-13-oa-list-corner-index-pagination-design.md) **替代。**
|
||||
>
|
||||
> 范围从仅「我发起的」扩展为五个 OA 列表(草稿 / 待办 / 已办 / 我发起 / 抄送)统一滚动分页验收 + 方案 A 折角序号。
|
||||
|
||||
## 背景
|
||||
|
||||
「我发起的」列表卡片(`pages/oa/mine/index`)与待办等同为钉钉风白卡片,缺少与 Web 表格「序号」对应的视觉锚点。产品选型对比了折角 / 圆点 / 左色条 / 胶囊 / 金额角标,确认落地 **A 折角序号**。
|
||||
|
||||
## 目标
|
||||
|
||||
在每张列表卡片左上角展示跨页连续序号,样式对齐 Demo A,不改变现有点击 / 长按行为。
|
||||
|
||||
## 非目标
|
||||
|
||||
- 待办 / 已办 / 抄送 / 草稿列表不同步改造
|
||||
- 折角不随审批状态变色
|
||||
- 不在角标展示金额(金额仍走 `previewFields` meta)
|
||||
- 不新增接口字段
|
||||
|
||||
## 决策
|
||||
|
||||
| 项 | 选定 |
|
||||
|----|------|
|
||||
| 样式 | 左上直角三角折角 + 白色两位序号(`<10` 补零) |
|
||||
| 颜色 | 品牌绿 `#0a9f6d`(三墙 Token,固定色) |
|
||||
| 序号 | `(page - 1) * pageSize + index + 1`;当前页 `PAGE_SIZE = 10` |
|
||||
| 范围 | 仅 `mine/index.vue` |
|
||||
|
||||
## UI 规格
|
||||
|
||||
- 卡片:`position: relative; overflow: hidden`(现有圆角保留)
|
||||
- 折角:CSS 三角(约 `34px` 直角边,按 rpx 换算对齐 Demo),位于 `top:0; left:0`
|
||||
- 数字:白字、字重 ≥700、约 10–11px 量级,贴在折角内侧,不溢出三角
|
||||
- 内容区:保持现有 padding;标题不被折角遮挡可读区(折角仅占左上小三角)
|
||||
|
||||
## 数据与交互
|
||||
|
||||
- 序号由前端根据当前 `page` / `PAGE_SIZE` / `v-for` 下标计算;列表 `reset` 后从 1 起算正确
|
||||
- 纯展示;点卡片进详情、长按打印 / 复制重开不变
|
||||
|
||||
## 验收
|
||||
|
||||
1. 第 1 页前 10 条显示 `01`–`10`;加载更多后第 11 条为 `11`(或 `11` 不强制补零到三位,两位数原样)
|
||||
2. 搜索重置后序号从 `01` 重新计
|
||||
3. 折角色与 Demo A 一致;状态文案 / hint 色逻辑不变
|
||||
4. 无金额角标、无其它列表回归改动
|
||||
|
||||
## 参考
|
||||
|
||||
- Demo:`mobile-ui/zkxw-mobile-oa-mine-card-index-badge-demo.html` → Tab「A 折角序号」
|
||||
- Web 序号语义:`docs/superpowers/specs/2026-08-11-oa-task-centers-pagination-design.md`
|
||||
保留本文档以免旧链接失效;实现与评审请以新设计为准。
|
||||
Reference in new issue
Block a user