Support recording/playing movies starting from a savestate.

This commit is contained in:
SuuperW 2018-09-03 01:05:41 -05:00
parent 484b062bf5
commit e697391dfd
9 changed files with 146 additions and 69 deletions

View File

@ -559,7 +559,7 @@ void CommandLine::process_movieCommands()
} }
else if(record_movie_file != "") else if(record_movie_file != "")
{ {
FCEUI_SaveMovie(record_movie_file.c_str(), L"", 0, NULL, FCEUI_MovieGetRTCDefault()); FCEUI_SaveMovie(record_movie_file.c_str(), L"", START_BLANK, NULL, FCEUI_MovieGetRTCDefault());
} }
} }

View File

@ -243,8 +243,7 @@ INT_PTR CALLBACK ReplayDialogProc(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM
return false; return false;
} }
START_FROM startFrom;
int flag=0;
//Record movie dialog //Record movie dialog
static INT_PTR CALLBACK RecordDialogProc(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam) static INT_PTR CALLBACK RecordDialogProc(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam)
@ -256,7 +255,11 @@ static INT_PTR CALLBACK RecordDialogProc(HWND hwndDlg, UINT uMsg, WPARAM wParam,
switch(uMsg) switch(uMsg)
{ {
case WM_INITDIALOG: { case WM_INITDIALOG: {
CheckDlgButton(hwndDlg, IDC_START_FROM_SRAM, ((flag == 1) ? BST_CHECKED : BST_UNCHECKED)); CheckDlgButton(hwndDlg, IDC_START_FROM_SRAM, startFrom == START_SRAM ? BST_CHECKED : BST_UNCHECKED);
CheckDlgButton(hwndDlg, IDC_START_FROM_POWER_ON, startFrom == START_SAVESTATE ? BST_UNCHECKED : BST_CHECKED);
EnableWindow(GetDlgItem(hwndDlg, IDC_START_FROM_SRAM), startFrom != START_SAVESTATE);
EnableWindow(GetDlgItem(hwndDlg, IDC_EDIT_SRAMFILENAME), startFrom == START_SRAM);
EnableWindow(GetDlgItem(hwndDlg, IDC_BUTTON_BROWSESRAM), startFrom == START_SRAM);
SetFocus(GetDlgItem(hwndDlg, IDC_EDIT_FILENAME)); SetFocus(GetDlgItem(hwndDlg, IDC_EDIT_FILENAME));
DateTime t = FCEUI_MovieGetRTCDefault(); DateTime t = FCEUI_MovieGetRTCDefault();
@ -313,7 +316,7 @@ static INT_PTR CALLBACK RecordDialogProc(HWND hwndDlg, UINT uMsg, WPARAM wParam,
t.tm_sec = systime.wSecond; t.tm_sec = systime.wSecond;
DateTime rtcstart(t.tm_year,t.tm_mon,t.tm_mday,t.tm_hour,t.tm_min,t.tm_sec); DateTime rtcstart(t.tm_year,t.tm_mon,t.tm_mday,t.tm_hour,t.tm_min,t.tm_sec);
FCEUI_SaveMovie(fname.c_str(), author, flag, sramfname, rtcstart); FCEUI_SaveMovie(fname.c_str(), author, startFrom, sramfname, rtcstart);
EndDialog(hwndDlg, 0); EndDialog(hwndDlg, 0);
} }
return true; return true;
@ -402,16 +405,33 @@ static INT_PTR CALLBACK RecordDialogProc(HWND hwndDlg, UINT uMsg, WPARAM wParam,
break; break;
} }
break; break;
}
case IDC_START_FROM_SRAM:
{
bool checked = IsDlgButtonChecked(hwndDlg, IDC_START_FROM_SRAM);
startFrom = checked ? START_SRAM : START_BLANK;
EnableWindow(GetDlgItem(hwndDlg, IDC_EDIT_SRAMFILENAME), checked);
EnableWindow(GetDlgItem(hwndDlg, IDC_BUTTON_BROWSESRAM), checked);
break;
} }
HWND cur = GetDlgItem(hwndDlg, IDC_EDIT_SRAMFILENAME); case IDC_START_FROM_POWER_ON: // TODO: test movies starting form savestate
{
IsDlgButtonChecked(hwndDlg, IDC_START_FROM_SRAM) ? flag=1 : flag=0; bool powerOn = IsDlgButtonChecked(hwndDlg, IDC_START_FROM_POWER_ON);
IsDlgButtonChecked(hwndDlg, IDC_START_FROM_SRAM) ? EnableWindow(cur, TRUE) : EnableWindow(cur, FALSE); startFrom = powerOn ? START_BLANK : START_SAVESTATE;
EnableWindow(GetDlgItem(hwndDlg, IDC_START_FROM_SRAM), powerOn);
cur = GetDlgItem(hwndDlg, IDC_BUTTON_BROWSESRAM); if (!powerOn)
IsDlgButtonChecked(hwndDlg, IDC_START_FROM_SRAM) ? EnableWindow(cur, TRUE) : EnableWindow(cur, FALSE); {
CheckDlgButton(hwndDlg, IDC_START_FROM_SRAM, false);
// CheckDlgButton does not send a WM_COMMAND message, so also disable SRAM stuff here
EnableWindow(GetDlgItem(hwndDlg, IDC_EDIT_SRAMFILENAME), false);
EnableWindow(GetDlgItem(hwndDlg, IDC_BUTTON_BROWSESRAM), false);
}
break;
}
}
}
return false; return false;
} }

