mirror of
https://github.com/hsoft/collapseos.git
synced 2024-12-25 05:48:06 +11:00
sms/pad: new module to manage Megadrive controller in SMS
This commit is contained in:
parent
ca5bc07a75
commit
9eb80d5eac
49
kernel/sms/pad.asm
Normal file
49
kernel/sms/pad.asm
Normal file
@ -0,0 +1,49 @@
|
|||||||
|
; pad - read input from MD controller
|
||||||
|
;
|
||||||
|
; Conveniently expose an API to read the status of a MD pad. Moreover,
|
||||||
|
; implement a mechanism to input arbitrary characters from it. It goes as
|
||||||
|
; follow:
|
||||||
|
;
|
||||||
|
; * Direction pad select characters. Up/Down move by one, Left/Right move by 5\
|
||||||
|
; * Start acts like Return
|
||||||
|
; * A acts like Backspace
|
||||||
|
; * B changes "character class": lowercase, uppercase, numbers, special chars.
|
||||||
|
; The space character is the first among special chars.
|
||||||
|
; * C confirms letter selection
|
||||||
|
;
|
||||||
|
; *** Consts ***
|
||||||
|
;
|
||||||
|
.equ PAD_CTLPORT 0x3f
|
||||||
|
.equ PAD_D1PORT 0xdc
|
||||||
|
|
||||||
|
; *** Variables ***
|
||||||
|
;
|
||||||
|
; *** Code ***
|
||||||
|
|
||||||
|
; Put status for port A in register A. Bits, from MSB to LSB:
|
||||||
|
; Start - A - C - B - Right - Left - Down - Up
|
||||||
|
; Each bit is high when button is unpressed and low if button is pressed. For
|
||||||
|
; example, when no button is pressed, 0xff is returned.
|
||||||
|
padStatusA:
|
||||||
|
; This logic below is for the Genesis controller, which is modal. TH is
|
||||||
|
; an output pin that swiches the meaning of TL and TR. When TH is high
|
||||||
|
; (unselected), TL = Button B and TR = Button C. When TH is low
|
||||||
|
; (selected), TL = Button A and TR = Start.
|
||||||
|
push bc
|
||||||
|
ld a, 0b11111101 ; TH output, unselected
|
||||||
|
out (PAD_CTLPORT), a
|
||||||
|
in a, (PAD_D1PORT)
|
||||||
|
and 0x3f ; low 6 bits are good
|
||||||
|
ld b, a ; let's store them
|
||||||
|
; Start and A are returned when TH is selected, in bits 5 and 4. Well
|
||||||
|
; get them, left-shift them and integrate them to B.
|
||||||
|
ld a, 0b11011101 ; TH output, selected
|
||||||
|
out (PAD_CTLPORT), a
|
||||||
|
in a, (PAD_D1PORT)
|
||||||
|
and 0b00110000
|
||||||
|
sla a
|
||||||
|
sla a
|
||||||
|
or b
|
||||||
|
; we're good now!
|
||||||
|
pop bc
|
||||||
|
ret
|
@ -1,11 +1,14 @@
|
|||||||
di
|
|
||||||
im 1
|
|
||||||
jp main
|
jp main
|
||||||
|
|
||||||
.fill 0x66-$
|
.fill 0x66-$
|
||||||
retn
|
retn
|
||||||
|
|
||||||
|
#include "sms/pad.asm"
|
||||||
|
|
||||||
main:
|
main:
|
||||||
|
di
|
||||||
|
im 1
|
||||||
|
|
||||||
ld sp, 0xdff0
|
ld sp, 0xdff0
|
||||||
|
|
||||||
ld hl, VdpData
|
ld hl, VdpData
|
||||||
@ -60,45 +63,30 @@ mainloop:
|
|||||||
; What we do here is simple. We go though all bits of port A controller
|
; What we do here is simple. We go though all bits of port A controller
|
||||||
; increasing B each time. As soon as we get a hit, we display that
|
; increasing B each time. As soon as we get a hit, we display that
|
||||||
; letter. Pressed buttons go low.
|
; letter. Pressed buttons go low.
|
||||||
; This logic below is for the Genesis controller, which is modal. TH is
|
call padStatusA
|
||||||
; an output pin that swiches the meaning of TL and TR. When TH is high
|
|
||||||
; (unselected), TL = Button B and TR = Button C. When TH is low
|
|
||||||
; (selected), TL = Button A and TR = Start.
|
|
||||||
ld a, 0b11111101 ; TH output, unselected
|
|
||||||
out (0x3f), a
|
|
||||||
ld b, 0x41 ; a
|
ld b, 0x41 ; a
|
||||||
in a, (0xdc) ; I/O port
|
bit 5, a ; Port A Button C pressed
|
||||||
and 0b00100000 ; Port A Button C pressed
|
|
||||||
jr z, updateLetter
|
jr z, updateLetter
|
||||||
inc b ; b
|
inc b ; b
|
||||||
in a, (0xdc)
|
bit 4, a ; Port A Button B pressed
|
||||||
and 0b00010000 ; Port A Button B pressed
|
|
||||||
jr z, updateLetter
|
jr z, updateLetter
|
||||||
inc b ; c
|
inc b ; c
|
||||||
in a, (0xdc)
|
bit 3, a ; Port A Right pressed
|
||||||
and 0b00001000 ; Port A Right pressed
|
|
||||||
jr z, updateLetter
|
jr z, updateLetter
|
||||||
inc b ; d
|
inc b ; d
|
||||||
in a, (0xdc)
|
bit 2, a ; Port A Left pressed
|
||||||
and 0b00000100 ; Port A Left pressed
|
|
||||||
jr z, updateLetter
|
jr z, updateLetter
|
||||||
inc b ; e
|
inc b ; e
|
||||||
in a, (0xdc)
|
bit 1, a ; Port A Down pressed
|
||||||
and 0b00000010 ; Port A Down pressed
|
|
||||||
jr z, updateLetter
|
jr z, updateLetter
|
||||||
inc b ; f
|
inc b ; f
|
||||||
in a, (0xdc)
|
bit 0, a ; Port A Up pressed
|
||||||
and 0b00000001 ; Port A Up pressed
|
|
||||||
jr z, updateLetter
|
jr z, updateLetter
|
||||||
ld a, 0b11011101 ; TH output, unselected
|
|
||||||
out (0x3f), a
|
|
||||||
inc b ; g
|
inc b ; g
|
||||||
in a, (0xdc)
|
bit 6, a ; Port A Button A pressed
|
||||||
and 0b00010000 ; Port A Button A pressed
|
|
||||||
jr z, updateLetter
|
jr z, updateLetter
|
||||||
inc b ; h
|
inc b ; h
|
||||||
in a, (0xdc)
|
bit 7, a ; Port A Start pressed
|
||||||
and 0b00100000 ; Port A Start pressed
|
|
||||||
jr z, allLetters ; when start is pressed, print all letters
|
jr z, allLetters ; when start is pressed, print all letters
|
||||||
; no button pressed on port A, continue to updateLetter
|
; no button pressed on port A, continue to updateLetter
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user