Files
CavesOfSwift/Sources/JolkEngine/Input/Keyboard.swift
2024-05-09 20:56:25 +10:00

138 lines
3.0 KiB
Swift

import SDL2
public class Keyboard
{
public enum Keys
{
case a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x, y, z
case right, left, down, up
}
public func keyDown(_ key: Keys) -> Bool
{
_keys[Int(key.sdlScancode.rawValue)] & Self._DOWN == Self._DOWN
}
public func keyPressed(_ key: Keys, repeat rep: Bool = false) -> Bool
{
var state = _keys[Int(key.sdlScancode.rawValue)]
if rep { state &= ~Self._REPEAT }
return state == Self._PRESS
}
public func keyReleased(_ key: Keys) -> Bool
{
_keys[Int(key.sdlKeycode.rawValue)] == Self._RELEASE
}
private static let _UP = UInt8(0b000), _DOWN = UInt8(0b010), _IMPULSE = UInt8(0b001)
private static let _REPEAT = UInt8(0b100)
private static let _PRESS: UInt8 = _DOWN | _IMPULSE
private static let _RELEASE: UInt8 = _UP | _IMPULSE
private var _keys = [UInt8](repeating: _UP, count: Int(SDL_NUM_SCANCODES.rawValue))
internal func newTick()
{
_keys = _keys.map({ $0 & ~(Self._IMPULSE | Self._REPEAT) })
}
internal func pressEvent(scan: SDL_Scancode, repeat rep: Bool)
{
var newState = Self._PRESS
if rep { newState |= Self._REPEAT }
_keys[Int(scan.rawValue)] = newState
}
internal func releaseEvent(scan: SDL_Scancode)
{
_keys[Int(scan.rawValue)] = Self._RELEASE
}
}
extension Keyboard.Keys
{
internal var sdlKeycode: SDL_KeyCode
{
switch self
{
case .a: SDLK_a
case .b: SDLK_b
case .c: SDLK_c
case .d: SDLK_d
case .e: SDLK_e
case .f: SDLK_f
case .g: SDLK_g
case .h: SDLK_h
case .i: SDLK_i
case .j: SDLK_j
case .k: SDLK_k
case .l: SDLK_l
case .m: SDLK_m
case .n: SDLK_n
case .o: SDLK_o
case .p: SDLK_p
case .q: SDLK_q
case .r: SDLK_r
case .s: SDLK_s
case .t: SDLK_t
case .u: SDLK_u
case .v: SDLK_v
case .w: SDLK_w
case .x: SDLK_x
case .y: SDLK_y
case .z: SDLK_z
case .left: SDLK_LEFT
case .right: SDLK_RIGHT
case .up: SDLK_UP
case .down: SDLK_DOWN
}
}
internal var sdlScancode: SDL_Scancode
{
switch self
{
case .a: SDL_SCANCODE_A
case .b: SDL_SCANCODE_B
case .c: SDL_SCANCODE_C
case .d: SDL_SCANCODE_D
case .e: SDL_SCANCODE_E
case .f: SDL_SCANCODE_F
case .g: SDL_SCANCODE_G
case .h: SDL_SCANCODE_H
case .i: SDL_SCANCODE_I
case .j: SDL_SCANCODE_J
case .k: SDL_SCANCODE_K
case .l: SDL_SCANCODE_L
case .m: SDL_SCANCODE_M
case .n: SDL_SCANCODE_N
case .o: SDL_SCANCODE_O
case .p: SDL_SCANCODE_P
case .q: SDL_SCANCODE_Q
case .r: SDL_SCANCODE_R
case .s: SDL_SCANCODE_S
case .t: SDL_SCANCODE_T
case .u: SDL_SCANCODE_U
case .v: SDL_SCANCODE_V
case .w: SDL_SCANCODE_W
case .x: SDL_SCANCODE_X
case .y: SDL_SCANCODE_Y
case .z: SDL_SCANCODE_Z
case .left: SDL_SCANCODE_LEFT
case .right: SDL_SCANCODE_RIGHT
case .up: SDL_SCANCODE_UP
case .down: SDL_SCANCODE_DOWN
}
}
}
extension SDL_KeyCode
{
internal init(scancode: SDL_Scancode)
{
self.init(scancode.rawValue | UInt32(SDLK_SCANCODE_MASK))
}
}