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
24
25 #include "agos/agos.h"
26 #include "agos/intern.h"
27
28 namespace AGOS {
29
30 #define OPCODE(x) _OPCODE(AGOSEngine_Elvira2, x)
31
setupOpcodes()32 void AGOSEngine_Elvira2::setupOpcodes() {
33 static const OpcodeEntryElvira2 opcodes[] = {
34 /* 00 */
35 OPCODE(o_invalid),
36 OPCODE(o_at),
37 OPCODE(o_notAt),
38 OPCODE(o_invalid),
39 /* 04 */
40 OPCODE(o_invalid),
41 OPCODE(o_carried),
42 OPCODE(o_notCarried),
43 OPCODE(o_isAt),
44 /* 08 */
45 OPCODE(oe1_isNotAt),
46 OPCODE(oe1_sibling),
47 OPCODE(oe1_notSibling),
48 OPCODE(o_zero),
49 /* 12 */
50 OPCODE(o_notZero),
51 OPCODE(o_eq),
52 OPCODE(o_notEq),
53 OPCODE(o_gt),
54 /* 16 */
55 OPCODE(o_lt),
56 OPCODE(o_eqf),
57 OPCODE(o_notEqf),
58 OPCODE(o_ltf),
59 /* 20 */
60 OPCODE(o_gtf),
61 OPCODE(oe1_isIn),
62 OPCODE(oe1_isNotIn),
63 OPCODE(o_chance),
64 /* 24 */
65 OPCODE(oe1_isPlayer),
66 OPCODE(o_isRoom),
67 OPCODE(o_isObject),
68 OPCODE(o_state),
69 /* 28 */
70 OPCODE(o_oflag),
71 OPCODE(oe1_canPut),
72 OPCODE(o_invalid),
73 OPCODE(o_destroy),
74 /* 32 */
75 OPCODE(o_invalid),
76 OPCODE(o_place),
77 OPCODE(oe1_copyof),
78 OPCODE(oe1_copyfo),
79 /* 36 */
80 OPCODE(o_copyff),
81 OPCODE(oe1_whatO),
82 OPCODE(o_invalid),
83 OPCODE(oe1_weigh),
84 /* 40 */
85 OPCODE(o_invalid),
86 OPCODE(o_clear),
87 OPCODE(o_let),
88 OPCODE(o_add),
89 /* 44 */
90 OPCODE(o_sub),
91 OPCODE(o_addf),
92 OPCODE(o_subf),
93 OPCODE(o_mul),
94 /* 48 */
95 OPCODE(o_div),
96 OPCODE(o_mulf),
97 OPCODE(o_divf),
98 OPCODE(o_mod),
99 /* 52 */
100 OPCODE(o_modf),
101 OPCODE(o_random),
102 OPCODE(oe2_moveDirn),
103 OPCODE(o_goto),
104 /* 56 */
105 OPCODE(o_oset),
106 OPCODE(o_oclear),
107 OPCODE(o_putBy),
108 OPCODE(o_inc),
109 /* 60 */
110 OPCODE(o_dec),
111 OPCODE(o_setState),
112 OPCODE(o_print),
113 OPCODE(o_message),
114 /* 64 */
115 OPCODE(o_msg),
116 OPCODE(o_invalid),
117 OPCODE(o_invalid),
118 OPCODE(o_invalid),
119 /* 68 */
120 OPCODE(o_end),
121 OPCODE(o_done),
122 OPCODE(o_invalid),
123 OPCODE(o_process),
124 /* 72 */
125 OPCODE(oe2_doClass),
126 OPCODE(oe2_pObj),
127 OPCODE(oe1_pName),
128 OPCODE(oe1_pcName),
129 /* 76 */
130 OPCODE(o_when),
131 OPCODE(o_if1),
132 OPCODE(o_if2),
133 OPCODE(oe2_isCalled),
134 /* 80 */
135 OPCODE(o_is),
136 OPCODE(o_invalid),
137 OPCODE(o_debug),
138 OPCODE(oe1_rescan),
139 /* 84 */
140 OPCODE(o_invalid),
141 OPCODE(o_invalid),
142 OPCODE(o_invalid),
143 OPCODE(o_comment),
144 /* 88 */
145 OPCODE(o_invalid),
146 OPCODE(oe1_loadGame),
147 OPCODE(o_getParent),
148 OPCODE(o_getNext),
149 /* 92 */
150 OPCODE(o_getChildren),
151 OPCODE(o_invalid),
152 OPCODE(oe1_findMaster),
153 OPCODE(oe1_nextMaster),
154 /* 96 */
155 OPCODE(o_picture),
156 OPCODE(o_loadZone),
157 OPCODE(oe1_animate),
158 OPCODE(oe1_stopAnimate),
159 /* 100 */
160 OPCODE(o_killAnimate),
161 OPCODE(o_defWindow),
162 OPCODE(o_window),
163 OPCODE(o_cls),
164 /* 104 */
165 OPCODE(o_closeWindow),
166 OPCODE(oe2_menu),
167 OPCODE(o_invalid),
168 OPCODE(o_addBox),
169 /* 108 */
170 OPCODE(o_delBox),
171 OPCODE(o_enableBox),
172 OPCODE(o_disableBox),
173 OPCODE(o_moveBox),
174 /* 112 */
175 OPCODE(o_invalid),
176 OPCODE(oe2_drawItem),
177 OPCODE(o_doIcons),
178 OPCODE(o_isClass),
179 /* 116 */
180 OPCODE(o_setClass),
181 OPCODE(o_unsetClass),
182 OPCODE(o_invalid),
183 OPCODE(o_waitSync),
184 /* 120*/
185 OPCODE(o_sync),
186 OPCODE(o_defObj),
187 OPCODE(o_invalid),
188 OPCODE(oe1_setTime),
189 /* 124 */
190 OPCODE(oe1_ifTime),
191 OPCODE(o_here),
192 OPCODE(o_doClassIcons),
193 OPCODE(o_playTune),
194 /* 128 */
195 OPCODE(o_invalid),
196 OPCODE(o_invalid),
197 OPCODE(o_setAdjNoun),
198 OPCODE(o_invalid),
199 /* 132 */
200 OPCODE(o_saveUserGame),
201 OPCODE(o_loadUserGame),
202 OPCODE(o_invalid),
203 OPCODE(oe2_pauseGame),
204 /* 136 */
205 OPCODE(o_copysf),
206 OPCODE(o_restoreIcons),
207 OPCODE(o_freezeZones),
208 OPCODE(o_placeNoIcons),
209 /* 140 */
210 OPCODE(o_clearTimers),
211 OPCODE(o_setDollar),
212 OPCODE(o_isBox),
213 OPCODE(oe2_doTable),
214 /* 144 */
215 OPCODE(oe2_setDoorOpen),
216 OPCODE(oe2_setDoorClosed),
217 OPCODE(oe2_setDoorLocked),
218 OPCODE(oe2_setDoorClosed),
219 /* 148 */
220 OPCODE(oe2_ifDoorOpen),
221 OPCODE(oe2_ifDoorClosed),
222 OPCODE(oe2_ifDoorLocked),
223 OPCODE(oe2_storeItem),
224 /* 152 */
225 OPCODE(oe2_getItem),
226 OPCODE(oe2_bSet),
227 OPCODE(oe2_bClear),
228 OPCODE(oe2_bZero),
229 /* 156 */
230 OPCODE(oe2_bNotZero),
231 OPCODE(oe2_getOValue),
232 OPCODE(oe2_setOValue),
233 OPCODE(o_invalid),
234 /* 160 */
235 OPCODE(oe2_ink),
236 OPCODE(oe2_printStats),
237 OPCODE(o_invalid),
238 OPCODE(o_invalid),
239 /* 164 */
240 OPCODE(o_invalid),
241 OPCODE(oe2_setSuperRoom),
242 OPCODE(oe2_getSuperRoom),
243 OPCODE(oe2_setExitOpen),
244 /* 168 */
245 OPCODE(oe2_setExitClosed),
246 OPCODE(oe2_setExitLocked),
247 OPCODE(oe2_setExitClosed),
248 OPCODE(oe2_ifExitOpen),
249 /* 172 */
250 OPCODE(oe2_ifExitClosed),
251 OPCODE(oe2_ifExitLocked),
252 OPCODE(oe2_playEffect),
253 OPCODE(oe2_getDollar2),
254 /* 176 */
255 OPCODE(oe2_setSRExit),
256 OPCODE(oe2_printPlayerDamage),
257 OPCODE(oe2_printMonsterDamage),
258 OPCODE(oe2_isAdjNoun),
259 /* 180 */
260 OPCODE(oe2_b2Set),
261 OPCODE(oe2_b2Clear),
262 OPCODE(oe2_b2Zero),
263 OPCODE(oe2_b2NotZero)
264 };
265
266 _opcodesElvira2 = opcodes;
267 _numOpcodes = 184;
268 }
269
executeOpcode(int opcode)270 void AGOSEngine_Elvira2::executeOpcode(int opcode) {
271 OpcodeProcElvira2 op = _opcodesElvira2[opcode].proc;
272 (this->*op) ();
273 }
274
275 // -----------------------------------------------------------------------
276 // Elvira 2 Opcodes
277 // -----------------------------------------------------------------------
278
oe2_moveDirn()279 void AGOSEngine_Elvira2::oe2_moveDirn() {
280 // 54: move direction
281 int16 d = getVarOrByte();
282 moveDirn(me(), d);
283 }
284
oe2_doClass()285 void AGOSEngine_Elvira2::oe2_doClass() {
286 // 72: do class
287 Item *i = getNextItemPtr();
288 byte cm = getByte();
289 int16 num = getVarOrWord();
290
291 _classMask = (cm != 0xFF) ? 1 << cm : 0;
292 _classLine = (SubroutineLine *)((byte *)_currentTable + _currentLine->next);
293 if (num == 1) {
294 _subjectItem = findInByClass(i, (1 << cm));
295 if (_subjectItem)
296 _classMode1 = 1;
297 else
298 _classMode1 = 0;
299 } else {
300 _objectItem = findInByClass(i, (1 << cm));
301 if (_objectItem)
302 _classMode2 = 1;
303 else
304 _classMode2 = 0;
305 }
306 }
307
oe2_pObj()308 void AGOSEngine_Elvira2::oe2_pObj() {
309 // 73: print object
310 SubObject *subObject = (SubObject *)findChildOfType(getNextItemPtr(), kObjectType);
311
312 if (subObject != NULL && subObject->objectFlags & kOFText)
313 showMessageFormat("%s", (const char *)getStringPtrByID(subObject->objectFlagValue[0]));
314 }
315
oe2_isCalled()316 void AGOSEngine_Elvira2::oe2_isCalled() {
317 // 79: childstruct fr2 is
318 Item *i = getNextItemPtr();
319 uint stringId = getNextStringID();
320 setScriptCondition(i->itemName == stringId);
321 }
322
oe2_menu()323 void AGOSEngine_Elvira2::oe2_menu() {
324 // 105: set agos menu
325 _agosMenu = getVarOrByte();
326 }
327
oe2_drawItem()328 void AGOSEngine_Elvira2::oe2_drawItem() {
329 // 113: draw item
330 Item *i = getNextItemPtr();
331 int a = getVarOrByte();
332 int x = getVarOrWord();
333 int y = getVarOrWord();
334 mouseOff();
335 drawIcon(_windowArray[a % 8], itemGetIconNumber(i), x, y);
336 mouseOn();
337 }
338
oe2_doTable()339 void AGOSEngine_Elvira2::oe2_doTable() {
340 // 143: start item sub
341 Item *i = getNextItemPtr();
342
343 SubRoom *r = (SubRoom *)findChildOfType(i, kRoomType);
344 if (r != NULL) {
345 Subroutine *sub = getSubroutineByID(r->subroutine_id);
346 if (sub) {
347 startSubroutine(sub);
348 return;
349 }
350 }
351
352 if (getGameType() == GType_ELVIRA2) {
353 SubSuperRoom *sr = (SubSuperRoom *)findChildOfType(i, kSuperRoomType);
354 if (sr != NULL) {
355 Subroutine *sub = getSubroutineByID(sr->subroutine_id);
356 if (sub) {
357 startSubroutine(sub);
358 return;
359 }
360 }
361 }
362 }
363
oe2_pauseGame()364 void AGOSEngine_Elvira2::oe2_pauseGame() {
365 // 135: pause game
366 HitArea *ha;
367
368 uint32 pauseTime = getTime();
369 haltAnimation();
370
371 while (!shouldQuit()) {
372 _lastHitArea = NULL;
373 _lastHitArea3 = NULL;
374
375 while (!shouldQuit()) {
376 if (processSpecialKeys() != 0 || _lastHitArea3 != 0)
377 break;
378 delay(1);
379 }
380
381 ha = _lastHitArea;
382
383 if (ha == NULL) {
384 } else if (ha->id == 201) {
385 break;
386 }
387 }
388
389 restartAnimation();
390 _gameStoppedClock = getTime() - pauseTime + _gameStoppedClock;
391 }
392
oe2_setDoorOpen()393 void AGOSEngine_Elvira2::oe2_setDoorOpen() {
394 // 144: set door open
395 Item *i = getNextItemPtr();
396 setDoorState(i, getVarOrByte(), 1);
397 }
398
oe2_setDoorClosed()399 void AGOSEngine_Elvira2::oe2_setDoorClosed() {
400 // 145: set door closed
401 Item *i = getNextItemPtr();
402 setDoorState(i, getVarOrByte(), 2);
403 }
404
oe2_setDoorLocked()405 void AGOSEngine_Elvira2::oe2_setDoorLocked() {
406 // 146: set door locked
407 Item *i = getNextItemPtr();
408 setDoorState(i, getVarOrByte(), 3);
409 }
410
oe2_ifDoorOpen()411 void AGOSEngine_Elvira2::oe2_ifDoorOpen() {
412 // 148: if door open
413 Item *i = getNextItemPtr();
414 uint16 d = getVarOrByte();
415
416 if (getGameType() == GType_WW) {
417 // WORKAROUND bug #2686883: A NULL item can occur when
418 // walking through Jack the Ripper scene
419 if (i == NULL) {
420 setScriptCondition(false);
421 return;
422 }
423 }
424
425 setScriptCondition(getDoorState(i, d) == 1);
426 }
427
oe2_ifDoorClosed()428 void AGOSEngine_Elvira2::oe2_ifDoorClosed() {
429 // 149: if door closed
430 Item *i = getNextItemPtr();
431 uint16 d = getVarOrByte();
432 setScriptCondition(getDoorState(i, d) == 2);
433 }
434
oe2_ifDoorLocked()435 void AGOSEngine_Elvira2::oe2_ifDoorLocked() {
436 // 150: if door locked
437 Item *i=getNextItemPtr();
438 uint16 d = getVarOrByte();
439 setScriptCondition(getDoorState(i, d) == 3);
440 }
441
oe2_storeItem()442 void AGOSEngine_Elvira2::oe2_storeItem() {
443 // 151: set array6 to item
444 uint var = getVarOrByte();
445 Item *item = getNextItemPtr();
446 _itemStore[var] = item;
447 }
448
oe2_getItem()449 void AGOSEngine_Elvira2::oe2_getItem() {
450 // 152: set m1 to m3 to array 6
451 Item *item = _itemStore[getVarOrByte()];
452 uint var = getVarOrByte();
453 if (var == 1) {
454 _subjectItem = item;
455 } else {
456 _objectItem = item;
457 }
458 }
459
oe2_bSet()460 void AGOSEngine_Elvira2::oe2_bSet() {
461 // 153: set bit
462 setBitFlag(getVarWrapper(), true);
463 }
464
oe2_bClear()465 void AGOSEngine_Elvira2::oe2_bClear() {
466 // 154: clear bit
467 setBitFlag(getVarWrapper(), false);
468 }
469
oe2_bZero()470 void AGOSEngine_Elvira2::oe2_bZero() {
471 // 155: is bit clear
472 setScriptCondition(!getBitFlag(getVarWrapper()));
473 }
474
oe2_bNotZero()475 void AGOSEngine_Elvira2::oe2_bNotZero() {
476 // 156: is bit set
477 uint bit = getVarWrapper();
478
479 // WORKAROUND: Enable copy protection again, in cracked version.
480 if (getGameType() == GType_SIMON1 && _currentTable && _currentTable->id == 2962 && bit == 63) {
481 bit = 50;
482 }
483
484 setScriptCondition(getBitFlag(bit));
485 }
486
oe2_getOValue()487 void AGOSEngine_Elvira2::oe2_getOValue() {
488 // 157: get item int prop
489 Item *item = getNextItemPtr();
490 SubObject *subObject = (SubObject *)findChildOfType(item, kObjectType);
491 uint prop = getVarOrByte();
492
493 if (subObject != NULL && subObject->objectFlags & (1 << prop) && prop < 16) {
494 uint offs = getOffsetOfChild2Param(subObject, 1 << prop);
495 writeNextVarContents(subObject->objectFlagValue[offs]);
496 } else {
497 writeNextVarContents(0);
498 }
499 }
500
oe2_setOValue()501 void AGOSEngine_Elvira2::oe2_setOValue() {
502 // 158: set item prop
503 Item *item = getNextItemPtr();
504 SubObject *subObject = (SubObject *)findChildOfType(item, kObjectType);
505 uint prop = getVarOrByte();
506 int value = getVarOrWord();
507
508 if (subObject != NULL && subObject->objectFlags & (1 << prop) && prop < 16) {
509 uint offs = getOffsetOfChild2Param(subObject, 1 << prop);
510 subObject->objectFlagValue[offs] = value;
511 }
512 }
513
oe2_ink()514 void AGOSEngine_Elvira2::oe2_ink() {
515 // 160
516 setTextColor(getVarOrByte());
517 }
518
oe2_printStats()519 void AGOSEngine_Elvira2::oe2_printStats() {
520 // 161: print stats
521 printStats();
522 }
523
oe2_setSuperRoom()524 void AGOSEngine_Elvira2::oe2_setSuperRoom() {
525 // 165: set super room
526 _superRoomNumber = getVarOrWord();
527 }
528
oe2_getSuperRoom()529 void AGOSEngine_Elvira2::oe2_getSuperRoom() {
530 // 166: get super room
531 writeNextVarContents(_superRoomNumber);
532 }
533
oe2_setExitOpen()534 void AGOSEngine_Elvira2::oe2_setExitOpen() {
535 // 167: set exit open
536 Item *i = getNextItemPtr();
537 uint16 n = getVarOrWord();
538 uint16 d = getVarOrByte();
539 setExitState(i, n, d, 1);
540 }
541
oe2_setExitClosed()542 void AGOSEngine_Elvira2::oe2_setExitClosed() {
543 // 168: set exit closed
544 Item *i = getNextItemPtr();
545 uint16 n = getVarOrWord();
546 uint16 d = getVarOrByte();
547 setExitState(i, n, d, 2);
548 }
549
oe2_setExitLocked()550 void AGOSEngine_Elvira2::oe2_setExitLocked() {
551 // 169: set exit locked
552 Item *i = getNextItemPtr();
553 uint16 n = getVarOrWord();
554 uint16 d = getVarOrByte();
555 setExitState(i, n, d, 3);
556 }
557
oe2_ifExitOpen()558 void AGOSEngine_Elvira2::oe2_ifExitOpen() {
559 // 171: if exit open
560 Item *i = getNextItemPtr();
561 uint16 n = getVarOrWord();
562 uint16 d = getVarOrByte();
563 setScriptCondition(getExitState(i, n, d) == 1);
564 }
565
oe2_ifExitClosed()566 void AGOSEngine_Elvira2::oe2_ifExitClosed() {
567 // 172: if exit closed
568 Item *i = getNextItemPtr();
569 uint16 n = getVarOrWord();
570 uint16 d = getVarOrByte();
571 setScriptCondition(getExitState(i, n, d) == 2);
572 }
573
oe2_ifExitLocked()574 void AGOSEngine_Elvira2::oe2_ifExitLocked() {
575 // 173: if exit locked
576 Item *i = getNextItemPtr();
577 uint16 n = getVarOrWord();
578 uint16 d = getVarOrByte();
579 setScriptCondition(getExitState(i, n, d) == 3);
580 }
581
oe2_playEffect()582 void AGOSEngine_Elvira2::oe2_playEffect() {
583 // 174: play sound
584 uint soundId = getVarOrWord();
585 loadSound(soundId, 0, 0);
586 }
587
oe2_getDollar2()588 void AGOSEngine_Elvira2::oe2_getDollar2() {
589 // 175
590 _showPreposition = true;
591
592 setup_cond_c_helper();
593
594 _objectItem = _hitAreaObjectItem;
595
596 if (_objectItem == _dummyItem2)
597 _objectItem = me();
598
599 if (_objectItem == _dummyItem3)
600 _objectItem = derefItem(me()->parent);
601
602 if (_objectItem != NULL) {
603 _scriptNoun2 = _objectItem->noun;
604 _scriptAdj2 = _objectItem->adjective;
605 } else {
606 _scriptNoun2 = -1;
607 _scriptAdj2 = -1;
608 }
609
610 _showPreposition = false;
611 }
612
oe2_setSRExit()613 void AGOSEngine_Elvira2::oe2_setSRExit() {
614 // 176: set super room exit
615 Item *i = getNextItemPtr();
616 uint n = getVarOrWord();
617 uint d = getVarOrByte();
618 uint s = getVarOrByte();
619 setSRExit(i, n, d, s);
620 }
621
oe2_printPlayerDamage()622 void AGOSEngine_Elvira2::oe2_printPlayerDamage() {
623 // 177: set player damage event
624 uint a = getVarOrByte();
625 if (_opcode177Var1 && !_opcode177Var2 && a != 0 && a <= 10) {
626 addVgaEvent(_vgaBaseDelay, PLAYER_DAMAGE_EVENT, NULL, 0, a);
627 _opcode177Var2 = 0;
628 _opcode177Var1 = 0;
629 }
630 }
631
oe2_printMonsterDamage()632 void AGOSEngine_Elvira2::oe2_printMonsterDamage() {
633 // 178: set monster damage event
634 uint a = getVarOrByte();
635 if (_opcode178Var1 && !_opcode178Var2 && a != 0 && a <= 10) {
636 addVgaEvent(_vgaBaseDelay, MONSTER_DAMAGE_EVENT, NULL, 0, a);
637 _opcode178Var2 = 0;
638 _opcode178Var1 = 0;
639 }
640 }
641
oe2_isAdjNoun()642 void AGOSEngine_Elvira2::oe2_isAdjNoun() {
643 // 179: item unk1 unk2 is
644 Item *item = getNextItemPtr();
645 int16 a = getNextWord();
646 int16 n = getNextWord();
647
648 if (getGameType() == GType_ELVIRA2 && item == NULL) {
649 // WORKAROUND bug #1745996: A NULL item can occur when
650 // interacting with items in the dinning room
651 setScriptCondition(false);
652 return;
653 }
654
655 assert(item);
656 setScriptCondition(item->adjective == a && item->noun == n);
657 }
658
oe2_b2Set()659 void AGOSEngine_Elvira2::oe2_b2Set() {
660 // 180: set bit2
661 uint bit = getVarOrByte();
662 _bitArrayTwo[bit / 16] |= (1 << (bit & 15));
663 }
664
oe2_b2Clear()665 void AGOSEngine_Elvira2::oe2_b2Clear() {
666 // 181: clear bit2
667 uint bit = getVarOrByte();
668 _bitArrayTwo[bit / 16] &= ~(1 << (bit & 15));
669 }
670
oe2_b2Zero()671 void AGOSEngine_Elvira2::oe2_b2Zero() {
672 // 182: is bit2 clear
673 uint bit = getVarOrByte();
674 setScriptCondition((_bitArrayTwo[bit / 16] & (1 << (bit & 15))) == 0);
675 }
676
oe2_b2NotZero()677 void AGOSEngine_Elvira2::oe2_b2NotZero() {
678 // 183: is bit2 set
679 uint bit = getVarOrByte();
680 setScriptCondition((_bitArrayTwo[bit / 16] & (1 << (bit & 15))) != 0);
681 }
682
printStats()683 void AGOSEngine_Elvira2::printStats() {
684 WindowBlock *window = _dummyWindow;
685 int val;
686 const uint8 y = (getPlatform() == Common::kPlatformAtariST) ? 132 : 134;
687
688 window->flags = 1;
689
690 mouseOff();
691
692 // Level
693 val = _variableArray[20];
694 if (val < -99)
695 val = -99;
696 if (val > 99)
697 val = 99;
698 writeChar(window, 10, y, 0, val);
699
700 // PP
701 val = _variableArray[22];
702 if (val < -99)
703 val = -99;
704 if (val > 99)
705 val = 99;
706 writeChar(window, 16, y, 6, val);
707
708 // HP
709 val = _variableArray[23];
710 if (val < -99)
711 val = -99;
712 if (val > 99)
713 val = 99;
714 writeChar(window, 23, y, 4, val);
715
716 // Experience
717 val = _variableArray[21];
718 if (val < -99)
719 val = -99;
720 if (val > 9999)
721 val = 9999;
722 writeChar(window, 30, y, 6, val / 100);
723 writeChar(window, 32, y, 2, val % 100);
724
725 mouseOn();
726 }
727
728 } // End of namespace AGOS
729