Files
XCEngine/docs/plan/仿Unity RHI架构设计.md

34 KiB
Raw Blame History

Unity风格RHI架构设计方案

一、概述

1.1 设计目标

本设计方案参考Unity引擎的渲染架构设计一套跨平台的渲染抽象层Graphics API使其能够同时支持DirectX 12、Vulkan、OpenGL等多种图形API。

Unity的核心设计理念

  • 分层架构上层应用与底层API完全解耦
  • CommandBuffer:使用命令缓冲模式,延迟执行渲染命令
  • 资源绑定抽象统一的资源绑定接口隐藏不同API的差异

1.2 架构概览

┌─────────────────────────────────────────────────────────┐
│                    应用层 / 渲染管线                       │
│              (RenderPass, DrawCall, Material)           │
├─────────────────────────────────────────────────────────┤
│                    CommandBuffer                         │
│            (统一的渲染命令缓冲类似Unity)                 │
├─────────────────────────────────────────────────────────┤
│                     Graphics API                         │
│  ┌────────────────┬────────────────┬────────────────┐  │
│  │  GraphicsAPI   │  GraphicsAPI   │  GraphicsAPI   │  │
│  │   (D3D12)     │   (Vulkan)    │   (OpenGL)    │  │
│  └────────────────┴────────────────┴────────────────┘  │
└─────────────────────────────────────────────────────────┘

二、核心接口设计

2.1 CommandBuffer命令缓冲

Unity的CommandBuffer是渲染命令的核心抽象本设计采用相同概念。

namespace XCEngine {
namespace Graphics {

// 前向声明
class ComputeBuffer;
class ComputeShader;
class Material;
class Mesh;
class ComputeProgram;
class RenderTexture;
class Texture;
class Shader;

// ==================== 基本类型定义 ====================

struct Rect {
    float x, y, width, height;
    Rect() : x(0), y(0), width(0), height(0) {}
    Rect(float x, float y, float w, float h) : x(x), y(y), width(w), height(h) {}
};

using byte = uint8_t;

// 命令缓冲类
class CommandBuffer {
public:
    CommandBuffer();
    ~CommandBuffer();

    // ==================== 状态设置 ====================

    // 设置渲染管线/程序
    void SetRenderProgram(ComputeProgram* program);
    void SetMaterial(Material* material);

    // 设置纹理
    void SetTexture(Shader* shader, const char* name, Texture* texture);
    void SetTexture(Shader* shader, int texureID, Texture* texture);
    void SetTextures(Shader* shader, const char* name, std::vector<Texture*>& textures);

    // 设置矩阵/向量参数
    void SetMatrix(Shader* shader, const char* name, const float4x4& matrix);
    void SetMatrixArray(Shader* shader, const char* name, const float4x4* matrices, int count);
    void SetVector(Shader* shader, const char* name, const float4& vector);
    void SetFloat(Shader* shader, const char* name, float value);
    void SetInt(Shader* shader, const char* name, int value);

    // 全局参数所有Shader可见
    void SetGlobalMatrix(const char* name, const float4x4& matrix);
    void SetGlobalVector(const char* name, const float4& vector);
    void SetGlobalFloat(const char* name, float value);
    void SetGlobalTexture(const char* name, Texture* texture);

    // ==================== 渲染目标 ====================

    // 设置渲染目标
    void SetRenderTarget(RenderTexture* color, RenderTexture* depth);
    void SetRenderTarget(RenderTexture* color);
    void SetRenderTarget(RenderTexture* color, int colorSlice, RenderTexture* depth, int depthSlice);

    // 激活渲染纹理(用于后续绘制)
    void ActivateRenderTarget(RenderTexture* color, RenderTexture* depth);

    // ==================== 视口 ====================

    void SetViewport(float x, float y, float width, float height);
    void SetViewports(int count, Viewport* viewports);
    void SetScissor(Rect rect);
    void SetScissors(int count, Rect* rects);

    // ==================== 绘制 ====================

    // 绘制网格
    void Draw(Mesh* mesh, int subMeshIndex = 0);
    void DrawInstanced(Mesh* mesh, int subMeshIndex, int instanceCount);
    void DrawMeshInstanced(Mesh* mesh, int subMeshIndex, int instanceCount, Material* material, int shaderPass = 0);

    // 绘制程序Compute Shader
    void DispatchCompute(ComputeShader* shader, int threadGroupsX, int threadGroupsY, int threadGroupsZ);

    // 间接绘制
    void DrawMeshInstancedIndirect(Mesh* mesh, ComputeBuffer* argsBuffer, int argsOffset = 0);

    // ==================== 清除 ====================

