/* 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. * */ #ifndef COMMON_VIRTUAL_KEYBOARD_H #define COMMON_VIRTUAL_KEYBOARD_H #include "common/scummsys.h" #ifdef ENABLE_VKEYBD class OSystem; #include "common/events.h" #include "common/hashmap.h" #include "common/hash-str.h" #include "common/keyboard.h" #include "common/list.h" #include "common/str.h" #include "common/fs.h" #include "backends/vkeybd/image-map.h" #include "graphics/surface.h" namespace Common { class Archive; class VirtualKeyboardGUI; class VirtualKeyboardParser; /** * Class that handles the functionality of the virtual keyboard. * This includes storage of the virtual key press events when the user clicks * a key and delivery of them when the keyboard is closed, as well as managing * the internal state of the keyboard, such as its active mode. */ class VirtualKeyboard { protected: /** * Enum to describe the different types of events that can be associated * with an area of the virtual keyboard bitmap. */ enum VKEventType { /** Standard key press event */ kVKEventKey, /** Modifier key press event */ kVKEventModifier, /** Switch the mode of the keyboard */ kVKEventSwitchMode, /** Close the keyboard, submitting all keypresses */ kVKEventSubmit, /** Close the keyboard, without submitting keypresses */ kVKEventCancel, /** Clear the virtual keypress queue */ kVKEventClear, /** Move the keypress queue insert position backwards */ kVKEventMoveLeft, /** Move the keypress queue insert position forwards */ kVKEventMoveRight, /** Delete keypress from queue at the current insert position */ kVKEventDelete }; /** VKEvent struct encapsulates data on a virtual keyboard event */ struct VKEvent { String name; VKEventType type; /** * Void pointer that will point to different types of data depending * on the type of the event, these are: * - KeyState struct for kVKEventKey events * - a flags byte for kVKEventModifier events * - c-string stating the name of the new mode for kSwitchMode events */ void *data; VKEvent() : data(0) {} ~VKEvent() { if (data) free(data); } }; typedef HashMap VKEventMap; /** * Mode struct encapsulates all the data for each mode of the keyboard */ struct Mode { String name; String resolution; String bitmapName; Graphics::Surface *image; uint32 transparentColor; ImageMap imageMap; VKEventMap events; Rect displayArea; uint32 displayFontColor; Mode() : image(0) {} ~Mode() { if (image) { image->free(); delete image; image = 0; } } }; typedef HashMap ModeMap; enum HorizontalAlignment { kAlignLeft, kAlignCenter, kAlignRight }; enum VerticalAlignment { kAlignTop, kAlignMiddle, kAlignBottom }; struct VirtualKeyPress { KeyState key; /** length of the key presses description string */ uint strLen; }; /** * Class that stores the queue of virtual key presses, as well as * maintaining a string that represents a preview of the queue */ class KeyPressQueue { public: KeyPressQueue(); void toggleFlags(byte fl); void clearFlags(); void insertKey(KeyState key); void deleteKey(); void moveLeft(); void moveRight(); KeyState pop(); void clear(); bool empty(); String getString(); uint getInsertIndex(); bool hasStringChanged(); private: byte _flags; String _flagsStr; typedef List KeyPressList; KeyPressList _keys; String _keysStr; bool _strChanged; KeyPressList::iterator _keyPos; uint _strPos; }; public: VirtualKeyboard(); virtual ~VirtualKeyboard(); /** * Loads the keyboard pack with the given name. * The system first looks for an uncompressed keyboard pack by searching * for packName.xml in the filesystem, if this does not exist then it * searches for a compressed keyboard pack by looking for packName.zip. * @param packName name of the keyboard pack */ bool loadKeyboardPack(const String &packName); /** * Shows the keyboard, starting an event loop that will intercept all * user input (like a modal GUI dialog). * It is assumed that the game has been paused, before this is called */ void show(); /** * Hides the keyboard, ending the event loop. * @param submit if true all accumulated key presses are submitted to * the event manager */ void close(bool submit); /** * Returns true if the keyboard is currently being shown */ bool isDisplaying(); /** * Returns true if the keyboard is loaded and ready to be shown */ bool isLoaded() { return _loaded; } protected: OSystem *_system; DisposablePtr _fileArchive; friend class VirtualKeyboardGUI; VirtualKeyboardGUI *_kbdGUI; KeyPressQueue _keyQueue; friend class VirtualKeyboardParser; VirtualKeyboardParser *_parser; void reset(); bool openPack(const String &packName, Archive *searchPath, DisposeAfterUse::Flag disposeSearchPath); void deleteEvents(); bool checkModeResolutions(); void switchMode(Mode *newMode); void switchMode(const String &newMode); void handleMouseDown(int16 x, int16 y); void handleMouseUp(int16 x, int16 y); String findArea(int16 x, int16 y); void processAreaClick(const String &area); bool _loaded; ModeMap _modes; Mode *_initialMode; Mode *_currentMode; HorizontalAlignment _hAlignment; VerticalAlignment _vAlignment; String _areaDown; bool _submitKeys; }; } // End of namespace Common #endif // #ifdef ENABLE_VKEYBD #endif // #ifndef COMMON_VIRTUAL_KEYBOARD_H