Files
UnityAI/03_核心功能/UI/UI界面拼接设计指南.md
Shiliang 411c34d664 docs(UI): 更新UI界面拼接设计指南
添加双向转换功能说明:
- 正向转换:JSON配置 → UI预制体
- 反向转换:UI预制体 → JSON配置

新增支持的组件类型:
- InputField、ScrollRect、GridLayoutGroup、VerticalLayoutGroup、HorizontalLayoutGroup

新增命令支持:
- ExportPrefabToJson:从预制体反向导出JSON

更新使用示例:
- 外部命令触发方式
- Unity编辑器菜单入口
- 代码调用示例
2026-05-27 15:52:23 +08:00

14 KiB
Raw Blame History

UI界面拼接设计指南

一、界面结构设计原则

1.1 模块化拆分

将界面按功能划分为独立模块:

模块类型 功能定位 示例
信息展示区 显示玩家状态、资源等静态信息 顶部信息栏、左侧状态栏
功能入口区 提供功能按钮入口 中央功能区、底部快捷栏
交互面板区 可展开/收起的功能面板 右侧功能面板、顶部按钮区
输入输出区 用户输入和系统反馈 聊天输入框、提示信息

1.2 经典布局模式

┌─────────────────────────────────────────────────────┐
│  TopArea          (信息展示 + 可收起功能按钮)        │
├──────────┬───────────────────────┬──────────────────┤
│  Left    │                       │  Right           │
│  Area    │     CenterArea        │  Area            │
│ (状态)   │   (核心功能入口)       │ (功能面板)       │
│          │                       │                  │
├──────────┴───────────────────────┴──────────────────┤
│  BottomArea       (快捷功能 + 状态信息 + 输入)       │
└─────────────────────────────────────────────────────┘

二、组件拆分方法

2.1 基础组件识别

组件类型 识别特征 处理方式
按钮 可点击、有交互反馈 使用 SFUI_Button
文本 静态/动态文字显示 使用 SFUI_TextMeshProUGUI
图片 图标、背景图 使用 SFUI_Image
进度条 HP、MP、经验等 使用 SFUI_Slider
列表 可滚动的项目列表 使用 SFUI_ScrollRect

2.2 复合组件封装

将功能相关的基础组件组合为复合组件,便于复用和维护:

设计原则

  • 将同一功能模块的组件封装在一起(如玩家头像+血条+蓝条)
  • 提供统一的数据设置接口
  • 保持组件之间的逻辑独立性

三、预制体层级规范

3.1 标准层级结构

WindowName (RectTransform)
├── ModuleName (RectTransform)           # 模块容器
│   ├── ComponentName (SFUI_*)           # 功能组件
│   ├── SubModule (RectTransform)        # 子模块
│   └── CollapsibleArea (RectTransform)  # 可收起区域
└── BtnCollapse (SFUI_Button)            # 收起控制按钮

3.2 命名规范

类型 命名规则 示例
模块容器 PascalCase + Area TopArea
功能组件 PascalCase BtnCollapseTop
可收起区域 PascalCase + FuncArea TopFuncArea
状态变量 m_ + PascalCase m_IsTopCollapsed

四、收起/展开功能设计

4.1 功能定义

按钮 控制区域 用途
BtnCollapseTop 顶部功能按钮区 收起/展开顶部按钮群
BtnCollapseRight 右侧功能面板区 收起/展开右侧功能面板

4.2 设计要点

状态管理:每个可收起区域需要一个布尔状态变量来记录当前收起/展开状态。

交互逻辑

  1. 点击收起按钮时,切换对应区域的显示/隐藏状态
  2. 同时切换按钮图标(收起时显示展开图标,展开时显示收起图标)

布局要求

  • 收起按钮应放置在对应区域的边缘位置,便于用户找到
  • 收起区域内的所有元素应作为一个整体进行显示/隐藏控制
  • 收起状态应在窗口生命周期内保持记忆

五、实际案例:主界面拼接

5.1 模块化设计思想

核心原则:将界面按功能边界划分为独立模块,模块内可嵌套子模块。

