aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--backends/common/virtual-keyboard-parser.cpp2
-rw-r--r--backends/common/virtual-keyboard.cpp90
-rw-r--r--backends/common/virtual-keyboard.h14
-rw-r--r--backends/events/default/default-events.cpp20
-rw-r--r--backends/events/default/default-events.h4
-rw-r--r--common/events.h5
-rw-r--r--common/list.h5
-rw-r--r--common/queue.h71
-rw-r--r--dists/msvc8/scummvm.vcproj4
9 files changed, 155 insertions, 60 deletions
diff --git a/backends/common/virtual-keyboard-parser.cpp b/backends/common/virtual-keyboard-parser.cpp
index f282ecd85d..26da9f465a 100644
--- a/backends/common/virtual-keyboard-parser.cpp
+++ b/backends/common/virtual-keyboard-parser.cpp
@@ -153,7 +153,7 @@ bool VirtualKeyboardParser::parserCallback_Mode() {
Common::String resolutions = modeNode->values["resolutions"];
Common::StringTokenizer tok (resolutions, " ,");
- uint16 scrW = _keyboard->_screenWidth, scrH = _keyboard->_screenHeight;
+ uint16 scrW = g_system->getOverlayWidth(), scrH = g_system->getOverlayHeight();
uint32 diff = 0xFFFFFFFF;
Common::String newResolution;
for (Common::String res = tok.nextToken(); res.size() > 0; res = tok.nextToken()) {
diff --git a/backends/common/virtual-keyboard.cpp b/backends/common/virtual-keyboard.cpp
index 5ddf5c00d2..0259bed5b9 100644
--- a/backends/common/virtual-keyboard.cpp
+++ b/backends/common/virtual-keyboard.cpp
@@ -39,17 +39,18 @@ VirtualKeyboard::VirtualKeyboard() : _currentMode(0), _keyDown(0) {
_parser = new VirtualKeyboardParser(this);
_loaded = _displaying = _drag = false;
- _screenWidth = _system->getOverlayWidth();
- _screenHeight = _system->getOverlayHeight();
+ _lastScreenChanged = _system->getScreenChangeID();
}
VirtualKeyboard::~VirtualKeyboard() {
// TODO: clean up event data pointers
+ deleteEventData();
delete _parser;
}
void VirtualKeyboard::reset() {
// TODO: clean up event data pointers
+ deleteEventData();
_modes.clear();
_initialMode = _currentMode = 0;
_kbdBound.left = _kbdBound.top
@@ -60,8 +61,17 @@ void VirtualKeyboard::reset() {
_keyDown = 0;
_displaying = _drag = false;
_firstRun = true;
- _screenWidth = _system->getOverlayWidth();
- _screenHeight = _system->getOverlayHeight();
+ _lastScreenChanged = _system->getScreenChangeID();
+}
+
+void VirtualKeyboard::deleteEventData() {
+ ModeMap::iterator it_m;
+ EventMap::iterator it_e;
+ for (it_m = _modes.begin(); it_m != _modes.end(); it_m++) {
+ EventMap *evt = &(it_m->_value.events);
+ for (it_e = evt->begin(); it_e != evt->end(); it_e++)
+ delete it_e->_value.data;
+ }
}
bool VirtualKeyboard::loadKeyboardPack(Common::String packName) {
@@ -116,31 +126,32 @@ bool VirtualKeyboard::loadKeyboardPack(Common::String packName) {
void VirtualKeyboard::setDefaultPosition()
{
+ int16 scrW = _system->getOverlayWidth(), scrH = _system->getOverlayHeight();
int16 kbdW = _kbdBound.width(), kbdH = _kbdBound.height();
int16 posX = 0, posY = 0;
- if (_screenWidth != kbdW) {
+ if (scrW != kbdW) {
switch (_hAlignment) {
case kAlignLeft:
posX = 0;
break;
case kAlignCentre:
- posX = (_screenWidth - kbdW) / 2;
+ posX = (scrW - kbdW) / 2;
break;
case kAlignRight:
- posX = _screenWidth - kbdW;
+ posX = scrW - kbdW;
break;
}
}
- if (_screenHeight != kbdH) {
+ if (scrH != kbdH) {
switch (_vAlignment) {
case kAlignTop:
posY = 0;
break;
case kAlignMiddle:
- posY = (_screenHeight - kbdH) / 2;
+ posY = (scrH - kbdH) / 2;
break;
case kAlignBottom:
- posY = _screenHeight - kbdH;
+ posY = scrH - kbdH;
break;
}
}
@@ -185,7 +196,7 @@ void VirtualKeyboard::processClick(const Common::String& area) {
switch (evt.type) {
case kEventKey:
// add virtual keypress to queue
- _keyQueue.push_back(*(Common::KeyState*)evt.data);
+ _keyQueue.push(*(Common::KeyState*)evt.data);
break;
case kEventSwitchMode:
// switch to new mode
@@ -218,28 +229,31 @@ void VirtualKeyboard::show() {
warning("Keyboard not loaded therefore can't be shown");
return;
}
- if (_screenWidth != _system->getOverlayWidth() || _screenHeight != _system->getOverlayHeight()) {
- _screenWidth = _system->getOverlayWidth();
- _screenHeight = _system->getOverlayHeight();
- if (!checkModeResolutions()) return;
- }
+ if (_lastScreenChanged != _system->getScreenChangeID())
+ screenChanged();
switchMode(_initialMode);
_displaying = true;
if (_firstRun) {
_firstRun = false;
setDefaultPosition();
}
+ _system->showOverlay();
runLoop();
+ _system->hideOverlay();
}
void VirtualKeyboard::hide() {
_displaying = false;
}
+void VirtualKeyboard::screenChanged() {
+ _lastScreenChanged = _system->getScreenChangeID();
+ if (!checkModeResolutions())
+ _displaying = false;
+}
+
void VirtualKeyboard::runLoop() {
Common::EventManager *eventMan = _system->getEventManager();
-
- _system->showOverlay();
while (_displaying) {
if (_needRedraw) redraw();
@@ -274,10 +288,7 @@ void VirtualKeyboard::runLoop() {
}
break;
case Common::EVENT_SCREEN_CHANGED:
- _screenWidth = _system->getOverlayWidth();
- _screenHeight = _system->getOverlayHeight();
- if (!checkModeResolutions())
- _displaying = false;
+ screenChanged();
break;
case Common::EVENT_QUIT:
_system->quit();
@@ -286,11 +297,20 @@ void VirtualKeyboard::runLoop() {
break;
}
// TODO - remove this line ?
- if (!_displaying) break;
+ //if (!_displaying) break;
}
}
- // clear keyboard from overlay
- _system->hideOverlay();
+
+ // push keydown & keyup events into the event manager
+ Common::Event evt;
+ evt.synthetic = false;
+ while (!_keyQueue.empty()) {
+ evt.kbd = _keyQueue.pop();
+ evt.type = Common::EVENT_KEYDOWN;
+ eventMan->pushEvent(evt);
+ evt.type = Common::EVENT_KEYUP;
+ eventMan->pushEvent(evt);
+ }
}
void VirtualKeyboard::redraw() {
@@ -300,8 +320,8 @@ void VirtualKeyboard::redraw() {
_system->clearOverlay();
_system->grabOverlay((OverlayColor*)surf.pixels, surf.w);
-
surf.blit(_currentMode->image, _kbdBound.left, _kbdBound.top, _system->RGBToColor(0xff, 0, 0xff));
+
_system->copyRectToOverlay((OverlayColor*)surf.pixels, surf.w, 0, 0, surf.w, surf.h);
surf.free();
@@ -309,22 +329,4 @@ void VirtualKeyboard::redraw() {
_needRedraw = false;
}
-bool VirtualKeyboard::pollEvent(Common::Event &event) {
- if (_displaying || (_keyQueue.empty() && !_keyDown))
- return false;
-
- event.synthetic = false; // ???
- if (_keyDown) {
- event.type = Common::EVENT_KEYUP;
- event.kbd = *_keyDown;
- _keyQueue.remove_at(0);
- _keyDown = 0;
- } else {
- _keyDown = _keyQueue.begin();
- event.type = Common::EVENT_KEYDOWN;
- event.kbd = *_keyDown;
- }
- return true;
-}
-
} // end of namespace GUI
diff --git a/backends/common/virtual-keyboard.h b/backends/common/virtual-keyboard.h
index b98511d464..fe5029558d 100644
--- a/backends/common/virtual-keyboard.h
+++ b/backends/common/virtual-keyboard.h
@@ -33,6 +33,7 @@ class OSystem;
#include "common/hash-str.h"
#include "common/image-map.h"
#include "common/keyboard.h"
+#include "common/queue.h"
#include "common/str.h"
#include "graphics/surface.h"
@@ -97,13 +98,6 @@ public:
return _loaded;
}
- /**
- * Get the next virtual key event in the event queue.
- * @param event point to an Event struct, which will be filled with the event data.
- * @return true if an event was retrieved.
- */
- bool pollEvent(Common::Event &event);
-
protected:
OSystem *_system;
@@ -114,6 +108,8 @@ protected:
// TODO : sort order of all this stuff
void reset();
+ void deleteEventData();
+ void screenChanged();
bool checkModeResolutions();
void setDefaultPosition();
void move(int16 x, int16 y);
@@ -133,7 +129,7 @@ protected:
Mode *_initialMode;
Mode *_currentMode;
- int16 _screenWidth, _screenHeight;
+ int _lastScreenChanged;
Common::Rect _kbdBound;
HorizontalAlignment _hAlignment;
@@ -143,7 +139,7 @@ protected:
Common::Point _dragPoint;
bool _drag;
- Common::Array<Common::KeyState> _keyQueue;
+ Common::Queue<Common::KeyState> _keyQueue;
Common::KeyState *_keyDown;
};
diff --git a/backends/events/default/default-events.cpp b/backends/events/default/default-events.cpp
index edb8f662e8..d06edaec1b 100644
--- a/backends/events/default/default-events.cpp
+++ b/backends/events/default/default-events.cpp
@@ -31,6 +31,7 @@
#include "engines/engine.h"
#include "gui/message.h"
+#include "gui/newgui.h"
#define RECORD_SIGNATURE 0x54455354
#define RECORD_VERSION 1
@@ -196,6 +197,7 @@ DefaultEventManager::DefaultEventManager(OSystem *boss) :
}
DefaultEventManager::~DefaultEventManager() {
+ delete _vk;
_boss->lockMutex(_timeMutex);
_boss->lockMutex(_recorderMutex);
_recordMode = kPassthrough;
@@ -351,10 +353,11 @@ bool DefaultEventManager::pollEvent(Common::Event &event) {
uint32 time = _boss->getMillis();
bool result;
- // poll virtual keyboard
- result = _vk->pollEvent(event);
- // if no vk event, then poll backend
- if (!result) result = _boss->pollEvent(event);
+ if (!_artificialEventQueue.empty()) {
+ event = _artificialEventQueue.pop();
+ result = true;
+ } else
+ result = _boss->pollEvent(event);
if (_recordMode != kPassthrough) {
@@ -390,16 +393,17 @@ bool DefaultEventManager::pollEvent(Common::Event &event) {
_keyRepeatTime = time + kKeyRepeatInitialDelay;
#endif
- // quick hack to show/hide keyboard
+ // HACK to show/hide keyboard (keyboard is not shown if gui is active)
if (event.kbd.keycode == Common::KEYCODE_F6 && event.kbd.flags == 0) {
if (_vk->isDisplaying()) {
_vk->hide();
- } else {
+ } else if (!g_gui.isActive()) {
if (!_vk->isLoaded()) _vk->loadKeyboardPack("test");
bool isPaused = (g_engine) ? g_engine->isPaused() : true;
if (!isPaused) g_engine->pauseEngine(true);
_vk->show();
if (!isPaused) g_engine->pauseEngine(false);
+ result = false;
}
}
@@ -466,4 +470,8 @@ bool DefaultEventManager::pollEvent(Common::Event &event) {
return result;
}
+void DefaultEventManager::pushEvent(Common::Event event) {
+ _artificialEventQueue.push(event);
+}
+
#endif // !defined(DISABLE_DEFAULT_EVENTMANAGER)
diff --git a/backends/events/default/default-events.h b/backends/events/default/default-events.h
index 4472b1115f..e836160188 100644
--- a/backends/events/default/default-events.h
+++ b/backends/events/default/default-events.h
@@ -27,6 +27,7 @@
#define BACKEND_EVENTS_DEFAULT_H
#include "common/events.h"
+#include "common/queue.h"
#include "common/savefile.h"
#include "backends/common/virtual-keyboard.h"
@@ -47,6 +48,8 @@ class DefaultEventManager : public Common::EventManager {
Common::VirtualKeyboard *_vk;
+ Common::Queue<Common::Event> _artificialEventQueue;
+
Common::Point _mousePos;
int _buttonState;
int _modifierState;
@@ -110,6 +113,7 @@ public:
~DefaultEventManager();
virtual bool pollEvent(Common::Event &event);
+ virtual void pushEvent(Common::Event event);
virtual void registerRandomSource(Common::RandomSource &rnd, const char *name);
virtual void processMillis(uint32 &millis);
diff --git a/common/events.h b/common/events.h
index d0cb740692..3e77824110 100644
--- a/common/events.h
+++ b/common/events.h
@@ -142,6 +142,11 @@ public:
*/
virtual bool pollEvent(Common::Event &event) = 0;
+ /**
+ * Pushes a "fake" event into the event queue
+ */
+ virtual void pushEvent(Common::Event event) = 0;
+
/** Register random source so it can be serialized in game test purposes **/
virtual void registerRandomSource(Common::RandomSource &rnd, const char *name) = 0;
diff --git a/common/list.h b/common/list.h
index c4e7b47644..0372d217b7 100644
--- a/common/list.h
+++ b/common/list.h
@@ -209,6 +209,11 @@ public:
++i;
}
+ void pop_front() {
+ iterator i = begin();
+ i = erase(i);
+ }
+
List<t_T> &operator=(const List<t_T> &list) {
if (this != &list) {
diff --git a/common/queue.h b/common/queue.h
new file mode 100644
index 0000000000..cb29c59058
--- /dev/null
+++ b/common/queue.h
@@ -0,0 +1,71 @@
+/* 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.
+ *
+ * $URL$
+ * $Id$
+ */
+
+#ifndef COMMON_QUEUE_H
+#define COMMON_QUEUE_H
+
+#include "common/scummsys.h"
+#include "common/list.h"
+
+namespace Common {
+
+/**
+ * Variable size Queue class, implemented using our Array class.
+ */
+template<class T>
+class Queue {
+protected:
+ List<T> _queue;
+public:
+ Queue<T>() {}
+ Queue<T>(const List<T> &queueContent) : _queue(queueContent) {}
+
+ bool empty() const {
+ return _queue.empty();
+ }
+ void clear() {
+ _queue.clear();
+ }
+ void push(const T &x) {
+ _queue.push_back(x);
+ }
+ T back() const {
+ return _queue.reverse_begin().operator*();
+ }
+ T front() const {
+ return _queue.begin().operator*();
+ }
+ T pop() {
+ T tmp = front();
+ _queue.pop_front();
+ return tmp;
+ }
+ int size() const {
+ return _queue.size();
+ }
+};
+
+} // End of namespace Common
+
+#endif
diff --git a/dists/msvc8/scummvm.vcproj b/dists/msvc8/scummvm.vcproj
index 8f7f42f9e4..638946334c 100644
--- a/dists/msvc8/scummvm.vcproj
+++ b/dists/msvc8/scummvm.vcproj
@@ -399,6 +399,10 @@
>
</File>
<File
+ RelativePath="..\..\common\queue.h"
+ >
+ </File>
+ <File
RelativePath="..\..\common\rect.h"
>
</File>