diff options
author | Max Horn | 2006-02-11 22:45:04 +0000 |
---|---|---|
committer | Max Horn | 2006-02-11 22:45:04 +0000 |
commit | 26ee630756ebdd7c96bccede0881a8c8b98e8f2b (patch) | |
tree | 26e378d5cf990a2b81c2c96e9e683a7f333b62e8 /engines/lure/res.cpp | |
parent | 2a9a0d4211b1ea5723f1409d91cb95de8984429e (diff) | |
download | scummvm-rg350-26ee630756ebdd7c96bccede0881a8c8b98e8f2b.tar.gz scummvm-rg350-26ee630756ebdd7c96bccede0881a8c8b98e8f2b.tar.bz2 scummvm-rg350-26ee630756ebdd7c96bccede0881a8c8b98e8f2b.zip |
Moved engines to the new engines/ directory
svn-id: r20582
Diffstat (limited to 'engines/lure/res.cpp')
-rw-r--r-- | engines/lure/res.cpp | 399 |
1 files changed, 399 insertions, 0 deletions
diff --git a/engines/lure/res.cpp b/engines/lure/res.cpp new file mode 100644 index 0000000000..929b983f68 --- /dev/null +++ b/engines/lure/res.cpp @@ -0,0 +1,399 @@ +/* ScummVM - Scumm Interpreter + * Copyright (C) 2005-2006 The ScummVM project + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + * $URL$ + * $Id$ + * + */ + +#include "lure/res.h" +#include "lure/disk.h" +#include "lure/scripts.h" +#include "lure/screen.h" + +namespace Lure { + +static Resources *int_resources = NULL; + +Resources &Resources::getReference() { + return *int_resources; +} + +Resources::Resources() { + int_resources = this; + reloadData(); +} + +Resources::~Resources() { + // Delete any unremoved active hotspots + freeData(); +} + +void Resources::freeData() { + _activeHotspots.clear(); + _roomData.clear(); + _hotspotData.clear(); + _hotspotOverrides.clear(); + _animData.clear(); + _exitJoins.clear(); + _delayList.clear(); + + delete _paletteSubset; + delete _scriptData; + delete _script2Data; + delete _hotspotScriptData; + delete _messagesData; +} + +struct AnimRecordTemp { + uint16 *offset; + MovementDataList *list; +}; + +void Resources::reloadData() { + Disk &d = Disk::getReference(); + MemoryBlock *mb; + uint16 *offset, offsetVal; + int ctr; + + // Get the palette subset data + _paletteSubset = new Palette(ALT_PALETTE_RESOURCE_ID); + + // Load room data + mb = d.getEntry(ROOM_DATA_RESOURCE_ID); + offset = (uint16 *) mb->data(); + for (ctr = 0; READ_LE_UINT16(offset) != 0xffff; ++ctr, ++offset) { + offsetVal = READ_LE_UINT16(offset); + if (offsetVal != 0) { + // Get room resource + RoomResource *rec = (RoomResource *) (mb->data() + offsetVal); + RoomData *newEntry = new RoomData(rec); + _roomData.push_back(newEntry); + + if (rec->numExits > 0) { + RoomExitResource *exitRes = (RoomExitResource *) + (mb->data() + offsetVal + sizeof(RoomResource)); + + for (uint16 exitCtr = 0; exitCtr < rec->numExits; ++exitCtr, ++exitRes) { + RoomExitData *exit = new RoomExitData(exitRes); + newEntry->exits.push_back(exit); + } + } + } + } + delete mb; + + // Load room exits + mb = d.getEntry(ROOM_EXITS_RESOURCE_ID); + ctr = 0; + for (;;) { + offsetVal = READ_LE_UINT16(mb->data() + (ctr * 2)); + if (offsetVal == 0xffff) break; + + if (offsetVal != 0) { + RoomData *room = getRoom(ctr); + if (room) { + RoomExitHotspotRecord *re = (RoomExitHotspotRecord *) + (mb->data() + offsetVal); + while (READ_LE_UINT16(&re->hotspotId) != 0xffff) { + RoomExitHotspotData *newEntry = new RoomExitHotspotData(re); + room->exitHotspots.push_back(newEntry); + ++re; + } + } + } + ++ctr; + } + delete mb; + + // Load room joins + mb = d.getEntry(ROOM_EXIT_JOINS_RESOURCE_ID); + RoomExitJoinRecord *joinRec = (RoomExitJoinRecord *) mb->data(); + while (READ_LE_UINT16(&joinRec->hotspot1Id) != 0xffff) { + RoomExitJoinData *newEntry = new RoomExitJoinData(joinRec); + _exitJoins.push_back(newEntry); + ++joinRec; + } + delete mb; + + // Load the hotspot list + mb = d.getEntry(HOTSPOT_DATA_RESOURCE_ID); + HotspotResource *hsRec = (HotspotResource *) mb->data(); + while (READ_LE_UINT16(&hsRec->hotspotId) != 0xffff) { + HotspotData *newEntry = new HotspotData(hsRec); + _hotspotData.push_back(newEntry); + ++hsRec; + } + delete mb; + + // Load the hotspot overrides + mb = d.getEntry(HOTSPOT_OVERRIDE_DATA_RESOURCE_ID); + HotspotOverrideResource *hsoRec = (HotspotOverrideResource *) mb->data(); + while (READ_LE_UINT16(&hsoRec->hotspotId) != 0xffff) { + HotspotOverrideData *newEntry = new HotspotOverrideData(hsoRec); + _hotspotOverrides.push_back(newEntry); + ++hsoRec; + } + delete mb; + + // Load the animation list + mb = d.getEntry(ANIM_DATA_RESOURCE_ID); + HotspotAnimResource *animRec = (HotspotAnimResource *) mb->data(); + while (READ_LE_UINT16(&animRec->animRecordId) != 0xffff) { + HotspotAnimData *newEntry = new HotspotAnimData(animRec); + _animData.push_back(newEntry); + + // Handle any direction frames + AnimRecordTemp dirEntries[4] = { + {&animRec->leftOffset, &newEntry->leftFrames}, + {&animRec->rightOffset, &newEntry->rightFrames}, + {&animRec->upOffset, &newEntry->upFrames}, + {&animRec->downOffset, &newEntry->downFrames}}; + for (int dirCtr = 0; dirCtr < 4; ++dirCtr) { + offsetVal = READ_LE_UINT16(dirEntries[dirCtr].offset); + if (offsetVal != 0) { + MovementResource *moveRec = (MovementResource *) + (mb->data() + offsetVal); + while (READ_LE_UINT16(&moveRec->frameNumber) != 0xffff) { + MovementData *newMove = new MovementData(moveRec); + dirEntries[dirCtr].list->push_back(newMove); + ++moveRec; + } + } + } + + ++animRec; + } + delete mb; + + // Hotspot scripts + mb = d.getEntry(HOTSPOT_SCRIPT_LIST_RESOURCE_ID); + uint16 numEntries = mb->size() / 2; + uint16 *srcVal = (uint16 *) mb->data(); + uint16 *destVal = _hotspotScriptData = (uint16 *) + Memory::alloc(numEntries * sizeof(uint16)); + for (ctr = 0; ctr < numEntries; ++ctr, ++srcVal, ++destVal) { + *destVal = READ_LE_UINT16(srcVal); + } + delete mb; + + // Handle the hotspot action lists + mb = d.getEntry(ACTION_LIST_RESOURCE_ID); + uint16 *v = (uint16 *) mb->data(); + uint16 recordId; + while ((recordId = READ_LE_UINT16(v)) != 0xffff) { + ++v; + offsetVal = READ_LE_UINT16(v); + ++v; + + HotspotActionList *list = new HotspotActionList( + recordId, mb->data() + offsetVal); + _actionsList.push_back(list); + } + delete mb; + + _delayList.clear(); + + // Load miscellaneous data + _scriptData = d.getEntry(SCRIPT_DATA_RESOURCE_ID); + _script2Data = d.getEntry(SCRIPT2_DATA_RESOURCE_ID); + _messagesData = d.getEntry(MESSAGES_LIST_RESOURCE_ID); +} + +RoomExitJoinData *Resources::getExitJoin(uint16 hotspotId) { + RoomExitJoinList::iterator i; + + for (i = _exitJoins.begin(); i != _exitJoins.end(); ++i) { + RoomExitJoinData *rec = *i; + if ((rec->hotspot1Id == hotspotId) || (rec->hotspot2Id == hotspotId)) + return rec; + } + + return NULL; +} + +uint16 Resources::getHotspotScript(uint16 index) { + return _hotspotScriptData[index]; +} + +RoomData *Resources::getRoom(uint16 roomNumber) { + RoomDataList::iterator i; + + for (i = _roomData.begin(); i != _roomData.end(); ++i) { + RoomData *rec = *i; + if (rec->roomNumber == roomNumber) return rec; + ++rec; + } + + return NULL; +} + +void Resources::insertPaletteSubset(Palette &p) { + p.palette()->copyFrom(_paletteSubset->palette(), 0, 129*4, 60*4); + p.palette()->copyFrom(_paletteSubset->palette(), 60*4, 220*4, 8*4); +} + +HotspotData *Resources::getHotspot(uint16 hotspotId) { + HotspotDataList::iterator i; + + for (i = _hotspotData.begin(); i != _hotspotData.end(); ++i) { + HotspotData *rec = *i; + if (rec->hotspotId == hotspotId) return rec; + } + + return NULL; +} + +Hotspot *Resources::getActiveHotspot(uint16 hotspotId) { + HotspotList::iterator i; + + for (i = _activeHotspots.begin(); i != _activeHotspots.end(); ++i) { + Hotspot *rec = *i; + if (rec->hotspotId() == hotspotId) return rec; + } + + return NULL; +} + + +HotspotOverrideData *Resources::getHotspotOverride(uint16 hotspotId) { + HotspotOverrideList::iterator i; + + for (i = _hotspotOverrides.begin(); i != _hotspotOverrides.end(); ++i) { + HotspotOverrideData *rec = *i; + if (rec->hotspotId == hotspotId) return rec; + } + + return NULL; +} + +HotspotAnimData *Resources::getAnimation(uint16 animRecordId) { + HotspotAnimList::iterator i; + + for (i = _animData.begin(); i != _animData.end(); ++i) { + HotspotAnimData *rec = *i; + if (rec->animRecordId == animRecordId) return rec; + } + + return NULL; +} + +uint16 Resources::getHotspotAction(uint16 actionsOffset, Action action) { + HotspotActionList *list = _actionsList.getActions(actionsOffset); + if (!list) return 0; + return list->getActionOffset(action); +} + +HotspotActionList *Resources::getHotspotActions(uint16 actionsOffset) { + return _actionsList.getActions(actionsOffset); +} + +void Resources::activateHotspot(uint16 hotspotId) { + HotspotData *res = getHotspot(hotspotId); + if (!res) return; + res->roomNumber &= 0x7fff; // clear any suppression bit in room # + + // Make sure that the hotspot isn't already active + HotspotList::iterator i = _activeHotspots.begin(); + bool found = false; + + for (; i != _activeHotspots.end(); ++i) { + Hotspot &h = *i.operator*(); + if (h.hotspotId() == res->hotspotId) { + found = true; + break; + } + } + if (found) return; + + // Check the script load flag + if (res->scriptLoadFlag) { + // Execute a script rather than doing a standard load + Script::execute(res->loadOffset); + } else { + // Standard load + bool loadFlag = true; + + switch (res->loadOffset) { + case 0x3afe: + // Copy protection check - since the game is freeware now, + // don't bother with it + loadFlag = false; + break; + + case 0x41BD: + // Empty handler used to prevent loading hotspots that + // are yet to be active (such as the straw fire) + loadFlag = false; + break; + + case 0x7172: + case 0x7167: + // Standard animation load + break; + + case 0x88ac: + // Torch in room #1 + loadFlag = _fieldList.getField(TORCH_HIDE) == 0; + break; + + default: + // All others simply activate the hotspot + warning("Hotspot %d uses unknown load offset proc %d", + res->hotspotId, res->loadOffset); + } + + if (loadFlag) { + Hotspot *hotspot = addHotspot(hotspotId); +// if (res->loadOffset == 0x7167) hotspot->setPersistant(true); + // DEBUG - for now only keep certain hotspots active + hotspot->setPersistant((res->hotspotId >= 0x3e8) && (res->hotspotId <= 0x3ea)); + } + } +} + +Hotspot *Resources::addHotspot(uint16 hotspotId) { + Hotspot *hotspot = new Hotspot(getHotspot(hotspotId)); + _activeHotspots.push_back(hotspot); + return hotspot; +} + +void Resources::deactivateHotspot(uint16 hotspotId) { + HotspotList::iterator i = _activeHotspots.begin(); + + while (i != _activeHotspots.end()) { + Hotspot *h = *i; + if (h->hotspotId() == hotspotId) + i = _activeHotspots.erase(i); + else + i++; + } +} + +uint16 Resources::numInventoryItems() { + uint16 numItems = 0; + HotspotDataList &list = _hotspotData; + HotspotDataList::iterator i; + for (i = list.begin(); i != list.end(); ++i) { + HotspotData *rec = *i; + if (rec->roomNumber == PLAYER_ID) ++numItems; + } + + return numItems; +} + +} // end of namespace Lure |