mirror of
https://github.com/edubart/otclient.git
synced 2025-10-19 05:53:26 +02:00
graphics optimization feature inspirated by diablo3 engine
* the rendering now consits of two panes - the background pane (for animated stuff like the map) - the foreground pane (for steady stuff, like UI) each pane has it own max FPS and works idependently this may increase graphics performance on many platforms
This commit is contained in:
@@ -75,7 +75,7 @@ void FrameBuffer::resize(const Size& size)
|
||||
logFatal("Unable to setup framebuffer object");
|
||||
internalRelease();
|
||||
} else {
|
||||
m_screenBackup = TexturePtr(new Texture(size.width(), size.height(), 4));
|
||||
m_screenBackup = TexturePtr(new Texture(size.width(), size.height()));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -113,6 +113,12 @@ void FrameBuffer::release()
|
||||
g_graphics.setViewportSize(m_oldViewportSize);
|
||||
}
|
||||
|
||||
void FrameBuffer::draw()
|
||||
{
|
||||
Rect rect(0,0, getSize());
|
||||
g_painter->drawTexturedRect(rect, m_texture, rect);
|
||||
}
|
||||
|
||||
void FrameBuffer::draw(const Rect& dest, const Rect& src)
|
||||
{
|
||||
g_painter->drawTexturedRect(dest, m_texture, src);
|
||||
@@ -132,9 +138,7 @@ void FrameBuffer::internalBind()
|
||||
boundFbo = m_fbo;
|
||||
} else {
|
||||
// backup screen color buffer into a texture
|
||||
m_screenBackup->bind();
|
||||
Size size = getSize();
|
||||
glCopyTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 0, 0, size.width(), size.height());
|
||||
m_screenBackup->copyFromScreen(Rect(0, 0, getSize()));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -145,16 +149,14 @@ void FrameBuffer::internalRelease()
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, m_prevBoundFbo);
|
||||
boundFbo = m_prevBoundFbo;
|
||||
} else {
|
||||
Size size = getSize();
|
||||
Rect screenRect(0, 0, getSize());
|
||||
|
||||
// copy the drawn color buffer into the framebuffer texture
|
||||
m_texture->bind();
|
||||
glCopyTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 0, 0, size.width(), size.height());
|
||||
m_texture->copyFromScreen(screenRect);
|
||||
|
||||
// restore screen original content
|
||||
glDisable(GL_BLEND);
|
||||
g_painter->drawTexturedRect(Rect(0, 0, size), m_screenBackup, Rect(0, 0, size));
|
||||
glEnable(GL_BLEND);
|
||||
g_painter->setCompositionMode(Painter::CompositionMode_Replace);
|
||||
g_painter->drawTexturedRect(screenRect, m_screenBackup, screenRect);
|
||||
}
|
||||
}
|
||||
|
||||
|
@@ -37,6 +37,7 @@ public:
|
||||
void bind();
|
||||
void clear(const Color& color = Color::black, const Rect& rect = Rect());
|
||||
void release();
|
||||
void draw();
|
||||
void draw(const Rect& dest);
|
||||
void draw(const Rect& dest, const Rect& src);
|
||||
|
||||
|
@@ -88,7 +88,6 @@ void Graphics::init()
|
||||
|
||||
selectPainterEngine(m_prefferedPainterEngine);
|
||||
m_emptyTexture = TexturePtr(new Texture);
|
||||
|
||||
}
|
||||
|
||||
void Graphics::terminate()
|
||||
|
@@ -53,7 +53,7 @@ void Painter::refreshState()
|
||||
updateGlTexture();
|
||||
}
|
||||
|
||||
void Painter::saveAndResetState()
|
||||
void Painter::saveState()
|
||||
{
|
||||
assert(m_oldStateIndex<10);
|
||||
m_olderStates[m_oldStateIndex].projectionMatrix = m_projectionMatrix;
|
||||
@@ -65,6 +65,11 @@ void Painter::saveAndResetState()
|
||||
m_olderStates[m_oldStateIndex].shaderProgram = m_shaderProgram;
|
||||
m_olderStates[m_oldStateIndex].texture = m_texture;
|
||||
m_oldStateIndex++;
|
||||
}
|
||||
|
||||
void Painter::saveAndResetState()
|
||||
{
|
||||
saveState();
|
||||
resetState();
|
||||
}
|
||||
|
||||
|
@@ -62,6 +62,7 @@ public:
|
||||
|
||||
void resetState();
|
||||
virtual void refreshState();
|
||||
void saveState();
|
||||
void saveAndResetState();
|
||||
void restoreSavedState();
|
||||
|
||||
|
@@ -50,9 +50,10 @@ void Particle::render()
|
||||
if(!m_texture)
|
||||
g_painter->drawFilledRect(m_rect);
|
||||
else {
|
||||
g_painter->saveState();
|
||||
g_painter->setCompositionMode(m_compositionMode);
|
||||
g_painter->drawTexturedRect(m_rect, m_texture);
|
||||
g_painter->setCompositionMode(Painter::CompositionMode_Normal);
|
||||
g_painter->restoreSavedState();
|
||||
}
|
||||
}
|
||||
|
||||
|
@@ -129,6 +129,12 @@ uint Texture::internalLoadGLTexture(uchar *pixels, int channels, int width, int
|
||||
return id;
|
||||
}
|
||||
|
||||
void Texture::copyFromScreen(const Rect& screenRect)
|
||||
{
|
||||
bind();
|
||||
glCopyTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, screenRect.x(), screenRect.y(), screenRect.width(), screenRect.height());
|
||||
}
|
||||
|
||||
void Texture::bind()
|
||||
{
|
||||
// must reset painter texture state
|
||||
|
@@ -30,9 +30,11 @@ class Texture : public std::enable_shared_from_this<Texture>
|
||||
public:
|
||||
Texture();
|
||||
Texture(const ImagePtr& image);
|
||||
Texture(int width, int height, int channels, uchar* pixels = NULL);
|
||||
Texture(int width, int height, int channels = 4, uchar* pixels = NULL);
|
||||
virtual ~Texture();
|
||||
|
||||
void copyFromScreen(const Rect& screenRect);
|
||||
|
||||
void bind();
|
||||
|
||||
/// Tries to generate mipmaps via hardware, otherwise fallback to software implementation
|
||||
|
Reference in New Issue
Block a user