View File

@ -18,6 +18,8 @@
#ifndef _WIN_REPLAY_H_ #ifndef _WIN_REPLAY_H_
#define _WIN_REPLAY_H_ #define _WIN_REPLAY_H_
enum START_FROM { START_BLANK, START_SRAM, START_SAVESTATE };
void Replay_LoadMovie(); void Replay_LoadMovie();
void MovieRecordTo(); void MovieRecordTo();

View File

@ -273,6 +273,7 @@
#define IDC_BUTTON_BROWSESRAM 980 #define IDC_BUTTON_BROWSESRAM 980
#define IDC_C_WATCH_UP 980 #define IDC_C_WATCH_UP 980
#define IDD_EDITWATCH 980 #define IDD_EDITWATCH 980
#define IDC_START_FROM_POWER_ON 981
#define IDC_C_WATCH_DOWN 981 #define IDC_C_WATCH_DOWN 981
#define RAMMENU_FILE_AUTOLOAD 982 #define RAMMENU_FILE_AUTOLOAD 982
#define RAMMENU_FILE_SAVEWINDOW 983 #define RAMMENU_FILE_SAVEWINDOW 983

View File

@ -963,27 +963,28 @@ BEGIN
PUSHBUTTON "Separator",IDC_C_WATCH_SEPARATE,225,136,36,14 PUSHBUTTON "Separator",IDC_C_WATCH_SEPARATE,225,136,36,14
END END
IDD_RECORDMOVIE DIALOGEX 0, 0, 301, 124 IDD_RECORDMOVIE DIALOGEX 0, 0, 301, 118
STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU
CAPTION "Record movie" CAPTION "Record movie"
FONT 8, "MS Shell Dlg", 400, 0, 0x1 FONT 8, "MS Shell Dlg", 400, 0, 0x1
BEGIN BEGIN
DEFPUSHBUTTON "OK",IDOK,177,106,50,14 DEFPUSHBUTTON "OK",IDOK,177,99,50,14
PUSHBUTTON "Cancel",IDCANCEL,231,106,50,14 PUSHBUTTON "Cancel",IDCANCEL,231,99,50,14
GROUPBOX "",65501,11,9,269,64 GROUPBOX "",65501,11,2,269,64
LTEXT "File:",IDC_STATIC,31,22,14,8 LTEXT "File:",IDC_STATIC,31,15,14,8
EDITTEXT IDC_EDIT_FILENAME,49,20,189,12,ES_AUTOHSCROLL EDITTEXT IDC_EDIT_FILENAME,49,13,189,12,ES_AUTOHSCROLL
PUSHBUTTON "...",IDC_BUTTON_BROWSEFILE,249,20,18,14 PUSHBUTTON "...",IDC_BUTTON_BROWSEFILE,249,13,18,14
LTEXT "Author:",IDC_STATIC,21,38,25,8 LTEXT "Author:",IDC_STATIC,21,31,25,8
EDITTEXT IDC_EDIT_AUTHOR,49,36,189,14,ES_AUTOHSCROLL EDITTEXT IDC_EDIT_AUTHOR,49,29,189,14,ES_AUTOHSCROLL
LTEXT "Date:",IDC_STATIC,28,56,18,8 LTEXT "Date:",IDC_STATIC,28,49,18,8
CONTROL "",IDC_DTP_DATE,"SysDateTimePick32",DTS_RIGHTALIGN | DTS_LONGDATEFORMAT | WS_TABSTOP,49,54,123,12 CONTROL "",IDC_DTP_DATE,"SysDateTimePick32",DTS_RIGHTALIGN | DTS_LONGDATEFORMAT | WS_TABSTOP,49,47,123,12
CONTROL "",IDC_DTP_TIME,"SysDateTimePick32",DTS_RIGHTALIGN | DTS_UPDOWN | WS_TABSTOP | 0x8,176,54,62,12 CONTROL "",IDC_DTP_TIME,"SysDateTimePick32",DTS_RIGHTALIGN | DTS_UPDOWN | WS_TABSTOP | 0x8,176,47,62,12
GROUPBOX "",IDC_STATIC,11,73,269,29 GROUPBOX "",IDC_STATIC,11,66,269,29
LTEXT "SRAM:",IDC_STATIC,19,85,25,8 LTEXT "SRAM:",IDC_STATIC,19,78,25,8
EDITTEXT IDC_EDIT_SRAMFILENAME,48,83,189,12,ES_AUTOHSCROLL EDITTEXT IDC_EDIT_SRAMFILENAME,48,76,189,12,ES_AUTOHSCROLL
PUSHBUTTON "...",IDC_BUTTON_BROWSESRAM,248,83,18,14 PUSHBUTTON "...",IDC_BUTTON_BROWSESRAM,248,76,18,14
CONTROL "Start from SRAM",IDC_START_FROM_SRAM,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,12,108,93,10 CONTROL "Start from SRAM",IDC_START_FROM_SRAM,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,12,101,73,10
CONTROL "Start from power on",IDC_START_FROM_POWER_ON,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,85,101,81,10
END END
IDD_REPLAY_METADATA DIALOGEX 0, 0, 325, 250 IDD_REPLAY_METADATA DIALOGEX 0, 0, 325, 250
@ -1904,7 +1905,7 @@ BEGIN
IDD_RECORDMOVIE, DIALOG IDD_RECORDMOVIE, DIALOG
BEGIN BEGIN
BOTTOMMARGIN, 113 BOTTOMMARGIN, 107
END END
IDD_SOUNDSETTINGS, DIALOG IDD_SOUNDSETTINGS, DIALOG
@ -2120,6 +2121,10 @@ BEGIN
IDM_FILE_STOPAVI "Stop AVI" IDM_FILE_STOPAVI "Stop AVI"
IDM_FILE_STOPWAV "Stop WAV" IDM_FILE_STOPWAV "Stop WAV"
IDM_FILE_RECORDAVI "Record AVI" IDM_FILE_RECORDAVI "Record AVI"
END
STRINGTABLE
BEGIN
IDM_FILE_RECORDWAV "Record WAV" IDM_FILE_RECORDWAV "Record WAV"
END END
@ -2133,23 +2138,58 @@ BEGIN
ID_LABEL_HK1 "Open ROM" ID_LABEL_HK1 "Open ROM"
ID_LABEL_HK2 "Reset" ID_LABEL_HK2 "Reset"
ID_LABEL_HK3 "Pause" ID_LABEL_HK3 "Pause"
ID_LABEL_HK3b "CPU mode"
ID_LABEL_HK3c "Increase JIT block size"
ID_LABEL_HK3d "Decrease JIT block size"
ID_LABEL_HK4 "Frame Advance" ID_LABEL_HK4 "Frame Advance"
ID_LABEL_HK5 "Fast Forward" ID_LABEL_HK5 "Fast Forward"
ID_LABEL_HK6 "Fast Forward Toggle" ID_LABEL_HK6 "Fast Forward Toggle"
ID_LABEL_HK7 "Increase Speed" ID_LABEL_HK7 "Increase Speed"
ID_LABEL_HK8 "Decrease Speed" ID_LABEL_HK8 "Decrease Speed"
ID_LABEL_HK8b "Limit Framerate Toggle"
ID_LABEL_HK9 "Microphone" ID_LABEL_HK9 "Microphone"
ID_LABEL_HK10 "Auto-Hold" ID_LABEL_HK10 "Auto-Hold"
ID_LABEL_HK11 "Auto-Hold Clear" ID_LABEL_HK11 "Auto-Hold Clear"
ID_LABEL_HK12 "Toggle Rasterizer" ID_LABEL_HK12 "Toggle Rasterizer"
ID_LABEL_HK13 "Save Screenshot as" ID_LABEL_HK13 "Save Screenshot as"
ID_LABEL_HK13b "Quick Screenshot"
ID_LABEL_HK14 "Record WAV" ID_LABEL_HK14 "Record WAV"
ID_LABEL_HK15 "Record AVI" ID_LABEL_HK15 "Record AVI"
END
STRINGTABLE
BEGIN
ID_LABEL_HK3b "CPU mode"
ID_LABEL_HK3c "Increase JIT block size"
END
STRINGTABLE
BEGIN
ID_LABEL_HK3d "Decrease JIT block size"
END
STRINGTABLE
BEGIN
ID_LABEL_HK8b "Limit Framerate Toggle"
END
STRINGTABLE
BEGIN
ID_LABEL_HK48 "Turbo A"
ID_LABEL_HK49 "Turbo Y"
ID_LABEL_HK50 "Turbo X"
ID_LABEL_HK51 "Turbo R"
ID_LABEL_HK52 "Turbo L"
ID_LABEL_HK53 "Reload ROM"
ID_LABEL_HK13b "Quick Screenshot"
ID_LABEL_HK54 "Search Cheats"
ID_LABEL_HK55 "Increase Pressure"
ID_LABEL_HK56 "Decrease Pressure"
ID_LABEL_HK57 "Rotation 0"
ID_LABEL_HK58 "Rotation 90"
ID_LABEL_HK59 "Rotation 180"
ID_LABEL_HK60 "Rotation 270"
ID_LABEL_HK61 "Toggle Stylus Jitter"
ID_LABEL_HK62 "Toggle Cursor"
END
STRINGTABLE
BEGIN
ID_LABEL_HK16 "Toggle Frame Display" ID_LABEL_HK16 "Toggle Frame Display"
ID_LABEL_HK17 "Toggle FPS Display" ID_LABEL_HK17 "Toggle FPS Display"
ID_LABEL_HK18 "Toggle Input Display" ID_LABEL_HK18 "Toggle Input Display"
@ -2166,6 +2206,10 @@ BEGIN
ID_LABEL_HK29 "Stylus Auto-Hold" ID_LABEL_HK29 "Stylus Auto-Hold"
ID_LABEL_HK30 "LCDs layout mode" ID_LABEL_HK30 "LCDs layout mode"
ID_LABEL_HK31 "LCDs swap" ID_LABEL_HK31 "LCDs swap"
END
STRINGTABLE
BEGIN
ID_LABEL_HK32 "Increase Volume" ID_LABEL_HK32 "Increase Volume"
ID_LABEL_HK33 "Decrease Volume" ID_LABEL_HK33 "Decrease Volume"
ID_LABEL_HK34 "Save to Slot " ID_LABEL_HK34 "Save to Slot "
@ -2182,21 +2226,10 @@ BEGIN
ID_LABEL_HK45 "Turbo Select" ID_LABEL_HK45 "Turbo Select"
ID_LABEL_HK46 "Turbo Start" ID_LABEL_HK46 "Turbo Start"
ID_LABEL_HK47 "Turbo B" ID_LABEL_HK47 "Turbo B"
ID_LABEL_HK48 "Turbo A" END
ID_LABEL_HK49 "Turbo Y"
ID_LABEL_HK50 "Turbo X" STRINGTABLE
ID_LABEL_HK51 "Turbo R" BEGIN
ID_LABEL_HK52 "Turbo L"
ID_LABEL_HK53 "Reload ROM"
ID_LABEL_HK54 "Search Cheats"
ID_LABEL_HK55 "Increase Pressure"
ID_LABEL_HK56 "Decrease Pressure"
ID_LABEL_HK57 "Rotation 0"
ID_LABEL_HK58 "Rotation 90"
ID_LABEL_HK59 "Rotation 180"
ID_LABEL_HK60 "Rotation 270"
ID_LABEL_HK61 "Toggle Stylus Jitter"
ID_LABEL_HK62 "Toggle Cursor"
ID_LABEL_HK63 "List Cheats" ID_LABEL_HK63 "List Cheats"
ID_LABEL_HK64 "Toggle Cheats" ID_LABEL_HK64 "Toggle Cheats"
ID_LABEL_HK65 "Toggle Main GPU" ID_LABEL_HK65 "Toggle Main GPU"

