123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132 |
- #include <iostream>
- #include "client/rendering/wrapper/Framebuffer.h"
- Framebuffer::Framebuffer(const WindowSize& size, uint mode, bool texCompare) : size(size), mode(mode), textures(0),
- buffer(0), error(false), factor(1) {
- glGenFramebuffers(1, &buffer);
- glBindFramebuffer(GL_FRAMEBUFFER, buffer);
- data[0] = {POSITION, GL_RGB16F, GL_RGB, GL_FLOAT};
- data[1] = {NORMAL, GL_RGB16F, GL_RGB, GL_FLOAT};
- data[2] = {COLOR, GL_RGBA, GL_RGBA, GL_UNSIGNED_BYTE};
- data[3] = {RED, GL_R32F, GL_RGB, GL_FLOAT};
- data[4] = {TANGENT, GL_RGB16F, GL_RGB, GL_FLOAT};
- data[5] = {DEPTH, GL_DEPTH_COMPONENT32, GL_DEPTH_COMPONENT, GL_FLOAT};
- GLuint attachments[5];
- uint counter = 0;
- for(uint i = 0; i < 5; i++) {
- if(mode & data[i].mask) {
- setupTexture(i, size.width, size.height, attachments, counter);
- }
- }
- if(mode & DEPTH) {
- genTexture(5, size.width, size.height);
- if(texCompare) {
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_COMPARE_MODE, GL_COMPARE_REF_TO_TEXTURE);
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_COMPARE_FUNC, GL_LEQUAL);
- }
- glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, textures[5], 0);
- }
- glDrawBuffers(counter, attachments);
- GLenum glError = glCheckFramebufferStatus(GL_FRAMEBUFFER);
- if(glError != GL_FRAMEBUFFER_COMPLETE) {
- std::cout << "frame buffer error: " << getErrorString(error) << "\n";
- error = true;
- }
- }
- Framebuffer::~Framebuffer() {
- glDeleteFramebuffers(1, &buffer);
- for(GLuint& texture : textures) {
- glDeleteTextures(1, &texture);
- }
- }
- bool Framebuffer::hasError() const {
- return error;
- }
- void Framebuffer::bind() const {
- glViewport(0, 0, size.width * factor, size.height * factor);
- glBindFramebuffer(GL_FRAMEBUFFER, buffer);
- glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
- }
- void Framebuffer::resize(uint width, uint height) const {
- width *= factor;
- height *= factor;
- for(uint i = 0; i < 6; i++) {
- if(mode & data[i].mask) {
- glBindTexture(GL_TEXTURE_2D, textures[i]);
- glTexImage2D(GL_TEXTURE_2D, 0, data[i].internalFormat, width, height, 0, data[i].format, data[i].type, nullptr);
- }
- }
- }
- void Framebuffer::bindTexture(uint textureUnit, GLuint texture) const {
- glActiveTexture(GL_TEXTURE0 + textureUnit);
- glBindTexture(GL_TEXTURE_2D, texture);
- }
- void Framebuffer::bindPositionTexture(uint textureUnit) const {
- bindTexture(textureUnit, textures[0]);
- }
- void Framebuffer::bindNormalTexture(uint textureUnit) const {
- bindTexture(textureUnit, textures[1]);
- }
- void Framebuffer::bindColorTexture(uint textureUnit) const {
- bindTexture(textureUnit, textures[2]);
- }
- void Framebuffer::bindRedTexture(uint textureUnit) const {
- bindTexture(textureUnit, textures[3]);
- }
- void Framebuffer::bindTangentTexture(uint textureUnit) const {
- bindTexture(textureUnit, textures[4]);
- }
- void Framebuffer::bindDepthTexture(uint textureUnit) const {
- bindTexture(textureUnit, textures[5]);
- }
- void Framebuffer::genTexture(uint index, uint width, uint height) {
- glGenTextures(1, textures + index);
- glBindTexture(GL_TEXTURE_2D, textures[index]);
- glTexImage2D(GL_TEXTURE_2D, 0, data[index].internalFormat, width, height, 0, data[index].format, data[index].type, nullptr);
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
- }
- void Framebuffer::setupTexture(uint index, uint width, uint height, GLuint* attachments, uint& counter) {
- genTexture(index, width, height);
- glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0 + counter, GL_TEXTURE_2D, textures[index], 0);
- attachments[counter] = GL_COLOR_ATTACHMENT0 + counter;
- counter++;
- }
- const char* Framebuffer::getErrorString(GLenum error) const {
- switch(error) {
- case GL_FRAMEBUFFER_UNDEFINED: return "GL_FRAMEBUFFER_UNDEFINED";
- case GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT: return "GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT";
- case GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT: return "GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT";
- case GL_FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER: return "GL_FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER";
- case GL_FRAMEBUFFER_INCOMPLETE_READ_BUFFER: return "GL_FRAMEBUFFER_INCOMPLETE_READ_BUFFER";
- case GL_FRAMEBUFFER_UNSUPPORTED: return "GL_FRAMEBUFFER_UNSUPPORTED";
- case GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE: return "GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE";
- case GL_FRAMEBUFFER_INCOMPLETE_LAYER_TARGETS: return "GL_FRAMEBUFFER_INCOMPLETE_LAYER_TARGETS";
- }
- return "unknown error";
- }
- void Framebuffer::setFactor(int factor) {
- this->factor = factor;
- resize(size.width, size.height);
- }
|