    void ClearRenderTarget(bool clearColor, bool clearDepth, bool clearStencil);
    void ClearColor(const float4& color);
    void ClearDepth(float depth);
    void ClearStencil(int stencil);

    // ==================== 纹理操作 ====================

    // 复制纹理
    void CopyTexture(Texture* src, Texture* dst);
    void CopyTexture(Texture* src, int srcElement, int srcMip, int srcX, int srcY, int srcZ,
                     Texture* dst, int dstElement, int dstMip, int dstX, int dstY, int dstZ,
                     int width, int height, int depth);

    // 异步读取纹理
    void AsyncReadPixels(RenderTexture* source, Rect rect, TextureFormat format, bool activeCube);

    // ==================== 计算着色器 ====================

    void SetComputeBuffer(ComputeShader* shader, const char* name, ComputeBuffer* buffer);

    // ==================== 同步 ====================

    void IssuePluginEvent(int eventID);
    void Flush();

    // ==================== 渲染状态设置 ====================

    // 设置模板引用值
    void SetStencilRef(int ref);

    // 启用/禁用裁剪
    void EnableScissor();
    void DisableScissor();

    // 渲染目标(立即模式,不记录命令)
    void SetRenderTargetImmediate(RenderTexture* color, RenderTexture* depth);
    void SetRenderTargetImmediate(RenderTexture* color);

    // 线条宽度
    void SetLineWidth(float width);

    // 视口变换矩阵
    void SetViewTransform(const float4x4& view, const float4x4& projection);
    void SetViewTransform(const float4x4& view, const float4x4& projection, const float4x4& brdf);

    // ==================== Blit后处理 ====================

    void Blit(Material* material, RenderTexture* source, RenderTexture* dest);
    void Blit(Material* material, RenderTexture* source, RenderTexture* dest, int pass);
    void Blit(Material* material, RenderTexture* source, RenderTexture* dest, int pass, int lodLevel);

    // ==================== 延迟执行 ====================

    // 执行此CommandBuffer
    void Execute();
    void Execute(CommandBuffer* other);

    // 立即执行(可选)
    void ExecuteImmediate();
};

// 全局命令缓冲
CommandBuffer* GetMainCommandBuffer();

} // namespace Graphics
} // namespace XCEngine

2.2 GraphicsDevice图形设备

Unity使用GraphicsDevice代表底层图形设备本设计采用相同概念。

namespace XCEngine {
namespace Graphics {

// 图形API类型
enum class GraphicsAPI {
    Direct3D12,
    Vulkan,
    OpenGL,
    OpenGLES3,
    Metal
};

// 设备能力
struct DeviceCapabilities {
    bool supportsComputeShaders;
    bool supportsGeometryShaders;
    bool supportsTessellation;
    bool supportsRaytracing;
    bool supportsMeshShaders;
    bool supportsNonPow2Textures;
    bool supportsRenderTargetFloat;
    bool supportsHDR;
    int maxTextureSize;
    int maxRenderTextureSize;
    int maxCubemapSize;
    int maxColorAttachments;
    int maxComputeBuffers;
    int maxComputeBufferSize;
    int maxVertexAttributes;
};

// 纹理格式信息
struct TextureFormatInfo {
    TextureFormat format;
    bool isSupported;
    int bitsPerPixel;
    bool isColor;
    bool isDepth;
    bool isPacked;
    bool isCompressed;
};

// 图形设备接口
class GraphicsDevice {
public:
    virtual ~GraphicsDevice() = default;

    // 设备信息
    virtual GraphicsAPI GetAPI() const = 0;
    virtual const char* GetDeviceName() const = 0;
    virtual const DeviceCapabilities& GetCapabilities() const = 0;

    // 创建资源
    virtual Texture* CreateTexture(const TextureDescriptor& desc) = 0;
    virtual RenderTexture* CreateRenderTexture(const RenderTextureDescriptor& desc) = 0;
    virtual ComputeBuffer* CreateComputeBuffer(const ComputeBufferDescriptor& desc) = 0;
    virtual Mesh* CreateMesh() = 0;
    virtual ComputeShader* CreateComputeShader(const void* source, int sourceLength) = 0;
    virtual ComputeProgram* CreateComputeProgram(ComputeShader* computeShader) = 0;
    virtual Material* CreateMaterial(Shader* shader) = 0;
    virtual Shader* CreateShader(const ShaderSource& source) = 0;

    // 命令缓冲管理
    virtual CommandBuffer* CreateCommandBuffer() = 0;
    virtual CommandBuffer* GetTempCommandBuffer() = 0;
    virtual void ReleaseTempCommandBuffer(CommandBuffer* cmd) = 0;
    virtual void SubmitCommandBuffer(CommandBuffer* cmd) = 0;

