aboutsummaryrefslogtreecommitdiff
path: root/backends
diff options
context:
space:
mode:
Diffstat (limited to 'backends')
-rw-r--r--backends/events/sdl/sdl-events.cpp73
-rw-r--r--backends/events/sdl/sdl-events.h5
-rw-r--r--backends/platform/dc/vmsave.cpp19
-rw-r--r--backends/platform/n64/framfs_save_manager.h3
-rw-r--r--backends/platform/n64/pakfs_save_manager.h4
-rw-r--r--backends/platform/sdl/posix/posix.cpp18
-rw-r--r--backends/platform/sdl/posix/posix.h2
-rw-r--r--backends/platform/sdl/sdl.cpp8
-rw-r--r--backends/platform/sdl/sdl.h1
9 files changed, 108 insertions, 25 deletions
diff --git a/backends/events/sdl/sdl-events.cpp b/backends/events/sdl/sdl-events.cpp
index 00e2f25cbc..acc1ff5dce 100644
--- a/backends/events/sdl/sdl-events.cpp
+++ b/backends/events/sdl/sdl-events.cpp
@@ -517,15 +517,17 @@ bool SdlEventSource::handleKeyDown(SDL_Event &ev, Common::Event &event) {
SDLModToOSystemKeyFlags(SDL_GetModState(), event);
+ SDLKey sdlKeycode = obtainKeycode(ev.key.keysym);
+
// Handle scroll lock as a key modifier
- if (ev.key.keysym.sym == SDLK_SCROLLOCK)
+ if (sdlKeycode == SDLK_SCROLLOCK)
_scrollLock = !_scrollLock;
if (_scrollLock)
event.kbd.flags |= Common::KBD_SCRL;
// Ctrl-m toggles mouse capture
- if (event.kbd.hasFlags(Common::KBD_CTRL) && ev.key.keysym.sym == 'm') {
+ if (event.kbd.hasFlags(Common::KBD_CTRL) && sdlKeycode == 'm') {
if (_graphicsManager) {
_graphicsManager->getWindow()->toggleMouseGrab();
}
@@ -534,26 +536,26 @@ bool SdlEventSource::handleKeyDown(SDL_Event &ev, Common::Event &event) {
#if defined(MACOSX)
// On Macintosh, Cmd-Q quits
- if ((ev.key.keysym.mod & KMOD_META) && ev.key.keysym.sym == 'q') {
+ if ((ev.key.keysym.mod & KMOD_META) && sdlKeycode == 'q') {
event.type = Common::EVENT_QUIT;
return true;
}
#elif defined(POSIX)
// On other *nix systems, Control-Q quits
- if ((ev.key.keysym.mod & KMOD_CTRL) && ev.key.keysym.sym == 'q') {
+ if ((ev.key.keysym.mod & KMOD_CTRL) && sdlKeycode == 'q') {
event.type = Common::EVENT_QUIT;
return true;
}
#else
// Ctrl-z quits
- if ((event.kbd.hasFlags(Common::KBD_CTRL) && ev.key.keysym.sym == 'z')) {
+ if ((event.kbd.hasFlags(Common::KBD_CTRL) && sdlKeycode == 'z')) {
event.type = Common::EVENT_QUIT;
return true;
}
#ifdef WIN32
// On Windows, also use the default Alt-F4 quit combination
- if ((ev.key.keysym.mod & KMOD_ALT) && ev.key.keysym.sym == SDLK_F4) {
+ if ((ev.key.keysym.mod & KMOD_ALT) && sdlKeycode == SDLK_F4) {
event.type = Common::EVENT_QUIT;
return true;
}
@@ -561,7 +563,7 @@ bool SdlEventSource::handleKeyDown(SDL_Event &ev, Common::Event &event) {
#endif
// Ctrl-u toggles mute
- if ((ev.key.keysym.mod & KMOD_CTRL) && ev.key.keysym.sym == 'u') {
+ if ((ev.key.keysym.mod & KMOD_CTRL) && sdlKeycode == 'u') {
event.type = Common::EVENT_MUTE;
return true;
}
@@ -570,8 +572,8 @@ bool SdlEventSource::handleKeyDown(SDL_Event &ev, Common::Event &event) {
return true;
event.type = Common::EVENT_KEYDOWN;
- event.kbd.keycode = SDLToOSystemKeycode(ev.key.keysym.sym);
- event.kbd.ascii = mapKey(ev.key.keysym.sym, (SDLMod)ev.key.keysym.mod, obtainUnicode(ev.key.keysym));
+ event.kbd.keycode = SDLToOSystemKeycode(sdlKeycode);
+ event.kbd.ascii = mapKey(sdlKeycode, (SDLMod)ev.key.keysym.mod, obtainUnicode(ev.key.keysym));
return true;
}
@@ -580,6 +582,7 @@ bool SdlEventSource::handleKeyUp(SDL_Event &ev, Common::Event &event) {
if (remapKey(ev, event))
return true;
+ SDLKey sdlKeycode = obtainKeycode(ev.key.keysym);
SDLMod mod = SDL_GetModState();
// Check if this is an event handled by handleKeyDown(), and stop if it is
@@ -587,21 +590,21 @@ bool SdlEventSource::handleKeyUp(SDL_Event &ev, Common::Event &event) {
// Check if the Ctrl key is down, so that we can trap cases where the
// user has the Ctrl key down, and has just released a special key
if (mod & KMOD_CTRL) {
- if (ev.key.keysym.sym == 'm' || // Ctrl-m toggles mouse capture
+ if (sdlKeycode == 'm' || // Ctrl-m toggles mouse capture
#if defined(MACOSX)
// Meta - Q, handled below
#elif defined(POSIX)
- ev.key.keysym.sym == 'q' || // On other *nix systems, Control-Q quits
+ sdlKeycode == 'q' || // On other *nix systems, Control-Q quits
#else
- ev.key.keysym.sym == 'z' || // Ctrl-z quit
+ sdlKeycode == 'z' || // Ctrl-z quit
#endif
- ev.key.keysym.sym == 'u') // Ctrl-u toggles mute
+ sdlKeycode == 'u') // Ctrl-u toggles mute
return false;
}
// Same for other keys (Meta and Alt)
#if defined(MACOSX)
- if ((mod & KMOD_META) && ev.key.keysym.sym == 'q')
+ if ((mod & KMOD_META) && sdlKeycode == 'q')
return false; // On Macintosh, Cmd-Q quits
#endif
@@ -609,8 +612,8 @@ bool SdlEventSource::handleKeyUp(SDL_Event &ev, Common::Event &event) {
// continue normally
event.type = Common::EVENT_KEYUP;
- event.kbd.keycode = SDLToOSystemKeycode(ev.key.keysym.sym);
- event.kbd.ascii = mapKey(ev.key.keysym.sym, (SDLMod)ev.key.keysym.mod, 0);
+ event.kbd.keycode = SDLToOSystemKeycode(sdlKeycode);
+ event.kbd.ascii = mapKey(sdlKeycode, (SDLMod)ev.key.keysym.mod, 0);
// Ctrl-Alt-<key> will change the GFX mode
SDLModToOSystemKeyFlags(mod, event);
@@ -868,6 +871,44 @@ bool SdlEventSource::handleResizeEvent(Common::Event &event, int w, int h) {
return false;
}
+SDLKey SdlEventSource::obtainKeycode(const SDL_keysym keySym) {
+#if !SDL_VERSION_ATLEAST(2, 0, 0) && defined(WIN32) && !defined(_WIN32_WCE)
+ // WORKAROUND: SDL 1.2 on Windows does not use the user configured keyboard layout,
+ // resulting in "keySym.sym" values to always be those expected for an US keyboard.
+ // For example, SDL returns SDLK_Q when pressing the 'A' key on an AZERTY keyboard.
+ // This defeats the purpose of keycodes which is to be able to refer to a key without
+ // knowing where it is physically located.
+ // We work around this issue by querying the currently active Windows keyboard layout
+ // using the scancode provided by SDL.
+
+ if (keySym.sym >= SDLK_0 && keySym.sym <= SDLK_9) {
+ // The keycode returned by SDL is kept for the number keys.
+ // Querying the keyboard layout for those would return the base key values
+ // for AZERTY keyboards, which are not numbers. For example, SDLK_1 would
+ // map to SDLK_AMPERSAND. This is theoretically correct but practically unhelpful,
+ // because it makes it impossible to handle key combinations such as "ctrl-1".
+ return keySym.sym;
+ }
+
+ int vk = MapVirtualKey(keySym.scancode, MAPVK_VSC_TO_VK);
+ if (vk) {
+ int ch = (MapVirtualKey(vk, MAPVK_VK_TO_CHAR) & 0x7FFF);
+ // The top bit of the result of MapVirtualKey with MAPVK_VSC_TO_VK signals
+ // a dead key was pressed. In that case we keep the value of the accent alone.
+ if (ch) {
+ if (ch >= 'A' && ch <= 'Z') {
+ // Windows returns uppercase ASCII whereas SDL expects lowercase
+ return (SDLKey)(SDLK_a + (ch - 'A'));
+ } else {
+ return (SDLKey)ch;
+ }
+ }
+ }
+#endif
+
+ return keySym.sym;
+}
+
uint32 SdlEventSource::obtainUnicode(const SDL_keysym keySym) {
#if SDL_VERSION_ATLEAST(2, 0, 0)
SDL_Event events[2];
diff --git a/backends/events/sdl/sdl-events.h b/backends/events/sdl/sdl-events.h
index caa60c1354..7e590aed3c 100644
--- a/backends/events/sdl/sdl-events.h
+++ b/backends/events/sdl/sdl-events.h
@@ -148,6 +148,11 @@ protected:
*/
uint32 obtainUnicode(const SDL_keysym keySym);
+ /**
+ * Extracts the keycode for the specified key sym.
+ */
+ SDLKey obtainKeycode(const SDL_keysym keySym);
+
#if SDL_VERSION_ATLEAST(2, 0, 0)
/**
* Whether _fakeKeyUp contains an event we need to send.
diff --git a/backends/platform/dc/vmsave.cpp b/backends/platform/dc/vmsave.cpp
index 75fc1ed0df..d896ba1299 100644
--- a/backends/platform/dc/vmsave.cpp
+++ b/backends/platform/dc/vmsave.cpp
@@ -269,15 +269,16 @@ public:
class OutVMSave : public Common::OutSaveFile {
private:
char *buffer;
- int pos, size, committed;
+ int _pos, size, committed;
char filename[16];
bool iofailed;
public:
uint32 write(const void *buf, uint32 cnt);
+ virtual int32 pos() const { return _pos; }
OutVMSave(const char *_filename)
- : pos(0), committed(-1), iofailed(false)
+ : _pos(0), committed(-1), iofailed(false)
{
strncpy(filename, _filename, 16);
buffer = new char[size = MAX_SAVE_SIZE];
@@ -320,14 +321,14 @@ void OutVMSave::finalize()
extern const char *gGameName;
extern Icon icon;
- if (committed >= pos)
+ if (committed >= _pos)
return;
char *data = buffer;
- int len = pos;
+ int len = _pos;
vmsaveResult r = writeSaveGame(gGameName, data, len, filename, icon);
- committed = pos;
+ committed = _pos;
if (r != VMSAVE_OK)
iofailed = true;
displaySaveResult(r);
@@ -386,13 +387,13 @@ bool InVMSave::seek(int32 offs, int whence)
uint32 OutVMSave::write(const void *buf, uint32 cnt)
{
int nbyt = cnt;
- if (pos + nbyt > size) {
- cnt = (size - pos);
+ if (_pos + nbyt > size) {
+ cnt = (size - _pos);
nbyt = cnt;
}
if (nbyt)
- memcpy(buffer + pos, buf, nbyt);
- pos += nbyt;
+ memcpy(buffer + _pos, buf, nbyt);
+ _pos += nbyt;
return cnt;
}
diff --git a/backends/platform/n64/framfs_save_manager.h b/backends/platform/n64/framfs_save_manager.h
index a066854aab..9bd4ee579e 100644
--- a/backends/platform/n64/framfs_save_manager.h
+++ b/backends/platform/n64/framfs_save_manager.h
@@ -71,6 +71,9 @@ private:
public:
uint32 write(const void *buf, uint32 cnt);
+ virtual int32 pos() const {
+ return framfs_tell(fd);
+ }
OutFRAMSave(const char *_filename) : fd(NULL) {
fd = framfs_open(_filename, "w");
diff --git a/backends/platform/n64/pakfs_save_manager.h b/backends/platform/n64/pakfs_save_manager.h
index ec66c80b73..0c08f0c506 100644
--- a/backends/platform/n64/pakfs_save_manager.h
+++ b/backends/platform/n64/pakfs_save_manager.h
@@ -72,6 +72,10 @@ private:
public:
uint32 write(const void *buf, uint32 cnt);
+ virtual int32 pos() const {
+ return pakfs_tell(fd);
+ }
+
OutPAKSave(const char *_filename) : fd(NULL) {
fd = pakfs_open(_filename, "w");
}
diff --git a/backends/platform/sdl/posix/posix.cpp b/backends/platform/sdl/posix/posix.cpp
index e2a642b288..0d5f39736a 100644
--- a/backends/platform/sdl/posix/posix.cpp
+++ b/backends/platform/sdl/posix/posix.cpp
@@ -141,6 +141,24 @@ Common::String OSystem_POSIX::getDefaultConfigFileName() {
return configFile;
}
+void OSystem_POSIX::addSysArchivesToSearchSet(Common::SearchSet &s, int priority) {
+#ifdef DATA_PATH
+ const char *snap = getenv("SNAP");
+ if (snap) {
+ Common::String dataPath = Common::String(snap) + DATA_PATH;
+ Common::FSNode dataNode(dataPath);
+ if (dataNode.exists() && dataNode.isDirectory()) {
+ // This is the same priority which is used for the data path (below),
+ // but we insert this one first, so it will be searched first.
+ s.add(dataPath, new Common::FSDirectory(dataNode, 4), priority);
+ }
+ }
+#endif
+
+ // For now, we always add the data path, just in case SNAP doesn't make sense.
+ OSystem_SDL::addSysArchivesToSearchSet(s, priority);
+}
+
Common::WriteStream *OSystem_POSIX::createLogFile() {
// Start out by resetting _logFilePath, so that in case
// of a failure, we know that no log file is open.
diff --git a/backends/platform/sdl/posix/posix.h b/backends/platform/sdl/posix/posix.h
index 0514d30191..050463c273 100644
--- a/backends/platform/sdl/posix/posix.h
+++ b/backends/platform/sdl/posix/posix.h
@@ -38,6 +38,8 @@ public:
virtual void init();
virtual void initBackend();
+ virtual void addSysArchivesToSearchSet(Common::SearchSet &s, int priority = 0);
+
protected:
/**
* Base string for creating the default path and filename for the
diff --git a/backends/platform/sdl/sdl.cpp b/backends/platform/sdl/sdl.cpp
index c55753194b..dca6891fef 100644
--- a/backends/platform/sdl/sdl.cpp
+++ b/backends/platform/sdl/sdl.cpp
@@ -492,6 +492,14 @@ AudioCDManager *OSystem_SDL::createAudioCDManager() {
#endif
}
+Common::SaveFileManager *OSystem_SDL::getSavefileManager() {
+#ifdef ENABLE_EVENTRECORDER
+ return g_eventRec.getSaveManager(_savefileManager);
+#else
+ return _savefileManager;
+#endif
+}
+
#ifdef USE_OPENGL
const OSystem::GraphicsMode *OSystem_SDL::getSupportedGraphicsModes() const {
diff --git a/backends/platform/sdl/sdl.h b/backends/platform/sdl/sdl.h
index c93c8308a7..1fe670c5c3 100644
--- a/backends/platform/sdl/sdl.h
+++ b/backends/platform/sdl/sdl.h
@@ -76,6 +76,7 @@ public:
virtual void getTimeAndDate(TimeDate &td) const;
virtual Audio::Mixer *getMixer();
virtual Common::TimerManager *getTimerManager();
+ virtual Common::SaveFileManager *getSavefileManager();
protected:
bool _inited;