2004-12-16 12:49:25 +00:00
|
|
|
/* ScummVM - Scumm Interpreter
|
2006-05-05 00:42:37 +00:00
|
|
|
* Copyright (C) 2001 Ludvig Strigeus
|
2006-01-18 17:39:49 +00:00
|
|
|
* Copyright (C) 2001-2006 The ScummVM project
|
2004-12-16 12:49:25 +00:00
|
|
|
*
|
|
|
|
* 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
|
2005-10-18 01:30:26 +00:00
|
|
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
2004-12-16 12:49:25 +00:00
|
|
|
*
|
2006-02-11 12:46:41 +00:00
|
|
|
* $URL$
|
|
|
|
* $Id$
|
2004-12-16 12:49:25 +00:00
|
|
|
*
|
|
|
|
*/
|
|
|
|
|
2005-06-24 15:23:51 +00:00
|
|
|
#include "common/stdafx.h"
|
2004-12-16 12:49:25 +00:00
|
|
|
|
|
|
|
#include "common/file.h"
|
|
|
|
|
2006-09-29 08:14:27 +00:00
|
|
|
#include "agos/agos.h"
|
2004-12-16 12:49:25 +00:00
|
|
|
|
2006-09-29 09:44:30 +00:00
|
|
|
namespace AGOS {
|
2004-12-16 12:49:25 +00:00
|
|
|
|
2006-09-29 09:44:30 +00:00
|
|
|
void AGOSEngine::loadIconFile() {
|
2005-05-10 22:56:25 +00:00
|
|
|
Common::File in;
|
2004-12-16 12:49:25 +00:00
|
|
|
uint size;
|
|
|
|
|
2006-04-22 02:14:42 +00:00
|
|
|
in.open(getFileName(GAME_ICONFILE));
|
2004-12-16 12:49:25 +00:00
|
|
|
if (in.isOpen() == false)
|
2006-04-22 02:14:42 +00:00
|
|
|
error("Can't open icons file '%s'", getFileName(GAME_ICONFILE));
|
2004-12-16 12:49:25 +00:00
|
|
|
|
|
|
|
size = in.size();
|
|
|
|
|
2005-05-06 11:37:33 +00:00
|
|
|
_iconFilePtr = (byte *)malloc(size);
|
|
|
|
if (_iconFilePtr == NULL)
|
2004-12-16 12:49:25 +00:00
|
|
|
error("Out of icon memory");
|
|
|
|
|
2005-05-06 11:37:33 +00:00
|
|
|
in.read(_iconFilePtr, size);
|
2004-12-16 12:49:25 +00:00
|
|
|
in.close();
|
|
|
|
}
|
|
|
|
|
2006-09-29 09:44:30 +00:00
|
|
|
void AGOSEngine::loadIconData() {
|
2006-04-03 14:40:07 +00:00
|
|
|
loadZone(8);
|
|
|
|
VgaPointersEntry *vpe = &_vgaBufferPointers[8];
|
2006-04-04 06:25:50 +00:00
|
|
|
|
2006-05-03 04:39:31 +00:00
|
|
|
byte *src = vpe->vgaFile2 + READ_LE_UINT32(vpe->vgaFile2 + 8);
|
2006-04-03 14:40:07 +00:00
|
|
|
|
|
|
|
_iconFilePtr = (byte *)malloc(43 * 336);
|
|
|
|
if (_iconFilePtr == NULL)
|
|
|
|
error("Out of icon memory");
|
|
|
|
|
|
|
|
memcpy(_iconFilePtr, src, 43 * 336);
|
2007-04-15 12:04:47 +00:00
|
|
|
unfreezeBottom();
|
2006-04-03 14:40:07 +00:00
|
|
|
}
|
|
|
|
|
2004-12-16 12:49:25 +00:00
|
|
|
// Thanks to Stuart Caie for providing the original
|
|
|
|
// C conversion upon which this function is based.
|
2007-05-07 13:40:29 +00:00
|
|
|
static void decompressIconPlanar(byte *dst, byte *src, uint width, uint height, byte base, uint pitch, bool decompress = true) {
|
2004-12-16 12:49:25 +00:00
|
|
|
byte icon_pln[288];
|
2006-10-13 02:22:33 +00:00
|
|
|
byte *i, *o, *srcPtr, x, y;
|
|
|
|
|
|
|
|
srcPtr = src;
|
|
|
|
if (decompress) {
|
|
|
|
// Decode RLE planar icon data
|
|
|
|
i = src;
|
|
|
|
o = icon_pln;
|
2007-05-17 09:02:01 +00:00
|
|
|
while (o < &icon_pln[288]) {
|
2006-10-13 02:22:33 +00:00
|
|
|
x = *i++;
|
|
|
|
if (x < 128) {
|
|
|
|
do {
|
|
|
|
*o++ = *i++;
|
|
|
|
*o++ = *i++;
|
|
|
|
*o++ = *i++;
|
|
|
|
} while (x-- > 0);
|
|
|
|
} else {
|
|
|
|
x = 256 - x;
|
|
|
|
do {
|
|
|
|
*o++ = i[0];
|
|
|
|
*o++ = i[1];
|
|
|
|
*o++ = i[2];
|
|
|
|
} while (x-- > 0);
|
|
|
|
i += 3;
|
|
|
|
}
|
2004-12-16 12:49:25 +00:00
|
|
|
}
|
2006-10-13 02:22:33 +00:00
|
|
|
srcPtr = icon_pln;
|
2004-12-16 12:49:25 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// Translate planar data to chunky (very slow method)
|
2007-05-17 09:02:01 +00:00
|
|
|
for (y = 0; y < 24; y++) {
|
|
|
|
for (x = 0; x < 24; x++) {
|
2004-12-16 12:49:25 +00:00
|
|
|
byte pixel =
|
2007-05-17 09:02:01 +00:00
|
|
|
(srcPtr[(( y) * 3) + (x >> 3)] & (1 << (7 - (x & 7))) ? 1 : 0)
|
|
|
|
| (srcPtr[((24 + y) * 3) + (x >> 3)] & (1 << (7 - (x & 7))) ? 2 : 0)
|
|
|
|
| (srcPtr[((48 + y) * 3) + (x >> 3)] & (1 << (7 - (x & 7))) ? 4 : 0)
|
|
|
|
| (srcPtr[((72 + y) * 3) + (x >> 3)] & (1 << (7 - (x & 7))) ? 8 : 0);
|
2004-12-16 12:49:25 +00:00
|
|
|
if (pixel)
|
|
|
|
dst[x] = pixel | base;
|
|
|
|
}
|
|
|
|
dst += pitch;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2006-10-17 00:38:04 +00:00
|
|
|
static void decompressIcon(byte *dst, byte *src, uint width, uint height, byte base, uint pitch) {
|
2004-12-16 12:49:25 +00:00
|
|
|
int8 reps;
|
|
|
|
byte color_1, color_2;
|
|
|
|
byte *dst_org = dst;
|
2006-10-17 00:38:04 +00:00
|
|
|
uint h = height;
|
2004-12-16 12:49:25 +00:00
|
|
|
|
|
|
|
for (;;) {
|
|
|
|
reps = *src++;
|
|
|
|
if (reps < 0) {
|
|
|
|
reps--;
|
|
|
|
color_1 = *src >> 4;
|
|
|
|
if (color_1 != 0)
|
|
|
|
color_1 |= base;
|
|
|
|
color_2 = *src++ & 0xF;
|
|
|
|
if (color_2 != 0)
|
|
|
|
color_2 |= base;
|
|
|
|
|
|
|
|
do {
|
|
|
|
if (color_1 != 0)
|
|
|
|
*dst = color_1;
|
|
|
|
dst += pitch;
|
|
|
|
if (color_2 != 0)
|
|
|
|
*dst = color_2;
|
|
|
|
dst += pitch;
|
|
|
|
|
|
|
|
// reached bottom?
|
|
|
|
if (--h == 0) {
|
|
|
|
// reached right edge?
|
2006-10-17 00:38:04 +00:00
|
|
|
if (--width == 0)
|
2004-12-16 12:49:25 +00:00
|
|
|
return;
|
|
|
|
dst = ++dst_org;
|
2006-10-17 00:38:04 +00:00
|
|
|
h = height;
|
2004-12-16 12:49:25 +00:00
|
|
|
}
|
|
|
|
} while (++reps != 0);
|
|
|
|
} else {
|
|
|
|
do {
|
|
|
|
color_1 = *src >> 4;
|
|
|
|
if (color_1 != 0)
|
|
|
|
*dst = color_1 | base;
|
|
|
|
dst += pitch;
|
|
|
|
|
|
|
|
color_2 = *src++ & 0xF;
|
|
|
|
if (color_2 != 0)
|
|
|
|
*dst = color_2 | base;
|
|
|
|
dst += pitch;
|
|
|
|
|
|
|
|
// reached bottom?
|
|
|
|
if (--h == 0) {
|
|
|
|
// reached right edge?
|
2006-10-17 00:38:04 +00:00
|
|
|
if (--width == 0)
|
2004-12-16 12:49:25 +00:00
|
|
|
return;
|
|
|
|
dst = ++dst_org;
|
2006-10-17 00:38:04 +00:00
|
|
|
h = height;
|
2004-12-16 12:49:25 +00:00
|
|
|
}
|
|
|
|
} while (--reps >= 0);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
void AGOSEngine_Simon2::drawIcon(WindowBlock *window, uint icon, uint x, uint y) {
|
2004-12-16 12:49:25 +00:00
|
|
|
byte *dst;
|
|
|
|
byte *src;
|
|
|
|
|
2005-05-06 11:37:33 +00:00
|
|
|
_lockWord |= 0x8000;
|
2006-03-22 13:54:26 +00:00
|
|
|
dst = getFrontBuf();
|
2004-12-16 12:49:25 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
dst += 110;
|
|
|
|
dst += x;
|
|
|
|
dst += (y + window->y) * _dxSurfacePitch;
|
2006-10-10 13:08:27 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
src = _iconFilePtr;
|
|
|
|
src += READ_LE_UINT16(&((uint16 *)src)[icon * 2 + 0]);
|
|
|
|
decompressIcon(dst, src, 20, 10, 224, _dxSurfacePitch);
|
2006-10-10 13:08:27 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
src = _iconFilePtr;
|
|
|
|
src += READ_LE_UINT16(&((uint16 *)src)[icon * 2 + 1]);
|
|
|
|
decompressIcon(dst, src, 20, 10, 208, _dxSurfacePitch);
|
2006-10-17 00:38:04 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
_lockWord &= ~0x8000;
|
|
|
|
}
|
2006-10-17 00:38:04 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
void AGOSEngine_Simon1::drawIcon(WindowBlock *window, uint icon, uint x, uint y) {
|
|
|
|
byte *dst;
|
|
|
|
byte *src;
|
2006-10-13 11:38:41 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
_lockWord |= 0x8000;
|
|
|
|
dst = getFrontBuf();
|
2006-10-17 00:38:04 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
dst += (x + window->x) * 8;
|
|
|
|
dst += (y * 25 + window->y) * _dxSurfacePitch;
|
2006-10-13 02:22:33 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
if (getPlatform() == Common::kPlatformAmiga) {
|
2006-10-13 02:22:33 +00:00
|
|
|
src = _iconFilePtr;
|
2007-05-07 01:11:10 +00:00
|
|
|
src += READ_BE_UINT32(&((uint32 *)src)[icon]);
|
|
|
|
uint8 color = (getFeatures() & GF_32COLOR) ? 16 : 240;
|
2007-05-07 13:40:29 +00:00
|
|
|
decompressIconPlanar(dst, src, 24, 24, color, _dxSurfacePitch);
|
2007-05-07 01:11:10 +00:00
|
|
|
} else {
|
|
|
|
src = _iconFilePtr;
|
|
|
|
src += READ_LE_UINT16(&((uint16 *)src)[icon]);
|
2007-05-17 09:02:01 +00:00
|
|
|
decompressIcon(dst, src, 24, 12, 224, _dxSurfacePitch);
|
2004-12-16 12:49:25 +00:00
|
|
|
}
|
|
|
|
|
2005-05-06 11:37:33 +00:00
|
|
|
_lockWord &= ~0x8000;
|
2004-12-16 12:49:25 +00:00
|
|
|
}
|
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
void AGOSEngine_Waxworks::drawIcon(WindowBlock *window, uint icon, uint x, uint y) {
|
|
|
|
byte *dst;
|
|
|
|
byte *src;
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
_lockWord |= 0x8000;
|
|
|
|
dst = getFrontBuf();
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
dst += (x + window->x) * 8;
|
|
|
|
dst += (y * 20 + window->y) * _dxSurfacePitch;
|
|
|
|
|
|
|
|
uint8 color = dst[0] & 0xF0;
|
|
|
|
if (getPlatform() == Common::kPlatformAmiga) {
|
2007-05-16 13:00:38 +00:00
|
|
|
// TODO
|
2007-05-17 09:02:01 +00:00
|
|
|
return;
|
2006-10-17 00:38:04 +00:00
|
|
|
} else {
|
2007-05-07 01:11:10 +00:00
|
|
|
src = _iconFilePtr;
|
|
|
|
src += READ_LE_UINT16(&((uint16 *)src)[icon]);
|
|
|
|
decompressIcon(dst, src, 24, 10, color, _dxSurfacePitch);
|
2006-04-06 00:54:26 +00:00
|
|
|
}
|
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
_lockWord &= ~0x8000;
|
|
|
|
}
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
void AGOSEngine_Elvira2::drawIcon(WindowBlock *window, uint icon, uint x, uint y) {
|
|
|
|
byte *dst;
|
|
|
|
byte *src;
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
_lockWord |= 0x8000;
|
|
|
|
dst = getFrontBuf();
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
dst += (x + window->x) * 8;
|
|
|
|
dst += (y * 8 + window->y) * _dxSurfacePitch;
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
uint color = dst[0] & 0xF0;
|
2007-05-07 13:40:29 +00:00
|
|
|
if (getFeatures() & GF_PLANAR) {
|
2007-05-07 01:11:10 +00:00
|
|
|
src = _iconFilePtr;
|
|
|
|
src += READ_BE_UINT32(&((uint32 *)src)[icon]);
|
2007-05-07 13:40:29 +00:00
|
|
|
decompressIconPlanar(dst, src, 24, 24, color, _dxSurfacePitch);
|
2007-05-07 01:11:10 +00:00
|
|
|
} else {
|
|
|
|
src = _iconFilePtr;
|
|
|
|
src += READ_LE_UINT16(&((uint16 *)src)[icon]);
|
2007-05-17 09:02:01 +00:00
|
|
|
decompressIcon(dst, src, 24, 12, color, _dxSurfacePitch);
|
2007-05-07 13:40:29 +00:00
|
|
|
}
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
_lockWord &= ~0x8000;
|
|
|
|
}
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
void AGOSEngine::drawIcon(WindowBlock *window, uint icon, uint x, uint y) {
|
|
|
|
byte *dst;
|
|
|
|
byte *src;
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
_lockWord |= 0x8000;
|
|
|
|
dst = getFrontBuf();
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
dst += (x + window->x) * 8;
|
|
|
|
dst += (y * 8 + window->y) * _dxSurfacePitch;
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 13:40:29 +00:00
|
|
|
if (getFeatures() & GF_PLANAR) {
|
2007-05-16 10:03:02 +00:00
|
|
|
src = _iconFilePtr;
|
|
|
|
src += READ_BE_UINT16(&((uint16 *)src)[icon]);
|
|
|
|
decompressIconPlanar(dst, src, 24, 24, 16, _dxSurfacePitch);
|
2007-05-07 13:40:29 +00:00
|
|
|
} else {
|
|
|
|
src = _iconFilePtr;
|
|
|
|
src += icon * 288;
|
|
|
|
decompressIconPlanar(dst, src, 24, 24, 16, _dxSurfacePitch, false);
|
|
|
|
}
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
_lockWord &= ~0x8000;
|
2006-04-06 00:54:26 +00:00
|
|
|
}
|
|
|
|
|
2007-04-15 05:04:48 +00:00
|
|
|
void AGOSEngine_Feeble::drawIconArray(uint num, Item *itemRef, int line, int classMask) {
|
2006-04-06 00:54:26 +00:00
|
|
|
Item *item_ptr_org = itemRef;
|
|
|
|
WindowBlock *window;
|
|
|
|
uint16 flagnumber = 201;
|
|
|
|
uint16 iconperline = 458;
|
|
|
|
uint16 iconsdown = 384;
|
|
|
|
uint16 idone = 0;
|
|
|
|
uint16 icount = 0;
|
|
|
|
uint16 xp = 188, yp = 306;
|
|
|
|
int k;
|
|
|
|
_iOverflow = 0;
|
|
|
|
|
|
|
|
line = _variableArray[30];
|
|
|
|
if (line == 0)
|
|
|
|
_variableArray[31] = 0;
|
|
|
|
|
|
|
|
window = _windowArray[num & 7];
|
|
|
|
if (window == NULL)
|
|
|
|
return;
|
|
|
|
|
|
|
|
for (k = flagnumber; k <= flagnumber + 18; k++)
|
|
|
|
_variableArray[k] = 0;
|
|
|
|
|
|
|
|
if (window->iconPtr)
|
|
|
|
removeIconArray(num);
|
|
|
|
|
|
|
|
window->iconPtr=(IconBlock *)malloc(sizeof(IconBlock));
|
|
|
|
window->iconPtr->itemRef = itemRef;
|
|
|
|
window->iconPtr->upArrow = -1;
|
|
|
|
window->iconPtr->downArrow = -1;
|
|
|
|
window->iconPtr->line = line;
|
|
|
|
window->iconPtr->classMask = classMask;
|
|
|
|
|
|
|
|
itemRef = derefItem(itemRef->child);
|
|
|
|
k = flagnumber;
|
|
|
|
|
|
|
|
while (itemRef && (line > 65)) {
|
|
|
|
uint16 ct = xp;
|
|
|
|
while (itemRef && ct < iconperline) {
|
|
|
|
if ((classMask == 0) || ((itemRef->classFlags & classMask) != 0)) {
|
2006-10-23 05:58:53 +00:00
|
|
|
if (hasIcon(itemRef)) {
|
2006-04-06 00:54:26 +00:00
|
|
|
ct += 45;
|
|
|
|
k++;
|
|
|
|
}
|
|
|
|
}
|
2006-10-06 14:44:39 +00:00
|
|
|
itemRef = derefItem(itemRef->next);
|
2006-04-06 00:54:26 +00:00
|
|
|
}
|
|
|
|
line -= 52;
|
|
|
|
if (k == (flagnumber + 18))
|
|
|
|
k = flagnumber;
|
|
|
|
}
|
|
|
|
yp -= line; // Adjust starting y
|
|
|
|
|
|
|
|
if (itemRef == NULL) {
|
|
|
|
window->iconPtr->line = 0;
|
|
|
|
itemRef = derefItem(item_ptr_org->child);
|
|
|
|
}
|
|
|
|
|
|
|
|
while (itemRef) {
|
|
|
|
if ((classMask != 0) && ((itemRef->classFlags & classMask) == 0))
|
|
|
|
goto l1;
|
2006-10-23 05:58:53 +00:00
|
|
|
if (hasIcon(itemRef) == 0)
|
2006-04-06 00:54:26 +00:00
|
|
|
goto l1;
|
|
|
|
if (!idone) {
|
|
|
|
/*
|
|
|
|
* Create thee icon and graphics rendering
|
|
|
|
*/
|
|
|
|
window->iconPtr->iconArray[icount].item = itemRef;
|
|
|
|
_variableArray[k] = itemGetIconNumber(itemRef);
|
|
|
|
window->iconPtr->iconArray[icount++].boxCode =
|
|
|
|
setupIconHitArea(window, k++, xp, yp, itemRef);
|
|
|
|
} else {
|
|
|
|
/*
|
|
|
|
* Just remember the overflow has occured
|
|
|
|
*/
|
|
|
|
window->iconPtr->iconArray[icount].item = NULL; /* END MARKINGS */
|
|
|
|
_iOverflow = 1;
|
|
|
|
}
|
|
|
|
xp += 45;
|
|
|
|
if (xp >= iconperline) { /* End of line ? */
|
|
|
|
if (k == (flagnumber + 18))
|
|
|
|
k = flagnumber;
|
|
|
|
xp = 188;
|
|
|
|
yp += 52; /* Move down */
|
|
|
|
if (yp >= iconsdown) { /* Full ? */
|
|
|
|
idone = 1; /* Note completed screen */
|
|
|
|
}
|
|
|
|
}
|
2006-10-06 14:44:39 +00:00
|
|
|
l1:; itemRef = derefItem(itemRef->next);
|
2006-04-06 00:54:26 +00:00
|
|
|
}
|
|
|
|
window->iconPtr->iconArray[icount].item = NULL; /* END MARKINGS */
|
|
|
|
if (_variableArray[30] == 0) {
|
|
|
|
if (yp != 306)
|
|
|
|
_variableArray[31] = 52;
|
|
|
|
if ((xp == 188) && (yp == 358))
|
|
|
|
_variableArray[31] = 0;
|
|
|
|
}
|
|
|
|
|
2006-04-08 12:06:52 +00:00
|
|
|
/* Plot arrows and add their boxes */
|
2006-10-23 11:13:51 +00:00
|
|
|
addArrows(window);
|
2006-04-06 00:54:26 +00:00
|
|
|
window->iconPtr->upArrow = _scrollUpHitArea;
|
|
|
|
window->iconPtr->downArrow = _scrollDownHitArea;
|
|
|
|
}
|
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
void AGOSEngine::drawIconArray(uint num, Item *itemRef, int line, int classMask) {
|
|
|
|
Item *item_ptr_org = itemRef;
|
|
|
|
WindowBlock *window;
|
|
|
|
uint width, height;
|
|
|
|
uint k, i, curWidth;
|
|
|
|
bool item_again, showArrows;
|
|
|
|
uint x_pos, y_pos;
|
|
|
|
const int iconSize = (getGameType() == GType_SIMON2) ? 20 : 1;
|
2006-10-23 11:13:51 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
window = _windowArray[num & 7];
|
2006-10-23 11:13:51 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
if (getGameType() == GType_SIMON2) {
|
|
|
|
width = 100;
|
|
|
|
height = 40;
|
2007-05-07 06:30:51 +00:00
|
|
|
} else if (getGameType() == GType_WW) {
|
|
|
|
width = window->width / 3;
|
|
|
|
height = window->height / 2;
|
2007-05-07 01:11:10 +00:00
|
|
|
} else {
|
|
|
|
width = window->width / 3;
|
|
|
|
height = window->height / 3;
|
|
|
|
}
|
|
|
|
|
|
|
|
i = 0;
|
|
|
|
|
|
|
|
if (window == NULL)
|
|
|
|
return;
|
|
|
|
|
|
|
|
if (window->iconPtr)
|
|
|
|
removeIconArray(num);
|
|
|
|
|
|
|
|
window->iconPtr = (IconBlock *) malloc(sizeof(IconBlock));
|
|
|
|
window->iconPtr->itemRef = itemRef;
|
|
|
|
window->iconPtr->upArrow = -1;
|
|
|
|
window->iconPtr->downArrow = -1;
|
|
|
|
window->iconPtr->line = line;
|
|
|
|
window->iconPtr->classMask = classMask;
|
|
|
|
|
|
|
|
itemRef = derefItem(itemRef->child);
|
|
|
|
|
|
|
|
while (itemRef && line-- != 0) {
|
|
|
|
curWidth = 0;
|
|
|
|
while (itemRef && width > curWidth) {
|
|
|
|
if ((classMask == 0 || itemRef->classFlags & classMask) && hasIcon(itemRef))
|
|
|
|
curWidth += iconSize;
|
|
|
|
itemRef = derefItem(itemRef->next);
|
2006-10-23 11:13:51 +00:00
|
|
|
}
|
2007-05-07 01:11:10 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
if (itemRef == NULL) {
|
|
|
|
window->iconPtr->line = 0;
|
|
|
|
itemRef = derefItem(item_ptr_org->child);
|
|
|
|
}
|
|
|
|
|
|
|
|
x_pos = 0;
|
|
|
|
y_pos = 0;
|
|
|
|
k = 0;
|
|
|
|
item_again = false;
|
|
|
|
showArrows = false;
|
|
|
|
|
|
|
|
while (itemRef) {
|
|
|
|
if ((classMask == 0 || itemRef->classFlags & classMask) && hasIcon(itemRef)) {
|
|
|
|
if (item_again == false) {
|
|
|
|
window->iconPtr->iconArray[k].item = itemRef;
|
|
|
|
if (getGameType() == GType_SIMON2) {
|
|
|
|
drawIcon(window, itemGetIconNumber(itemRef), x_pos, y_pos);
|
|
|
|
window->iconPtr->iconArray[k].boxCode =
|
|
|
|
setupIconHitArea(window, 0, x_pos, y_pos, itemRef);
|
2007-05-07 06:30:51 +00:00
|
|
|
} else if (getGameType() == GType_SIMON1 || getGameType() == GType_WW) {
|
2007-05-07 01:11:10 +00:00
|
|
|
drawIcon(window, itemGetIconNumber(itemRef), x_pos * 3, y_pos);
|
|
|
|
window->iconPtr->iconArray[k].boxCode =
|
|
|
|
setupIconHitArea(window, 0, x_pos * 3, y_pos, itemRef);
|
|
|
|
} else {
|
|
|
|
drawIcon(window, itemGetIconNumber(itemRef), x_pos * 3, y_pos * 3);
|
|
|
|
window->iconPtr->iconArray[k].boxCode =
|
|
|
|
setupIconHitArea(window, 0, x_pos * 3, y_pos * 3, itemRef);
|
|
|
|
}
|
|
|
|
k++;
|
|
|
|
} else {
|
|
|
|
window->iconPtr->iconArray[k].item = NULL;
|
|
|
|
showArrows = 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
x_pos += iconSize;
|
|
|
|
if (x_pos >= width) {
|
|
|
|
x_pos = 0;
|
|
|
|
y_pos += iconSize;
|
|
|
|
if (y_pos >= height)
|
|
|
|
item_again = true;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
itemRef = derefItem(itemRef->next);
|
|
|
|
}
|
|
|
|
|
|
|
|
window->iconPtr->iconArray[k].item = NULL;
|
|
|
|
|
|
|
|
if (showArrows != 0 || window->iconPtr->line != 0) {
|
|
|
|
/* Plot arrows and add their boxes */
|
|
|
|
addArrows(window);
|
|
|
|
window->iconPtr->upArrow = _scrollUpHitArea;
|
|
|
|
window->iconPtr->downArrow = _scrollDownHitArea;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
uint AGOSEngine_Feeble::setupIconHitArea(WindowBlock *window, uint num, uint x, uint y, Item *item_ptr) {
|
|
|
|
HitArea *ha = findEmptyHitArea();
|
|
|
|
|
|
|
|
ha->x = x;
|
|
|
|
ha->y = y;
|
|
|
|
ha->item_ptr = item_ptr;
|
|
|
|
ha->width = 45;
|
|
|
|
ha->height = 44;
|
|
|
|
ha->flags = kBFBoxInUse | kBFBoxItem;
|
|
|
|
ha->id = num;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->verb = 208;
|
|
|
|
|
|
|
|
return ha - _hitAreas;
|
|
|
|
}
|
|
|
|
|
|
|
|
uint AGOSEngine_Simon2::setupIconHitArea(WindowBlock *window, uint num, uint x, uint y, Item *item_ptr) {
|
|
|
|
HitArea *ha = findEmptyHitArea();
|
|
|
|
|
|
|
|
ha->x = x + 110;
|
|
|
|
ha->y = window->y + y;
|
|
|
|
ha->item_ptr = item_ptr;
|
|
|
|
ha->width = 20;
|
|
|
|
ha->height = 20;
|
|
|
|
ha->flags = kBFDragBox | kBFBoxInUse | kBFBoxItem;
|
|
|
|
ha->id = 0x7FFD;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->verb = 208;
|
|
|
|
|
|
|
|
return ha - _hitAreas;
|
|
|
|
}
|
|
|
|
|
|
|
|
uint AGOSEngine_Simon1::setupIconHitArea(WindowBlock *window, uint num, uint x, uint y, Item *item_ptr) {
|
|
|
|
HitArea *ha = findEmptyHitArea();
|
|
|
|
|
|
|
|
ha->x = (x + window->x) * 8;
|
|
|
|
ha->y = y * 25 + window->y;
|
|
|
|
ha->item_ptr = item_ptr;
|
|
|
|
ha->width = 24;
|
|
|
|
ha->height = 24;
|
|
|
|
ha->flags = kBFDragBox | kBFBoxInUse | kBFBoxItem;
|
|
|
|
ha->id = 0x7FFD;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->verb = 208;
|
|
|
|
|
|
|
|
return ha - _hitAreas;
|
|
|
|
}
|
|
|
|
|
|
|
|
uint AGOSEngine_Waxworks::setupIconHitArea(WindowBlock *window, uint num, uint x, uint y, Item *item_ptr) {
|
|
|
|
HitArea *ha = findEmptyHitArea();
|
|
|
|
|
|
|
|
ha->x = (x + window->x) * 8;
|
|
|
|
ha->y = y * 20 + window->y;
|
|
|
|
ha->item_ptr = item_ptr;
|
|
|
|
ha->width = 24;
|
|
|
|
ha->height = 20;
|
|
|
|
ha->flags = kBFDragBox | kBFBoxInUse | kBFBoxItem;
|
|
|
|
ha->id = 0x7FFD;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->verb = 208;
|
|
|
|
|
|
|
|
return ha - _hitAreas;
|
|
|
|
}
|
|
|
|
|
|
|
|
uint AGOSEngine_Elvira2::setupIconHitArea(WindowBlock *window, uint num, uint x, uint y, Item *item_ptr) {
|
|
|
|
HitArea *ha = findEmptyHitArea();
|
|
|
|
|
|
|
|
ha->x = (x + window->x) * 8;
|
|
|
|
ha->y = y * 8 + window->y;
|
|
|
|
ha->item_ptr = item_ptr;
|
|
|
|
ha->width = 24;
|
|
|
|
ha->height = 24;
|
|
|
|
ha->id = 0x7FFD;
|
|
|
|
ha->priority = 100;
|
|
|
|
|
|
|
|
if (window->iconPtr->classMask == 2) {
|
|
|
|
ha->flags = kBFDragBox | kBFBoxInUse;
|
|
|
|
ha->verb = 248 + 0x4000;
|
2006-10-23 11:13:51 +00:00
|
|
|
} else {
|
|
|
|
ha->flags = kBFDragBox | kBFBoxInUse | kBFBoxItem;
|
2007-05-07 01:11:10 +00:00
|
|
|
ha->verb = 208;
|
2006-10-23 11:13:51 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
return ha - _hitAreas;
|
|
|
|
}
|
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
uint AGOSEngine::setupIconHitArea(WindowBlock *window, uint num, uint x, uint y, Item *item_ptr) {
|
|
|
|
HitArea *ha = findEmptyHitArea();
|
|
|
|
|
|
|
|
ha->x = (x + window->x) * 8;
|
|
|
|
ha->y = y * 8 + window->y;
|
|
|
|
ha->item_ptr = item_ptr;
|
|
|
|
ha->width = 24;
|
|
|
|
ha->height = 24;
|
|
|
|
ha->flags = kBFDragBox | kBFBoxInUse | kBFBoxItem;
|
|
|
|
ha->id = 0x7FFD;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->verb = 253;
|
|
|
|
|
|
|
|
return ha - _hitAreas;
|
|
|
|
}
|
|
|
|
|
|
|
|
void AGOSEngine_Feeble::addArrows(WindowBlock *window) {
|
2006-04-06 00:54:26 +00:00
|
|
|
HitArea *ha;
|
|
|
|
|
|
|
|
ha = findEmptyHitArea();
|
|
|
|
_scrollUpHitArea = ha - _hitAreas;
|
2007-05-07 01:11:10 +00:00
|
|
|
|
|
|
|
ha->x = 496;
|
|
|
|
ha->y = 279;
|
|
|
|
ha->width = 30;
|
|
|
|
ha->height = 45;
|
|
|
|
ha->flags = kBFBoxInUse | kBFNoTouchName;
|
|
|
|
ha->id = 0x7FFB;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->window = window;
|
|
|
|
ha->verb = 1;
|
2006-04-06 00:54:26 +00:00
|
|
|
|
|
|
|
ha = findEmptyHitArea();
|
|
|
|
_scrollDownHitArea = ha - _hitAreas;
|
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
ha->x = 496;
|
|
|
|
ha->y = 324;
|
|
|
|
ha->width = 30;
|
|
|
|
ha->height = 44;
|
|
|
|
ha->flags = kBFBoxInUse | kBFNoTouchName;
|
|
|
|
ha->id = 0x7FFC;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->window = window;
|
|
|
|
ha->verb = 1;
|
|
|
|
}
|
2006-04-06 00:54:26 +00:00
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
void AGOSEngine_Simon2::addArrows(WindowBlock *window) {
|
|
|
|
HitArea *ha;
|
|
|
|
|
|
|
|
ha = findEmptyHitArea();
|
|
|
|
_scrollUpHitArea = ha - _hitAreas;
|
|
|
|
|
|
|
|
ha->x = 81;
|
|
|
|
ha->y = 158;
|
|
|
|
ha->width = 12;
|
|
|
|
ha->height = 26;
|
|
|
|
ha->flags = kBFBoxInUse | kBFNoTouchName;
|
|
|
|
ha->id = 0x7FFB;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->window = window;
|
|
|
|
ha->verb = 1;
|
|
|
|
|
|
|
|
ha = findEmptyHitArea();
|
|
|
|
_scrollDownHitArea = ha - _hitAreas;
|
|
|
|
|
|
|
|
ha->x = 227;
|
|
|
|
ha->y = 162;
|
|
|
|
ha->width = 12;
|
|
|
|
ha->height = 26;
|
|
|
|
ha->flags = kBFBoxInUse | kBFNoTouchName;
|
|
|
|
ha->id = 0x7FFC;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->window = window;
|
|
|
|
ha->verb = 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
void AGOSEngine_Simon1::addArrows(WindowBlock *window) {
|
|
|
|
HitArea *ha;
|
|
|
|
|
|
|
|
ha = findEmptyHitArea();
|
|
|
|
_scrollUpHitArea = ha - _hitAreas;
|
|
|
|
|
|
|
|
ha->x = 308;
|
|
|
|
ha->y = 149;
|
|
|
|
ha->width = 12;
|
|
|
|
ha->height = 17;
|
|
|
|
ha->flags = kBFBoxInUse | kBFNoTouchName;
|
|
|
|
ha->id = 0x7FFB;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->window = window;
|
|
|
|
ha->verb = 1;
|
|
|
|
|
|
|
|
ha = findEmptyHitArea();
|
|
|
|
_scrollDownHitArea = ha - _hitAreas;
|
|
|
|
|
|
|
|
ha->x = 308;
|
|
|
|
ha->y = 176;
|
|
|
|
ha->width = 12;
|
|
|
|
ha->height = 17;
|
|
|
|
ha->flags = kBFBoxInUse | kBFNoTouchName;
|
|
|
|
ha->id = 0x7FFC;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->window = window;
|
|
|
|
ha->verb = 1;
|
|
|
|
|
|
|
|
if (getFeatures() & GF_32COLOR) {
|
|
|
|
// TODO: Manually draws arrows
|
2006-10-17 00:38:04 +00:00
|
|
|
} else {
|
2007-05-07 01:11:10 +00:00
|
|
|
stopAnimate(128);
|
2007-05-07 13:09:10 +00:00
|
|
|
uint8 palette = (getPlatform() == Common::kPlatformAmiga) ? 15: 14;
|
2007-05-07 01:11:10 +00:00
|
|
|
animate(0, 1, 128, 0, 0, palette);
|
2006-04-06 00:54:26 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2007-05-07 01:11:10 +00:00
|
|
|
void AGOSEngine_Waxworks::addArrows(WindowBlock *window) {
|
|
|
|
HitArea *ha;
|
|
|
|
|
|
|
|
ha = findEmptyHitArea();
|
|
|
|
_scrollUpHitArea = ha - _hitAreas;
|
|
|
|
|
|
|
|
setBitFlag(22, true);
|
|
|
|
ha->x = 255;
|
|
|
|
ha->y = 153;
|
|
|
|
ha->width = 9;
|
|
|
|
ha->height = 11;
|
|
|
|
ha->flags = kBFBoxInUse | kBFNoTouchName;
|
|
|
|
ha->id = 0x7FFB;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->window = window;
|
|
|
|
ha->verb = 1;
|
|
|
|
|
|
|
|
ha = findEmptyHitArea();
|
|
|
|
_scrollDownHitArea = ha - _hitAreas;
|
|
|
|
|
|
|
|
ha->x = 255;
|
|
|
|
ha->y = 170;
|
|
|
|
ha->width = 9;
|
|
|
|
ha->height = 11;
|
|
|
|
ha->flags = kBFBoxInUse | kBFNoTouchName;
|
2007-05-07 06:30:51 +00:00
|
|
|
ha->id = 0x7FFC;
|
2007-05-07 01:11:10 +00:00
|
|
|
ha->priority = 100;
|
|
|
|
ha->window = window;
|
|
|
|
ha->verb = 1;
|
|
|
|
setWindowImageEx(6, 103);
|
|
|
|
}
|
|
|
|
|
|
|
|
void AGOSEngine_Elvira2::addArrows(WindowBlock *window) {
|
|
|
|
HitArea *ha;
|
|
|
|
|
|
|
|
ha = findEmptyHitArea();
|
|
|
|
_scrollUpHitArea = ha - _hitAreas;
|
|
|
|
|
|
|
|
setBitFlag(21, true);
|
|
|
|
ha->x = 54;
|
|
|
|
ha->y = 154;
|
|
|
|
ha->width = 12;
|
|
|
|
ha->height = 10;
|
|
|
|
ha->flags = kBFBoxInUse;
|
|
|
|
ha->id = 0x7FFB;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->window = window;
|
|
|
|
ha->verb = 1;
|
|
|
|
|
|
|
|
ha = findEmptyHitArea();
|
|
|
|
_scrollDownHitArea = ha - _hitAreas;
|
|
|
|
|
|
|
|
ha->x = 54;
|
|
|
|
ha->y = 178;
|
|
|
|
ha->width = 12;
|
|
|
|
ha->height = 10;
|
|
|
|
ha->flags = kBFBoxInUse;
|
2007-05-07 06:30:51 +00:00
|
|
|
ha->id = 0x7FFC;
|
2007-05-07 01:11:10 +00:00
|
|
|
ha->priority = 100;
|
|
|
|
ha->window = window;
|
|
|
|
ha->verb = 1;
|
|
|
|
setWindowImageEx(6, 106);
|
|
|
|
}
|
|
|
|
|
|
|
|
void AGOSEngine::addArrows(WindowBlock *window) {
|
|
|
|
HitArea *ha;
|
|
|
|
|
|
|
|
ha = findEmptyHitArea();
|
|
|
|
_scrollUpHitArea = ha - _hitAreas;
|
|
|
|
|
|
|
|
ha->x = 30 * 8;
|
|
|
|
ha->y = 151;
|
|
|
|
ha->width = 16;
|
|
|
|
ha->height = 19;
|
|
|
|
ha->flags = kBFBoxInUse;
|
|
|
|
ha->id = 0x7FFB;
|
|
|
|
ha->priority = 100;
|
|
|
|
ha->window = window;
|
|
|
|
ha->verb = 1;
|
|
|
|
|
|
|
|
ha = findEmptyHitArea();
|
|
|
|
_scrollDownHitArea = ha - _hitAreas;
|
|
|
|
|
|
|
|
ha->x = 30 * 8;
|
|
|
|
ha->y = 170;
|
|
|
|
ha->width = 16;
|
|
|
|
ha->height = 19;
|
|
|
|
ha->flags = kBFBoxInUse;
|
2007-05-07 06:30:51 +00:00
|
|
|
ha->id = 0x7FFC;
|
2007-05-07 01:11:10 +00:00
|
|
|
ha->priority = 100;
|
|
|
|
ha->window = window;
|
|
|
|
ha->verb = 1;
|
|
|
|
}
|
|
|
|
|
2006-10-23 11:13:51 +00:00
|
|
|
void AGOSEngine::removeArrows(WindowBlock *window, uint num) {
|
|
|
|
if (getGameType() == GType_SIMON1) {
|
2007-04-28 07:00:33 +00:00
|
|
|
if (getFeatures() & GF_32COLOR) {
|
|
|
|
// TODO: Manually removes arrows
|
|
|
|
} else {
|
2007-05-13 08:46:48 +00:00
|
|
|
stopAnimate(129);
|
|
|
|
uint8 palette = (getPlatform() == Common::kPlatformAmiga) ? 15: 14;
|
|
|
|
animate(0, 1, 129, 0, 0, palette);
|
2007-04-28 07:00:33 +00:00
|
|
|
}
|
2006-10-17 00:38:04 +00:00
|
|
|
} else if (getGameType() == GType_WW) {
|
2006-10-23 11:13:51 +00:00
|
|
|
setBitFlag(22, false);
|
|
|
|
setWindowImageEx(6, 103);
|
2006-10-17 00:38:04 +00:00
|
|
|
} else if (getGameType() == GType_ELVIRA2) {
|
2006-10-23 11:13:51 +00:00
|
|
|
setBitFlag(21, false);
|
|
|
|
setWindowImageEx(6, 106);
|
2004-12-16 12:49:25 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2006-09-29 09:44:30 +00:00
|
|
|
void AGOSEngine::removeIconArray(uint num) {
|
2006-04-06 00:54:26 +00:00
|
|
|
WindowBlock *window;
|
|
|
|
uint16 curWindow;
|
|
|
|
uint16 i;
|
|
|
|
|
|
|
|
window = _windowArray[num & 7];
|
|
|
|
curWindow = _curWindow;
|
|
|
|
|
|
|
|
if (window == NULL || window->iconPtr == NULL)
|
|
|
|
return;
|
|
|
|
|
2006-10-17 01:17:48 +00:00
|
|
|
if (getGameType() != GType_FF && getGameType() != GType_PP) {
|
2006-04-06 00:54:26 +00:00
|
|
|
changeWindow(num);
|
2006-04-06 10:47:37 +00:00
|
|
|
windowPutChar(12);
|
2006-04-06 00:54:26 +00:00
|
|
|
changeWindow(curWindow);
|
|
|
|
}
|
|
|
|
|
|
|
|
for (i = 0; window->iconPtr->iconArray[i].item != NULL; i++) {
|
2006-10-21 01:51:59 +00:00
|
|
|
freeBox(window->iconPtr->iconArray[i].boxCode);
|
2006-04-06 00:54:26 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
if (window->iconPtr->upArrow != -1) {
|
2006-10-21 01:51:59 +00:00
|
|
|
freeBox(window->iconPtr->upArrow);
|
2006-04-06 00:54:26 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
if (window->iconPtr->downArrow != -1) {
|
2006-10-21 01:51:59 +00:00
|
|
|
freeBox(window->iconPtr->downArrow);
|
2006-10-17 00:38:04 +00:00
|
|
|
removeArrows(window, num);
|
2006-04-06 00:54:26 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
free(window->iconPtr);
|
|
|
|
window->iconPtr = NULL;
|
|
|
|
|
|
|
|
_fcsData1[num] = 0;
|
|
|
|
_fcsData2[num] = 0;
|
|
|
|
}
|
|
|
|
|
2006-09-29 09:44:30 +00:00
|
|
|
} // End of namespace AGOS
|