mirror of
https://github.com/love2d/love.git
synced 2026-08-17 19:23:38 +02:00
Added love.graphics.discard, which discards the contents of the screen (or currently active Canvas.)
Using it just after activating a Canvas can improve performance on many mobile devices, if the conditions for using it are right. --HG-- branch : minor
This commit is contained in:
@@ -424,6 +424,49 @@ void Graphics::clear(Color c)
|
|||||||
glClear(GL_COLOR_BUFFER_BIT | GL_STENCIL_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
glClear(GL_COLOR_BUFFER_BIT | GL_STENCIL_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Graphics::discard(bool color, bool stencil)
|
||||||
|
{
|
||||||
|
if (!(GLAD_VERSION_4_3 || GLAD_ARB_ES3_compatibility || GLAD_ES_VERSION_3_0 || GLAD_EXT_discard_framebuffer))
|
||||||
|
return;
|
||||||
|
|
||||||
|
std::vector<GLenum> attachments;
|
||||||
|
attachments.reserve(3);
|
||||||
|
|
||||||
|
// glDiscardFramebuffer uses different attachment enums for the default FBO.
|
||||||
|
if (!Canvas::current && gl.getDefaultFBO() == 0)
|
||||||
|
{
|
||||||
|
if (color)
|
||||||
|
attachments.push_back(GL_COLOR);
|
||||||
|
|
||||||
|
if (stencil)
|
||||||
|
{
|
||||||
|
attachments.push_back(GL_STENCIL);
|
||||||
|
attachments.push_back(GL_DEPTH);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (color)
|
||||||
|
{
|
||||||
|
attachments.push_back(GL_COLOR_ATTACHMENT0);
|
||||||
|
for (int i = 0; i < (int) states.back().canvases.size() - 1; i++)
|
||||||
|
attachments.push_back(GL_COLOR_ATTACHMENT1 + i);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (stencil)
|
||||||
|
{
|
||||||
|
attachments.push_back(GL_STENCIL_ATTACHMENT);
|
||||||
|
attachments.push_back(GL_DEPTH_ATTACHMENT);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Hint for the driver that it doesn't need to save these buffers.
|
||||||
|
if (GLAD_VERSION_4_3 || GLAD_ARB_ES3_compatibility || GLAD_ES_VERSION_3_0)
|
||||||
|
glInvalidateFramebuffer(GL_FRAMEBUFFER, (GLint) attachments.size(), &attachments[0]);
|
||||||
|
else if (GLAD_EXT_discard_framebuffer)
|
||||||
|
glDiscardFramebufferEXT(GL_FRAMEBUFFER, (GLint) attachments.size(), &attachments[0]);
|
||||||
|
}
|
||||||
|
|
||||||
void Graphics::present()
|
void Graphics::present()
|
||||||
{
|
{
|
||||||
if (!isActive())
|
if (!isActive())
|
||||||
@@ -433,23 +476,8 @@ void Graphics::present()
|
|||||||
std::vector<StrongRef<Canvas>> canvases = states.back().canvases;
|
std::vector<StrongRef<Canvas>> canvases = states.back().canvases;
|
||||||
setCanvas();
|
setCanvas();
|
||||||
|
|
||||||
if (GLAD_ES_VERSION_3_0 || GLAD_EXT_discard_framebuffer)
|
// Discard the stencil buffer before swapping.
|
||||||
{
|
discard(false, true);
|
||||||
GLenum attachments[] = {GL_STENCIL, GL_DEPTH};
|
|
||||||
|
|
||||||
if (gl.getDefaultFBO() != 0)
|
|
||||||
{
|
|
||||||
// A non-zero FBO needs different attachment enums.
|
|
||||||
attachments[0] = GL_STENCIL_ATTACHMENT;
|
|
||||||
attachments[1] = GL_DEPTH_ATTACHMENT;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Hint for the driver that it doesn't need to save these buffers.
|
|
||||||
if (GLAD_ES_VERSION_3_0)
|
|
||||||
glInvalidateFramebuffer(GL_FRAMEBUFFER, 2, attachments);
|
|
||||||
else if (GLAD_EXT_discard_framebuffer)
|
|
||||||
glDiscardFramebufferEXT(GL_FRAMEBUFFER, 2, attachments);
|
|
||||||
}
|
|
||||||
|
|
||||||
#ifdef LOVE_IOS
|
#ifdef LOVE_IOS
|
||||||
// Hack: SDL's color renderbuffer needs to be bound when swapBuffers is called.
|
// Hack: SDL's color renderbuffer needs to be bound when swapBuffers is called.
|
||||||
|
|||||||
@@ -85,6 +85,11 @@ public:
|
|||||||
**/
|
**/
|
||||||
void clear(Color c);
|
void clear(Color c);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Discards the contents of the screen.
|
||||||
|
**/
|
||||||
|
void discard(bool color, bool stencil);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Flips buffers. (Rendered geometry is presented on screen).
|
* Flips buffers. (Rendered geometry is presented on screen).
|
||||||
**/
|
**/
|
||||||
|
|||||||
@@ -61,6 +61,14 @@ int w_clear(lua_State *L)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int w_discard(lua_State *L)
|
||||||
|
{
|
||||||
|
bool color = luax_optboolean(L, 1, true);
|
||||||
|
bool stencil = luax_optboolean(L, 2, true);
|
||||||
|
instance()->discard(color, stencil);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
int w_present(lua_State *)
|
int w_present(lua_State *)
|
||||||
{
|
{
|
||||||
instance()->present();
|
instance()->present();
|
||||||
@@ -1465,6 +1473,7 @@ static const luaL_Reg functions[] =
|
|||||||
{
|
{
|
||||||
{ "reset", w_reset },
|
{ "reset", w_reset },
|
||||||
{ "clear", w_clear },
|
{ "clear", w_clear },
|
||||||
|
{ "discard", w_discard },
|
||||||
{ "present", w_present },
|
{ "present", w_present },
|
||||||
|
|
||||||
{ "newImage", w_newImage },
|
{ "newImage", w_newImage },
|
||||||
|
|||||||
@@ -42,6 +42,7 @@ namespace opengl
|
|||||||
|
|
||||||
int w_reset(lua_State *L);
|
int w_reset(lua_State *L);
|
||||||
int w_clear(lua_State *L);
|
int w_clear(lua_State *L);
|
||||||
|
int w_discard(lua_State *L);
|
||||||
int w_present(lua_State *L);
|
int w_present(lua_State *L);
|
||||||
int w_isCreated(lua_State *L);
|
int w_isCreated(lua_State *L);
|
||||||
int w_isActive(lua_State *L);
|
int w_isActive(lua_State *L);
|
||||||
|
|||||||
Reference in New Issue
Block a user