mirror of
https://github.com/fruit-bat/pico-zxspectrum.git
synced 2025-04-19 00:04:01 +03:00
PS/2 keyboard support
This commit is contained in:
parent
75bac822f5
commit
41eb8a6aaa
20
README.md
20
README.md
@ -12,6 +12,7 @@ Uses [Wren's Amazing PicoDVI](https://github.com/Wren6991/PicoDVI) and [CarlK's
|
||||
* LCD support (ST7789 320x240)
|
||||
* VGA video (RGB332, RGB222, RGBY1111)
|
||||
* USB Keyboard & Joysticks
|
||||
* PS/2 Keyboard
|
||||
* PWM sound for ear, mic and AY-3-8912
|
||||
* 12 quick save slots
|
||||
* Load from .z80 snapshot files
|
||||
@ -32,6 +33,7 @@ Uses [Wren's Amazing PicoDVI](https://github.com/Wren6991/PicoDVI) and [CarlK's
|
||||
|
||||
|
||||
## Updates
|
||||
* 27/06/22 - Added basic support for PS/2 keyboards
|
||||
* 27/06/22 - Added support for RGB222 and RGBY1111 over VGA
|
||||
* 22/06/22 - Even better sound with 4 pin audio output (HDMI version only)
|
||||
* 18/06/22 - Dont't freeze if SD card missing
|
||||
@ -67,6 +69,9 @@ Uses [Wren's Amazing PicoDVI](https://github.com/Wren6991/PicoDVI) and [CarlK's
|
||||
| GP21 | | 21 | 27 | | | | Buzzer audio out |
|
||||
| GP26 | | 26 | 31 | | | | PWM audio out |
|
||||
| GP27 | | 26 | 32 | | | | PWM audio out |
|
||||
| GP6 | | 6 | 9 | | | | PS/2 keyboard data |
|
||||
| GP7 | | 7 | 10 | | | | PS/2 keyboard clock |
|
||||
|
||||
|
||||
### Audio pins
|
||||
Audio output comes in 3 variants 1, 2 and 4 pin:
|
||||
@ -124,6 +129,19 @@ See this [CMakeLists.txt](src/picomputer/picomputer_vga_zx/CMakeLists.txt) for a
|
||||
|
||||
See this [CMakeLists.txt](src/picomputer/picomputer_vga/CMakeLists.txt) for an example configuration.
|
||||
|
||||
### PS/2 Keyboards
|
||||
The emulator can accept input from a PS/2 keyboard wired to GP6 and GP7.
|
||||
A suggested circuit is shown below:
|
||||

|
||||
|
||||
The resistors and Zeners are there in case the keyboard contains a pull-up resistor to 5v on either the data or clock lines;
|
||||
the data and clock lines are, in theory, open-collector with no pull-up.
|
||||
|
||||
I'm told most PS/2 keyboards can be run at 3.3v and the the extra components become redundant... but I've not tried with mine.
|
||||
You may find the Pico struggles to deliver enough power at 3.3v for the SD card writes and running a keyboard.
|
||||
|
||||
Currently there is no toggling on the lock keys (caps/num lock) and the indicator leds are not used.
|
||||
|
||||
## Components
|
||||
<a href="https://shop.pimoroni.com/products/raspberry-pi-pico">
|
||||
<img src="https://cdn.shopify.com/s/files/1/0174/1800/products/PICOBOARDWHITEANGLE2_768x768.jpg" width="200"/>
|
||||
@ -359,4 +377,4 @@ tio -m ODELBS /dev/ttyUSB0
|
||||
[USB HID 1.1](https://www.usb.org/sites/default/files/hid1_11.pdf)<br/>
|
||||
[ST7789 LCD driver reference](docs/ST7789_Datasheet.pdf)<br/>
|
||||
[RGB for 128k ZX Spectrum](docs/128_rgb.pdf)<br/>
|
||||
|
||||
[PS/2 vs HID keyboard codes](docs/ps2-hid.pdf)<br/>
|
||||
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
BIN
docs/ps2-hid.pdf
Normal file
BIN
docs/ps2-hid.pdf
Normal file
Binary file not shown.
BIN
docs/ps2_interface_mk1.cddx
Normal file
BIN
docs/ps2_interface_mk1.cddx
Normal file
Binary file not shown.
BIN
docs/ps2_interface_mk1.png
Normal file
BIN
docs/ps2_interface_mk1.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 14 KiB |
59
docs/ps2_interface_mk1.svg
Normal file
59
docs/ps2_interface_mk1.svg
Normal file
@ -0,0 +1,59 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!-- Generator: Circuit Diagram, cdlibrary.dll 4.0.0.0 -->
|
||||
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
|
||||
<svg version="1.1" width="480" height="220" xmlns="http://www.w3.org/2000/svg">
|
||||
<text x="270" y="150" style="font-family:Arial;font-size:11px;text-anchor:start" dominant-baseline="middle" transform="rotate(0, 270, 150)">2x 3.3v Zenner 1W</text>
|
||||
<text x="398" y="190" style="font-family:Arial;font-size:12px;text-anchor:start" dominant-baseline="middle" transform="rotate(0, 398, 190)">PS/2 GND</text>
|
||||
<line x1="350" y1="190" x2="387" y2="190" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<ellipse cx="390" cy="190" rx="3" ry="3" style="fill-opacity:0;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<text x="398" y="110" style="font-family:Arial;font-size:12px;text-anchor:start" dominant-baseline="middle" transform="rotate(0, 398, 110)">PS/2 CLK</text>
|
||||
<line x1="350" y1="110" x2="387" y2="110" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<ellipse cx="390" cy="110" rx="3" ry="3" style="fill-opacity:0;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<text x="398" y="70" style="font-family:Arial;font-size:12px;text-anchor:start" dominant-baseline="middle" transform="rotate(0, 398, 70)">PS/2 DAT</text>
|
||||
<line x1="350" y1="70" x2="387" y2="70" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<ellipse cx="390" cy="70" rx="3" ry="3" style="fill-opacity:0;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<text x="398" y="30" style="font-family:Arial;font-size:12px;text-anchor:start" dominant-baseline="middle" transform="rotate(0, 398, 30)">PS/2 VCC</text>
|
||||
<line x1="350" y1="30" x2="387" y2="30" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<ellipse cx="390" cy="30" rx="3" ry="3" style="fill-opacity:0;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<line x1="250" y1="70" x2="250" y2="130" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="210" y1="110" x2="210" y2="130" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="210" y1="30" x2="350" y2="30" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="330" y1="110" x2="350" y2="110" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="330" y1="70" x2="350" y2="70" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="210" y1="70" x2="280" y2="70" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="210" y1="110" x2="280" y2="110" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="250" y1="170" x2="250" y2="190" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="210" y1="180" x2="210" y2="190" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="210" y1="170" x2="210" y2="180" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="210" y1="190" x2="350" y2="190" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="250" y1="170" x2="250" y2="130" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<path d="M 250,143 M 242,143 L 258,143 M 250,143 L 258,158 L 242,158 L 250,143" style="fill-opacity:0;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="259" y1="143" x2="259" y2="148" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="210" y1="170" x2="210" y2="130" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<path d="M 210,143 M 202,143 L 218,143 M 210,143 L 218,158 L 202,158 L 210,143" style="fill-opacity:0;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="219" y1="143" x2="219" y2="148" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="280" y1="110" x2="285" y2="110" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="325" y1="110" x2="330" y2="110" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<rect x="285" y="102" width="40" height="16" style="fill-opacity:0;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<text x="305" y="96" style="font-family:Arial;font-size:11px;text-anchor:middle" dominant-baseline="baseline" transform="rotate(0, 305, 96)">330 Ω</text>
|
||||
<line x1="280" y1="70" x2="285" y2="70" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<line x1="325" y1="70" x2="330" y2="70" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<rect x="285" y="62" width="40" height="16" style="fill-opacity:0;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<text x="305" y="56" style="font-family:Arial;font-size:11px;text-anchor:middle" dominant-baseline="baseline" transform="rotate(0, 305, 56)">330 Ω</text>
|
||||
<text x="152" y="30" style="font-family:Arial;font-size:12px;text-anchor:end" dominant-baseline="middle" transform="rotate(0, 152, 30)">Pico pin 40 (VBUS 5v)</text>
|
||||
<line x1="163" y1="30" x2="210" y2="30" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<ellipse cx="160" cy="30" rx="3" ry="3" style="fill-opacity:0;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<text x="152" y="190" style="font-family:Arial;font-size:12px;text-anchor:end" dominant-baseline="middle" transform="rotate(0, 152, 190)">Pico pin 38 (GND 0v)</text>
|
||||
<line x1="163" y1="190" x2="210" y2="190" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<ellipse cx="160" cy="190" rx="3" ry="3" style="fill-opacity:0;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<text x="152" y="110" style="font-family:Arial;font-size:12px;text-anchor:end" dominant-baseline="middle" transform="rotate(0, 152, 110)">Pico pin 10 (GP7 clk)</text>
|
||||
<line x1="163" y1="110" x2="210" y2="110" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<ellipse cx="160" cy="110" rx="3" ry="3" style="fill-opacity:0;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<text x="152" y="70" style="font-family:Arial;font-size:12px;text-anchor:end" dominant-baseline="middle" transform="rotate(0, 152, 70)">Pico pin 9 (GP6 data)</text>
|
||||
<line x1="163" y1="70" x2="210" y2="70" style="stroke:rgb(0, 0, 0);stroke-linecap:square;stroke-width:2" />
|
||||
<ellipse cx="160" cy="70" rx="3" ry="3" style="fill-opacity:0;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<ellipse cx="250" cy="70" rx="2" ry="2" style="fill-opacity:1;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<ellipse cx="210" cy="110" rx="2" ry="2" style="fill-opacity:1;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<ellipse cx="250" cy="190" rx="2" ry="2" style="fill-opacity:1;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
<ellipse cx="210" cy="190" rx="2" ry="2" style="fill-opacity:1;fill:rgb(0, 0, 0);stroke:rgb(0, 0, 0);stroke-width:2" />
|
||||
</svg>
|
@ -119,9 +119,12 @@ extern "C" void __not_in_flash_func(process_kbd_unmount)(uint8_t dev_addr, uint
|
||||
}
|
||||
|
||||
extern "C" void __not_in_flash_func(process_kbd_report)(hid_keyboard_report_t const *report, hid_keyboard_report_t const *prev_report) {
|
||||
printf("CURR ");print(report);
|
||||
#if 0
|
||||
// Some help debugging keyboard input/drivers
|
||||
printf("PREV ");print(prev_report);
|
||||
|
||||
printf("CURR ");print(report);
|
||||
#endif
|
||||
|
||||
int r;
|
||||
if (showMenu) {
|
||||
r = picoWinHidKeyboard.processHidReport(report, prev_report);
|
||||
|
Loading…
x
Reference in New Issue
Block a user