Problem with binding index buffers in DirectX 11 - c++

I have rendered 3d objects numerous times before in DirectX but this time encountered a strange problem, on which I wasted a day figuring out and still have nothing. I have a DX11 Context in which I load 3d models from obj files. I had to make a skybox and figured out that a good starting point would be to try to render a cube and then proceed further. My graphics pipeline draws many things, so unless I purposefully unbind the index shader, it will remain bound. If I try to render the cube with my cube’s index buffer bound, it doesn’t work. But if I don’t bind the index buffer it uses the previously bound buffer (as far as I can make out) and renders the vertices weirdly as expected. I must be missing something major here. I have spent hours and hours and still couldn’t solve the problem. I would be grateful if someone could help…
PS: I am using these weird indices just for testing, as I had assumed that they were causing the problem.
I am quite baffled by this behavior, I must be missing something here.
void SkyBox::CreateShader(Vertex * verts, size_t size_of_verts, WORD* indices, size_t size_of_indices)
{
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// Shader Compilation ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
ID3D10Blob* VS = nullptr;
ID3D10Blob* PS = nullptr;
ID3D10Blob* ErrMSG = nullptr;
D3DX11CompileFromFile("SkyShader.shader", 0, 0, "SKYMAP_VS", "vs_4_0", 0, 0, 0, &VS, &ErrMSG, 0);
D3DX11CompileFromFile("SkyShader.shader", 0, 0, "SKYMAP_PS", "ps_4_0", 0, 0, 0, &PS, &ErrMSG, 0);
char* p = new char[100];
// encapsulate both shaders into shader objects
if (!ErrMSG && VS && PS)
{
pRenderer->GetDevice()->CreateVertexShader(VS->GetBufferPointer(), VS->GetBufferSize(), nullptr, &pVertexShader);
pRenderer->GetDevice()->CreatePixelShader(PS->GetBufferPointer(), PS->GetBufferSize(), nullptr, &pPixelShader);
}
else
{
ELOG("The Shader file cannot be compiled. Please run this executable from the directory that contains the Shader file.");
exit(1);
}
D3D11_INPUT_ELEMENT_DESC IED[] =
{
{"POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
{"NORMAL", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 12, D3D11_INPUT_PER_VERTEX_DATA, 0 },
};
UINT numElements = ARRAYSIZE(IED);
pRenderer->GetDevice()->CreateInputLayout(IED, 2, VS->GetBufferPointer(), VS->GetBufferSize(), &pLayout);
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// Vertex Buffer ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
D3D11_BUFFER_DESC bd;
ZeroMemory(&bd, sizeof(bd));
bd.Usage = D3D11_USAGE_DYNAMIC;
bd.ByteWidth = size_of_verts;
bd.BindFlags = D3D11_BIND_VERTEX_BUFFER;
bd.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
D3D11_SUBRESOURCE_DATA InitData;
ZeroMemory(&InitData, sizeof(InitData));
InitData.pSysMem = verts;
pRenderer->GetDevice()->CreateBuffer(&bd, &InitData, OUT &pVBuffer); // creating the buffer
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// Index Buffer /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
ZeroMemory(&bd, sizeof(bd));
bd.Usage = D3D11_USAGE_DEFAULT;
bd.ByteWidth = size_of_indices;
bd.BindFlags = D3D11_BIND_INDEX_BUFFER;
bd.CPUAccessFlags = 0;
ZeroMemory(&InitData, sizeof(InitData));
InitData.pSysMem = indices;
pRenderer->GetDevice()->CreateBuffer(&bd, &InitData, OUT &pIBuffer);
}
SkyBox::SkyBox()
{
}
SkyBox::SkyBox(CRenderer * pRenderer)
:
pRenderer(pRenderer)
{
}
void SkyBox::CreateTri()
{
Vertex verts[]
{
{-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, -0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, 0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, 0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, 0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, 0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, 0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, -0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, -0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, -0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, 0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, 0.5f, -0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{ 0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 0.0f},
{-0.5f, 0.5f, -0.5f, 0.0f, 0.0f, 0.0f}
};
WORD indices[] {
0, 1, 2,
3, 4, 5,
6, 7, 8,
9, 10, 11,
12, 13, 14,
15, 16, 17,
18, 19, 20,
21, 22, 23,
24, 25, 26,
27, 28, 29,
30, 31, 32,
33, 34, 35,
};
CubeMesh Cube;
Cube.CreateMesh();
CreateShader(verts, sizeof(Vertex) * 36, indices, sizeof(WORD) * 36);
}
void SkyBox::Render()
{
const UINT vStride = sizeof(Vertex);
const UINT vOffset = 0;
pRenderer->GetDeviceContext()->VSSetShader(pVertexShader, 0, 0);
pRenderer->GetDeviceContext()->PSSetShader(pPixelShader, 0, 0);
pRenderer->GetDeviceContext()->IASetInputLayout(pLayout);
pRenderer->GetDeviceContext()->IASetVertexBuffers(0, 1, &pVBuffer, &vStride, &vOffset);
pRenderer->GetDeviceContext()->IASetIndexBuffer(pIBuffer, DXGI_FORMAT_R16_UINT, 0);
pRenderer->GetDeviceContext()->DrawIndexed(36, 0, 0);
}
And here's the shader
float4 SKYMAP_VS( float4 Pos : POSITION, float4 Norm : NORMAL ) : SV_POSITION
{
return Pos;
}
float4 SKYMAP_PS( float4 Pos : SV_POSITION ) : SV_Target
{
return float4( 1.0f, 1.0f, 0.0f, 1.0f );
}
// I don't know how it could be simpler...
```c++
In SkyBox::Render(), if i don't set the index buffer it uses the previously bound buffer (as mentioned before) but if i bind the buffer it literally draws nothing. And yes, the the index buffer is created successfully.

Related

How to subdivide Plane in OpenGL?

I want to generate VBO and EBO for subdivided plane, I draw with GL_TRIANGLES, I want to know effective way to do this.
Eventually it will be a huge cube consists from 6 subdivided plane, so, i can't imagine alghorithm to generate VBO and EBO for subdivide.
What i have as input data:
cube
std::vector<float> vertices =
{
// +Y SIDE //Colors
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f,
0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f,
-0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f,
0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f,
// -Y SIDE
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f, 0.0f,
0.5f, -0.5f, -0.5f, 0.0f, 1.0f, 0.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 1.0f, 0.0f,
0.5f, -0.5f, 0.5f, 0.0f, 1.0f, 0.0f,
// +X SIDE
0.5f, 0.5f, 0.5f, 1.0f, 0.0f, 0.0f,
0.5f, 0.5f, -0.5f, 1.0f, 0.0f, 0.0f,
0.5f, -0.5f, 0.5f, 1.0f, 0.0f, 0.0f,
0.5f, -0.5f, -0.5f, 1.0f, 0.0f, 0.0f,
// -X SIDE
-0.5f, 0.5f, 0.5f, 1.0f, 0.0f, 0.0f,
-0.5f, 0.5f, -0.5f, 1.0f, 0.0f, 0.0f,
-0.5f, -0.5f, 0.5f, 1.0f, 0.0f, 0.0f,
-0.5f, -0.5f, -0.5f, 1.0f, 0.0f, 0.0f,
// +Z SIDE
-0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
// -Z SIDE
-0.5f, 0.5f, -0.5f, 0.0f, 0.0f, 1.0f,
0.5f, 0.5f, -0.5f, 0.0f, 0.0f, 1.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, 1.0f,
0.5f, -0.5f, -0.5f, 0.0f, 0.0f, 1.0f
};
std::vector<unsigned int> indices =
{
// +Y
1, 2, 0, 3, 2, 1,
// -Y
4, 6, 5, 5, 6, 7,
// +X
8, 9, 10, 9, 11, 10,
// -X
14, 13, 12, 14, 15, 13,
// +Z
17, 18, 16, 19, 18, 17,
// -Z
20, 22, 21, 21, 22, 23
};
So, i want to write a function witch accept subdivision and change my indeces and vertices vectors, just loop over existed planes in cube and subdivide it

Cube getting squashed and rendering as trapezium

I'm trying to render a cube and rotate it along it's Y axis using OpenGL ES 2.0, however the cube does not render as a cube but rather as some sort of very flat trapezium. A few images showing the odd behaviour:
Very flat:
beginning to rotate:
mid-rotation:
and after rotation:
I'm not exactly sure what is causing the strange behaviour. I am utilising the Pigs in a Blanket library for rendering on PS Vita.
These are my cube vertices. The first 3 values in each row are the vertex data, the last 2 values are for texture mapping
GLfloat vertices[] = {
-0.5f, -0.5f, -0.5f, 0.0f, 0.0f,
0.5f, -0.5f, -0.5f, 1.0f, 0.0f,
0.5f, 0.5f, -0.5f, 1.0f, 1.0f,
0.5f, 0.5f, -0.5f, 1.0f, 1.0f,
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 0.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f,
0.5f, -0.5f, 0.5f, 1.0f, 0.0f,
0.5f, 0.5f, 0.5f, 1.0f, 1.0f,
0.5f, 0.5f, 0.5f, 1.0f, 1.0f,
-0.5f, 0.5f, 0.5f, 0.0f, 1.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f,
-0.5f, 0.5f, 0.5f, 1.0f, 0.0f,
-0.5f, 0.5f, -0.5f, 1.0f, 1.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f,
-0.5f, 0.5f, 0.5f, 1.0f, 0.0f,
0.5f, 0.5f, 0.5f, 1.0f, 0.0f,
0.5f, 0.5f, -0.5f, 1.0f, 1.0f,
0.5f, -0.5f, -0.5f, 0.0f, 1.0f,
0.5f, -0.5f, -0.5f, 0.0f, 1.0f,
0.5f, -0.5f, 0.5f, 0.0f, 0.0f,
0.5f, 0.5f, 0.5f, 1.0f, 0.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f,
0.5f, -0.5f, -0.5f, 1.0f, 1.0f,
0.5f, -0.5f, 0.5f, 1.0f, 0.0f,
0.5f, -0.5f, 0.5f, 1.0f, 0.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f,
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f,
0.5f, 0.5f, -0.5f, 1.0f, 1.0f,
0.5f, 0.5f, 0.5f, 1.0f, 0.0f,
0.5f, 0.5f, 0.5f, 1.0f, 0.0f,
-0.5f, 0.5f, 0.5f, 0.0f, 0.0f,
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f
};
This is my initialization function. surface_width = 960, surface_height = 544 and aspect = 1.764706
void TestScene::init(EGLint s_width, EGLint s_height)
{
surface_height = s_height;
surface_width = s_width;
model = glm::mat4(1.0f);
projection = glm::mat4(1.0f);
glGenBuffers(1, &VBO);
glBindBuffer(GL_ARRAY_BUFFER, VBO);
glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
texture.load_texture("app0:assets/wall.jpg");
if (!shader.load_shaders("app0:shaders/vert.cg", "app0:shaders/frag.cg"))
sceKernelExitProcess(0);
}
This is my rendering function
void TestScene::render(EGLDisplay display, EGLSurface surface, double deltaTime)
{
glViewport(0, 0, surface_width, surface_height);
glClearColor(0.2f, 0.3f, 0.3f, 1.0f);
glEnable(GL_DEPTH_TEST);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, texture.ID);
glUseProgram(shader.ID);
GLint mvpLoc = glGetUniformLocation(shader.ID, "mvp");
GLint position = glGetAttribLocation(shader.ID, "vPosition");
GLint texLoc = glGetAttribLocation(shader.ID, "vTexCoord");
GLfloat aspect = (GLfloat)surface_width/(GLfloat)surface_height;
projection = glm::perspective(glm::radians(camera.Zoom), aspect, 0.1f, 100.0f);
view = camera.GetViewMatrix();
model = glm::rotate(model, glm::radians(1.0f), glm::vec3(0.0f, -1.0f, 0.0f));
glm::mat4 mvp = projection * view * model;
glUniformMatrix4fv(mvpLoc, 1, GL_FALSE, glm::value_ptr(mvp));
// Bind vertex positions
glEnableVertexAttribArray(position);
glBindBuffer(GL_ARRAY_BUFFER, VBO);
glVertexAttribPointer(position, 3, GL_FLOAT, GL_FALSE, 5 * sizeof(float), (void*)0);
// Bind texture positions
glEnableVertexAttribArray(texLoc);
glVertexAttribPointer(texLoc, 2, GL_FLOAT, GL_FALSE, 5 * sizeof(float), (void*)(3 * sizeof(float)));
glDrawArrays(GL_TRIANGLES, 0, 36);
glDisableVertexAttribArray(position);
glDisableVertexAttribArray(texLoc);
eglSwapBuffers(display, surface);
}
My cameras zoom value is 45.0f and this is the GetViewMatrix method:
glm::mat4 Camera::GetViewMatrix()
{
return glm::lookAt(Position, Position + Front, Up);
}
and finally the shaders:
vert.cg
void main
(
uniform float4x4 mvp,
float4 vPosition,
float2 vTexCoord: TEXCOORD0,
out float4 oPosition: POSITION,
out float2 fTexCoord: TEXCOORD
)
{
oPosition = mul(mvp, vPosition);
fTexCoord = vTexCoord;
};
frag.cg
float4 main
(
in float2 fTexCoord: TEXCOORD0,
uniform sampler2D texture1: TEXUNIT0
)
{
float4 col;
col = tex2D(texture1, fTexCoord);
return col;
}
I have a feeling it has something to do with my projection matrix but I'm not entirely sure. Any help is greatly appreciated, thank you
UPDATE:
If I update the near value in glm::perspective from 0.1f to 1.0f it produces a better looking but still false result, so I'm pretty sure the issue is in my projection matrix. What am I doing wrong here?
projection = glm::perspective(glm::radians(camera.Zoom), aspect, 0.1f, 100.0f);
becomes
projection = glm::perspective(glm::radians(camera.Zoom), aspect, 1.0f, 100.0f);
for the following results:
Wider but still incorrect
Another angle
Again
I've found the issue. I was multiplying the model view projection matrix incorrectly in the vert shader.
oPosition = mul(mvp, vPosition);
should be
oPosition = mul(vPosition, mvp);
this works with a near value of 0.1f
EDIT
Also the missing faces were due to incorrect winding order with my vertices. Here is a corrected set of vertices, they are in clockwise order glFrontFace(GL_CW);
GLfloat vertices[] = {
// Back face
-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, // Bottom-left
0.5f, -0.5f, -0.5f, 1.0f, 0.0f, // bottom-right
0.5f, 0.5f, -0.5f, 1.0f, 1.0f, // top-right
0.5f, 0.5f, -0.5f, 1.0f, 1.0f, // top-right
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f, // top-left
-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, // bottom-left
// Front face
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, // bottom-left
0.5f, 0.5f, 0.5f, 1.0f, 1.0f, // top-right
0.5f, -0.5f, 0.5f, 1.0f, 0.0f, // bottom-right
0.5f, 0.5f, 0.5f, 1.0f, 1.0f, // top-right
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, // bottom-left
-0.5f, 0.5f, 0.5f, 0.0f, 1.0f, // top-left
// Left face
-0.5f, 0.5f, 0.5f, 1.0f, 0.0f, // top-right
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f, // bottom-left
-0.5f, 0.5f, -0.5f, 1.0f, 1.0f, // top-left
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f, // bottom-left
-0.5f, 0.5f, 0.5f, 1.0f, 0.0f, // top-right
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, // bottom-right
// Right face
0.5f, 0.5f, 0.5f, 1.0f, 0.0f, // top-left
0.5f, 0.5f, -0.5f, 1.0f, 1.0f, // top-right
0.5f, -0.5f, -0.5f, 0.0f, 1.0f, // bottom-right
0.5f, -0.5f, -0.5f, 0.0f, 1.0f, // bottom-right
0.5f, -0.5f, 0.5f, 0.0f, 0.0f, // bottom-left
0.5f, 0.5f, 0.5f, 1.0f, 0.0f, // top-left
// Bottom face
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f, // top-right
0.5f, -0.5f, 0.5f, 1.0f, 0.0f, // bottom-left
0.5f, -0.5f, -0.5f, 1.0f, 1.0f, // top-left
0.5f, -0.5f, 0.5f, 1.0f, 0.0f, // bottom-left
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f, // top-right
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, // bottom-right
// Top face
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f, // top-left
0.5f, 0.5f, -0.5f, 1.0f, 1.0f, // top-right
0.5f, 0.5f, 0.5f, 1.0f, 0.0f, // bottom-right
0.5f, 0.5f, 0.5f, 1.0f, 0.0f, // bottom-right
-0.5f, 0.5f, 0.5f, 0.0f, 0.0f, // bottom-left
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f // top-left
};

opengl- vertex normal not taken in account

I was just getting into diffuse lighting, but the object always gives a black output,
The vertex and the fragment normals are defined as:
float vertices[] = {
-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f,
0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f,
0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f,
0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f,
-0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
-0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
-0.5f, 0.5f, 0.5f, -1.0f, 0.0f, 0.0f,
-0.5f, 0.5f, -0.5f, -1.0f, 0.0f, 0.0f,
-0.5f, -0.5f, -0.5f, -1.0f, 0.0f, 0.0f,
-0.5f, -0.5f, -0.5f, -1.0f, 0.0f, 0.0f,
-0.5f, -0.5f, 0.5f, -1.0f, 0.0f, 0.0f,
-0.5f, 0.5f, 0.5f, -1.0f, 0.0f, 0.0f,
0.5f, 0.5f, 0.5f, 1.0f, 0.0f, 0.0f,
0.5f, 0.5f, -0.5f, 1.0f, 0.0f, 0.0f,
0.5f, -0.5f, -0.5f, 1.0f, 0.0f, 0.0f,
0.5f, -0.5f, -0.5f, 1.0f, 0.0f, 0.0f,
0.5f, -0.5f, 0.5f, 1.0f, 0.0f, 0.0f,
0.5f, 0.5f, 0.5f, 1.0f, 0.0f, 0.0f,
-0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f,
0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f,
0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f,
0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f,
-0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f,
-0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f,
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f,
0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f,
0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f,
0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f,
-0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f,
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f
};
The relevant VAO is defined as:
unsigned int VAO, lightVAO, VBO;
glGenVertexArrays(1, &VAO);
glBindVertexArray(VAO);
glGenBuffers(1, &VBO);
glBindBuffer(GL_ARRAY_BUFFER, VBO);
glBufferData(GL_ARRAY_BUFFER,sizeof(vertices), vertices, GL_STATIC_DRAW);
glVertexAttribPointer(0,3, GL_FLOAT,GL_FALSE, 6*sizeof(float),(const void*)0);
glEnableVertexAttribArray(0);
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 6*sizeof(float), (const void*)3);
glEnableVertexAttribArray(1);
The relavant uniform are set as:
mShader.use();//activate the shader, already compiled
mShader.setMat4fv("model", model1);//model matrix
mShader.setMat4fv("view", view1);//view matrix
mShader.setMat4fv("projection", projection1);//projection matrix
mShader.setVec3f("lightPosition", 1.2f, 1.0f, 2.0f);//light source position
mShader.setVec3f("objectColor", 1.0f, 0.0f, 0.0f);//our object's base color
mShader.setVec3f("lightColor", 1.0f, 1.0f, 1.0f);//light source color
glBindVertexArray(VAO);
glDrawArrays(GL_TRIANGLES, 0, 36);
//glSwapBuffers is also performed, which I've double checked
The vertex shader for the object is this:
#version 330 core
layout (location = 0) in vec3 aPos;
layout (location = 1) in vec3 aNormal;
uniform mat4 model;
uniform mat4 view;
uniform mat4 projection;
out vec3 mPos;
out vec3 mNormal;
uniform vec3 lightPosition;
uniform vec3 lightColor;
uniform vec3 objectColor;
out vec3 FragColor;
void main(){
gl_Position = projection * view * model * vec4(aPos, 1.0f);
vec3 norm = normalize(aNormal);
vec3 Fragpos = vec3(model*vec4(aPos, 1.0f));
vec3 lightDir = normalize(lightPosition-Fragpos);
float diff = max(dot(norm, lightDir), 0.0f);
vec3 diffuse = diff*lightColor;
FragColor = diffuse;
}
The fragment shader is this:
#version 330
in vec3 FragColor;
out vec4 outFragColor;
void main(){
outFragColor = vec4(FragColor, 1.0f);
}
Yet the output is:
What could be the possible cause for this. The source code is almost exactly same to the one given in learnopenGL
The full code for reference is:
#include <GL/glew.h>
#include <GLFW/glfw3.h>
#include "Libs/glm/glm.hpp"
#include "Libs/glm/gtc/matrix_transform.hpp"
#include "Libs/glm/gtc/type_ptr.hpp"
#include <iostream>
#include "mLibs/camera.hpp"
#ifndef STB_IMAGE_IMPLEMENTATION
#define STB_IMAGE_IMPLEMENTATION //must define to use the library
#endif
#include "Libs/stb_image.h"
#ifdef WINDOWS
#include <direct.h>//for windows
#define getcwd _getcwd
#else
#include <unistd.h>//for unix
#endif
#include "mLibs/window.hpp"
#include "mLibs/shaderClass.hpp"
void mouse_callback(GLFWwindow* window, double xpos, double ypos);
void scroll_callback(GLFWwindow* window, double xOffset, double yOffset);
void framebuffer_size_callback(GLFWwindow* window, int width, int height);
void processInput(GLFWwindow *window);
Camera camera(glm::vec3(0.0f, 0.0f, 3.0f));
float deltaTime = 0.0f;
float lastFrame = 0.0f;
// settings
const unsigned int SCR_WIDTH = 800;
const unsigned int SCR_HEIGHT = 600;
bool firstMouse = true;
float lastX = SCR_WIDTH/2.0f;
float lastY = SCR_HEIGHT/2.0f;
std::string objVShader = "objVShader.vs";
std::string objFShader = "objFShader.fs";
std::string lightVShader = "lightVShader.vs";
std::string lightFShader = "lightFShader.fs";
void framebuffer_size_callback(GLFWwindow* window, int width, int height){
glViewport(0, 0, width, height);
}
int main(){
GLFWwindow* mainWindow = static_cast<GLFWwindow*>(window::getWindow());
if(glewInit() != GLEW_OK){
util::LogUtil::Log("GLEW: ", "GlewInitialization failed");
window::DestroyAndTerminate(mainWindow);
}
glfwSetFramebufferSizeCallback(mainWindow, framebuffer_size_callback);
glfwSetFramebufferSizeCallback(mainWindow, framebuffer_size_callback);
glfwSetCursorPosCallback(mainWindow, mouse_callback);
glfwSetScrollCallback(mainWindow, scroll_callback);
glEnable(GL_DEPTH_TEST);
float vertices[] = {
-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f,
0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f,
0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f,
0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f,
-0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
-0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f,
-0.5f, 0.5f, 0.5f, -1.0f, 0.0f, 0.0f,
-0.5f, 0.5f, -0.5f, -1.0f, 0.0f, 0.0f,
-0.5f, -0.5f, -0.5f, -1.0f, 0.0f, 0.0f,
-0.5f, -0.5f, -0.5f, -1.0f, 0.0f, 0.0f,
-0.5f, -0.5f, 0.5f, -1.0f, 0.0f, 0.0f,
-0.5f, 0.5f, 0.5f, -1.0f, 0.0f, 0.0f,
0.5f, 0.5f, 0.5f, 1.0f, 0.0f, 0.0f,
0.5f, 0.5f, -0.5f, 1.0f, 0.0f, 0.0f,
0.5f, -0.5f, -0.5f, 1.0f, 0.0f, 0.0f,
0.5f, -0.5f, -0.5f, 1.0f, 0.0f, 0.0f,
0.5f, -0.5f, 0.5f, 1.0f, 0.0f, 0.0f,
0.5f, 0.5f, 0.5f, 1.0f, 0.0f, 0.0f,
-0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f,
0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f,
0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f,
0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f,
-0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f,
-0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f,
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f,
0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f,
0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f,
0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f,
-0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f,
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f
};
unsigned int VAO, lightVAO, VBO;
glGenVertexArrays(1, &VAO);
glBindVertexArray(VAO);
glGenBuffers(1, &VBO);
glBindBuffer(GL_ARRAY_BUFFER, VBO);
glBufferData(GL_ARRAY_BUFFER,sizeof(vertices), vertices, GL_STATIC_DRAW);
glVertexAttribPointer(0,3, GL_FLOAT,GL_FALSE, 6*sizeof(float),(const void*)0);
glEnableVertexAttribArray(0);
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 6*sizeof(float), (const void*)3);
glEnableVertexAttribArray(1);
glGenVertexArrays(1, &lightVAO);
glBindVertexArray(lightVAO);
//select lightVAO and bind the same VBO to this VAO
glBindBuffer(GL_ARRAY_BUFFER, VBO);
glVertexAttribPointer(0,3, GL_FLOAT,GL_FALSE,6*sizeof(float),(const void*)0);
glEnableVertexAttribArray(0);
glm::mat4 model1 = glm::mat4(1.0f);
glm::mat4 view1 = glm::mat4(1.0f);
glm::mat4 projection1 = glm::mat4(1.0f);
glm::mat4 model2 = glm::mat4(1.0f);
glm::mat4 view2 = glm::mat4(1.0f);
glm::mat4 projection2 = glm::mat4(1.0f);
Shader mShader(objVShader.c_str(), objFShader.c_str());
Shader lightCubeShader(lightVShader.c_str(), lightFShader.c_str());
mShader.CompileShaders();
lightCubeShader.CompileShaders();
model2 = glm::translate(model2, glm::vec3(.3f, .4f, .5f));
projection1 = glm::perspective(camera.Zoom, static_cast<float>(SCR_WIDTH/SCR_HEIGHT), 0.1f, 100.0f);
float currentFrame;
while(!window::WindowShouldClose(mainWindow)){
glfwPollEvents();
currentFrame = glfwGetTime();
deltaTime = currentFrame - lastFrame;
lastFrame = currentFrame;
processInput(mainWindow);
view1 = camera.GetViewMatrix();
glClearColor(1, 0, 1, 1);
glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);
mShader.use();
mShader.setMat4fv("model", model1);
mShader.setMat4fv("view", view1);
mShader.setMat4fv("projection", projection1);
mShader.setVec3f("lightPosition", 1.2f, 1.0f, 2.0f);
mShader.setVec3f("objectColor", 1.0f, 0.0f, 0.0f);
mShader.setVec3f("lightColor", 1.0f, 1.0f, 1.0f);
glBindVertexArray(VAO);
glDrawArrays(GL_TRIANGLES,0, 36);
lightCubeShader.use();
model2 = glm::mat4(1.0f);
model2 = glm::translate(model2, glm::vec3(1, 1, 1));
model2 = glm::scale(model2, glm::vec3(0.5f, 0.5f, 0.5f));
lightCubeShader.setMat4fv("model", model2);
lightCubeShader.setMat4fv("view", view1);
lightCubeShader.setMat4fv("projection", projection1);
glBindVertexArray(lightVAO);
glDrawArrays(GL_TRIANGLES,0, 36);
glfwSwapBuffers(mainWindow);
}
glDeleteVertexArrays(1,&VAO);
glDeleteVertexArrays(1,&lightVAO);
glDeleteBuffers(1, &VBO);
return 0;
}
void mouse_callback(GLFWwindow* window, double xpos, double ypos){
if(firstMouse){
lastX = xpos;
lastY = ypos;
firstMouse = false;
}
float xOffset = xpos-lastX;
float yOffset = lastY - ypos;
lastX = xpos;
lastY = ypos;
camera.ProcessMouseMovement(xOffset, yOffset);
}
void scroll_callback(GLFWwindow* window, double xOffset, double yOffset){
camera.ProcessMouseScroll(yOffset);
}
void processInput(GLFWwindow *window)
{
if (glfwGetKey(window, GLFW_KEY_ESCAPE) == GLFW_PRESS)
glfwSetWindowShouldClose(window, true);
if(glfwGetKey(window, GLFW_KEY_W)==GLFW_PRESS)
camera.ProcessKeyboard(FORWARD, deltaTime);
if(glfwGetKey(window, GLFW_KEY_S)==GLFW_PRESS)
camera.ProcessKeyboard(BACKWARD, deltaTime);
if(glfwGetKey(window, GLFW_KEY_A)==GLFW_PRESS)
camera.ProcessKeyboard(LEFT, deltaTime);
if(glfwGetKey(window, GLFW_KEY_D)==GLFW_PRESS)
camera.ProcessKeyboard(RIGHT, deltaTime);
if(glfwGetKey(window, GLFW_KEY_Q)==GLFW_PRESS)
camera.ProcessKeyboard(UP, deltaTime);
if(glfwGetKey(window, GLFW_KEY_E)==GLFW_PRESS)
camera.ProcessKeyboard(DOWN, deltaTime);
}
If a named buffer object is bound, then the last parameter of glVertexAttribPointer is treated as a byte offset into the buffer object's data store. The offset of the normal vector attribute are 3*4 bytes, thus (const void*)3 has to be (const void*)(3*sizeof(float)):
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 6*sizeof(float), (const void*)3);
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 6*sizeof(float),
(const void*)(3*sizeof(float));

Skybox texture does not show with OpenGL?

So I am having this assignment which requires to create a skybox; the texture is provided as a single file. Bear in mind, I am very slow when it comes to understanding OpenGL, and this particular SkyBox has been driving me insane. I read up on every little thing on the internet that I thought could relate to my issue, but I either can't comprehend what is going on, which is not what I am after since I want to know what I am doing and not copy/paste some code, or the result ends up being something different.
The code relating to the skybox so far:
GLfloat cubeVertexData[108] =
{
0.5f, -0.5f, -0.5f,
0.5f, 0.5f, -0.5f,
0.5f, -0.5f, 0.5f,
0.5f, -0.5f, 0.5f,
0.5f, 0.5f, -0.5f,
0.5f, 0.5f, 0.5f,
0.5f, 0.5f, -0.5f,
-0.5f, 0.5f, -0.5f,
0.5f, 0.5f, 0.5f,
0.5f, 0.5f, 0.5f,
-0.5f, 0.5f, -0.5f,
-0.5f, 0.5f, 0.5f,
-0.5f, 0.5f, -0.5f,
-0.5f, -0.5f, -0.5f,
-0.5f, 0.5f, 0.5f,
-0.5f, 0.5f, 0.5f,
-0.5f, -0.5f, -0.5f,
-0.5f, -0.5f, 0.5f,
//4
-0.5f, -0.5f, -0.5f,
0.5f, -0.5f, -0.5f,
-0.5f, -0.5f, 0.5f,
-0.5f, -0.5f, 0.5f,
0.5f, -0.5f, -0.5f,
0.5f, -0.5f, 0.5f,
//5
0.5f, 0.5f, 0.5f,
-0.5f, 0.5f, 0.5f,
0.5f, -0.5f, 0.5f,
0.5f, -0.5f, 0.5f,
-0.5f, 0.5f, 0.5f,
-0.5f, -0.5f, 0.5f,
//6
0.5f, -0.5f, -0.5f,
-0.5f, -0.5f, -0.5f,
0.5f, 0.5f, -0.5f,
0.5f, 0.5f, -0.5f,
-0.5f, -0.5f, -0.5f,
-0.5f, 0.5f, -0.5f
};
GLfloat textureCoordsSkyBox[72] = {
//face 1
0.75,0.33, // 0,1,
0.75,0.67, // 1,1,
0.5,0.33, // 0,0,
0.5,0.33, // 0,0,
0.75,0.67, // 1,0,
0.5,0.67, // 1,1,
//face 2
0.5,1.0, // 1,1,
0.25,1, // 0,1,
0.5,0.67, // 1,0,
0.5,0.67, // 1,0,
0.25,1.0, // 0,1,
0.25,0.67, // 1,1,
//face 3
0,0.67,// 1,1,
0,0.33,// 0,1,
0.25,0.67,// 1,0,
0.25,0.67,// 1,0,
0,0.33,// 0,1,
0.25,0.33,// 0,0,
//face 4
0.25,0.0,// 0,1,
0.5,0.0,// 1,1,
0.25,0.33,// 0,0,
0.25,0.33,// 0,0,
0.5,0.0,// 1,1,
0.5,0.33,// 0,0,
//face 5
0.5,0.67,// 1,0,
0.25,0.67,// 0,0,
0.5,0.33,// 1,1,
0.5,0.33,// 1,1,
0.25,0.67,// 0,0,
0.25,0.33,// 0,1,
//face 6
0.75,0.33,// 1,1,
1.0,0.33,// 0,1,
0.75,0.67,// 1,0,
0.75,0.67,// 1,0,
1.0,0.33,// 0,1,
1.0,0.67// 0,0
};
GLfloat gCubeVertexdataNormals[108] =
{
1.0f, 0.0f, 0.0f,
1.0f, 0.0f, 0.0f,
1.0f, 0.0f, 0.0f,
1.0f, 0.0f, 0.0f,
1.0f, 0.0f, 0.0f,
1.0f, 0.0f, 0.0f,
0.0f, 1.0f, 0.0f,
0.0f, 1.0f, 0.0f,
0.0f, 1.0f, 0.0f,
0.0f, 1.0f, 0.0f,
0.0f, 1.0f, 0.0f,
0.0f, 1.0f, 0.0f,
-1.0f, 0.0f, 0.0f,
-1.0f, 0.0f, 0.0f,
-1.0f, 0.0f, 0.0f,
-1.0f, 0.0f, 0.0f,
-1.0f, 0.0f, 0.0f,
-1.0f, 0.0f, 0.0f,
0.0f, -1.0f, 0.0f,
0.0f, -1.0f, 0.0f,
0.0f, -1.0f, 0.0f,
0.0f, -1.0f, 0.0f,
0.0f, -1.0f, 0.0f,
0.0f, -1.0f, 0.0f,
0.0f, 0.0f, 1.0f,
0.0f, 0.0f, 1.0f,
0.0f, 0.0f, 1.0f,
0.0f, 0.0f, 1.0f,
0.0f, 0.0f, 1.0f,
0.0f, 0.0f, 1.0f,
0.0f, 0.0f, -1.0f,
0.0f, 0.0f, -1.0f,
0.0f, 0.0f, -1.0f,
0.0f, 0.0f, -1.0f,
0.0f, 0.0f, -1.0f,
0.0f, 0.0f, -1.0f
};
void DrawSkyBox() {
glFrontFace(GL_CW);
glBindTexture(GL_TEXTURE_2D, textures[SKYIMAGE]);
glEnableClientState(GL_VERTEX_ARRAY);
glEnableClientState(GL_NORMAL_ARRAY);
glNormalPointer(GL_FLOAT, 0, gCubeVertexdataNormals);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glVertexPointer(3, GL_FLOAT, 0, cubeVertexData);
glTexCoordPointer(2, GL_FLOAT, 0, textureCoordsSkyBox);
glDrawArrays(GL_TRIANGLES, 0, 36);
glDisableClientState(GL_VERTEX_ARRAY);
glDisableClientState(GL_NORMAL_ARRAY);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);
}
Loading texture [part of code missing as I have different textures for other elements loaded here]:
.....
#define SKYIMAGE 5 //sky image
const char *textureFiles[TEXTURE_COUNT] = { "stormydays.tga".... };
I am not sure if it is of importance, but I will also mention that the other textured elements of the scene do not have coordinates from 0-1, but from 100 to 1000. I tried previously to set up the textureCoordsSkyBox to 1000 in terms of coordinates, but still no result.
I imagine I do something completely wrong when it comes to the binding of the texture, but I am having a hard time comprehending how I can improve that part. Any advice would be deeply appreciated. Thank you in advance.
-Edit-
So this is the texture I am using:
What I am seeing is just black, besides the other elements of the scene like the back wall, some grass and some flowers [this is what I was referring to when I said textured elements of the scene]. I am attaching the code here of what part of my drawing the scene function looks like:
void RenderScene(void)
{
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glLoadIdentity();
glMatrixMode(GL_MODELVIEW);
gluLookAt(cameraX, cameraY, cameraZ,//eye
50.00, 90.00, 50.00,//centre
0.00, 1000.00, 0.00);//up
glPushMatrix();
DrawSkyBox();
glPopMatrix();
glPushMatrix();
glTranslatef(0.0, 0.0, -100.0);
glRotatef(-90.0, 1.0, 0.0, 0.0);
drawTexturedSurface(IMAGE1); //grass
glPopMatrix();
glPushMatrix();
glTranslatef(0.0, 0.0, -350.0);
drawTexturedSurface(IMAGE4); //front stone wall
glPopMatrix();
glPushMatrix();
.......
glPopMatrix();
drawGUI();
glPushMatrix();
glutSwapBuffers();
}
Also, it is the fixed version of OpenGL. I tried messing about with GL_LIGHTING, GL_CULL_FACE, GL_DEPTH_TEST and glDisableClientState but it is the same result. Also, I don't get any errors.
In your case the skybox is a very tiny object in the center of the world.
You have to draw the skybox in at the position of the camera. When you darw the sykbox, then you have to disable the depth test, this cause that the depth buffer is not written and all other parts of the scene cover the skybox.
Further two-dimensional texturing has to be enabled by glEnable(GL_TEXTURE_2D), before the skybox geometry is drawn:
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glLoadIdentity();
glMatrixMode(GL_MODELVIEW);
gluLookAt(
cameraX, cameraY, cameraZ,//eye
50.00, 90.00, 50.00,//centre
0.00, 1000.00, 0.00);//up
glDisable(GL_DEPTH_TEST);
glPushMatrix();
glTranslatef(cameraX, cameraY, cameraZ); // model transformation to the camera position
glEnable(GL_TEXTURE_2D);
DrawSkyBox();
glPopMatrix();
glEnable(GL_DEPTH_TEST);

VAO gets deleted without calling glDeleteVertexArrays()

I have just started to learn OpenGL and I am currently trying to apply the OpenGL knowledge I have acquired in a small game architecture, but I am having a hard time making this work with Classes. I am trying to display a triangle on the screen using a separate class like this:
CubeModel.h
#pragma once
#include <vector>
#include <glad\glad.h>
class CubeModel
{
public:
//x y and z are dimensions of the cube
CubeModel();
CubeModel( float x, float y, float z);
~CubeModel();
void Bind();
void Unbind();
private:
unsigned int m_VAO, m_VBO;
std::vector<float> m_vertices = {
-0.5f, -0.5f, 0.0f,
0.5f, -0.5f, 0.0f,
0.0f, 0.5f, 0.0f
};
std::vector<float> m_vertices2 = {
-0.5f, -0.5f, -0.5f, 0.0f, 0.0f,
0.5f, -0.5f, -0.5f, 1.0f, 0.0f,
0.5f, 0.5f, -0.5f, 1.0f, 1.0f,
0.5f, 0.5f, -0.5f, 1.0f, 1.0f,
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 0.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f,
0.5f, -0.5f, 0.5f, 1.0f, 0.0f,
0.5f, 0.5f, 0.5f, 1.0f, 1.0f,
0.5f, 0.5f, 0.5f, 1.0f, 1.0f,
-0.5f, 0.5f, 0.5f, 0.0f, 1.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f,
-0.5f, 0.5f, 0.5f, 1.0f, 0.0f,
-0.5f, 0.5f, -0.5f, 1.0f, 1.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f,
-0.5f, 0.5f, 0.5f, 1.0f, 0.0f,
0.5f, 0.5f, 0.5f, 1.0f, 0.0f,
0.5f, 0.5f, -0.5f, 1.0f, 1.0f,
0.5f, -0.5f, -0.5f, 0.0f, 1.0f,
0.5f, -0.5f, -0.5f, 0.0f, 1.0f,
0.5f, -0.5f, 0.5f, 0.0f, 0.0f,
0.5f, 0.5f, 0.5f, 1.0f, 0.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f,
0.5f, -0.5f, -0.5f, 1.0f, 1.0f,
0.5f, -0.5f, 0.5f, 1.0f, 0.0f,
0.5f, -0.5f, 0.5f, 1.0f, 0.0f,
-0.5f, -0.5f, 0.5f, 0.0f, 0.0f,
-0.5f, -0.5f, -0.5f, 0.0f, 1.0f,
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f,
0.5f, 0.5f, -0.5f, 1.0f, 1.0f,
0.5f, 0.5f, 0.5f, 1.0f, 0.0f,
0.5f, 0.5f, 0.5f, 1.0f, 0.0f,
-0.5f, 0.5f, 0.5f, 0.0f, 0.0f,
-0.5f, 0.5f, -0.5f, 0.0f, 1.0f
};
};
CubeModel.cpp
#include "CubeModel.h"
CubeModel::CubeModel()
{
CubeModel(1.0f, 1.0f, 1.0f);
}
CubeModel::CubeModel(float x, float y, float z)
{
unsigned int VAO, VBO;
glGenVertexArrays(1, &VAO);
glGenBuffers(1, &VBO);
glBindVertexArray(VAO);
glBindBuffer(GL_ARRAY_BUFFER, VBO);
glBufferData(GL_ARRAY_BUFFER, sizeof(m_vertices[0]) * m_vertices.size(),
m_vertices.data(), GL_STATIC_DRAW);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
glEnableVertexAttribArray(0);
glBindVertexArray(0);
m_VAO = VAO;
m_VBO = VBO;
}
CubeModel::~CubeModel()
{
glDeleteVertexArrays(1, &m_VAO);
glDeleteBuffers(1, &m_VBO);
}
void CubeModel::Bind()
{
glBindVertexArray(m_VAO);
}
void CubeModel::Unbind()
{
glBindVertexArray(0);
}
Game_State.h (where CubeModel is used):
#pragma once
#include "Window.h"
#include "Shader.h"
#include "CubeModel.h"
#define TIMESTEP 1.0f/100.0f
class Game_State
{
public:
Game_State();
~Game_State();
int Run();
bool IsDone();
private:
void HandleInput();
void Update(double deltatime);
void Render();
Window m_window;
double m_elapsedTime = 0;
Shader m_cubeShader;
CubeModel m_testCube;
};
Game_State.cpp:
#include "Game_State.h"
Game_State::Game_State()
: m_window("Title to be determined...", glm::vec2(1920, 1080))
, m_cubeShader("cubeshader.vs","cubeshader.fs")
{
}
Game_State::~Game_State()
{
}
int Game_State::Run()
{
while (m_elapsedTime > TIMESTEP)
{
m_elapsedTime -= TIMESTEP;
HandleInput();
Update(m_elapsedTime);
}
Render();
m_elapsedTime += glfwGetTime();
glfwSetTime(0.0f);
return 0;
}
void Game_State::Update(double deltatime)
{
m_window.Update();
}
void Game_State::Render()
{
m_window.BeginDraw(0.7f, 0.5f, 0.3f, 1.0f);
m_cubeShader.use();
m_testCube.Bind();
glDrawArrays(GL_TRIANGLES, 0, 6);
m_testCube.Unbind();
m_window.EndDraw();
}
void Game_State::HandleInput()
{
if (glfwGetKey(m_window.GetWindow(), GLFW_KEY_F11) == GLFW_PRESS)
{
m_window.ToggleFullscreen();
}
if (glfwGetKey(m_window.GetWindow(), GLFW_KEY_ESCAPE) == GLFW_PRESS)
{
m_window.CloseWindow();
}
}
bool Game_State::IsDone() { return m_window.IsDone(); }
When i tried to debug the code, everything was working and the VAO and VBO both got an ID but by the time i call the bind function before drawing it to the screen in a separate render function it binds the array with ID 0. Both the m_VAO and m_VBO gets reset to 0 by the time bind() is called, what is the reason for this?!?! I've tried using this exact code directly in the render function and it works so the render is fine it seems. (I'm using GLFW and GLAD)
Thanks in advance! :)
This:
CubeModel::CubeModel()
{
CubeModel(1.0f, 1.0f, 1.0f);
}
is wrong. That creates a CubeModel temporary within the constructor. That's not the same thing as delegating the constructor. If that's what you wanted, you have to use the proper C++11 syntax:
CubeModel::CubeModel() : CubeModel(1.0f, 1.0f, 1.0f)
{}
Note that this may not be your only problem, since you neglected to post all of your code.
For example, CubeModel is technically copyable, but it shouldn't be. You make no special allowances for copying (which by its nature, would have to create a new VAO and buffer, and copy the data from the other VAO/buffer). So you need to delete the copy operations, and write appropriate move operations:
CubeModel(const CubeModel &) = delete;
CubeModel(CubeModel &&other) : m_VAO(other.m_VAO), m_VBO(other.m_VBO)
{
other.m_VAO = 0;
other.m_VBO = 0;
}
And do something similar for the move assignment operation. Or just leave it as being unassignable.
In C++, you can't call a constructor from inside another constructor as you do here:
CubeModel::CubeModel()
{
CubeModel(1.0f, 1.0f, 1.0f);
}
What is actually happening here is that you create a temporary, unnamed CubeModel which get's deleted when the default constructor is left. That's when your VAO gets deleted.
If you don't want to duplicate the code in both function, you need to write a new method and call that one from both constructors.