TOLTECS: Saving/loading is working; it still needs work but will suffice to make debugging somewhat easier.

This commit is contained in:
Benjamin Haisch 2008-08-12 08:49:53 +00:00 committed by Willem Jan Palenstijn
parent dd5567613f
commit 51214a461a
5 changed files with 233 additions and 34 deletions

View File

@ -154,6 +154,20 @@ void AnimationPlayer::saveState(Common::WriteStream *out) {
}
void AnimationPlayer::loadState(Common::ReadStream *in) {
_resIndex = in->readUint16LE();
_width = in->readUint16LE();
_height = in->readUint16LE();
_frameCount = in->readUint16LE();
_frameNumber = in->readUint16LE();
_keepFrameCounter = in->readUint32LE();
_curFrameSize = in->readUint32LE();
_nextFrameSize = in->readUint32LE();
_nextFrameOffset = in->readUint32LE();
_firstCurFrameSize = in->readUint32LE();
_firstNextFrameSize = in->readUint32LE();
_firstNextFrameOffset = in->readUint32LE();
}
} // End of namespace Toltecs

View File

@ -187,10 +187,30 @@ void Palette::saveState(Common::WriteStream *out) {
}
out->writeByte(_fragmentIndex);
}
void Palette::loadState(Common::ReadStream *in) {
// Save currently active palette
byte palette[768];
in->read(palette, 768);
setFullPalette(palette);
in->read(_mainPalette, 768);
in->read(_animPalette, 768);
in->read(_colorTransTable, 256);
uint16 fragmentCount = in->readUint16LE();
_fragments.clear();
for (uint16 i = 0; i < fragmentCount; i++) {
PaletteFragment fragment;
fragment.id = in->readUint16LE();
fragment.index = in->readByte();
fragment.count = in->readByte();
_fragments.push_back(fragment);
}
_fragmentIndex = in->readByte();
}

View File

