fix(input): Key.Up/Down/Left/Right are the held set's 128-131

The arrow Key constants folded to the codes of w/s/a/d, which is what the
per-frame key reports for an arrow, but cocoa.ll has always stored an arrow in
the held-key set under 128-131. So Input.key_down(Key.Up) read the W bit and
Input.move_i's arrow half never moved anything. Input.key keeps its WASD alias,
so games comparing it with 'w' (snake, chronorift) still take the arrows.

New example input_arrows.ludic, checked by ludic-dev test.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
Orkun ÇAKILKAYA 2026-09-13 03:00:29 +03:00
parent 572e09b2b1
commit 6117f73602
4 changed files with 54 additions and 10 deletions

View file

@ -0,0 +1,30 @@
# input_arrows.ludic — the arrow keys in the held-key set. Key.Up/Down/Left/Right are
# 128-131, the codes the platform stores an arrow under; they used to fold to w/s/a/d,
# so Input.key_down(Key.Up) read the W bit and Input.move_i ignored the arrows. Driven
# headless by injection, the same way the #50 device tests are.
#
# Deterministic; a full run prints: 128 129 130 131 1 0 -1 1 0
program InputArrows {
function bi(b: bool) -> int { if b { return 1 }; return 0 }
entry {
print(Key.Up)
print(Key.Down)
print(Key.Left)
print(Key.Right)
Input.press(Key.Up) # hold the up arrow
Input.poll()
print(bi(Input.key_down(Key.Up))) # 1 — the arrow is held
print(bi(Input.key_down('w'))) # 0 — and it is not W
let m = Input.move_i()
print(m.y) # -1 — move_i takes the arrows as well as WASD
Input.release(Key.Up)
Input.press(Key.Right)
Input.poll()
let r = Input.move_i()
print(r.x) # 1
print(bi(Input.key_down(Key.Up))) # 0 — released
}
}