    // 同步
    virtual void WaitForIdle() = 0;

    // 特性检测
    virtual bool SupportsTextureFormat(TextureFormat format) const = 0;
    virtual bool SupportsVertexFormat(VertexAttribute format) const = 0;

    // 纹理格式信息
    virtual TextureFormatInfo GetTextureFormatInfo(TextureFormat format) const = 0;

    // 性能统计
    virtual void ResetStatistics() = 0;
    virtual void GetStatistics() const = 0;
};

// 工厂函数
GraphicsDevice* CreateGraphicsDevice(GraphicsAPI api, void* windowHandle = nullptr);
void DestroyGraphicsDevice(GraphicsDevice* device);
GraphicsAPI GetDefaultGraphicsAPI();
std::vector<GraphicsAPI> GetAvailableGraphicsAPIs();

} // namespace Graphics
} // namespace XCEngine

2.3 Texture纹理

namespace XCEngine {
namespace Graphics {

enum class TextureFormat {
    // 颜色格式
    Alpha8,
    ARGB4444,
    RGB24,
    RGBA32,
    ARGB32,
    RGB565,
    DXT1,
    DXT5,
    RGBA4444,
    BGRA32,
    FloatRGHalf,
    FloatRGBAHalf,
    FloatRGBA,
    FloatR,
    HalfR,
    IntR,
    IntRG,
    IntRGB,
    IntRGBA,
    DXT1Crunched,
    DXT5Crunched,
    RGBCrunched,
    RGBACrunched,

    // 深度格式
    Depth16,
    Depth24,
    Depth24Stencil8,
    Depth32Float,
    Depth32FloatStencil8,

    // 阴影格式
    Shadowmap16,
    Shadowmap24,

    // HDR
    RGB9E5,
    RG11B10Float,
    RGB10A2,

    // YUV
    YUV422,
    YUV420
};

enum class TextureDimension {
    None,
    Texture2D,
    Texture3D,
    Texture2DArray,
    TextureCube,
    TextureCubeArray
};

enum class TextureWrapMode {
    Repeat,
    Clamp,
    Mirror,
    Border
};

enum class TextureFilterMode {
    Point,
    Bilinear,
    Trilinear,
    Anisotropic
};

enum class TextureUsage {
    Default = 0,
    RenderTarget = 1,
    DepthStencil = 2,
    Memoryless = 3,
    Staging = 4
};

struct TextureDescriptor {
    int width;
    int height;
    int depth;
    int mipmapLevels;
    int anisoLevel;
    TextureFilterMode filterMode;
    TextureWrapMode wrapMode;
    TextureFormat format;
    TextureDimension dimension;
    TextureUsage usage;
    bool enableRandomWrite;
    bool useMipMap;
    bool autoGenerateMipMaps;
};

class Texture {
public:
    virtual ~Texture() = default;

    // 属性
    virtual int GetWidth() const = 0;
    virtual int GetHeight() const = 0;
    virtual int GetDepth() const = 0;
    virtual int GetMipmapLevels() const = 0;
    virtual TextureFormat GetFormat() const = 0;
    virtual TextureDimension GetDimension() const = 0;

    // 过滤模式
    virtual void SetFilterMode(TextureFilterMode mode) = 0;
    virtual TextureFilterMode GetFilterMode() const = 0;

    // 纹理坐标包装模式
    virtual void SetWrapMode(TextureWrapMode mode) = 0;
    virtual TextureWrapMode GetWrapMode() const = 0;

    // 各向异性过滤
    virtual void SetAnisoLevel(int level) = 0;
    virtual int GetAnisoLevel() const = 0;

    // MipMap
    virtual void GenerateMipMaps() = 0;
    virtual void SetAnisotropicFiltering(float min, float max) = 0;

    // 像素数据
    virtual void SetData(const void* data, int mipLevel = 0) = 0;
    virtual void GetData(void* data, int mipLevel = 0) = 0;

    // 底层句柄
    virtual void* GetNativeTexturePtr() = 0;
    virtual void* GetNativeTexturePtr(int target) = 0;
};

} // namespace Graphics
} // namespace XCEngine

2.4 RenderTexture渲染纹理

