From e3e631e2977a42388678e445f142254236c8a951 Mon Sep 17 00:00:00 2001 From: Paul Gilbert Date: Tue, 7 May 2019 19:42:21 +1000 Subject: GLK: HUGO: Added engine feilds --- engines/glk/hugo/heglk.cpp | 55 ++++++++++++++++++ engines/glk/hugo/hugo.cpp | 48 ++++++++++++++- engines/glk/hugo/hugo.h | 97 +++++++++++++++++++++++++++++++ engines/glk/hugo/hugo_types.h | 132 +++++++++++++----------------------------- 4 files changed, 240 insertions(+), 92 deletions(-) create mode 100644 engines/glk/hugo/heglk.cpp (limited to 'engines/glk/hugo') diff --git a/engines/glk/hugo/heglk.cpp b/engines/glk/hugo/heglk.cpp new file mode 100644 index 0000000000..1dd0935982 --- /dev/null +++ b/engines/glk/hugo/heglk.cpp @@ -0,0 +1,55 @@ +/* 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. + * + */ + +#include "glk/hugo/hugo.h" + +namespace Glk { +namespace Hugo { + +void Hugo::hugo_init_screen() { + // Open the main window... + mainwin = currentwin = glk_window_open(0, 0, 0, wintype_TextBuffer, 1); + assert(mainwin); + + // ...and set it up for default output + glk_set_window(mainwin); + + // By setting the width and height so high, we're basically forcing the Glk library + // to deal with text-wrapping and page ends + SCREENWIDTH = 0x7fff; + SCREENHEIGHT = 0x7fff; + FIXEDCHARWIDTH = 1; + FIXEDLINEHEIGHT = 1; + + hugo_settextwindow(1, 1, + SCREENWIDTH/FIXEDCHARWIDTH, SCREENHEIGHT/FIXEDLINEHEIGHT); +} + +void Hugo::hugo_cleanup_screen() { +} + +void Hugo::hugo_settextwindow(int left, int top, int right, int bottom) { + // TODO +} + +} // End of namespace Hugo +} // End of namespace Glk diff --git a/engines/glk/hugo/hugo.cpp b/engines/glk/hugo/hugo.cpp index 5945d81d83..7884bc43e0 100644 --- a/engines/glk/hugo/hugo.cpp +++ b/engines/glk/hugo/hugo.cpp @@ -25,11 +25,57 @@ namespace Glk { namespace Hugo { -Hugo::Hugo(OSystem *syst, const GlkGameDescription &gameDesc) : GlkAPI(syst, gameDesc) { +Hugo::Hugo(OSystem *syst, const GlkGameDescription &gameDesc) : GlkAPI(syst, gameDesc), + mainwin(nullptr), currentwin(nullptr), address_scale(16), + SCREENWIDTH(0), SCREENHEIGHT(0), FIXEDCHARWIDTH(0), FIXEDLINEHEIGHT(0), + game_version(0), object_size(0), game(nullptr), script(nullptr), save(nullptr), + playback(nullptr), record(nullptr), io(nullptr), ioblock('\0'), ioerror('\0'), + codestart(0), objtable(0), eventtable(0), proptable(0), arraytable(0), dicttable(0), + syntable(0), initaddr(0), mainaddr(0), parseaddr(0), parseerroraddr(0), + findobjectaddr(0), endgameaddr(0), speaktoaddr(0), performaddr(0), + objects(0), events(0), dictcount(0), syncount(0), mem(nullptr), loaded_in_memory(0), + defseg(0), gameseg(0), codeptr(0), codeend(0), currentpos(0), currentline(0), full(0), + def_fcolor(0), def_bgcolor(0), def_slfcolor(0), def_slbgcolor(0), fcolor(0), bgcolor(0), + icolor(0), default_bgcolor(0), currentfont(0), capital(0), textto(0), + physical_windowwidth(0), physical_windowheight(0), physical_windowtop(0), + physical_windowleft(0), physical_windowbottom(0), physical_windowright(0), + inwindow(0), charwidth(0), lineheight(0), current_text_x(0), current_text_y(0), + undoptr(0), undoturn(0), undoinvalid(0), undorecord(0) { +#if !defined (COMPILE_V25) + Common::fill(&context_command[0][0], &context_command[MAX_CONTEXT_COMMANDS][64], 0); + context_commands = 0; +#endif + + Common::fill(&id[0], &id[3], '\0'); + Common::fill(&serial[0], &serial[9], '\0'); + Common::fill(&pbuffer[0], &pbuffer[MAXBUFFER * 2 + 1], 0); + Common::fill(&undostack[0][0], &undostack[MAXUNDO][5], 0); } +// TODO: Proper method implementations +void SetupDisplay() {} +void LoadGame() {} +void PlayGame() {} +void hugo_closefiles() {} + void Hugo::runGame() { + hugo_init_screen(); + + SetupDisplay(); + + strcpy(pbuffer, ""); + + gameseg = 0; + + LoadGame(); + + PlayGame(); + + hugo_cleanup_screen(); + hugo_blockfree(mem); + mem = nullptr; + hugo_closefiles(); } Common::Error Hugo::loadGameData(strid_t file) { diff --git a/engines/glk/hugo/hugo.h b/engines/glk/hugo/hugo.h index 7032bbad9f..15d171173f 100644 --- a/engines/glk/hugo/hugo.h +++ b/engines/glk/hugo/hugo.h @@ -34,6 +34,103 @@ namespace Hugo { * Hugo game interpreter */ class Hugo : public GlkAPI { +private: + winid_t mainwin, currentwin; + + /** + * address_scale refers to the factor by which addresses are multiplied to + * get the "real" address. In this way, a 16-bit integer can reference + * 64K * 16 = 1024K of memory. + */ + int address_scale; + + int game_version; + int object_size; + HUGO_FILE game; + HUGO_FILE script; + HUGO_FILE save; + HUGO_FILE playback; + HUGO_FILE record; + HUGO_FILE io; char ioblock; char ioerror; + + char id[3]; + char serial[9]; + unsigned int codestart; + unsigned int objtable; + unsigned int eventtable; + unsigned int proptable; + unsigned int arraytable; + unsigned int dicttable; + unsigned int syntable; + unsigned int initaddr; + unsigned int mainaddr; + unsigned int parseaddr; + unsigned int parseerroraddr; + unsigned int findobjectaddr; + unsigned int endgameaddr; + unsigned int speaktoaddr; + unsigned int performaddr; + int objects; + int events; + int dictcount; + int syncount; +#if !defined (COMPILE_V25) + char context_command[MAX_CONTEXT_COMMANDS][64]; + int context_commands; +#endif + unsigned char *mem; + int loaded_in_memory; + unsigned int defseg; + unsigned int gameseg; + long codeptr; + long codeend; + char pbuffer[MAXBUFFER * 2 + 1]; + int currentpos; + int currentline; + int full; + signed char def_fcolor, def_bgcolor, def_slfcolor, def_slbgcolor; + signed char fcolor, bgcolor, icolor, default_bgcolor; + int currentfont; + char capital; + unsigned int textto; + int SCREENWIDTH, SCREENHEIGHT; + int physical_windowwidth, physical_windowheight, + physical_windowtop, physical_windowleft, + physical_windowbottom, physical_windowright; + int inwindow; + int charwidth, lineheight, FIXEDCHARWIDTH, FIXEDLINEHEIGHT; + int current_text_x, current_text_y; + int undostack[MAXUNDO][5]; + int undoptr; + int undoturn; + char undoinvalid; + char undorecord; +private: + /** + * \defgroup heglk + * @{ + */ + + /** + * Does whatever has to be done to initially set up the display + */ + void hugo_init_screen(); + + /** + * Does whatever has to be done to clean up the display pre-termination + */ + void hugo_cleanup_screen(); + + void hugo_settextwindow(int left, int top, int right, int bottom); + + /**@}*/ +private: + /** + * Allocate memory block + */ + void *hugo_blockalloc(size_t num) { return new byte[num]; } + + void hugo_blockfree(void *block) { delete[] block; } public: /** * Constructor diff --git a/engines/glk/hugo/hugo_types.h b/engines/glk/hugo/hugo_types.h index 19e5396967..3c06293dff 100644 --- a/engines/glk/hugo/hugo_types.h +++ b/engines/glk/hugo/hugo_types.h @@ -28,106 +28,56 @@ namespace Glk { namespace Hugo { -#define MAX_HINTS 260 -#define MAX_HCONTENTS 30000 +#define HUGO_FILE strid_t +#define MAX_CONTEXT_COMMANDS 32 +#define MAXBUFFER 255 +#define MAXUNDO 1024 -#define MAX_POSITIONS 20 -#define MAX_ANIMS 200 -#define MAX_FRAMES 20 -#define MAX_STRING_SIZE 0xFF00 -#define MAX_PICTURE_SIZE 0xC800 -#define MAX_MUSIC_SIZE 0x4E20 -#define MAX_HITEMS 25 - -struct lookup { - int16 flag; - int16 count; - - lookup() : flag(0), count(0) {} -}; - -struct picture { - byte * data; - uint32 data_size; - uint16 width; - uint16 height; - uint16 wbytes; - uint16 plane_step; - byte *mask; - - picture() : data(nullptr), data_size(0), width(0), height(0), wbytes(0), plane_step(0), - mask(nullptr) {} +/** + * Library/engine globals + */ +enum EngineGlobals { + object = 0, + xobject = 1, + self = 2, + wordcount = 3, + player = 4, + actor = 5, + location = 6, + verbroutine = 7, + endflag = 8, + prompt = 9, + objectcount = 10, + system_status = 11 }; /** - * Hugo animated pictures support - * - * Note: Some of the pictures for Wonderland and the Collection Volume 1 games - * are animations. To detect these, pass a pointer to a type8 as the is_anim - * argument to ms_extract(). - * - * There are two types of animated images, however almost all images are type1. - * A type1 image consists of four main elements: - * 1) A static picture which is loaded straight at the beginning - * 2) A set of frames with a mask. These frames are just "small pictures", which - * are coded like the normal static pictures. The image mask determines - * how the frame is removed after it has been displayed. A mask is exactly - * 1/8 the size of the image and holds 1 bit per pixel, saying "remove pixel" - * or leave pixel set when frame gets removed. It might be a good idea to check - * your system documentation for masking operations as your system might be - * able to use this mask data directly. - * 3) Positioning tables. These hold animation sequences consisting of commands - * like "Draw frame 12 at (123,456)" - * 4) A playback script, which determines how to use the positioning tables. - * These scripts are handled inside Hugo, so no need to worry about. - * However, details can be found in the ms_animate() function. - * - * A type2 image is like a type1 image, but it does not have a static - * picture, nor does it have frame masking. It just consists of frames. - * - * How to support animations? - * After getting is_anim == 1 you should call ms_animate() immediately, and at - * regular intervals until ms_animate() returns 0. An appropriate interval - * between calls is about 100 milliseconds. - * Each call to ms_animate() will fill in the arguments with the address - * and size of an array of ms_position structures (see below), each of - * which holds an an animation frame number and x and y co-ordinates. To - * display the animation, decode all the animation frames (discussed below) - * from a single call to ms_animate() and display each one over the main picture. - * If your port does not support animations, define NO_ANIMATION. + * Library/engine properties */ -struct ms_position { - int16 x, y; - int16 number; - - ms_position() : x(0), y(0), number(0) {} +enum EngineProperties { + before = 1, + after = 2, + noun = 3, + adjective = 4, + article = 5 }; /** - * Hugo Windows hint support - * - * The windowed Hugo Scolls games included online hints. To add support - * for the hints to your hugo port, you should implement the ms_showhints - * function. It retrieves a pointer to an array of ms_hint structs - * The root element is always hints[0]. The elcount determines the number - * of items in this topic. You probably want to display those in some kind - * of list interface. The content pointer points to the actual description of - * the items, separated by '\0' terminators. The nodetype is 1 if the items are - * "folders" and 2 if the items are hints. Hints should be displayed one after - * another. For "folder" items, the links array holds the index of the hint in - * the array which is to be displayed on selection. One hint block has exactly - * one type. The parent element determines the "back" target. + * "display" object properties */ -struct ms_hint { - uint16 elcount; - uint16 nodetype; - byte *content; - uint16 links[MAX_HITEMS]; - uint16 parent; - - ms_hint() : elcount(0), nodetype(0), content(nullptr), parent(0) { - Common::fill(&links[0], &links[MAX_HITEMS], 0); - } +enum ObjectProperties { + screenwidth = 1, + screenheight = 2, + linelength = 3, + windowlines = 4, + cursor_column = 5, + cursor_row = 6, + hasgraphics = 7, + title_caption = 8, + hasvideo = 9, + needs_repaint = 10, + pointer_x = 11, + pointer_y = 12 }; } // End of namespace Hugo -- cgit v1.2.3