Moves glReadPixels to GL backend.
This was SVN commit r26802.
This commit is contained in:
parent
5de50c447c
commit
7bd075d570
@ -413,7 +413,7 @@ void CRenderer::RenderFrame(const bool needsPresent)
|
|||||||
if (m_ShouldPreloadResourcesBeforeNextFrame)
|
if (m_ShouldPreloadResourcesBeforeNextFrame)
|
||||||
{
|
{
|
||||||
m_ShouldPreloadResourcesBeforeNextFrame = false;
|
m_ShouldPreloadResourcesBeforeNextFrame = false;
|
||||||
// We don't meed to render logger for the preload.
|
// We don't need to render logger for the preload.
|
||||||
RenderFrameImpl(true, false);
|
RenderFrameImpl(true, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -421,12 +421,13 @@ void CRenderer::RenderFrame(const bool needsPresent)
|
|||||||
{
|
{
|
||||||
RenderBigScreenShot(needsPresent);
|
RenderBigScreenShot(needsPresent);
|
||||||
}
|
}
|
||||||
|
else if (m_ScreenShotType == ScreenShotType::DEFAULT)
|
||||||
|
{
|
||||||
|
RenderScreenShot(needsPresent);
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (m_ScreenShotType == ScreenShotType::DEFAULT)
|
RenderFrameImpl(true, true);
|
||||||
RenderScreenShot();
|
|
||||||
else
|
|
||||||
RenderFrameImpl(true, true);
|
|
||||||
|
|
||||||
m->deviceCommandContext->Flush();
|
m->deviceCommandContext->Flush();
|
||||||
if (needsPresent)
|
if (needsPresent)
|
||||||
@ -541,7 +542,7 @@ void CRenderer::RenderFrame2D(const bool renderGUI, const bool renderLogger)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void CRenderer::RenderScreenShot()
|
void CRenderer::RenderScreenShot(const bool needsPresent)
|
||||||
{
|
{
|
||||||
m_ScreenShotType = ScreenShotType::NONE;
|
m_ScreenShotType = ScreenShotType::NONE;
|
||||||
|
|
||||||
@ -551,23 +552,25 @@ void CRenderer::RenderScreenShot()
|
|||||||
VfsPath filename;
|
VfsPath filename;
|
||||||
vfs::NextNumberedFilename(g_VFS, filenameFormat, g_NextScreenShotNumber, filename);
|
vfs::NextNumberedFilename(g_VFS, filenameFormat, g_NextScreenShotNumber, filename);
|
||||||
|
|
||||||
const size_t w = (size_t)g_xres, h = (size_t)g_yres;
|
const size_t width = static_cast<size_t>(g_xres), height = static_cast<size_t>(g_yres);
|
||||||
const size_t bpp = 24;
|
const size_t bpp = 24;
|
||||||
GLenum fmt = GL_RGB;
|
|
||||||
int flags = TEX_BOTTOM_UP;
|
|
||||||
|
|
||||||
// Hide log messages and re-render
|
// Hide log messages and re-render
|
||||||
RenderFrameImpl(true, false);
|
RenderFrameImpl(true, false);
|
||||||
|
|
||||||
const size_t img_size = w * h * bpp / 8;
|
const size_t img_size = width * height * bpp / 8;
|
||||||
const size_t hdr_size = tex_hdr_size(filename);
|
const size_t hdr_size = tex_hdr_size(filename);
|
||||||
std::shared_ptr<u8> buf;
|
std::shared_ptr<u8> buf;
|
||||||
AllocateAligned(buf, hdr_size + img_size, maxSectorSize);
|
AllocateAligned(buf, hdr_size + img_size, maxSectorSize);
|
||||||
GLvoid* img = buf.get() + hdr_size;
|
void* img = buf.get() + hdr_size;
|
||||||
Tex t;
|
Tex t;
|
||||||
if (t.wrap(w, h, bpp, flags, buf, hdr_size) < 0)
|
if (t.wrap(width, height, bpp, TEX_BOTTOM_UP, buf, hdr_size) < 0)
|
||||||
return;
|
return;
|
||||||
glReadPixels(0, 0, (GLsizei)w, (GLsizei)h, fmt, GL_UNSIGNED_BYTE, img);
|
|
||||||
|
m->deviceCommandContext->ReadbackFramebufferSync(0, 0, width, height, img);
|
||||||
|
m->deviceCommandContext->Flush();
|
||||||
|
if (needsPresent)
|
||||||
|
g_VideoMode.GetBackendDevice()->Present();
|
||||||
|
|
||||||
if (tex_write(&t, filename) == INFO::OK)
|
if (tex_write(&t, filename) == INFO::OK)
|
||||||
{
|
{
|
||||||
@ -590,7 +593,7 @@ void CRenderer::RenderBigScreenShot(const bool needsPresent)
|
|||||||
|
|
||||||
// If the game hasn't started yet then use WriteScreenshot to generate the image.
|
// If the game hasn't started yet then use WriteScreenshot to generate the image.
|
||||||
if (!g_Game)
|
if (!g_Game)
|
||||||
return RenderScreenShot();
|
return RenderScreenShot(needsPresent);
|
||||||
|
|
||||||
int tiles = 4, tileWidth = 256, tileHeight = 256;
|
int tiles = 4, tileWidth = 256, tileHeight = 256;
|
||||||
CFG_GET_VAL("screenshot.tiles", tiles);
|
CFG_GET_VAL("screenshot.tiles", tiles);
|
||||||
@ -614,15 +617,6 @@ void CRenderer::RenderBigScreenShot(const bool needsPresent)
|
|||||||
|
|
||||||
const int imageWidth = tileWidth * tiles, imageHeight = tileHeight * tiles;
|
const int imageWidth = tileWidth * tiles, imageHeight = tileHeight * tiles;
|
||||||
const int bpp = 24;
|
const int bpp = 24;
|
||||||
// we want writing BMP to be as fast as possible,
|
|
||||||
// so read data from OpenGL in BMP format to obviate conversion.
|
|
||||||
#if CONFIG2_GLES // GLES doesn't support BGR
|
|
||||||
const GLenum fmt = GL_RGB;
|
|
||||||
const int flags = TEX_BOTTOM_UP;
|
|
||||||
#else
|
|
||||||
const GLenum fmt = GL_BGR;
|
|
||||||
const int flags = TEX_BOTTOM_UP | TEX_BGR;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
const size_t imageSize = imageWidth * imageHeight * bpp / 8;
|
const size_t imageSize = imageWidth * imageHeight * bpp / 8;
|
||||||
const size_t tileSize = tileWidth * tileHeight * bpp / 8;
|
const size_t tileSize = tileWidth * tileHeight * bpp / 8;
|
||||||
@ -638,7 +632,7 @@ void CRenderer::RenderBigScreenShot(const bool needsPresent)
|
|||||||
|
|
||||||
Tex t;
|
Tex t;
|
||||||
GLvoid* img = imageBuffer.get() + headerSize;
|
GLvoid* img = imageBuffer.get() + headerSize;
|
||||||
if (t.wrap(imageWidth, imageHeight, bpp, flags, imageBuffer, headerSize) < 0)
|
if (t.wrap(imageWidth, imageHeight, bpp, TEX_BOTTOM_UP, imageBuffer, headerSize) < 0)
|
||||||
{
|
{
|
||||||
free(tileData);
|
free(tileData);
|
||||||
return;
|
return;
|
||||||
@ -672,18 +666,18 @@ void CRenderer::RenderBigScreenShot(const bool needsPresent)
|
|||||||
|
|
||||||
RenderFrameImpl(false, false);
|
RenderFrameImpl(false, false);
|
||||||
|
|
||||||
|
m->deviceCommandContext->ReadbackFramebufferSync(0, 0, tileWidth, tileHeight, tileData);
|
||||||
|
m->deviceCommandContext->Flush();
|
||||||
|
if (needsPresent)
|
||||||
|
g_VideoMode.GetBackendDevice()->Present();
|
||||||
|
|
||||||
// Copy the tile pixels into the main image
|
// Copy the tile pixels into the main image
|
||||||
glReadPixels(0, 0, tileWidth, tileHeight, fmt, GL_UNSIGNED_BYTE, tileData);
|
|
||||||
for (int y = 0; y < tileHeight; ++y)
|
for (int y = 0; y < tileHeight; ++y)
|
||||||
{
|
{
|
||||||
void* dest = static_cast<char*>(img) + ((tileY * tileHeight + y) * imageWidth + (tileX * tileWidth)) * bpp / 8;
|
void* dest = static_cast<char*>(img) + ((tileY * tileHeight + y) * imageWidth + (tileX * tileWidth)) * bpp / 8;
|
||||||
void* src = static_cast<char*>(tileData) + y * tileWidth * bpp / 8;
|
void* src = static_cast<char*>(tileData) + y * tileWidth * bpp / 8;
|
||||||
memcpy(dest, src, tileWidth * bpp / 8);
|
memcpy(dest, src, tileWidth * bpp / 8);
|
||||||
}
|
}
|
||||||
|
|
||||||
m->deviceCommandContext->Flush();
|
|
||||||
if (needsPresent)
|
|
||||||
g_VideoMode.GetBackendDevice()->Present();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -150,7 +150,7 @@ protected:
|
|||||||
|
|
||||||
void RenderFrameImpl(const bool renderGUI, const bool renderLogger);
|
void RenderFrameImpl(const bool renderGUI, const bool renderLogger);
|
||||||
void RenderFrame2D(const bool renderGUI, const bool renderLogger);
|
void RenderFrame2D(const bool renderGUI, const bool renderLogger);
|
||||||
void RenderScreenShot();
|
void RenderScreenShot(const bool needsPresent);
|
||||||
void RenderBigScreenShot(const bool needsPresent);
|
void RenderBigScreenShot(const bool needsPresent);
|
||||||
|
|
||||||
// SetRenderPath: Select the preferred render path.
|
// SetRenderPath: Select the preferred render path.
|
||||||
|
@ -725,6 +725,15 @@ void CDeviceCommandContext::SetFramebuffer(CFramebuffer* framebuffer)
|
|||||||
glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, framebuffer->GetHandle());
|
glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, framebuffer->GetHandle());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void CDeviceCommandContext::ReadbackFramebufferSync(
|
||||||
|
const uint32_t x, const uint32_t y, const uint32_t width, const uint32_t height,
|
||||||
|
void* data)
|
||||||
|
{
|
||||||
|
ENSURE(m_Framebuffer);
|
||||||
|
glReadPixels(x, y, width, height, GL_RGB, GL_UNSIGNED_BYTE, data);
|
||||||
|
ogl_WarnIfError();
|
||||||
|
}
|
||||||
|
|
||||||
void CDeviceCommandContext::SetScissors(const uint32_t scissorCount, const Rect* scissors)
|
void CDeviceCommandContext::SetScissors(const uint32_t scissorCount, const Rect* scissors)
|
||||||
{
|
{
|
||||||
ENSURE(scissorCount <= 1);
|
ENSURE(scissorCount <= 1);
|
||||||
|
@ -57,6 +57,9 @@ public:
|
|||||||
void ClearFramebuffer();
|
void ClearFramebuffer();
|
||||||
void ClearFramebuffer(const bool color, const bool depth, const bool stencil);
|
void ClearFramebuffer(const bool color, const bool depth, const bool stencil);
|
||||||
void SetFramebuffer(CFramebuffer* framebuffer);
|
void SetFramebuffer(CFramebuffer* framebuffer);
|
||||||
|
void ReadbackFramebufferSync(
|
||||||
|
const uint32_t x, const uint32_t y, const uint32_t width, const uint32_t height,
|
||||||
|
void* data);
|
||||||
|
|
||||||
void UploadTexture(CTexture* texture, const Format dataFormat,
|
void UploadTexture(CTexture* texture, const Format dataFormat,
|
||||||
const void* data, const size_t dataSize,
|
const void* data, const size_t dataSize,
|
||||||
|
Loading…
Reference in New Issue
Block a user