tests: Greatly simplify and clean up the layer activation-order test

The test has been through a major refactor, lifting out common parts, improving
comments, and naming.

Signed-off-by: Gergely Nagy <algernon@keyboard.io>
pull/867/head
Gergely Nagy 4 years ago
parent d90820afc7
commit ffcd17ba6e
No known key found for this signature in database
GPG Key ID: AC1E90BAC433F68F

@ -23,52 +23,52 @@
KEYMAPS(
[0] = KEYMAP_STACKED
(
Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A
,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A
,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A
,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A
,Key_A ,Key_A ,Key_A ,M(0)
Key_0 ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,M(0)
,ShiftToLayer(1)
,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A
,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A
,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A
,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A ,Key_A
,Key_A ,Key_A ,Key_A ,Key_A
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,Key_0
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX
,ShiftToLayer(2)
),
[1] = KEYMAP_STACKED
(
Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B
,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B
,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B
,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B
,Key_B ,Key_B ,Key_B ,Key_B
Key_1 ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX
,___
,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B
,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B
,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B
,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B ,Key_B
,Key_B ,Key_B ,Key_B ,Key_B
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,Key_1
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX
,___
),
[2] = KEYMAP_STACKED
(
Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C
,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C
,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C
,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C
,Key_C ,Key_C ,Key_C ,Key_C
Key_2 ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX
,___
,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C
,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C
,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C
,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C ,Key_C
,Key_C ,Key_C ,Key_C ,Key_C
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,Key_2
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX ,XXX ,XXX ,XXX
,XXX ,XXX ,XXX ,XXX
,___
)
) // KEYMAPS(

