In OpenGL, this looks something like this:
// Specification of what one vertex looks like.
struct Vertex
{
float Position[3];
float Normal[3];
float TexCoord[2];
};
// Get the loaded vertex data, and the size of the data.
const Vertex* vertexData = model.GetVertices();
size_t vertexCount = model.GetVertexCount();
size_t vertexDataSizeInBytes = vertexCount
* sizeof(Vertex);
// Create a GPU vertex buffer and upload the vertex data into it.
GLuint vertexBuffer;
glGenBuffers(1, &vertexBuffer);
glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
glBufferData(GL_ARRAY_BUFFER, vertexDataSizeInBytes
, vertexData
, GL_STATIC_DRAW);
// Define the format of the vertex attributes.
// Arguments: attribute index, attribute size, attribute type, attribute normalized, attribute stride, attribute initial offset (casted to void* for historical reasons).
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), (GLvoid*) offsetof(Vertex, Position));
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), (GLvoid*) offsetof(Vertex, Normal));
glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, sizeof(Vertex), (GLvoid*) offsetof(Vertex, TexCoord));
// Enable the vertex attributes.
glEnableVertexAttribArray(0);
glEnableVertexAttribArray(1);
glEnableVertexAttribArray(2);
// Draw the model.
glDrawArrays(GL_TRIANGLES, 0,
vertexCount
);
// Define the format of the vertex attributes.
// Arguments: attribute index, attribute size, attribute type, attribute normalized, attribute stride, attribute initial offset.
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), (GLvoid*) offsetof(Vertex, Position));
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), (GLvoid*) offsetof(Vertex, Normal));
glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, sizeof(Vertex), (GLvoid*) offsetof(Vertex, TexCoord));
struct Vertex
{
float Position[3];
float Normal[3];
float TexCoord[2];
};
Therefore, I'd like to write my struct Vertex like this instead:
struct Vertex
{
std::array<float,3> Position;
std::array<float,3> Normal;
std::array<float,2> TexCoord;
};
// Define the format of the vertex attributes.
// Arguments: attribute index, attribute size, attribute type, attribute normalized, attribute stride, attribute initial offset.
glVertexAttribPointer(0, Vertex().Position.size(), GL_FLOAT, GL_FALSE, sizeof(Vertex), (GLvoid*) offsetof(Vertex, Position));
glVertexAttribPointer(1, Vertex().Normal.size(), GL_FLOAT, GL_FALSE, sizeof(Vertex), (GLvoid*) offsetof(Vertex, Normal));
glVertexAttribPointer(2, Vertex().TexCoord.size(), GL_FLOAT, GL_FALSE, sizeof(Vertex), (GLvoid*) offsetof(Vertex, TexCoord));
For now, I rely on alternate solutions like "sizeof(Position) / sizeof(*Position)", or keeping a "static const int PositionSize = 3" and using that everywhere.
When I looked around Stack Overflow, I found threads like this one (http://stackoverflow.com/questions/8262963/stdarray-alignment) where others had found implementations where that was not necessarily the case.
Thus, in conclusion, I would like to suggest that standard library implementations be held accountable for guaranteeing that sizeof/alignof a std::array match that of an identical type/size C-style array (except the special case of a 0-sized std::array, which has no C-style array equivalent.) This would make it much easier to work with data that has a specified binary format (such as GPU vertex buffer data), and make std::array a much safer refactoring tool for replacing C-style arrays.
To view this discussion on the web visit https://groups.google.com/d/msgid/unofficial-real-time-cxx/CALQmNFh%2B6VVMjWUSoz6-PZZTnM6KyoWaJcATLiLaGWpLpunPPQ%40mail.gmail.com.
--
You received this message because you are subscribed to the Google Groups "unofficial-real-time-cxx" group.
To unsubscribe from this group and stop receiving emails from it, send an email to unofficial-real-ti...@googlegroups.com.
To post to this group, send email to unofficial-r...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/unofficial-real-time-cxx/CAFk2RUZTkSeVLP-kmD4L2yLmmkcK0VxjqL8bVu%2B55cJv3gqLCg%40mail.gmail.com.
I didn't know about make_array, thanks. That would be a good alternative in this situation.On Mon, May 25, 2015 at 8:47 AM, Ville Voutilainen <ville.vo...@gmail.com> wrote:On 25 May 2015 at 18:41, Matt Newport <ma...@mattnewport.com> wrote:
> I think std::size is actually a preferable solution. I find myself doing
> this kind of thing a lot in D3D11:
>
> ID3D11Buffer* vsConstantBuffers[] = {cameraConstantBuffer,
> objectConstantBuffer, lightingConstantBuffer};
> context->VSSetConstantBuffers(0, size(vsConstantBuffers),
> vsConstantBuffers);
>
> In this situation using std::array would require redundantly specifying the
> number of elements as a template argument rather than relying on
> automatically deducing the array size with a plain C array.
There's always make_array, see
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2015/n4481.html#container.array.creation
struct BoundingBox1
{
std::array<float,3> Minimum;
std::array<float,3> Maximum;
};
struct BoundingBox2
{
float Minimum[3];
float Maximum[3];
};
BoundingBox1 bbox1;
bbox1.Minimum = { 1.0f, 2.0f, 3.0f }; // nice!
bbox1.Maximum = { 2.0f, 3.0f, 4.0f };
BoundingBox2 bbox2;
bbox2.Minimum = { 1.0f, 2.0f, 3.0f }; // error: assigning to an array
bbox2.Maximum = { 2.0f, 3.0f, 4.0f }; // from an initializer list :(
--
You received this message because you are subscribed to the Google Groups "unofficial-real-time-cxx" group.
To unsubscribe from this group and stop receiving emails from it, send an email to unofficial-real-ti...@googlegroups.com.
To post to this group, send email to unofficial-r...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/unofficial-real-time-cxx/d587120b-79de-45f6-ad50-335b73d9c3ee%40googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/unofficial-real-time-cxx/CA%2BnMcg6whca0pP4TbN1_g4u2wm0fdOYgdnNAua908zLWQvbY_g%40mail.gmail.com.
Is there a rationale for why a standard library implementation would want to unilaterally specify a different alignment for std::array?
-----------------------------------------------------------------
Unfortunately, I don't feel comfortable designing struct Vertex like this, because it seems like you can't depend on sizeof(array<T,N>) == sizeof(T[N]) and alignof(array<T,N>) == alignof(T[N]).