1 /* ScummVM - Graphic Adventure Engine
2  *
3  * ScummVM is the legal property of its developers, whose names
4  * are too numerous to list here. Please refer to the COPYRIGHT
5  * file distributed with this source distribution.
6  *
7  * This program is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU General Public License
9  * as published by the Free Software Foundation; either version 2
10  * of the License, or (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
20  *
21  */
22 
23 #ifndef TOLTECS_SCREEN_H
24 #define TOLTECS_SCREEN_H
25 
26 #include "graphics/surface.h"
27 #include "toltecs/toltecs.h"
28 
29 namespace Toltecs {
30 
31 struct DrawRequest {
32 	int16 x, y;
33 	int16 resIndex;
34 	uint16 flags;
35 	int16 baseColor;
36 	int8 scaling;
37 };
38 
39 struct SpriteDrawItem {
40 	int16 x, y;
41 	int16 width, height;
42 	int16 origWidth, origHeight;
43 	int16 resIndex, frameNum;
44 	uint32 offset;
45 	int16 xdelta, ydelta;
46 	uint16 flags;
47 	int16 skipX, yerror;
48 	int16 priority;
49 	int16 baseColor;
50 };
51 
52 struct SpriteFrameEntry {
53 	int16 y, x, h, w;
54 	uint32 offset;
SpriteFrameEntrySpriteFrameEntry55 	SpriteFrameEntry() {
56 	}
SpriteFrameEntrySpriteFrameEntry57 	SpriteFrameEntry(byte *data) {
58 		y = READ_LE_UINT16(data + 0);
59 		x = READ_LE_UINT16(data + 2);
60 		h = READ_LE_UINT16(data + 4);
61 		w = READ_LE_UINT16(data + 6);
62 		offset = READ_LE_UINT32(data + 8);
63 	}
64 };
65 
66 class Font {
67 public:
Font(byte * fontData)68 	Font(byte *fontData) : _fontData(fontData) {
69 	}
~Font()70 	~Font() {
71 	}
getSpacing()72 	int16 getSpacing() const {
73 		return _fontData[1];
74 	}
getHeight()75 	int16 getHeight() const {
76 		return _fontData[2];
77 	}
getWidth()78 	int16 getWidth() const {
79 		return _fontData[3];
80 	}
getCharWidth(byte ch)81 	int16 getCharWidth(byte ch) const {
82 		return _fontData[4 + (ch - 0x21)];
83 	}
getCharData(byte ch)84 	byte *getCharData(byte ch) const {
85 		return _fontData + 0x298 + READ_LE_UINT16(&_fontData[0xE0 + (ch - 0x21) * 2]);
86 	}
getTextWidth(const byte * text)87 	int16 getTextWidth(const byte *text) {
88 		int16 width = 0;
89 		while (*text && *text < 0xF0) {
90 			byte ch = *text++;
91 			if (ch <= 0x20) {
92 				width += getWidth();
93 			} else {
94 				width += getCharWidth(ch) + getSpacing() - 1;
95 			}
96 		}
97 		return width;
98 	}
99 
100 protected:
101 	byte *_fontData;
102 };
103 
104 struct PixelPacket {
105 	byte count;
106 	byte pixel;
107 };
108 
109 enum SpriteReaderStatus {
110 	kSrsPixelsLeft,
111 	kSrsEndOfLine,
112 	kSrsEndOfSprite
113 };
114 
115 class SpriteFilter {
116 public:
SpriteFilter(const SpriteDrawItem & sprite)117 	SpriteFilter(const SpriteDrawItem &sprite) : _sprite(&sprite) {
118 	}
~SpriteFilter()119 	virtual ~SpriteFilter() {}
120 	virtual SpriteReaderStatus readPacket(PixelPacket &packet) = 0;
121 protected:
122 	const SpriteDrawItem *_sprite;
123 };
124 
125 struct TextRect {
126 	int16 x, y;
127 	int16 width, length;
128 };
129 
130 struct TalkTextItem {
131 	int16 duration;
132 	int16 slotIndex;
133 	int16 slotOffset;
134 	int16 fontNum;
135 	byte color;
136 	byte lineCount;
137 	TextRect lines[15];
138 	bool alwaysDisplayed;
139 };
140 
141 struct GuiTextWrapState {
142 	int16 len1, len2;
143 	byte *sourceString;
144 	byte *destString;
145 	int16 width;
146 	byte textBuffer[100];
147 };
148 
149 class RenderQueue;
150 
151 class Screen {
152 public:
153 	Screen(ToltecsEngine *vm);
154 	~Screen();
155 
156 	void unpackRle(byte *source, byte *dest, uint16 width, uint16 height);
157 
158 	void loadMouseCursor(uint resIndex);
159 
160 	void drawGuiImage(int16 x, int16 y, uint resIndex);
161 
162 	void startShakeScreen(int16 shakeCounter);
163 	void stopShakeScreen();
164 	bool updateShakeScreen();
165 
166 	// Sprite list
167 	void addStaticSprite(byte *spriteItem);
168 	void addAnimatedSprite(int16 x, int16 y, int16 fragmentId, byte *data, int16 *spriteArray, bool loop, int mode);
169 
170 	// Sprite drawing
171 	void drawSprite(const SpriteDrawItem &sprite);
172 	void drawSpriteCore(byte *dest, SpriteFilter &reader, const SpriteDrawItem &sprite);
173 	void blastSprite(int16 x, int16 y, int16 fragmentId, int16 resIndex, uint16 flags);
174 
175 	// Verb line
176 	void updateVerbLine(int16 slotIndex, int16 slotOffset);
177 
178 	// Talk text
179 	void updateTalkText(int16 slotIndex, int16 slotOffset, bool alwaysDisplayed);
180 	void addTalkTextRect(Font &font, int16 x, int16 &y, int16 length, int16 width, TalkTextItem *item);
181 	void addTalkTextItemsToRenderQueue();
182 	int16 getTalkTextDuration();
183 	bool isTalkTextActive(int16 slotIndex);
184 	void finishTalkTextItem(int16 slotIndex);
185 	void finishTalkTextItems();
186 	void keepTalkTextItemsAlive();
187 
188 	// Font/text
189 	void registerFont(uint fontIndex, uint resIndex);
190 	void drawGuiTextMulti(byte *textData);
191 	int16 wrapGuiText(uint fontResIndex, int maxWidth, GuiTextWrapState &wrapState);
192 	void drawGuiText(int16 x, int16 y, byte fontColor1, byte fontColor2, uint fontResIndex, GuiTextWrapState &wrapState);
193 
194 	int16 drawString(int16 x, int16 y, byte color, uint fontResIndex, const byte *text, int len = -1, int16 *ywobble = NULL, bool outline = false);
195 	void drawChar(const Font &font, byte *dest, int16 x, int16 y, byte ch, byte color, bool outline);
196 
197 	void drawSurface(int16 x, int16 y, Graphics::Surface *surface);
198 
199 	void saveState(Common::WriteStream *out);
200 	void loadState(Common::ReadStream *in);
201 
getFontResIndex(int fontNum)202 	uint getFontResIndex(int fontNum) const { return _fontResIndexArray[fontNum]; }
203 
204 //protected:
205 public:
206 
207 	struct VerbLineItem {
208 		int16 slotIndex;
209 		int16 slotOffset;
210 	};
211 
212 	struct Rect {
213 		int16 x, y, width, height;
214 	};
215 
216 	ToltecsEngine *_vm;
217 
218 	byte *_frontScreen, *_backScreen;
219 
220 	uint _fontResIndexArray[10];
221 	byte _fontColor1, _fontColor2;
222 
223 	// Screen shaking
224 	bool _shakeActive;
225 	uint32 _shakeTime;
226 	int16 _shakeCounterInit, _shakeCounter;
227 	int _shakePos;
228 
229 	// Verb line
230 	int16 _verbLineNum;
231 	VerbLineItem _verbLineItems[8];
232 	int16 _verbLineX, _verbLineY, _verbLineWidth;
233 	int16 _verbLineCount;
234 
235 	// Talk text
236 	int16 _talkTextX, _talkTextY;
237 	int16 _talkTextMaxWidth;
238 	byte _talkTextFontColor;
239 	int16 _talkTextItemNum;
240 	TalkTextItem _talkTextItems[5];
241 
242 	RenderQueue *_renderQueue;
243 	bool _fullRefresh;
244 	bool _guiRefresh;
245 
246 	bool createSpriteDrawItem(const DrawRequest &drawRequest, SpriteDrawItem &sprite);
247 	void addDrawRequest(const DrawRequest &drawRequest);
248 
249 };
250 
251 } // End of namespace Toltecs
252 
253 #endif /* TOLTECS_SCREEN_H */
254