Something went wrong. Try again.
keyboard stuff
Something went wrong. Try again.
13 kB · 465 lines
C++
at master
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466/* Copyright 2017 Colin T.A. Gray * * 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, either version 2 of the License, or * (at your option) any later version. * * 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 <http://www.gnu.org/licenses/>. */
#include "gtest/gtest.h"#include "keyboard_report_util.hpp"#include "test_common.hpp"
using testing::_;using testing::AnyNumber;using testing::InSequence;
class ActionLayer : public TestFixture {};
TEST_F(ActionLayer, LayerStateDBG) { TestDriver driver;
layer_state_set(0);
VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerStateSet) { TestDriver driver;
layer_state_set(0); EXPECT_EQ(layer_state, 0); layer_state_set(0b001100); EXPECT_EQ(layer_state, 0b001100);
VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerStateIs) { TestDriver driver;
layer_state_set(0); EXPECT_EQ(layer_state_is(0), true); EXPECT_EQ(layer_state_is(1), false); layer_state_set(1); EXPECT_EQ(layer_state_is(0), true); EXPECT_EQ(layer_state_is(1), false); layer_state_set(2); EXPECT_EQ(layer_state_is(0), false); EXPECT_EQ(layer_state_is(1), true); EXPECT_EQ(layer_state_is(2), false);
VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerStateCmp) { TestDriver driver; uint32_t prev_layer;
prev_layer = 0; EXPECT_EQ(layer_state_cmp(prev_layer, 0), true); EXPECT_EQ(layer_state_cmp(prev_layer, 1), false);
prev_layer = 1; EXPECT_EQ(layer_state_cmp(prev_layer, 0), true); EXPECT_EQ(layer_state_cmp(prev_layer, 1), false);
prev_layer = 2; EXPECT_EQ(layer_state_cmp(prev_layer, 0), false); EXPECT_EQ(layer_state_cmp(prev_layer, 1), true); EXPECT_EQ(layer_state_cmp(prev_layer, 2), false);
VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerClear) { TestDriver driver;
layer_clear(); EXPECT_EQ(layer_state, 0);
VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerMove) { TestDriver driver;
layer_move(0); EXPECT_EQ(layer_state, 1); layer_move(3); EXPECT_EQ(layer_state, 0b1000);
VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerOn) { TestDriver driver;
layer_clear(); layer_on(1); layer_on(3); layer_on(3); EXPECT_EQ(layer_state, 0b1010);
VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerOff) { TestDriver driver;
layer_clear(); layer_on(1); layer_on(3); layer_off(3); layer_off(2); EXPECT_EQ(layer_state, 0b0010);
VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, MomentaryLayerDoesNothing) { TestDriver driver; KeymapKey layer_key = KeymapKey{0, 0, 0, MO(1)};
set_keymap({layer_key});
/* Press and release MO, nothing should happen. */ EXPECT_NO_REPORT(driver); layer_key.press(); run_one_scan_loop(); VERIFY_AND_CLEAR(driver);
EXPECT_NO_REPORT(driver); layer_key.release(); run_one_scan_loop(); VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, MomentaryLayerWithKeypress) { TestDriver driver; KeymapKey layer_key = KeymapKey{0, 0, 0, MO(1)};
/* These keys must have the same position in the matrix, only the layer is different. */ KeymapKey regular_key = KeymapKey{0, 1, 0, KC_A}; set_keymap({layer_key, regular_key, KeymapKey{1, 1, 0, KC_B}});
/* Press MO. */ EXPECT_NO_REPORT(driver); layer_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);
/* Press key on layer 1 */ EXPECT_REPORT(driver, (KC_B)).Times(1); regular_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);
/* Release key on layer 1 */ EXPECT_EMPTY_REPORT(driver); regular_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);
/* Release MO */ EXPECT_NO_REPORT(driver); layer_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0)); VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, ToggleLayerDoesNothing) { GTEST_SKIP() << "TODO: Toggle layer does not activate the expected layer on key press but on release.";
TestDriver driver; KeymapKey layer_key = KeymapKey{0, 0, 0, TG(1)};
set_keymap({layer_key});
/* Press TG. Layer state should not change as it's applied on release. */ EXPECT_NO_REPORT(driver); layer_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);
/* Release TG. */ EXPECT_NO_REPORT(driver); layer_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, ToggleLayerUpAndDown) { GTEST_SKIP() << "TODO: Toggle layer does not activate the expected layer on key press but on release.";
TestDriver driver; KeymapKey toggle_layer_1_on_layer_0 = KeymapKey{0, 0, 0, TG(1)}; KeymapKey toggle_layer_0_on_layer_1 = KeymapKey{1, 1, 0, TG(0)};
set_keymap({toggle_layer_1_on_layer_0, toggle_layer_0_on_layer_1});
/* Toggle Layer 1. */ EXPECT_NO_REPORT(driver); toggle_layer_1_on_layer_0.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);
EXPECT_NO_REPORT(driver); toggle_layer_1_on_layer_0.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);
/* Toggle Layer 0. */ EXPECT_NO_REPORT(driver); toggle_layer_0_on_layer_1.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0)); VERIFY_AND_CLEAR(driver);
EXPECT_NO_REPORT(driver); toggle_layer_0_on_layer_1.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0)); VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerTapToggleDoesNothing) { GTEST_SKIP() << "TODO: Tap toggle layer does not activate the expected layer on key press.";
TestDriver driver; KeymapKey layer_key = KeymapKey{0, 0, 0, TT(1)};
set_keymap({layer_key});
/* Press and release TT. */ EXPECT_NO_REPORT(driver); layer_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);
EXPECT_NO_REPORT(driver); layer_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0)); VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerTapToggleWithKeypress) { GTEST_SKIP() << "TODO: Tap toggle layer does not activate the expected layer on key press.";
TestDriver driver; KeymapKey layer_key = KeymapKey{0, 0, 0, TT(1)};
/* These keys must have the same position in the matrix, only the layer is different. */ KeymapKey regular_key = KeymapKey{0, 1, 0, KC_A}; set_keymap({layer_key, regular_key, KeymapKey{1, 1, 0, KC_B}});
/* Press TT. */ EXPECT_NO_REPORT(driver); layer_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);
EXPECT_REPORT(driver, (KC_B)).Times(1); regular_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);
EXPECT_EMPTY_REPORT(driver); regular_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);
EXPECT_NO_REPORT(driver); layer_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0)); VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerTapToggleWithToggleWithKeypress) { GTEST_SKIP() << "TODO: Tap toggle layer does not activate the expected layer on key press.";
TestDriver driver; KeymapKey layer_key = KeymapKey{0, 0, 0, TT(1)};
/* These keys must have the same position in the matrix, only the layer is different. */ KeymapKey regular_key = KeymapKey{0, 1, 0, KC_A}; set_keymap({layer_key, regular_key, KeymapKey{1, 1, 0, KC_B}});
/* Tap TT five times . */ EXPECT_NO_REPORT(driver);
layer_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); layer_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0));
layer_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); layer_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0));
layer_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); layer_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0));
layer_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); layer_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0));
layer_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); layer_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1));
VERIFY_AND_CLEAR(driver);
EXPECT_REPORT(driver, (KC_B)).Times(1); regular_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);
EXPECT_EMPTY_REPORT(driver); regular_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerTapReleasedBeforeKeypressReleaseWithModifiers) { TestDriver driver; InSequence s;
KeymapKey layer_0_key_0 = KeymapKey{0, 0, 0, LT(1, KC_T)}; KeymapKey layer_0_key_1 = KeymapKey{0, 1, 0, KC_X}; KeymapKey layer_1_key_1 = KeymapKey{1, 1, 0, RALT(KC_9)};
set_keymap({layer_0_key_0, layer_0_key_1, layer_1_key_1});
/* Press layer tap and wait for tapping term to switch to layer 1 */ EXPECT_NO_REPORT(driver); layer_0_key_0.press(); idle_for(TAPPING_TERM); EXPECT_TRUE(layer_state_is(0)); VERIFY_AND_CLEAR(driver);
/* Press key with layer 1 mapping, result basically expected * altough more reports are send then necessary. */ EXPECT_REPORT(driver, (KC_RALT)).Times(1); EXPECT_REPORT(driver, (KC_RALT, KC_9)).Times(1); layer_1_key_1.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); VERIFY_AND_CLEAR(driver);
/* Release layer tap key, no report is send because key is still held. */ EXPECT_NO_REPORT(driver); layer_0_key_0.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0)); VERIFY_AND_CLEAR(driver);
/* Unregister keycode and modifier. */ EXPECT_REPORT(driver, (KC_RALT)).Times(1); EXPECT_EMPTY_REPORT(driver); layer_1_key_1.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0)); VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerModWithKeypress) { TestDriver driver; KeymapKey layer_key = KeymapKey{0, 0, 0, LM(1, MOD_RALT)}; KeymapKey regular_key = KeymapKey{0, 1, 0, KC_A}; set_keymap({layer_key, regular_key, KeymapKey{1, 1, 0, KC_B}});
// Allow any number of reports with no keys or only KC_RALT. // clang-format off EXPECT_CALL(driver, send_keyboard_mock(AnyOf( KeyboardReport(), KeyboardReport(KC_RALT)))) .Times(AnyNumber()); // clang-format on EXPECT_REPORT(driver, (KC_RALT, KC_B)).Times(1);
layer_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); EXPECT_EQ(get_mods(), MOD_BIT(KC_RALT));
tap_key(regular_key);
layer_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0)); EXPECT_EQ(get_mods(), 0);
VERIFY_AND_CLEAR(driver);}
TEST_F(ActionLayer, LayerModHonorsModConfig) { TestDriver driver; KeymapKey layer_key = KeymapKey{0, 0, 0, LM(1, MOD_RALT)}; KeymapKey regular_key = KeymapKey{0, 1, 0, KC_A}; set_keymap({layer_key, regular_key, KeymapKey{1, 1, 0, KC_B}});
// Allow any number of reports with no keys or only KC_RALT. // clang-format off EXPECT_CALL(driver, send_keyboard_mock(AnyOf( KeyboardReport(), KeyboardReport(KC_RGUI)))) .Times(AnyNumber()); // clang-format on EXPECT_REPORT(driver, (KC_RGUI, KC_B)).Times(1);
keymap_config.swap_ralt_rgui = true;
layer_key.press(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(1)); EXPECT_EQ(get_mods(), MOD_BIT(KC_RGUI));
tap_key(regular_key);
layer_key.release(); run_one_scan_loop(); EXPECT_TRUE(layer_state_is(0)); EXPECT_EQ(get_mods(), 0);
VERIFY_AND_CLEAR(driver);}