namespace XCEngine {
namespace Graphics {

enum class RenderTextureFormat {
    ARGB32,
    ARGBHalf,
    ARGBFloat,
    RGHalf,
    RGFloat,
    RFloat,
    Int,
    Long,
    Depth,
    ARGBInt,
    RGBAUShort,
    RGBA16,
    RGB10A2,
    R8,
    RG16,
    R16,
    RGHalf,
    RG16,
    R8Int,
    RG8Int,
    R16Int,
    R32Int,
    RGBA8,
    RFloat,
    RGHalf,
    RHalf
};

enum class RenderTextureMemoryless {
    None,
    Depth,
    Color
};

struct RenderTextureDescriptor {
    int width;
    int height;
    int volumeDepth;
    int mipCount;
    int depthBufferBits;
    RenderTextureFormat colorFormat;
    RenderTextureFormat depthFormat;
    int stencilFormat;
    int antiAliasing;
    bool enableRandomWrite;
    bool useMipMap;
    bool sRGB;
    TextureDimension dimension;
    RenderTextureMemoryless memoryless;
    bool bindMSRenderTarget;
    bool bindMSDepthSurface;
    bool useDynamicscale;
    bool forceIntoRT;
};

class RenderTexture : public Texture {
public:
    virtual ~RenderTexture() = default;

    // 创建/释放
    virtual bool Create() = 0;
    virtual void Release() = 0;

    // 是否有效
    virtual bool IsCreated() const = 0;
    virtual bool IsDestroyed() const = 0;

    // 颜色缓冲
    virtual Texture* GetColorBuffer() = 0;
    virtual void SetColorBuffer(Texture* color) = 0;

    // 深度缓冲
    virtual Texture* GetDepthBuffer() = 0;
    virtual void SetDepthBuffer(Texture* depth) = 0;

    // 深度模板
    virtual int GetDepthBufferBits() const = 0;

    // MSAA
    virtual int GetAntiAliasing() const = 0;
    virtual void SetAntiAliasing(int aa) = 0;

    // 纹理数量
    virtual int GetVolumeDepth() const = 0;
    virtual int GetMipMapLevelCount() const = 0;

    // 维度
    virtual TextureDimension GetDimension() const = 0;

    // 是否使用MipMap
    virtual bool GetMipMap() const = 0;
    virtual void SetMipMap(bool value) = 0;

    // sRGB读写
    virtual bool GetSRGBRead() const = 0;
    virtual void SetSRGBRead(bool value) = 0;
    virtual bool GetSRGBWrite() const = 0;
    virtual void SetSRGBWrite(bool value) = 0;

    // 临时渲染纹理
    static RenderTexture* GetTemporary(const RenderTextureDescriptor& desc);
    static void ReleaseTemporary(RenderTexture* rt);

    // ==================== 生命周期 ====================

    // 初始化/反初始化
    virtual void Initialize() = 0;
    virtual void Deinitialize() = 0;
    virtual bool IsInitialized() const = 0;

    // 创建/销毁(替代构造函数)
    virtual bool Create() = 0;
    virtual void Destroy() = 0;

    // 是否有效
    virtual bool IsCreated() const = 0;
    virtual bool IsDestroyed() const = 0;

    // 描述符
    virtual void* GetDescriptor() = 0;

    // 目标纹理
    virtual void SetTargetTexture(Texture* tex) = 0;
    virtual Texture* GetTargetTexture() = 0;

    // ==================== 激活/解析 ====================

    // 激活/停用
    virtual void Activate() = 0;
    virtual void Resolve() = 0;
    virtual void Resolve(Texture* target, int mipLevel = 0) = 0;
};

} // namespace Graphics
} // namespace XCEngine

2.5 ComputeBuffer计算缓冲

namespace XCEngine {
namespace Graphics {

enum class ComputeBufferType {
    Default,
    Raw,
    Append,
    Counter,
    DrawIndirect,
    Structured,
    ByteAddress
};

enum class ComputeBufferUsage {
    Default = 0,
    Dynamic = 1,
    Immutable = 2,
    Staging = 3
};

struct ComputeBufferDescriptor {
    int count;
    int stride;
    ComputeBufferType type;
    ComputeBufferUsage usage;
};

class ComputeBuffer {
public:
    virtual ~ComputeBuffer() = default;

    // 属性
    virtual int GetCount() const = 0;
    virtual int GetStride() const = 0;
    virtual ComputeBufferType GetBufferType() const = 0;

    // 数据操作
    virtual void SetData(const void* data) = 0;
    virtual void GetData(void* data) = 0;
    virtual void SetCounterValue(int counterValue) = 0;

    // 原子操作用于Append/Counter类型
    virtual void Begin() = 0;  // 开始计数
    virtual void End() = 0;    // 结束计数
    virtual int GetCounterValue() = 0;

    // 有效性检查
    virtual bool IsValid() const = 0;

    // 底层句柄
    virtual void* GetNativeBufferPtr() = 0;
};

} // namespace Graphics
} // namespace XCEngine

2.6 Shader与ComputeShader

