From 192cef725169c0732175884ad1bebe430bb0034b Mon Sep 17 00:00:00 2001
From: Sam Lantinga <[EMAIL REDACTED]>
Date: Sat, 25 Oct 2025 12:42:31 -0700
Subject: [PATCH] Don't repeat control keys
Also, numlock has the same toggling behavior as capslock in SDL 1.2
Fixes https://github.com/libsdl-org/sdl12-compat/issues/332
---
src/SDL12_compat.c | 45 ++++++++++++++++++++++++++++++++++++---------
1 file changed, 36 insertions(+), 9 deletions(-)
diff --git a/src/SDL12_compat.c b/src/SDL12_compat.c
index e31a90573..1b82aa1ca 100644
--- a/src/SDL12_compat.c
+++ b/src/SDL12_compat.c
@@ -4759,6 +4759,27 @@ static int DecodeUTF8Char(char **ptr)
return value;
}
+static int IsRepeatable(SDL12Key key)
+{
+ switch (key) {
+ case SDLK12_UNKNOWN:
+ case SDLK12_NUMLOCK:
+ case SDLK12_CAPSLOCK:
+ case SDLK12_LCTRL:
+ case SDLK12_RCTRL:
+ case SDLK12_LSHIFT:
+ case SDLK12_RSHIFT:
+ case SDLK12_LALT:
+ case SDLK12_RALT:
+ case SDLK12_LMETA:
+ case SDLK12_RMETA:
+ case SDLK12_MODE:
+ return 0;
+ default:
+ return 1;
+ }
+}
+
/* Add the pending KEYDOWN event to the EventQueue, possibly with 'unicode' set
* Returns 1 if there was a pending event. */
static int FlushPendingKeydownEvent(Uint32 unicode)
@@ -4770,7 +4791,7 @@ static int FlushPendingKeydownEvent(Uint32 unicode)
PendingKeydownEvent.key.keysym.unicode = unicode;
PushEventIfNotFiltered(&PendingKeydownEvent);
- if (KeyRepeatDelay) {
+ if (KeyRepeatDelay && IsRepeatable(PendingKeydownEvent.key.keysym.sym)) {
SDL20_memcpy(&KeyRepeatEvent, &PendingKeydownEvent, sizeof (SDL12_Event));
/* SDL 1.2 waits for the delay, and then a full interval past that before the first repeat is reported. */
KeyRepeatNextTicks = SDL20_GetTicks() + KeyRepeatDelay + KeyRepeatInterval;
@@ -4909,8 +4930,9 @@ EventFilter20to12(void *data, SDL_Event *event20)
event12.key.keysym.sym = Scancode20toKeysym12(event20->key.keysym.scancode);
}
- if (event12.key.keysym.sym == SDLK12_CAPSLOCK) {
- /* SDL 1.2 only sends capslock key events on keydown */
+ if (event12.key.keysym.sym == SDLK12_CAPSLOCK ||
+ event12.key.keysym.sym == SDLK12_NUMLOCK) {
+ /* SDL 1.2 only sends capslock and numlock key events on keydown */
return 1;
}
@@ -4947,18 +4969,23 @@ EventFilter20to12(void *data, SDL_Event *event20)
event12.key.keysym.sym = Scancode20toKeysym12(event20->key.keysym.scancode);
}
- if (event12.key.keysym.sym == SDLK12_CAPSLOCK) {
- /* SDL 1.2 toggles capslock on keypress */
- if (KeyState[SDLK12_CAPSLOCK]) {
- KeyState[SDLK12_CAPSLOCK] = SDL_RELEASED;
+ if (event12.key.keysym.sym == SDLK12_CAPSLOCK ||
+ event12.key.keysym.sym == SDLK12_NUMLOCK) {
+ /* SDL 1.2 toggles capslock and numlock on keypress */
+ if (KeyState[event12.key.keysym.sym]) {
+ KeyState[event12.key.keysym.sym] = SDL_RELEASED;
event12.type = SDL12_KEYUP;
event12.key.which = 0;
event12.key.state = SDL_RELEASED;
event12.key.keysym.scancode = Scancode20to12(event20->key.keysym.scancode);
- event12.key.keysym.sym = SDLK12_CAPSLOCK;
- event12.key.keysym.mod = event20->key.keysym.mod & ~KMOD_CAPS;
+ event12.key.keysym.mod = event20->key.keysym.mod;
event12.key.keysym.unicode = 0;
+ if (event12.key.keysym.sym == SDLK12_CAPSLOCK) {
+ event12.key.keysym.mod &= ~KMOD12_CAPS;
+ } else if (event12.key.keysym.sym == SDLK12_NUMLOCK) {
+ event12.key.keysym.mod &= ~KMOD12_NUM;
+ }
break;
}
}