diff options
author | Paul Gilbert | 2018-10-27 18:44:32 -0700 |
---|---|---|
committer | Paul Gilbert | 2018-12-08 19:05:59 -0800 |
commit | 9eb4debd158f0348c9a13f548c788d9f9d721f70 (patch) | |
tree | cd8d033e1e73671516b031738297cbfe8328b517 /engines/gargoyle | |
parent | 7bbedcd099dfe552547b97482c1d974318d3ce16 (diff) | |
download | scummvm-rg350-9eb4debd158f0348c9a13f548c788d9f9d721f70.tar.gz scummvm-rg350-9eb4debd158f0348c9a13f548c788d9f9d721f70.tar.bz2 scummvm-rg350-9eb4debd158f0348c9a13f548c788d9f9d721f70.zip |
GLK: Logic for keypress event handling
Diffstat (limited to 'engines/gargoyle')
-rw-r--r-- | engines/gargoyle/clipboard.cpp | 39 | ||||
-rw-r--r-- | engines/gargoyle/clipboard.h | 43 | ||||
-rw-r--r-- | engines/gargoyle/events.cpp | 98 | ||||
-rw-r--r-- | engines/gargoyle/events.h | 24 | ||||
-rw-r--r-- | engines/gargoyle/gargoyle.cpp | 9 | ||||
-rw-r--r-- | engines/gargoyle/gargoyle.h | 3 | ||||
-rw-r--r-- | engines/gargoyle/module.mk | 1 | ||||
-rw-r--r-- | engines/gargoyle/window_text_buffer.cpp | 7 | ||||
-rw-r--r-- | engines/gargoyle/window_text_buffer.h | 5 | ||||
-rw-r--r-- | engines/gargoyle/windows.cpp | 90 | ||||
-rw-r--r-- | engines/gargoyle/windows.h | 22 |
11 files changed, 324 insertions, 17 deletions
diff --git a/engines/gargoyle/clipboard.cpp b/engines/gargoyle/clipboard.cpp new file mode 100644 index 0000000000..ef11d55a9a --- /dev/null +++ b/engines/gargoyle/clipboard.cpp @@ -0,0 +1,39 @@ +/* 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 "gargoyle/clipboard.h" + +namespace Gargoyle { + +void Clipboard::store(const uint32 *text, size_t len) { + // TODO +} + +void Clipboard::send() { + // TODO +} + +void Clipboard::receive() { + // TODO +} + +} // End of namespace Gargoyle diff --git a/engines/gargoyle/clipboard.h b/engines/gargoyle/clipboard.h new file mode 100644 index 0000000000..ccd8d79f50 --- /dev/null +++ b/engines/gargoyle/clipboard.h @@ -0,0 +1,43 @@ +/* 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 GARGOYLE_CLIPBOARD_H +#define GARGOYLE_CLIPBOARD_H + +#include "common/array.h" + +namespace Gargoyle { + +class Clipboard { +private: + Common::Array<uint32> _text; +public: + void store(const uint32 *text, size_t len); + + void send(); + + void receive(); +}; + +} // End of namespace Gargoyle + +#endif diff --git a/engines/gargoyle/events.cpp b/engines/gargoyle/events.cpp index 6fcf6340c8..00adce84ab 100644 --- a/engines/gargoyle/events.cpp +++ b/engines/gargoyle/events.cpp @@ -21,11 +21,35 @@ */ #include "gargoyle/events.h" +#include "gargoyle/clipboard.h" +#include "gargoyle/gargoyle.h" +#include "gargoyle/windows.h" namespace Gargoyle { void Events::getEvent(event_t *event, bool polled) { - // TODO + _currentEvent = event; + event->clear(); + + Common::Event ev; + dispatchEvent(*_currentEvent, polled); + + if (!polled) { + while (!g_vm->shouldQuit() && _currentEvent->type == evtype_None && !_timeouts) { + pollEvents(); + g_system->delayMillis(10); + + dispatchEvent(*_currentEvent, polled); + } + } + + if (_currentEvent->type == evtype_None && _timeouts) { + store(evtype_Timer, NULL, 0, 0); + dispatchEvent(*_currentEvent, polled); + _timeouts = false; + } + + _currentEvent = nullptr; } void Events::store(EvType type, Window *win, uint32 val1, uint32 val2) { @@ -60,4 +84,76 @@ void Events::dispatchEvent(Event &ev, bool polled) { ev = dispatch; } +void Events::pollEvents() { + Common::Event event; + + do { + g_system->getEventManager()->pollEvent(event); + + switch (event.type) { + case Common::EVENT_KEYDOWN: + handleKeyDown(event.kbd); + return; + default: + break; + } + } while (event.type == Common::EVENT_MOUSEMOVE); +} + +void Events::handleKeyDown(const Common::KeyState &ks) { + Clipboard &clipboard = *g_vm->_clipboard; + Windows &windows = *g_vm->_windows; + + if (ks.flags & Common::KBD_CTRL) { + if (ks.keycode == Common::KEYCODE_a) + windows.inputHandleKey(keycode_Home); + else if (ks.keycode == Common::KEYCODE_c) + clipboard.send(); + else if (ks.keycode == Common::KEYCODE_e) + windows.inputHandleKey(keycode_End); + else if (ks.keycode == Common::KEYCODE_u) + windows.inputHandleKey(keycode_Escape); + else if (ks.keycode == Common::KEYCODE_v) + clipboard.receive(); + else if (ks.keycode == Common::KEYCODE_x) + clipboard.send(); + else if (ks.keycode == Common::KEYCODE_LEFT || ks.keycode == Common::KEYCODE_KP4) + windows.inputHandleKey(keycode_SkipWordLeft); + else if (ks.keycode == Common::KEYCODE_RIGHT || ks.keycode == Common::KEYCODE_KP6) + windows.inputHandleKey(keycode_SkipWordRight); + + return; + } + + if (ks.flags & Common::KBD_ALT) + return; + + if (ks.keycode == Common::KEYCODE_RETURN) windows.inputHandleKey(keycode_Return); + else if (ks.keycode == Common::KEYCODE_BACKSPACE) windows.inputHandleKey(keycode_Delete); + else if (ks.keycode == Common::KEYCODE_DELETE) windows.inputHandleKey(keycode_Erase); + else if (ks.keycode == Common::KEYCODE_TAB) windows.inputHandleKey(keycode_Tab); + else if (ks.keycode == Common::KEYCODE_UP) windows.inputHandleKey(keycode_PageUp); + else if (ks.keycode == Common::KEYCODE_PAGEDOWN) windows.inputHandleKey(keycode_PageDown); + else if (ks.keycode == Common::KEYCODE_HOME) windows.inputHandleKey(keycode_Home); + else if (ks.keycode == Common::KEYCODE_END) windows.inputHandleKey(keycode_End); + else if (ks.keycode == Common::KEYCODE_LEFT) windows.inputHandleKey(keycode_Left); + else if (ks.keycode == Common::KEYCODE_RIGHT) windows.inputHandleKey(keycode_Right); + else if (ks.keycode == Common::KEYCODE_UP) windows.inputHandleKey(keycode_Up); + else if (ks.keycode == Common::KEYCODE_DOWN) windows.inputHandleKey(keycode_Down); + else if (ks.keycode == Common::KEYCODE_ESCAPE) windows.inputHandleKey(keycode_Escape); + else if (ks.keycode == Common::KEYCODE_F1) windows.inputHandleKey(keycode_Func1); + else if (ks.keycode == Common::KEYCODE_F2) windows.inputHandleKey(keycode_Func2); + else if (ks.keycode == Common::KEYCODE_F3) windows.inputHandleKey(keycode_Func3); + else if (ks.keycode == Common::KEYCODE_F4) windows.inputHandleKey(keycode_Func4); + else if (ks.keycode == Common::KEYCODE_F5) windows.inputHandleKey(keycode_Func5); + else if (ks.keycode == Common::KEYCODE_F6) windows.inputHandleKey(keycode_Func6); + else if (ks.keycode == Common::KEYCODE_F7) windows.inputHandleKey(keycode_Func7); + else if (ks.keycode == Common::KEYCODE_F8) windows.inputHandleKey(keycode_Func8); + else if (ks.keycode == Common::KEYCODE_F9) windows.inputHandleKey(keycode_Func9); + else if (ks.keycode == Common::KEYCODE_F10) windows.inputHandleKey(keycode_Func10); + else if (ks.keycode == Common::KEYCODE_F11) windows.inputHandleKey(keycode_Func11); + else if (ks.keycode == Common::KEYCODE_F12) windows.inputHandleKey(keycode_Func12); + else windows.inputHandleKey(ks.ascii); +} + } // End of namespace Gargoyle diff --git a/engines/gargoyle/events.h b/engines/gargoyle/events.h index 54a277424a..cd0a3a6620 100644 --- a/engines/gargoyle/events.h +++ b/engines/gargoyle/events.h @@ -138,19 +138,37 @@ public: } }; +/** + * Events manager + */ class Events { private: - EventQueue _eventsPolled; - EventQueue _eventsLogged; + EventQueue _eventsPolled; ///< User generated events + EventQueue _eventsLogged; ///< Custom events generated by game code + Event *_currentEvent; ///< Event pointer passed during event retrieval + bool _timeouts; ///< Timer timeouts flag private: + /** + * Dispatches an event + */ void dispatchEvent(Event &ev, bool polled); + + /** + * Poll for user events + */ + void pollEvents(); + + /** + * Handle a key down event + */ + void handleKeyDown(const Common::KeyState &ks); public: bool _forceClick; public: /** * Constructor */ - Events() : _forceClick(false) {} + Events() : _forceClick(false), _currentEvent(nullptr), _timeouts(false) {} /** * Get any pending event diff --git a/engines/gargoyle/gargoyle.cpp b/engines/gargoyle/gargoyle.cpp index 1a8cc617fb..1f74c31c79 100644 --- a/engines/gargoyle/gargoyle.cpp +++ b/engines/gargoyle/gargoyle.cpp @@ -29,6 +29,7 @@ #include "graphics/scaler.h" #include "graphics/thumbnail.h" #include "gargoyle/gargoyle.h" +#include "gargoyle/clipboard.h" #include "gargoyle/conf.h" #include "gargoyle/events.h" #include "gargoyle/picture.h" @@ -42,14 +43,15 @@ namespace Gargoyle { GargoyleEngine *g_vm; GargoyleEngine::GargoyleEngine(OSystem *syst, const GargoyleGameDescription *gameDesc) : - _gameDescription(gameDesc), Engine(syst), _random("Gargoyle"), _conf(nullptr), - _events(nullptr), _picList(nullptr), _screen(nullptr), _windows(nullptr), - _windowMask(nullptr), _copySelect(false), + _gameDescription(gameDesc), Engine(syst), _random("Gargoyle"), _clipboard(nullptr), + _conf(nullptr), _events(nullptr), _picList(nullptr), _screen(nullptr), _windows(nullptr), + _windowMask(nullptr), _copySelect(false), _terminated(false), gli_unregister_obj(nullptr), gli_register_arr(nullptr), gli_unregister_arr(nullptr) { g_vm = this; } GargoyleEngine::~GargoyleEngine() { + delete _clipboard; delete _conf; delete _events; delete _picList; @@ -68,6 +70,7 @@ void GargoyleEngine::initialize() { initGraphics(640, 480, false); _screen = new Screen(); + _clipboard = new Clipboard(); _conf = new Conf(); _events = new Events(); _picList = new PicList(); diff --git a/engines/gargoyle/gargoyle.h b/engines/gargoyle/gargoyle.h index c34538b47c..9677d67706 100644 --- a/engines/gargoyle/gargoyle.h +++ b/engines/gargoyle/gargoyle.h @@ -33,6 +33,7 @@ namespace Gargoyle { +class Clipboard; class Conf; class Events; class PicList; @@ -93,6 +94,7 @@ protected: */ virtual void runGame(Common::SeekableReadStream *gameFile) = 0; public: + Clipboard *_clipboard; Conf *_conf; Events *_events; PicList *_picList; @@ -101,6 +103,7 @@ public: Windows *_windows; WindowMask *_windowMask; bool _copySelect; + bool _terminated; void (*gli_unregister_obj)(void *obj, glui32 objclass, gidispatch_rock_t objrock); gidispatch_rock_t (*gli_register_arr)(void *array, glui32 len, const char *typecode); void (*gli_unregister_arr)(void *array, glui32 len, const char *typecode, gidispatch_rock_t objrock); diff --git a/engines/gargoyle/module.mk b/engines/gargoyle/module.mk index b8ef788a7e..a45608fc02 100644 --- a/engines/gargoyle/module.mk +++ b/engines/gargoyle/module.mk @@ -1,6 +1,7 @@ MODULE := engines/gargoyle MODULE_OBJS := \ + clipboard.o \ conf.o \ detection.o \ events.o \ diff --git a/engines/gargoyle/window_text_buffer.cpp b/engines/gargoyle/window_text_buffer.cpp index fa8a7cced5..c322127b9f 100644 --- a/engines/gargoyle/window_text_buffer.cpp +++ b/engines/gargoyle/window_text_buffer.cpp @@ -21,6 +21,7 @@ */ #include "gargoyle/window_text_buffer.h" +#include "gargoyle/clipboard.h" #include "gargoyle/conf.h" #include "gargoyle/gargoyle.h" #include "gargoyle/screen.h" @@ -1155,7 +1156,7 @@ void TextBufferWindow::redraw() { if (selbuf && _copyPos) { Windows::_claimSelect = true; - copyTextToClipboard(_copyBuf, _copyPos); + g_vm->_clipboard->store(_copyBuf, _copyPos); for (i = 0; i < _copyPos; i++) _copyBuf[i] = 0; _copyPos = 0; @@ -1623,10 +1624,6 @@ int TextBufferWindow::calcWidth(glui32 *chars, Attributes *attrs, int startchar, return w; } -void TextBufferWindow::copyTextToClipboard(const glui32 *text, size_t len) { - // TODO -} - void TextBufferWindow::getSize(glui32 *width, glui32 *height) const { if (width) *width = (_bbox.width() - g_conf->_tMarginX * 2) / g_conf->_cellW; diff --git a/engines/gargoyle/window_text_buffer.h b/engines/gargoyle/window_text_buffer.h index be9ffcbd74..61b30e266d 100644 --- a/engines/gargoyle/window_text_buffer.h +++ b/engines/gargoyle/window_text_buffer.h @@ -84,11 +84,6 @@ private: void scrollOneLine(bool forced); void scrollResize(); int calcWidth(glui32 *chars, Attributes *attrs, int startchar, int numchars, int spw); - - /** - * Copy the passed text to the clipboard - */ - void copyTextToClipboard(const glui32 *text, size_t len); public: int _width, _height; int _spaced; diff --git a/engines/gargoyle/windows.cpp b/engines/gargoyle/windows.cpp index 19f61ba77d..06b83e14bb 100644 --- a/engines/gargoyle/windows.cpp +++ b/engines/gargoyle/windows.cpp @@ -294,6 +294,96 @@ void Windows::inputGuessFocus() { } } +void Windows::inputMoreFocus() { + Window *altWin = _focusWin; + + do { + if (altWin && altWin->_moreRequest) + break; + altWin = iterateTreeOrder(altWin); + } while (altWin != _focusWin); + + _focusWin = altWin; +} + +void Windows::inputNextFocus() { + Window *altWin = _focusWin; + + do + { + altWin = iterateTreeOrder(altWin); + if (altWin + && (altWin->_lineRequest || altWin->_charRequest || + altWin->_lineRequestUni || altWin->_charRequestUni)) + break; + } while (altWin != _focusWin); + + if (_focusWin != altWin) { + _focusWin = altWin; + _forceRedraw = true; + redraw(); + } +} + +void Windows::inputScrollFocus() { + Window *altWin = _focusWin; + + do { + if (altWin && altWin->_scrollRequest) + break; + altWin = iterateTreeOrder(altWin); + } while (altWin != _focusWin); + + _focusWin = altWin; +} + +void Windows::inputHandleKey(glui32 key) { + if (_moreFocus) { + inputMoreFocus(); + } else { + switch (key) { + case keycode_Tab: + inputNextFocus(); + return; + case keycode_PageUp: + case keycode_PageDown: + case keycode_MouseWheelUp: + case keycode_MouseWheelDown: + inputScrollFocus(); + break; + default: + inputGuessFocus(); + break; + } + } + + Window *win = _focusWin; + if (!win) + return; + + bool deferExit = false; + + TextGridWindow *gridWindow = dynamic_cast<TextGridWindow *>(win); + TextBufferWindow *bufWindow = dynamic_cast<TextBufferWindow *>(win); + + if (gridWindow) { + if (gridWindow->_charRequest || gridWindow->_charRequestUni) + gridWindow->acceptReadChar(key); + else if (gridWindow->_lineRequest || gridWindow->_lineRequestUni) + gridWindow->acceptReadLine(key); + } else if (bufWindow) { + if (bufWindow->_charRequest || bufWindow->_charRequestUni) + bufWindow->acceptReadChar(key); + else if (bufWindow->_lineRequest || bufWindow->_lineRequestUni) + bufWindow->acceptReadLine(key); + else if (bufWindow->_moreRequest || bufWindow->_scrollRequest) + deferExit = bufWindow->acceptScroll(key); + } + + if (!deferExit && g_vm->_terminated) + g_vm->quitGame(); +} + void Windows::selectionChanged() { _claimSelect = false; _forceRedraw = true; diff --git a/engines/gargoyle/windows.h b/engines/gargoyle/windows.h index b0ee311685..08408223d4 100644 --- a/engines/gargoyle/windows.h +++ b/engines/gargoyle/windows.h @@ -101,6 +101,23 @@ private: void refocus(Window *win); Window *iterateTreeOrder(Window *win); + + + /** + * Pick first window which has a more request + */ + void inputMoreFocus(); + + /** + * + */ + void inputNextFocus(); + + /** + * Pick first window which might want scrolling. + * This is called after pressing page keys. + */ + void inputScrollFocus(); public: static bool _overrideReverse; static bool _overrideFgSet; @@ -154,6 +171,11 @@ public: */ void inputGuessFocus(); + /** + * Handle input keypress + */ + void inputHandleKey(glui32 key); + void selectionChanged(); void clearClaimSelect() { _claimSelect = false; } |