// нарисовать множество полигонов с указанным материалом / VBO void OpenGL_Engine::DrawTriangles_OpenGL15(GraphShadow& e, const Faces& faces, const TexCoords* coords) { if (e.vertexes && !(faces.triangles.empty() && faces.quads.empty()) && !e.vertexes->empty())// если есть полигоны и вершины { glPushAttrib(GL_ALL_ATTRIB_BITS); glPushClientAttrib(GL_CLIENT_VERTEX_ARRAY_BIT); total.vertexCount += e.vertexes->size(); total.faceCount += faces.triangles.size(); // if(coords) { glTexCoordPointer(2, GL_FLOAT, 0, &coords->data.front()); glEnableClientState(GL_TEXTURE_COORD_ARRAY); } if (BindVBO(e.vertexes, GL_VERTEX_ARRAY, GL_ARRAY_BUFFER_ARB, 3)) { glVertexPointer(3, GL_FLOAT, 0, 0); } if (BindVBO(e.normals, GL_NORMAL_ARRAY, GL_ARRAY_BUFFER_ARB, 3)) { glNormalPointer(GL_FLOAT, 0, 0); } //Draw All if (!faces.triangles.empty()) { total.batchCount++; if (BindVBO(&faces.triangles, 0, GL_ELEMENT_ARRAY_BUFFER_ARB, 3)) { glDrawElements(GL_TRIANGLES, faces.triangles.size()*3, GL_UNSIGNED_INT, 0); } else { glDrawElements(GL_TRIANGLES, faces.triangles.size()*3/*a,b,c*/, GL_UNSIGNED_INT, &faces.triangles.front().a[0]); } } if (!faces.quads.empty()) { total.batchCount++; if (BindVBO(&faces.quads, 0, GL_ELEMENT_ARRAY_BUFFER_ARB, 4)) { glDrawElements(GL_QUADS, faces.quads.size()*4, GL_UNSIGNED_INT, 0); } else { glDrawElements(GL_QUADS, faces.quads.size()*4, GL_UNSIGNED_INT, &faces.quads.front().a[0]); } } glPopClientAttrib(); glPopAttrib(); } }
void OpenGL_Engine::BindTexCoords3f_OpenGL15(const TexCoords3f* coords) { if(coords != NULL) { if (BindVBO(coords, GL_TEXTURE_COORD_ARRAY, GL_ARRAY_BUFFER_ARB, 3)) { glTexCoordPointer(3, GL_FLOAT, 0,0); } } }
void UMesh::Initialize() { ComputeBoundSphere(); InitializeBuffers(); auto renderer = URenderer::GetInstance(); renderer->BindVBO(&vb); renderer->BindVBO(&ib); InitializeMaterial(URenderPass::Normal); InitializeMaterial(URenderPass::Depth); InitializeMaterial(URenderPass::Forward); InitializeMaterial(URenderPass::Deffered); OPENGL_CHECK_FOR_ERRORS(); }
GModelSphere::GModelSphere(const int rows, const int cols, const float rad) { VertexAttribute.clear(); Index.clear(); for (int i = 0; i < rows + 1; i++){ float r = (float)M_PI / (float)rows * i; float ry = cos(r); float rr = sin(r); for (int j = 0; j < cols + 1; j++){ float tr = (float)M_PI * 2 / (float)cols * j; float tx = rr * rad * cos(tr); float ty = ry * rad; float tz = rr * rad * sin(tr); float rx = rr * cos(tr); float rz = rr * sin(tr); GVertexAttribute vertexAttr; vertexAttr.position = vec3(tx, ty, tz); vertexAttr.normal = vec3(rx, ry, rz); // vertexAttr.color = vec4(1.0, 0.0, 1.0, 1.0); vec3 hsv(360.0f / (float)rows * i, 1.0, 1.0); vertexAttr.color = vec4(hsv2rgb(hsv), 1.0); VertexAttribute.push_back(vertexAttr); } for (int i = 0; i < rows; i++){ for (int j = 0; j < cols; j++){ int r = (cols + 1) * i + j; Index.push_back(u16vec3(r, r + 1, r + cols + 2)); Index.push_back(u16vec3(r, r + cols + 2, r + cols + 1)); } } } CreateVBO(); CreateIBO(); BindVBO(); BindIBO(); }
void OpenGL_Engine::BindTexCoords_OpenGL15(const TexCoords* coords, const TextureMatrix* textureMatrix) { if (coords != NULL) { if (BindVBO(coords, GL_TEXTURE_COORD_ARRAY, GL_ARRAY_BUFFER_ARB, 2)) { glTexCoordPointer(2, GL_FLOAT, 0,0); if (textureMatrix != NULL && textureMatrixLevel == 0) { glMatrixMode(GL_TEXTURE); //glPushMatrix(); // OpenGL error (on modelview matrix pop, pop texture matrix too) textureMatrixLevel++; glLoadIdentity(); glScalef( textureMatrix->texCoordsScale.x, textureMatrix->texCoordsScale.y, textureMatrix->texCoordsScale.z); glTranslatef( textureMatrix->texCoordsTranslation.x, textureMatrix->texCoordsTranslation.y, textureMatrix->texCoordsTranslation.z); glRotatef( textureMatrix->texCoordsRotation/(float)(M_PI)*180.0f, 0.0f, 0.0f, 1.0f); glMatrixMode(GL_MODELVIEW); } } } }
bool OGLIndexedDraw::Init(int windowWidth, int windowHeight) { bool res = gs::Stage::Init(windowWidth, windowHeight); if (res) { res &= InitGUI(); /******************************* Shaders ********************************/ auto vertexShader = std::make_unique<gs::Shader>(GL_VERTEX_SHADER); auto fragmentShader = std::make_unique<gs::Shader>(GL_FRAGMENT_SHADER); auto program = std::make_shared<gs::Program>(); vertexShader->SetSource("heightmap.vert"); res &= vertexShader->Compile(); fragmentShader->SetSource("heightmap.frag"); res &= fragmentShader->Compile(); program->Attach(vertexShader->get()); program->Attach(fragmentShader->get()); res &= program->Link(); program->Use(); programs.push_back(program); glm::mat4 MVP = projection * glm::lookAt(glm::vec3(0, 40, -30), glm::vec3(0), glm::vec3(0, 1, 0)); GLint mvpLocation = glGetUniformLocation(program->get(), "MVP"); glUniformMatrix4fv(mvpLocation, 1, GL_FALSE, glm::value_ptr(MVP)); hDivLocation = glGetUniformLocation(program->get(), "heightDivider"); /******************************* Geometry ********************************/ auto vao = std::make_unique<gs::VertexArray>(); vao->BindVAO(); vaos.push_back(std::move(vao)); auto vbo = std::make_unique<gs::VertexBuffer>(GL_ARRAY_BUFFER); vbo->BindVBO(); vbos.push_back(std::move(vbo)); heights = { 4.0f, 2.0f, 3.0f, 1.0f, 3.0f, 5.0f, 8.0f, 2.0f, 7.0f, 10.0f, 12.0f, 6.0f, 4.0f, 6.0f, 8.0f, 3.0f }; const float halfX = WORLD_SIZE_X * 0.5f; const float halfZ = WORLD_SIZE_Z * 0.5f; for (size_t i = 0; i < HM_SIZE_Z; i++) { for (size_t j = 0; j < HM_SIZE_X; j++) { short currentLineOffset = (short)j * HM_SIZE_Z; float xPos = j / (float)(HM_SIZE_X - 1) * WORLD_SIZE_X - halfX; float yPos = heights[i + currentLineOffset]; float zPos = i / (float)(HM_SIZE_Z - 1) * WORLD_SIZE_Z - halfZ; vertices[i + currentLineOffset] = glm::vec3(xPos, yPos, zPos); } } glBufferData(GL_ARRAY_BUFFER, sizeof(glm::vec3) * vertices.size(), vertices.data(), GL_STATIC_DRAW); /******************************* Indices ********************************/ auto ibo = std::make_unique<gs::VertexBuffer>(GL_ELEMENT_ARRAY_BUFFER); ibo->BindVBO(); vbos.push_back(std::move(ibo)); const GLushort restartIndex = HM_SIZE_X * HM_SIZE_Z; indices = { 0, 4, 1, 5, 2, 6, 3, 7, restartIndex, 4, 8, 5, 9, 6, 10, 7, 11, restartIndex, 8, 12, 9, 13, 10, 14, 11, 15}; glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(GLushort) * indices.size(), indices.data(), GL_STATIC_DRAW); glEnableVertexAttribArray(0); glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, nullptr); glEnable(GL_PRIMITIVE_RESTART); glEnable(GL_DEPTH_TEST); glPrimitiveRestartIndex(restartIndex); } return res; }
GModelCube::GModelCube(const float side){ const float hs = side*0.5f; VertexAttribute.resize(4 * 6); int i = 0; VertexAttribute[i++].position = vec3(-hs, -hs, hs); VertexAttribute[i++].position = vec3(hs, -hs, hs); VertexAttribute[i++].position = vec3(hs, hs, hs); VertexAttribute[i++].position = vec3(-hs, hs, hs); VertexAttribute[i++].position = vec3(-hs, -hs, -hs); VertexAttribute[i++].position = vec3(-hs, hs, -hs); VertexAttribute[i++].position = vec3(hs, hs, -hs); VertexAttribute[i++].position = vec3(hs, -hs, -hs); VertexAttribute[i++].position = vec3(-hs, hs, -hs); VertexAttribute[i++].position = vec3(-hs, hs, hs); VertexAttribute[i++].position = vec3(hs, hs, hs); VertexAttribute[i++].position = vec3(hs, hs, -hs); VertexAttribute[i++].position = vec3(-hs, -hs, -hs); VertexAttribute[i++].position = vec3(hs, -hs, -hs); VertexAttribute[i++].position = vec3(hs, -hs, hs); VertexAttribute[i++].position = vec3(-hs, -hs, hs); VertexAttribute[i++].position = vec3(hs, -hs, -hs); VertexAttribute[i++].position = vec3(hs, hs, -hs); VertexAttribute[i++].position = vec3(hs, hs, hs); VertexAttribute[i++].position = vec3(hs, -hs, hs); VertexAttribute[i++].position = vec3(-hs, -hs, -hs); VertexAttribute[i++].position = vec3(-hs, -hs, hs); VertexAttribute[i++].position = vec3(-hs, hs, hs); VertexAttribute[i++].position = vec3(-hs, hs, -hs); i = 0; VertexAttribute[i++].normal = vec3(-1.0, -1.0, 1.0); VertexAttribute[i++].normal = vec3(1.0, -1.0, 1.0); VertexAttribute[i++].normal = vec3(1.0, 1.0, 1.0); VertexAttribute[i++].normal = vec3(-1.0, 1.0, 1.0); VertexAttribute[i++].normal = vec3(-1.0, -1.0, -1.0); VertexAttribute[i++].normal = vec3(-1.0, 1.0, -1.0); VertexAttribute[i++].normal = vec3(1.0, 1.0, -1.0); VertexAttribute[i++].normal = vec3(1.0, -1.0, -1.0); VertexAttribute[i++].normal = vec3(-1.0, 1.0, -1.0); VertexAttribute[i++].normal = vec3(-1.0, 1.0, 1.0); VertexAttribute[i++].normal = vec3(1.0, 1.0, 1.0); VertexAttribute[i++].normal = vec3(1.0, 1.0, -1.0); VertexAttribute[i++].normal = vec3(-1.0, -1.0, -1.0); VertexAttribute[i++].normal = vec3(1.0, -1.0, -1.0); VertexAttribute[i++].normal = vec3(1.0, -1.0, 1.0); VertexAttribute[i++].normal = vec3(-1.0, -1.0, 1.0); VertexAttribute[i++].normal = vec3(1.0, -1.0, -1.0); VertexAttribute[i++].normal = vec3(1.0, 1.0, -1.0); VertexAttribute[i++].normal = vec3(1.0, 1.0, 1.0); VertexAttribute[i++].normal = vec3(1.0, -1.0, 1.0); VertexAttribute[i++].normal = vec3(-1.0, -1.0, -1.0); VertexAttribute[i++].normal = vec3(-1.0, -1.0, 1.0); VertexAttribute[i++].normal = vec3(-1.0, 1.0, 1.0); VertexAttribute[i++].normal = vec3(-1.0, 1.0, -1.0); for (int i = 0; i < VertexAttribute.size(); i++){ vec3 hsv(360.0f / (float)i, 1.0, 1.0); VertexAttribute[i].color = vec4(hsv2rgb(hsv), 1.0); } Index.resize(2 * 6); i = 0; Index[i++] = u16vec3(0, 1, 2); Index[i++] = u16vec3(0, 2, 3); Index[i++] = u16vec3(4, 5, 6); Index[i++] = u16vec3(4, 6, 7); Index[i++] = u16vec3(8, 9, 10); Index[i++] = u16vec3(8, 10, 11); Index[i++] = u16vec3(12, 13, 14); Index[i++] = u16vec3(12, 14, 15); Index[i++] = u16vec3(16, 17, 18); Index[i++] = u16vec3(16, 18, 19); Index[i++] = u16vec3(20, 21, 22); Index[i++] = u16vec3(20, 22, 23); CreateVBO(); CreateIBO(); BindVBO(); BindIBO(); }
bool OGLSpotLight::Init(int windowWidth, int windowHeight) { bool res = gs::Stage::Init(windowWidth, windowHeight); if (!res) { return false; } cubePositions.resize(10); res &= InitGUI(); // Init Camera camera.SetPosition(glm::vec3(0, 0, 50)); camera.SetSpeed(15.0f); camera.SetupProjection(45.0f, windowWidth / (float)windowHeight); // Init light InitLight(); // Init materials InitCubePosition(); // Init program res &= AddProgram("mesh.vert", "spotLight.frag"); auto program = programs[0]; // Get uniform locations res &= AddLightUniform(program.get()); res &= AddMatricesUniform(program.get()); res &= program->AddUniform("material.shininess"); res &= program->AddUniform("samplerDiffuse1"); program->AddUniform("samplerDiffuse2"); program->AddUniform("samplerDiffuse3"); program->AddUniform("samplerSpecular1"); program->AddUniform("samplerSpecular2"); glUniform1i(program->GetUniform("samplerDiffuse1"), 0); glUniform1i(program->GetUniform("samplerDiffuse2"), 1); glUniform1i(program->GetUniform("samplerDiffuse3"), 2); glUniform1i(program->GetUniform("samplerSpecular1"), 3); glUniform1i(program->GetUniform("samplerSpecular2"), 4); // Init geometry auto vao = std::make_unique<gs::VertexArray>(); vao->BindVAO(); auto vbo = std::make_unique<gs::VertexBuffer>(GL_ARRAY_BUFFER); vbo->BindVBO(); OGLCube cube; auto& vertices = cube.GetVertices(); cube.InitVertices(glm::vec3(0)); glBufferData(vbo->GetTarget(), sizeof(gs::Vertex) * vertices.size(), vertices.data(), GL_STATIC_DRAW); vbos.push_back(std::move(vbo)); vao->AddAttribute(0, 3, GL_FLOAT, GL_FALSE, sizeof(gs::Vertex), 0); vao->AddAttribute(1, 2, GL_FLOAT, GL_FALSE, sizeof(gs::Vertex), (void*)offsetof(gs::Vertex, texCoords)); vao->AddAttribute(2, 3, GL_FLOAT, GL_FALSE, sizeof(gs::Vertex), (void*)offsetof(gs::Vertex, normal)); vaos.push_back(std::move(vao)); auto diffuse = std::make_unique<gs::Texture>(IMAGE_TYPE::GLI); diffuse->SetContribution(LIGHT_CONTRIBUTION::DIFFUSE); res &= diffuse->LoadTexture("containerDiffuse.dds"); diffuse->BindTexture(GL_TEXTURE0); textures.push_back(std::move(diffuse)); auto specular = std::make_unique<gs::Texture>(IMAGE_TYPE::GLI); specular->SetContribution(LIGHT_CONTRIBUTION::DIFFUSE); res &= specular->LoadTexture("containerSpecular.dds"); specular->BindTexture(GL_TEXTURE3); textures.push_back(std::move(specular)); glEnable(GL_DEPTH_TEST); res = true; return res; }
bool OGLSimpleLighting::Init(int windowWidth, int windowHeight) { bool res = gs::Stage::Init(windowWidth, windowHeight); if (res) { res &= InitGUI(); // Program textured objects setup auto vertexShader = std::make_unique<gs::Shader>(GL_VERTEX_SHADER); auto programTex = std::make_shared<gs::Program>(); vertexShader->SetSource("simpleLighting.vert"); res &= vertexShader->Compile(); programTex->Attach(vertexShader->get()); auto fragmentShader = std::make_unique<gs::Shader>(GL_FRAGMENT_SHADER); fragmentShader->SetSource("simpleLighting.frag"); res &= fragmentShader->Compile(); programTex->Attach(fragmentShader->get()); res &= programTex->Link(); programTex->Use(); programs.push_back(programTex); mvpLocation = glGetUniformLocation(programTex->get(), "MVP"); normalMatrixLocation = glGetUniformLocation(programTex->get(), "NormalMatrix"); light.direction = glm::vec3(-1.0f, 0.0f, 0.0f); light.ambientColor = glm::vec3(0.2f); light.diffuseColor = glm::vec3(1.0f); light.specularColor = light.diffuseColor; lightDirLoc = glGetUniformLocation(programTex->get(), "light.direction"); diffuseLoc = glGetUniformLocation(programTex->get(), "light.diffuseColor"); ambientLoc = glGetUniformLocation(programTex->get(), "light.ambientColor"); //Texture setup auto textureFloor = std::make_unique<gs::Texture>(IMAGE_TYPE::GLI); res &= textureFloor->LoadTexture("Floor.dds"); textureFloor->ChangeParameter(GL_TEXTURE_MIN_FILTER, GL_NEAREST_MIPMAP_LINEAR); textureFloor->ChangeParameter(GL_TEXTURE_MAG_FILTER, GL_LINEAR); textures.push_back(std::move(textureFloor)); auto textureCamouflage = std::make_unique<gs::Texture>(IMAGE_TYPE::GLI); res &= textureCamouflage->LoadTexture("Hieroglyphes.dds"); textures.push_back(std::move(textureCamouflage)); // Geometry setup auto vao = std::make_unique<gs::VertexArray>(); vao->BindVAO(); vaos.push_back(std::move(vao)); auto vbo = std::make_unique<gs::VertexBuffer>(GL_ARRAY_BUFFER); vbo->BindVBO(); std::vector<gs::Vertex> vertices; OGLCube cube; cube.InitVertices(glm::vec3(0)); vertices.insert(vertices.end(), cube.GetVertices().begin(), cube.GetVertices().end()); OGLQuad quad; quad.SetSize(1000); quad.InitVertices(glm::vec3(0)); vertices.insert(vertices.end(), quad.GetVertices().begin(), quad.GetVertices().end()); glBufferData(GL_ARRAY_BUFFER, sizeof(gs::Vertex) * vertices.size(), vertices.data(), GL_STATIC_DRAW); vbos.push_back(std::move(vbo)); glEnableVertexAttribArray(0); glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(gs::Vertex), (void*)offsetof(gs::Vertex, position)); glEnableVertexAttribArray(1); glVertexAttribPointer(1, 2, GL_FLOAT, GL_FALSE, sizeof(gs::Vertex), (void*)offsetof(gs::Vertex, texCoords)); glEnableVertexAttribArray(2); glVertexAttribPointer(2, 3, GL_FLOAT, GL_FALSE, sizeof(gs::Vertex), (void*)offsetof(gs::Vertex, normal)); // Camera setup camera.SetPosition(glm::vec3(0.0f, 0.0f, 3.0f)); camera.SetSpeed(8.0f); camera.SetupProjection(45.0f, windowWidth/(float)windowHeight); lightObj.Load(""); // OpenGL setup glEnable(GL_DEPTH_TEST); } return res; }
bool OGLFrustumCulling::Init(int windowWidth, int windowHeight) { bool res = gs::Stage::Init(windowWidth, windowHeight); if (res) { res &= InitGUI(); auto program = std::make_shared<gs::Program>(); program->CreateShader(GL_VERTEX_SHADER, "sinDisplacement.vert"); program->CreateShader(GL_GEOMETRY_SHADER, "frustumCulling.geom"); program->CreateShader(GL_FRAGMENT_SHADER, "roundedPoints.frag"); res &= program->Link(); program->Use(); programs.push_back(program); program->AddUniform("MVP"); program->AddUniform("time"); program->AddUniform("frustumPlanes"); program->AddUniform("amplitude"); auto programFrustum = std::make_shared<gs::Program>(); programFrustum->CreateShader(GL_VERTEX_SHADER, "oglLight.vert"); programFrustum->CreateShader(GL_FRAGMENT_SHADER, "firstPoint.frag"); res &= programFrustum->Link(); programFrustum->Use(); programs.push_back(programFrustum); programFrustum->AddUniform("MVP"); auto vao = std::make_unique<gs::VertexArray>(); vao->BindVAO(); auto vbo = std::make_unique<gs::VertexBuffer>(GL_ARRAY_BUFFER); std::vector<glm::vec3> positions; for (size_t z = 0; z <= NUM_VERTICESZ; z++) { for (size_t x = 0; x <= NUM_VERTICESX; x++) { auto xCoord = ((((float)x / ((NUM_VERTICESX - 1)) * 2) - 1)) * HALF_SIZEX; auto zCoord = ((((float)z / ((NUM_VERTICESZ - 1)) * 2) - 1)) * HALF_SIZEZ; positions.push_back(glm::vec3(xCoord, 0.0f, zCoord)); } } vbo->BindVBO(); glBufferData(vbo->GetTarget(), sizeof(glm::vec3) * positions.size(), positions.data(), GL_STATIC_DRAW); vbos.push_back(std::move(vbo)); vao->AddAttribute(0, 3, GL_FLOAT, GL_FALSE, 0, nullptr); vaos.push_back(std::move(vao)); totalVertices = (int)positions.size(); ground.SetSize(1000); ground.SetProgram(programs[1]); ground.Load(""); camera.SetSpeed(10); camera.SetPosition(glm::vec3(0,0,20)); camera.SetupProjection(45.0f, windowWidth/(float)windowHeight, 0.01f); cameraExternal.SetSpeed(0); cameraExternal.SetPosition(glm::vec3(0,20,30)); cameraExternal.SetTarget(camera.GetPosition()); cameraExternal.SetupProjection(45.0f, windowWidth/(float)windowHeight); cameraExternal.Update(); glPointSize(30.0f); //glCullFace(GL_FRONT_FACE); } return res; }