@ -43,64 +43,61 @@
namespace Toltecs {
// TODO: Saveload is not working yet
/* TODO:
- Saveload is working so far but only one slot is supported until the game menu is implemented
- Save with F6; Load with F9
- Saving during an animation (AnimationPlayer) is not working correctly yet
- Maybe switch to SCUMM/Tinsel serialization approach?
*/
#define SAVEGAME_VERSION 0 // 0 is dev version until in official SVN
void ToltecsEngine::savegame(const char *filename) {
Common::OutSaveFile *out;
if (!(out = g_system->getSavefileManager()->openForSaving(filename))) {
warning("Can't create file '%s', game not saved", filename);
return;
}
// Save game variables
for (uint variable = 0; variable < 22; variable++) {
int16 value = _script->getGameVar(variable);
out->writeUint16LE(value);
}
out->writeUint32LE(SAVEGAME_VERSION);
out->writeUint16LE(_cameraX);
out->writeUint16LE(_cameraY);
out->writeUint16LE(_cameraHeight);
out->writeUint16LE(_guiHeight);
out->writeUint16LE(_sceneWidth);
out->writeUint16LE(_sceneHeight);
out->writeUint32LE(_sceneResIndex);
out->writeUint16LE(_walkSpeedX);
out->writeUint16LE(_walkSpeedY);
out->writeUint32LE(_counter01);
out->writeUint32LE(_counter02);
out->writeByte(_movieSceneFlag ? 1 : 0);
out->writeByte(_flag01);
_palette->saveState(out);
_script->saveState(out);
_anim->saveState(out);
// Save GUI
{
}
_screen->saveState(out);
/*
case 0: return "mouseDisabled";
case 1: return "mouseY";
case 2: return "mouseX";
case 3: return "mouseButton";
case 4: return "verbLineY";
case 5: return "verbLineX";
case 6: return "verbLineWidth";
case 7: return "verbLineCount";
case 8: return "verbLineNum";
case 9: return "talkTextItemNum";
case 10: return "talkTextY";
case 11: return "talkTextX";
case 12: return "talkTextFontColor";
case 13: return "cameraY";
case 14: return "cameraX";
case 15: return "walkSpeedY";
case 16: return "walkSpeedX";
case 17: return "flag01";
case 18: return "sceneResIndex";
case 19: return "cameraTop";
case 20: return "sceneHeight";
case 21: return "sceneWidth";
*/
/*
PersistentGameVarRef <offset _sceneHeight, 2>
PersistentGameVarRef <offset _sceneWidth, 2>
PersistentGameVarRef <offset screenFlag01, 2>
PersistentGameVarRef <offset currentSequenceResIndex, 4>
PersistentGameVarRef <offset currentSequenceLoopCount, 4>
PersistentGameVarRef <offset sequenceVolume, 4>
PersistentGameVarRef <offset dword_99AC0, 4>
PersistentGameVarRef <offset verbLineNum, 22h>
*/
delete out;
@ -108,7 +105,50 @@ PersistentGameVarRef <offset verbLineNum, 22h>
}
void ToltecsEngine::loadgame(const char *filename) {
Common::InSaveFile *in;
if (!(in = g_system->getSavefileManager()->openForLoading(filename))) {
warning("Can't open file '%s', game not loaded", filename);
return;
}
uint32 version = in->readUint32LE();
if (version != SAVEGAME_VERSION) {
warning("Savegame '%s' too old, game not loaded (got v%d, need v%d)", filename, version, SAVEGAME_VERSION);
return;
}
_cameraX = in->readUint16LE();
_cameraY = in->readUint16LE();
_cameraHeight = in->readUint16LE();
_guiHeight = in->readUint16LE();
_sceneWidth = in->readUint16LE();
_sceneHeight = in->readUint16LE();
_sceneResIndex = in->readUint32LE();
_walkSpeedX = in->readUint16LE();
_walkSpeedY = in->readUint16LE();
_counter01 = in->readUint32LE();
_counter02 = in->readUint32LE();
_movieSceneFlag = in->readByte() != 0;
_flag01 = in->readByte();
_palette->loadState(in);
_script->loadState(in);
_anim->loadState(in);
_screen->loadState(in);
delete in;
loadScene(_sceneResIndex);
_screen->clearSprites();
_newCameraX = _cameraX;
_newCameraY = _cameraY;
}
} // End of namespace Toltecs

View File

