c++ - 如何将指向 GLEW 函数的指针传递给模板?

标签 c++ templates opengl

我正在尝试为保存缓冲区的 OpenGL 编写一个简单的包装器。由于有许多缓冲区,每个缓冲区都有专门的生成和删除功能,我希望使用一个模板,以便我可以轻松地创建这些包装器。最终目标是拥有这样的东西:

gl::VBO v;
v.gen();

我已尝试执行以下操作:

using TBuilder = void(*)(GLsizei, GLuint *);

template<std::size_t N, TBuilder TConstructor, TBuilder TFreer>
struct OGLWrapper{
    std::array<GLuint, N> data;
    void gen(){
        TConstructor(N, &data[0]);
    }
    ~OGLWrapper(){
        TFreer(N, &data[0]);
    }
};

using VBO = OGLWrapper<1, glGenBuffers, glDeleteBuffers>;

问题是 glGenBuffersglDeleteBuffers 不是编译时常量。在调用 glewInit() 之前它们是不可用的。我希望有一种方法可以延迟查找这些函数,直到生成 VBO。在这种情况下完全有可能无法使用模板,但我希望有一种巧妙的方式来包装我的 OpenGL 资源。


阅读答案后,我了解到:

using TBuilder = decltype(&glGenBuffers);
using TFreer = decltype(&glDeleteBuffers);

template<std::size_t N, TBuilder TCons, TFreer TDes>
struct OGLWrapper{
    std::array<GLuint, N> data;
    OGLWrapper():data{}{}
    void gen(){
        (*TCons)(N, &data[0]);
    }
    ~OGLWrapper(){
        (*TDes)(N, &data[0]);
    }
};

using VBO = OGLWrapper<1, &glGenBuffers, &glDeleteBuffers>;
using VAO = OGLWrapper<1, &glGenVertexArrays, &glDeleteVertexArrays>;

这很好,但我希望删除 TBuilder 和 TFreer typedef。我担心的是泛化,因为我不确定其他函数是否使用这些签名。有没有办法让模板推导出这些类型?

最佳答案

using TBuilder = void(*)(GLsizei, GLuint *);

template<std::size_t N, TBuilder* TConstructor, TBuilder* TFreer>
struct OGLWrapper{
  std::array<GLuint, N> data;
  void gen(){
    (*TConstructor)(N, &data[0]);
  }
  ~OGLWrapper(){
    (*TFreer)(N, &data[0]);
  }
};

using VBO = OGLWrapper<1, &glGenBuffers, &glDeleteBuffers>;

实例

我们存储指向函数指针的指针。函数指针仅在您调用 glewInit() 时更新。因此,如果您在此之前使用 VBO,它会执行 UB,但您期望什么?

您可能需要注意的一件事是调用约定。但是只要您的 TBuildertypedef 是准确的,您就可以了。

最后一个问题是,即使未调用 gen,您的析构函数也会运行。也许你应该在类的构造函数中运行 gen?或者记录是否使用 bool 调用了 gen

关于c++ - 如何将指向 GLEW 函数的指针传递给模板?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29658389/

相关文章:

c++ - 带模板的二进制搜索功能,用于数组-编译问题

java - 建议使用一个用于 OpenGL 的矩阵运算的简单 Java 数学库 (lwjgl)

c++ - 使用 CGL 编译 MacOS 应用程序

c++ - 根据模板类型动态指定要使用的方法

c++ - 如何使用模板查找最多的多个数字?

c++ - 如何使用带矩阵的透视图设置特定视点

c++将指针传递给函数

c++ - 在没有适当的 operator() 的情况下调用类类型的对象

c++ - 使用 Sleep() 或 SetTimer 的线程循环

c++ - 令人尴尬的并行代码的低性能