namespace XCEngine {
namespace Graphics {

// Shader属性类型
enum class ShaderPropertyType {
    Color,
    Vector,
    Float,
    Range,
    Texture
};

struct ShaderProperty {
    std::string name;
    ShaderPropertyType type;
    int nameID;
    float defaultValue;
    float defaultMin;
    float defaultMax;
};

// Shader编译结果
struct ShaderCompilationResult {
    bool success;
    std::string errorMessage;
    int line;
    std::vector<std::string> errors;
    std::vector<std::string> warnings;
};

// Shader源
struct ShaderSource {
    const char* code;
    const char* filename;
    const char* entryPoint;
    ShaderLanguage language;
};

// Shader语言
enum class ShaderLanguage {
    HLSL,
    GLSL,
    SPIRV,
    DXIL
};

// Shader类型
enum class ShaderType {
    Vertex,
    Fragment,
    Geometry,
    Compute,
    Hull,
    Domain,
    RayGeneration,
    RayIntersection,
    RayMiss,
    RayClosestHit
};

class Shader {
public:
    virtual ~Shader() = default;

    // 属性
    virtual const char* GetName() const = 0;
    virtual int GetPropertyCount() const = 0;
    virtual ShaderProperty GetProperty(int index) const = 0;
    virtual int FindPropertyIndex(const char* name) const = 0;
    virtual ShaderPropertyType GetPropertyType(int nameID) const = 0;

    // 编译
    virtual bool IsSupported() const = 0;
    virtual bool IsValid() const = 0;
    virtual bool Compile(const char* entryPoint, ShaderType type) = 0;

    // Pass数量
    virtual int GetPassCount() const = 0;

    // 查找属性
    virtual int FindPropertyIndexByName(const char* name) const = 0;

    // 关键字
    virtual void DisableKeyword(const char* keyword) = 0;
    virtual void EnableKeyword(const char* keyword) = 0;
    virtual bool IsKeywordEnabled(const char* keyword) const = 0;

    // 获取Shader变体数量
    virtual int GetVariantCount() const = 0;
    virtual int GetVariantCount(int pass) const = 0;

    // 设置全局关键词
    static void EnableKeywordGlobal(const char* keyword);
    static void DisableKeywordGlobal(const char* keyword);

    // 预编译
    virtual void Precompile() = 0;
};

// Compute Shader
class ComputeShader : public Shader {
public:
    virtual ~ComputeShader() = 0;

    // 内核
    virtual const char* GetKernelName() const = 0;
    virtual void SetKernelArg(const char* argName, const void* data, int dataSize) = 0;
    virtual void SetTexture(const char* argName, Texture* texture) = 0;
    virtual void SetBuffer(const char* argName, ComputeBuffer* buffer) = 0;

    // 线程组大小
    virtual int GetKernelThreadGroupSizeX() const = 0;
    virtual int GetKernelThreadGroupSizeY() const = 0;
    virtual int GetKernelThreadGroupSizeZ() const = 0;
};

// Compute Program
class ComputeProgram {
public:
    virtual ~ComputeProgram() = 0;

    virtual ComputeShader* GetKernel() const = 0;
    virtual bool IsValid() const = 0;
    virtual void GetKernelThreadGroupSizes(size_t& x, size_t& y, size_t& z) const = 0;
};

} // namespace Graphics
} // namespace XCEngine

2.7 Material与RenderState

namespace XCEngine {
namespace Graphics {

// 混合模式
enum class BlendMode {
    Alpha,
    AlphaPremultiply,
    Additive,
    Multiply,
    Overlay,
    Opaque,
    Transparent,
    Custom
};

// 混合因子
enum class BlendFactor {
    Zero,
    One,
    SrcColor,
    InvSrcColor,
    SrcAlpha,
    InvSrcAlpha,
    DstAlpha,
    InvDstAlpha,
    DstColor,
    InvDstColor,
    SrcAlphaSat,
    BlendFactor,
    InvBlendFactor,
    Src1Color,
    InvSrc1Color,
    Src1Alpha,
    InvSrc1Alpha
};

// 混合操作
enum class BlendOp {
    Add,
    Subtract,
    ReverseSubtract,
    Min,
    Max
};

// 比较函数
enum class CompareFunction {
    Disabled,
    Never,
    Less,
    Equal,
    LessEqual,
    Greater,
    NotEqual,
    GreaterEqual,
    Always
};

// 模板操作
enum class StencilOp {
    Keep,
    Zero,
    Replace,
    IncrSat,
    DecrSat,
    Invert,
    IncrWrap,
    DecrWrap
};

// 背面剔除
enum class CullMode {
    Off,
    Front,
    Back
};

// 深度写入
enum class DepthWrite {
    Less,
    LessEqual,
    Equal,
    GreaterEqual,
    Greater,
    Always
};

// 颜色写入
enum class ColorWriteMask {
    Alpha = 1,
    Blue = 2,
    Green = 4,
    Red = 8,
    All = 15
};

struct RenderState {
    // 混合
    BlendMode blend;
    BlendFactor srcBlend;
    BlendFactor dstBlend;
    BlendOp blendOp;
    BlendFactor srcBlendAlpha;
    BlendFactor dstBlendAlpha;
    BlendOp blendOpAlpha;
    ColorWriteMask colorWriteMask;