View File

@ -39,6 +39,8 @@
#include "version.h" #include "version.h"
#include "path.h" #include "path.h"
#include "emufile.h" #include "emufile.h"
#include "replay.h"
#include "saves.h"
using namespace std; using namespace std;
bool freshMovie = false; //True when a movie loads, false when movie is altered. Used to determine if a movie has been altered since opening bool freshMovie = false; //True when a movie loads, false when movie is altered. Used to determine if a movie has been altered since opening
@ -639,9 +641,17 @@ const char* _CDECL_ FCEUI_LoadMovie(const char *fname, bool _read_only, bool tas
oldSettings = new MovieData(true); oldSettings = new MovieData(true);
LoadSettingsFromMovie(currMovieData); LoadSettingsFromMovie(currMovieData);
if (currMovieData.savestate.size() == 0)
{
firstReset = true; firstReset = true;
NDS_Reset(); NDS_Reset();
firstReset = false; firstReset = false;
}
else
{
EMUFILE_MEMORY efs = EMUFILE_MEMORY(&currMovieData.savestate);
savestate_load(efs);
}
////WE NEED TO LOAD A SAVESTATE ////WE NEED TO LOAD A SAVESTATE
//if(currMovieData.savestate.size() != 0) //if(currMovieData.savestate.size() != 0)
@ -729,7 +739,7 @@ bool MovieData::loadSramFrom(std::vector<u8>* buf)
//begin recording a new movie //begin recording a new movie
//TODO - BUG - the record-from-another-savestate doesnt work. //TODO - BUG - the record-from-another-savestate doesnt work.
void FCEUI_SaveMovie(const char *fname, std::wstring author, int flag, std::string sramfname, const DateTime &rtcstart) void FCEUI_SaveMovie(const char *fname, std::wstring author, START_FROM startFrom, std::string sramfname, const DateTime &rtcstart)
{ {
//if(!FCEU_IsValidUI(FCEUI_RECORDMOVIE)) //if(!FCEU_IsValidUI(FCEUI_RECORDMOVIE))
// return; // return;
@ -758,15 +768,26 @@ void FCEUI_SaveMovie(const char *fname, std::wstring author, int flag, std::stri
NDS_CreateDummyFirmware(&CommonSettings.fw_config); NDS_CreateDummyFirmware(&CommonSettings.fw_config);
} }
if (startFrom == START_SAVESTATE)
{
// ?? MovieData::dumpSavestateTo(&currMovieData.savestate,Z_BEST_COMPRESSION);
EMUFILE_MEMORY efs;
savestate_save(efs, Z_BEST_COMPRESSION);
currMovieData.savestate.resize(efs.size());
efs.fseek(0, SEEK_SET);
efs.fread(currMovieData.savestate.begin()._Ptr, efs.size());
}
else
{
NDS_Reset(); NDS_Reset();
//todo ? //todo ?
//poweron(true); //poweron(true);
//else
// MovieData::dumpSavestateTo(&currMovieData.savestate,Z_BEST_COMPRESSION);
if(flag == 1) if (startFrom == START_SRAM)
EMUFILE::readAllBytes(&currMovieData.sram, sramfname); EMUFILE::readAllBytes(&currMovieData.sram, sramfname);
}
//we are going to go ahead and dump the header. from now on we will only be appending frames //we are going to go ahead and dump the header. from now on we will only be appending frames
currMovieData.dump(*osRecordingMovie, false); currMovieData.dump(*osRecordingMovie, false);

View File

@ -28,6 +28,8 @@
#include "utils/guid.h" #include "utils/guid.h"
#include "utils/md5.h" #include "utils/md5.h"
#include "replay.h"
struct UserInput; struct UserInput;
class EMUFILE; class EMUFILE;
@ -276,7 +278,7 @@ extern MovieData currMovieData; //adelikat: main needs this for frame counter d
extern bool movie_reset_command; extern bool movie_reset_command;
bool FCEUI_MovieGetInfo(EMUFILE &fp, MOVIE_INFO &info, bool skipFrameCount); bool FCEUI_MovieGetInfo(EMUFILE &fp, MOVIE_INFO &info, bool skipFrameCount);
void FCEUI_SaveMovie(const char *fname, std::wstring author, int flag, std::string sramfname, const DateTime &rtcstart); void FCEUI_SaveMovie(const char *fname, std::wstring author, START_FROM startFrom, std::string sramfname, const DateTime &rtcstart);
const char* _CDECL_ FCEUI_LoadMovie(const char *fname, bool _read_only, bool tasedit, int _pauseframe); // returns NULL on success, errmsg on failure const char* _CDECL_ FCEUI_LoadMovie(const char *fname, bool _read_only, bool tasedit, int _pauseframe); // returns NULL on success, errmsg on failure
void UnloadMovieEmulationSettings(); void UnloadMovieEmulationSettings();
bool AreMovieEmulationSettingsActive(); bool AreMovieEmulationSettingsActive();

View File

@ -1043,12 +1043,9 @@ bool savestate_save (const char *file_name)
{ {
EMUFILE_MEMORY ms; EMUFILE_MEMORY ms;
size_t elems_written; size_t elems_written;
#ifdef HAVE_LIBZ if (!savestate_save(ms))
if (!savestate_save(ms, Z_DEFAULT_COMPRESSION))
#else
if (!savestate_save(ms, 0))
#endif
return false; return false;
FILE* file = fopen(file_name,"wb"); FILE* file = fopen(file_name,"wb");
if(file) if(file)
{ {

View File

@ -21,6 +21,7 @@
#define _SRAM_H #define _SRAM_H
#include "types.h" #include "types.h"
#include "zlib.h"
#define NB_STATES 10 #define NB_STATES 10
@ -64,6 +65,6 @@ void savestate_slot(int num);
void loadstate_slot(int num); void loadstate_slot(int num);
bool savestate_load(class EMUFILE &is); bool savestate_load(class EMUFILE &is);
bool savestate_save(class EMUFILE &outstream, int compressionLevel); bool savestate_save(class EMUFILE &outstream, int compressionLevel = Z_DEFAULT_COMPRESSION);
#endif #endif