2026-07-23 06:27:43 +00:00
|
|
|
#pragma once
|
|
|
|
|
#include "vde/mesh/halfedge_mesh.h"
|
|
|
|
|
#include <vector>
|
|
|
|
|
#include <cstdint>
|
|
|
|
|
#include <string>
|
|
|
|
|
|
|
|
|
|
namespace vde::foundation {
|
|
|
|
|
|
2026-07-24 11:04:04 +00:00
|
|
|
/**
|
|
|
|
|
* @brief 二进制序列化格式的网格数据结构
|
|
|
|
|
*
|
|
|
|
|
* 存储网格的扁平表示,顶点坐标连续排列,面索引连续排列。
|
|
|
|
|
* 所有面均为三角形(face_valence 固定为 3)。
|
|
|
|
|
*
|
|
|
|
|
* @ingroup foundation
|
|
|
|
|
*/
|
2026-07-23 06:27:43 +00:00
|
|
|
struct SerializedMesh {
|
2026-07-24 11:04:04 +00:00
|
|
|
/// 顶点数量
|
2026-07-23 06:27:43 +00:00
|
|
|
uint32_t vertex_count;
|
2026-07-24 11:04:04 +00:00
|
|
|
/// 面数量
|
2026-07-23 06:27:43 +00:00
|
|
|
uint32_t face_count;
|
2026-07-24 11:04:04 +00:00
|
|
|
/// 顶点坐标,扁平排列:x0 y0 z0 x1 y1 z1 ...
|
|
|
|
|
std::vector<double> vertices;
|
|
|
|
|
/// 面顶点索引,扁平排列:v0_0 v0_1 v0_2 v1_0 v1_1 v1_2 ...
|
|
|
|
|
std::vector<int32_t> face_indices;
|
|
|
|
|
/// 每面的顶点数(当前固定为 3,即纯三角形网格)
|
|
|
|
|
std::vector<int32_t> face_valence;
|
2026-07-23 06:27:43 +00:00
|
|
|
};
|
|
|
|
|
|
2026-07-24 11:04:04 +00:00
|
|
|
/**
|
|
|
|
|
* @brief 二进制序列化器
|
|
|
|
|
*
|
|
|
|
|
* 提供网格的快速二进制序列化/反序列化,用于 VDE 本地格式(VDE 二进制格式)。
|
|
|
|
|
*
|
|
|
|
|
* 文件格式:
|
|
|
|
|
* - 8 字节魔数 "VDEGEOM\0" (0x56444547454F4D00)
|
|
|
|
|
* - 4 字节格式版本号
|
|
|
|
|
* - 4 字节标志位
|
|
|
|
|
* - 序列化的网格数据
|
|
|
|
|
*
|
|
|
|
|
* @note 该格式专为 VDE 内部快速读写设计,不适用于跨平台数据交换
|
|
|
|
|
* @note 使用 glTF/OBJ/STL 进行外部交换,此格式用于本地缓存
|
|
|
|
|
*
|
|
|
|
|
* @ingroup foundation
|
|
|
|
|
*/
|
2026-07-23 06:27:43 +00:00
|
|
|
class BinarySerializer {
|
|
|
|
|
public:
|
2026-07-24 11:04:04 +00:00
|
|
|
/**
|
|
|
|
|
* @brief 序列化网格到二进制缓冲区
|
|
|
|
|
*
|
|
|
|
|
* @param mesh 要序列化的半边网格
|
|
|
|
|
* @return 压缩后的二进制数据(含文件头)
|
|
|
|
|
*
|
|
|
|
|
* @code{.cpp}
|
|
|
|
|
* auto data = BinarySerializer::serialize(mesh);
|
|
|
|
|
* // data 可直接写入文件或通过网络传输
|
|
|
|
|
* @endcode
|
|
|
|
|
*/
|
2026-07-23 08:19:24 +00:00
|
|
|
static std::vector<uint8_t> serialize(const mesh::HalfedgeMesh& mesh);
|
2026-07-23 06:27:43 +00:00
|
|
|
|
2026-07-24 11:04:04 +00:00
|
|
|
/**
|
|
|
|
|
* @brief 从二进制缓冲区反序列化网格
|
|
|
|
|
*
|
|
|
|
|
* @param data 之前由 serialize() 生成的二进制数据
|
|
|
|
|
* @return 恢复的半边网格
|
|
|
|
|
*
|
|
|
|
|
* @throws std::runtime_error 若数据校验失败(魔数/版本不匹配)
|
|
|
|
|
*
|
|
|
|
|
* @code{.cpp}
|
|
|
|
|
* auto mesh = BinarySerializer::deserialize(data);
|
|
|
|
|
* @endcode
|
|
|
|
|
*/
|
2026-07-23 08:19:24 +00:00
|
|
|
static mesh::HalfedgeMesh deserialize(const std::vector<uint8_t>& data);
|
2026-07-23 06:27:43 +00:00
|
|
|
|
2026-07-24 11:04:04 +00:00
|
|
|
/**
|
|
|
|
|
* @brief 序列化并写入文件
|
|
|
|
|
*
|
|
|
|
|
* 等价于 serialize() + 文件写入,一步完成。
|
|
|
|
|
*
|
|
|
|
|
* @param path 输出文件路径
|
|
|
|
|
* @param mesh 要保存的半边网格
|
|
|
|
|
* @return true 写入成功
|
|
|
|
|
* @return false 文件创建失败
|
|
|
|
|
*
|
|
|
|
|
* @see read_file
|
|
|
|
|
*/
|
2026-07-23 08:19:24 +00:00
|
|
|
static bool write_file(const std::string& path, const mesh::HalfedgeMesh& mesh);
|
2026-07-23 06:27:43 +00:00
|
|
|
|
2026-07-24 11:04:04 +00:00
|
|
|
/**
|
|
|
|
|
* @brief 从文件读取并反序列化
|
|
|
|
|
*
|
|
|
|
|
* 等价于文件读取 + deserialize(),一步完成。
|
|
|
|
|
*
|
|
|
|
|
* @param path VDE 二进制格式文件路径
|
|
|
|
|
* @return 恢复的半边网格
|
|
|
|
|
*
|
|
|
|
|
* @throws std::runtime_error 若文件无法打开或格式无效
|
|
|
|
|
*
|
|
|
|
|
* @see write_file
|
|
|
|
|
*/
|
2026-07-23 08:19:24 +00:00
|
|
|
static mesh::HalfedgeMesh read_file(const std::string& path);
|
2026-07-23 06:27:43 +00:00
|
|
|
};
|
|
|
|
|
|
2026-07-24 11:04:04 +00:00
|
|
|
/**
|
|
|
|
|
* @brief VDE 二进制文件魔数:"VDEGEOM\0"
|
|
|
|
|
*
|
|
|
|
|
* 用于识别 VDE 二进制网格文件。
|
|
|
|
|
*/
|
|
|
|
|
constexpr uint64_t VDE_MAGIC = 0x56444547454F4D00ULL; // "VDEGEOM\0"
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* @brief VDE 二进制格式当前版本号
|
|
|
|
|
*
|
|
|
|
|
* 用于向前兼容:读取时检查版本号,若不一致则拒绝或执行迁移。
|
|
|
|
|
*/
|
|
|
|
|
constexpr uint32_t VDE_FORMAT_VERSION = 1;
|
|
|
|
|
|
2026-07-23 06:27:43 +00:00
|
|
|
} // namespace vde::foundation
|