Browse Source

Ensure that the renderbuffer object is properly created before using it.

pull/68/head
Vladimír Vondruš 12 years ago
parent
commit
385549d0b8
  1. 21
      src/Magnum/Renderbuffer.cpp
  2. 8
      src/Magnum/Renderbuffer.h
  3. 20
      src/Magnum/Test/RenderbufferGLTest.cpp

21
src/Magnum/Renderbuffer.cpp

@ -64,7 +64,7 @@ Int Renderbuffer::maxSamples() {
return value;
}
Renderbuffer::Renderbuffer() { glGenRenderbuffers(1, &_id); }
Renderbuffer::Renderbuffer(): _created{false} { glGenRenderbuffers(1, &_id); }
Renderbuffer::~Renderbuffer() {
/* Moved out, nothing to do */
@ -77,11 +77,24 @@ Renderbuffer::~Renderbuffer() {
glDeleteRenderbuffers(1, &_id);
}
std::string Renderbuffer::label() const {
inline void Renderbuffer::createIfNotAlready() {
if(_created) return;
/* glGen*() does not create the object, just reserves the name. Some
commands (such as glObjectLabel()) operate with IDs directly and they
require the object to be created. Binding the renderbuffer finally
creates it. Also all EXT DSA functions implicitly create it. */
bind();
CORRADE_INTERNAL_ASSERT(_created);
}
std::string Renderbuffer::label() {
createIfNotAlready();
return Context::current()->state().debug->getLabelImplementation(GL_RENDERBUFFER, _id);
}
Renderbuffer& Renderbuffer::setLabelInternal(const Containers::ArrayReference<const char> label) {
createIfNotAlready();
Context::current()->state().debug->labelImplementation(GL_RENDERBUFFER, _id, label);
return *this;
}
@ -99,7 +112,9 @@ void Renderbuffer::bind() {
if(binding == _id) return;
/* Binding the renderbuffer finally creates it */
binding = _id;
_created = true;
glBindRenderbuffer(GL_RENDERBUFFER, _id);
}
@ -110,6 +125,7 @@ void Renderbuffer::storageImplementationDefault(RenderbufferFormat internalForma
#ifndef MAGNUM_TARGET_GLES
void Renderbuffer::storageImplementationDSA(RenderbufferFormat internalFormat, const Vector2i& size) {
_created = true;
glNamedRenderbufferStorageEXT(_id, GLenum(internalFormat), size.x(), size.y());
}
#endif
@ -147,6 +163,7 @@ void Renderbuffer::storageMultisampleImplementationNV(const GLsizei samples, con
#ifndef MAGNUM_TARGET_GLES
void Renderbuffer::storageMultisampleImplementationDSA(GLsizei samples, RenderbufferFormat internalFormat, const Vector2i& size) {
_created = true;
glNamedRenderbufferStorageMultisampleEXT(_id, samples, GLenum(internalFormat), size.x(), size.y());
}
#endif

8
src/Magnum/Renderbuffer.h

@ -124,7 +124,7 @@ class MAGNUM_EXPORT Renderbuffer: public AbstractObject {
* @fn_gl_extension2{GetObjectLabel,EXT,debug_label} with
* @def_gl{RENDERBUFFER}
*/
std::string label() const;
std::string label();
/**
* @brief Set renderbuffer label
@ -178,6 +178,8 @@ class MAGNUM_EXPORT Renderbuffer: public AbstractObject {
void setStorageMultisample(Int samples, RenderbufferFormat internalFormat, const Vector2i& size);
private:
void MAGNUM_LOCAL createIfNotAlready();
Renderbuffer& setLabelInternal(Containers::ArrayReference<const char> label);
void MAGNUM_LOCAL storageImplementationDefault(RenderbufferFormat internalFormat, const Vector2i& size);
@ -198,14 +200,16 @@ class MAGNUM_EXPORT Renderbuffer: public AbstractObject {
void MAGNUM_LOCAL bind();
GLuint _id;
bool _created; /* see createIfNotAlready() for details */
};
inline Renderbuffer::Renderbuffer(Renderbuffer&& other) noexcept: _id(other._id) {
inline Renderbuffer::Renderbuffer(Renderbuffer&& other) noexcept: _id{other._id}, _created{other._created} {
other._id = 0;
}
inline Renderbuffer& Renderbuffer::operator=(Renderbuffer&& other) noexcept {
std::swap(_id, other._id);
std::swap(_created, other._created);
return *this;
}

20
src/Magnum/Test/RenderbufferGLTest.cpp

@ -111,29 +111,15 @@ void RenderbufferGLTest::label() {
CORRADE_SKIP(Extensions::GL::ARB::framebuffer_object::string() + std::string(" is not available."));
#endif
/* No-Op version is tested in AbstractObjectGLTest */
if(!Context::current()->isExtensionSupported<Extensions::GL::KHR::debug>() &&
!Context::current()->isExtensionSupported<Extensions::GL::EXT::debug_label>())
CORRADE_SKIP("Required extension is not available");
{
/** @todo Is this even legal optimization? */
CORRADE_EXPECT_FAIL("The object must be used at least once before setting/querying label.");
CORRADE_VERIFY(false);
}
Renderbuffer renderbuffer;
#ifndef MAGNUM_TARGET_GLES2
renderbuffer.setStorage(RenderbufferFormat::RGBA8, {128, 128});
#else
renderbuffer.setStorage(RenderbufferFormat::RGBA4, {128, 128});
#endif
CORRADE_COMPARE(renderbuffer.label(), "");
MAGNUM_VERIFY_NO_ERROR();
renderbuffer.setLabel("MyRenderbuffer");
CORRADE_COMPARE(renderbuffer.label(), "MyRenderbuffer");
MAGNUM_VERIFY_NO_ERROR();
CORRADE_COMPARE(renderbuffer.label(), "MyRenderbuffer");
}
void RenderbufferGLTest::setStorage() {

Loading…
Cancel
Save