    // 深度
    bool depthWrite;
    bool depthTest;
    CompareFunction depthFunc;

    // 模板
    bool stencil;
    CompareFunction stencilCompare;
    StencilOp stencilPass;
    StencilOp stencilFail;
    StencilOp stencilZFail;
    byte stencilReadMask;
    byte stencilWriteMask;
    byte stencilRef;

    // 背面剔除
    CullMode cullMode;
    bool frontFaceCCW;

    // 深度偏移
    bool depthBias;
    float slopeScaledDepthBias;
    float depthBiasClamp;
    float depthBiasConstantFactor;

    // 渲染队列
    int renderQueue;
};

// ==================== Pass渲染通道 ====================
// Unity中每个Material有多个Pass每个Pass独立渲染
class Pass {
public:
    virtual ~Pass() = default;

    // 渲染状态
    virtual const RenderState& GetRenderState() const = 0;
    virtual void SetRenderState(const RenderState& state) = 0;

    // Shader
    virtual Shader* GetShader() const = 0;
    virtual void SetShader(Shader* shader) = 0;

    // 混合
    virtual void SetBlendMode(BlendMode mode) = 0;

    // 模板
    virtual void SetStencil(const RenderState& state) = 0;

    // 渲染队列覆盖
    virtual void SetRenderQueue(int queue) = 0;
    virtual int GetRenderQueue() const = 0;
};

// ==================== Material材质 ====================

class Material {
public:
    virtual ~Material() = default;

    // Shader
    virtual Shader* GetShader() const = 0;
    virtual void SetShader(Shader* shader) = 0;

    // Pass管理
    virtual int GetPassCount() const = 0;
    virtual Pass* GetPass(int index) = 0;
    virtual Pass* CreatePass(const char* name = nullptr) = 0;
    virtual void ReleasePass(Pass* pass) = 0;
    virtual const char* GetPassName(int index) const = 0;
    virtual int FindPass(const char* name) const = 0;
    virtual void SetPass(int pass) = 0;

    // 快捷方法作用于当前Pass
    virtual void SetInt(const char* name, int value) = 0;
    virtual void SetFloat(const char* name, float value) = 0;
    virtual void SetFloatArray(const char* name, const float* values, int count) = 0;
    virtual void SetVector(const char* name, const float4& value) = 0;
    virtual void SetVectorArray(const char* name, const float4* values, int count) = 0;
    virtual void SetMatrix(const char* name, const float4x4& value) = 0;
    virtual void SetMatrixArray(const char* name, const float4x4* values, int count) = 0;
    virtual void SetTexture(const char* name, Texture* value) = 0;

    // 渲染状态快捷方法作用于当前Pass
    virtual RenderState GetRenderState() const = 0;
    virtual void SetRenderState(const RenderState& state) = 0;
    virtual void SetOverrideTag(const char* tag) = 0;

    // 渲染队列
    virtual int GetRenderQueue() const = 0;
    virtual void SetRenderQueue(int queue) = 0;
    virtual void SetRenderQueue(int queue, int subqueueShift) = 0;

    // 关键字
    virtual void EnableKeyword(const char* keyword) = 0;
    virtual void DisableKeyword(const char* keyword) = 0;
    virtual bool IsKeywordEnabled(const char* keyword) const = 0;
    virtual void ShaderKeywordsFromGlobal() = 0;

    // Pass启用
    virtual void SetPassEnabled(const char* passName, bool enabled) = 0;
    virtual bool IsPassEnabled(const char* passName) const = 0;

    // 复制
    virtual Material* Clone() = 0;
};

} // namespace Graphics
} // namespace XCEngine

2.8 Mesh网格

namespace XCEngine {
namespace Graphics {

enum class MeshTopology {
    Points,
    Lines,
    LineStrip,
    Triangles,
    TriangleStrip,
    Quads
};

enum class MeshIndexFormat {
    Index16,
    Index32
};

class Mesh {
public:
    virtual ~Mesh() = 0;

    // 顶点数据
    virtual void SetVertices(const float3* vertices, int count) = 0;
    virtual void SetVertices(const void* vertices, int count, const VertexAttribute* attributes, int attributeCount) = 0;
    virtual void GetVertices(float3* vertices) = 0;
    virtual int GetVertexCount() const = 0;

