diff options
Diffstat (limited to 'src/graphics')
-rw-r--r-- | src/graphics/Gui.cpp | 1 | ||||
-rw-r--r-- | src/graphics/RenderSection.cpp | 281 | ||||
-rw-r--r-- | src/graphics/Shader.cpp | 2 | ||||
-rw-r--r-- | src/graphics/Shader.hpp | 22 | ||||
-rw-r--r-- | src/graphics/Texture.cpp | 2 | ||||
-rw-r--r-- | src/graphics/Texture.hpp | 14 | ||||
-rw-r--r-- | src/graphics/Widget.cpp | 1 |
7 files changed, 285 insertions, 38 deletions
diff --git a/src/graphics/Gui.cpp b/src/graphics/Gui.cpp new file mode 100644 index 0000000..bbf7cf2 --- /dev/null +++ b/src/graphics/Gui.cpp @@ -0,0 +1 @@ +#include <graphics/Gui.hpp>
\ No newline at end of file diff --git a/src/graphics/RenderSection.cpp b/src/graphics/RenderSection.cpp new file mode 100644 index 0000000..fec67b5 --- /dev/null +++ b/src/graphics/RenderSection.cpp @@ -0,0 +1,281 @@ +#include <graphics/RenderSection.hpp> + +const GLfloat vertices[] = { + //Z+ edge + -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, + + //Z- edge + -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, + + //X+ edge + -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, + + //X- edge + 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, + + //Y+ edge + 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, + + //Y- edge + -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, +}; + +const GLfloat uv_coords[] = { + //Z+ + 0.0f, 1.0f, + 0.0f, 0.0f, + 1.0f, 0.0f, + 0.0f, 1.0f, + 1.0f, 0.0f, + 1.0f, 1.0f, + + //Z- + 1.0f, 0.0f, + 1.0f, 1.0f, + 0.0f, 0.0f, + 0.0f, 0.0f, + 1.0f, 1.0f, + 0.0f, 1.0f, + + //X+ + 0.0f, 0.0f, + 1.0f, 0.0f, + 0.0f, 1.0f, + 0.0f, 1.0f, + 1.0f, 0.0f, + 1.0f, 1.0f, + + //X- + 0.0f, 0.0f, + 1.0f, 1.0f, + 0.0f, 1.0f, + 0.0f, 0.0f, + 1.0f, 0.0f, + 1.0f, 1.0f, + + //Y+ + 0.0f, 0.0f, + 1.0f, 1.0f, + 0.0f, 1.0f, + 0.0f, 0.0f, + 1.0f, 0.0f, + 1.0f, 1.0f, + + //Y- + 1.0f, 0.0f, + 0.0f, 1.0f, + 0.0f, 0.0f, + 1.0f, 1.0f, + 0.0f, 1.0f, + 1.0f, 0.0f, +}; + +void RenderState::SetActiveVao(GLuint Vao) { + if (Vao != ActiveVao) { + glBindVertexArray(Vao); + ActiveVao = Vao; + } +} + +void RenderState::SetActiveShader(GLuint Shader) { + if (Shader != ActiveShader) { + glUseProgram(Shader); + ActiveShader = Shader; + } +} + +const GLuint magicUniqueConstant = 88375; +GLuint RenderSection::VboVertices = magicUniqueConstant; +GLuint RenderSection::VboUvs = magicUniqueConstant; +std::map<GLuint, int> RenderSection::refCounterVbo; +std::map<GLuint, int> RenderSection::refCounterVao; + + +RenderSection::RenderSection(World *world, Vector position) : sectionPosition(position), world(world) { + + if (VboVertices == magicUniqueConstant) { + glGenBuffers(1, &VboVertices); + glGenBuffers(1, &VboUvs); + + //Cube vertices + glBindBuffer(GL_ARRAY_BUFFER, VboVertices); + glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW); + + //Cube UVs + glBindBuffer(GL_ARRAY_BUFFER, VboUvs); + glBufferData(GL_ARRAY_BUFFER, sizeof(uv_coords), uv_coords, GL_STATIC_DRAW); + + LOG(INFO) << "Created VBOs with vertices (" << VboVertices << ") and UVs (" << VboUvs + << ") for ordinary blocks"; + } + + glGenBuffers(1, &VboBlocks); + if (refCounterVbo.find(VboBlocks) == refCounterVbo.end()) + refCounterVbo[VboBlocks] = 0; + refCounterVbo[VboBlocks]++; + + glGenBuffers(1, &VboModels); + if (refCounterVbo.find(VboModels) == refCounterVbo.end()) + refCounterVbo[VboModels] = 0; + refCounterVbo[VboModels]++; + + glGenVertexArrays(1, &Vao); + if (refCounterVao.find(Vao) == refCounterVao.end()) + refCounterVao[Vao] = 0; + refCounterVao[Vao]++; + + glBindVertexArray(Vao); + { + //Cube vertices + glBindBuffer(GL_ARRAY_BUFFER, VboVertices); + glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(GLfloat), nullptr); + glEnableVertexAttribArray(0); + + //Cube UVs + glBindBuffer(GL_ARRAY_BUFFER, VboUvs); + glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, 2 * sizeof(GLfloat), nullptr); + glEnableVertexAttribArray(2); + + //Blocks ids + glBindBuffer(GL_ARRAY_BUFFER, VboBlocks); + glVertexAttribPointer(7, 2, GL_FLOAT, GL_FALSE, 2 * sizeof(GLfloat), nullptr); + glEnableVertexAttribArray(7); + glVertexAttribDivisor(7, 1); + glCheckError(); + + //Blocks models + size_t sizeOfMat4 = 4 * 4 * sizeof(GLfloat); + glBindBuffer(GL_ARRAY_BUFFER, VboModels); + glVertexAttribPointer(8 + 0, 4, GL_FLOAT, GL_FALSE, sizeOfMat4, nullptr); + glVertexAttribPointer(8 + 1, 4, GL_FLOAT, GL_FALSE, sizeOfMat4, (void *) (1 * 4 * sizeof(GLfloat))); + glVertexAttribPointer(8 + 2, 4, GL_FLOAT, GL_FALSE, sizeOfMat4, (void *) (2 * 4 * sizeof(GLfloat))); + glVertexAttribPointer(8 + 3, 4, GL_FLOAT, GL_FALSE, sizeOfMat4, (void *) (3 * 4 * sizeof(GLfloat))); + glEnableVertexAttribArray(8 + 0); + glEnableVertexAttribArray(8 + 1); + glEnableVertexAttribArray(8 + 2); + glEnableVertexAttribArray(8 + 3); + glVertexAttribDivisor(8 + 0, 1); + glVertexAttribDivisor(8 + 1, 1); + glVertexAttribDivisor(8 + 2, 1); + glVertexAttribDivisor(8 + 3, 1); + + glBindBuffer(GL_ARRAY_BUFFER, 0); + } + glBindVertexArray(0); + UpdateState(); + glCheckError(); +} + +RenderSection::~RenderSection() { + refCounterVbo[VboBlocks]--; + refCounterVbo[VboModels]--; + refCounterVao[Vao]--; + if (refCounterVbo[VboBlocks] <= 0) + glDeleteBuffers(1, &VboBlocks); + if (refCounterVbo[VboModels] <= 0) + glDeleteBuffers(1, &VboBlocks); + if (refCounterVao[Vao] <= 0) + glDeleteVertexArrays(1, &Vao); +} + +void RenderSection::UpdateState() { + Section *section = &world->sections.find(sectionPosition)->second; + std::vector<glm::mat4> models; + std::vector<glm::vec2> blocks; + for (int y = 0; y < 16; y++) { + for (int z = 0; z < 16; z++) { + for (int x = 0; x < 16; x++) { + Block block = section->GetBlock(Vector(x, y, z)); + if (block.id == 0) + continue; + + unsigned char isVisible = 0; + if (x == 0 || x == 15 || y == 0 || y == 15 || z == 0 || z == 15) { + isVisible = 0; + } else { + isVisible |= (section->GetBlock(Vector(x + 1, y, z)).id != 0) << 0; + isVisible |= (section->GetBlock(Vector(x - 1, y, z)).id != 0) << 1; + isVisible |= (section->GetBlock(Vector(x, y + 1, z)).id != 0) << 2; + isVisible |= (section->GetBlock(Vector(x, y - 1, z)).id != 0) << 3; + isVisible |= (section->GetBlock(Vector(x, y, z + 1)).id != 0) << 4; + isVisible |= (section->GetBlock(Vector(x, y, z - 1)).id != 0) << 5; + } + if (isVisible == 0x3F) + continue; + + glm::vec2 data(block.id, block.state); + blocks.push_back(data); + glm::mat4 model; + model = glm::translate(model, glm::vec3(section->GetPosition().GetX() * 16, + section->GetPosition().GetY() * 16, + section->GetPosition().GetZ() * 16)); + model = glm::translate(model, glm::vec3(x, y, z)); + double size = 0.999; + model = glm::scale(model, glm::vec3(size, size, size)); + models.push_back(model); + } + } + } + glBindBuffer(GL_ARRAY_BUFFER, VboBlocks); + glBufferData(GL_ARRAY_BUFFER, blocks.size() * sizeof(glm::vec2), blocks.data(), GL_DYNAMIC_DRAW); + + glBindBuffer(GL_ARRAY_BUFFER, VboModels); + glBufferData(GL_ARRAY_BUFFER, models.size() * sizeof(glm::mat4), models.data(), GL_DYNAMIC_DRAW); + + glBindBuffer(GL_ARRAY_BUFFER, 0); + + numOfBlocks = blocks.size(); +} + +void RenderSection::Render(RenderState &state) { + state.SetActiveVao(Vao); + glDrawArraysInstanced(GL_TRIANGLES, 0, 36, numOfBlocks); + glCheckError(); +} + +Section *RenderSection::GetSection() { + return &world->sections.find(sectionPosition)->second; +} + +RenderSection::RenderSection(const RenderSection &other) { + this->world = other.world; + this->VboModels = other.VboModels; + this->VboBlocks = other.VboBlocks; + this->sectionPosition = other.sectionPosition; + this->Vao = other.Vao; + this->numOfBlocks = other.numOfBlocks; + + refCounterVbo[VboBlocks]++; + refCounterVbo[VboModels]++; + refCounterVao[Vao]++; +} diff --git a/src/graphics/Shader.cpp b/src/graphics/Shader.cpp index cf43115..3d2efb8 100644 --- a/src/graphics/Shader.cpp +++ b/src/graphics/Shader.cpp @@ -1,4 +1,4 @@ -#include "Shader.hpp" +#include <graphics/Shader.hpp> Shader::Shader(const GLchar *vertexPath, const GLchar *fragmentPath, const GLchar *geometryPath) { vertex = vertexPath; diff --git a/src/graphics/Shader.hpp b/src/graphics/Shader.hpp deleted file mode 100644 index 1bcee3a..0000000 --- a/src/graphics/Shader.hpp +++ /dev/null @@ -1,22 +0,0 @@ -#pragma once -#include <string> -#include <fstream> -#include <sstream> -#include <easylogging++.h> -#include <GL/glew.h> - -class Shader -{ -private: - const GLchar *vertex; - const GLchar *fragment; -public: - // Идентификатор программы - GLuint Program; - // Конструктор считывает и собирает шейдер - Shader(const GLchar* vertexPath, const GLchar* fragmentPath, const GLchar* geometryPath = nullptr); - // Использование программы - void Use(); - - void Reload(); -};
\ No newline at end of file diff --git a/src/graphics/Texture.cpp b/src/graphics/Texture.cpp index 5d183c3..e5e2bba 100644 --- a/src/graphics/Texture.cpp +++ b/src/graphics/Texture.cpp @@ -1,4 +1,4 @@ -#include "Texture.hpp" +#include <graphics/Texture.hpp> Texture::Texture(std::string filename, GLenum textureWrapping, GLenum textureFiltering) { glGenTextures(1, &texture); diff --git a/src/graphics/Texture.hpp b/src/graphics/Texture.hpp deleted file mode 100644 index 277806a..0000000 --- a/src/graphics/Texture.hpp +++ /dev/null @@ -1,14 +0,0 @@ -#pragma once - -#include <SFML/Graphics.hpp> -#include <easylogging++.h> -#include <GL/glew.h> - -class Texture { - Texture(Texture&); - Texture&operator=(Texture&); -public: - GLuint texture; - Texture(std::string filename, GLenum textureWrapping = GL_CLAMP_TO_BORDER, GLenum textureFiltering = GL_NEAREST); - ~Texture(); -};
\ No newline at end of file diff --git a/src/graphics/Widget.cpp b/src/graphics/Widget.cpp new file mode 100644 index 0000000..e53bc87 --- /dev/null +++ b/src/graphics/Widget.cpp @@ -0,0 +1 @@ +#include <graphics/Widget.hpp>
\ No newline at end of file |