Add function to load only screenshot from snapshot file

This commit is contained in:
OV2 2019-12-19 18:18:45 +01:00
parent 2e7a345dca
commit 3c2ef2aa21
2 changed files with 153 additions and 29 deletions

View File

@ -1069,26 +1069,9 @@ int S9xUnfreezeGameMem (const uint8 *buf, uint32 bufSize)
return result; return result;
} }
bool8 S9xUnfreezeGame (const char *filename) void S9xMessageFromResult(int result, const char* base)
{ {
STREAM stream = NULL; switch(result)
char drive[_MAX_DRIVE + 1], dir[_MAX_DIR + 1], def[_MAX_FNAME + 1], ext[_MAX_EXT + 1];
const char *base = S9xBasename(filename);
_splitpath(filename, drive, dir, def, ext);
S9xResetSaveTimer(!strcmp(ext, "oops") || !strcmp(ext, "oop") || !strcmp(ext, ".oops") || !strcmp(ext, ".oop"));
if (S9xOpenSnapshotFile(filename, TRUE, &stream))
{
int result;
result = S9xUnfreezeFromStream(stream);
S9xCloseSnapshotFile(stream);
if (result != SUCCESS)
{
switch (result)
{ {
case WRONG_FORMAT: case WRONG_FORMAT:
S9xMessage(S9X_ERROR, S9X_WRONG_FORMAT, SAVE_ERR_WRONG_FORMAT); S9xMessage(S9X_ERROR, S9X_WRONG_FORMAT, SAVE_ERR_WRONG_FORMAT);
@ -1116,7 +1099,28 @@ bool8 S9xUnfreezeGame (const char *filename)
S9xMessage(S9X_ERROR, S9X_ROM_NOT_FOUND, String); S9xMessage(S9X_ERROR, S9X_ROM_NOT_FOUND, String);
break; break;
} }
}
bool8 S9xUnfreezeGame (const char *filename)
{
STREAM stream = NULL;
char drive[_MAX_DRIVE + 1], dir[_MAX_DIR + 1], def[_MAX_FNAME + 1], ext[_MAX_EXT + 1];
const char *base = S9xBasename(filename);
_splitpath(filename, drive, dir, def, ext);
S9xResetSaveTimer(!strcmp(ext, "oops") || !strcmp(ext, "oop") || !strcmp(ext, ".oops") || !strcmp(ext, ".oop"));
if (S9xOpenSnapshotFile(filename, TRUE, &stream))
{
int result;
result = S9xUnfreezeFromStream(stream);
S9xCloseSnapshotFile(stream);
if (result != SUCCESS)
{
S9xMessageFromResult(result, base);
return (FALSE); return (FALSE);
} }
@ -1141,6 +1145,34 @@ bool8 S9xUnfreezeGame (const char *filename)
return (FALSE); return (FALSE);
} }
bool8 S9xUnfreezeScreenshot(const char *filename, uint16 **image_buffer, int &width, int &height)
{
STREAM stream = NULL;
const char *base = S9xBasename(filename);
if(S9xOpenSnapshotFile(filename, TRUE, &stream))
{
int result;
result = S9xUnfreezeScreenshotFromStream(stream, image_buffer, width, height);
S9xCloseSnapshotFile(stream);
if(result != SUCCESS)
{
S9xMessageFromResult(result, base);
return (FALSE);
}
return (TRUE);
}
sprintf(String, SAVE_ERR_SAVE_NOT_FOUND, base);
S9xMessage(S9X_INFO, S9X_FREEZE_FILE_INFO, String);
return (FALSE);
}
void S9xFreezeToStream (STREAM stream) void S9xFreezeToStream (STREAM stream)
{ {
char buffer[8192]; char buffer[8192];
@ -1801,6 +1833,96 @@ int S9xUnfreezeFromStream (STREAM stream)
return (result); return (result);
} }
// load screenshot from file, allocating memory for it
int S9xUnfreezeScreenshotFromStream(STREAM stream, uint16 **image_buffer, int &width, int &height)
{
int result = SUCCESS;
int version, len;
char buffer[PATH_MAX + 1];
len = strlen(SNAPSHOT_MAGIC) + 1 + 4 + 1;
if(READ_STREAM(buffer, len, stream) != (unsigned int)len)
return (WRONG_FORMAT);
if(strncmp(buffer, SNAPSHOT_MAGIC, strlen(SNAPSHOT_MAGIC)) != 0)
return (WRONG_FORMAT);
version = atoi(&buffer[strlen(SNAPSHOT_MAGIC) + 1]);
if(version > SNAPSHOT_VERSION)
return (WRONG_VERSION);
result = UnfreezeBlock(stream, "NAM", (uint8 *)buffer, PATH_MAX);
if(result != SUCCESS)
return (result);
uint8 *local_screenshot = NULL;
// skip all blocks until screenshot
SkipBlockWithName(stream, "CPU");
SkipBlockWithName(stream, "REG");
SkipBlockWithName(stream, "PPU");
SkipBlockWithName(stream, "DMA");
SkipBlockWithName(stream, "VRA");
SkipBlockWithName(stream, "RAM");
SkipBlockWithName(stream, "SRA");
SkipBlockWithName(stream, "FIL");
SkipBlockWithName(stream, "SND");
SkipBlockWithName(stream, "CTL");
SkipBlockWithName(stream, "TIM");
SkipBlockWithName(stream, "SFX");
SkipBlockWithName(stream, "SA1");
SkipBlockWithName(stream, "SAR");
SkipBlockWithName(stream, "DP1");
SkipBlockWithName(stream, "DP2");
SkipBlockWithName(stream, "DP4");
SkipBlockWithName(stream, "CX4");
SkipBlockWithName(stream, "ST0");
SkipBlockWithName(stream, "OBC");
SkipBlockWithName(stream, "OBM");
SkipBlockWithName(stream, "S71");
SkipBlockWithName(stream, "SRT");
SkipBlockWithName(stream, "CLK");
SkipBlockWithName(stream, "BSX");
SkipBlockWithName(stream, "MSU");
result = UnfreezeStructCopy(stream, "SHO", &local_screenshot, SnapScreenshot, COUNT(SnapScreenshot), version);
if(result == SUCCESS && local_screenshot)
{
SnapshotScreenshotInfo *ssi = new SnapshotScreenshotInfo;
UnfreezeStructFromCopy(ssi, SnapScreenshot, COUNT(SnapScreenshot), local_screenshot, version);
width = min(ssi->Width, IMAGE_WIDTH);
height = min(ssi->Height, IMAGE_HEIGHT);
*image_buffer = (uint16 *)malloc(width * height * sizeof(uint16));
uint8 *rowpix = ssi->Data;
uint16 *screen = (*image_buffer);
for(int y = 0; y < height; y++, screen += width)
{
for(int x = 0; x < width; x++)
{
uint32 r, g, b;
r = *(rowpix++);
g = *(rowpix++);
b = *(rowpix++);
screen[x] = BUILD_PIXEL(r, g, b);
}
}
delete ssi;
}
if(local_screenshot) delete[] local_screenshot;
return (result);
}
static int FreezeSize (int size, int type) static int FreezeSize (int size, int type)
{ {
switch (type) switch (type)

View File

@ -31,5 +31,7 @@ bool8 S9xUnfreezeGame (const char *);
int S9xUnfreezeGameMem (const uint8 *,uint32); int S9xUnfreezeGameMem (const uint8 *,uint32);
void S9xFreezeToStream (STREAM); void S9xFreezeToStream (STREAM);
int S9xUnfreezeFromStream (STREAM); int S9xUnfreezeFromStream (STREAM);
bool8 S9xUnfreezeScreenshot(const char *filename, uint16 **image_buffer, int &width, int &height);
int S9xUnfreezeScreenshotFromStream(STREAM stream, uint16 **image_buffer, int &width, int &height);
#endif #endif