3 ms·
Current keyboard designs bug me, to put it mildly. Put a mux on each group of switches, have the microcontroller rapidly scan the muxes to determine which swit
by TheLoneWolfling 12y ago
Current keyboard designs bug me, to put it mildly.
Put a mux on each group of switches, have the microcontroller rapidly scan the muxes to determine which switches are down.
And now all of a sudden you have a keyboard that you can actually press down as many keys as you need and it still works. Except it won't. Because USB keyboards don't support arbitrary numbers of keys being pressed at once.
- idbfs 12y ago"Because USB keyboards don't support arbitrary numbers of keys being pressed at once." There is actually nothing in the USB or HID specifications preventing USB keyboards from supporting n-key rollover (when using the report protocol -- keyboards using the boot protocol are limited to a 6-key rollover). The reason most don't is simply to reduce cost and complexity. A sufficiently motivated person could build a USB-compliant keyboard that supported an arbitrary number of simultaneoue keypresses, and some do (e.g. http://www.maxkeyboard.com/max-keyboard-nighthawk-x9-red-backlit-mechanical-keyboard.html http://www.maxkeyboard.com/max-keyboard-nighthawk-x9-red-bac...).
- makomk 12y agoApparently there are all kinds of interesting bugs out there in the wild that you run into if you actually build a USB keyboard with full n-key rollover - enough that most manufacturers just emulate two keyboards and call it a day.
- TheLoneWolfling 12y agoUnfortunately, specifications are great, but in actuality you have to take a look at what is implemented as opposed to what is supposed to be implemented. In particular, if you try to go over 6-key rollover, good luck. You end up having to, and I'm not making this up, emulate a USB hub connected to multiple keyboards. It's absurd. And all because of the following: "However, the compatibility version of HID that all present systems implement limits USB keyboards to reporting a mere six regular keys together with four modifiers. Additional keys pressed beyond the limit will generally cause some of the other keys to be dropped." [http://deskthority.net/wiki/Rollover,_blocking_and_ghosting#Interface-limited_NKRO http://deskthority.net/wiki/Rollover,_blocking_and_ghosting#...] "non-working n-key rollover with a USB connection is a side effect of the data packet." [http://geekhack.org/index.php?topic=5572.msg85020#msg85020 http://geekhack.org/index.php?topic=5572.msg85020#msg85020] (Effectively, instead of doing make:key / break:key packets, the compatibility version of HID does current_keys_pressed:[array of 6 keys]. Why they didn't stick with the make/break of the PS/2 protocol is beyond me.)
- thisjepisje 12y agoI'd love that, I sometimes use my keyboard to play synth and the muxing behaviour is very annoying.
- TheLoneWolfling 12y agoElaborating on this, in case anyone wants to know more details (I'd edit the original, but for some reason HN decides you can't edit comments after an annoyingly short time limit.) Say you have N free pins on your controller, and you want to read K keys. Find the smallest integer number of columns such that log2(k/c) + k/c <= n - so, for example, with 108 keys and 20 pins, you can have 7 columns, with 16 rows (keys/column). This means a 3-bit mux, which is relatively easy to find. Tie each row via diodes to 1 key in each column. Then tie each row to a pin on the controller. Tie each column to an output of the mux, and tie the input of the mux to Vcc. You'll also probably want to tie each column to a grounding resister as well. Maybe a small cap. (Or just use the chip that does this directly, I can never remember the name. Output selector? Something along that line. "An IC that outputs Vcc on the selected pin and ground on all others".). Then connect the selector of the mux to the remaining pins on the controller. To operate, just loop through all valid outputs on the mux repeatedly - probably with gray code, as that way you don't need to make as many pin transitions. Each time you change the output of the mux, read the values of those keys. You'll probably need a mapping of row/column -> key, as well as the previous values of keys. Any time the value of a key changes, output the appropriate packet. (Note: most of the time most keys don't change. As such it may be faster to do a quick check that "old column values == new column values" before checking bits one by one.) As long as your scan rate is sufficiently high, you shouldn't miss keypresses. (And if you want to get fancy, you can actually borrow a technique from dRAM. Have each key connected from ground to a cap (per-key) to a diode to Vcc. Potentially with a resistor, although the diode might be enough. Then do the above row/column, but tied to the caps / diodes as opposed to the keys themselves. This way you'll be able to read that there is voltage on the cap even if your scan missed when it was down. It also provides a certain amount of debouncing. The disadvantage is that there's a whole lot more per-key.)
- ChuckMcM 12y agoYou may be surprised to find that you can get microprocessors with over a hundred general purpose I/O pins if you're willing to solder them all down (the STM32Fx series in the QFP208 comes to mind) that would let you wire every key of a 104 or 107 key keyboard to a pin for monitoring. And you could read them all at close to a megahertz so you could get an effective state of all the keys at a given point in time. (the chip can run at 168Mhz and you're looking at basically 14 I/O ports.)