@ -964,13 +964,105 @@ void Screen::drawChar2(const Font &font, byte *dest, int16 x, int16 y, byte ch,
}
void Screen::saveState(Common::WriteStream *out) {
// Save verb line
out->writeUint16LE(_verbLineNum);
out->writeUint16LE(_verbLineX);
out->writeUint16LE(_verbLineY);
out->writeUint16LE(_verbLineWidth);
out->writeUint16LE(_verbLineCount);
for (int i = 0; i < 8; i++) {
out->writeUint16LE(_verbLineItems[i].slotIndex);
out->writeUint16LE(_verbLineItems[i].slotOffset);
}
// Save talk text items
out->writeUint16LE(_talkTextX);
out->writeUint16LE(_talkTextY);
out->writeUint16LE(_talkTextMaxWidth);
out->writeByte(_talkTextFontColor);
out->writeUint16LE(_talkTextItemNum);
for (int i = 0; i < 5; i++) {
out->writeUint16LE(_talkTextItems[i].duration);
out->writeUint16LE(_talkTextItems[i].slotIndex);
out->writeUint16LE(_talkTextItems[i].slotOffset);
out->writeUint16LE(_talkTextItems[i].fontNum);
out->writeByte(_talkTextItems[i].color);
out->writeByte(_talkTextItems[i].rectCount);
for (int j = 0; j < _talkTextItems[i].rectCount; j++) {
out->writeUint16LE(_talkTextItems[i].rects[j].x);
out->writeUint16LE(_talkTextItems[i].rects[j].y);
out->writeUint16LE(_talkTextItems[i].rects[j].width);
out->writeUint16LE(_talkTextItems[i].rects[j].length);
}
}
// Save GUI bitmap
{
byte *gui = _frontScreen + _vm->_cameraHeight * 640;
for (int i = 0; i < _vm->_guiHeight; i++) {
out->write(gui, 640);
gui += 640;
}
}
// Save fonts
for (int i = 0; i < 10; i++)
out->writeUint32LE(_fontResIndexArray[i]);
out->writeByte(_fontColor1);
out->writeByte(_fontColor2);
}
void Screen::loadState(Common::ReadStream *in) {
// Load verb line
_verbLineNum = in->readUint16LE();
_verbLineX = in->readUint16LE();
_verbLineY = in->readUint16LE();
_verbLineWidth = in->readUint16LE();
_verbLineCount = in->readUint16LE();
for (int i = 0; i < 8; i++) {
_verbLineItems[i].slotIndex = in->readUint16LE();
_verbLineItems[i].slotOffset = in->readUint16LE();
}
// Load talk text items
_talkTextX = in->readUint16LE();
_talkTextY = in->readUint16LE();
_talkTextMaxWidth = in->readUint16LE();
_talkTextFontColor = in->readByte();
_talkTextItemNum = in->readUint16LE();
for (int i = 0; i < 5; i++) {
_talkTextItems[i].duration = in->readUint16LE();
_talkTextItems[i].slotIndex = in->readUint16LE();
_talkTextItems[i].slotOffset = in->readUint16LE();
_talkTextItems[i].fontNum = in->readUint16LE();
_talkTextItems[i].color = in->readByte();
_talkTextItems[i].rectCount = in->readByte();
for (int j = 0; j < _talkTextItems[i].rectCount; j++) {
_talkTextItems[i].rects[j].x = in->readUint16LE();
_talkTextItems[i].rects[j].y = in->readUint16LE();
_talkTextItems[i].rects[j].width = in->readUint16LE();
_talkTextItems[i].rects[j].length = in->readUint16LE();
}
}
// Load GUI bitmap
{
byte *gui = _frontScreen + _vm->_cameraHeight * 640;
for (int i = 0; i < _vm->_guiHeight; i++) {
in->read(gui, 640);
gui += 640;
}
}
// Load fonts
for (int i = 0; i < 10; i++)
_fontResIndexArray[i] = in->readUint32LE();
_fontColor1 = in->readByte();
_fontColor2 = in->readByte();
}

View File

@ -1243,10 +1243,43 @@ void ScriptInterpreter::saveState(Common::WriteStream *out) {
// Save stack
out->write(_stack, kScriptStackSize);
out->writeUint16LE(_savedSp);
// Save IP
out->writeUint16LE((int16)(_code - getSlotData(_regs.reg4)));
}
void ScriptInterpreter::loadState(Common::ReadStream *in) {
// Load registers
_regs.reg0 = in->readUint16LE();
_regs.reg1 = in->readUint16LE();
_regs.reg2 = in->readUint16LE();
_regs.reg3 = in->readUint16LE();
_regs.reg4 = in->readUint16LE();
_regs.reg5 = in->readUint16LE();
_regs.reg6 = in->readUint16LE();
_regs.sp = in->readUint16LE();
_regs.reg8 = in->readUint16LE();
// Load slots
for (int slot = 0; slot < kMaxScriptSlots; slot++) {
_slots[slot].size = in->readUint32LE();
_slots[slot].resIndex = in->readUint16LE();
_slots[slot].data = NULL;
if (_slots[slot].size > 0) {
_slots[slot].data = new byte[_slots[slot].size];
in->read(_slots[slot].data, _slots[slot].size);
}
}
// Load stack
in->read(_stack, kScriptStackSize);
_savedSp = in->readUint16LE();
// Load IP
_code = getSlotData(_regs.reg4) + in->readUint16LE();
}
} // End of namespace Toltecs