模块归类方法

  1. 一级模块:按空间位置划分(顶部、左侧、中央、右侧、底部)
  2. 二级模块:按功能类型划分(信息展示区、功能按钮区、输入输出区)
  3. 三级模块:按具体功能划分(玩家头像、资源显示、功能按钮群)

层级关系示例

Window
├── TopArea (一级:位置)
│   ├── InfoPanel (二级:信息展示)
│   │   └── TxtWelcome (三级:具体组件)
│   └── FuncButtons (二级:功能按钮)
│       └── BtnUpload (三级:具体按钮)
└── LeftArea (一级:位置)
    └── PlayerPortrait (二级:复合组件)
        ├── ImgAvatar (三级:头像)
        └── BarHP (三级:血条)

设计要点

  • 同一功能域内的元素归为同一模块(如头像、血条、蓝条归为玩家状态模块)
  • 独立交互功能作为独立模块(如收起按钮单独作为控制模块)
  • 可收起区域作为独立子模块,便于统一控制显示/隐藏

六、界面拼接流程

6.1 设计阶段

  1. 需求分析:明确界面功能和交互需求
  2. 模块划分:将界面拆分为独立功能模块
  3. 层级设计:设计预制体层级结构

6.2 开发阶段

  1. 组件创建:创建基础组件和复合组件
  2. 预制体搭建:按层级结构搭建预制体
  3. 脚本编写:实现交互逻辑和收起/展开功能

6.3 测试阶段

  1. 功能测试:验证所有按钮和交互功能
  2. 收起测试:测试收起/展开功能正常工作
  3. 适配测试:验证不同分辨率下的显示效果

七、注意事项

  1. 组件复用:相同功能的组件尽量复用,减少冗余
  2. 状态管理:收起状态需要正确保存和恢复
  3. 图标反馈:收起按钮图标应随状态变化
  4. 性能优化:可收起区域使用 SetActive 而非销毁重建
  5. 命名规范:统一的命名规则便于维护和查找

八、JSON配置驱动的UI生成方式

8.1 概述

本项目支持JSON配置与Unity预制体的双向转换

  • 正向转换JSON配置 → UI预制体
  • 反向转换UI预制体 → JSON配置

实现UI界面的快速构建、迭代和版本控制。

8.2 核心组件

组件 职责 文件路径
UIPrefabGenerator 解析JSON并生成UI预制体 Assets/Editor/Command/UIPrefabGenerator.cs
UIPrefabToJson 从预制体反向导出JSON Assets/Editor/Command/UIPrefabToJson.cs
RemoteCommand 提供外部调用接口 Assets/Editor/Command/RemoteCommand.cs
ExternalCommandListener 监听外部命令触发文件 Assets/Editor/Command/ExternalCommandListener.cs

8.3 JSON配置文件结构

{
  "name": "BagWindow",
  "width": 1024,
  "height": 768,
  "elements": [
    {
      "type": "Image",
      "name": "BgPanel",
      "anchorMin": [0, 0],
      "anchorMax": [1, 1],
      "position": [0, 0, 0],
      "sizeDelta": [0, 0],
      "sprite": "Assets/Game/GameHFResource/CN/UIWindows/BagWindow/Sprites/Bg.png"
    },
    {
      "type": "Text",
      "name": "TitleText",
      "anchorMin": [0.5, 0.9],
      "anchorMax": [0.5, 0.9],
      "position": [0, 0, 0],
      "sizeDelta": [200, 40],
      "text": "背包",
      "font": "Assets/Game/GameHFResource/CN/Fonts/FZY4K-M05S SDF.asset",
      "fontSize": 28,
      "color": [1, 1, 1, 1]
    }
  ]
}

8.4 支持的UI元素类型

类型 对应Unity组件 关键属性
Image Image sprite, color, type, preserveAspect
TextMeshProUGUI TextMeshProUGUI text, font, fontSize, color, alignment
Button Button interactable, transition, navigationMode
Slider Slider minValue, maxValue, value, wholeNumbers, direction
Toggle Toggle isOn, toggleTransition, transition
InputField InputField text, placeholder, characterLimit, contentType
ScrollRect ScrollRect horizontal, vertical, movementType
GridLayoutGroup GridLayoutGroup cellSize, spacing, constraint, padding
VerticalLayoutGroup VerticalLayoutGroup spacing, childAlignment, padding
HorizontalLayoutGroup HorizontalLayoutGroup spacing, childAlignment, padding

