1. itsnotabigtruck
  2. love-openzdk

Source

love-openzdk / src / modules / graphics / opengl2 / Framebuffer.cpp

/**
* Copyright (c) 2006-2010 LOVE Development Team
* 
* This software is provided 'as-is', without any express or implied
* warranty.  In no event will the authors be held liable for any damages
* arising from the use of this software.
* 
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
* 
* 1. The origin of this software must not be misrepresented; you must not
*    claim that you wrote the original software. If you use this software
*    in a product, an acknowledgment in the product documentation would be
*    appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
*    misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
**/

// C++
#include <cassert>

// OpenGL
#include <GLES2/gl2.h>
#include <GLES2/gl2ext.h>

// LOVE
#include <image/ImageData.h>
#include <graphics/Drawable.h>
#include <graphics/Volatile.h>
#include <graphics/opengl2/Framebuffer.h>
#include <graphics/opengl2/GLUtilities.h>

namespace love
{
namespace graphics
{
namespace opengl2
{
	Framebuffer::Framebuffer(int width, int height)
		: width(width), height(height), fbo(0), texture(0)
	{
		// Validate arguments
		assert(width > 0);
		assert(height > 0);
	}

	void Framebuffer::draw(float x, float y, float angle, float sx, float sy, float ox, float oy) const
	{
		// FIXME: Implement draw
		assert(0);
	}

	int Framebuffer::getHeight() const
	{
		return height;
	}

	int Framebuffer::getWidth() const
	{
		return width;
	}

	bool Framebuffer::loadVolatile()
	{
		// Create a texture of the desired size
		glGenTextures(1, &texture);
		assert(texture);
		glBindTexture(GL_TEXTURE_2D, texture);
		glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0,
				GL_RGBA, GL_UNSIGNED_BYTE, NULL);
		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);

		// Create a framebuffer object over the texture
		glGenFramebuffers(1, &fbo);
		assert(fbo);
		glBindFramebuffer(GL_FRAMEBUFFER, fbo);
		glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0,
				GL_TEXTURE_2D, texture, 0);
		GLenum status = glCheckFramebufferStatus(GL_FRAMEBUFFER);
		glBindFramebuffer(GL_FRAMEBUFFER, 0); // FIXME: restore previous FBO

		// Ensure that everything is kosher
		if (LGLErrorTestR() || status != GL_FRAMEBUFFER_COMPLETE)
		{
			unloadVolatile();
			return false;
		}
		return true;
	}

	love::image::ImageData * Framebuffer::retrieve() const
	{
		// FIXME: Implement retrieve
		assert(0);
		return NULL;
	}

	void Framebuffer::unloadVolatile()
	{
		// Delete the FBO and backing texture if necessary
		if (fbo)
			glDeleteFramebuffers(1, &fbo);
		fbo = 0;
		if (texture)
			glDeleteTextures(1, &texture);
		texture = 0;
	}

	Framebuffer::~Framebuffer()
	{
		// Clean everything up if we haven't already done so
		unloadVolatile();
	}

} // opengl2
} // graphics
} // love