# 开发者指南
**本文档引用的文件**
- [GeoMative.cpp](file://cpp/Main/GeoMative.cpp)
- [Global.cpp](file://cpp/Main/Global.cpp)
- [ProManager.cpp](file://cpp/Managers/ProManager.cpp)
- [DevManager.cpp](file://cpp/Managers/DevManager.cpp)
- [ExecManager.cpp](file://cpp/Managers/ExecManager.cpp)
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp)
- [TdManager.cpp](file://cpp/Managers/TdManager.cpp)
- [IOManager.cpp](file://cpp/Managers/IOManager.cpp)
- [GeoMative.h](file://h/GeoMative.h)
- [Constant.h](file://h/Constant.h)
## 目录
1. [项目结构](#项目结构)
2. [核心架构模式](#核心架构模式)
3. [关键常量与全局函数](#关键常量与全局函数)
4. [代码贡献指南](#代码贡献指南)
5. [调试技巧](#调试技巧)
6. [扩展开发最佳实践](#扩展开发最佳实践)
## 项目结构
Geomative Studio 项目采用模块化设计,各目录职责划分清晰,便于维护和扩展。核心代码位于 `cpp` 目录下,按功能划分为多个子目录。
```mermaid
graph TD
subgraph "核心模块"
Managers["Managers
管理器模块"]
Operator["Operator
操作器模块"]
ProblemZone["ProblemZone
数据模型"]
Views["Views
视图与UI"]
end
subgraph "基础组件"
Main["Main
应用入口"]
Tools["Tools
工具类"]
Lock["Lock
线程锁"]
end
subgraph "外部依赖"
h["h
头文件"]
res["res
资源文件"]
end
Main --> Managers
Managers --> Operator
Operator --> ProblemZone
ProblemZone --> Views
Tools --> Managers
Tools --> Operator
```
**目录来源**
- [cpp/Main/GeoMative.cpp](file://cpp/Main/GeoMative.cpp)
- [cpp/Managers/ProManager.cpp](file://cpp/Managers/ProManager.cpp)
- [cpp/Operator/DataOperator.cpp](file://cpp/Operator/DataOperator.cpp)
- [cpp/ProblemZone/Project.cpp](file://cpp/ProblemZone/Project.cpp)
- [cpp/Views/MainFrm.cpp](file://cpp/Views/MainFrm.cpp)
- [cpp/Tools/FileOperTools.cpp](file://cpp/Tools/FileOperTools.cpp)
**模块职责说明:**
- **cpp/Managers**: 包含应用程序的核心管理器类,负责业务逻辑的组织与协调。每个管理器(如 `ProManager`, `DevManager`)负责一个特定领域的数据和操作。
- **cpp/Operator**: 包含具体的操作实现类,负责执行与设备、数据、脚本等交互的具体操作。这些类通常被管理器调用以完成复杂的业务流程。
- **cpp/ProblemZone**: 定义了应用程序的核心数据模型,如 `Project`, `TestingZone`, `Device` 等。这些类代表了数据库中的实体,并封装了相关的数据和行为。
- **cpp/Views**: 包含所有用户界面相关的类,如对话框、视图和框架窗口。这些类负责与用户交互并展示数据。
**Section sources**
- [cpp/Main/GeoMative.cpp](file://cpp/Main/GeoMative.cpp)
- [cpp/Managers/ProManager.cpp](file://cpp/Managers/ProManager.cpp)
- [cpp/Operator/DataOperator.cpp](file://cpp/Operator/DataOperator.cpp)
- [cpp/ProblemZone/Project.cpp](file://cpp/ProblemZone/Project.cpp)
- [cpp/Views/MainFrm.cpp](file://cpp/Views/MainFrm.cpp)
## 核心架构模式
本应用程序采用了多种经典的设计模式来确保代码的可维护性、可扩展性和松耦合。
### 单例模式 (Singleton Pattern)
`CGeoMativeApp` 类是整个应用程序的单例,它在 `Global.cpp` 中被实例化为全局对象 `theApp`。该类负责管理应用程序的生命周期、全局状态和核心组件的初始化。
```mermaid
classDiagram
class CGeoMativeApp {
+m_pConnection : _ConnectionPtr
+m_pProManager : CProManager*
+m_pDevManager : CDevManager*
+m_pTdManager : CTdManager*
+m_pExecManager : CExecManager*
+m_pSptManager : CSptManager*
+m_pIOManager : CIOManager*
+InitInstance() bool
+ExitInstance() int
+GetDBPasswordInfo() void
+GetCfgUrl() bool
}
CGeoMativeApp "1" -- "1" CProManager : 拥有
CGeoMativeApp "1" -- "1" CDevManager : 拥有
CGeoMativeApp "1" -- "1" CTdManager : 拥有
CGeoMativeApp "1" -- "1" CExecManager : 拥有
CGeoMativeApp "1" -- "1" CSptManager : 拥有
CGeoMativeApp "1" -- "1" CIOManager : 拥有
```
**Diagram sources**
- [cpp/Main/GeoMative.cpp](file://cpp/Main/GeoMative.cpp#L56-L87)
- [h/GeoMative.h](file://h/GeoMative.h#L147-L152)
### 工厂模式 (Factory Pattern)
`CProManager` 类实现了工厂模式,通过 `GetDMS` 方法根据句柄(Handle)动态创建或获取相应的数据管理对象(`CProject`, `CTestingZone`)。这种方法将对象的创建逻辑集中在一个地方,提高了代码的灵活性。
```mermaid
sequenceDiagram
participant Client as "客户端"
participant ProManager as "CProManager"
participant Factory as "工厂方法"
participant Project as "CProject"
participant Tz as "CTestingZone"
Client->>ProManager : GetDMS(dwHandle)
ProManager->>Factory : 检查m_dmsLinkList缓存
alt 缓存中不存在
Factory->>Factory : 根据uStyle创建新对象
alt uStyle == PZ_STYLE_PRO
Factory->>Project : new CProject()
else uStyle == PZ_STYLE_TZ
Factory->>Tz : new CTestingZone()
end
Factory->>ProManager : 将新对象加入缓存
end
ProManager->>Client : 返回对象指针
```
**Diagram sources**
- [cpp/Managers/ProManager.cpp](file://cpp/Managers/ProManager.cpp#L153-L182)
### 观察者模式 (Observer Pattern)
应用程序通过 Windows 消息映射(Message Map)机制实现了观察者模式。`CGeoMativeApp` 类定义了消息处理函数(如 `OnFileExit`, `OnHelpAbout`),当特定事件(如菜单点击)发生时,系统会自动调用这些函数。这使得事件的发布者(系统)与订阅者(应用程序)解耦。
```mermaid
classDiagram
class CGeoMativeApp {
+OnFileExit() void
+OnHelpAbout() void
+OnCfgTerrain() void
}
class MessageMap {
+IDM_FILE_EXIT --> OnFileExit
+IDM_HELP_ABOUT --> OnHelpAbout
+IDM_TERRAIN_SET --> OnCfgTerrain
}
MessageMap --> CGeoMativeApp : 触发
```
**Diagram sources**
- [cpp/Main/GeoMative.cpp](file://cpp/Main/GeoMative.cpp#L45-L51)
- [cpp/Main/GeoMative.cpp](file://cpp/Main/GeoMative.cpp#L789-L792)
## 关键常量与全局函数
### 关键常量
常量定义在 `h/Constant.h` 文件中,用于统一管理应用程序的配置和状态码。
```mermaid
erDiagram
enum "EN_TRANSFER_FILE_METHOD" {
EN_TRANSFER_FILE_BY_COM
EN_TRANSFER_FILE_BY_USB
EN_TRANSFER_FILE_BY_CLOUND
EN_TRANSFER_FILE_BY_WIFI
}
enum "EN_VERSION_INFO" {
EN_ON_LIEN_VERSION_1
EN_ON_LIEN_VERSION_2
}
enum "EN_CHANNEL_INFO" {
EN_SINGLE_CHANNEL
EN_MULTI_CHANNEL
}
constant "APP_SUCCESS" 1
constant "APP_FAIL" 0
constant "APP_CANCLE" 2
constant "APP_DUPLICATE" 3
constant "APP_OVERFLOW" 4
```
**Section sources**
- [h/GeoMative.h](file://h/GeoMative.h#L84-L113)
- [h/Constant.h](file://h/Constant.h)
### 全局函数与工具类
`Global.cpp` 文件中定义了多个全局函数和变量,为整个应用程序提供基础服务。
- **全局变量**:
- `g_szMacAddress`: 存储当前计算机的MAC地址。
- `g_iTransFileMode`: 表示文件传输模式(USB、蓝牙、云端等)。
- `g_iUILanguage`: 表示当前用户界面语言。
- **全局函数**:
- `SplitterString(...)`: 用于分割字符串。
- `StatStringCount(...)`: 统计子串在源字符串中的出现次数。
- `bIsInteger(...)`, `bIsFloat(...)`: 用于验证字符串是否为整数或浮点数。
- `GetExcelHeaderIndex(...)`: 生成Excel单元格的列名。
- `GetSysTimeFunction(...)`: 一个线程函数,用于持续获取系统时间。
这些工具类(如 `CFileOperTools`, `CGUCodeCreator`)提供了文件操作、唯一标识符生成等通用功能。
**Section sources**
- [cpp/Main/Global.cpp](file://cpp/Main/Global.cpp)
- [cpp/Tools/FileOperTools.cpp](file://cpp/Tools/FileOperTools.cpp)
- [cpp/Tools/GUCodeCreator.cpp](file://cpp/Tools/GUCodeCreator.cpp)
## 代码贡献指南
### 环境搭建
1. **克隆仓库**: `git clone https://github.com/geomative/GeomativeStudio.git`
2. **打开解决方案**: 使用 Visual Studio 打开 `Geomative.sln`。
3. **配置数据库**: 确保 `DB/GeoMativeDB.accdb` 文件存在且可访问。
4. **编译运行**: 直接编译并运行项目。
### 代码规范
- **命名约定**: 采用匈牙利命名法,类名以 `C` 开头,变量名使用小写前缀(如 `sz` 表示CString,`dw` 表示DWORD)。
- **注释**: 关键函数和复杂逻辑必须添加注释,解释其目的和实现方式。
- **错误处理**: 使用 `try-catch` 块捕获 `_com_error` 异常,并通过 `AfxMessageBox` 或 `MessageBoxEx` 向用户报告错误。
### 贡献流程
1. **创建分支**: `git checkout -b feature/your-feature-name`
2. **编写代码**: 遵循上述规范。
3. **测试**: 确保新功能或修复的bug已通过测试。
4. **提交**: `git add .` 和 `git commit -m "描述你的更改"`
5. **推送**: `git push origin feature/your-feature-name`
6. **创建Pull Request**: 在GitHub上创建PR,等待代码审查。
**Section sources**
- [README.md](file://README.md)
## 调试技巧
### 常见问题排查
1. **数据库连接失败**:
- 检查 `DB/GeoMativeDB.accdb` 文件路径和权限。
- 确认连接字符串 `szConn` 是否正确。
- 检查 `m_pConnection->Open(...)` 调用的返回值和异常信息。
2. **设备无法识别**:
- 检查 `g_iTransFileMode` 的值是否正确配置。
- 确认设备驱动程序已正确安装。
- 查看 `LOG` 目录下的日志文件,如 `general\20211110.txt`。
3. **线程创建失败**:
- 检查 `::CreateThread` 的返回值。
- 确保线程函数(如 `GetSysTimeFunction`)的签名正确。
- 使用 `OutputDebugString` 输出调试信息。
### 日志记录
- **使用 `CFileOperTools::GetInstance()->WriteComLog(...)`**: 这是记录应用程序日志的标准方法。它会将日志写入 `LOG` 目录下的文件。
- **使用 `OutputDebugString`**: 用于在Visual Studio的“输出”窗口中打印调试信息,对实时调试非常有用。
**Section sources**
- [cpp/Main/GeoMative.cpp](file://cpp/Main/GeoMative.cpp#L279-L289)
- [cpp/Tools/FileOperTools.cpp](file://cpp/Tools/FileOperTools.cpp)
- [cpp/Managers/DevManager.cpp](file://cpp/Managers/DevManager.cpp)
## 扩展开发最佳实践
### 新增功能模块
1. **定义数据模型**: 在 `cpp/ProblemZone` 目录下创建新的类(如 `NewFeature.cpp/h`),继承自 `CDataMngStruct`。
2. **创建管理器**: 在 `cpp/Managers` 目录下创建管理器类(如 `CNewFeatureManager.cpp/h`),负责该模块的业务逻辑。
3. **实现操作器**: 在 `cpp/Operator` 目录下创建操作器类(如 `CNewFeatureOperator.cpp/h`),处理具体的数据操作。
4. **添加UI**: 在 `cpp/Views` 目录下创建对话框或视图类,并将其与管理器和操作器集成。
5. **注册到主应用**: 在 `CGeoMativeApp` 的构造函数中创建管理器实例,并在 `ExitInstance` 中释放。
### 性能优化
- **避免重复数据库查询**: 使用 `CProManager` 中的 `m_dmsLinkList` 缓存机制来存储已加载的对象。
- **合理使用线程**: 对于耗时操作(如文件传输、数据库操作),使用独立线程以避免阻塞UI。
- **及时释放资源**: 在 `ExitInstance` 和析构函数中,确保所有动态分配的内存和打开的资源(如数据库连接、文件句柄)都被正确释放。
**Section sources**
- [cpp/Main/GeoMative.cpp](file://cpp/Main/GeoMative.cpp#L56-L128)
- [cpp/Managers/ProManager.cpp](file://cpp/Managers/ProManager.cpp#L32-L51)