0

I saw in a tutorial that you can fill a VBO directly with a std::vector<glm::vec3> like this:

std::vector< glm::vec3 > vertices;
// fill the vector and create VBO
glBufferData(GL_ARRAY_BUFFER, vertices.size() * sizeof(glm::vec3), &vertices[0], GL_STATIC_DRAW);

Now I wonder if I can do the same with a QVector<QVector3D>. QVector can replace std::vector because the memory is contiguous in both of them. But QVector3D and glm::vec3 are both non POD(correct me if I am wrong) and somehow glm::vec3 works. Is it standard behaviour? Can I try to do the same with QVector3D?

genpfault
  • 51,148
  • 11
  • 85
  • 139
Nazar554
  • 4,105
  • 3
  • 27
  • 38
  • I am scared that UB will kill my cat...:P – Nazar554 Apr 23 '14 at 16:54
  • I know. But sometimes the cat must be sacrificed for the greater good :) `glm::vec3` uses `float` types, `QVector3D` uses `float` as well. It should work fine. I think that C++11 makes both types [POD](http://stackoverflow.com/a/7169675/1329652) again. – Kuba hasn't forgotten Monica Apr 23 '14 at 16:59

1 Answers1

1

I would not be comfortable using glm::vec3 in this way, as I don't recall seeing any documentation specifying its internal layout. The fact that there is a glm::value_ptr(obj) helper defined in type_ptr.hpp makes me even more suspicious.

That said, you can inspect its source code and verify for yourself that it has exactly 3 floats and no extra fields, and also put in a compile-time check that sizeof(glm::vec3) == 3*sizeof(float) in case struct padding does anything funny.

A cursory look at the documentation for QVector3D does not show any indication of the internal memory layout. So just as with glm::vec3 you would need to inspect its source code to verify that x,y,z are laid out in the order you expect, and then verify that sizeof(QVector3d) == sizeof(GLfloat) * 3.

Also keep in mind that while it may work on your specific compiler/platform, YMMV if trying to port to other platforms. Or for that matter, if updating to a new version of either library.

EDIT: Regarding the comment on OP about POD, I don't think that's actually relevant? Neither 'trivial' nor 'standard layout' imply that there aren't extra fields in the class for bookkeeping, nor anything about padding, and I'm not sure you can guarantee either classification in the first place based on the published documentation. trivial vs. standard layout vs. POD

Community
  • 1
  • 1
Kevin Lam
  • 445
  • 3
  • 9
  • I checked the QVector3D header and it seems that the x,y,z layout is right. And sizeof(QVector3D) is 12(3*4). But it seems that I will not use this if it is not portable. – Nazar554 Apr 23 '14 at 17:28
  • I’ve used `QVector`’s `.data()` in production as a buffer of 3n `float`s. I static assert that `sizeof(QVector3D) == 3*sizeof(float)` and same with `alignof` and I also have a unit test that checks that the elements of a `QVector3D` are where they should be within the object. (That could probably be done in a `static_assert` with `constexpr` now... – Ben Jun 15 '19 at 03:19