X-Git-Url: http://git.tdb.fi/?p=libs%2Fgl.git;a=blobdiff_plain;f=source%2Fframebuffer.cpp;h=cf478ce29b686d842ce2074078952633b2e47b02;hp=ae8f4dd471a936881f77e8e569de8e97ba5bc8c0;hb=HEAD;hpb=a86623004ba91baef76dac9275e9b79366acce16 diff --git a/source/framebuffer.cpp b/source/framebuffer.cpp deleted file mode 100644 index ae8f4dd4..00000000 --- a/source/framebuffer.cpp +++ /dev/null @@ -1,327 +0,0 @@ -#include -#include -#include -#include "error.h" -#include "framebuffer.h" -#include "misc.h" -#include "renderbuffer.h" -#include "texture2d.h" - -using namespace std; - -namespace Msp { -namespace GL { - -void operator<<(LexicalConverter &conv, FramebufferStatus status) -{ - switch(status) - { - case FRAMEBUFFER_INCOMPLETE_ATTACHMENT: - conv.result("incomplete attachment"); - break; - case FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT: - conv.result("missing attachment"); - break; - case FRAMEBUFFER_INCOMPLETE_DIMENSIONS: - conv.result("mismatched attachment dimensions"); - break; - case FRAMEBUFFER_INCOMPLETE_FORMATS: - conv.result("mismatched attachment formats"); - break; - case FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER: - conv.result("missing draw buffer attachment"); - break; - case FRAMEBUFFER_INCOMPLETE_READ_BUFFER: - conv.result("missing read buffer attachment"); - break; - case FRAMEBUFFER_UNSUPPORTED: - conv.result("unsupported"); - break; - default: - conv.result(lexical_cast(status, "%#x")); - break; - } -} - -framebuffer_incomplete::framebuffer_incomplete(FramebufferStatus status): - runtime_error(lexical_cast(status)) -{ } - - -Framebuffer::Framebuffer(unsigned i): - id(i), - dirty(0) -{ - if(id) - throw invalid_argument("System framebuffer must have id 0"); - - int viewport[4]; - glGetIntegerv(GL_VIEWPORT, viewport); - width = viewport[2]; - height = viewport[3]; -} - -Framebuffer::Framebuffer(): - width(0), - height(0), - dirty(0) -{ - static Require _req(EXT_framebuffer_object); - - glGenFramebuffers(1, &id); -} - -Framebuffer::~Framebuffer() -{ - if(id) - glDeleteFramebuffers(1, &id); - if(current()==this) - unbind(); -} - -void Framebuffer::update_attachment(unsigned mask) const -{ - if(current()==this) - { - std::vector color_bufs; - color_bufs.reserve(attachments.size()); - for(unsigned i=0; iget_id()); - else if(attch.type==GL_TEXTURE_2D) - { - static_cast(attch.tex)->allocate(attch.level); - glFramebufferTexture2D(GL_FRAMEBUFFER, attch.attachment, attch.type, attch.tex->get_id(), attch.level); - } - else if(attch.type==GL_TEXTURE_CUBE_MAP) - { - static_cast(attch.tex)->allocate(attch.level); - glFramebufferTexture2D(GL_FRAMEBUFFER, attch.attachment, attch.cube_face, attch.tex->get_id(), attch.level); - } - else - glFramebufferRenderbuffer(GL_FRAMEBUFFER, attch.attachment, 0, 0); - } - - if(attch.attachment>=COLOR_ATTACHMENT0 && attch.attachment<=COLOR_ATTACHMENT3) - color_bufs.push_back(attch.attachment); - } - - if(color_bufs.empty()) - { - glDrawBuffer(GL_NONE); - glReadBuffer(GL_NONE); - } - else if(color_bufs.size()==1) - { - glDrawBuffer(color_bufs.front()); - glReadBuffer(color_bufs.front()); - } - else - { - static Require _req(ARB_draw_buffers); - glDrawBuffers(color_bufs.size(), &color_bufs[0]); - glReadBuffer(color_bufs.front()); - } - } - else - dirty |= mask; -} - -void Framebuffer::check_size() -{ - for(vector::iterator i=attachments.begin(); i!=attachments.end(); ++i) - if(i->type) - { - if(i->type==GL_RENDERBUFFER) - { - width = i->rbuf->get_width(); - height = i->rbuf->get_height(); - } - else if(i->type==GL_TEXTURE_2D) - { - Texture2D *tex = static_cast(i->tex); - width = tex->get_width(); - height = tex->get_height(); - } - else if(i->type==GL_TEXTURE_CUBE_MAP) - { - width = static_cast(i->tex)->get_size(); - height = width; - } - if(current()==this) - glViewport(0, 0, width, height); - break; - } -} - -unsigned Framebuffer::get_attachment_index(FramebufferAttachment attch) -{ - for(unsigned i=0; i(glCheckFramebufferStatus(GL_FRAMEBUFFER)); -} - -void Framebuffer::require_complete() const -{ - FramebufferStatus status = check_status(); - if(status!=FRAMEBUFFER_COMPLETE) - throw framebuffer_incomplete(status); -} - -void Framebuffer::clear(BufferBits bits) -{ - Bind _bind(this, true); - glClear(bits); -} - -void Framebuffer::blit_from(const Framebuffer &other, int sx0, int sy0, int sx1, int sy1, int dx0, int dy0, int dx1, int dy1, BufferBits bits, bool filter) -{ - static Require _req(EXT_framebuffer_blit); - - const Framebuffer *old = current(); - if(set_current(this)) - { - glBindFramebuffer(GL_DRAW_FRAMEBUFFER, id); - if(dirty) - { - update_attachment(dirty); - dirty = 0; - } - } - if(old!=&other) - glBindFramebuffer(GL_READ_FRAMEBUFFER, other.id); - - glBlitFramebuffer(sx0, sy0, sx1, sy1, dx0, dy0, dx1, dy1, bits, (filter ? GL_LINEAR : GL_NEAREST)); - - set_current(old); - glBindFramebuffer(GL_FRAMEBUFFER, (old ? old->id : 0)); -} - -void Framebuffer::blit_from(const Framebuffer &other, int sx, int sy, unsigned wd, unsigned ht, int dx, int dy, BufferBits bits) -{ - blit_from(other, sx, sy, sx+wd, sy+ht, dx, dy, dx+wd, dy+ht, bits, false); -} - -void Framebuffer::blit_from(const Framebuffer &other, BufferBits bits, bool filter) -{ - blit_from(other, 0, 0, other.width, other.height, 0, 0, width, height, bits, filter); -} - -void Framebuffer::bind() const -{ - if(set_current(this)) - { - glBindFramebuffer(GL_FRAMEBUFFER, id); - if(dirty) - { - update_attachment(dirty); - dirty = 0; - } - if(width && height) - glViewport(0, 0, width, height); - } -} - -const Framebuffer *Framebuffer::current() -{ - if(!cur_obj) - cur_obj = &system(); - return cur_obj; -} - -void Framebuffer::unbind() -{ - system().bind(); -} - -Framebuffer &Framebuffer::system() -{ - static Framebuffer sys_framebuf(0); - return sys_framebuf; -} - - -Framebuffer::Attachment::Attachment(FramebufferAttachment a): - attachment(a), - type(0), - level(0) -{ } - -void Framebuffer::Attachment::set(Renderbuffer &r) -{ - type = GL_RENDERBUFFER; - rbuf = &r; - level = 0; -} - -void Framebuffer::Attachment::set(Texture &t, GLenum f, unsigned l) -{ - type = t.get_target(); - tex = &t; - cube_face = f; - level = l; -} - -void Framebuffer::Attachment::clear() -{ - type = 0; -} - -} // namespace GL -} // namespace Msp