# 第三步：代码质量与排除规则

## 类名与清理逻辑

* **类名语义化**：基于 `node.name`。将中文名称翻译为简洁的英文类名（如 `container`, `submitBtn`, `titleWrapper`），**类名使用 camelCase**，以便在 JS 中作为 `styles.xxx` 使用。
* **清理逻辑（结构清理补丁 / Anti-Noise）**：
  * 忽略 `visible: false` 的节点。
  * 移除类名中的非法 CSS 字符（如冒号、空格、特殊符号）；在 Less 中类名与 React 中的 `styles.xxx` 一一对应。
* **样式合并**：若一个容器仅包含一个背景矩形（无其他有效子内容），将矩形的 `fill` 和 `borderRadius` 直接提升至容器属性，避免生成冗余的绝对定位矩形层。若该矩形为「仅纯色矩形」且兄弟存在图片填充，可按 [07-dsl-fields.md](./07-dsl-fields.md) 的冗余纯色矩形规则过滤。
* **无效层级过滤**：位于导航栏内的 `StatusBar` 子树应被物理剔除（见下方「特定排除」）。

---

## 导航栏（NavBar）规则

* **优先使用 SmartUI NavBar**：设计稿中的顶部导航栏区域优先使用 `@ray-js/smart-ui` 的 `NavBar` 组件实现。根据设计稿中的标题、返回箭头、左右文本/图标等信息映射为 NavBar 的 `title`、`leftArrow`、`leftText`、`rightIcon`、`rightText`、`background` 等 props。
* **右侧不实现胶囊**：小程序容器运行时会自带胶囊，代码中不要手动实现。

### NavBar 深色背景适配

当页面使用深色背景（如黑底面板）+ `navigationStyle: 'custom'` 时，NavBar 的默认文字颜色（黑色）在深色背景上不可见。

#### 首选方案：`customClass` + CSS 变量覆盖

通过 **`customClass`**（非 `className`）注入 CSS 变量，控制 NavBar 内部文字颜色：

```tsx
<NavBar
  title={Strings.editSceneTitle}
  leftText={Strings.cancel}
  border={false}
  background="transparent"
  safeAreaInsetTop
  customClass={styles.darkNav}
/>
```

```less
.darkNav {
  --nav-bar-title-text-color: #ffffff;
  --nav-bar-text-color: #ffffff;
  --nav-bar-arrow-color: #ffffff;
  --nav-bar-icon-color: #ffffff;
}
```

**⚠️ 关键注意事项**：

1. **必须使用 `customClass`，不要使用 `className`**：`className` 只挂载在外层包装标签上，CSS 变量无法穿透到组件内部节点；`customClass` 挂载在内部根节点（`.smart-nav-bar`），CSS 变量才能正确级联到子元素。此规则适用于所有 SmartUI 组件。

2. **`leftTextType="home"` 使用不同的 CSS 变量**：首页样式的文字颜色由 `--nav-bar-home-text-color` 控制，设置 `--nav-bar-text-color` 对其**无效**。

```less
// 二级页面（title / leftText）
.darkNav {
  --nav-bar-title-text-color: #ffffff;
  --nav-bar-text-color: #ffffff;
}

// 首页（leftTextType="home"）
.darkNavHome {
  --nav-bar-home-text-color: #ffffff;  // ← 必须用这个变量
}
```

3. `customStyle={{ color: '#fff' }}` 不能覆盖内部文字颜色，必须使用对应的 CSS 变量。完整变量列表见 → [09-smart-ui-dark-theme.md](./09-smart-ui-dark-theme.md)。

#### 回退方案：自定义 View 导航头

若 CSS 变量方案在特定版本不生效（UI 校对发现标题不可见），回退为自定义 View：

```tsx
<View className={styles.navBar}>
  <Text className={styles.navTitle}>{Strings.deviceName}</Text>
</View>
```

```less
.navBar {
  position: relative;
  z-index: 2;
  display: flex;
  align-items: center;
  padding: 0 20rpx 0 32rpx;
  height: 88rpx;
  margin-top: 88rpx; /* 状态栏高度 */
}
.navTitle {
  font-size: 44rpx;
  font-weight: 600;
  color: #ffffff;
}
```

* **判断标准**：截屏后如果标题区域为空但 DOM 快照（`take_snapshot`）中文本节点存在 → 确认为颜色不可见问题 → 先尝试 `customClass` + CSS 变量方案，不生效再使用 View 回退。

---

## 特定排除

* **StatusBar 过滤**：若节点位于「导航栏」内部且 `name` 包含 "StatusBar"、"状态栏" 或相关电量/时间信息，请**跳过整棵子树**，不生成任何代码。
* **Capsule 过滤**：若节点位于「导航栏」内部且 `name` 为 "Capsule"（或包含 "Capsule"），请**跳过该节点及其整棵子树**，不生成任何代码。**导航栏顶部右侧不要实现胶囊**，因小程序运行时会自带胶囊。
* **NavBar 内部子节点**：导航栏整体已由 SmartUI `NavBar` 组件接管，导航栏内的具体子节点（标题文本、返回图标等）无需逐个手动生成，只需映射为 NavBar 的 props 即可。
