628 lines
18 KiB
Markdown
628 lines
18 KiB
Markdown
# 广寒基地拓扑图表现层数据库化设计
|
||
|
||
日期:2026-07-09
|
||
状态:待用户审核
|
||
范围:广寒基地工程总图的视觉表现层数据设计,不包含本轮代码实现
|
||
|
||
## 1. 背景
|
||
|
||
当前 `guanghan_topology_demo.html` 已经从后端快照读取大部分拓扑数据:
|
||
|
||
- 任务与时间点决定快照时间;
|
||
- 组件、端口、连接、状态来自 PostgreSQL;
|
||
- SVG 节点坐标、尺寸、分组、标签覆盖、显示提示和散热器标记来自 `diagram_layouts`、`diagram_nodes`、`diagram_node_members`;
|
||
- 页面会按快照隐藏尚未出现的组件和连接。
|
||
|
||
但页面仍然保留了一部分视觉语义:
|
||
|
||
- `core-card`、`power-card`、`vehicle-card` 等样式键对应什么颜色,由前端 CSS 决定;
|
||
- `structural_mount`、`pressurized_passage`、`fuel`、`power` 等连接类型如何映射成线条颜色、线宽、虚实线,由前端 JS/CSS 决定;
|
||
- 图例项由 HTML 硬编码;
|
||
- 散热器虽然由数据库标记是否显示,但具体形状、颜色、标签仍由前端决定。
|
||
|
||
因此当前状态是“半数据库驱动”。本设计把它推进到 B1 级别:数据库决定工程图的主要视觉语义,前端只保留通用渲染和交互壳。
|
||
|
||
## 2. 目标
|
||
|
||
本设计的目标是让后端数据库决定以下内容:
|
||
|
||
1. 节点矩形的位置、尺寸、圆角、填充色、描边色、描边宽度。
|
||
2. 连接线的颜色、线宽、虚实线、图例文案。
|
||
3. 装饰件的基础视觉参数,例如散热器的颜色、描边、标签。
|
||
4. 工程图图例的项目、顺序、显示名称和示例样式。
|
||
5. 节点 `style_key`、连接 `connection_type`、装饰件 `decoration_key` 到具体视觉参数的映射。
|
||
|
||
验收时应能做到:
|
||
|
||
- 修改数据库中 `pressurized_passage` 的颜色后,页面加压走道颜色随之变化,不需要改 HTML/CSS;
|
||
- 修改数据库中 `core-card` 的填充/描边后,核心舱视觉随之变化;
|
||
- 图例完全由 API 返回,不再在页面硬编码;
|
||
- GHC-01 到 GHC-05 的历史快照仍按数据库事实正确显示;
|
||
- 当前已确认的空间结构不变。
|
||
|
||
## 3. 非目标
|
||
|
||
B1 方案不把整个页面变成数据库控制的 UI 系统。以下内容仍属于前端通用壳:
|
||
|
||
- 页面字体族、整体背景、工具栏、弹窗、按钮、hover/focus 效果;
|
||
- 文本截断算法、SVG 元素创建方式、键盘可访问性;
|
||
- 响应式断点和滚动容器;
|
||
- 模块详情弹窗的排版;
|
||
- 业务时态表的结构重写;
|
||
- 数据库直接存储完整 SVG 或 HTML。
|
||
|
||
这条边界很重要:数据库掌握“工程图是什么样”,前端掌握“页面如何交互”。
|
||
|
||
## 4. 设计原则
|
||
|
||
### 4.1 表现层不是业务事实
|
||
|
||
组件、任务、连接、状态仍然是业务事实。布局和样式是对这些事实的可视化表达。
|
||
|
||
因此:
|
||
|
||
- 快照时间继续只决定哪些组件、连接、状态存在;
|
||
- 默认情况下,视觉主题不随历史时间变化;
|
||
- 早期任务快照可以使用同一张当前工程总图布局,只隐藏当时尚不存在的组件。
|
||
|
||
这能保持不同时刻的空间比较稳定,避免 GHC-01、GHC-03、GHC-05 每次切换都“重排整张图”。
|
||
|
||
### 4.2 数据库保存语义映射,不保存前端实现
|
||
|
||
数据库可以保存:
|
||
|
||
- `stroke_color = '#51e89c'`
|
||
- `stroke_width = 9`
|
||
- `dash_array = null`
|
||
- `legend_label = '加压走道'`
|
||
|
||
数据库不保存:
|
||
|
||
- CSS 选择器;
|
||
- JavaScript 函数名;
|
||
- HTML 片段;
|
||
- 浏览器专用的布局技巧。
|
||
|
||
### 4.3 可迁移、可扩展、可回退
|
||
|
||
新增表现层表应与现有 `diagram_layouts` 兼容。实现时可以分阶段上线:
|
||
|
||
1. 先建表并 seed 当前样式;
|
||
2. API 同时返回旧字段和新 `presentation`;
|
||
3. 前端切换到新字段;
|
||
4. 测试通过后,保留旧 CSS 类作为安全兜底,但不再作为事实来源。
|
||
|
||
## 5. 数据模型
|
||
|
||
### 5.1 `diagram_themes`
|
||
|
||
主题表表示一套工程图视觉风格。广寒基地初期只需要一个主题。
|
||
|
||
建议字段:
|
||
|
||
| 字段 | 类型 | 说明 |
|
||
|---|---|---|
|
||
| `id` | `uuid` | 主键 |
|
||
| `base_id` | `uuid` | 所属基地 |
|
||
| `theme_key` | `text` | 例如 `guanghan_dark_engineering_v1` |
|
||
| `name` | `text` | 显示名称 |
|
||
| `description` | `text` | 可空 |
|
||
| `tokens` | `jsonb` | 少量通用色值,例如文字色、弱文字色;不放完整 CSS |
|
||
| `is_default` | `boolean` | 是否默认主题 |
|
||
| `created_at` / `updated_at` | `timestamptz` | 审计字段 |
|
||
|
||
约束:
|
||
|
||
```sql
|
||
UNIQUE (base_id, theme_key)
|
||
```
|
||
|
||
`tokens` 示例:
|
||
|
||
```json
|
||
{
|
||
"textColor": "#eaf2ff",
|
||
"mutedTextColor": "#91a3bd",
|
||
"labelColor": "#f4df7b"
|
||
}
|
||
```
|
||
|
||
### 5.2 `diagram_node_styles`
|
||
|
||
节点样式表把现有 `diagram_nodes.style_key` 从“前端 CSS 类名”变成“数据库样式键”。
|
||
|
||
建议字段:
|
||
|
||
| 字段 | 类型 | 说明 |
|
||
|---|---|---|
|
||
| `id` | `uuid` | 主键 |
|
||
| `theme_id` | `uuid` | 所属主题 |
|
||
| `style_key` | `text` | 例如 `core-card`、`power-card` |
|
||
| `display_name` | `text` | 管理用途 |
|
||
| `fill_color` | `text` | SVG 填充色 |
|
||
| `stroke_color` | `text` | SVG 描边色 |
|
||
| `stroke_width` | `numeric` | SVG 描边宽度 |
|
||
| `corner_radius` | `numeric` | 矩形圆角 |
|
||
| `title_color` | `text` | 可空,默认使用主题文字色 |
|
||
| `meta_color` | `text` | 可空 |
|
||
| `hint_color` | `text` | 可空 |
|
||
| `created_at` / `updated_at` | `timestamptz` | 审计字段 |
|
||
|
||
约束:
|
||
|
||
```sql
|
||
UNIQUE (theme_id, style_key)
|
||
```
|
||
|
||
现有样式键继续保留:
|
||
|
||
- `node-card`
|
||
- `core-card`
|
||
- `power-card`
|
||
- `power-node-card`
|
||
- `vehicle-card`
|
||
|
||
这样数据迁移最小,页面也容易渐进切换。
|
||
|
||
### 5.3 `diagram_edge_styles`
|
||
|
||
连接样式表按业务连接类型定义线条表现。
|
||
|
||
建议字段:
|
||
|
||
| 字段 | 类型 | 说明 |
|
||
|---|---|---|
|
||
| `id` | `uuid` | 主键 |
|
||
| `theme_id` | `uuid` | 所属主题 |
|
||
| `connection_type` | `text` | 对应 `topology_connections.connection_type` |
|
||
| `display_name` | `text` | 例如 `加压走道` |
|
||
| `stroke_color` | `text` | 线条颜色 |
|
||
| `stroke_width` | `numeric` | 线宽 |
|
||
| `dash_array` | `text` | 可空,例如 `13 10` |
|
||
| `line_cap` | `text` | 例如 `square` |
|
||
| `legend_group` | `text` | 可空,用于多个连接类型共用一个图例 |
|
||
| `legend_order` | `integer` | 图例排序辅助 |
|
||
| `created_at` / `updated_at` | `timestamptz` | 审计字段 |
|
||
|
||
约束:
|
||
|
||
```sql
|
||
UNIQUE (theme_id, connection_type)
|
||
```
|
||
|
||
当前建议映射:
|
||
|
||
| `connection_type` | 默认图例 | 默认表现 |
|
||
|---|---|---|
|
||
| `structural_mount` | 结构直连 | 灰蓝色实线 |
|
||
| `pressurized_passage` | 加压走道 | 绿色实线 |
|
||
| `fuel` | 燃料 / 供电 | 紫色虚线 |
|
||
| `power` | 燃料 / 供电 | 紫色虚线 |
|
||
| `cooling` | 冷却 | 预留,可暂不显示图例 |
|
||
| `docking` | 对接口 | 预留 |
|
||
|
||
如果 `fuel` 和 `power` 继续共用图例,可以让两条记录使用同一个 `legend_group = 'utility'`。
|
||
|
||
### 5.4 `diagram_decoration_styles`
|
||
|
||
装饰件样式表定义散热器等非组件元素的表现。装饰件是否出现仍由 `diagram_nodes.decorations` 决定。
|
||
|
||
建议字段:
|
||
|
||
| 字段 | 类型 | 说明 |
|
||
|---|---|---|
|
||
| `id` | `uuid` | 主键 |
|
||
| `theme_id` | `uuid` | 所属主题 |
|
||
| `decoration_key` | `text` | 例如 `radiator` |
|
||
| `display_name` | `text` | 例如 `大型折叠散热面板` |
|
||
| `fill_color` | `text` | 主体填充色 |
|
||
| `stroke_color` | `text` | 主体描边色 |
|
||
| `stroke_width` | `numeric` | 主体描边宽度 |
|
||
| `label` | `text` | 图上短标签,例如 `散热器` |
|
||
| `label_color` | `text` | 标签颜色 |
|
||
| `render_params` | `jsonb` | 小规模绘制参数 |
|
||
| `legend_order` | `integer` | 图例排序辅助 |
|
||
| `created_at` / `updated_at` | `timestamptz` | 审计字段 |
|
||
|
||
约束:
|
||
|
||
```sql
|
||
UNIQUE (theme_id, decoration_key)
|
||
```
|
||
|
||
`render_params` 示例:
|
||
|
||
```json
|
||
{
|
||
"widthRatio": 0.55,
|
||
"maxWidth": 130,
|
||
"height": 16,
|
||
"offsetXRatio": 0.55,
|
||
"offsetY": -18,
|
||
"ribCount": 3
|
||
}
|
||
```
|
||
|
||
`render_params` 只用于装饰件的小型形状参数。它不承载任意 SVG,也不允许注入脚本或 HTML。
|
||
|
||
### 5.5 `diagram_legend_items`
|
||
|
||
图例可以从节点、连接和装饰件样式自动推导,但为了保证顺序和文案稳定,建议单独建表。
|
||
|
||
建议字段:
|
||
|
||
| 字段 | 类型 | 说明 |
|
||
|---|---|---|
|
||
| `id` | `uuid` | 主键 |
|
||
| `theme_id` | `uuid` | 所属主题 |
|
||
| `legend_key` | `text` | 例如 `pressurized` |
|
||
| `label` | `text` | 例如 `加压走道` |
|
||
| `item_type` | `text` | `edge`、`decoration`、`node` |
|
||
| `style_ref` | `text` | 引用 `connection_type`、`decoration_key` 或 `style_key` |
|
||
| `display_order` | `integer` | 显示顺序 |
|
||
| `is_visible` | `boolean` | 是否显示 |
|
||
|
||
约束:
|
||
|
||
```sql
|
||
UNIQUE (theme_id, legend_key)
|
||
CHECK (item_type IN ('edge', 'decoration', 'node'))
|
||
```
|
||
|
||
当前图例建议:
|
||
|
||
1. `structural`:结构直连,引用 `structural_mount`
|
||
2. `pressurized`:加压走道,引用 `pressurized_passage`
|
||
3. `utility`:燃料 / 供电,引用 `fuel` 或 `power` 中任一代表样式
|
||
4. `radiator`:大型折叠散热面板,引用 `radiator`
|
||
|
||
### 5.6 `diagram_layouts` 扩展
|
||
|
||
为布局绑定默认主题:
|
||
|
||
| 字段 | 类型 | 说明 |
|
||
|---|---|---|
|
||
| `theme_id` | `uuid` | 引用 `diagram_themes(id)`,可空;为空时使用基地默认主题 |
|
||
|
||
建议约束:
|
||
|
||
```sql
|
||
ALTER TABLE topology.diagram_layouts
|
||
ADD COLUMN theme_id uuid REFERENCES topology.diagram_themes(id);
|
||
```
|
||
|
||
### 5.7 `diagram_nodes` 扩展
|
||
|
||
现有字段基本足够,但建议补一个可选字段:
|
||
|
||
| 字段 | 类型 | 说明 |
|
||
|---|---|---|
|
||
| `render_meta` | `jsonb` | 节点级小规模渲染参数,例如特殊文本锚点;首期可不使用 |
|
||
|
||
首期可以不新增 `render_meta`,只让 `style_key` 指向 `diagram_node_styles`。如果后续发现某个节点需要特殊文本位置,再引入该字段。
|
||
|
||
## 6. API 设计
|
||
|
||
### 6.1 快照响应结构
|
||
|
||
现有 `/api/v1/bases/guanghan/snapshot` 继续返回 `base`、`query`、`components`、`connections`、`layout`。新增 `layout.presentation`。
|
||
|
||
建议结构:
|
||
|
||
```json
|
||
{
|
||
"layout": {
|
||
"layout": {
|
||
"key": "engineering_overview_v1",
|
||
"name": "工程总图 v1",
|
||
"canvasWidth": 1500,
|
||
"canvasHeight": 1900,
|
||
"themeKey": "guanghan_dark_engineering_v1"
|
||
},
|
||
"nodes": [
|
||
{
|
||
"nodeKey": "core_cabin",
|
||
"styleKey": "core-card",
|
||
"x": 630,
|
||
"y": 470,
|
||
"width": 240,
|
||
"height": 200,
|
||
"memberKeys": ["core_cabin"]
|
||
}
|
||
],
|
||
"presentation": {
|
||
"theme": {
|
||
"key": "guanghan_dark_engineering_v1",
|
||
"name": "广寒深色工程图",
|
||
"tokens": {
|
||
"textColor": "#eaf2ff",
|
||
"mutedTextColor": "#91a3bd"
|
||
}
|
||
},
|
||
"nodeStyles": {
|
||
"core-card": {
|
||
"fillColor": "#3b250d",
|
||
"strokeColor": "#ffad42",
|
||
"strokeWidth": 5,
|
||
"cornerRadius": 16,
|
||
"titleColor": "#eaf2ff",
|
||
"metaColor": "#a6b5c9",
|
||
"hintColor": "#71849e"
|
||
}
|
||
},
|
||
"edgeStyles": {
|
||
"pressurized_passage": {
|
||
"displayName": "加压走道",
|
||
"strokeColor": "#51e89c",
|
||
"strokeWidth": 9,
|
||
"dashArray": null,
|
||
"lineCap": "square",
|
||
"legendGroup": "pressurized"
|
||
}
|
||
},
|
||
"decorationStyles": {
|
||
"radiator": {
|
||
"displayName": "大型折叠散热面板",
|
||
"fillColor": "#6b5814",
|
||
"strokeColor": "#f0d869",
|
||
"strokeWidth": 2,
|
||
"label": "散热器",
|
||
"labelColor": "#f4df7b",
|
||
"renderParams": {
|
||
"widthRatio": 0.55,
|
||
"maxWidth": 130,
|
||
"height": 16,
|
||
"offsetXRatio": 0.55,
|
||
"offsetY": -18,
|
||
"ribCount": 3
|
||
}
|
||
}
|
||
},
|
||
"legendItems": [
|
||
{
|
||
"key": "pressurized",
|
||
"label": "加压走道",
|
||
"itemType": "edge",
|
||
"styleRef": "pressurized_passage",
|
||
"displayOrder": 20
|
||
}
|
||
]
|
||
}
|
||
}
|
||
}
|
||
```
|
||
|
||
### 6.2 缺省与错误处理
|
||
|
||
API 查询布局时:
|
||
|
||
1. 使用默认布局;
|
||
2. 如果布局绑定了主题,使用该主题;
|
||
3. 如果布局未绑定主题,使用基地默认主题;
|
||
4. 如果节点引用的 `style_key` 不存在,API 应返回明确错误或在响应中标记 `presentationWarnings`。
|
||
|
||
建议首期采用“API 返回 500/配置错误,不静默降级”的策略。拓扑图是工程资料,缺失样式不应伪装成正确页面。
|
||
|
||
前端可以有开发兜底色,但只用于防止页面彻底空白,不能作为测试验收依据。
|
||
|
||
### 6.3 样式值安全
|
||
|
||
API 应只返回白名单字段。颜色值应校验为:
|
||
|
||
- `#RGB`
|
||
- `#RRGGBB`
|
||
- `rgb(...)`
|
||
- `rgba(...)`
|
||
- 少量受控命名色如 `transparent`
|
||
|
||
首期建议只使用 `#RRGGBB`,简单、稳定、可测试。
|
||
|
||
`dash_array` 只允许数字和空格,例如 `13 10`。
|
||
`line_cap` 只允许 `butt`、`round`、`square`。
|
||
`render_params` 只允许预定义键,不允许任意 SVG 属性透传。
|
||
|
||
## 7. 前端渲染设计
|
||
|
||
### 7.1 节点
|
||
|
||
当前逻辑:
|
||
|
||
```text
|
||
rect.class = node.styleKey
|
||
CSS 决定 fill/stroke/stroke-width
|
||
```
|
||
|
||
目标逻辑:
|
||
|
||
```text
|
||
style = presentation.nodeStyles[node.styleKey]
|
||
rect.setAttribute('fill', style.fillColor)
|
||
rect.setAttribute('stroke', style.strokeColor)
|
||
rect.setAttribute('stroke-width', style.strokeWidth)
|
||
rect.setAttribute('rx', style.cornerRadius)
|
||
```
|
||
|
||
文本颜色同理从节点样式或主题 token 获取。
|
||
|
||
### 7.2 连接
|
||
|
||
当前逻辑:
|
||
|
||
```text
|
||
connection.type -> connectionClass(type)
|
||
CSS 决定颜色和虚实线
|
||
```
|
||
|
||
目标逻辑:
|
||
|
||
```text
|
||
style = presentation.edgeStyles[connection.type]
|
||
line.stroke = style.strokeColor
|
||
line.strokeWidth = style.strokeWidth
|
||
line.strokeDasharray = style.dashArray
|
||
line.strokeLinecap = style.lineCap
|
||
```
|
||
|
||
连接合并逻辑保留:多个数据库连接如果落在同一对视觉节点之间,并且使用同一种连接类型或同一个视觉样式,可以合并成一条线。
|
||
|
||
### 7.3 装饰件
|
||
|
||
当前逻辑:
|
||
|
||
```text
|
||
if node.decorations.radiator:
|
||
createRadiator(node)
|
||
```
|
||
|
||
目标逻辑:
|
||
|
||
```text
|
||
for each decorationKey in node.decorations:
|
||
style = presentation.decorationStyles[decorationKey]
|
||
createKnownDecoration(decorationKey, node, style)
|
||
```
|
||
|
||
首期只实现 `radiator` 这一种已知装饰件。后续新增装饰件时,应先在前端注册一个安全的已知 renderer,再允许数据库使用该 `decoration_key`。
|
||
|
||
### 7.4 图例
|
||
|
||
当前图例由 HTML 写死。目标是:
|
||
|
||
1. 页面保留空的 `<div id="legend">`;
|
||
2. 前端遍历 `presentation.legendItems`;
|
||
3. 根据 `itemType` 和 `styleRef` 找到对应样式;
|
||
4. 创建线段或色块示例。
|
||
|
||
这样图例顺序、文案和显示/隐藏由数据库决定。
|
||
|
||
## 8. Seed 数据建议
|
||
|
||
首期 seed 应把当前用户已认可的视觉效果完整落库:
|
||
|
||
### 8.1 节点样式
|
||
|
||
| `style_key` | 用途 |
|
||
|---|---|
|
||
| `core-card` | 广寒核心舱 |
|
||
| `node-card` | 普通舱段 |
|
||
| `power-card` | 电力模块分支 |
|
||
| `power-node-card` | 电力模块中心节点 |
|
||
| `vehicle-card` | 吴刚/冰轮等车辆 |
|
||
|
||
### 8.2 连接样式
|
||
|
||
| `connection_type` | 图例 | 要求 |
|
||
|---|---|---|
|
||
| `structural_mount` | 结构直连 | 灰蓝实线 |
|
||
| `pressurized_passage` | 加压走道 | 绿色实线 |
|
||
| `fuel` | 燃料 / 供电 | 紫色虚线 |
|
||
| `power` | 燃料 / 供电 | 紫色虚线 |
|
||
|
||
### 8.3 装饰件样式
|
||
|
||
| `decoration_key` | 用途 |
|
||
|---|---|
|
||
| `radiator` | 电力模块四个大分支顶部的大型折叠散热面板 |
|
||
|
||
散热器继续不是独立组件,不出现在弹窗里,不覆盖加压走道。
|
||
|
||
## 9. 测试策略
|
||
|
||
### 9.1 API 测试
|
||
|
||
新增测试应覆盖:
|
||
|
||
- snapshot 响应包含 `layout.presentation`;
|
||
- `nodeStyles` 包含所有 `diagram_nodes.style_key`;
|
||
- `edgeStyles` 包含当前快照里所有 `connections.type`;
|
||
- `legendItems` 按 `displayOrder` 排序;
|
||
- `radiator` 装饰件样式存在;
|
||
- 缺失样式时返回明确配置错误。
|
||
|
||
### 9.2 前端源码测试
|
||
|
||
源码测试应确认:
|
||
|
||
- 页面不再硬编码图例文字;
|
||
- 页面不再通过 `.core-card`、`.pressurized` 等 CSS 类决定业务颜色;
|
||
- 页面读取 `presentation.nodeStyles`、`presentation.edgeStyles`、`presentation.decorationStyles`、`presentation.legendItems`。
|
||
|
||
### 9.3 浏览器端到端测试
|
||
|
||
E2E 应覆盖:
|
||
|
||
- GHC-01、GHC-05 正常渲染;
|
||
- GHC-05 有两条绿色加压走道;
|
||
- 图例来自 API;
|
||
- 打开模块弹窗正常;
|
||
- 修改测试数据库中的 `pressurized_passage.stroke_color` 后,浏览器渲染颜色变化;
|
||
- 修改 `core-card.fill_color` 后,核心舱填充颜色变化;
|
||
- 历史任务节点/连接/散热器数量不回退。
|
||
|
||
### 9.4 截图验收
|
||
|
||
实现阶段每次页面修改后仍遵循现有要求:必须自己截图检查效果。
|
||
|
||
至少保留:
|
||
|
||
- GHC-05 顶部/中部/底部截图;
|
||
- GHC-01 早期快照截图;
|
||
- 图例截图;
|
||
- 修改测试主题颜色后的验证截图。
|
||
|
||
## 10. 实施分期建议
|
||
|
||
### Phase 1:数据库与 API
|
||
|
||
- 新增表现层迁移;
|
||
- seed 当前已认可样式;
|
||
- API 返回 `layout.presentation`;
|
||
- 增加 API 单元测试。
|
||
|
||
### Phase 2:前端切换
|
||
|
||
- 图例改为从 `presentation.legendItems` 生成;
|
||
- 节点、连接、散热器改为使用 API 样式;
|
||
- 移除业务颜色 CSS 的事实来源角色;
|
||
- 保留通用 CSS 和交互样式。
|
||
|
||
### Phase 3:验证与清理
|
||
|
||
- 跑完整单元测试和 E2E;
|
||
- 截图核对 GHC-01 到 GHC-05;
|
||
- 用测试数据临时改颜色,验证前端无代码修改即可变化;
|
||
- 更新验收报告。
|
||
|
||
## 11. 与未来扩展的关系
|
||
|
||
未来核心舱北、东、西三方向会继续扩展十字结构,北部成为多台吴刚着陆器连接点,西部成为多个 rover 连接点。B1 表现层设计支持这种扩展:
|
||
|
||
- 新节点继续写入 `diagram_nodes`;
|
||
- 新节点使用已有或新增 `style_key`;
|
||
- 新连接类型如果需要新视觉表现,只新增 `diagram_edge_styles` 和 `diagram_legend_items`;
|
||
- 未来扩展锚点仍不在页面显示,只有实际组件在快照时间存在后才渲染。
|
||
|
||
如果将来需要同时支持“工程总图”“简化拓扑图”“施工阶段图”等多个视图,可以新增不同 `diagram_layouts.layout_key`,并让 API 支持 `layout=` 参数。但这不是本轮 B1 的首期目标。
|
||
|
||
## 12. 决策摘要
|
||
|
||
本设计采用 B1:表现层数据库化。
|
||
|
||
明确放入数据库:
|
||
|
||
- 节点位置和尺寸;
|
||
- 节点颜色、描边、圆角;
|
||
- 连接线颜色、线宽、虚实线;
|
||
- 散热器基础视觉参数;
|
||
- 图例项。
|
||
|
||
明确留在前端:
|
||
|
||
- 页面壳、弹窗、工具栏、响应式;
|
||
- hover/focus;
|
||
- 文本截断;
|
||
- SVG 创建和交互事件;
|
||
- 安全的已知装饰件 renderer。
|
||
|
||
这个边界能满足“由后台数据库决定各组件渲染位置、颜色等信息”,同时避免把数据库变成一个难维护的 HTML/CSS 仓库。
|