    // 索引数据
    virtual void SetIndices(const uint16_t* indices, int count) = 0;
    virtual void SetIndices(const uint32_t* indices, int count) = 0;
    virtual void GetIndices(uint16_t* indices) = 0;
    virtual void GetIndices(uint32_t* indices) = 0;
    virtual int GetIndexCount() const = 0;
    virtual MeshIndexFormat GetIndexFormat() const = 0;

    // 顶点属性
    virtual void SetTangents(const float4* tangents) = 0;
    virtual void SetNormals(const float3* normals) = 0;
    virtual void SetColors(const Color* colors) = 0;
    virtual void SetColors(const float4* colors) = 0;
    virtual void SetUVs(int channel, const float2* uvs) = 0;
    virtual void SetUVs(int channel, const float3* uvs) = 0;
    virtual void SetBoneWeights(const float4* weights, const uint8_t* indices) = 0;

    // 子网格
    virtual void SetSubmeshCount(int count) = 0;
    virtual void SetSubmesh(int index, int startIndex, int indexCount, int baseVertex) = 0;

    // 边界
    virtual void RecalculateBounds() = 0;
    virtual AABB GetBounds() const = 0;

    // 顶点缓冲区
    virtual int GetVertexBufferCount() const = 0;
    virtual VertexBuffer* GetVertexBuffer(int index) const = 0;

    // 索引缓冲区
    virtual VertexBuffer* GetIndexBuffer() const = 0;

    // 拓扑
    virtual void SetTopology(MeshTopology topology) = 0;
    virtual MeshTopology GetTopology() const = 0;

    // 动态标记(频繁更新)
    virtual void MarkDynamic() = 0;
    virtual bool IsDynamic() const = 0;

    // 上传
    virtual void UploadMeshData(bool markNoLongerReadable = false) = 0;
    virtual void Clear() = 0;

    // 获取子网格信息
    virtual int GetSubmeshCount() const = 0;
    virtual void GetSubmesh(int index, int& startIndex, int& indexCount, int& baseVertex) const = 0;
};

} // namespace Graphics
} // namespace XCEngine

2.9 辅助类型

namespace XCEngine {
namespace Graphics {

// 顶点属性格式
enum class VertexAttributeFormat {
    Float,
    Float2,
    Float3,
    Float4,
    Half,
    Half2,
    Half4,
    Int,
    Int2,
    Int3,
    Int4,
    UInt,
    UInt2,
    UInt3,
    UInt4,
    Color,
    Color32,
    Short,
    Short2,
    Short4,
    UShort,
    UShort2,
    UShort4
};

// 顶点输入描述
struct VertexAttribute {
    std::string semantic;
    int semanticIndex;
    VertexAttributeFormat format;
    int stream;
    int offset;
};

// 顶点布局
class VertexLayout {
public:
    void AddAttribute(const char* semantic, int semanticIndex, VertexAttributeFormat format);
    void AddAttribute(const char* semantic, VertexAttributeFormat format);
    const std::vector<VertexAttribute>& GetAttributes() const;
    int GetStride() const;
};

// 视口
struct Viewport {
    float x, y;
    float width, height;
    float minDepth, maxDepth;

    Viewport() : x(0), y(0), width(0), height(0), minDepth(0), maxDepth(1) {}
    Viewport(float x, float y, float w, float h) : x(x), y(y), width(w), height(h), minDepth(0), maxDepth(1) {}
};

// 矩阵和向量使用现有Math库
using float4x4 = XCEngine::Math::Matrix4;
using float4 = XCEngine::Math::Vector4;
using float3 = XCEngine::Math::Vector3;
using float2 = XCEngine::Math::Vector2;
using Color = XCEngine::Math::Color;
using AABB = XCEngine::Math::AABB;

} // namespace Graphics
} // namespace XCEngine

三、后端实现

3.1 D3D12后端

namespace XCEngine {
namespace Graphics {
namespace D3D12 {

class D3D12GraphicsDevice : public GraphicsDevice {
public:
    D3D12GraphicsDevice(ID3D12Device* device, IDXGIFactory4* factory);
    ~D3D12GraphicsDevice() override;

    GraphicsAPI GetAPI() const override { return GraphicsAPI::Direct3D12; }
    const char* GetDeviceName() const override;
    const DeviceCapabilities& GetCapabilities() const override;

