// Standalone tests for which dispatched action ids end the FX reclaim span — no REAPER, // no test framework. The predicate is the whole of the interception's decision; the close // it drives needs a DAW. What is assertable here: the id pair is exact, and it is scoped // to the main sections, because command ids are per-section and the same integer under // another section is an unrelated action. #include "../src/shell/undo/undo_intercept.h" #include using namespace reasampler; static int g_fail = 0; #define CHECK(cond) do { if(!(cond)) { \ std::printf("FAIL line %d: %s\n", __LINE__, #cond); ++g_fail; } } while(0) namespace { constexpr int kMainSection = 0; constexpr int kMainAltSection = 100; constexpr int kMidiEditor = 32060; constexpr int kMediaExplorer = 32063; void undoAndRedoInTheMainSectionAreIntercepted() { CHECK(isMainUndoRedoCommand(kEditUndoCommand, kMainSection)); CHECK(isMainUndoRedoCommand(kEditRedoCommand, kMainSection)); // Main alt shares the main id space (reaper_plugin.h: "0/100=main/main alt"), so a // Ctrl-Z fired while the alt section is active is the same action. CHECK(isMainUndoRedoCommand(kEditUndoCommand, kMainAltSection)); CHECK(isMainUndoRedoCommand(kEditRedoCommand, kMainAltSection)); } void everyOtherMainSectionActionIsLeftAlone() { // Every action in the tree passes through this predicate; only these two ids may end // the span, or an ordinary edit made mid-drain would split the switch's undo point. CHECK(!isMainUndoRedoCommand(kEditUndoCommand - 1, kMainSection)); CHECK(!isMainUndoRedoCommand(kEditRedoCommand + 1, kMainSection)); CHECK(!isMainUndoRedoCommand(40012, kMainSection)); CHECK(!isMainUndoRedoCommand(0, kMainSection)); CHECK(!isMainUndoRedoCommand(-1, kMainSection)); } void theSameIdsUnderAnotherSectionAreNotOurUndo() { CHECK(!isMainUndoRedoCommand(kEditUndoCommand, kMidiEditor)); CHECK(!isMainUndoRedoCommand(kEditRedoCommand, kMidiEditor)); CHECK(!isMainUndoRedoCommand(kEditUndoCommand, kMediaExplorer)); // A hook that could not name its section (null KbdSectionInfo) is not assumed to be // main — hookcommand covers the main section unconditionally anyway. CHECK(!isMainUndoRedoCommand(kEditUndoCommand, -1)); } } // namespace int main() { undoAndRedoInTheMainSectionAreIntercepted(); everyOtherMainSectionActionIsLeftAlone(); theSameIdsUnderAnotherSectionAreNotOurUndo(); if (g_fail) { std::printf("%d check(s) failed\n", g_fail); return 1; } std::printf("undo_intercept: all checks passed\n"); return 0; }