8.5 外部命令触发机制

8.5.1 触发方式

通过创建/修改 Trigger_Command.txt 文件触发UI生成

GenerateUIPrefab:Assets/Editor/UI/BagWindow.json

8.5.2 命令格式

<命令名>:<参数1>:<参数2>:...

支持的命令

命令 参数 说明
GenerateUIPrefab jsonPath [, prefabPath] 根据JSON生成UI预制体
ExportPrefabToJson prefabPath [, jsonPath] 从预制体反向导出JSON
ReadJson [参数列表] 读取JSON配置测试用

8.5.3 完整执行流程

┌─────────────────────────────────────────────────────────────────────┐
│  外部系统写入命令到 Trigger_Command.txt                             │
└─────────────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────────────┐
│  ExternalCommandListener (FileSystemWatcher) 检测到文件变化         │
└─────────────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────────────┐
│  解析命令格式GenerateUIPrefab:Assets/Editor/UI/BagWindow.json     │
└─────────────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────────────┐
│  通过反射调用 RemoteCommand.GenerateUIPrefab(string[] args)         │
└─────────────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────────────┐
│  UIPrefabGenerator.GeneratePrefabFromJson(jsonPath, prefabPath)    │
└─────────────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────────────┐
│  生成预制体到指定路径Assets/Game/GameHFResource/CN/UIWindows/...  │
└─────────────────────────────────────────────────────────────────────┘

8.6 Unity编辑器菜单测试

在Unity编辑器中提供了测试菜单

菜单路径 功能
Tools > UI > Export Prefab to JSON 选择预制体导出JSON
Tools > UI > Generate BagWindow Prefab 生成BagWindow预制体
Tools > External > Test ReadJson 测试ReadJson命令
Tools > External > Test GenerateUIPrefab 测试正向生成
Tools > External > Test ExportPrefabToJson 测试反向导出

8.7 使用示例

方式一:外部命令触发

# 正向从JSON生成预制体
echo "GenerateUIPrefab:Assets/Editor/UI/BagWindow.json" > "F:\JMNet\CrystalBattle_Client\Trigger_Command.txt"

# 反向从预制体导出JSON
echo "ExportPrefabToJson:Assets/Game/GameHFResource/CN/UIWindows/BagWindow/BagWindow.prefab" > "F:\JMNet\CrystalBattle_Client\Trigger_Command.txt"

方式二Unity编辑器菜单

正向生成

  1. 打开Unity编辑器
  2. 点击菜单 Tools > External > Test GenerateUIPrefab
  3. 查看Console窗口日志确认执行结果

反向导出

  1. 打开Unity编辑器
  2. 点击菜单 Tools > UI > Export Prefab to JSON
  3. 选择要导出的预制体文件

方式三:代码调用

// 正向从JSON生成预制体
UIPrefabGenerator.GeneratePrefabFromJson(
    "Assets/Editor/UI/BagWindow.json",
    "Assets/Game/GameHFResource/CN/UIWindows/BagWindow/BagWindow.prefab"
);

// 反向从预制体导出JSON
UIPrefabToJson.ExportPrefabToJson(
    "Assets/Game/GameHFResource/CN/UIWindows/BagWindow/BagWindow.prefab",
    "Assets/Editor/UI/BagWindow.json"
);

8.8 注意事项

  1. 路径格式JSON中的资源路径使用 / 分隔符且为Unity项目相对路径
  2. 资源引用确保JSON中引用的Sprite、Font等资源已存在于项目中
  3. 编码格式JSON文件使用UTF-8编码
  4. 坐标系统使用Unity RectTransform的anchorMin/anchorMax/position/sizeDelta四元组
  5. 文件锁定:生成前确保目标预制体文件未被其他进程占用

版本: v1.1
适用: StrayFog框架UI拼接开发人员