diff --git a/doc/plugin/TopsyTurvy.md b/doc/plugin/TopsyTurvy.md new file mode 100644 index 00000000..c4370c48 --- /dev/null +++ b/doc/plugin/TopsyTurvy.md @@ -0,0 +1,51 @@ +# Kaleidoscope-TopsyTurvy + +`TopsyTurvy` is a plugin that inverts the behaviour of the `Shift` key for some +selected keys. That is, if configured so, it will input `!` when pressing the +`1` key without `Shift`, but with the modifier pressed, it will input the +original `1` symbol. + +## Using the plugin + +To use the plugin, one needs to include the header, mark keys to apply plugin +effects to, and use the plugin: + +```c++ +#include +#include + +// In the keymap: +TOPSY(1), TOPSY(2), TOPSY(3) + +KALEIDOSCOPE_INIT_PLUGINS(TopsyTurvy); + +void setup () { + Kaleidoscope.setup (); +} +``` + +## Keymap markup + +There is only one macro that the plugin provides, which one can use in keymap definitions: + +### `TOPSY(key)` + +> Mark the specified `key` (without the `Key_` prefix!) for TopsyTurvy, and swap +> the effect of `Shift` when the key is used. One can have any number of +> topsy-turvy keys on a keymap. +> +> The keys must be plain old keys, modifiers or anything other augmentation +> cannot be applied. + +The plugin provides a number of macros one can use in keymap definitions: + +## Plugin methods + +The plugin provides the `TopsyTurvy` object, without any public methods or properties. + +## Further reading + +Starting from the [example][plugin:example] is the recommended way of getting +started with the plugin. + + [plugin:example]: ../../examples/TopsyTurvy/TopsyTurvy.ino diff --git a/examples/TopsyTurvy/TopsyTurvy.ino b/examples/TopsyTurvy/TopsyTurvy.ino new file mode 100644 index 00000000..1e1e52ed --- /dev/null +++ b/examples/TopsyTurvy/TopsyTurvy.ino @@ -0,0 +1,51 @@ +/* -*- mode: c++ -*- + * Kaleidoscope-TopsyTurvy -- Turn the effect of Shift upside down for certain keys + * Copyright (C) 2017, 2018 Keyboard.io, Inc + * + * This program is free software: you can redistribute it and/or modify it under + * the terms of the GNU General Public License as published by the Free Software + * Foundation, version 3. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more + * details. + * + * You should have received a copy of the GNU General Public License along with + * this program. If not, see . + */ + +#include +#include + +// *INDENT-OFF* +const Key keymaps[][ROWS][COLS] PROGMEM = { + [0] = KEYMAP_STACKED + ( + Key_NoKey, TOPSY(1), TOPSY(2), TOPSY(3), TOPSY(4), TOPSY(5), Key_NoKey, + Key_Backtick, Key_Q, Key_W, Key_E, Key_R, Key_T, Key_Tab, + Key_PageUp, Key_A, Key_S, Key_D, Key_F, Key_G, + Key_PageDown, Key_Z, Key_X, Key_C, Key_V, Key_B, Key_Escape, + + Key_LeftControl, Key_Backspace, Key_LeftGui, Key_LeftShift, + Key_skip, + + Key_skip, TOPSY(6), TOPSY(7), TOPSY(8), TOPSY(9), TOPSY(0), Key_skip, + Key_Enter, Key_Y, Key_U, Key_I, Key_O, Key_P, Key_Equals, + Key_H, Key_J, Key_K, Key_L, Key_Semicolon, Key_Quote, + Key_skip, Key_N, Key_M, Key_Comma, Key_Period, Key_Slash, Key_Minus, + + Key_RightShift, Key_RightAlt, Key_Spacebar, Key_RightControl, + Key_skip), +}; +// *INDENT-ON* + +KALEIDOSCOPE_INIT_PLUGINS(TopsyTurvy); + +void setup() { + Kaleidoscope.setup(); +} + +void loop() { + Kaleidoscope.loop(); +} diff --git a/src/Kaleidoscope-TopsyTurvy.h b/src/Kaleidoscope-TopsyTurvy.h new file mode 100644 index 00000000..ee7c5351 --- /dev/null +++ b/src/Kaleidoscope-TopsyTurvy.h @@ -0,0 +1,20 @@ +/* -*- mode: c++ -*- + * Kaleidoscope-TopsyTurvy -- Turn the effect of Shift upside down for certain keys + * Copyright (C) 2017 Keyboard.io, Inc + * + * This program is free software: you can redistribute it and/or modify it under + * the terms of the GNU General Public License as published by the Free Software + * Foundation, version 3. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more + * details. + * + * You should have received a copy of the GNU General Public License along with + * this program. If not, see . + */ + +#pragma once + +#include diff --git a/src/kaleidoscope/plugin/TopsyTurvy.cpp b/src/kaleidoscope/plugin/TopsyTurvy.cpp new file mode 100644 index 00000000..a7e460e7 --- /dev/null +++ b/src/kaleidoscope/plugin/TopsyTurvy.cpp @@ -0,0 +1,75 @@ +/* -*- mode: c++ -*- + * Kaleidoscope-TopsyTurvy -- Turn the effect of Shift upside down for certain keys + * Copyright (C) 2017, 2018 Keyboard.io, Inc + * + * This program is free software: you can redistribute it and/or modify it under + * the terms of the GNU General Public License as published by the Free Software + * Foundation, version 3. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more + * details. + * + * You should have received a copy of the GNU General Public License along with + * this program. If not, see . + */ + +#include +#include "kaleidoscope/hid.h" + +namespace kaleidoscope { +namespace plugin { + +uint8_t TopsyTurvy::last_pressed_position_; +bool TopsyTurvy::is_shifted_; +bool TopsyTurvy::is_active_; + +EventHandlerResult TopsyTurvy::onKeyswitchEvent(Key &mapped_key, byte row, byte col, uint8_t key_state) { + + if (mapped_key == Key_LeftShift || + mapped_key == Key_RightShift) { + is_shifted_ = keyIsPressed(key_state); + if (is_active_) + return EventHandlerResult::EVENT_CONSUMED; + } + + if (mapped_key < ranges::TT_FIRST || mapped_key > ranges::TT_LAST) { + if (keyToggledOn(key_state) && (mapped_key < Key_LeftControl || mapped_key > Key_RightGui)) { + last_pressed_position_ = row * COLS + col; + } + + return EventHandlerResult::OK; + } + + if (keyToggledOn(key_state)) { + last_pressed_position_ = row * COLS + col; + } else { + if (last_pressed_position_ != row * COLS + col) { + return EventHandlerResult::EVENT_CONSUMED; + } + } + + is_active_ = keyIsPressed(key_state); + mapped_key.raw = mapped_key.raw - ranges::TT_FIRST; + + // invert the shift state + if (!is_shifted_) { + mapped_key.flags |= SHIFT_HELD; + return EventHandlerResult::OK; + } + + if (keyIsPressed(key_state)) { + hid::releaseKey(Key_LeftShift); + hid::releaseKey(Key_RightShift); + + return EventHandlerResult::OK; + } + + return EventHandlerResult::EVENT_CONSUMED; +} + +} +} + +kaleidoscope::plugin::TopsyTurvy TopsyTurvy; diff --git a/src/kaleidoscope/plugin/TopsyTurvy.h b/src/kaleidoscope/plugin/TopsyTurvy.h new file mode 100644 index 00000000..d5ad5923 --- /dev/null +++ b/src/kaleidoscope/plugin/TopsyTurvy.h @@ -0,0 +1,42 @@ +/* -*- mode: c++ -*- + * Kaleidoscope-TopsyTurvy -- Turn the effect of Shift upside down for certain keys + * Copyright (C) 2017, 2018 Keyboard.io, Inc + * + * This program is free software: you can redistribute it and/or modify it under + * the terms of the GNU General Public License as published by the Free Software + * Foundation, version 3. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more + * details. + * + * You should have received a copy of the GNU General Public License along with + * this program. If not, see . + */ + +#pragma once + +#include +#include + +#define TOPSY(k) (Key) { .raw = kaleidoscope::ranges::TT_FIRST + (Key_ ## k).keyCode } + +namespace kaleidoscope { +namespace plugin { + +class TopsyTurvy: public kaleidoscope::Plugin { + public: + TopsyTurvy(void) {} + + EventHandlerResult onKeyswitchEvent(Key &mapped_key, byte row, byte col, uint8_t key_state); + + private: + static uint8_t last_pressed_position_; + static bool is_shifted_; + static bool is_active_; +}; +} +} + +extern kaleidoscope::plugin::TopsyTurvy TopsyTurvy;