VideoCommon: Add shared framedumping code.

This commit is contained in:
degasus 2016-10-07 20:31:51 +02:00
parent 34d733d376
commit f45ddddf1c
2 changed files with 100 additions and 10 deletions

View File

@ -20,6 +20,7 @@
#include "Common/CommonTypes.h"
#include "Common/Event.h"
#include "Common/FileUtil.h"
#include "Common/Flag.h"
#include "Common/Profiler.h"
#include "Common/StringUtil.h"
@ -97,14 +98,10 @@ static float AspectToWidescreen(float aspect)
return aspect * ((16.0f / 9.0f) / (4.0f / 3.0f));
}
Renderer::Renderer() : frame_data(), bLastFrameDumped(false)
Renderer::Renderer()
{
UpdateActiveConfig();
TextureCacheBase::OnConfigChanged(g_ActiveConfig);
#if defined _WIN32 || defined HAVE_LIBAV
bAVIDumping = false;
#endif
}
Renderer::~Renderer()
@ -113,9 +110,14 @@ Renderer::~Renderer()
prev_efb_format = PEControl::INVALID_FMT;
efb_scale_numeratorX = efb_scale_numeratorY = efb_scale_denominatorX = efb_scale_denominatorY = 1;
#if defined _WIN32 || defined HAVE_LIBAV
if (SConfig::GetInstance().m_DumpFrames && bLastFrameDumped && bAVIDumping)
#if defined(HAVE_LIBAV) || defined(_WIN32)
// Stop frame dumping if it was left enabled at shutdown time.
if (bAVIDumping)
{
AVIDump::Stop();
bAVIDumping = false;
}
#endif
}
@ -534,6 +536,86 @@ void Renderer::Swap(u32 xfbAddr, u32 fbWidth, u32 fbStride, u32 fbHeight, const
XFBWrited = false;
}
bool Renderer::IsFrameDumping()
{
#if defined(HAVE_LIBAV) || defined(_WIN32)
if (SConfig::GetInstance().m_DumpFrames)
return true;
if (bLastFrameDumped && bAVIDumping)
{
AVIDump::Stop();
std::vector<u8>().swap(frame_data);
m_last_framedump_width = m_last_framedump_height = 0;
bAVIDumping = false;
OSD::AddMessage("Stop dumping frames", 2000);
}
bLastFrameDumped = false;
#endif
return false;
}
void Renderer::DumpFrameData(const u8* data, int w, int h, AVIDump::DumpFormat format,
bool swap_upside_down)
{
#if defined(HAVE_LIBAV) || defined(_WIN32)
if (w == 0 || h == 0)
return;
size_t image_size;
switch (format)
{
case AVIDump::DumpFormat::FORMAT_BGR:
image_size = 3 * w * h;
break;
case AVIDump::DumpFormat::FORMAT_RGBA:
image_size = 4 * w * h;
break;
}
m_last_framedump_width = w;
m_last_framedump_height = h;
m_last_framedump_format = format;
// TODO: Refactor this. Right now it's needed for the implace flipping of the image.
// It's also used to repeat the last frame.
frame_data.assign(data, data + image_size);
if (!bLastFrameDumped)
{
bAVIDumping = AVIDump::Start(w, h, format);
if (!bAVIDumping)
{
OSD::AddMessage("AVIDump Start failed", 2000);
}
else
{
OSD::AddMessage(StringFromFormat("Dumping Frames to \"%sframedump0.avi\" (%dx%d RGB24)",
File::GetUserPath(D_DUMPFRAMES_IDX).c_str(), w, h),
2000);
}
}
if (bAVIDumping)
{
if (swap_upside_down)
FlipImageData(&frame_data[0], w, h, 4);
AVIDump::AddFrame(&frame_data[0], w, h);
}
bLastFrameDumped = true;
#endif
}
void Renderer::RepeatFrameDumpFrame()
{
#if defined(HAVE_LIBAV) || defined(_WIN32)
if (SConfig::GetInstance().m_DumpFrames && bAVIDumping && !frame_data.empty())
{
AVIDump::AddFrame(&frame_data[0], m_last_framedump_width, m_last_framedump_height);
}
#endif
}
void Renderer::FlipImageData(u8* data, int w, int h, int pixel_width)
{
for (int y = 0; y < h / 2; ++y)

View File

@ -23,6 +23,7 @@
#include "Common/Event.h"
#include "Common/Flag.h"
#include "Common/MathUtil.h"
#include "VideoCommon/AVIDump.h"
#include "VideoCommon/BPMemory.h"
#include "VideoCommon/FPSCounter.h"
#include "VideoCommon/VideoBackendBase.h"
@ -146,14 +147,21 @@ protected:
static void CheckFifoRecording();
static void RecordVideoMemory();
bool IsFrameDumping();
void DumpFrameData(const u8* data, int w, int h, AVIDump::DumpFormat format,
bool swap_upside_down = false);
void RepeatFrameDumpFrame();
static volatile bool s_bScreenshot;
static std::mutex s_criticalScreenshot;
static std::string s_sScreenshotName;
bool bAVIDumping;
std::vector<u8> frame_data;
bool bLastFrameDumped;
bool bAVIDumping = false;
bool bLastFrameDumped = false;
int m_last_framedump_width = 0;
int m_last_framedump_height = 0;
AVIDump::DumpFormat m_last_framedump_format;
// The framebuffer size
static int s_target_width;