scummvm/engines/dm/gfx.cpp

1603 lines
69 KiB
C++
Raw Normal View History

2016-08-26 22:36:31 +02:00
/* ScummVM - Graphic Adventure Engine
*
* ScummVM is the legal property of its developers, whose names
* are too numerous to list here. Please refer to the COPYRIGHT
* file distributed with this source distribution.
*
* 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.
*
*/
/*
* Based on the Reverse Engineering work of Christophe Fontanel,
* maintainer of the Dungeon Master Encyclopaedia (http://dmweb.free.fr/)
*/
#include "engines/util.h"
#include "common/system.h"
#include "common/file.h"
#include "graphics/palette.h"
#include "common/endian.h"
#include "gfx.h"
#include "dungeonman.h"
namespace DM {
2016-06-17 22:34:03 +02:00
Box gBoxMovementArrows = Box(224, 319, 124, 168);
2016-05-22 00:32:53 +02:00
enum StairFrameIndex {
kFrameStairsUpFront_D3L = 0, // @ G0110_s_Graphic558_Frame_StairsUpFront_D3L
kFrameStairsUpFront_D3C = 1, // @ G0111_s_Graphic558_Frame_StairsUpFront_D3C
kFrameStairsUpFront_D3R = 2, // @ G0112_s_Graphic558_Frame_StairsUpFront_D3R
kFrameStairsUpFront_D2L = 3, // @ G0113_s_Graphic558_Frame_StairsUpFront_D2L
kFrameStairsUpFront_D2C = 4, // @ G0114_s_Graphic558_Frame_StairsUpFront_D2C
kFrameStairsUpFront_D2R = 5, // @ G0115_s_Graphic558_Frame_StairsUpFront_D2R
kFrameStairsUpFront_D1L = 6, // @ G0116_s_Graphic558_Frame_StairsUpFront_D1L
kFrameStairsUpFront_D1C = 7, // @ G0117_s_Graphic558_Frame_StairsUpFront_D1C
kFrameStairsUpFront_D1R = 8, // @ G0118_s_Graphic558_Frame_StairsUpFront_D1R
kFrameStairsUpFront_D0L = 9, // @ G0119_s_Graphic558_Frame_StairsUpFront_D0L
kFrameStairsUpFront_D0R = 10, // @ G0120_s_Graphic558_Frame_StairsUpFront_D0R
kFrameStairsDownFront_D3L = 11, // @ G0121_s_Graphic558_Frame_StairsDownFront_D3L
kFrameStairsDownFront_D3C = 12, // @ G0122_s_Graphic558_Frame_StairsDownFront_D3C
kFrameStairsDownFront_D3R = 13, // @ G0123_s_Graphic558_Frame_StairsDownFront_D3R
kFrameStairsDownFront_D2L = 14, // @ G0124_s_Graphic558_Frame_StairsDownFront_D2L
kFrameStairsDownFront_D2C = 15, // @ G0125_s_Graphic558_Frame_StairsDownFront_D2C
kFrameStairsDownFront_D2R = 16, // @ G0126_s_Graphic558_Frame_StairsDownFront_D2R
kFrameStairsDownFront_D1L = 17, // @ G0127_s_Graphic558_Frame_StairsDownFront_D1L
kFrameStairsDownFront_D1C = 18, // @ G0128_s_Graphic558_Frame_StairsDownFront_D1C
kFrameStairsDownFront_D1R = 19, // @ G0129_s_Graphic558_Frame_StairsDownFront_D1R
kFrameStairsDownFront_D0L = 20, // @ G0130_s_Graphic558_Frame_StairsDownFront_D0L
kFrameStairsDownFront_D0R = 21, // @ G0131_s_Graphic558_Frame_StairsDownFront_D0R
kFrameStairsSide_D2L = 22, // @ G0132_s_Graphic558_Frame_StairsSide_D2L
kFrameStairsSide_D2R = 23, // @ G0133_s_Graphic558_Frame_StairsSide_D2R
kFrameStairsUpSide_D1L = 24, // @ G0134_s_Graphic558_Frame_StairsUpSide_D1L
kFrameStairsUpSide_D1R = 25, // @ G0135_s_Graphic558_Frame_StairsUpSide_D1R
kFrameStairsDownSide_D1L = 26, // @ G0136_s_Graphic558_Frame_StairsDownSide_D1L
kFrameStairsDownSide_D1R = 27, // @ G0137_s_Graphic558_Frame_StairsDownSide_D1R
kFrameStairsSide_D0L = 28, // @ G0138_s_Graphic558_Frame_StairsSide_D0L
kFrameStairsSide_D0R = 29 // @ G0139_s_Graphic558_Frame_StairsSide_D0R
};
2016-06-04 10:03:26 +02:00
Frame gStairFrames[] = {
Frame(0, 79, 25, 70, 40, 46, 0, 0),
Frame(64, 159, 25, 70, 48, 46, 0, 0),
Frame(149, 223, 25, 70, 40, 46, 5, 0),
Frame(0, 63, 22, 83, 32, 62, 0, 0),
Frame(64, 159, 22, 83, 48, 62, 0, 0),
Frame(160, 223, 22, 83, 32, 62, 0, 0),
Frame(0, 31, 9, 108, 16, 100, 0, 0),
Frame(32, 191, 9, 108, 80, 100, 0, 0),
Frame(192, 223, 9, 108, 16, 100, 0, 0),
Frame(0, 31, 58, 101, 16, 44, 0, 0),
Frame(192, 223, 58, 101, 16, 44, 0, 0),
Frame(0, 79, 28, 68, 40, 41, 0, 0),
Frame(64, 159, 28, 70, 48, 43, 0, 0),
Frame(149, 223, 28, 68, 40, 41, 5, 0),
Frame(0, 63, 24, 85, 32, 62, 0, 0),
Frame(64, 159, 24, 85, 48, 62, 0, 0),
Frame(160, 223, 24, 85, 32, 62, 0, 0),
Frame(0, 31, 18, 108, 16, 91, 0, 0),
Frame(32, 191, 18, 108, 80, 91, 0, 0),
Frame(192, 223, 18, 108, 16, 91, 0, 0),
Frame(0, 31, 76, 135, 16, 60, 0, 0),
Frame(192, 223, 76, 135, 16, 60, 0, 0),
Frame(60, 75, 57, 61, 8, 5, 0, 0),
Frame(148, 163, 57, 61, 8, 5, 0, 0),
Frame(32, 63, 57, 99, 16, 43, 0, 0),
Frame(160, 191, 57, 99, 16, 43, 0, 0),
Frame(32, 63, 60, 98, 16, 39, 0, 0),
Frame(160, 191, 60, 98, 16, 39, 0, 0),
Frame(0, 15, 73, 85, 8, 13, 0, 0),
Frame(208, 223, 73, 85, 8, 13, 0, 0)
};
2016-05-22 00:32:53 +02:00
#define kFirstWallOrn 121 // @ C121_GRAPHIC_FIRST_WALL_ORNAMENT
#define kFirstFloorSet 75 // @ C075_GRAPHIC_FIRST_FLOOR_SET
#define kFirstWallSet 77 // @ C077_GRAPHIC_FIRST_WALL_SET
#define kFirstStairs 90 // @ C090_GRAPHIC_FIRST_STAIRS
#define kFirstDoorSet 108 // @ C108_GRAPHIC_FIRST_DOOR_SET
#define kInscriptionFont 120 // @ C120_GRAPHIC_INSCRIPTION_FONT
#define kFirstWallOrn 121 // @ C121_GRAPHIC_FIRST_WALL_ORNAMENT
#define kFirstFloorOrn 247 // @ C247_GRAPHIC_FIRST_FLOOR_ORNAMENT
#define kFirstDoorOrn 303 // @ C303_GRAPHIC_FIRST_DOOR_ORNAMENT
2016-05-18 00:39:08 +02:00
enum ViewSquare {
kViewSquare_D4C = -3, // @ CM3_VIEW_SQUARE_D4C
kViewSquare_D4L = -2, // @ CM2_VIEW_SQUARE_D4L
kViewSquare_D4R = -1, // @ CM1_VIEW_SQUARE_D4R
kViewSquare_D3C = 0, // @ C00_VIEW_SQUARE_D3C
kViewSquare_D3L = 1, // @ C01_VIEW_SQUARE_D3L
kViewSquare_D3R = 2, // @ C02_VIEW_SQUARE_D3R
kViewSquare_D2C = 3, // @ C03_VIEW_SQUARE_D2C
kViewSquare_D2L = 4, // @ C04_VIEW_SQUARE_D2L
kViewSquare_D2R = 5, // @ C05_VIEW_SQUARE_D2R
kViewSquare_D1C = 6, // @ C06_VIEW_SQUARE_D1C
kViewSquare_D1L = 7, // @ C07_VIEW_SQUARE_D1L
kViewSquare_D1R = 8, // @ C08_VIEW_SQUARE_D1R
kViewSquare_D0C = 9, // @ C09_VIEW_SQUARE_D0C
kViewSquare_D0L = 10, // @ C10_VIEW_SQUARE_D0L
kViewSquare_D0R = 11, // @ C11_VIEW_SQUARE_D0R
kViewSquare_D3C_Explosion = 3, // @ C03_VIEW_SQUARE_D3C_EXPLOSION
kViewSquare_D3L_Explosion = 4, // @ C04_VIEW_SQUARE_D3L_EXPLOSION
kViewSquare_D1C_Explosion = 9, // @ C09_VIEW_SQUARE_D1C_EXPLOSION
kViewSquare_D0C_Explosion = 12 // @ C12_VIEW_SQUARE_D0C_EXPLOSION
};
2016-05-19 16:26:56 +02:00
Frame gCeilingFrame(0, 223, 0, 28, 112, 29, 0, 0); // @ K0012_s_Frame_Ceiling
Frame gFloorFrame(0, 223, 66, 135, 112, 70, 0, 0); // @ K0013_s_Frame_Floor
2016-06-20 18:03:48 +02:00
Frame gFrameWall_D3L2 = Frame(0, 15, 25, 73, 8, 49, 0, 0); // @ G0711_s_Graphic558_Frame_Wall_D3L2
2016-06-04 10:03:26 +02:00
Frame gFrameWall_D3R2 = Frame(208, 223, 25, 73, 8, 49, 0, 0); // @ G0712_s_Graphic558_Frame_Wall_D3R2
2016-05-19 16:26:56 +02:00
Frame gFrameWalls[12] = { // @ G0163_as_Graphic558_Frame_Walls
/* { X1, X2, Y1, Y2, pixelWidth, Height, X, Y } */
2016-06-04 10:03:26 +02:00
Frame(74, 149, 25, 75, 64, 51, 18, 0), /* D3C */
Frame(0, 83, 25, 75, 64, 51, 32, 0), /* D3L */
Frame(139, 223, 25, 75, 64, 51, 0, 0), /* D3R */
Frame(60, 163, 20, 90, 72, 71, 16, 0), /* D2C */
Frame(0, 74, 20, 90, 72, 71, 61, 0), /* D2L */
Frame(149, 223, 20, 90, 72, 71, 0, 0), /* D2R */
Frame(32, 191, 9, 119, 128, 111, 48, 0), /* D1C */
Frame(0, 63, 9, 119, 128, 111, 192, 0), /* D1L */
Frame(160, 223, 9, 119, 128, 111, 0, 0), /* D1R */
Frame(0, 223, 0, 135, 0, 0, 0, 0), /* D0C */
Frame(0, 31, 0, 135, 16, 136, 0, 0), /* D0L */
Frame(192, 223, 0, 135, 16, 136, 0, 0)
}; /* D0R */
2016-05-18 00:39:08 +02:00
enum WallSetIndices {
kDoorFrameFront = 0, // @ G0709_puc_Bitmap_WallSet_DoorFrameFront
kDoorFrameLeft_D1C = 1, // @ G0708_puc_Bitmap_WallSet_DoorFrameLeft_D1C
kDoorFameLeft_D2C = 2, // @ G0707_puc_Bitmap_WallSet_DoorFrameLeft_D2C
kDoorFrameLeft_D3C = 3, // @ G0706_puc_Bitmap_WallSet_DoorFrameLeft_D3C
kDoorFrameLeft_D3L = 4, // @ G0705_puc_Bitmap_WallSet_DoorFrameLeft_D3L
kDoorFrameTop_D1LCR = 5, // @ G0704_puc_Bitmap_WallSet_DoorFrameTop_D1LCR
kDoorFrameTop_D2LCR = 6, // @ G0703_puc_Bitmap_WallSet_DoorFrameTop_D2LCR
kWall_D0R = 7, // @ G0702_puc_Bitmap_WallSet_Wall_D0R
kWall_D0L = 8, // @ G0701_puc_Bitmap_WallSet_Wall_D0L
kWall_D1LCR = 9, // @ G0700_puc_Bitmap_WallSet_Wall_D1LCR
kWall_D2LCR = 10, // @ G0699_puc_Bitmap_WallSet_Wall_D2LCR
kWall_D3LCR = 11, // @ G0698_puc_Bitmap_WallSet_Wall_D3LCR
kWall_D3L2 = 12, // @ G0697_puc_Bitmap_WallSet_Wall_D3L2
kWall_D3R2 = 13, // @ G0696_puc_Bitmap_WallSet_Wall_D3R2
2016-05-21 19:36:24 +02:00
kDoorFrameRight_D1C = 14, // @ G0710_puc_Bitmap_WallSet_DoorFrameRight_D1C
kWall_D0R_Flipped = 15,
kWall_D0L_Flipped = 16,
kWall_D1LCR_Flipped = 17,
kWall_D2LCR_Flipped = 18,
kWall_D3LCR_Flipped = 19,
kWall_D0R_Native = 20,
kWall_D0L_Native = 21,
kWall_D1LCR_Native = 22,
kWall_D2LCR_Native = 23,
2016-06-22 00:24:34 +02:00
kWall_D3LCR_Native = 24
};
byte gDoorOrnCoordIndices[12] = { // @ G0196_auc_Graphic558_DoorOrnamentCoordinateSetIndices
0, /* Door Ornament #00 Square Grid */
1, /* Door Ornament #01 Iron Bars */
1, /* Door Ornament #02 Jewels */
1, /* Door Ornament #03 Wooden Bars */
0, /* Door Ornament #04 Arched Grid */
2, /* Door Ornament #05 Block Lock */
3, /* Door Ornament #06 Corner Lock */
1, /* Door Ornament #07 Black door */
2, /* Door Ornament #08 Red Triangle Lock */
2, /* Door Ornament #09 Triangle Lock */
1, /* Door Ornament #10 Ra Door */
1}; /* Door Ornament #11 Iron Door Damages */
byte gFloorOrnCoordSetIndices[9] = { // @ G0195_auc_Graphic558_FloorOrnamentCoordinateSetIndices
0, /* Floor Ornament 00 Square Grate */
0, /* Floor Ornament 01 Square Pressure Pad */
0, /* Floor Ornament 02 Moss */
0, /* Floor Ornament 03 Round Grate */
2, /* Floor Ornament 04 Round Pressure Plate */
0, /* Floor Ornament 05 Black Flame Pit */
0, /* Floor Ornament 06 Crack */
2, /* Floor Ornament 07 Tiny Pressure Pad */
0}; /* Floor Ornament 08 Puddle */
uint16 gWallOrnCoordSets[8][13][6] = { // @ G0205_aaauc_Graphic558_WallOrnamentCoordinateSets
/* { X1, X2, Y1, Y2, PixelWidth, Height } */
{{80, 83, 41, 45, 8 * 2, 5}, /* D3L */
{140, 143, 41, 45, 8 * 2, 5}, /* D3R */
{16, 29, 39, 50, 8 * 2, 12}, /* D3L */
{107, 120, 39, 50, 8 * 2, 12}, /* D3C */
{187, 200, 39, 50, 8 * 2, 12}, /* D3R */
{67, 77, 40, 49, 8 * 2, 10}, /* D2L */
{146, 156, 40, 49, 8 * 2, 10}, /* D2R */
{0, 17, 38, 55, 16 * 2, 18}, /* D2L */
{102, 123, 38, 55, 16 * 2, 18}, /* D2C */
{206, 223, 38, 55, 16 * 2, 18}, /* D2R */
{48, 63, 38, 56, 8 * 2, 19}, /* D1L */
{160, 175, 38, 56, 8 * 2, 19}, /* D1R */
{96, 127, 36, 63, 16 * 2, 28}}, /* D1C */
{{74, 82, 41, 60, 8 * 2, 20}, /* D3L */
{141, 149, 41, 60, 8 * 2, 20}, /* D3R */
{1, 47, 37, 63, 24 * 2, 27}, /* D3L */
{88, 134, 37, 63, 24 * 2, 27}, /* D3C */
{171, 217, 37, 63, 24 * 2, 27}, /* D3R */
{61, 76, 38, 67, 8 * 2, 30}, /* D2L */
{147, 162, 38, 67, 8 * 2, 30}, /* D2R */
{0, 43, 37, 73, 32 * 2, 37}, /* D2L */
{80, 143, 37, 73, 32 * 2, 37}, /* D2C */
{180, 223, 37, 73, 32 * 2, 37}, /* D2R */
{32, 63, 36, 83, 16 * 2, 48}, /* D1L */
{160, 191, 36, 83, 16 * 2, 48}, /* D1R */
{64, 159, 36, 91, 48 * 2, 56}}, /* D1C */
{{80, 83, 66, 70, 8 * 2, 5}, /* D3L */
{140, 143, 66, 70, 8 * 2, 5}, /* D3R */
{16, 29, 64, 75, 8 * 2, 12}, /* D3L */
{106, 119, 64, 75, 8 * 2, 12}, /* D3C */
{187, 200, 64, 75, 8 * 2, 12}, /* D3R */
{67, 77, 74, 83, 8 * 2, 10}, /* D2L */
{146, 156, 74, 83, 8 * 2, 10}, /* D2R */
{0, 17, 73, 90, 16 * 2, 18}, /* D2L */
{100, 121, 73, 90, 16 * 2, 18}, /* D2C */
{206, 223, 73, 90, 16 * 2, 18}, /* D2R */
{48, 63, 84, 102, 8 * 2, 19}, /* D1L */
{160, 175, 84, 102, 8 * 2, 19}, /* D1R */
{96, 127, 92, 119, 16 * 2, 28}}, /* D1C */
{{80, 83, 49, 53, 8 * 2, 5}, /* D3L */
{140, 143, 49, 53, 8 * 2, 5}, /* D3R */
{16, 29, 50, 61, 8 * 2, 12}, /* D3L */
{106, 119, 50, 61, 8 * 2, 12}, /* D3C */
{187, 200, 50, 61, 8 * 2, 12}, /* D3R */
{67, 77, 53, 62, 8 * 2, 10}, /* D2L */
{146, 156, 53, 62, 8 * 2, 10}, /* D2R */
{0, 17, 55, 72, 16 * 2, 18}, /* D2L */
{100, 121, 55, 72, 16 * 2, 18}, /* D2C */
{206, 223, 55, 72, 16 * 2, 18}, /* D2R */
{48, 63, 57, 75, 8 * 2, 19}, /* D1L */
{160, 175, 57, 75, 8 * 2, 19}, /* D1R */
{96, 127, 64, 91, 16 * 2, 28}}, /* D1C */
{{75, 90, 40, 44, 8 * 2, 5}, /* D3L */
{133, 148, 40, 44, 8 * 2, 5}, /* D3R */
{1, 48, 44, 49, 24 * 2, 6}, /* D3L */
{88, 135, 44, 49, 24 * 2, 6}, /* D3C */
{171, 218, 44, 49, 24 * 2, 6}, /* D3R */
{60, 77, 40, 46, 16 * 2, 7}, /* D2L */
{146, 163, 40, 46, 16 * 2, 7}, /* D2R */
{0, 35, 43, 50, 32 * 2, 8}, /* D2L */
{80, 143, 43, 50, 32 * 2, 8}, /* D2C */
{184, 223, 43, 50, 32 * 2, 8}, /* D2R */
{32, 63, 41, 52, 16 * 2, 12}, /* D1L */
{160, 191, 41, 52, 16 * 2, 12}, /* D1R */
{64, 159, 41, 52, 48 * 2, 12}}, /* D1C */
{{78, 85, 36, 51, 8 * 2, 16}, /* D3L */
{138, 145, 36, 51, 8 * 2, 16}, /* D3R */
{10, 41, 34, 53, 16 * 2, 20}, /* D3L */
{98, 129, 34, 53, 16 * 2, 20}, /* D3C */
{179, 210, 34, 53, 16 * 2, 20}, /* D3R */
{66, 75, 34, 56, 8 * 2, 23}, /* D2L */
{148, 157, 34, 56, 8 * 2, 23}, /* D2R */
{0, 26, 33, 61, 24 * 2, 29}, /* D2L */
{91, 133, 33, 61, 24 * 2, 29}, /* D2C */
{194, 223, 33, 61, 24 * 2, 29}, /* D2R */
{41, 56, 31, 65, 8 * 2, 35}, /* D1L */
{167, 182, 31, 65, 8 * 2, 35}, /* D1R */
{80, 143, 29, 71, 32 * 2, 43}}, /* D1C */
{{75, 82, 25, 75, 8 * 2, 51}, /* D3L */
{142, 149, 25, 75, 8 * 2, 51}, /* D3R */
{12, 60, 25, 75, 32 * 2, 51}, /* D3L */
{88, 136, 25, 75, 32 * 2, 51}, /* D3C */
{163, 211, 25, 75, 32 * 2, 51}, /* D3R */
{64, 73, 20, 90, 8 * 2, 71}, /* D2L */
{150, 159, 20, 90, 8 * 2, 71}, /* D2R */
{0, 38, 20, 90, 32 * 2, 71}, /* D2L */
{82, 142, 20, 90, 32 * 2, 71}, /* D2C */
{184, 223, 20, 90, 32 * 2, 71}, /* D2R */
{41, 56, 9, 119, 8 * 2, 111}, /* D1L */
{169, 184, 9, 119, 8 * 2, 111}, /* D1R */
{64, 159, 9, 119, 48 * 2, 111}}, /* D1C */
{{74, 85, 25, 75, 8 * 2, 51}, /* D3L */
{137, 149, 25, 75, 8 * 2, 51}, /* D3R */
{0, 75, 25, 75, 40 * 2, 51}, /* D3L Atari ST: { 0, 83, 25, 75, 48*2, 51 } */
{74, 149, 25, 75, 40 * 2, 51}, /* D3C Atari ST: { 74, 149, 25, 75, 48*2, 51 } */
{148, 223, 25, 75, 40 * 2, 51}, /* D3R Atari ST: { 139, 223, 25, 75, 48*2, 51 } */
{60, 77, 20, 90, 16 * 2, 71}, /* D2L */
{146, 163, 20, 90, 16 * 2, 71}, /* D2R */
{0, 74, 20, 90, 56 * 2, 71}, /* D2L */
{60, 163, 20, 90, 56 * 2, 71}, /* D2C */
{149, 223, 20, 90, 56 * 2, 71}, /* D2R */
{32, 63, 9, 119, 16 * 2, 111}, /* D1L */
{160, 191, 9, 119, 16 * 2, 111}, /* D1R */
{32, 191, 9, 119, 80 * 2, 111}}}; /* D1C */
byte gWallOrnCoordSetIndices[60] = { // @ G0194_auc_Graphic558_WallOrnamentCoordinateSetIndices
1, /* Wall Ornament 00 Unreadable Inscription */
1, /* Wall Ornament 01 Square Alcove */
1, /* Wall Ornament 02 Vi Altar */
1, /* Wall Ornament 03 Arched Alcove */
0, /* Wall Ornament 04 Hook */
0, /* Wall Ornament 05 Iron Lock */
0, /* Wall Ornament 06 Wood Ring */
0, /* Wall Ornament 07 Small Switch */
0, /* Wall Ornament 08 Dent 1 */
0, /* Wall Ornament 09 Dent 2 */
0, /* Wall Ornament 10 Iron Ring */
2, /* Wall Ornament 11 Crack */
3, /* Wall Ornament 12 Slime Outlet */
0, /* Wall Ornament 13 Dent 3 */
0, /* Wall Ornament 14 Tiny Switch */
0, /* Wall Ornament 15 Green Switch Out */
0, /* Wall Ornament 16 Blue Switch Out */
0, /* Wall Ornament 17 Coin Slot */
0, /* Wall Ornament 18 Double Iron Lock */
0, /* Wall Ornament 19 Square Lock */
0, /* Wall Ornament 20 Winged Lock */
0, /* Wall Ornament 21 Onyx Lock */
0, /* Wall Ornament 22 Stone Lock */
0, /* Wall Ornament 23 Cross Lock */
0, /* Wall Ornament 24 Topaz Lock */
0, /* Wall Ornament 25 Skeleton Lock */
0, /* Wall Ornament 26 Gold Lock */
0, /* Wall Ornament 27 Tourquoise Lock */
0, /* Wall Ornament 28 Emerald Lock */
0, /* Wall Ornament 29 Ruby Lock */
0, /* Wall Ornament 30 Ra Lock */
0, /* Wall Ornament 31 Master Lock */
0, /* Wall Ornament 32 Gem Hole */
2, /* Wall Ornament 33 Slime */
2, /* Wall Ornament 34 Grate */
1, /* Wall Ornament 35 Fountain */
1, /* Wall Ornament 36 Manacles */
1, /* Wall Ornament 37 Ghoul's Head */
1, /* Wall Ornament 38 Empty Torch Holder */
1, /* Wall Ornament 39 Scratches */
4, /* Wall Ornament 40 Poison Holes */
4, /* Wall Ornament 41 Fireball Holes */
4, /* Wall Ornament 42 Dagger Holes */
5, /* Wall Ornament 43 Champion Mirror */
0, /* Wall Ornament 44 Lever Up */
0, /* Wall Ornament 45 Lever Down */
1, /* Wall Ornament 46 Full Torch Holder */
0, /* Wall Ornament 47 Red Switch Out */
0, /* Wall Ornament 48 Eye Switch */
0, /* Wall Ornament 49 Big Switch Out */
2, /* Wall Ornament 50 Crack Switch Out */
0, /* Wall Ornament 51 Green Switch In */
0, /* Wall Ornament 52 Blue Switch In */
0, /* Wall Ornament 53 Red Switch In */
0, /* Wall Ornament 54 Big Switch In */
2, /* Wall Ornament 55 Crack Switch In. Atari ST Version 1.0 1987-12-08: 0 */
6, /* Wall Ornament 56 Amalgam (Encased Gem) */
6, /* Wall Ornament 57 Amalgam (Free Gem) */
6, /* Wall Ornament 58 Amalgam (Without Gem) */
7}; /* Wall Ornament 59 Lord Order (Outside) */
CreatureAspect gCreatureAspects[kCreatureTypeCount] = { // @ G0219_as_Graphic558_CreatureAspects
/* { FirstNativeBitmapRelativeIndex, FirstDerivedBitmapIndex, pixelWidthFront, HeightFront,
pixelWidthSide, HeightSide, pixelWidthAttack, HeightAttack, CoordinateSet / TransparentColor,
Replacement Color Set Index for color 10 / Replacement Color Set Index for color 9 } */
{0, 0, 56 * 2, 84, 56 * 2, 84, 56 * 2, 84, 0x1D, 0x01}, /* Creature #00 Giant Scorpion / Scorpion */
{4, 0, 32 * 2, 66, 0 * 2, 0, 32 * 2, 69, 0x0B, 0x20}, /* Creature #01 Swamp Slime / Slime Devil */
{6, 0, 24 * 2, 48, 24 * 2, 48, 0 * 2, 0, 0x0B, 0x00}, /* Creature #02 Giggler */
{10, 0, 32 * 2, 61, 0 * 2, 0, 32 * 2, 61, 0x24, 0x31}, /* Creature #03 Wizard Eye / Flying Eye */
{12, 0, 32 * 2, 64, 56 * 2, 64, 32 * 2, 64, 0x14, 0x34}, /* Creature #04 Pain Rat / Hellhound */
{16, 0, 24 * 2, 49, 40 * 2, 49, 0 * 2, 0, 0x18, 0x34}, /* Creature #05 Ruster */
{19, 0, 32 * 2, 60, 0 * 2, 0, 32 * 2, 60, 0x0D, 0x00}, /* Creature #06 Screamer */
{21, 0, 32 * 2, 43, 0 * 2, 0, 32 * 2, 64, 0x04, 0x00}, /* Creature #07 Rockpile / Rock pile */
{23, 0, 32 * 2, 83, 0 * 2, 0, 32 * 2, 93, 0x04, 0x00}, /* Creature #08 Ghost / Rive */
{25, 0, 32 * 2, 101, 32 * 2, 101, 32 * 2, 101, 0x14, 0x00}, /* Creature #09 Stone Golem */
{29, 0, 32 * 2, 82, 32 * 2, 82, 32 * 2, 83, 0x04, 0x00}, /* Creature #10 Mummy */
{33, 0, 32 * 2, 80, 0 * 2, 0, 32 * 2, 99, 0x14, 0x00}, /* Creature #11 Black Flame */
{35, 0, 32 * 2, 80, 32 * 2, 80, 32 * 2, 76, 0x04, 0x00}, /* Creature #12 Skeleton */
{39, 0, 32 * 2, 96, 56 * 2, 93, 32 * 2, 90, 0x1D, 0x20}, /* Creature #13 Couatl */
{43, 0, 32 * 2, 49, 16 * 2, 49, 32 * 2, 56, 0x04, 0x30}, /* Creature #14 Vexirk */
{47, 0, 32 * 2, 59, 56 * 2, 43, 32 * 2, 67, 0x14, 0x78}, /* Creature #15 Magenta Worm / Worm */
{51, 0, 32 * 2, 83, 32 * 2, 74, 32 * 2, 74, 0x04, 0x65}, /* Creature #16 Trolin / Ant Man */
{55, 0, 24 * 2, 49, 24 * 2, 53, 24 * 2, 53, 0x24, 0x00}, /* Creature #17 Giant Wasp / Muncher */
{59, 0, 32 * 2, 89, 32 * 2, 89, 32 * 2, 89, 0x04, 0x00}, /* Creature #18 Animated Armour / Deth Knight */
{63, 0, 32 * 2, 84, 32 * 2, 84, 32 * 2, 84, 0x0D, 0xA9}, /* Creature #19 Materializer / Zytaz */
{67, 0, 56 * 2, 27, 0 * 2, 0, 56 * 2, 80, 0x04, 0x65}, /* Creature #20 Water Elemental */
{69, 0, 56 * 2, 77, 56 * 2, 81, 56 * 2, 77, 0x04, 0xA9}, /* Creature #21 Oitu */
{73, 0, 32 * 2, 87, 32 * 2, 89, 32 * 2, 89, 0x04, 0xCB}, /* Creature #22 Demon */
{77, 0, 32 * 2, 96, 32 * 2, 94, 32 * 2, 96, 0x04, 0x00}, /* Creature #23 Lord Chaos */
{81, 0, 64 * 2, 94, 72 * 2, 94, 64 * 2, 94, 0x04, 0xCB}, /* Creature #24 Red Dragon / Dragon */
{85, 0, 32 * 2, 93, 0 * 2, 0, 0 * 2, 0, 0x04, 0xCB}, /* Creature #25 Lord Order */
{86, 0, 32 * 2, 93, 0 * 2, 0, 0 * 2, 0, 0x04, 0xCB}}; /* Creature #26 Grey Lord */
ObjectAspect gObjectAspects[kObjAspectCount] = { // @ G0209_as_Graphic558_ObjectAspects
/* FirstNativeBitmapRelativeIndex, FirstDerivedBitmapRelativeIndex, ByteWidth, Height, GraphicInfo, CoordinateSet */
ObjectAspect(0, 0, 24, 27, 0x11, 0),
ObjectAspect(2, 6, 24, 8, 0x00, 1),
ObjectAspect(3, 8, 8, 18, 0x00, 1),
ObjectAspect(4, 10, 8, 8, 0x00, 1),
ObjectAspect(5, 12, 8, 4, 0x00, 1),
ObjectAspect(6, 14, 16, 11, 0x00, 1),
ObjectAspect(7, 16, 24, 13, 0x00, 0),
ObjectAspect(8, 18, 32, 16, 0x00, 0),
ObjectAspect(9, 20, 40, 24, 0x00, 0),
ObjectAspect(10, 22, 16, 20, 0x00, 1),
ObjectAspect(11, 24, 40, 20, 0x00, 0),
ObjectAspect(12, 26, 32, 4, 0x00, 1),
ObjectAspect(13, 28, 40, 8, 0x00, 1),
ObjectAspect(14, 30, 32, 17, 0x00, 0),
ObjectAspect(15, 32, 40, 17, 0x00, 2),
ObjectAspect(16, 34, 16, 9, 0x00, 1),
ObjectAspect(17, 36, 24, 5, 0x00, 1),
ObjectAspect(18, 38, 16, 9, 0x00, 0),
ObjectAspect(19, 40, 8, 4, 0x00, 1),
ObjectAspect(20, 42, 32, 21, 0x00, 2),
ObjectAspect(21, 44, 32, 25, 0x00, 2),
ObjectAspect(22, 46, 32, 14, 0x00, 1),
ObjectAspect(23, 48, 32, 26, 0x00, 2),
ObjectAspect(24, 50, 32, 16, 0x00, 0),
ObjectAspect(25, 52, 32, 16, 0x00, 0),
ObjectAspect(26, 54, 16, 16, 0x00, 1),
ObjectAspect(27, 56, 16, 15, 0x00, 1),
ObjectAspect(28, 58, 16, 13, 0x00, 1),
ObjectAspect(29, 60, 16, 10, 0x00, 1),
ObjectAspect(30, 62, 40, 24, 0x00, 0),
ObjectAspect(31, 64, 40, 9, 0x00, 1),
ObjectAspect(32, 66, 16, 3, 0x00, 1),
ObjectAspect(33, 68, 32, 5, 0x00, 1),
ObjectAspect(34, 70, 40, 16, 0x00, 0),
ObjectAspect(35, 72, 8, 7, 0x00, 1),
ObjectAspect(36, 74, 32, 7, 0x00, 1),
ObjectAspect(37, 76, 24, 14, 0x00, 0),
ObjectAspect(38, 78, 16, 8, 0x00, 0),
ObjectAspect(39, 80, 8, 3, 0x00, 1),
ObjectAspect(40, 82, 40, 9, 0x00, 1),
ObjectAspect(41, 84, 24, 14, 0x00, 0),
ObjectAspect(42, 86, 40, 20, 0x00, 0),
ObjectAspect(43, 88, 40, 15, 0x00, 1),
ObjectAspect(44, 90, 32, 10, 0x00, 1),
ObjectAspect(45, 92, 32, 19, 0x00, 0),
ObjectAspect(46, 94, 40, 25, 0x00, 2),
ObjectAspect(47, 96, 24, 7, 0x00, 1),
ObjectAspect(48, 98, 8, 7, 0x00, 1),
ObjectAspect(49, 100, 16, 5, 0x00, 1),
ObjectAspect(50, 102, 8, 9, 0x00, 1),
ObjectAspect(51, 104, 32, 11, 0x00, 1),
ObjectAspect(52, 106, 32, 14, 0x00, 0),
ObjectAspect(53, 108, 24, 20, 0x00, 0),
ObjectAspect(54, 110, 16, 14, 0x00, 1),
ObjectAspect(55, 112, 32, 23, 0x00, 0),
ObjectAspect(56, 114, 24, 16, 0x00, 0),
ObjectAspect(57, 116, 32, 25, 0x00, 0),
ObjectAspect(58, 118, 24, 25, 0x00, 0),
ObjectAspect(59, 120, 8, 8, 0x00, 1),
ObjectAspect(60, 122, 8, 7, 0x00, 1),
ObjectAspect(61, 124, 8, 8, 0x00, 1),
ObjectAspect(62, 126, 8, 8, 0x00, 1),
ObjectAspect(63, 128, 8, 5, 0x00, 1),
ObjectAspect(64, 130, 8, 13, 0x01, 1),
ObjectAspect(65, 134, 16, 13, 0x00, 1),
ObjectAspect(66, 136, 16, 14, 0x00, 0),
ObjectAspect(67, 138, 16, 10, 0x00, 1),
ObjectAspect(68, 140, 8, 18, 0x00, 1),
ObjectAspect(69, 142, 8, 17, 0x00, 1),
ObjectAspect(70, 144, 32, 18, 0x00, 0),
ObjectAspect(71, 146, 16, 23, 0x00, 0),
ObjectAspect(72, 148, 16, 24, 0x00, 0),
ObjectAspect(73, 150, 16, 15, 0x00, 0),
ObjectAspect(74, 152, 8, 7, 0x00, 1),
ObjectAspect(75, 154, 8, 15, 0x00, 1),
ObjectAspect(76, 156, 8, 9, 0x00, 1),
ObjectAspect(77, 158, 16, 14, 0x00, 0),
ObjectAspect(78, 160, 8, 8, 0x00, 1),
ObjectAspect(79, 162, 16, 9, 0x00, 1),
ObjectAspect(80, 164, 8, 13, 0x01, 1),
ObjectAspect(81, 168, 8, 18, 0x00, 1),
ObjectAspect(82, 170, 24, 28, 0x00, 0),
ObjectAspect(83, 172, 40, 13, 0x00, 1),
ObjectAspect(84, 174, 8, 4, 0x00, 1),
2016-06-04 10:44:37 +02:00
ObjectAspect(85, 176, 32, 17, 0x00, 0)
};
ProjectileAspect gProjectileAspect[kProjectileAspectCount] = { // @ G0210_as_Graphic558_ProjectileAspects
/* ProjectileAspect( FirstNativeBitmapRelativeIndex, FirstDerivedBitmapRelativeIndex, ByteWidth, Height, GraphicInfo ) */
ProjectileAspect(0, 0, 32, 11, 0x0011), /* Arrow */
ProjectileAspect(3, 18, 16, 11, 0x0011), /* Dagger */
ProjectileAspect(6, 36, 24, 47, 0x0010), /* Axe - Executioner */
ProjectileAspect(9, 54, 32, 15, 0x0112), /* Explosion Lightning Bolt */
ProjectileAspect(11, 54, 32, 12, 0x0011), /* Slayer */
ProjectileAspect(14, 72, 24, 47, 0x0010), /* Stone Club */
ProjectileAspect(17, 90, 24, 47, 0x0010), /* Club */
ProjectileAspect(20, 108, 16, 11, 0x0011), /* Poison Dart */
ProjectileAspect(23, 126, 48, 18, 0x0011), /* Storm - Side Splitter - Diamond Edge - Falchion - Ra Blade - Rapier - Biter - Samurai Sword - Sword - Dragon Fang */
ProjectileAspect(26, 144, 8, 15, 0x0012), /* Throwing Star */
ProjectileAspect(28, 156, 16, 28, 0x0103), /* Explosion Fireball */
ProjectileAspect(29, 156, 16, 11, 0x0103), /* Explosion Default */
ProjectileAspect(30, 156, 16, 28, 0x0103), /* Explosion Slime */
ProjectileAspect(31, 156, 16, 24, 0x0103) /* Explosion Poison Bolt Poison Cloud */
};
// TODO: this is ONLY for the Amiga version, name will have to be refactored
/* Identical to the palette at the end of the swoosh palette animation */
uint16 gPalSwoosh[16] = {0x000, 0xFFF, 0xFFF, 0xFFF, 0xFFF, 0xFFF, 0xFFF, 0xFFF, 0x000, 0xFFF, 0xAAA, 0xFFF, 0xAAA, 0x444, 0xFF0, 0xFF0}; // @ K0057_aui_Palette_Swoosh
uint16 gPalMousePointer[16] = {0x000, 0x666, 0x888, 0x620, 0x0CC, 0x840, 0x080, 0x0C0, 0xF00, 0xFA0, 0xC86, 0xFF0, 0x000, 0xAAA, 0x00F, 0xFFF}; // @ K0150_aui_Palette_MousePointer
/* Atari ST: { 0x003, 0x055, 0x773, 0x420, 0x774, 0x000, 0x040, 0x500, 0x642, 0x775, 0x742, 0x760, 0x750, 0x000, 0x310, 0x776 }, RGB colors are different */
uint16 gPalCredits[16] = {0x006, 0x0AA, 0xFF6, 0x840, 0xFF8, 0x000, 0x080, 0xA00, 0xC84, 0xFFA, 0xF84, 0xFC0, 0xFA0, 0x000, 0x620, 0xFFC}; // @ G0019_aui_Graphic562_Palette_Credits
/* Atari ST: { 0x000, 0x333, 0x444, 0x420, 0x654, 0x210, 0x040, 0x050, 0x432, 0x700, 0x543, 0x321, 0x222, 0x555, 0x310, 0x777 }, RGB colors are different */
uint16 gPalEntrance[16] = {0x000, 0x666, 0x888, 0x840, 0xCA8, 0x0C0, 0x080, 0x0A0, 0x864, 0xF00, 0xA86, 0x642, 0x444, 0xAAA, 0x620, 0xFFF}; // @ G0020_aui_Graphic562_Palette_Entrance
uint16 gPalDungeonView[6][16] = { // @ G0021_aaui_Graphic562_Palette_DungeonView
/* Atari ST: { 0x000, 0x333, 0x444, 0x310, 0x066, 0x420, 0x040, 0x060, 0x700, 0x750, 0x643, 0x770, 0x222, 0x555, 0x007, 0x777 }, RGB colors are different */
0x000, 0x666, 0x888, 0x620, 0x0CC, 0x840, 0x080, 0x0C0, 0xF00, 0xFA0, 0xC86, 0xFF0, 0x444, 0xAAA, 0x00F, 0xFFF,
/* Atari ST: { 0x000, 0x222, 0x333, 0x310, 0x066, 0x410, 0x030, 0x050, 0x600, 0x640, 0x532, 0x760, 0x111, 0x444, 0x006, 0x666 }, RGB colors are different */
0x000, 0x444, 0x666, 0x620, 0x0CC, 0x820, 0x060, 0x0A0, 0xC00, 0x000, 0x000, 0xFC0, 0x222, 0x888, 0x00C, 0xCCC,
/* Atari ST: { 0x000, 0x111, 0x222, 0x210, 0x066, 0x310, 0x020, 0x040, 0x500, 0x530, 0x421, 0x750, 0x000, 0x333, 0x005, 0x555 }, RGB colors are different */
0x000, 0x222, 0x444, 0x420, 0x0CC, 0x620, 0x040, 0x080, 0xA00, 0x000, 0x000, 0xFA0, 0x000, 0x666, 0x00A, 0xAAA,
/* Atari ST: { 0x000, 0x000, 0x111, 0x100, 0x066, 0x210, 0x010, 0x030, 0x400, 0x420, 0x310, 0x640, 0x000, 0x222, 0x004, 0x444 }, RGB colors are different */
0x000, 0x000, 0x222, 0x200, 0x0CC, 0x420, 0x020, 0x060, 0x800, 0x000, 0x000, 0xC80, 0x000, 0x444, 0x008, 0x888,
/* Atari ST: { 0x000, 0x000, 0x000, 0x000, 0x066, 0x100, 0x000, 0x020, 0x300, 0x310, 0x200, 0x530, 0x000, 0x111, 0x003, 0x333 }, RGB colors are different */
0x000, 0x000, 0x000, 0x000, 0x0CC, 0x200, 0x000, 0x040, 0x600, 0x000, 0x000, 0xA60, 0x000, 0x222, 0x006, 0x666,
/* Atari ST: { 0x000, 0x000, 0x000, 0x000, 0x066, 0x000, 0x000, 0x010, 0x200, 0x200, 0x100, 0x320, 0x000, 0x000, 0x002, 0x222 }, RGB colors are different */
2016-06-04 10:44:37 +02:00
0x000, 0x000, 0x000, 0x000, 0x0CC, 0x000, 0x000, 0x020, 0x400, 0x000, 0x000, 0x640, 0x000, 0x000, 0x004, 0x444
};
CreatureReplColorSet gCreatureReplColorSets[13] = { // @ G0220_as_Graphic558_CreatureReplacementColorSets
/* { Color, Color, Color, Color, Color, Color, D2 replacement color index (x10), D3 replacement color index (x10) } */
{0x0CA0, 0x0A80, 0x0860, 0x0640, 0x0420, 0x0200, 90, 90}, /* Atari ST: { 0x0650, 0x0540, 0x0430, 0x0320, 0x0210, 0x0100, 90, 90 }, RGB colors are different */
{0x0060, 0x0040, 0x0020, 0x0000, 0x0000, 0x0000, 0, 0}, /* Atari ST: { 0x0030, 0x0020, 0x0010, 0x0000, 0x0000, 0x0000, 0, 0 }, */
{0x0860, 0x0640, 0x0420, 0x0200, 0x0000, 0x0000, 100, 100}, /* Atari ST: { 0x0430, 0x0320, 0x0210, 0x0100, 0x0000, 0x0000, 100, 100 }, */
{0x0640, 0x0420, 0x0200, 0x0000, 0x0000, 0x0000, 90, 0}, /* Atari ST: { 0x0320, 0x0210, 0x0100, 0x0000, 0x0000, 0x0000, 90, 0 }, */
{0x000A, 0x0008, 0x0006, 0x0004, 0x0002, 0x0000, 90, 100}, /* Atari ST: { 0x0005, 0x0004, 0x0003, 0x0002, 0x0001, 0x0000, 90, 100 }, */
{0x0008, 0x0006, 0x0004, 0x0002, 0x0000, 0x0000, 100, 0}, /* Atari ST: { 0x0004, 0x0003, 0x0002, 0x0001, 0x0000, 0x0000, 100, 0 }, */
{0x0808, 0x0606, 0x0404, 0x0202, 0x0000, 0x0000, 90, 0}, /* Atari ST: { 0x0404, 0x0303, 0x0202, 0x0101, 0x0000, 0x0000, 90, 0 }, */
{0x0A0A, 0x0808, 0x0606, 0x0404, 0x0202, 0x0000, 100, 90}, /* Atari ST: { 0x0505, 0x0404, 0x0303, 0x0202, 0x0101, 0x0000, 100, 90 }, */
{0x0FA0, 0x0C80, 0x0A60, 0x0840, 0x0620, 0x0400, 100, 50}, /* Atari ST: { 0x0750, 0x0640, 0x0530, 0x0420, 0x0310, 0x0200, 100, 50 }, */
{0x0F80, 0x0C60, 0x0A40, 0x0820, 0x0600, 0x0200, 50, 70}, /* Atari ST: { 0x0740, 0x0630, 0x0520, 0x0410, 0x0300, 0x0100, 50, 30 }, D3 replacement color index is different */
{0x0800, 0x0600, 0x0400, 0x0200, 0x0000, 0x0000, 100, 120}, /* Atari ST: { 0x0400, 0x0300, 0x0200, 0x0100, 0x0000, 0x0000, 100, 100 }, D3 replacement color index is different */
{0x0600, 0x0400, 0x0200, 0x0000, 0x0000, 0x0000, 120, 0}, /* Atari ST: { 0x0300, 0x0200, 0x0100, 0x0000, 0x0000, 0x0000, 120, 0 }, */
{0x0C86, 0x0A64, 0x0842, 0x0620, 0x0400, 0x0200, 100, 50}}; /* Atari ST: { 0x0643, 0x0532, 0x0421, 0x0310, 0x0200, 0x0100, 100, 50 } }; */
byte gPalChangesCreature_D3[16] = {0, 120, 10, 30, 40, 30, 0, 60, 30, 0, 0, 110, 0, 20, 0, 130}; // @ G0221_auc_Graphic558_PaletteChanges_Creature_D3
byte gPalChangesCreature_D2[16] = {0, 10, 20, 30, 40, 30, 60, 70, 50, 0, 0, 110, 120, 130, 140, 150}; // @ G0222_auc_Graphic558_PaletteChanges_Creature_D2
Viewport gDefultViewPort(0, 0, 320, 200);
// TODO: I guessed the numbers
Viewport gDungeonViewport(0, 33, 224, 126); // @ G0296_puc_Bitmap_Viewport
byte gPalChangesNoChanges[16] = {0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 110, 120, 130, 140, 150}; // @ G0017_auc_Graphic562_PaletteChanges_NoChanges
byte gPalChangesFloorOrn_D3[16] = {0, 120, 10, 30, 40, 30, 0, 60, 30, 90, 100, 110, 0, 20, 140, 130}; // @ G0213_auc_Graphic558_PaletteChanges_FloorOrnament_D3
byte gPalChangesFloorOrn_D2[16] = {0, 10, 20, 30, 40, 30, 60, 70, 50, 90, 100, 110, 120, 130, 140, 150}; // @ G0214_auc_Graphic558_PaletteChanges_FloorOrnament_D2
int gFountainOrnIndices[kFountainOrnCount] = {35}; // @ G0193_ai_Graphic558_FountainOrnamentIndices
byte gAlcoveOrnIndices[kAlcoveOrnCount] = { // @ G0192_auc_Graphic558_AlcoveOrnamentIndices
1, /* Square Alcove */
2, /* Vi Altar */
3}; /* Arched Alcove */
2016-06-20 18:03:48 +02:00
DisplayMan::DisplayMan(DMEngine *dmEngine) : _vm(dmEngine) {
_vgaBuffer = nullptr;
_bitmaps = nullptr;
_grapItemCount = 0;
_packedItemPos = nullptr;
_packedBitmaps = nullptr;
_bitmaps = nullptr;
_tmpBitmap = nullptr;
_floorBitmap = nullptr;
_ceilingBitmap = nullptr;
_currMapAllowedCreatureTypes = nullptr;
_screenWidth = _screenHeight = 0;
_championPortraitOrdinal = 0;
_currMapViAltarIndex = 0;
for (int i = 0; i < 25; i++)
_wallSetBitMaps[i] = nullptr;
for (int i = 0; i < kStairsGraphicCount; i++)
_stairIndices[i] = 0;
2016-06-20 18:03:48 +02:00
for (int i = 0; i < 4; i++)
2016-06-20 18:03:48 +02:00
_palChangesProjectile[i] = nullptr;
for (int i = 0; i < kAlcoveOrnCount; i++)
_currMapAlcoveOrnIndices[i] = 0;
for (int i = 0; i < kFountainOrnCount; i++)
_currMapFountainOrnIndices[i] = 0;
for (int i = 0; i < 2; i++) {
for (int j = 0; j < 16; j++) {
_currMapWallOrnInfo[j][i] = 0;
_currMapFloorOrnInfo[j][i] = 0;
}
for (int j = 0; j < 17; j++) {
_currMapDoorOrnInfo[j][i] = 0;
}
}
2016-06-20 18:03:48 +02:00
for (int i = 0; i < 16; i++) {
_currMapWallOrnIndices[i] = 0;
_currMapFloorOrnIndices[i] = 0;
}
for (int i = 0; i < 18; i++)
_currMapDoorOrnIndices[i] = 0;
2016-06-18 17:48:48 +02:00
_inscriptionThing = Thing::_thingNone;
2016-08-26 22:33:28 +02:00
_useByteBoxCoordinates = false;
}
DisplayMan::~DisplayMan() {
delete[] _packedItemPos;
delete[] _packedBitmaps;
delete[] _vgaBuffer;
if (_bitmaps) {
delete[] _bitmaps[0];
delete[] _bitmaps;
}
delete[] _wallSetBitMaps[kWall_D3R2]; // copy of another bitmap, but flipped
delete[] _wallSetBitMaps[kDoorFrameRight_D1C]; // copy of another bitmap, but flipped
2016-05-21 19:36:24 +02:00
for (uint16 i = kWall_D0L_Flipped; i <= kWall_D3LCR_Flipped; ++i)
delete[] _wallSetBitMaps[i];
}
void DisplayMan::setUpScreens(uint16 width, uint16 height) {
_screenWidth = width;
_screenHeight = height;
2016-05-22 00:32:53 +02:00
delete[] _tmpBitmap;
_tmpBitmap = new byte[_screenWidth * _screenHeight];
delete[] _vgaBuffer;
_vgaBuffer = new byte[_screenWidth * _screenHeight];
clearScreen(kColorBlack);
}
void DisplayMan::loadGraphics() {
Common::File f;
f.open("graphics.dat");
2016-05-22 00:32:53 +02:00
_grapItemCount = f.readUint16BE();
delete[] _packedItemPos;
2016-05-22 00:32:53 +02:00
_packedItemPos = new uint32[_grapItemCount + 1];
_packedItemPos[0] = 0;
2016-05-22 00:32:53 +02:00
for (uint16 i = 1; i < _grapItemCount + 1; ++i)
_packedItemPos[i] = f.readUint16BE() + _packedItemPos[i - 1];
delete[] _packedBitmaps;
2016-05-22 00:32:53 +02:00
_packedBitmaps = new uint8[_packedItemPos[_grapItemCount]];
2016-05-22 00:32:53 +02:00
f.seek(2 + _grapItemCount * 4);
for (uint32 i = 0; i < _packedItemPos[_grapItemCount]; ++i)
_packedBitmaps[i] = f.readByte();
f.close();
unpackGraphics();
for (uint16 i = kDoorOrnDestroyedMask; i <= kDoorOrnThivesEyeMask; ++i) {
_currMapDoorOrnInfo[i][kNativeBitmapIndex] = i + (kDoorMaskDestroyedIndice - kDoorOrnDestroyedMask);
_currMapDoorOrnInfo[i][kNativeCoordinateSet] = 1;
}
_currMapFloorOrnInfo[kFloorOrnFootprints][kNativeBitmapIndex] = 1;
_currMapFloorOrnInfo[kFloorOrnFootprints][kNativeCoordinateSet] = 1;
_palChangesProjectile[0] = gPalChangesFloorOrn_D3;
_palChangesProjectile[1] = gPalChangesFloorOrn_D2;
_palChangesProjectile[2] = _palChangesProjectile[3] = gPalChangesNoChanges;
loadFloorSet(kFloorSetStone);
loadWallSet(kWallSetStone);
}
void DisplayMan::unpackGraphics() {
uint32 unpackedBitmapsSize = 0;
for (uint16 i = 0; i <= 20; ++i)
2016-06-18 18:02:48 +02:00
unpackedBitmapsSize += getWidth(i) * getHeight(i);
for (uint16 i = 22; i <= 532; ++i)
2016-06-18 18:02:48 +02:00
unpackedBitmapsSize += getWidth(i) * getHeight(i);
unpackedBitmapsSize += (5 + 1) * 6 * 128; // 5 x 6 characters, 128 of them, +1 for convenience padding
// graphics items go from 0-20 and 22-532 inclusive, _unpackedItemPos 21 and 22 are there for indexing convenience
if (_bitmaps) {
delete[] _bitmaps[0];
delete[] _bitmaps;
}
_bitmaps = new byte*[575]; // largest graphic indice (i think)
_bitmaps[0] = new byte[unpackedBitmapsSize];
loadIntoBitmap(0, _bitmaps[0]);
for (uint16 i = 1; i <= 20; ++i) {
2016-06-18 18:02:48 +02:00
_bitmaps[i] = _bitmaps[i - 1] + getWidth(i - 1) * getHeight(i - 1);
loadIntoBitmap(i, _bitmaps[i]);
}
2016-06-18 18:02:48 +02:00
_bitmaps[22] = _bitmaps[20] + getWidth(20) * getHeight(20);
for (uint16 i = 23; i <= 532; ++i) {
2016-06-18 18:02:48 +02:00
_bitmaps[i] = _bitmaps[i - 1] + getWidth(i - 1) * getHeight(i - 1);
loadIntoBitmap(i, _bitmaps[i]);
}
_bitmaps[kFontGraphicIndice] = _bitmaps[532] + getWidth(532) * getHeight(532);
loadFNT1intoBitmap(kFontGraphicIndice, _bitmaps[kFontGraphicIndice]);
}
void DisplayMan::loadFNT1intoBitmap(uint16 index, byte* destBitmap) {
uint8 *data = _packedBitmaps + _packedItemPos[index];
for (uint16 i = 0; i < 6; i++) {
for (uint16 w = 0; w < 128; ++w) {
*destBitmap++ = kColorBlack;
uint16 nextByte = *data++;
for (int16 pixel = 4; pixel >= 0; --pixel) {
*destBitmap++ = (nextByte >> pixel) & 0x1;
}
}
}
}
void DisplayMan::loadPalette(uint16 *palette) {
byte colorPalette[16 * 3];
for (int i = 0; i < 16; ++i) {
colorPalette[i * 3] = (palette[i] >> 8) * (256 / 16);
colorPalette[i * 3 + 1] = (palette[i] >> 4) * (256 / 16);
colorPalette[i * 3 + 2] = palette[i] * (256 / 16);
}
_vm->_system->getPaletteManager()->setPalette(colorPalette, 0, 16);
}
void DisplayMan::loadIntoBitmap(uint16 index, byte *destBitmap) {
uint8 *data = _packedBitmaps + _packedItemPos[index];
uint16 width = READ_BE_UINT16(data);
uint16 height = READ_BE_UINT16(data + 2);
uint16 nextByteIndex = 4;
for (uint16 k = 0; k < width * height;) {
uint8 nextByte = data[nextByteIndex++];
uint8 nibble1 = (nextByte & 0xF0) >> 4;
uint8 nibble2 = (nextByte & 0x0F);
if (nibble1 <= 7) {
for (int j = 0; j < nibble1 + 1; ++j)
destBitmap[k++] = nibble2;
} else if (nibble1 == 0x8) {
uint8 byte1 = data[nextByteIndex++];
for (int j = 0; j < byte1 + 1; ++j)
destBitmap[k++] = nibble2;
} else if (nibble1 == 0xC) {
uint16 word1 = READ_BE_UINT16(data + nextByteIndex);
nextByteIndex += 2;
for (int j = 0; j < word1 + 1; ++j)
destBitmap[k++] = nibble2;
} else if (nibble1 == 0xB) {
uint8 byte1 = data[nextByteIndex++];
for (int j = 0; j < byte1 + 1; ++j, ++k)
destBitmap[k] = destBitmap[k - width];
destBitmap[k++] = nibble2;
} else if (nibble1 == 0xF) {
uint16 word1 = READ_BE_UINT16(data + nextByteIndex);
nextByteIndex += 2;
for (int j = 0; j < word1 + 1; ++j, ++k)
destBitmap[k] = destBitmap[k - width];
destBitmap[k++] = nibble2;
} else if (nibble1 == 9) {
uint8 byte1 = data[nextByteIndex++];
if (byte1 % 2)
byte1++;
else
destBitmap[k++] = nibble2;
for (int j = 0; j < byte1 / 2; ++j) {
uint8 byte2 = data[nextByteIndex++];
destBitmap[k++] = (byte2 & 0xF0) >> 4;
destBitmap[k++] = byte2 & 0x0F;
}
}
}
}
void DisplayMan::blitToBitmap(byte *srcBitmap, uint16 srcWidth, uint16 srcX, uint16 srcY,
byte *destBitmap, uint16 destWidth,
uint16 destFromX, uint16 destToX, uint16 destFromY, uint16 destToY,
Color transparent, Viewport &destViewport) {
for (uint16 y = 0; y < destToY - destFromY; ++y)
for (uint16 x = 0; x < destToX - destFromX; ++x) {
byte srcPixel = srcBitmap[srcWidth * (y + srcY) + srcX + x];
if (srcPixel != transparent)
2016-06-18 18:02:48 +02:00
destBitmap[destWidth * (y + destFromY + destViewport._posY) + destFromX + x + destViewport._posX] = srcPixel;
}
}
void DisplayMan::blitToBitmap(byte* srcBitmap, uint16 srcWidth, uint16 srcX, uint16 srcY, byte* destBitmap, uint16 destWidth, Box& box, Color transparent, Viewport& viewport) {
blitToBitmap(srcBitmap, srcWidth, srcX, srcY, destBitmap, destWidth, box._x1, box._x2, box._y1, box._y2, transparent, viewport);
}
2016-06-25 21:05:29 +02:00
void DisplayMan::blitToScreen(byte *srcBitmap, uint16 srcWidth, uint16 srcX, uint16 srcY,
uint16 destFromX, uint16 destToX, uint16 destFromY, uint16 destToY,
Color transparent, Viewport &viewport) {
blitToBitmap(srcBitmap, srcWidth, srcX, srcY,
getCurrentVgaBuffer(), _screenWidth, destFromX, destToX, destFromY, destToY, transparent, viewport);
}
void DisplayMan::blitToBitmap(byte *srcBitmap, uint16 srcWidth, uint16 srcHeight, byte *destBitmap, uint16 destWidth, uint16 destX, uint16 destY) {
for (uint16 y = 0; y < srcHeight; ++y)
memcpy(destBitmap + destWidth*(y + destY) + destX, srcBitmap + y * srcWidth, sizeof(byte)* srcWidth);
}
void DisplayMan::flipBitmapHorizontal(byte *bitmap, uint16 width, uint16 height) {
for (uint16 y = 0; y < height; ++y) {
for (uint16 x = 0; x < width / 2; ++x) {
byte tmp;
tmp = bitmap[y*width + x];
bitmap[y*width + x] = bitmap[y*width + width - 1 - x];
bitmap[y*width + width - 1 - x] = tmp;
}
}
}
void DisplayMan::flipBitmapVertical(byte *bitmap, uint16 width, uint16 height) {
byte *tmp = new byte[width];
for (uint16 y = 0; y < height / 2; ++y) {
memcpy(tmp, bitmap + y * width, width);
memcpy(bitmap + y * width, bitmap + (height - 1 - y) * width, width);
memcpy(bitmap + (height - 1 - y) * width, tmp, width);
}
delete[] tmp;
}
void DisplayMan::updateScreen() {
_vm->_system->copyRectToScreen(_vgaBuffer, _screenWidth, 0, 0, _screenWidth, _screenHeight);
_vm->_system->updateScreen();
}
byte *DisplayMan::getCurrentVgaBuffer() {
return _vgaBuffer;
}
2016-06-18 18:02:48 +02:00
uint16 DisplayMan::getWidth(uint16 index) {
byte *data = _packedBitmaps + _packedItemPos[index];
return READ_BE_UINT16(data);
}
2016-06-18 18:02:48 +02:00
uint16 DisplayMan::getHeight(uint16 index) {
uint8 *data = _packedBitmaps + _packedItemPos[index];
return READ_BE_UINT16(data + 2);
}
void DisplayMan::drawWallSetBitmapWithoutTransparency(byte *bitmap, Frame &f) {
2016-06-18 18:02:48 +02:00
if (f._srcWidth)
blitToScreen(bitmap, f._srcWidth, f._srcX, f._srcY, f._destFromX, f._destToX, f._destFromY, f._destToY, kColorNoTransparency, gDungeonViewport);
}
void DisplayMan::drawWallSetBitmap(byte *bitmap, Frame &f) {
2016-06-18 18:02:48 +02:00
if (f._srcWidth)
blitToScreen(bitmap, f._srcWidth, f._srcX, f._srcY, f._destFromX, f._destToX, f._destFromY, f._destToY, kColorFlesh, gDungeonViewport);
}
void DisplayMan::drawSquareD3L(direction dir, int16 posX, int16 posY) {
2016-05-19 16:26:56 +02:00
uint16 squareAspect[5];
_vm->_dungeonMan->setSquareAspect(squareAspect, dir, posX, posY);
2016-05-22 00:32:53 +02:00
switch (squareAspect[kElemAspect]) {
case kStairsFrontElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Up_Front_D3L, gStairFrames[kFrameStairsUpFront_D3L]);
else
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Down_Front_D3L, gStairFrames[kFrameStairsDownFront_D3L]);
break;
2016-05-19 16:26:56 +02:00
case kWallElemType:
drawWallSetBitmap(_wallSetBitMaps[kWall_D3LCR], gFrameWalls[kViewSquare_D3L]);
isDrawnWallOrnAnAlcove(squareAspect[kRightWallOrnOrdAspect], kViewWall_D3L_RIGHT);
if (isDrawnWallOrnAnAlcove(squareAspect[kFrontWallOrnOrdAspect], kViewWall_D3L_FRONT)) {
// ... missing code
}
2016-05-19 16:26:56 +02:00
break;
default:
break;
2016-05-19 16:26:56 +02:00
}
}
void DisplayMan::drawSquareD3R(direction dir, int16 posX, int16 posY) {
uint16 squareAspect[5];
_vm->_dungeonMan->setSquareAspect(squareAspect, dir, posX, posY);
switch (squareAspect[0]) {
2016-05-22 00:32:53 +02:00
case kStairsFrontElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmapFlippedHorizontally(kStairsNativeIndex_Up_Front_D3L, gStairFrames[kFrameStairsUpFront_D3R]);
else
drawFloorPitOrStairsBitmapFlippedHorizontally(kStairsNativeIndex_Down_Front_D3L, gStairFrames[kFrameStairsDownFront_D3R]);
break;
case kWallElemType:
drawWallSetBitmap(_wallSetBitMaps[kWall_D3LCR], gFrameWalls[kViewSquare_D3R]);
isDrawnWallOrnAnAlcove(squareAspect[kLeftWallOrnOrdAspect], kViewWall_D3R_LEFT);
if (isDrawnWallOrnAnAlcove(squareAspect[kFrontWallOrnOrdAspect], kViewWall_D3R_FRONT)) {
// ... missing code
}
break;
default:
break;
}
}
void DisplayMan::drawSquareD3C(direction dir, int16 posX, int16 posY) {
uint16 squareAspect[5];
_vm->_dungeonMan->setSquareAspect(squareAspect, dir, posX, posY);
switch (squareAspect[0]) {
2016-05-22 00:32:53 +02:00
case kStairsFrontElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Up_Front_D3C, gStairFrames[kFrameStairsUpFront_D3C]);
else
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Down_Front_D3C, gStairFrames[kFrameStairsDownFront_D3C]);
break;
case kWallElemType:
drawWallSetBitmapWithoutTransparency(_wallSetBitMaps[kWall_D3LCR], gFrameWalls[kViewSquare_D3C]);
if (isDrawnWallOrnAnAlcove(squareAspect[kFrontWallOrnOrdAspect], kViewWall_D3C_FRONT)) {
//... missing code
}
break;
default:
break;
}
}
void DisplayMan::drawSquareD2L(direction dir, int16 posX, int16 posY) {
uint16 squareAspect[5];
_vm->_dungeonMan->setSquareAspect(squareAspect, dir, posX, posY);
switch (squareAspect[0]) {
2016-05-22 00:32:53 +02:00
case kStairsFrontElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Up_Front_D2L, gStairFrames[kFrameStairsUpFront_D2L]);
else
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Down_Front_D2L, gStairFrames[kFrameStairsDownFront_D2L]);
break;
case kWallElemType:
drawWallSetBitmap(_wallSetBitMaps[kWall_D2LCR], gFrameWalls[kViewSquare_D2L]);
isDrawnWallOrnAnAlcove(squareAspect[kRightWallOrnOrdAspect], kViewWall_D2L_RIGHT);
if (isDrawnWallOrnAnAlcove(squareAspect[kFrontWallOrnOrdAspect], kViewWall_D2L_FRONT)) {
// ... missing code
}
break;
2016-05-22 00:32:53 +02:00
case kStairsSideElemType:
2016-06-22 00:24:34 +02:00
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Side_D2L, gStairFrames[kFrameStairsSide_D2L]);
2016-05-22 00:32:53 +02:00
break;
default:
break;
}
}
void DisplayMan::drawSquareD2R(direction dir, int16 posX, int16 posY) {
uint16 squareAspect[5];
_vm->_dungeonMan->setSquareAspect(squareAspect, dir, posX, posY);
switch (squareAspect[0]) {
2016-05-22 00:32:53 +02:00
case kStairsFrontElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmapFlippedHorizontally(kStairsNativeIndex_Up_Front_D2L, gStairFrames[kFrameStairsUpFront_D2R]);
else
drawFloorPitOrStairsBitmapFlippedHorizontally(kStairsNativeIndex_Down_Front_D2L, gStairFrames[kFrameStairsDownFront_D2R]);
break;
case kWallElemType:
drawWallSetBitmap(_wallSetBitMaps[kWall_D2LCR], gFrameWalls[kViewSquare_D2R]);
isDrawnWallOrnAnAlcove(squareAspect[kLeftWallOrnOrdAspect], kViewWall_D2R_LEFT);
if (isDrawnWallOrnAnAlcove(squareAspect[kFrontWallOrnOrdAspect], kViewWall_D2R_FRONT)) {
// ... missing code
}
break;
2016-05-22 00:32:53 +02:00
case kStairsSideElemType:
drawFloorPitOrStairsBitmapFlippedHorizontally(kStairsNativeIndex_Side_D2L, gStairFrames[kFrameStairsSide_D2R]);
break;
default:
break;
}
}
void DisplayMan::drawSquareD2C(direction dir, int16 posX, int16 posY) {
uint16 squareAspect[5];
_vm->_dungeonMan->setSquareAspect(squareAspect, dir, posX, posY);
switch (squareAspect[0]) {
2016-05-22 00:32:53 +02:00
case kStairsFrontElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Up_Front_D2C, gStairFrames[kFrameStairsUpFront_D2C]);
else
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Down_Front_D2C, gStairFrames[kFrameStairsDownFront_D2C]);
break;
case kWallElemType:
drawWallSetBitmapWithoutTransparency(_wallSetBitMaps[kWall_D2LCR], gFrameWalls[kViewSquare_D2C]);
if (isDrawnWallOrnAnAlcove(squareAspect[kFrontWallOrnOrdAspect], kViewWall_D2C_FRONT)) {
// ... missing code
}
break;
default:
break;
}
}
void DisplayMan::drawSquareD1L(direction dir, int16 posX, int16 posY) {
uint16 squareAspect[5];
_vm->_dungeonMan->setSquareAspect(squareAspect, dir, posX, posY);
switch (squareAspect[0]) {
2016-05-22 00:32:53 +02:00
case kStairsFrontElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Up_Front_D1L, gStairFrames[kFrameStairsUpFront_D1L]);
else
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Down_Front_D1L, gStairFrames[kFrameStairsDownFront_D1L]);
break;
case kWallElemType:
drawWallSetBitmap(_wallSetBitMaps[kWall_D1LCR], gFrameWalls[kViewSquare_D1L]);
isDrawnWallOrnAnAlcove(squareAspect[kRightWallOrnOrdAspect], kViewWall_D1L_RIGHT);
break;
2016-05-22 00:32:53 +02:00
case kStairsSideElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Up_Side_D1L, gStairFrames[kFrameStairsUpSide_D1L]);
else
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Down_Side_D1L, gStairFrames[kFrameStairsDownSide_D1L]);
break;
default:
break;
}
}
void DisplayMan::drawSquareD1R(direction dir, int16 posX, int16 posY) {
uint16 squareAspect[5];
_vm->_dungeonMan->setSquareAspect(squareAspect, dir, posX, posY);
switch (squareAspect[0]) {
2016-05-22 00:32:53 +02:00
case kStairsFrontElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmapFlippedHorizontally(kStairsNativeIndex_Up_Front_D1L, gStairFrames[kFrameStairsUpFront_D1R]);
else
drawFloorPitOrStairsBitmapFlippedHorizontally(kStairsNativeIndex_Down_Front_D1L, gStairFrames[kFrameStairsDownFront_D1R]);
break;
case kWallElemType:
drawWallSetBitmap(_wallSetBitMaps[kWall_D1LCR], gFrameWalls[kViewSquare_D1R]);
isDrawnWallOrnAnAlcove(squareAspect[kLeftWallOrnOrdAspect], kViewWall_D1R_LEFT);
break;
2016-05-22 00:32:53 +02:00
case kStairsSideElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmapFlippedHorizontally(kStairsNativeIndex_Up_Side_D1L, gStairFrames[kFrameStairsUpSide_D1R]);
else
drawFloorPitOrStairsBitmapFlippedHorizontally(kStairsNativeIndex_Down_Side_D1L, gStairFrames[kFrameStairsDownSide_D1R]);
break;
default:
break;
}
}
void DisplayMan::drawSquareD1C(direction dir, int16 posX, int16 posY) {
uint16 squareAspect[5];
_vm->_dungeonMan->setSquareAspect(squareAspect, dir, posX, posY);
switch (squareAspect[0]) {
2016-05-22 00:32:53 +02:00
case kStairsFrontElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Up_Front_D1C, gStairFrames[kFrameStairsUpFront_D1C]);
else
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Down_Front_D1C, gStairFrames[kFrameStairsDownFront_D1C]);
break;
case kWallElemType:
_vm->_dungeonMan->_isFacingAlcove = false;
_vm->_dungeonMan->_isFacingViAltar = false;
_vm->_dungeonMan->_isFacingFountain = false;
drawWallSetBitmapWithoutTransparency(_wallSetBitMaps[kWall_D1LCR], gFrameWalls[kViewSquare_D1C]);
if (isDrawnWallOrnAnAlcove(squareAspect[kFrontWallOrnOrdAspect], kViewWall_D1C_FRONT)) {
// .... code not yet implemneted
}
break;
default:
break;
}
}
void DisplayMan::drawSquareD0L(direction dir, int16 posX, int16 posY) {
uint16 squareAspect[5];
_vm->_dungeonMan->setSquareAspect(squareAspect, dir, posX, posY);
switch (squareAspect[0]) {
2016-05-22 00:32:53 +02:00
case kStairsSideElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Side_D0L, gStairFrames[kFrameStairsSide_D0L]);
break;
case kWallElemType:
drawWallSetBitmap(_wallSetBitMaps[kWall_D0L], gFrameWalls[kViewSquare_D0L]);
break;
default:
break;
}
}
void DisplayMan::drawSquareD0R(direction dir, int16 posX, int16 posY) {
uint16 squareAspect[5];
_vm->_dungeonMan->setSquareAspect(squareAspect, dir, posX, posY);
switch (squareAspect[0]) {
2016-05-22 00:32:53 +02:00
case kStairsSideElemType:
if (squareAspect[kStairsUpAspect])
drawFloorPitOrStairsBitmapFlippedHorizontally(kStairsNativeIndex_Side_D0L, gStairFrames[kFrameStairsSide_D0R]);
return;
case kWallElemType:
drawWallSetBitmap(_wallSetBitMaps[kWall_D0R], gFrameWalls[kViewSquare_D0R]);
break;
default:
break;
}
}
void DisplayMan::drawSquareD0C(direction dir, int16 posX, int16 posY) {
uint16 squareAspect[5];
_vm->_dungeonMan->setSquareAspect(squareAspect, dir, posX, posY);
switch (squareAspect[0]) {
2016-05-22 00:32:53 +02:00
case kStairsFrontElemType:
if (squareAspect[kStairsUpAspect]) {
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Up_Front_D0C_Left, gStairFrames[kFrameStairsUpFront_D0L]);
drawFloorPitOrStairsBitmapFlippedHorizontally(kStairsNativeIndex_Up_Front_D0C_Left, gStairFrames[kFrameStairsUpFront_D0R]);
} else {
drawFloorPitOrStairsBitmap(kStairsNativeIndex_Down_Front_D0C_Left, gStairFrames[kFrameStairsDownFront_D0L]);
drawFloorPitOrStairsBitmapFlippedHorizontally(kStairsNativeIndex_Down_Front_D0C_Left, gStairFrames[kFrameStairsDownFront_D0R]);
}
break;
default:
break;
}
}
void DisplayMan::drawDungeon(direction dir, int16 posX, int16 posY) {
loadPalette(gPalEntrance);
// TODO: this is a global variable, set from here
bool flippedFloorCeiling = (posX + posY + dir) & 1;
// NOTE: this can hold every bitmap, width and height is "flexible"
byte *tmpBitmap = new byte[305 * 111];
clearBitmap(tmpBitmap, 305, 111, kColorBlack);
for (int16 i = 0; i < 6; ++i)
_vm->_dungeonMan->_dungeonViewClickableBoxes[i].setToZero();
for (uint16 i = 0; i < 6; ++i) {
_vm->_dungeonMan->_dungeonViewClickableBoxes[i]._x1 = 255 + 1;
}
if (flippedFloorCeiling) {
2016-06-18 18:02:48 +02:00
uint16 w = gFloorFrame._srcWidth, h = gFloorFrame._srcHeight;
blitToBitmap(_floorBitmap, w, h, tmpBitmap, w);
flipBitmapHorizontal(tmpBitmap, w, h);
drawWallSetBitmap(tmpBitmap, gFloorFrame);
drawWallSetBitmap(_ceilingBitmap, gCeilingFrame);
2016-05-19 16:26:56 +02:00
2016-05-21 19:36:24 +02:00
for (uint16 i = 0; i <= kWall_D3LCR - kWall_D0R; ++i)
_wallSetBitMaps[i + kWall_D0R] = _wallSetBitMaps[i + kWall_D0R_Flipped];
} else {
2016-06-18 18:02:48 +02:00
uint16 w = gCeilingFrame._srcWidth, h = gCeilingFrame._srcHeight;
blitToBitmap(_ceilingBitmap, w, h, tmpBitmap, w);
flipBitmapHorizontal(tmpBitmap, w, h);
drawWallSetBitmap(tmpBitmap, gCeilingFrame);
drawWallSetBitmap(_floorBitmap, gFloorFrame);
}
if (_vm->_dungeonMan->getRelSquareType(dir, 3, -2, posX, posY) == kWallElemType)
2016-05-19 16:26:56 +02:00
drawWallSetBitmap(_wallSetBitMaps[kWall_D3L2], gFrameWall_D3L2);
if (_vm->_dungeonMan->getRelSquareType(dir, 3, 2, posX, posY) == kWallElemType)
2016-05-19 16:26:56 +02:00
drawWallSetBitmap(_wallSetBitMaps[kWall_D3R2], gFrameWall_D3R2);
2016-05-07 23:27:16 +02:00
int16 tmpPosX = posX, tmpPosY = posY;
_vm->_dungeonMan->mapCoordsAfterRelMovement(dir, 3, -1, tmpPosX, tmpPosY);
2016-05-21 19:36:24 +02:00
drawSquareD3L(dir, tmpPosX, tmpPosY);
tmpPosX = posX, tmpPosY = posY;
_vm->_dungeonMan->mapCoordsAfterRelMovement(dir, 3, 1, tmpPosX, tmpPosY);
drawSquareD3R(dir, tmpPosX, tmpPosY);
tmpPosX = posX, tmpPosY = posY;
_vm->_dungeonMan->mapCoordsAfterRelMovement(dir, 3, 0, tmpPosX, tmpPosY);
drawSquareD3C(dir, tmpPosX, tmpPosY);
tmpPosX = posX, tmpPosY = posY;
_vm->_dungeonMan->mapCoordsAfterRelMovement(dir, 2, -1, tmpPosX, tmpPosY);
drawSquareD2L(dir, tmpPosX, tmpPosY);
tmpPosX = posX, tmpPosY = posY;
_vm->_dungeonMan->mapCoordsAfterRelMovement(dir, 2, 1, tmpPosX, tmpPosY);
drawSquareD2R(dir, tmpPosX, tmpPosY);
tmpPosX = posX, tmpPosY = posY;
_vm->_dungeonMan->mapCoordsAfterRelMovement(dir, 2, 0, tmpPosX, tmpPosY);
drawSquareD2C(dir, tmpPosX, tmpPosY);
tmpPosX = posX, tmpPosY = posY;
_vm->_dungeonMan->mapCoordsAfterRelMovement(dir, 1, -1, tmpPosX, tmpPosY);
drawSquareD1L(dir, tmpPosX, tmpPosY);
tmpPosX = posX, tmpPosY = posY;
_vm->_dungeonMan->mapCoordsAfterRelMovement(dir, 1, 1, tmpPosX, tmpPosY);
drawSquareD1R(dir, tmpPosX, tmpPosY);
tmpPosX = posX, tmpPosY = posY;
_vm->_dungeonMan->mapCoordsAfterRelMovement(dir, 1, 0, tmpPosX, tmpPosY);
drawSquareD1C(dir, tmpPosX, tmpPosY);
tmpPosX = posX, tmpPosY = posY;
_vm->_dungeonMan->mapCoordsAfterRelMovement(dir, 0, -1, tmpPosX, tmpPosY);
drawSquareD0L(dir, tmpPosX, tmpPosY);
tmpPosX = posX, tmpPosY = posY;
_vm->_dungeonMan->mapCoordsAfterRelMovement(dir, 0, 1, tmpPosX, tmpPosY);
drawSquareD0R(dir, tmpPosX, tmpPosY);
drawSquareD0C(dir, posX, posY);
2016-05-07 23:27:16 +02:00
2016-05-21 19:36:24 +02:00
for (uint16 i = 0; i <= kWall_D3LCR - kWall_D0R; ++i)
_wallSetBitMaps[i + kWall_D0R] = _wallSetBitMaps[i + kWall_D0R_Native];
delete[] tmpBitmap;
}
void DisplayMan::clearScreen(Color color) {
memset(getCurrentVgaBuffer(), color, sizeof(byte) * _screenWidth * _screenHeight);
}
void DisplayMan::clearBitmap(byte *bitmap, uint16 width, uint16 height, Color color) {
memset(bitmap, color, sizeof(byte) * width * height);
}
void DisplayMan::loadFloorSet(FloorSet set) {
// there are 2 bitmaps per set, first one is at 75
GraphicIndice indice = (GraphicIndice)(kFirstFloorSet + (kFloorSetGraphicCount * set));
_floorBitmap = _bitmaps[indice];
_ceilingBitmap = _bitmaps[indice + 1];
}
2016-05-21 19:36:24 +02:00
2016-06-17 22:34:03 +02:00
Box gBoxWallBitmap_D3LCR = Box(0, 115, 0, 50); // @ G0161_s_Graphic558_Box_WallBitmap_D3LCR
Box gBoxWallBitmap_D2LCR = Box(0, 135, 0, 70); // @ G0162_s_Graphic558_Box_WallBitmap_D2LCR
2016-05-21 19:36:24 +02:00
void DisplayMan::loadWallSet(WallSet set) {
uint16 firstIndice = (set * kWallSetGraphicCount) + kFirstWallSet;
for (uint16 i = 0; i < kWallSetGraphicCount; ++i) {
_wallSetBitMaps[i] = _bitmaps[i + firstIndice];
}
2016-05-21 19:36:24 +02:00
for (uint16 i = 0; i <= kWall_D3LCR - kWall_D0R; ++i)
_wallSetBitMaps[i + kWall_D0R_Native] = _wallSetBitMaps[i + kWall_D0R];
uint16 srcIndex[7] = {kDoorFrameLeft_D1C, kWall_D3L2, kWall_D1LCR, kWall_D0L, kWall_D0R,
kWall_D2LCR, kWall_D3LCR};
uint16 destIndex[7] = {kDoorFrameRight_D1C, kWall_D3R2, kWall_D1LCR_Flipped, kWall_D0R_Flipped, kWall_D0L_Flipped,
kWall_D2LCR_Flipped, kWall_D3LCR_Flipped};
2016-05-22 00:32:53 +02:00
// the original loads these flipped walls in loadCurrentMapGraphics
2016-05-21 19:36:24 +02:00
for (uint16 i = 0; i < 7; ++i) {
uint16 srcGraphicIndice = firstIndice + srcIndex[i];
2016-06-18 18:02:48 +02:00
uint16 w = getWidth(srcGraphicIndice), h = getHeight(srcGraphicIndice);
2016-05-21 19:36:24 +02:00
delete[] _wallSetBitMaps[destIndex[i]];
_wallSetBitMaps[destIndex[i]] = new byte[w * h];
blitToBitmap(_wallSetBitMaps[srcIndex[i]], w, h, _wallSetBitMaps[destIndex[i]], w);
if (srcIndex[i] != kWall_D2LCR && srcIndex[i] != kWall_D3LCR) // TODO: implement flipping of these two bitmaps, disabled with if
flipBitmapHorizontal(_wallSetBitMaps[destIndex[i]], w, h);
2016-05-19 16:26:56 +02:00
}
2016-05-21 19:36:24 +02:00
/*
uint16 graphicIndice = firstIndice + kWall_D2LCR;
uint16 w = width(graphicIndice), h = height(graphicIndice);
byte *tmp = new byte[w * h];
clearBitmap(tmp, w, h, kColorFlesh);
Box *box = &gBoxWallBitmap_D2LCR;
blitToBitmap(_wallSetBitMaps[kWall_D2LCR_Flipped], w, 8, 0, tmp, w, box->X1, box->X2, box->Y1, box->Y2, kColorNoTransparency);
delete[] _wallSetBitMaps[kWall_D2LCR_Flipped];
_wallSetBitMaps[kWall_D2LCR_Flipped] = tmp;
graphicIndice = firstIndice + kWall_D3LCR;
w = width(graphicIndice), h = height(graphicIndice);
tmp = new byte[w * h];
clearBitmap(tmp, w, h, kColorFlesh);
box = &gBoxWallBitmap_D3LCR;
blitToBitmap(_wallSetBitMaps[kWall_D3LCR_Flipped], w, 8, 0, tmp, w, box->X1, box->X2, box->Y1, box->Y2, kColorNoTransparency);
delete[] _wallSetBitMaps[kWall_D3LCR_Flipped];
_wallSetBitMaps[kWall_D3LCR_Flipped] = tmp;*/
}
void DisplayMan::loadCurrentMapGraphics() {
loadFloorSet(_vm->_dungeonMan->_currMap._map->_floorSet);
loadWallSet(_vm->_dungeonMan->_currMap._map->_wallSet);
2016-05-22 00:32:53 +02:00
// the original loads some flipped walls here, I moved it to loadWallSet
for (uint16 i = 0, firstGraphicIndex = _vm->_dungeonMan->_currMap._map->_wallSet * kStairsGraphicCount + kFirstStairs; i < kStairsGraphicCount; ++i)
2016-05-22 00:32:53 +02:00
_stairIndices[i] = firstGraphicIndex + i;
for (int16 i = 0; i < kAlcoveOrnCount; ++i)
_currMapAlcoveOrnIndices[i] = -1;
for (int16 i = 0; i < kFountainOrnCount; ++i)
_currMapFountainOrnIndices[i] = -1;
uint16 alcoveCount = 0;
uint16 fountainCount = 0;
Map &currMap = *_vm->_dungeonMan->_currMap._map;
_currMapViAltarIndex = -1;
2016-06-18 17:48:48 +02:00
for (uint16 i = 0; i < currMap._wallOrnCount; ++i) {
uint16 ornIndice = _currMapWallOrnIndices[i];
uint16 nativeIndice = kFirstWallOrn + ornIndice * 2;
_currMapWallOrnInfo[i][kNativeBitmapIndex] = nativeIndice;
for (uint16 ornCounter = 0; ornCounter < kAlcoveOrnCount; ++ornCounter) {
if (ornIndice == gAlcoveOrnIndices[ornCounter]) {
_currMapAlcoveOrnIndices[alcoveCount++] = i;
if (ornIndice == 2)
_currMapViAltarIndex = i;
}
}
for (uint16 ornCounter = 0; ornCounter < kFountainOrnCount; ++ornCounter)
if (ornIndice == gFountainOrnIndices[ornCounter])
_currMapFountainOrnIndices[fountainCount++] = i;
_currMapWallOrnInfo[i][kNativeCoordinateSet] = gWallOrnCoordSetIndices[ornIndice];
}
2016-06-18 17:48:48 +02:00
for (uint16 i = 0; i < currMap._floorOrnCount; ++i) {
uint16 ornIndice = _currMapFloorOrnIndices[i];
uint16 nativeIndice = kFirstFloorOrn + ornIndice * 6;
_currMapFloorOrnInfo[i][kNativeBitmapIndex] = nativeIndice;
_currMapFloorOrnInfo[i][kNativeCoordinateSet] = gFloorOrnCoordSetIndices[ornIndice];
}
2016-06-18 17:48:48 +02:00
for (uint16 i = 0; i < currMap._doorOrnCount; ++i) {
uint16 ornIndice = _currMapDoorOrnIndices[i];
uint16 nativeIndice = kFirstDoorOrn + ornIndice;
_currMapDoorOrnInfo[i][kNativeBitmapIndex] = nativeIndice;
_currMapDoorOrnInfo[i][kNativeCoordinateSet] = gDoorOrnCoordIndices[ornIndice];
}
applyCreatureReplColors(9, 8);
applyCreatureReplColors(10, 12);
2016-06-18 17:48:48 +02:00
for (uint16 creatureType = 0; creatureType < currMap._creatureTypeCount; ++creatureType) {
CreatureAspect &aspect = gCreatureAspects[_currMapAllowedCreatureTypes[creatureType]];
uint16 replColorOrdinal = aspect.getReplColour9();
if (replColorOrdinal)
2016-06-23 23:12:39 +02:00
applyCreatureReplColors(9, _vm->ordinalToIndex(replColorOrdinal));
replColorOrdinal = aspect.getReplColour10();
if (replColorOrdinal)
2016-06-23 23:12:39 +02:00
applyCreatureReplColors(10, _vm->ordinalToIndex(replColorOrdinal));
}
}
void DisplayMan::applyCreatureReplColors(int replacedColor, int replacementColor) {
for (int16 i = 0; i < 6; ++i)
2016-06-18 18:02:48 +02:00
gPalDungeonView[i][replacedColor] = gCreatureReplColorSets[replacementColor]._RGBColor[i];
2016-06-18 18:02:48 +02:00
gPalChangesCreature_D2[replacedColor] = gCreatureReplColorSets[replacementColor]._D2ReplacementColor;
gPalChangesCreature_D3[replacedColor] = gCreatureReplColorSets[replacementColor]._D3ReplacementColor;
}
2016-05-22 00:32:53 +02:00
void DisplayMan::drawFloorPitOrStairsBitmap(StairIndex relIndex, Frame &f) {
2016-06-18 18:02:48 +02:00
if (f._srcWidth) {
blitToScreen(_bitmaps[_stairIndices[relIndex]], f._srcWidth, f._srcX, f._srcY, f._destFromX, f._destToX, f._destFromY, f._destToY, kColorFlesh, gDungeonViewport);
2016-05-22 00:32:53 +02:00
}
}
void DisplayMan::drawFloorPitOrStairsBitmapFlippedHorizontally(StairIndex relIndex, Frame &f) {
2016-06-18 18:02:48 +02:00
if (f._srcWidth) {
blitToBitmap(_bitmaps[_stairIndices[relIndex]], f._srcWidth, f._srcHeight, _tmpBitmap, f._srcWidth);
flipBitmapHorizontal(_tmpBitmap, f._srcWidth, f._srcHeight);
blitToScreen(_tmpBitmap, f._srcWidth, f._srcX, f._srcY, f._destFromX, f._destToX, f._destFromY, f._destToY, kColorFlesh, gDungeonViewport);
2016-05-22 00:32:53 +02:00
}
}
2016-06-17 22:34:03 +02:00
Box gBoxWallPatchBehindInscription = Box(110, 113, 37, 63); // @ G0202_ac_Graphic558_Box_WallPatchBehindInscription
byte gInscriptionLineY[4] = { // @ G0203_auc_Graphic558_InscriptionLineY
48, /* 1 Line */
59, /* 2 lines */
75, /* 3 lines */
86}; /* 4 lines */
byte gWallOrnDerivedBitmapIndexIncrement[12] = { // @ G0190_auc_Graphic558_WallOrnamentDerivedBitmapIndexIncrement
0, /* D3L Right */
0, /* D3R Left */
1, /* D3L Front */
1, /* D3C Front */
1, /* D3R Front */
2, /* D2L Right */
2, /* D2R Left */
3, /* D2L Front */
3, /* D2C Front */
3, /* D2R Front */
4, /* D1L Right */
4}; /* D1R Left */
byte gPalChangesDoorButtonAndWallOrn_D3[16] = {0, 0, 120, 30, 40, 30, 0, 60, 30, 90, 100, 110, 0, 10, 0, 20}; // @ G0198_auc_Graphic558_PaletteChanges_DoorButtonAndWallOrnament_D3
byte gPalChangesDoorButtonAndWallOrn_D2[16] = {0, 120, 10, 30, 40, 30, 60, 70, 50, 90, 100, 110, 0, 20, 140, 130}; // @ G0199_auc_Graphic558_PaletteChanges_DoorButtonAndWallOrnament_D2
byte gUnreadableInscriptionBoxY2[15] = { // @ G0204_auc_Graphic558_UnreadableInscriptionBoxY2
/* { Y for 1 line, Y for 2 lines, Y for 3 lines } */
45, 48, 53, /* D3L Right, D3R Left */
43, 49, 56, /* D3L Front, D3C Front, D3R Front */
42, 49, 56, /* D2L Right, D2R Left */
46, 53, 63, /* D2L Front, D2C Front, D2R Front */
46, 57, 68}; /* D1L Right, D1R Left */
2016-06-17 22:34:03 +02:00
Box gBoxChampionPortraitOnWall = Box(96, 127, 35, 63); // G0109_s_Graphic558_Box_ChampionPortraitOnWall
bool DisplayMan::isDrawnWallOrnAnAlcove(int16 wallOrnOrd, ViewWall viewWallIndex) {
byte *bitmapGreen;
byte *bitmapRed;
int16 coordinateSetOffset;
bool flipHorizontal;
bool isInscription;
bool isAlcove;
Frame frame;
unsigned char inscriptionString[70];
if (wallOrnOrd) {
int16 var_X;
int16 wallOrnIndex = wallOrnOrd - 1;
int16 nativeBitmapIndex = _currMapWallOrnInfo[wallOrnIndex][kNativeBitmapIndex];
uint16 *coordinateSetA = gWallOrnCoordSets[_currMapWallOrnInfo[wallOrnIndex][kNativeCoordinateSet]][viewWallIndex];
isAlcove = _vm->_dungeonMan->isWallOrnAnAlcove(wallOrnIndex);
2016-06-22 00:37:58 +02:00
isInscription = (wallOrnIndex == _vm->_dungeonMan->_currMapInscriptionWallOrnIndex);
if (isInscription) {
_vm->_dungeonMan->decodeText((char*)inscriptionString, _inscriptionThing, kTextTypeInscription);
}
if (viewWallIndex >= kViewWall_D1L_RIGHT) {
if (viewWallIndex == kViewWall_D1C_FRONT) {
if (isInscription) {
Frame &D1CFrame = gFrameWalls[kViewSquare_D1C];
2016-06-18 18:02:48 +02:00
blitToScreen(_wallSetBitMaps[kWall_D1LCR], D1CFrame._srcWidth, 94, 28, gBoxWallPatchBehindInscription._x1, gBoxWallPatchBehindInscription._x2,
gBoxWallPatchBehindInscription._y1, gBoxWallPatchBehindInscription._y2, kColorNoTransparency, gDungeonViewport);
unsigned char *string = inscriptionString;
bitmapRed = _bitmaps[kInscriptionFontIndice];
int16 textLineIndex = 0;
do {
int16 characterCount = 0;
unsigned char *character = string;
while (*character++ < 0x80) {
characterCount++;
}
2016-06-18 18:02:48 +02:00
frame._destToX = (frame._destFromX = 112 - (characterCount * 4)) + 7;
frame._destFromY = (frame._destToY = gInscriptionLineY[textLineIndex++]) - 7;
while (characterCount--) {
2016-06-18 18:02:48 +02:00
blitToScreen(bitmapRed, 288, (*string++) * 8, 0, frame._destFromX, frame._destToX, frame._destFromY, frame._destToY, kColorFlesh, gDungeonViewport);
frame._destFromX += 8;
frame._destToX += 8;
}
} while (*string++ != 0x81);
return isAlcove;
}
nativeBitmapIndex++;
_vm->_dungeonMan->_dungeonViewClickableBoxes[kViewCellDoorButtonOrWallOrn]._x1 = coordinateSetA[0];
_vm->_dungeonMan->_dungeonViewClickableBoxes[kViewCellDoorButtonOrWallOrn]._x2 = coordinateSetA[1];
_vm->_dungeonMan->_dungeonViewClickableBoxes[kViewCellDoorButtonOrWallOrn]._y1 = coordinateSetA[2];
_vm->_dungeonMan->_dungeonViewClickableBoxes[kViewCellDoorButtonOrWallOrn]._y2 = coordinateSetA[3];
_vm->_dungeonMan->_isFacingAlcove = isAlcove;
_vm->_dungeonMan->_isFacingViAltar = (wallOrnIndex == _currMapViAltarIndex);
_vm->_dungeonMan->_isFacingFountain = false;
for (int16 fountainOrnIndex = 0; fountainOrnIndex < kFountainOrnCount; ++fountainOrnIndex) {
if (_currMapFountainOrnIndices[fountainOrnIndex] == wallOrnIndex) {
_vm->_dungeonMan->_isFacingFountain = true;
break;
}
}
}
bitmapGreen = _bitmaps[nativeBitmapIndex];
if (viewWallIndex == kViewWall_D1R_LEFT) {
blitToBitmap(bitmapGreen, coordinateSetA[4], coordinateSetA[5], _tmpBitmap, coordinateSetA[4]);
flipBitmapHorizontal(_tmpBitmap, coordinateSetA[4], coordinateSetA[5]);
bitmapGreen = _tmpBitmap;
}
var_X = 0;
} else {
coordinateSetOffset = 0;
uint16 *coordSetB;
int16 wallOrnCoordSetIndex = _currMapWallOrnInfo[wallOrnIndex][kNativeCoordinateSet];
2016-06-22 00:37:58 +02:00
flipHorizontal = (viewWallIndex == kViewWall_D2R_LEFT) || (viewWallIndex == kViewWall_D3R_LEFT);
if (flipHorizontal) {
coordSetB = gWallOrnCoordSets[wallOrnCoordSetIndex][kViewWall_D1R_LEFT];
} else if ((viewWallIndex == kViewWall_D2L_RIGHT) || (viewWallIndex == kViewWall_D3L_RIGHT)) {
coordSetB = gWallOrnCoordSets[wallOrnCoordSetIndex][kViewWall_D1L_RIGHT];
} else {
nativeBitmapIndex++;
coordSetB = gWallOrnCoordSets[wallOrnCoordSetIndex][kViewWall_D1C_FRONT];
if (viewWallIndex == kViewWall_D2L_FRONT) {
coordinateSetOffset = 6;
} else if (viewWallIndex == kViewWall_D2R_FRONT) {
coordinateSetOffset = -6;
}
}
int16 pixelWidth = (coordinateSetA + coordinateSetOffset)[1] - (coordinateSetA + coordinateSetOffset)[0];
blitToBitmapShrinkWithPalChange(_bitmaps[nativeBitmapIndex], coordSetB[4] << 1, coordSetB[5], _tmpBitmap, pixelWidth + 1, coordinateSetA[5],
(viewWallIndex <= kViewWall_D3R_FRONT) ? gPalChangesDoorButtonAndWallOrn_D3 : gPalChangesDoorButtonAndWallOrn_D2);
bitmapGreen = _bitmaps[nativeBitmapIndex];
var_X = pixelWidth;
if (flipHorizontal) {
2016-06-20 18:03:48 +02:00
if (bitmapGreen != _tmpBitmap)
blitToBitmap(bitmapGreen, coordSetB[4], coordSetB[5], _tmpBitmap, coordSetB[4]);
flipBitmapHorizontal(_tmpBitmap, coordSetB[4], coordSetB[5]);
bitmapGreen = _tmpBitmap;
var_X = 15 - (var_X & 0xF);
} else if (viewWallIndex == kViewWall_D2L_FRONT) {
var_X -= coordinateSetA[1] - coordinateSetA[0];
} else {
var_X = 0;
}
}
if (isInscription) {
unsigned char *string = inscriptionString;
int16 unreadableTextLineCount = 0;
do {
while (*string < 0x80) {
string++;
}
unreadableTextLineCount++;
} while (*string++ != 0x81);
if (unreadableTextLineCount < 4) {
2016-06-18 18:02:48 +02:00
frame._destFromX = coordinateSetA[0];
frame._destToX = coordinateSetA[1];
frame._destFromY = coordinateSetA[2];
frame._destToY = coordinateSetA[3];
frame._srcWidth = coordinateSetA[4];
frame._srcHeight = coordinateSetA[5];
2016-06-18 18:02:48 +02:00
coordinateSetA = &frame._destFromX;
coordinateSetA[3] = gUnreadableInscriptionBoxY2[gWallOrnDerivedBitmapIndexIncrement[viewWallIndex] * 3 + unreadableTextLineCount - 1];
}
}
blitToScreen(bitmapGreen, coordinateSetA[4], var_X, 0, coordinateSetA[0], coordinateSetA[1], coordinateSetA[2], coordinateSetA[3], kColorFlesh, gDungeonViewport);
if ((viewWallIndex == kViewWall_D1C_FRONT) && _championPortraitOrdinal--) {
Box &box = gBoxChampionPortraitOnWall;
2016-06-18 18:02:48 +02:00
blitToScreen(_bitmaps[kChampionPortraitsIndice], 256, (_championPortraitOrdinal & 0x7) << 5, (_championPortraitOrdinal >> 3) * 29, box._x1, box._x2, box._y1, box._y2,
kColorDarkGary, gDungeonViewport);
}
return isAlcove;
}
return false;
}
void DisplayMan::blitToBitmapShrinkWithPalChange(byte *srcBitmap, int16 srcWidth, int16 srcHeight, byte *destBitmap, int16 destWidth, int16 destHeight, byte *palChange) {
double rateW = srcWidth / destWidth;
double rateH = srcHeight / destHeight;
for (uint16 y = 0; y < destHeight; ++y) {
for (uint16 x = 0; x < destWidth; ++x) {
if (palChange)
destBitmap[y * destWidth + x] = palChange[srcBitmap[(int)(y * rateH * srcWidth) + (int)(x * rateW)]];
else
destBitmap[y * destWidth + x] = srcBitmap[(int)(y * rateH * srcWidth) + (int)(x * rateW)];
}
}
}
byte* DisplayMan::getBitmap(uint16 index) {
return _bitmaps[index];
}
2016-06-19 11:47:22 +02:00
Common::MemoryReadStream DisplayMan::getCompressedData(uint16 index) {
return Common::MemoryReadStream(_packedBitmaps + _packedItemPos[index], getCompressedDataSize(index), DisposeAfterUse::NO);
}
uint32 DisplayMan::getCompressedDataSize(uint16 index) {
return _packedItemPos[index + 1] - _packedItemPos[index];
}
2016-06-19 18:05:19 +02:00
void DisplayMan::clearScreenBox(Color color, Box &box, Viewport &viewport) {
2016-06-19 11:47:22 +02:00
uint16 width = box._x2 - box._x1;
for (int y = box._y1 + viewport._posY; y < box._y2 + viewport._posY; ++y)
memset(_vgaBuffer + y * _screenWidth + box._x1 + viewport._posX, color, sizeof(byte) * width);
2016-06-19 11:47:22 +02:00
}
2016-06-20 18:03:48 +02:00
void DisplayMan::blitToScreen(byte *srcBitmap, uint16 srcWidth, uint16 srcX, uint16 srcY,
Box &box,
Color transparent, Viewport &viewport) {
2016-06-20 18:03:48 +02:00
blitToScreen(srcBitmap, srcWidth, srcX, srcY, box._x1, box._x2, box._y1, box._y2, transparent, viewport);
}
}