Model 01 layout conflicts with software-defined keyboard layout
It seems that in order to use the default Dvorak layout*, you must have QWERTY (“English (US)”) selected as your keyboard layout in your operating system*. Does this seem odd or contradictory to anyone else?
(* default Dvorak layout meaning https://github.com/keyboardio/Kaleidoscope/wiki/Common-Alternate-Layouts#dvorak, which I see is now even included in Model01-Firmware.ino
in master using PRIMARY_KEYMAP_DVORAK
so I will have fewer merge conflicts when I pull down master now—nice!)
(*I’m using Ubuntu Linux, but I’m pretty sure it would be the same on any other operating system.)
If I try to use the Model 01 with my OS set to Dvorak then typing aoeui
actually comes through as ar.gc
instead! Arg, indeed!
I’m sure there’s a logical explanation for it… Something like… When you press the key corresponding to Key_O in the firmware (the one with the S keyboard on mine since I still haven’t switched from the default QWERTY keycaps), the Model 01 emits a key scan code (?) for a letter O. The OS then interprets the scan code according to the software-defined keyboard layout, sees that in Dvorak, O is remapped to R, and sends an R to the system instead of an O. But that’s not what I want it to do!
Is there no way to make the Model 01 emit an “absolute” letter O that will always be interpreted as an O rather than relative to any host OS setting?
I’m guessing not… I guess the OS-level keyboard layout setting, by definition, defines how incoming [key codes] get interpreted. It seems like OS-level keyboard layouts are really kind of a crude workaround for the fact that most physical keyboards don’t themselves provide any way to switch layouts. They’re really just faking it, “tricking” the system into thinking you’d typed an O when you actually typed an S on your QWERTY-only keyboard.
This illusion works great … until you throw a Model 01 into the mix. In fact, software-defined keyboard layouts are the only way I can type Dvorak on my laptop keyboard on my cheap, generic QWERTY USB keyboard — but it prevents the actual character emitted by the physical keyboard from coming through as-is, which becomes a problem …
When is this a problem?
It seems that it’s primarily a problem when you have multiple keyboards — which everyone who uses their Model 01 on a laptop is going to have! You have your built-in laptop keyboard, and then you have your Model 01 plugged into it via USB. And some of us may have another “normal” external keyboard plugged in as well (at least I do)…
It’s no problem if you’re just using QWERTY on all of your keyboards. Or if you only want to use Dvorak on your Model 01 (and for some reason want to use a different layout, QWERTY, on your QWERTY-only keyboard(s)). Or if you only want to use Dvorak on your “dumb” keyboards (one that don’t let you switch layouts in hardware, thus requiring you to use software-based layout trickery) and aren’t using a Model 01.
It’s only a problem if you want to continue touch typing Dvorak on your “dumb” keyboards and also on your Model 01.
Currently, whenever I switch from my Model 01 back to a dumb keyboard, I have to either hunt and peck for the keys since I don’t touch type QWERTY anymore, or I have to remember to switch back to Dvorak with the OS layout switcher. Both of those options are annoying, especially when you switch between keyboards frequently. (Then when I switch back to the Model 01 again, if I’ve switched the OS layout, I have to remember to switch it back to QWERTY again.)
How I’d like it to work…
In case it’s not obvious from my rambling above, what I’d like is to be able to leave my OS layout switched to Dvorak (so that I can continue to type Dvorak on my dumb keyboards, like I’m used to) and still be able to type Dvorak on my Model 01.
Has anyone else wished for that ability?? Surely I’m not alone out there, with the number of people using alternate layouts as high as it is in the Keyboardio community. (The same problems would apply to any alternate layout—this isn’t specific to Dvorak.)
And if you have wished for it, has anyone taken the time to come up with a Model 01 layout/plugin/function/converter/tool that allows it to work that way?
I know it’s possible. You’d just have to account for the extra QWERTY-to-Dvorak translation that the OS is going to do and reverse it. So in order to make the Key_O key come across as an O, you have to replace it with a Key_S like in the Model 01 QWERTY layout. In fact, all of the letters will go back where they are in the QWERTY layout. “So why don’t you just leave your Model 01 on the factory QWERTY layout then?”, you ask. Well, because:
- That only gets you partway there. That gets all the letters to come through correctly and some punctuation (like
;
), yes, but it’s doesn’t get all punctuation characters in their correct/expected locations. For example,=
key in QWERTY should be a/
in the Model 01 Dvorak, but instead gives me neither: it shows a]
character instead — which is indeed what I would expect on a “regular” keyboard, but I want it to match the Model 01 Dvorak and give me a/
( since Model 01 variant of Dvorak is a bit more logically organized than a naive QWERTY-to-Dvorak character translation would give you).
For reference, here is what software-mapped-Dvorak gives me on factory-default Model 01 QWERTY (looking only at the printable characters on the 3 main layers for now) vs. (every other line) how I want it to show up (to match Model 01 Dvorak):
# Row 1
`',.py fgcrl] # Primary (Model 01 QWERTY on Dvorak)
`',.py fgcrl/ # Primary (Model 01 Dvorak on QWERTY)
~"<>PY FGCRL} # Shift (Model 01 QWERTY on Dvorak)
~"<>PY FGCRL? # Shift (Model 01 Dvorak on QWERTY)
' . ?+/= # Function (Model 01 QWERTY on Dvorak)
' . {}[] # Function (Model 01 Dvorak on QWERTY)
# Row 2
aoeui dhtns- # Primary (Model 01 QWERTY on Dvorak)
aoeui dhtns- # Primary (Model 01 Dvorak on QWERTY)
AOEUI DHTNS_ # Shift (Model 01 QWERTY on Dvorak)
AOEUI DHTNS_ # Shift (Model 01 Dvorak on QWERTY)
s- # Function (Model 01 QWERTY on Dvorak)
s- # Function (Model 01 Dvorak on QWERTY)
# Row 3
;qjkx bmwvz[ # Primary (Model 01 QWERTY on Dvorak)
;qjkx bmwvz= # Primary (Model 01 Dvorak on QWERTY)
:QJKX BMWVZ{ # Shift (Model 01 QWERTY on Dvorak)
:QJKX BMWVZ+ # Shift (Model 01 Dvorak on QWERTY)
v\| # Function (Model 01 QWERTY on Dvorak)
j v\| # Function (Model 01 Dvorak on QWERTY)
- I want to be able to customize my layout. Which means having a human-readable layout that I can edit. What’s shown in the layout source code should be what actually gets output.
I shouldn’t have to write LSHIFT(Key_Minus)
where I actually want it to output Key_LeftCurlyBracket
. Look at this crazy change I had to make to the Function layer in order to actually keep curly brackets in their standard (and perfectly reasonable) locations (in all standard Model 01 layouts, which normally only change the Primary layer):
- Consumer_PlaySlashPause, Consumer_ScanNextTrack, Key_LeftCurlyBracket, Key_RightCurlyBracket, Key_LeftBracket, Key_RightBracket, Key_F12,
+ Consumer_PlaySlashPause, Consumer_ScanNextTrack, LSHIFT(Key_Minus), LSHIFT(Key_Equals), Key_Minus, Key_Equals, Key_F12,
What I’d like, in other words, is a Kaleidoscope plugin that lets me tell it “I want to use this with the layout set to Dvorak in the operating system” and have it do all the work of translating what key codes we actually need to output to get the desired character as defined in the layout.
In other words, I should be able to just say something like let host_layout = "dvorak"
and be able to just use the PRIMARY_KEYMAP_DVORAK
layout option as-is. That should be a pretty easy plugin to write, right?