- c - 在位数组中找到第一个零
- linux - Unix 显示有关匹配两种模式之一的文件的信息
- 正则表达式替换多个文件
- linux - 隐藏来自 xtrace 的命令
我目前正在围绕 OpenGL 的 glUniform
编写包装器C++ 中的函数,努力使它们类型安全。我有一堆 set_uniform
函数被重载以接受 OpenGL POD(GLint
、GLuint
、GLfloat
) 或任何 GLM vector 和矩阵类型。
我认为到目前为止一切都很简单,但后来我遇到了 bool 类型的问题。 GLSL提供了bool
, bec2
, bvec3
and bvec4
所以我必须提供一个set_uniform
重载 GLboolean
以及 GLM bool vector 类型。
根据 OpenGL 手册,没有 glUniform
函数可以接受 GLboolean
或指向 GLboolean
数组的指针。我必须传递 GLint
、GLuint
或 GLfloat
驱动程序将为我进行转换。
Either the i, ui or f variants may be used to provide values for uniform variables of type bool, bvec2, bvec3, bvec4, or arrays of these. The uniform variable will be set to false if the input value is 0 or 0.0f, and it will be set to true otherwise.
在传递之前将 GLboolean
转换为 GLint
很容易,但事实证明 GLM vector 类型更加困难。我越深入实现,就越担心这个库。
将 GLM vector 类型传递给 OpenGL 的推荐方法是使用 glm::value_ptr
:
glm::bvec3 v(true, true, false);
glUniform3iv(some_uniform_id, 1, glm::value_ptr(v));
这段代码有很多问题。
首先,glm::bvec3
is implemented as a struct of 3 bool
s (不是 GLboolean
,而是 C++ bool
)。我认为我不应该直接传递它,因为 glUniform3iv
需要一个指向某些 GLint
的 void
指针。 C++ 规范不保证 bool
的大小。这意味着 glUniform3iv
可能会读取第二个和第三个组件的垃圾,或者更糟的是,它实际上正在读取数组末尾。
为了纠正这个问题,我在传递给 OpenGL 之前从 glm::bvec3
转换为 glm::ivec3
:
glm::bvec3 bv(true, true, false);
glm::ivec3 iv = bv;
glUniform3iv(some_uniform_id, 1, glm::value_ptr(iv));
我对此不是 100% 满意,因为 glm::ivec3
有一个 glm::detail::mediump_int_t
的值类型,它是一个 typedef
用于 int
而不是 GLint
但也许这可以归结为“库设计者知道大小是相同的”。
第二个也是更主要的问题是 glm::value_ptr
是 just passing the address of the first struct
member并将 struct
视为 array
,而不考虑填充。
我是不是漏掉了什么? GLM 库与 OpenGL 一起使用非常广泛,它甚至列在 Khronos 自己的 wiki 上。然而,它提供的用于将其结构传递给 OpenGL 的函数,即 glm::value_ptr
,没有努力确保它传递的类型实际上与 OpenGL 期望的类型大小相同,并且完全无视任何可能存在的填充。 GLM 库是否在类型大小和结构填充方面做了一些隐藏的欺骗,以便发送到 OpenGL 的数据是有效的,或者这个库是否存在一些严重的基本问题?
最佳答案
Is the GLM library doing some hidden trickery with regard to type sizes and struct padding so that the data sent to OpenGL is valid or does this library have some serious fundamental problems?
都没有。它只是在制作 same assumptions其他人对结构布局和指针算法的行为所做的。
C++ 标准不允许 value_ptr
工作;这显然是未定义的行为。但它也是处理此类事情的常用技术。许多真实的、功能性的代码都假设一个 struct { int x; int y;};
可以被认为等同于 int[2]
。在大多数 C++ 实现下,这一切都将按预期运行。
在处理低级编程时,做出这种性质的假设并非没有道理。
I'm not 100% happy with this since
glm::ivec3
has a value type ofglm::detail::mediump_int_t
which is atypedef
forint
rather thanGLint
but maybe this can be chalked up to 'the library designer knows the sizes are the same'.
与此无关。虽然 GLM 被称为“OpenGL 数学”,但它不依赖于 OpenGL 自身。因此,它无法访问 GLint
或任何其他 OpenGL 定义的类型。
因此您可以假设 ivec3
的 value_type
与 GLint
的类型相同(您甚至可以编写 static_assert
s 来验证它)或者你可以做出自己的变化。毕竟,GLM 是模板化的:
using gl_ivec3 = glm::tvec<GLint, 3>;
...
glm::gl_ivec3 iv = bv;
glUniform3iv(some_uniform_id, 1, glm::value_ptr(iv));
关于c++ - 通过 glUniform 将 GLM 的 vector 类型传递给 OpenGL,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49580872/
我有这个析构函数,它在运行时产生错误“vector 迭代器不可取消引用”。 gridMatrix 是一个 std::vector * > * > * > * > 我添加了 typename 和 typ
我有一个 vector 的 vector ,比方说 std::vector > my2dArray; 现在我想要一个 vector ,其中包含 my2dArray 中 vector 的大小。手动这看起
假设我有一些 vector :v1、v2、v3 假设我还有一个 vector 来保存这些 vList = {v1, v2, v3} 如果我同步了 (vList),这是否意味着 v1、v2 和 v3 也
我正在创建一个 char 的二维 vector 数组作为类变量,但我在将 vector 添加到 vector 数组中时遇到了麻烦。 我正在使用 C++ 11 标准运行 gcc。 我尝试使用 vecto
如何修改 Vec基于 Vec 中某项的信息没有对向量的不可变和可变引用? 我已尝试创建一个最小示例来演示我的特定问题。在我的真实代码中,Builder struct 已经是其他答案提出的中间结构。具体
这个问题在这里已经有了答案: What is the idiomatic Rust way to copy/clone a vector in a parameterized function? (
在我的程序中,我有一个整数 vector 的 vector 。现在我想从 vector 的 vector 中取出一个 vector 并在另一个 vector 容器中对其进行操作,但是我得到了错误...
我得到一个vector>数据由 OpenCV 提供。由于某些原因(例如偏移/缩放),我需要转换数据 Point至Point2f 。我怎样才能做到这一点? 例如: std::vector > conto
我有一个函数,该函数应使用来自字符串类型的给定 vector vector 中的某些元素初始化来自字符串类型的空 vector vector 。我的语法看起来像这样 std::vector> extr
我得到一个vector>数据由 OpenCV 提供。由于某些原因(例如偏移/缩放),我需要转换数据 Point至Point2f 。我怎样才能做到这一点? 例如: std::vector > conto
这里有很多类似的问题,但我没有真正找到任何可以特别回答我的问题的问题。 我有一个 vector 的 vector 作为类的属性。另一个属性是 bucket_count。我想将 vector 的 vec
如果我像这样创建一个 vector 的 vector : std::vector> myVectorOfVectors; 然后用一些东西填充它: std::vector myVector1; myVe
我正在用 C++ 编写自定义 vector 类。我对这样的代码有疑问: vector vec; vec.push_back(one); vec.push_back(two);
这是我发布的问题 c++ program for reading an unknown size csv file (filled only with floats) with constant (b
vector> a; for (int i=0;i v(i+1); iota(v.begin(),v.end(),1); a.push_back(v); } a.erase(a.beg
也许已经晚了,但我不明白为什么我会得到一个超出此代码范围的 vector 下标: int m = 3; int n = 2; std::vector> path(m, std::vector(n, 0
这个问题真的很奇怪,我似乎找不到任何导致它的原因。 所以这里有一个赋值运算符重载函数,鸟类和哺乳动物都是 vector 。 (下面是类) const Register& Register::opera
我怎么去 std::vector> 只是 std::vector> ?有真正有效的方法吗? 最佳答案 我会做这样的事情: #include #include int main() { //
我正在尝试将这些 vector 中的一些数据写入文本文件。当我运行代码时,它返回运行时错误。 Category、Product、Cart、Customer和Address都是struct 包含每个 g
显然它会因您使用的编译器而异,但我很好奇执行 vector> 时的性能问题与 vector*> ,尤其是在 C++ 中。具体来说: 假设您的外部 vector 已满,您想要开始将元素插入到第一个内部
我是一名优秀的程序员,十分优秀!