@ -26,150 +26,179 @@ using ::testing::IsEmpty;
class LayerActivationOrder : public VirtualDeviceTest {
public:
void SingleKeyTest(Key k) {
sim_.Press(0, 0); // k
auto state = RunCycle();
const KeyAddr KEYSWITCH_TOP_LEFT = KeyAddr{0, 0}; // layer-dependent key
const KeyAddr KEYSWITCH_TOP_RIGHT = KeyAddr{0, 15}; // layer-dependent key
const KeyAddr KEYSWITCH_LEFT_PALM = KeyAddr{3, 6}; // ShiftToLayer(1)
const KeyAddr KEYSWITCH_RIGHT_PALM = KeyAddr{3, 9}; // ShiftToLayer(2)
const KeyAddr KEYSWITCH_LEFT_THUMB_RIGHTMOST = KeyAddr{3, 7}; // L0 deactivate macro
const Key LAYER0_KEY = Key_0;
const Key LAYER1_KEY = Key_1;
const Key LAYER2_KEY = Key_2;
void pressKeyswitch(const KeyAddr& addr) {
sim_.Press(addr.row(), addr.col());
}
void releaseKeyswitch(const KeyAddr& addr) {
sim_.Release(addr.row(), addr.col());
}
auto pressKeyswitchAndCycle(const KeyAddr& addr) {
pressKeyswitch(addr);
return RunCycle();
}
auto releaseKeyswitchAndCycle(const KeyAddr& addr) {
releaseKeyswitch(addr);
return RunCycle();
}
void assertSingleReportThatContains(std::unique_ptr<State> &state, Key k) {
ASSERT_EQ(state->HIDReports()->Keyboard().size(), 1);
EXPECT_THAT(
state->HIDReports()->Keyboard(0).ActiveKeycodes(),
Contains(k));
}
sim_.Release(0, 0); // k
state = RunCycle();
void assertSingleReportThatDoesNotContain(std::unique_ptr<State> &state, Key k) {
ASSERT_EQ(state->HIDReports()->Keyboard().size(), 1);
EXPECT_THAT(
state->HIDReports()->Keyboard(0).ActiveKeycodes(),
::testing::Not(Contains(k)));
}
void assertSingleEmptyReport(std::unique_ptr<State> &state) {
ASSERT_EQ(state->HIDReports()->Keyboard().size(), 1);
EXPECT_THAT(
state->HIDReports()->Keyboard(0).ActiveKeycodes(),
IsEmpty());
}
void assertNoReport(std::unique_ptr<State> &state) {
ASSERT_EQ(state->HIDReports()->Keyboard().size(), 0);
}
void assertNoReportAfterCycle() {
auto state = RunCycle();
assertNoReport(state);
}
void TestPressAndRelease(const KeyAddr& addr, Key k) {
auto state = pressKeyswitchAndCycle(addr);
assertSingleReportThatContains(state, k);
state = RunCycle();
state = releaseKeyswitchAndCycle(addr);
assertSingleEmptyReport(state);
// 2 cycles after releasing k
EXPECT_EQ(state->HIDReports()->Keyboard().size(), 0);
assertNoReportAfterCycle();
}
};
TEST_F(LayerActivationOrder, BaseLayerHasNotRegressed) {
SingleKeyTest(Key_A);
TestPressAndRelease(KEYSWITCH_TOP_LEFT, LAYER0_KEY);
}
TEST_F(LayerActivationOrder, ShifToLayerOne) {
// Pressing (3,6) shifts to Layer 1, and we stay there until release.
// Pressing (KEYSWITCH_LEFT_PALM) shifts to Layer 1, and we stay there until release.
auto state = pressKeyswitchAndCycle(KEYSWITCH_LEFT_PALM);
TestPressAndRelease(KEYSWITCH_TOP_LEFT, LAYER1_KEY);
sim_.Press(3, 6); // ShiftToLayer(1)
auto state = RunCycle();
SingleKeyTest(Key_B);
// Releasing (3,6) gets us back to the base layer
sim_.Release(3, 6); // ShiftToLayer(1)
state = RunCycle();
SingleKeyTest(Key_A);
// Releasing (KEYSWITCH_LEFT_PALM) gets us back to the base layer
state = releaseKeyswitchAndCycle(KEYSWITCH_LEFT_PALM);
TestPressAndRelease(KEYSWITCH_TOP_LEFT, LAYER0_KEY);
}
TEST_F(LayerActivationOrder, ShiftingWithCaching) {
// Pressing (0, 0) will activate A
sim_.Press(0, 0);
auto state = RunCycle();
ASSERT_EQ(state->HIDReports()->Keyboard().size(), 1);
EXPECT_THAT(
state->HIDReports()->Keyboard(0).ActiveKeycodes(),
Contains(Key_A));
// Pressing (KEYSWITCH_TOP_LEFT) will activate the key on layer 0
auto state = pressKeyswitchAndCycle(KEYSWITCH_TOP_LEFT);
assertSingleReportThatContains(state, LAYER0_KEY);
// Pressing (3, 6) will switch to Layer 1
sim_.Press(3, 6);
state = RunCycle();
// ...since we're still pressing (0, 0), and there was no change in the HID
// states, we shouldn't emit a report.
ASSERT_EQ(state->HIDReports()->Keyboard().size(), 0);
// Pressing (KEYSWITCH_LEFT_PALM) will switch to Layer 1
state = pressKeyswitchAndCycle(KEYSWITCH_LEFT_PALM);
// Pressing (0, 1), the report shall contain 'A' _and_ 'B'.
sim_.Press(0, 1);
state = RunCycle();
// ...since we're still pressing (KEYSWITCH_TOP_LEFT), and there was no change
// in the HID states, we shouldn't emit a report.
assertNoReport(state);
ASSERT_EQ(state->HIDReports()->Keyboard().size(), 1);
EXPECT_THAT(
state->HIDReports()->Keyboard(0).ActiveKeycodes(),
Contains(Key_A));
EXPECT_THAT(
state->HIDReports()->Keyboard(0).ActiveKeycodes(),
Contains(Key_B));
// Releasing (0, 0), the report should now contain B only
sim_.Release(0, 0);
state = RunCycle();
// Pressing (KEYSWITCH_TOP_RIGHT), the report shall contain keys from both
// layer 0 and layer1, because we started holding the layer 0 key prior to
// switching layers, so it's code should remain cached.
state = pressKeyswitchAndCycle(KEYSWITCH_TOP_RIGHT);
assertSingleReportThatContains(state, LAYER0_KEY);
assertSingleReportThatContains(state, LAYER1_KEY);
ASSERT_EQ(state->HIDReports()->Keyboard().size(), 1);
EXPECT_THAT(
state->HIDReports()->Keyboard(0).ActiveKeycodes(),
Contains(Key_B));
// Releasing (KEYSWITCH_TOP_LEFT), the report should now contain the key from
// layer1 only, and should not contain the layer0 key anymore.
state = releaseKeyswitchAndCycle(KEYSWITCH_TOP_LEFT);
assertSingleReportThatContains(state, LAYER1_KEY);
assertSingleReportThatDoesNotContain(state, LAYER0_KEY);
// Release (0, 1)
sim_.Release(0, 1);
state = RunCycle();
// Release (KEYSWITCH_TOP_RIGHT)
state = releaseKeyswitchAndCycle(KEYSWITCH_TOP_RIGHT);
// Test B in isolation again
SingleKeyTest(Key_B);
// Test the layer 1 key in isolation again
TestPressAndRelease(KEYSWITCH_TOP_LEFT, LAYER1_KEY);
// Release the layer key as well.
sim_.Release(3, 6);
state = RunCycle();
state = releaseKeyswitchAndCycle(KEYSWITCH_LEFT_PALM);
ASSERT_EQ(state->HIDReports()->Keyboard().size(), 0);
// Since the layer key release is internal to us, we shouldn't send a report.
assertNoReport(state);
}
TEST_F(LayerActivationOrder, Ordering) {
// Pressing (3, 9) will switch to Layer 2
sim_.Press(3, 9);
auto state = RunCycle();
// Pressing (0, 0) will activate 'C'
sim_.Press(0, 0);
state = RunCycle();
ASSERT_EQ(state->HIDReports()->Keyboard().size(), 1);
EXPECT_THAT(
state->HIDReports()->Keyboard(0).ActiveKeycodes(),
Contains(Key_C));
// Pressing (3, 6) will activate Layer 1
sim_.Press(3, 6);
// Pressing (KEYSWITCH_RIGHT_PALM) will switch to Layer 2
auto state = pressKeyswitchAndCycle(KEYSWITCH_RIGHT_PALM);
// Pressing (KEYSWITCH_TOP_LEFT) will activate a key on layer 2
state = pressKeyswitchAndCycle(KEYSWITCH_TOP_LEFT);
assertSingleReportThatContains(state, LAYER2_KEY);
// Pressing (KEYSWITCH_LEFT_PALM) will activate Layer 1
state = pressKeyswitchAndCycle(KEYSWITCH_LEFT_PALM);
// Pressing (KEYSWITCH_TOP_RIGHT) will activate the layer 1 key now, due to
// activation ordering.
state = pressKeyswitchAndCycle(KEYSWITCH_TOP_RIGHT);
// We should have both the layer 1 and the layer 2 key active, because we're
// holding both.
assertSingleReportThatContains(state, LAYER1_KEY);
assertSingleReportThatContains(state, LAYER2_KEY);
// Releaseing all held keys, we should get an empty report.
releaseKeyswitch(KEYSWITCH_TOP_LEFT);
releaseKeyswitch(KEYSWITCH_TOP_RIGHT);
releaseKeyswitch(KEYSWITCH_LEFT_PALM);
releaseKeyswitch(KEYSWITCH_RIGHT_PALM);
state = RunCycle();
// Pressing (0, 1) will activate 'B' now, due to activation ordering.
sim_.Press(0, 1);
state = RunCycle();
assertSingleEmptyReport(state);
ASSERT_EQ(state->HIDReports()->Keyboard().size(), 1);
EXPECT_THAT(
state->HIDReports()->Keyboard(0).ActiveKeycodes(),
Contains(Key_C));
EXPECT_THAT(
state->HIDReports()->Keyboard(0).ActiveKeycodes(),
Contains(Key_B));
sim_.Release(0, 0);
sim_.Release(0, 1);
sim_.Release(3, 6);
sim_.Release(3, 9);
// One more cycle, and we should generate no report at all
state = RunCycle();
assertNoReport(state);
}
TEST_F(LayerActivationOrder, LayerZero) {
sim_.Press(3, 7); // Macro#0: Layer.deactivate(0)
auto state = RunCycle();
// Pressing the rightmost of the left thumb keys should deactivate layer 0
auto state = pressKeyswitchAndCycle(KEYSWITCH_LEFT_THUMB_RIGHTMOST);
// Pressing KEYSWITCH_TOP_LEFT should fall back to activating the key on layer 0
state = pressKeyswitchAndCycle(KEYSWITCH_TOP_LEFT);
assertSingleReportThatContains(state, LAYER0_KEY);
sim_.Press(0, 0); // A
// Releasing all keys should generate a single empty report
releaseKeyswitch(KEYSWITCH_TOP_LEFT);
releaseKeyswitch(KEYSWITCH_LEFT_THUMB_RIGHTMOST);
state = RunCycle();
ASSERT_EQ(state->HIDReports()->Keyboard().size(), 1);
EXPECT_THAT(
state->HIDReports()->Keyboard(0).ActiveKeycodes(),
Contains(Key_A));
assertSingleEmptyReport(state);
// Afterwards, we should generate no more reports.
state = RunCycle();
assertNoReport(state);
}
} // namespace

Loading…
Cancel
Save