256 lines
6.3 KiB
C++
256 lines
6.3 KiB
C++
/* 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 3 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, see <http://www.gnu.org/licenses/>.
|
|
*
|
|
*/
|
|
|
|
#include "common/scummsys.h"
|
|
#include "graphics/cursorman.h"
|
|
#include "common/events.h"
|
|
#include "common/endian.h"
|
|
#include "common/system.h"
|
|
#include "engines/util.h"
|
|
#include "ultima/shared/engine/events.h"
|
|
|
|
namespace Ultima {
|
|
namespace Shared {
|
|
|
|
EventsManager::EventsManager(EventsCallback *callback) : _callback(callback), _playTime(0),
|
|
_gameCounter(0), _frameCounter(0), _priorFrameCounterTime(0), _buttonsDown(0),
|
|
_specialButtons(0), _priorFrameTime(0) {
|
|
}
|
|
|
|
void EventsManager::showCursor() {
|
|
CursorMan.showMouse(true);
|
|
}
|
|
|
|
void EventsManager::hideCursor() {
|
|
CursorMan.showMouse(false);
|
|
}
|
|
|
|
bool EventsManager::isCursorVisible() {
|
|
return CursorMan.isVisible();
|
|
}
|
|
|
|
bool EventsManager::pollEvent(Common::Event &event) {
|
|
uint32 timer = g_system->getMillis();
|
|
|
|
if (timer >= (_priorFrameCounterTime + GAME_FRAME_TIME)) {
|
|
// Time to build up next game frame
|
|
_priorFrameCounterTime = timer;
|
|
nextFrame();
|
|
}
|
|
|
|
// Event handling
|
|
if (g_system->getEventManager()->pollEvent(event)) {
|
|
if (isMouseDownEvent(event.type)) {
|
|
setButtonDown(whichButton(event.type), true);
|
|
_mousePos = event.mouse;
|
|
} else if (isMouseUpEvent(event.type)) {
|
|
setButtonDown(whichButton(event.type), false);
|
|
_mousePos = event.mouse;
|
|
} else if (event.type == Common::EVENT_MOUSEMOVE) {
|
|
_mousePos = event.mouse;
|
|
}
|
|
|
|
switch (event.type) {
|
|
case Common::EVENT_KEYDOWN: {
|
|
handleKbdSpecial(event.kbd);
|
|
break;
|
|
}
|
|
case Common::EVENT_KEYUP:
|
|
handleKbdSpecial(event.kbd);
|
|
break;
|
|
case Common::EVENT_MOUSEMOVE:
|
|
_mousePos = event.mouse;
|
|
break;
|
|
case Common::EVENT_LBUTTONDOWN:
|
|
case Common::EVENT_RBUTTONDOWN:
|
|
break;
|
|
case Common::EVENT_LBUTTONUP:
|
|
case Common::EVENT_RBUTTONUP:
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
void EventsManager::pollEvents() {
|
|
Common::Event event;
|
|
|
|
while (pollEvent(event)) {
|
|
switch (event.type) {
|
|
case Common::EVENT_MOUSEMOVE:
|
|
eventTarget()->mouseMove(_mousePos);
|
|
break;
|
|
case Common::EVENT_LBUTTONDOWN:
|
|
eventTarget()->leftButtonDown(_mousePos);
|
|
break;
|
|
case Common::EVENT_LBUTTONUP:
|
|
eventTarget()->leftButtonUp(_mousePos);
|
|
break;
|
|
case Common::EVENT_MBUTTONDOWN:
|
|
eventTarget()->middleButtonDown(_mousePos);
|
|
break;
|
|
case Common::EVENT_MBUTTONUP:
|
|
eventTarget()->middleButtonUp(_mousePos);
|
|
break;
|
|
case Common::EVENT_RBUTTONDOWN:
|
|
eventTarget()->rightButtonDown(_mousePos);
|
|
break;
|
|
case Common::EVENT_RBUTTONUP:
|
|
eventTarget()->rightButtonUp(_mousePos);
|
|
break;
|
|
case Common::EVENT_WHEELUP:
|
|
case Common::EVENT_WHEELDOWN:
|
|
eventTarget()->mouseWheel(_mousePos, event.type == Common::EVENT_WHEELUP);
|
|
break;
|
|
case Common::EVENT_KEYDOWN:
|
|
eventTarget()->keyDown(event.kbd);
|
|
break;
|
|
case Common::EVENT_KEYUP:
|
|
eventTarget()->keyUp(event.kbd);
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
void EventsManager::pollEventsAndWait() {
|
|
pollEvents();
|
|
g_system->delayMillis(10);
|
|
}
|
|
|
|
void EventsManager::nextFrame() {
|
|
++_frameCounter;
|
|
++_playTime;
|
|
|
|
// Handle any idle updates
|
|
if (!_eventTargets.empty())
|
|
eventTarget()->onIdle();
|
|
|
|
// Render anything pending for the screen
|
|
Graphics::Screen *screen = _callback->getScreen();
|
|
if (screen)
|
|
screen->update();
|
|
}
|
|
|
|
void EventsManager::setButtonDown(MouseButton button, bool isDown) {
|
|
assert(button != BUTTON_NONE);
|
|
|
|
byte mask = 0;
|
|
switch (button) {
|
|
case BUTTON_LEFT:
|
|
mask = MK_LBUTTON;
|
|
break;
|
|
case BUTTON_RIGHT:
|
|
mask = MK_RBUTTON;
|
|
break;
|
|
case BUTTON_MIDDLE:
|
|
mask = MK_MBUTTON;
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
|
|
if (isDown) {
|
|
_buttonsDown |= BUTTON_MASK(button);
|
|
_specialButtons |= mask;
|
|
} else {
|
|
_buttonsDown &= ~BUTTON_MASK(button);
|
|
_specialButtons &= ~mask;
|
|
}
|
|
}
|
|
|
|
uint32 EventsManager::getTicksCount() const {
|
|
return _frameCounter * GAME_FRAME_TIME;
|
|
}
|
|
|
|
void EventsManager::sleep(uint time) {
|
|
uint32 delayEnd = g_system->getMillis() + time;
|
|
|
|
while (!g_engine->shouldQuit() && g_system->getMillis() < delayEnd)
|
|
pollEventsAndWait();
|
|
}
|
|
|
|
bool EventsManager::waitForPress(uint expiry) {
|
|
uint32 delayEnd = g_system->getMillis() + expiry;
|
|
CPressTarget pressTarget;
|
|
addTarget(&pressTarget);
|
|
|
|
while (!g_engine->shouldQuit() && g_system->getMillis() < delayEnd && !pressTarget._pressed) {
|
|
pollEventsAndWait();
|
|
}
|
|
|
|
removeTarget();
|
|
return pressTarget._pressed;
|
|
}
|
|
|
|
void EventsManager::setMousePos(const Point &pt) {
|
|
g_system->warpMouse(pt.x, pt.y);
|
|
_mousePos = pt;
|
|
eventTarget()->mouseMove(_mousePos);
|
|
}
|
|
|
|
void EventsManager::handleKbdSpecial(Common::KeyState keyState) {
|
|
if (keyState.flags & Common::KBD_CTRL)
|
|
_specialButtons |= MK_CONTROL;
|
|
else
|
|
_specialButtons &= ~MK_CONTROL;
|
|
|
|
if (keyState.flags & Common::KBD_SHIFT)
|
|
_specialButtons |= MK_SHIFT;
|
|
else
|
|
_specialButtons &= ~MK_SHIFT;
|
|
}
|
|
|
|
|
|
bool shouldQuit() {
|
|
return g_engine->shouldQuit();
|
|
}
|
|
|
|
bool isMouseDownEvent(Common::EventType type) {
|
|
return type == Common::EVENT_LBUTTONDOWN || type == Common::EVENT_RBUTTONDOWN
|
|
|| type == Common::EVENT_MBUTTONDOWN;
|
|
}
|
|
|
|
bool isMouseUpEvent(Common::EventType type) {
|
|
return type == Common::EVENT_LBUTTONUP || type == Common::EVENT_RBUTTONUP
|
|
|| type == Common::EVENT_MBUTTONUP;
|
|
}
|
|
|
|
MouseButton whichButton(Common::EventType type) {
|
|
if (type == Common::EVENT_LBUTTONDOWN || type == Common::EVENT_LBUTTONUP)
|
|
return BUTTON_LEFT;
|
|
else if (type == Common::EVENT_RBUTTONDOWN || type == Common::EVENT_RBUTTONUP)
|
|
return BUTTON_RIGHT;
|
|
else if (type == Common::EVENT_MBUTTONDOWN || type == Common::EVENT_MBUTTONUP)
|
|
return BUTTON_MIDDLE;
|
|
else
|
|
return BUTTON_NONE;
|
|
}
|
|
|
|
} // End of namespace Shared
|
|
} // End of namespace Ultima
|