a
This commit is contained in:
@@ -0,0 +1,394 @@
|
||||
# 项目管理
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [ProManager.cpp](file://cpp/Managers/ProManager.cpp)
|
||||
- [ProManager.h](file://h/ProManager.h)
|
||||
- [Project.cpp](file://cpp/ProblemZone/Project.cpp)
|
||||
- [Project.h](file://h/Project.h)
|
||||
- [TestingZone.cpp](file://cpp/ProblemZone/TestingZone.cpp)
|
||||
- [TestingZone.h](file://h/TestingZone.h)
|
||||
- [opcreateprojectdlg.h](file://h/opcreateprojectdlg.h)
|
||||
- [opcreateprojectdlg.cpp](file://cpp/Views/opcreateprojectdlg.cpp)
|
||||
- [DataMngStruct.h](file://h/DataMngStruct.h)
|
||||
- [DevManager.h](file://h/DevManager.h)
|
||||
- [SptManager.h](file://h/SptManager.h)
|
||||
- [project.xml](file://CACHE/project.xml)
|
||||
- [testzone.xml](file://CACHE/testzone.xml)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [项目管理概述](#项目管理概述)
|
||||
2. [CProManager类架构与实现](#cpromanager类架构与实现)
|
||||
3. [项目数据模型与持久化](#项目数据模型与持久化)
|
||||
4. [项目与测区的层级关系](#项目与测区的层级关系)
|
||||
5. [项目配置同步到设备流程](#项目配置同步到设备流程)
|
||||
6. [项目管理API使用示例](#项目管理api使用示例)
|
||||
7. [与其他管理器的集成](#与其他管理器的集成)
|
||||
8. [多项目环境下的资源管理](#多项目环境下的资源管理)
|
||||
|
||||
## 项目管理概述
|
||||
|
||||
Geomative Studio的项目管理模块是整个系统的核心组件,负责管理地质探测项目的全生命周期。该模块通过CProManager类实现,提供了项目创建、打开、配置和删除等核心功能。每个项目包含一个或多个测区(TZ),形成清晰的层级结构。项目数据存储在数据库中,并通过XML缓存文件在本地持久化,同时支持与设备的双向同步。本模块与设备管理器、脚本管理器等组件紧密集成,确保了数据的一致性和操作的协同性。
|
||||
|
||||
## CProManager类架构与实现
|
||||
|
||||
CProManager类是项目管理的核心实现,负责协调项目和测区的创建、查询和删除操作。该类通过数据库连接管理项目数据,并与设备进行通信以实现数据同步。
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class CProManager {
|
||||
+ShowProList(dwDevHandle, proList) bool
|
||||
+ShowTzList(dwProHandle, tzList) bool
|
||||
+GetDMS(dwHandle) CDataMngStruct*
|
||||
+CreateProjectInDB(dwID) UINT
|
||||
+CreateProjectInDev(dwID, pDev) UINT
|
||||
+CreateTzInDB(dwID, dwPrID) UINT
|
||||
+CreateTzInDev(dwID, pDev) UINT
|
||||
+DeleteProjectInDB(dwID) void
|
||||
+DeleteProjectInDev(szMac, szPrCN, pDev) UINT
|
||||
+DeleteTzInDB(dwID) void
|
||||
+DeleteTzInDev(szPrCN, szTzCN, pDev) UINT
|
||||
+InsertDefaultTzToProject(dwProjectID) UINT
|
||||
+CreateDefaultTzInDev(dwProID, pDev) UINT
|
||||
}
|
||||
class CDataMngStruct {
|
||||
+ShowDetailInfo(dmsDetailList) bool
|
||||
}
|
||||
class CProject {
|
||||
+ShowDetailInfo(proDetailList) bool
|
||||
}
|
||||
class CTestingZone {
|
||||
+ShowDetailInfo(tzDetailList) bool
|
||||
}
|
||||
CProManager --> CDataMngStruct : "管理"
|
||||
CDataMngStruct <|-- CProject : "继承"
|
||||
CDataMngStruct <|-- CTestingZone : "继承"
|
||||
CProManager --> CLinkList : "m_dmsLinkList"
|
||||
CProManager --> CHandleProcessor : "m_handleProcessor"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [ProManager.h](file://h/ProManager.h#L30-L74)
|
||||
- [Project.h](file://h/Project.h#L16-L38)
|
||||
- [TestingZone.h](file://h/TestingZone.h#L14-L30)
|
||||
- [DataMngStruct.h](file://h/DataMngStruct.h#L14-L20)
|
||||
|
||||
**本节来源**
|
||||
- [ProManager.cpp](file://cpp/Managers/ProManager.cpp#L32-L80)
|
||||
- [ProManager.h](file://h/ProManager.h#L30-L74)
|
||||
|
||||
## 项目数据模型与持久化
|
||||
|
||||
项目数据模型包含多个关键字段,这些字段在数据库和XML缓存文件中保持一致。项目数据首先存储在数据库的project表中,然后通过XML文件在本地缓存。
|
||||
|
||||
### 项目数据模型字段
|
||||
|
||||
| 字段名 | 中文名称 | 数据类型 | 描述 |
|
||||
|-------|--------|--------|------|
|
||||
| CN | 项目编号 | 字符串 | 项目的唯一标识符,使用GUID生成 |
|
||||
| PRname | 项目名称 | 字符串 | 项目的名称,用户可读 |
|
||||
| PRdesc | 项目描述 | 字符串 | 项目的详细描述信息 |
|
||||
| location | 位置 | 字符串 | 项目实施的地理位置 |
|
||||
| PRdate | 创建日期 | 日期 | 项目的创建日期 |
|
||||
| duration | 持续时间 | 字符串 | 项目预计的持续时间 |
|
||||
| PS | 项目负责人 | 字符串 | 项目的主要负责人 |
|
||||
| CS | 客户名称 | 字符串 | 项目的客户或委托方 |
|
||||
| PM | 项目经理 | 字符串 | 项目的管理负责人 |
|
||||
| QAS | 质量保证 | 字符串 | 质量保证相关人员 |
|
||||
| standard | 标准 | 字符串 | 项目遵循的技术标准 |
|
||||
|
||||
### XML缓存持久化机制
|
||||
|
||||
项目数据通过XML文件在CACHE目录下持久化存储。系统使用CMarkup库创建和解析XML文件,确保数据的可读性和可移植性。
|
||||
|
||||
```xml
|
||||
<?xml version="1.0" encoding="ansi"?>
|
||||
<project>
|
||||
<project_name>test project</project_name>
|
||||
<cn>63EFC4AB5B284FC8B1B46F0CEB8F9DA4</cn>
|
||||
<description />
|
||||
<location />
|
||||
<create_date>2016-05-17</create_date>
|
||||
<create_time>00:00:00</create_time>
|
||||
<test_date>2020-04-11</test_date>
|
||||
<test_time>11:53:06</test_time>
|
||||
<duration>10</duration>
|
||||
<PS />
|
||||
<CS />
|
||||
<PM />
|
||||
<QA />
|
||||
<standard />
|
||||
<testzone_count>0</testzone_count>
|
||||
<testzones>
|
||||
<testzone TYPE="3">A9F3D38BDCF84401B8C3050D583BCBEE</testzone>
|
||||
</testzones>
|
||||
</project>
|
||||
```
|
||||
|
||||
当创建新项目时,系统会自动生成XML文件并存储在`CACHE\projects\<项目编号>\`目录下。这种持久化机制确保了即使在离线状态下,项目数据也能被访问和管理。
|
||||
|
||||
**本节来源**
|
||||
- [Project.h](file://h/Project.h#L26-L37)
|
||||
- [project.xml](file://CACHE/project.xml)
|
||||
- [ProManager.cpp](file://cpp/Managers/ProManager.cpp#L397-L426)
|
||||
|
||||
## 项目与测区的层级关系
|
||||
|
||||
项目与测区之间存在明确的层级关系,一个项目可以包含多个测区,形成树状结构。这种设计符合地质探测的实际工作流程,允许用户在同一个项目下管理多个不同位置或类型的探测区域。
|
||||
|
||||
### 层级结构实现
|
||||
|
||||
```mermaid
|
||||
graph TD
|
||||
A[项目] --> B[测区1]
|
||||
A --> C[测区2]
|
||||
A --> D[测区3]
|
||||
B --> E[1D VES \| 2D ERI]
|
||||
C --> F[3D ERT]
|
||||
D --> G[All Type]
|
||||
```
|
||||
|
||||
在数据模型中,项目(Project)和测区(TestingZone)都继承自CDataMngStruct基类,实现了多态性。CProManager通过m_dmsLinkList链表管理所有项目和测区对象,使用句柄(Handle)机制进行高效访问。
|
||||
|
||||
测区类型通过TZtype字段表示:
|
||||
- 类型1或0:1D VES | 2D ERI(一维垂直电测深或二维电阻率成像)
|
||||
- 类型2:3D ERT(三维电阻率断层扫描)
|
||||
- 类型3:默认测区
|
||||
|
||||
每个项目创建时会自动包含一个默认测区,确保项目结构的完整性。用户可以通过GUI界面或API创建额外的测区来满足不同的探测需求。
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant GUI as GUI界面
|
||||
participant ProManager as CProManager
|
||||
participant DB as 数据库
|
||||
participant XML as XML缓存
|
||||
GUI->>ProManager : 创建项目请求
|
||||
ProManager->>DB : 在数据库创建项目记录
|
||||
DB-->>ProManager : 返回项目ID
|
||||
ProManager->>DB : 为项目插入默认测区
|
||||
ProManager->>XML : 创建project.xml文件
|
||||
ProManager->>XML : 创建testzone.xml文件
|
||||
ProManager-->>GUI : 返回创建结果
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [ProManager.cpp](file://cpp/Managers/ProManager.cpp#L319-L341)
|
||||
- [TestingZone.cpp](file://cpp/ProblemZone/TestingZone.cpp#L61-L73)
|
||||
- [testzone.xml](file://CACHE/testzone.xml)
|
||||
|
||||
**本节来源**
|
||||
- [ProManager.cpp](file://cpp/Managers/ProManager.cpp#L319-L341)
|
||||
- [TestingZone.cpp](file://cpp/ProblemZone/TestingZone.cpp#L61-L73)
|
||||
- [testzone.xml](file://CACHE/testzone.xml)
|
||||
|
||||
## 项目配置同步到设备流程
|
||||
|
||||
项目配置同步到设备是项目管理的关键功能,确保了现场设备与工作站的数据一致性。该流程涉及多个步骤,包括数据准备、文件传输和状态更新。
|
||||
|
||||
### 同步流程
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A[开始同步] --> B{项目已存在?}
|
||||
B --> |否| C[在设备中创建项目]
|
||||
B --> |是| D[跳过创建]
|
||||
C --> E[生成项目XML文件]
|
||||
E --> F[创建本地缓存目录]
|
||||
F --> G[传输文件到设备]
|
||||
G --> H{传输成功?}
|
||||
H --> |是| I[更新数据库同步状态]
|
||||
H --> |否| J[显示错误信息]
|
||||
J --> K[回滚操作]
|
||||
I --> L[创建默认测区]
|
||||
L --> M[生成测区XML文件]
|
||||
M --> N[传输测区文件到设备]
|
||||
N --> O{传输成功?}
|
||||
O --> |是| P[更新数据库同步状态]
|
||||
O --> |否| Q[显示错误信息]
|
||||
Q --> R[删除已创建的项目]
|
||||
P --> S[同步完成]
|
||||
```
|
||||
|
||||
同步流程的具体实现如下:
|
||||
1. 首先检查项目是否已存在于设备中,避免重复创建
|
||||
2. 从数据库读取项目配置信息
|
||||
3. 使用CMarkup库生成project.xml文件
|
||||
4. 创建本地缓存目录`CACHE\projects\<项目编号>\`
|
||||
5. 调用设备的SendFile方法将文件传输到设备的/SD/projects/目录
|
||||
6. 如果传输成功,更新数据库中的同步状态;如果失败,执行回滚操作
|
||||
|
||||
此流程确保了数据同步的原子性和一致性,防止了部分同步导致的数据不一致问题。
|
||||
|
||||
**图表来源**
|
||||
- [ProManager.cpp](file://cpp/Managers/ProManager.cpp#L343-L483)
|
||||
- [ProManager.cpp](file://cpp/Managers/ProManager.cpp#L485-L707)
|
||||
|
||||
**本节来源**
|
||||
- [ProManager.cpp](file://cpp/Managers/ProManager.cpp#L343-L707)
|
||||
|
||||
## 项目管理API使用示例
|
||||
|
||||
项目管理模块提供了丰富的API,支持通过GUI界面和后台代码进行项目操作。以下是常见的使用示例。
|
||||
|
||||
### GUI界面操作
|
||||
|
||||
通过GUI界面创建项目的流程:
|
||||
1. 用户点击"新建项目"按钮
|
||||
2. 系统弹出COpCreateProjectDlg对话框
|
||||
3. 用户填写项目信息(名称、描述、位置等)
|
||||
4. 系统验证项目名称的唯一性
|
||||
5. 调用CProManager::CreateProjectInDB方法在数据库中创建项目
|
||||
|
||||
```cpp
|
||||
// GUI创建项目的核心代码流程
|
||||
COpCreateProjectDlg opCreateProDlg;
|
||||
INT_PTR lRet = opCreateProDlg.DoModal();
|
||||
if (IDOK == lRet) {
|
||||
UINT uExecCode = theApp.m_pProManager->CreateProjectInDB(dwID);
|
||||
if (APP_SUCCESS == uExecCode) {
|
||||
// 更新UI显示
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 后台代码操作
|
||||
|
||||
通过后台代码创建和管理项目的示例:
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant App as 应用程序
|
||||
participant DataOperator as DataOperator
|
||||
participant ProManager as CProManager
|
||||
participant DB as 数据库
|
||||
App->>DataOperator : CreateProjectInDB(pNavDataView)
|
||||
DataOperator->>ProManager : CreateProjectInDB(dwID)
|
||||
ProManager->>DB : 检查项目名称是否存在
|
||||
DB-->>ProManager : 返回检查结果
|
||||
ProManager->>DB : 插入项目记录
|
||||
DB-->>ProManager : 返回项目ID
|
||||
ProManager->>ProManager : InsertDefaultTzToProject
|
||||
ProManager-->>DataOperator : 返回执行代码
|
||||
DataOperator->>DB : 开始事务
|
||||
DataOperator->>DB : 提交事务
|
||||
DataOperator-->>App : 返回结果
|
||||
```
|
||||
|
||||
后台操作的关键特点是使用了数据库事务,确保了操作的原子性。如果任何步骤失败,整个事务将被回滚,保持数据的一致性。
|
||||
|
||||
**图表来源**
|
||||
- [opcreateprojectdlg.cpp](file://cpp/Views/opcreateprojectdlg.cpp#L21-L37)
|
||||
- [DataOperator.cpp](file://cpp/Operator/DataOperator.cpp#L618-L667)
|
||||
|
||||
**本节来源**
|
||||
- [opcreateprojectdlg.h](file://h/opcreateprojectdlg.h#L15-L36)
|
||||
- [opcreateprojectdlg.cpp](file://cpp/Views/opcreateprojectdlg.cpp#L21-L37)
|
||||
- [DataOperator.cpp](file://cpp/Operator/DataOperator.cpp#L618-L667)
|
||||
|
||||
## 与其他管理器的集成
|
||||
|
||||
项目管理器与设备管理器、脚本管理器等组件紧密集成,形成了完整的系统架构。这种集成确保了各模块之间的数据一致性和操作协同性。
|
||||
|
||||
### 与设备管理器的集成
|
||||
|
||||
项目管理器与设备管理器通过设备句柄和序列号进行通信。当需要将项目同步到设备时,项目管理器会调用设备管理器获取设备对象,然后执行文件传输操作。
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class CProManager {
|
||||
+CreateProjectInDev(dwID, pDev) UINT
|
||||
+CreateTzInDev(dwID, pDev) UINT
|
||||
}
|
||||
class CDevManager {
|
||||
+GetDevice(dwHandle) CDevice*
|
||||
+GetDevice(szDevSN) CDevice*
|
||||
}
|
||||
class CDevice {
|
||||
+SendFile(szHostPath, szLocalPath, szFileName) BOOL
|
||||
+m_szDevSN CString
|
||||
}
|
||||
CProManager --> CDevice : "使用"
|
||||
CDevManager --> CDevice : "管理"
|
||||
CProManager ..> CDevManager : "依赖"
|
||||
```
|
||||
|
||||
这种设计实现了关注点分离,项目管理器专注于项目数据的管理,而设备管理器负责设备的连接和通信。
|
||||
|
||||
### 与脚本管理器的集成
|
||||
|
||||
项目管理器与脚本管理器的集成主要体现在测区与脚本的关系上。每个测区可以关联多个探测脚本,这些脚本由脚本管理器管理。
|
||||
|
||||
```mermaid
|
||||
graph TD
|
||||
A[CProManager] --> |获取| B[CDevManager]
|
||||
B --> |提供| C[CDevice]
|
||||
C --> |用于| D[文件传输]
|
||||
A --> |创建| E[project.xml]
|
||||
A --> |创建| F[testzone.xml]
|
||||
E --> |包含| G[项目元数据]
|
||||
F --> |包含| H[测区元数据]
|
||||
F --> |引用| I[脚本文件]
|
||||
I --> |由| J[CSptManager]
|
||||
J --> |管理| K[脚本生命周期]
|
||||
```
|
||||
|
||||
脚本管理器负责脚本的创建、编辑和删除,而项目管理器确保这些脚本与正确的测区关联。这种分工使得系统更加模块化,易于维护和扩展。
|
||||
|
||||
**图表来源**
|
||||
- [DevManager.h](file://h/DevManager.h#L16-L68)
|
||||
- [SptManager.h](file://h/SptManager.h#L27-L87)
|
||||
- [ProManager.h](file://h/ProManager.h#L30-L74)
|
||||
|
||||
**本节来源**
|
||||
- [DevManager.h](file://h/DevManager.h#L16-L68)
|
||||
- [SptManager.h](file://h/SptManager.h#L27-L87)
|
||||
|
||||
## 多项目环境下的资源管理
|
||||
|
||||
在多项目环境下,系统需要高效管理内存和文件资源,避免资源泄漏和性能下降。CProManager类通过链表和句柄机制实现了高效的资源管理。
|
||||
|
||||
### 内存管理策略
|
||||
|
||||
CProManager使用CLinkList模板类管理所有项目和测区对象。每个对象通过唯一句柄访问,实现了对象的延迟加载和缓存机制。
|
||||
|
||||
```cpp
|
||||
// 对象获取的伪代码
|
||||
CDataMngStruct* CProManager::GetDMS(DWORD dwHandle) {
|
||||
CDataMngStruct* pDMS = m_dmsLinkList.Get(dwHandle);
|
||||
if (NULL == pDMS) {
|
||||
// 按需创建对象
|
||||
pDMS = new CProject(dwID, m_pConnection);
|
||||
m_dmsLinkList.Add(dwHandle, pDMS);
|
||||
}
|
||||
return pDMS;
|
||||
}
|
||||
```
|
||||
|
||||
这种策略的优点:
|
||||
- **延迟加载**:只有在需要时才从数据库加载数据,减少启动时间和内存占用
|
||||
- **对象缓存**:重复访问同一对象时直接从缓存获取,提高性能
|
||||
- **内存控制**:通过链表管理对象生命周期,避免内存泄漏
|
||||
|
||||
### 资源清理机制
|
||||
|
||||
系统在析构时会清理所有管理的对象:
|
||||
|
||||
```cpp
|
||||
CProManager::~CProManager() {
|
||||
int iDMSIndex = 0;
|
||||
while (NULL != m_dmsLinkList.Find(iDMSIndex)) {
|
||||
delete m_dmsLinkList.Find(iDMSIndex);
|
||||
iDMSIndex++;
|
||||
}
|
||||
m_dmsLinkList.DeleteAll();
|
||||
}
|
||||
```
|
||||
|
||||
此外,系统还提供了DeleteObjInMem方法,允许在运行时显式删除不再需要的对象,进一步优化内存使用。
|
||||
|
||||
**本节来源**
|
||||
- [ProManager.cpp](file://cpp/Managers/ProManager.cpp#L39-L51)
|
||||
- [ProManager.cpp](file://cpp/Managers/ProManager.cpp#L155-L182)
|
||||
- [ProManager.h](file://h/ProManager.h#L72-L73)
|
||||
Reference in New Issue
Block a user