/* 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. * */ /* * This code is based on the original source code of Lord Avalot d'Argent version 1.3. * Copyright (c) 1994-1995 Mike, Mark and Thomas Thurman. */ #include "graph.h" /*#include "Crt.h"*/ /*$R+*/ namespace Avalanche { const array<1, 5, shortint> adjustment = {{7, 0, 7, 7, 7}}; const array<0, 3, byte> plane_to_use = {{2, 2, 2, 3}}; const array<1, 5, byte> waveorder = {{5, 1, 2, 3, 4}}; const array<1, 26, byte> glerkfade = {{1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4, 4, 4, 3, 3, 3, 2, 2, 1}}; const array<1, 18, byte> greldetfade = {{1, 2, 3, 4, 5, 6, 6, 6, 5, 5, 4, 4, 3, 3, 2, 2, 1, 1}}; enum flavourtype {ch_ega, ch_bgi, ch_natural, ch_two, ch_one, last_flavourtype}; struct chunkblocktype { flavourtype flavour; integer x, y; integer xl, yl; longint size; }; typedef array<1, 6, 0, 3, 0, 34, 1, 9, byte> glerktype; untyped_file f; chunkblocktype cb; array<1, 5, 2, 3, 0, 65, 0, 25, byte> ghost; byte fv; pointer memlevel; byte y, yy, bit, xofs; array<0, 1, pointer> eyes; pointer exclamation; array<1, 6, pointer> aargh; array<1, 3, pointer> bat; glerktype *glerk; array<1, 5, pointer> green_eyes; matrix<1, 6, false, true, pointer> greldet; array<1, 6, pointtype> aargh_where; integer gd, gm; boolean gb; byte glerkstage; integer bat_x, bat_y; word bat_count; shortint aargh_count; integer greldet_x, greldet_y; byte greldet_count; boolean red_greldet; void plain_grab() /* Just grabs the next one and puts it where it's told to. */ { integer xx, yy, xofs; ; blockread(f, cb, sizeof(cb)); switch (cb.flavour) { case ch_one: { ; xofs = cb.x / 8; bit = 3; for (yy = 0; yy <= cb.yl; yy ++) { ; port[0x3c4] = 2; port[0x3ce] = 4; port[0x3c5] = 1 << bit; port[0x3cf] = bit; blockread(f, mem[0xa000 * (yy + cb.y) * 80 + xofs], cb.xl / 8); } } break; case ch_ega: { ; xofs = cb.x / 8; bit = 3; for (bit = 0; bit <= 3; bit ++) for (yy = 0; yy <= cb.yl; yy ++) { ; port[0x3c4] = 2; port[0x3ce] = 4; port[0x3c5] = 1 << bit; port[0x3cf] = bit; blockread(f, mem[0xa000 * (yy + cb.y) * 80 + xofs], cb.xl / 8); } } break; } } void get_me(pointer &p) { ; blockread(f, cb, sizeof(cb)); /* Take it for granted that cb.flavour = ch_BGI! */ { ; getmem(p, cb.size); blockread(f, p, cb.size); } } void get_me_aargh(byte which) { ; blockread(f, cb, sizeof(cb)); /* Take it for granted that cb.flavour = ch_BGI! */ { ; getmem(aargh[which], cb.size); blockread(f, aargh[which], cb.size); } { pointtype &with = aargh_where[which]; with.x = cb.x; with.y = cb.y; } } void wait(word how_long) { word i; char r; for (i = 1; i <= how_long; i ++) if (keypressed()) { sound(6177); while (keypressed()) r = readkey(); delay(1); nosound; } else delay(1); } void do_bat(); static byte batimage; static pointtype batsize; static void super_blank() { pointtype oldsize; move(bat[batimage - 1], oldsize, 4); bar(bat_x + batsize.x, bat_y, bat_x + oldsize.x, bat_y + oldsize.y); } void do_bat() { shortint dx, iy; bat_count += 1; if (odd(bat_count)) { switch (bat_count) { case 1 ... 90: { dx = 2; iy = 1; batimage = 1; } break; case 91 ... 240: { dx = 1; iy = 1; batimage = 2; } break; case 241 ... 260: { dx = 1; iy = 4; batimage = 3; } break; } move(bat[batimage], batsize, 4); if ((bat_count == 91) || (bat_count == 241)) super_blank(); /* When the bat changes, blank out the old one. */ bar(bat_x, bat_y, bat_x + batsize.x, bat_y + iy); bar(bat_x + batsize.x, bat_y, bat_x + batsize.x - dx, bat_y + batsize.y); bat_x -= dx; bat_y += 1; putimage(bat_x, bat_y, bat[batimage], 0); } } void big_green_eyes(byte how) { putimage(330, 103, green_eyes[how], 0); putimage(376, 103, green_eyes[how], 0); } int main(int argc, const char *argv[]) { pio_initialize(argc, argv); ; if (paramstr(1) != "jsb") exit(255); gd = 3; gm = 0; initgraph(gd, gm, ""); fillchar(ghost, sizeof(ghost), '\0'); assign(f, "spooky.avd"); reset(f, 1); seek(f, 44); mark(memlevel); for (fv = 1; fv <= 5; fv ++) { ; blockread(f, cb, sizeof(cb)); for (bit = 2; bit <= 3; bit ++) for (y = 0; y <= cb.yl; y ++) blockread(f, ghost[fv][bit][y], cb.xl / 8); } get_me(eyes[0]); /* Get BGI-based ones */ get_me(eyes[1]); get_me(exclamation); plain_grab(); /* Grabs to screen (cobweb) */ plain_grab(); /* Grabs to screen (Mark's signature) */ plain_grab(); /* Grabs to screen (open door) */ for (fv = 1; fv <= 3; fv ++) get_me(bat[fv]); /* new(glerk); for fv:=1 to 5 do { Grab the Glerk. } begin; blockread(f,cb,sizeof(cb)); for bit:=0 to 3 do for y:=0 to 34 do blockread(f,glerk^[fv,bit,y],cb.xl div 8); inc(gd,gm); end; */ glerk = new glerktype; for (fv = 1; fv <= 6; fv ++) { ; blockread(f, cb, sizeof(cb)); bit = 3; for (bit = 0; bit <= 3; bit ++) for (yy = 0; yy <= cb.yl; yy ++) /* begin; port[$3c4]:=2; port[$3ce]:=4; port[$3C5]:=1 shl bit; port[$3CF]:=bit;*/ blockread(f, (*glerk)[fv][bit][yy], cb.xl / 8); /* move(glerk^[fv,bit,yy],mem[$A000:yy*80+177],xl div 8);*/ /* blockread(f,mem[$A000:yy*80+177],xl div 8);*/ /* end;*/ } for (fv = 1; fv <= 6; fv ++) get_me_aargh(fv); for (fv = 1; fv <= 5; fv ++) get_me(green_eyes[fv]); for (gb = false; gb <= true; gb ++) for (fv = 1; fv <= 6; fv ++) get_me(greldet[fv][gb]); close(f); /* Avvy walks over... */ setfillstyle(1, 0); glerkstage = 0; bat_x = 277; bat_y = 40; bat_count = 0; for (gd = 500; gd >= 217; gd --) { ; if (set::of(range(22, 27), eos).has((gd % 30))) { ; if ((gd % 30) == 27) bar(gd, 135, gd + 16, 136); putimage(gd, 136, eyes[0], 0); putpixel(gd + 16, 137, 0); } else { ; if (gd % 30 == 21) bar(gd, 137, gd + 17, 138); putimage(gd, 135, eyes[0], 0); putpixel(gd + 16, 136, 0); /* eyes would leave a trail 1 pixel high behind them */ } /* Plot the Glerk: */ if (gd % 10 == 0) { ; glerkstage += 1; if (glerkstage > 26) flush(); for (gm = 0; gm <= 34; gm ++) for (bit = 0; bit <= 3; bit ++) { ; port[0x3c4] = 2; port[0x3ce] = 4; port[0x3c5] = 1 << bit; port[0x3cf] = bit; move((*glerk)[glerkfade[glerkstage]][bit][gm], mem[0xa000 * 1177 + gm * 80], 9); } bit = getpixel(0, 0); } do_bat(); wait(15); } setfillstyle(1, 0); bar(456, 14, 530, 50); /* It descends... */ for (gm = -64; gm <= 103; gm ++) { ; bit = getpixel(0, 0); if (gm > 0) fillchar(mem[0xa000 * (gm - 1) * 80], 26, '\0'); for (y = 0; y <= 65; y ++) if ((y + gm) >= 0) for (bit = 0; bit <= 3; bit ++) { ; port[0x3c4] = 2; port[0x3ce] = 4; port[0x3c5] = 1 << bit; port[0x3cf] = bit; move(ghost[2 + (abs(gm / 7) % 2) * 3][plane_to_use[bit]][y], mem[0xa000 * (y + gm) * 80], 26); } wait(27); } /* And waves... */ aargh_count = -14; for (gd = 1; gd <= 4; gd ++) for (fv = 1; fv <= 5; fv ++) { ; y = getpixel(0, 0); for (y = 0; y <= 7; y ++) fillchar(mem[0xa000 * 7760 + y * 80], 26, '\0'); for (y = 0; y <= 65; y ++) for (bit = 0; bit <= 3; bit ++) { ; port[0x3c4] = 2; port[0x3ce] = 4; port[0x3c5] = 1 << bit; port[0x3cf] = bit; move(ghost[waveorder[fv]][plane_to_use[bit]][y], mem[0xa000 * 7760 + (y + adjustment[fv]) * 80], 26); } aargh_count += 1; if (aargh_count > 0) { pointtype &with = aargh_where[aargh_count]; putimage(with.x, with.y, aargh[aargh_count], 0); } wait(177); } /* ! appears */ gd = getpixel(0, 0); putimage(246, 127, exclamation, 0); wait(777); bar(172, 78, 347, 111); /* erase "aargh" */ for (gm = 5; gm >= 1; gm --) { wait(377); big_green_eyes(gm); } bar(246, 127, 251, 133); /* erase the "!" */ /* He hurries back. */ glerkstage = 1; greldet_count = 18; red_greldet = false; for (gd = 217; gd <= 479; gd ++) { ; if (set::of(range(22, 27), eos).has((gd % 30))) { ; if ((gd % 30) == 22) bar(gd + 22, 134, gd + 38, 137); putimage(gd + 23, 136, eyes[1], 0); putpixel(gd + 22, 137, 0); } else { ; if (gd % 30 == 28) bar(gd + 22, 135, gd + 38, 138); putimage(gd + 23, 135, eyes[1], 0); putpixel(gd + 22, 136, 0); /* eyes would leave a trail 1 pixel high behind them */ } /* Plot the Green Eyes: */ if (gd % 53 == 5) { ; big_green_eyes(glerkstage); glerkstage += 1; } /* Plot the Greldet: */ if (greldet_count == 18) { /* A new greldet. */ greldet_x = Random(600); greldet_y = Random(80); greldet_count = 0; red_greldet = ! red_greldet; } greldet_count += 1; putimage (greldet_x, greldet_y, greldet[greldetfade[greldet_count]][red_greldet], 0); wait(10); } release(memlevel); closegraph(); return EXIT_SUCCESS; } } // End of namespace Avalanche.