    Texture* CreateTexture(const TextureDescriptor& desc) override;
    RenderTexture* CreateRenderTexture(const RenderTextureDescriptor& desc) override;
    ComputeBuffer* CreateComputeBuffer(const ComputeBufferDescriptor& desc) override;
    Mesh* CreateMesh() override;
    ComputeShader* CreateComputeShader(const void* source, int sourceLength) override;
    ComputeProgram* CreateComputeProgram(ComputeShader* computeShader) override;
    Material* CreateMaterial(Shader* shader) override;
    Shader* CreateShader(const ShaderSource& source) override;

    CommandBuffer* CreateCommandBuffer() override;
    void SubmitCommandBuffer(CommandBuffer* cmd) override;

    void WaitForIdle() override;
    bool SupportsTextureFormat(TextureFormat format) const override;
    bool SupportsVertexFormat(VertexAttribute format) const override;

private:
    ComPtr<ID3D12Device> m_device;
    ComPtr<IDXGIFactory4> m_factory;
    ComPtr<ID3D12CommandQueue> m_commandQueue;
    DeviceCapabilities m_capabilities;
};

class D3D12CommandBuffer : public CommandBuffer {
public:
    D3D12CommandBuffer(ID3D12Device* device);
    ~D3D12CommandBuffer() override;

    // 实现CommandBuffer接口...
    // 使用D3D12的ID3D12GraphicsCommandList

private:
    ComPtr<ID3D12GraphicsCommandList> m_commandList;
    std::vector<ComPtr<ID3D12Resource>> m_resources;
};

} // namespace D3D12
} // namespace Graphics
} // namespace XCEngine

3.2 OpenGL后端

namespace XCEngine {
namespace Graphics {
namespace OpenGL {

class OpenGLGraphicsDevice : public GraphicsDevice {
public:
    OpenGLGraphicsDevice(void* windowHandle);
    ~OpenGLGraphicsDevice() override;

    GraphicsAPI GetAPI() const override { return GraphicsAPI::OpenGL; }
    const char* GetDeviceName() const override;
    const DeviceCapabilities& GetCapabilities() const override;

    // 实现工厂方法...

private:
    void* m_windowHandle;
    DeviceCapabilities m_capabilities;
};

class OpenGLCommandBuffer : public CommandBuffer {
public:
    OpenGLCommandBuffer();
    ~OpenGLCommandBuffer() override;

    // 实现CommandBuffer接口
    // OpenGL直接执行无需命令列表
    // 可以使用Display List或记录命令

private:
    GLuint m_vao;
    std::unordered_map<std::string, GLuint> m_boundTextures;
};

} // namespace OpenGL
} // namespace Graphics
} // namespace XCEngine

四、目录结构

engine/
├── include/XCEngine/
│   └── Graphics/
│       ├── CommandBuffer.h       # 命令缓冲
│       ├── GraphicsDevice.h      # 图形设备
│       ├── Texture.h            # 纹理
│       ├── RenderTexture.h      # 渲染纹理
│       ├── ComputeBuffer.h      # 计算缓冲
│       ├── Shader.h             # Shader
│       ├── ComputeShader.h      # Compute Shader
│       ├── Material.h           # 材质
│       ├── Mesh.h               # 网格
│       ├── VertexLayout.h       # 顶点布局
│       ├── Types.h              # 类型定义
│       └── Enums.h              # 枚举定义
│
└── src/
    └── Graphics/
        ├── D3D12/
        │   ├── D3D12Device.cpp
        │   ├── D3D12CommandBuffer.cpp
        │   ├── D3D12Texture.cpp
        │   └── ...
        │
        ├── OpenGL/
        │   ├── OpenGLDevice.cpp
        │   ├── OpenGLCommandBuffer.cpp
        │   ├── OpenGLTexture.cpp
        │   └── ...
        │
        └── Common/
            └── ...

五、使用示例

// 创建图形设备
GraphicsDevice* device = CreateGraphicsDevice(GraphicsAPI::D3D12, hwnd);

// 创建纹理
TextureDescriptor texDesc;
texDesc.width = 1024;
texDesc.height = 1024;
texDesc.format = TextureFormat::RGBA32;
texDesc.dimension = TextureDimension::Texture2D;
Texture* texture = device->CreateTexture(texDesc);

// 创建Compute Shader
ComputeShader* computeShader = device->CreateComputeShader(csSource, csSourceLen);

// 创建Compute Program
ComputeProgram* computeProgram = device->CreateComputeProgram(computeShader);

// 创建CommandBuffer
CommandBuffer* cmd = device->CreateCommandBuffer();

// 渲染命令
cmd->SetComputeTexture(computeShader, "MainTex", texture);
cmd->DispatchCompute(computeShader, 32, 32, 1);

// 执行
device->SubmitCommandBuffer(cmd);

文档版本2.0 更新日期2026-03-16