From 2d4ab1d724e1adc6008277ae3eee592b706ddee8 Mon Sep 17 00:00:00 2001 From: Fred Emmott Date: Thu, 30 Jun 2022 17:11:19 -0500 Subject: [PATCH] Add shift mode support --- README.md | 15 +++++++++++++++ lib/Shift.h | 46 ++++++++++++++++++++++++++++++++++++++++++++ lib/easymode.h | 1 + tests/Shift_test.cpp | 35 +++++++++++++++++++++++++++++++++ 4 files changed, 97 insertions(+) create mode 100644 lib/Shift.h create mode 100644 tests/Shift_test.cpp diff --git a/README.md b/README.md index 31d0045..4908207 100644 --- a/README.md +++ b/README.md @@ -165,6 +165,7 @@ These can then be added to your code, as shown in `devicedb.h`. - `HatToButtons` - `LatchedToMomentaryButton` - `MomentaryToLatchedButton` +- `Shift` - `ShortPressLongPress` - `SquareDeadzone` @@ -318,6 +319,20 @@ Does the exact opposite of `LatchedToMomentaryButton`: it converts a short press stick.Button1 >> MomentaryToLatchedButton() >> vj.Button1; ``` +## Shift + +Switches between actions, depending on an on/off state: + +```C++ +bool shifted = false; +stick.Button15 >> &shifted; +stick.Button16 >> Shift { + &shifted, + /* normal behavior */ vj.Button1, + /* shifted behavior */ vj.Button2, +}; +``` + ## ShortPressLongPress This divides a button into two, depending on if a button is pressed and quickly released, or held for a moment. diff --git a/lib/Shift.h b/lib/Shift.h new file mode 100644 index 0000000..c413fdd --- /dev/null +++ b/lib/Shift.h @@ -0,0 +1,46 @@ +/* + * Copyright (c) 2020-present, Fred Emmott + * All rights reserved. + * + * This source code is licensed under the ISC license found in the LICENSE file + * in the root directory of this source tree. + */ +#pragma once + +#include "Sink.h" +#include "SinkPtr.h" + +namespace fredemmott::inputmapping { + +template +class Shift : public Sink { + private: + bool* mShifted = nullptr; + SinkPtr mA, mB; + + public: + template A, convertible_to_sink_ptr B> + Shift(bool* shifted, A&& a, B&& b) + : mShifted(shifted), + mA(convert_to_any_sink_ptr(std::forward(a))), + mB(convert_to_any_sink_ptr(std::forward(b))) { + } + + virtual void map(typename T::Value value) override { + auto next = *mShifted ? mB : mA; + next->map(value); + } +}; + +// Help template inference along a bit... + +template A, convertible_to_sink_ptr B> +Shift(bool*, A, B) -> Shift; + +template A, convertible_to_sink_ptr