From 55f7ce118e3b515fb3b18425bb79e2dda1a2b97d Mon Sep 17 00:00:00 2001 From: Mike Griese Date: Mon, 1 Jun 2020 16:39:33 -0500 Subject: [PATCH 1/9] This adds short-form aliases for each of the existing wt subcommands --- .../TerminalApp/AppCommandlineArgs.cpp | 201 ++++++++++-------- src/cascadia/TerminalApp/AppCommandlineArgs.h | 14 +- .../Resources/en-US/Resources.resw | 12 ++ 3 files changed, 137 insertions(+), 90 deletions(-) diff --git a/src/cascadia/TerminalApp/AppCommandlineArgs.cpp b/src/cascadia/TerminalApp/AppCommandlineArgs.cpp index 0d8dbec1a71..ae91a37d1e9 100644 --- a/src/cascadia/TerminalApp/AppCommandlineArgs.cpp +++ b/src/cascadia/TerminalApp/AppCommandlineArgs.cpp @@ -180,6 +180,7 @@ void AppCommandlineArgs::_buildParser() // Method Description: // - Adds the `new-tab` subcommand and related options to the commandline parser. +// - Additionally adds the `nt` subcommand, which is just a shortened version of `new-tab` // Arguments: // - // Return Value: @@ -187,27 +188,35 @@ void AppCommandlineArgs::_buildParser() void AppCommandlineArgs::_buildNewTabParser() { _newTabCommand.subcommand = _app.add_subcommand("new-tab", RS_A(L"CmdNewTabDesc")); - _addNewTerminalArgs(_newTabCommand); + _newTabShort.subcommand = _app.add_subcommand("nt", RS_A(L"CmdNTDesc")); + + auto setupSubcommand = [this](auto& subcommand) { + _addNewTerminalArgs(subcommand); + + // When ParseCommand is called, if this subcommand was provided, this + // callback function will be triggered on the same thread. We can be sure + // that `this` will still be safe - this function just lets us know this + // command was parsed. + subcommand.subcommand->callback([&, this]() { + // Build the NewTab action from the values we've parsed on the commandline. + auto newTabAction = winrt::make_self(); + newTabAction->Action(ShortcutAction::NewTab); + auto args = winrt::make_self(); + // _getNewTerminalArgs MUST be called before parsing any other options, + // as it might clear those options while finding the commandline + args->TerminalArgs(_getNewTerminalArgs(subcommand)); + newTabAction->Args(*args); + _startupActions.push_back(*newTabAction); + }); + }; - // When ParseCommand is called, if this subcommand was provided, this - // callback function will be triggered on the same thread. We can be sure - // that `this` will still be safe - this function just lets us know this - // command was parsed. - _newTabCommand.subcommand->callback([&, this]() { - // Build the NewTab action from the values we've parsed on the commandline. - auto newTabAction = winrt::make_self(); - newTabAction->Action(ShortcutAction::NewTab); - auto args = winrt::make_self(); - // _getNewTerminalArgs MUST be called before parsing any other options, - // as it might clear those options while finding the commandline - args->TerminalArgs(_getNewTerminalArgs(_newTabCommand)); - newTabAction->Args(*args); - _startupActions.push_back(*newTabAction); - }); + setupSubcommand(_newTabCommand); + setupSubcommand(_newTabShort); } // Method Description: // - Adds the `split-pane` subcommand and related options to the commandline parser. +// - Additionally adds the `sp` subcommand, which is just a shortened version of `split-pane` // Arguments: // - // Return Value: @@ -215,49 +224,57 @@ void AppCommandlineArgs::_buildNewTabParser() void AppCommandlineArgs::_buildSplitPaneParser() { _newPaneCommand.subcommand = _app.add_subcommand("split-pane", RS_A(L"CmdSplitPaneDesc")); - _addNewTerminalArgs(_newPaneCommand); - _horizontalOption = _newPaneCommand.subcommand->add_flag("-H,--horizontal", - _splitHorizontal, - RS_A(L"CmdSplitPaneHorizontalArgDesc")); - _verticalOption = _newPaneCommand.subcommand->add_flag("-V,--vertical", - _splitVertical, - RS_A(L"CmdSplitPaneVerticalArgDesc")); - _verticalOption->excludes(_horizontalOption); - - // When ParseCommand is called, if this subcommand was provided, this - // callback function will be triggered on the same thread. We can be sure - // that `this` will still be safe - this function just lets us know this - // command was parsed. - _newPaneCommand.subcommand->callback([&, this]() { - // Build the SplitPane action from the values we've parsed on the commandline. - auto splitPaneActionAndArgs = winrt::make_self(); - splitPaneActionAndArgs->Action(ShortcutAction::SplitPane); - auto args = winrt::make_self(); - // _getNewTerminalArgs MUST be called before parsing any other options, - // as it might clear those options while finding the commandline - args->TerminalArgs(_getNewTerminalArgs(_newPaneCommand)); - args->SplitStyle(SplitState::Automatic); - // Make sure to use the `Option`s here to check if they were set - - // _getNewTerminalArgs might reset them while parsing a commandline - if ((*_horizontalOption || *_verticalOption)) - { - if (_splitHorizontal) - { - args->SplitStyle(SplitState::Horizontal); - } - else if (_splitVertical) + _newPaneShort.subcommand = _app.add_subcommand("sp", RS_A(L"CmdSPDesc")); + + auto setupSubcommand = [this](auto& subcommand) { + _addNewTerminalArgs(subcommand); + subcommand._horizontalOption = subcommand.subcommand->add_flag("-H,--horizontal", + _splitHorizontal, + RS_A(L"CmdSplitPaneHorizontalArgDesc")); + subcommand._verticalOption = subcommand.subcommand->add_flag("-V,--vertical", + _splitVertical, + RS_A(L"CmdSplitPaneVerticalArgDesc")); + subcommand._verticalOption->excludes(subcommand._horizontalOption); + + // When ParseCommand is called, if this subcommand was provided, this + // callback function will be triggered on the same thread. We can be sure + // that `this` will still be safe - this function just lets us know this + // command was parsed. + subcommand.subcommand->callback([&, this]() { + // Build the SplitPane action from the values we've parsed on the commandline. + auto splitPaneActionAndArgs = winrt::make_self(); + splitPaneActionAndArgs->Action(ShortcutAction::SplitPane); + auto args = winrt::make_self(); + // _getNewTerminalArgs MUST be called before parsing any other options, + // as it might clear those options while finding the commandline + args->TerminalArgs(_getNewTerminalArgs(subcommand)); + args->SplitStyle(SplitState::Automatic); + // Make sure to use the `Option`s here to check if they were set - + // _getNewTerminalArgs might reset them while parsing a commandline + if ((*subcommand._horizontalOption || *subcommand._verticalOption)) { - args->SplitStyle(SplitState::Vertical); + if (_splitHorizontal) + { + args->SplitStyle(SplitState::Horizontal); + } + else if (_splitVertical) + { + args->SplitStyle(SplitState::Vertical); + } } - } - splitPaneActionAndArgs->Args(*args); - _startupActions.push_back(*splitPaneActionAndArgs); - }); + splitPaneActionAndArgs->Args(*args); + _startupActions.push_back(*splitPaneActionAndArgs); + }); + }; + + setupSubcommand(_newPaneCommand); + setupSubcommand(_newPaneShort); } // Method Description: -// - Adds the `new-tab` subcommand and related options to the commandline parser. +// - Adds the `focus-tab` subcommand and related options to the commandline parser. +// - Additionally adds the `ft` subcommand, which is just a shortened version of `focus-tab` // Arguments: // - // Return Value: @@ -265,39 +282,48 @@ void AppCommandlineArgs::_buildSplitPaneParser() void AppCommandlineArgs::_buildFocusTabParser() { _focusTabCommand = _app.add_subcommand("focus-tab", RS_A(L"CmdFocusTabDesc")); - auto* indexOpt = _focusTabCommand->add_option("-t,--target", _focusTabIndex, RS_A(L"CmdFocusTabTargetArgDesc")); - auto* nextOpt = _focusTabCommand->add_flag("-n,--next", - _focusNextTab, - RS_A(L"CmdFocusTabNextArgDesc")); - auto* prevOpt = _focusTabCommand->add_flag("-p,--previous", - _focusPrevTab, - RS_A(L"CmdFocusTabPrevArgDesc")); - nextOpt->excludes(prevOpt); - indexOpt->excludes(prevOpt); - indexOpt->excludes(nextOpt); - - // When ParseCommand is called, if this subcommand was provided, this - // callback function will be triggered on the same thread. We can be sure - // that `this` will still be safe - this function just lets us know this - // command was parsed. - _focusTabCommand->callback([&, this]() { - // Build the action from the values we've parsed on the commandline. - auto focusTabAction = winrt::make_self(); - - if (_focusTabIndex >= 0) - { - focusTabAction->Action(ShortcutAction::SwitchToTab); - auto args = winrt::make_self(); - args->TabIndex(_focusTabIndex); - focusTabAction->Args(*args); - _startupActions.push_back(*focusTabAction); - } - else if (_focusNextTab || _focusPrevTab) - { - focusTabAction->Action(_focusNextTab ? ShortcutAction::NextTab : ShortcutAction::PrevTab); - _startupActions.push_back(*focusTabAction); - } - }); + _focusTabShort = _app.add_subcommand("ft", RS_A(L"CmdFTDesc")); + + auto setupSubcommand = [this](auto* subcommand) { + auto* indexOpt = subcommand->add_option("-t,--target", + _focusTabIndex, + RS_A(L"CmdFocusTabTargetArgDesc")); + auto* nextOpt = subcommand->add_flag("-n,--next", + _focusNextTab, + RS_A(L"CmdFocusTabNextArgDesc")); + auto* prevOpt = subcommand->add_flag("-p,--previous", + _focusPrevTab, + RS_A(L"CmdFocusTabPrevArgDesc")); + nextOpt->excludes(prevOpt); + indexOpt->excludes(prevOpt); + indexOpt->excludes(nextOpt); + + // When ParseCommand is called, if this subcommand was provided, this + // callback function will be triggered on the same thread. We can be sure + // that `this` will still be safe - this function just lets us know this + // command was parsed. + subcommand->callback([&, this]() { + // Build the action from the values we've parsed on the commandline. + auto focusTabAction = winrt::make_self(); + + if (_focusTabIndex >= 0) + { + focusTabAction->Action(ShortcutAction::SwitchToTab); + auto args = winrt::make_self(); + args->TabIndex(_focusTabIndex); + focusTabAction->Args(*args); + _startupActions.push_back(*focusTabAction); + } + else if (_focusNextTab || _focusPrevTab) + { + focusTabAction->Action(_focusNextTab ? ShortcutAction::NextTab : ShortcutAction::PrevTab); + _startupActions.push_back(*focusTabAction); + } + }); + }; + + setupSubcommand(_focusTabCommand); + setupSubcommand(_focusTabShort); } // Method Description: @@ -386,7 +412,10 @@ NewTerminalArgs AppCommandlineArgs::_getNewTerminalArgs(AppCommandlineArgs::NewT bool AppCommandlineArgs::_noCommandsProvided() { return !(*_newTabCommand.subcommand || + *_newTabShort.subcommand || *_focusTabCommand || + *_focusTabShort || + *_newPaneShort.subcommand || *_newPaneCommand.subcommand); } diff --git a/src/cascadia/TerminalApp/AppCommandlineArgs.h b/src/cascadia/TerminalApp/AppCommandlineArgs.h index 1a46d644b8a..d5b805c1349 100644 --- a/src/cascadia/TerminalApp/AppCommandlineArgs.h +++ b/src/cascadia/TerminalApp/AppCommandlineArgs.h @@ -53,15 +53,21 @@ class TerminalApp::AppCommandlineArgs final CLI::Option* startingDirectoryOption; }; + struct NewPaneSubcommand : public NewTerminalSubcommand + { + CLI::Option* _horizontalOption; + CLI::Option* _verticalOption; + }; + // --- Subcommands --- NewTerminalSubcommand _newTabCommand; - NewTerminalSubcommand _newPaneCommand; + NewTerminalSubcommand _newTabShort; + NewPaneSubcommand _newPaneCommand; + NewPaneSubcommand _newPaneShort; CLI::App* _focusTabCommand; + CLI::App* _focusTabShort; // Are you adding a new sub-command? Make sure to update _noCommandsProvided! - CLI::Option* _horizontalOption; - CLI::Option* _verticalOption; - std::string _profileName; std::string _startingDirectory; diff --git a/src/cascadia/TerminalApp/Resources/en-US/Resources.resw b/src/cascadia/TerminalApp/Resources/en-US/Resources.resw index bdc3cf861e8..6a63d079b45 100644 --- a/src/cascadia/TerminalApp/Resources/en-US/Resources.resw +++ b/src/cascadia/TerminalApp/Resources/en-US/Resources.resw @@ -231,6 +231,10 @@ Move focus to the next tab + + An alias for the "focus-tab" subcommand. + {Locked="\"focus-tab\""} + Move focus to the previous tab @@ -240,12 +244,20 @@ Create a new tab + + An alias for the "new-tab" subcommand. + {Locked="\"new-tab\""} + Open with the given profile. Accepts either the name or GUID of a profile Create a new split pane + + An alias for the "split-pane" subcommand. + {Locked="\"split-pane\""} + Create the new pane as a horizontal split (think [-]) From 4cf5376356cc2d04ea83c406a108a8791abe3758 Mon Sep 17 00:00:00 2001 From: Mike Griese Date: Mon, 1 Jun 2020 16:56:22 -0500 Subject: [PATCH 2/9] Get the tests to pass as well --- .../CommandlineTest.cpp | 73 +++++++++++++------ 1 file changed, 52 insertions(+), 21 deletions(-) diff --git a/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp b/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp index e6e67bdb373..57f45319b16 100644 --- a/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp +++ b/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp @@ -388,9 +388,16 @@ namespace TerminalAppLocalTests void CommandlineTest::ParseNewTabCommand() { + BEGIN_TEST_METHOD_PROPERTIES() + TEST_METHOD_PROPERTY(L"Data:useShortForm", L"{false, true}") + END_TEST_METHOD_PROPERTIES() + + INIT_TEST_PROPERTY(bool, useShortForm, L"TODO"); + const wchar_t* subcommand = useShortForm ? L"nt" : L"new-tab"; + { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"new-tab" }; + std::vector rawCommands{ L"wt.exe", subcommand }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(1u, appArgs._startupActions.size()); @@ -409,7 +416,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"new-tab", L"--profile", L"cmd" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"--profile", L"cmd" }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(1u, appArgs._startupActions.size()); @@ -429,7 +436,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"new-tab", L"--startingDirectory", L"c:\\Foo" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"--startingDirectory", L"c:\\Foo" }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(1u, appArgs._startupActions.size()); @@ -449,7 +456,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"new-tab", L"powershell.exe" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"powershell.exe" }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(1u, appArgs._startupActions.size()); @@ -469,7 +476,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"new-tab", L"powershell.exe", L"This is an arg with spaces" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"powershell.exe", L"This is an arg with spaces" }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(1u, appArgs._startupActions.size()); @@ -490,7 +497,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"new-tab", L"powershell.exe", L"This is an arg with spaces", L"another-arg", L"more spaces in this one" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"powershell.exe", L"This is an arg with spaces", L"another-arg", L"more spaces in this one" }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(1u, appArgs._startupActions.size()); @@ -511,7 +518,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"new-tab", L"-p", L"Windows PowerShell" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"-p", L"Windows PowerShell" }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(1u, appArgs._startupActions.size()); @@ -531,7 +538,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"new-tab", L"wsl", L"-d", L"Alpine" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"wsl", L"-d", L"Alpine" }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(1u, appArgs._startupActions.size()); @@ -551,7 +558,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"new-tab", L"-p", L"1", L"wsl", L"-d", L"Alpine" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"-p", L"1", L"wsl", L"-d", L"Alpine" }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(1u, appArgs._startupActions.size()); @@ -574,9 +581,16 @@ namespace TerminalAppLocalTests void CommandlineTest::ParseSplitPaneIntoArgs() { + BEGIN_TEST_METHOD_PROPERTIES() + TEST_METHOD_PROPERTY(L"Data:useShortForm", L"{false, true}") + END_TEST_METHOD_PROPERTIES() + + INIT_TEST_PROPERTY(bool, useShortForm, L"TODO"); + const wchar_t* subcommand = useShortForm ? L"sp" : L"split-pane"; + { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"split-pane" }; + std::vector rawCommands{ L"wt.exe", subcommand }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(2u, appArgs._startupActions.size()); @@ -595,7 +609,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"split-pane", L"-H" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"-H" }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(2u, appArgs._startupActions.size()); @@ -614,7 +628,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"split-pane", L"-V" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"-V" }; auto commandlines = AppCommandlineArgs::BuildCommands(rawCommands); VERIFY_ARE_EQUAL(1u, commandlines.size()); _buildCommandlinesHelper(appArgs, 1u, rawCommands); @@ -635,7 +649,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"split-pane", L"-p", L"1", L"wsl", L"-d", L"Alpine" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"-p", L"1", L"wsl", L"-d", L"Alpine" }; auto commandlines = AppCommandlineArgs::BuildCommands(rawCommands); VERIFY_ARE_EQUAL(1u, commandlines.size()); _buildCommandlinesHelper(appArgs, 1u, rawCommands); @@ -662,7 +676,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"split-pane", L"-p", L"1", L"-H", L"wsl", L"-d", L"Alpine" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"-p", L"1", L"-H", L"wsl", L"-d", L"Alpine" }; auto commandlines = AppCommandlineArgs::BuildCommands(rawCommands); VERIFY_ARE_EQUAL(1u, commandlines.size()); _buildCommandlinesHelper(appArgs, 1u, rawCommands); @@ -689,7 +703,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"split-pane", L"-p", L"1", L"wsl", L"-d", L"Alpine", L"-H" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"-p", L"1", L"wsl", L"-d", L"Alpine", L"-H" }; auto commandlines = AppCommandlineArgs::BuildCommands(rawCommands); VERIFY_ARE_EQUAL(1u, commandlines.size()); _buildCommandlinesHelper(appArgs, 1u, rawCommands); @@ -718,8 +732,18 @@ namespace TerminalAppLocalTests void CommandlineTest::ParseComboCommandlineIntoArgs() { + BEGIN_TEST_METHOD_PROPERTIES() + TEST_METHOD_PROPERTY(L"Data:useShortFormNewTab", L"{false, true}") + TEST_METHOD_PROPERTY(L"Data:useShortFormSplitPane", L"{false, true}") + END_TEST_METHOD_PROPERTIES() + + INIT_TEST_PROPERTY(bool, useShortFormNewTab, L"TODO"); + INIT_TEST_PROPERTY(bool, useShortFormSplitPane, L"TODO"); + const wchar_t* ntSubcommand = useShortFormNewTab ? L"nt" : L"new-tab"; + const wchar_t* spSubcommand = useShortFormSplitPane ? L"sp" : L"split-pane"; + AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"new-tab", L";", L"split-pane" }; + std::vector rawCommands{ L"wt.exe", ntSubcommand, L";", spSubcommand }; auto commandlines = AppCommandlineArgs::BuildCommands(rawCommands); _buildCommandlinesHelper(appArgs, 2u, rawCommands); @@ -834,9 +858,16 @@ namespace TerminalAppLocalTests void CommandlineTest::ParseFocusTabArgs() { + BEGIN_TEST_METHOD_PROPERTIES() + TEST_METHOD_PROPERTY(L"Data:useShortForm", L"{false, true}") + END_TEST_METHOD_PROPERTIES() + + INIT_TEST_PROPERTY(bool, useShortForm, L"TODO"); + const wchar_t* subcommand = useShortForm ? L"ft" : L"focus-tab"; + { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"focus-tab" }; + std::vector rawCommands{ L"wt.exe", subcommand }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(1u, appArgs._startupActions.size()); @@ -846,7 +877,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"focus-tab", L"-n" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"-n" }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(2u, appArgs._startupActions.size()); @@ -860,7 +891,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"focus-tab", L"-p" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"-p" }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(2u, appArgs._startupActions.size()); @@ -874,7 +905,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"focus-tab", L"-t", L"2" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"-t", L"2" }; _buildCommandlinesHelper(appArgs, 1u, rawCommands); VERIFY_ARE_EQUAL(2u, appArgs._startupActions.size()); @@ -894,7 +925,7 @@ namespace TerminalAppLocalTests Log::Comment(NoThrowString().Format( L"Attempt an invalid combination of flags")); AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", L"focus-tab", L"-p", L"-n" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"-p", L"-n" }; auto commandlines = AppCommandlineArgs::BuildCommands(rawCommands); VERIFY_ARE_EQUAL(1u, commandlines.size()); From 3c6bd72e22c9b34282ca69d2654c08a733b58f8c Mon Sep 17 00:00:00 2001 From: Mike Griese Date: Thu, 18 Jun 2020 14:29:03 -0500 Subject: [PATCH 3/9] clean up leftover todos --- .../LocalTests_TerminalApp/CommandlineTest.cpp | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp b/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp index 57f45319b16..e9191a4f2f5 100644 --- a/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp +++ b/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp @@ -392,7 +392,7 @@ namespace TerminalAppLocalTests TEST_METHOD_PROPERTY(L"Data:useShortForm", L"{false, true}") END_TEST_METHOD_PROPERTIES() - INIT_TEST_PROPERTY(bool, useShortForm, L"TODO"); + INIT_TEST_PROPERTY(bool, useShortForm, L"If true, use `nt` instead of `new-tab`"); const wchar_t* subcommand = useShortForm ? L"nt" : L"new-tab"; { @@ -585,7 +585,7 @@ namespace TerminalAppLocalTests TEST_METHOD_PROPERTY(L"Data:useShortForm", L"{false, true}") END_TEST_METHOD_PROPERTIES() - INIT_TEST_PROPERTY(bool, useShortForm, L"TODO"); + INIT_TEST_PROPERTY(bool, useShortForm, L"If true, use `sp` instead of `split-pane`"); const wchar_t* subcommand = useShortForm ? L"sp" : L"split-pane"; { @@ -737,8 +737,8 @@ namespace TerminalAppLocalTests TEST_METHOD_PROPERTY(L"Data:useShortFormSplitPane", L"{false, true}") END_TEST_METHOD_PROPERTIES() - INIT_TEST_PROPERTY(bool, useShortFormNewTab, L"TODO"); - INIT_TEST_PROPERTY(bool, useShortFormSplitPane, L"TODO"); + INIT_TEST_PROPERTY(bool, useShortFormNewTab, L"If true, use `nt` instead of `new-tab`"); + INIT_TEST_PROPERTY(bool, useShortFormSplitPane, L"If true, use `sp` instead of `split-pane`"); const wchar_t* ntSubcommand = useShortFormNewTab ? L"nt" : L"new-tab"; const wchar_t* spSubcommand = useShortFormSplitPane ? L"sp" : L"split-pane"; @@ -862,7 +862,7 @@ namespace TerminalAppLocalTests TEST_METHOD_PROPERTY(L"Data:useShortForm", L"{false, true}") END_TEST_METHOD_PROPERTIES() - INIT_TEST_PROPERTY(bool, useShortForm, L"TODO"); + INIT_TEST_PROPERTY(bool, useShortForm, L"If true, use `ft` instead of `focus-tab`"); const wchar_t* subcommand = useShortForm ? L"ft" : L"focus-tab"; { From 6f748f75f25add212c923e8f162341699281b71f Mon Sep 17 00:00:00 2001 From: Mike Griese Date: Fri, 19 Jun 2020 10:21:59 -0500 Subject: [PATCH 4/9] Add support for move-focus, and add tests --- .../CommandlineTest.cpp | 136 ++++++++++++++++++ .../TerminalApp/AppCommandlineArgs.cpp | 54 +++++++ src/cascadia/TerminalApp/AppCommandlineArgs.h | 4 + src/cascadia/TerminalApp/Pane.cpp | 13 ++ .../Resources/en-US/Resources.resw | 10 ++ 5 files changed, 217 insertions(+) diff --git a/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp b/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp index e9191a4f2f5..bd6851004f5 100644 --- a/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp +++ b/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp @@ -44,6 +44,7 @@ namespace TerminalAppLocalTests TEST_METHOD(ParseSplitPaneIntoArgs); TEST_METHOD(ParseComboCommandlineIntoArgs); TEST_METHOD(ParseFocusTabArgs); + TEST_METHOD(ParseMoveFocusArgs); TEST_METHOD(ParseArgumentsWithParsingTerminators); TEST_METHOD(ParseNoCommandIsNewTab); @@ -67,6 +68,23 @@ namespace TerminalAppLocalTests appArgs.ValidateStartupCommands(); } + void _buildCommandlinesExpectFailureHelper(AppCommandlineArgs& appArgs, + const size_t expectedSubcommands, + std::vector& rawCommands) + { + auto commandlines = AppCommandlineArgs::BuildCommands(rawCommands); + VERIFY_ARE_EQUAL(expectedSubcommands, commandlines.size()); + for (auto& cmdBlob : commandlines) + { + const auto result = appArgs.ParseCommand(cmdBlob); + VERIFY_ARE_NOT_EQUAL(0, result); + VERIFY_ARE_NOT_EQUAL("", appArgs._exitMessage); + Log::Comment(NoThrowString().Format( + L"Exit Message:\n%hs", + appArgs._exitMessage.c_str())); + } + } + void _logCommandline(std::vector& rawCommands) { std::wstring buffer; @@ -944,6 +962,124 @@ namespace TerminalAppLocalTests } } + void CommandlineTest::ParseMoveFocusArgs() + { + BEGIN_TEST_METHOD_PROPERTIES() + TEST_METHOD_PROPERTY(L"Data:useShortForm", L"{false, true}") + END_TEST_METHOD_PROPERTIES() + + INIT_TEST_PROPERTY(bool, useShortForm, L"If true, use `mf` instead of `move-focus`"); + const wchar_t* subcommand = useShortForm ? L"mf" : L"move-focus"; + + { + AppCommandlineArgs appArgs{}; + std::vector rawCommands{ L"wt.exe", subcommand }; + Log::Comment(NoThrowString().Format( + L"Just the subcommand, without a direction, should fail.")); + + _buildCommandlinesExpectFailureHelper(appArgs, 1u, rawCommands); + } + { + AppCommandlineArgs appArgs{}; + std::vector rawCommands{ L"wt.exe", subcommand, L"left" }; + _buildCommandlinesHelper(appArgs, 1u, rawCommands); + + VERIFY_ARE_EQUAL(2u, appArgs._startupActions.size()); + + // The first action is going to always be a new-tab action + VERIFY_ARE_EQUAL(ShortcutAction::NewTab, appArgs._startupActions.at(0).Action()); + + auto actionAndArgs = appArgs._startupActions.at(1); + VERIFY_ARE_EQUAL(ShortcutAction::MoveFocus, actionAndArgs.Action()); + VERIFY_IS_NOT_NULL(actionAndArgs.Args()); + auto myArgs = actionAndArgs.Args().try_as(); + VERIFY_IS_NOT_NULL(myArgs); + VERIFY_ARE_EQUAL(winrt::TerminalApp::Direction::Left, myArgs.Direction()); + } + { + AppCommandlineArgs appArgs{}; + std::vector rawCommands{ L"wt.exe", subcommand, L"right" }; + _buildCommandlinesHelper(appArgs, 1u, rawCommands); + + VERIFY_ARE_EQUAL(2u, appArgs._startupActions.size()); + + // The first action is going to always be a new-tab action + VERIFY_ARE_EQUAL(ShortcutAction::NewTab, appArgs._startupActions.at(0).Action()); + + auto actionAndArgs = appArgs._startupActions.at(1); + VERIFY_ARE_EQUAL(ShortcutAction::MoveFocus, actionAndArgs.Action()); + VERIFY_IS_NOT_NULL(actionAndArgs.Args()); + auto myArgs = actionAndArgs.Args().try_as(); + VERIFY_IS_NOT_NULL(myArgs); + VERIFY_ARE_EQUAL(winrt::TerminalApp::Direction::Right, myArgs.Direction()); + } + { + AppCommandlineArgs appArgs{}; + std::vector rawCommands{ L"wt.exe", subcommand, L"up" }; + _buildCommandlinesHelper(appArgs, 1u, rawCommands); + + VERIFY_ARE_EQUAL(2u, appArgs._startupActions.size()); + + // The first action is going to always be a new-tab action + VERIFY_ARE_EQUAL(ShortcutAction::NewTab, appArgs._startupActions.at(0).Action()); + + auto actionAndArgs = appArgs._startupActions.at(1); + VERIFY_ARE_EQUAL(ShortcutAction::MoveFocus, actionAndArgs.Action()); + VERIFY_IS_NOT_NULL(actionAndArgs.Args()); + auto myArgs = actionAndArgs.Args().try_as(); + VERIFY_IS_NOT_NULL(myArgs); + VERIFY_ARE_EQUAL(winrt::TerminalApp::Direction::Up, myArgs.Direction()); + } + { + AppCommandlineArgs appArgs{}; + std::vector rawCommands{ L"wt.exe", subcommand, L"down" }; + _buildCommandlinesHelper(appArgs, 1u, rawCommands); + + VERIFY_ARE_EQUAL(2u, appArgs._startupActions.size()); + + // The first action is going to always be a new-tab action + VERIFY_ARE_EQUAL(ShortcutAction::NewTab, appArgs._startupActions.at(0).Action()); + + auto actionAndArgs = appArgs._startupActions.at(1); + VERIFY_ARE_EQUAL(ShortcutAction::MoveFocus, actionAndArgs.Action()); + VERIFY_IS_NOT_NULL(actionAndArgs.Args()); + auto myArgs = actionAndArgs.Args().try_as(); + VERIFY_IS_NOT_NULL(myArgs); + VERIFY_ARE_EQUAL(winrt::TerminalApp::Direction::Down, myArgs.Direction()); + } + { + AppCommandlineArgs appArgs{}; + std::vector rawCommands{ L"wt.exe", subcommand, L"thisIsNotADirection" }; + Log::Comment(NoThrowString().Format( + L"move-focus with an invalid direction should fail.")); + _buildCommandlinesExpectFailureHelper(appArgs, 1u, rawCommands); + } + { + AppCommandlineArgs appArgs{}; + std::vector rawCommands{ L"wt.exe", subcommand, L"left", L";", subcommand, L"right" }; + _buildCommandlinesHelper(appArgs, 2u, rawCommands); + + VERIFY_ARE_EQUAL(3u, appArgs._startupActions.size()); + + // The first action is going to always be a new-tab action + VERIFY_ARE_EQUAL(ShortcutAction::NewTab, appArgs._startupActions.at(0).Action()); + + auto actionAndArgs = appArgs._startupActions.at(1); + VERIFY_ARE_EQUAL(ShortcutAction::MoveFocus, actionAndArgs.Action()); + VERIFY_IS_NOT_NULL(actionAndArgs.Args()); + auto myArgs = actionAndArgs.Args().try_as(); + VERIFY_IS_NOT_NULL(myArgs); + VERIFY_ARE_EQUAL(winrt::TerminalApp::Direction::Left, myArgs.Direction()); + + actionAndArgs = appArgs._startupActions.at(2); + VERIFY_ARE_EQUAL(ShortcutAction::MoveFocus, actionAndArgs.Action()); + VERIFY_IS_NOT_NULL(actionAndArgs.Args()); + myArgs = actionAndArgs.Args().try_as(); + VERIFY_IS_NOT_NULL(myArgs); + VERIFY_ARE_EQUAL(winrt::TerminalApp::Direction::Right, myArgs.Direction()); + } + } + void CommandlineTest::ValidateFirstCommandIsNewTab() { AppCommandlineArgs appArgs{}; diff --git a/src/cascadia/TerminalApp/AppCommandlineArgs.cpp b/src/cascadia/TerminalApp/AppCommandlineArgs.cpp index 753afb2fe6e..81ceb3fe41c 100644 --- a/src/cascadia/TerminalApp/AppCommandlineArgs.cpp +++ b/src/cascadia/TerminalApp/AppCommandlineArgs.cpp @@ -191,6 +191,7 @@ void AppCommandlineArgs::_buildParser() _buildNewTabParser(); _buildSplitPaneParser(); _buildFocusTabParser(); + _buildMoveFocusParser(); } // Method Description: @@ -341,6 +342,54 @@ void AppCommandlineArgs::_buildFocusTabParser() setupSubcommand(_focusTabShort); } +// Method Description: +// - Adds the `focus-tab` subcommand and related options to the commandline parser. +// - Additionally adds the `ft` subcommand, which is just a shortened version of `focus-tab` +// Arguments: +// - +// Return Value: +// - +void AppCommandlineArgs::_buildMoveFocusParser() +{ + _moveFocusCommand = _app.add_subcommand("move-focus", RS_A(L"CmdMoveFocusDesc")); + _moveFocusShort = _app.add_subcommand("mf", RS_A(L"CmdMFDesc")); + + auto setupSubcommand = [this](auto* subcommand) { + std::map map = { + { "left", winrt::TerminalApp::Direction::Left }, + { "right", winrt::TerminalApp::Direction::Right }, + { "up", winrt::TerminalApp::Direction::Up }, + { "down", winrt::TerminalApp::Direction::Down } + }; + + auto* directionOpt = subcommand->add_option("direction", + _moveFocusDirection, + RS_A(L"CmdMoveFocusDirectionArgDesc")); + + directionOpt->transform(CLI::CheckedTransformer(map, CLI::ignore_case)); + directionOpt->required(); + // When ParseCommand is called, if this subcommand was provided, this + // callback function will be triggered on the same thread. We can be sure + // that `this` will still be safe - this function just lets us know this + // command was parsed. + subcommand->callback([&, this]() { + if (_moveFocusDirection != winrt::TerminalApp::Direction::None) + { + auto moveFocusAction = winrt::make_self(); + + moveFocusAction->Action(ShortcutAction::MoveFocus); + auto args = winrt::make_self(); + args->Direction(_moveFocusDirection); + moveFocusAction->Args(*args); + _startupActions.push_back(*moveFocusAction); + } + }); + }; + + setupSubcommand(_moveFocusCommand); + setupSubcommand(_moveFocusShort); +} + // Method Description: // - Add the `NewTerminalArgs` parameters to the given subcommand. This enables // that subcommand to support all the properties in a NewTerminalArgs. @@ -438,6 +487,8 @@ bool AppCommandlineArgs::_noCommandsProvided() *_newTabShort.subcommand || *_focusTabCommand || *_focusTabShort || + *_moveFocusCommand || + *_moveFocusShort || *_newPaneShort.subcommand || *_newPaneCommand.subcommand); } @@ -464,6 +515,9 @@ void AppCommandlineArgs::_resetStateToDefault() _focusNextTab = false; _focusPrevTab = false; + _focusPrevTab = false; + + _moveFocusDirection = winrt::TerminalApp::Direction::None; // DON'T clear _launchMode here! This will get called once for every // subcommand, so we don't want `wt -F new-tab ; split-pane` clearing out // the "global" fullscreen flag (-F). diff --git a/src/cascadia/TerminalApp/AppCommandlineArgs.h b/src/cascadia/TerminalApp/AppCommandlineArgs.h index 00c7f3cd904..95106f900b2 100644 --- a/src/cascadia/TerminalApp/AppCommandlineArgs.h +++ b/src/cascadia/TerminalApp/AppCommandlineArgs.h @@ -69,11 +69,14 @@ class TerminalApp::AppCommandlineArgs final NewPaneSubcommand _newPaneShort; CLI::App* _focusTabCommand; CLI::App* _focusTabShort; + CLI::App* _moveFocusCommand; + CLI::App* _moveFocusShort; // Are you adding a new sub-command? Make sure to update _noCommandsProvided! std::string _profileName; std::string _startingDirectory; std::string _startingTitle; + winrt::TerminalApp::Direction _moveFocusDirection{ winrt::TerminalApp::Direction::None }; // _commandline will contain the command line with which we'll be spawning a new terminal std::vector _commandline; @@ -100,6 +103,7 @@ class TerminalApp::AppCommandlineArgs final void _buildNewTabParser(); void _buildSplitPaneParser(); void _buildFocusTabParser(); + void _buildMoveFocusParser(); bool _noCommandsProvided(); void _resetStateToDefault(); int _handleExit(const CLI::App& command, const CLI::Error& e); diff --git a/src/cascadia/TerminalApp/Pane.cpp b/src/cascadia/TerminalApp/Pane.cpp index b931755c1e3..d76abb027c8 100644 --- a/src/cascadia/TerminalApp/Pane.cpp +++ b/src/cascadia/TerminalApp/Pane.cpp @@ -535,6 +535,19 @@ void Pane::_FocusFirstChild() { if (_IsLeaf()) { + if (_root.ActualWidth() == 0 && _root.ActualHeight() == 0) + { + // When these sizes are 0, then the pane might sitll be in startup, + // and doesn't yet have a real size. In that case, the control.Focus + // event won't be handled until _after_ the startup events are all + // processed. THis will lead to the Tab not being notified that the + // focus moved to a different Pane. + // + // In that scenario, trigger the event manually here, to correctly + // inform the Tab that we're now focused. + _GotFocusHandlers(shared_from_this()); + } + _control.Focus(FocusState::Programmatic); } else diff --git a/src/cascadia/TerminalApp/Resources/en-US/Resources.resw b/src/cascadia/TerminalApp/Resources/en-US/Resources.resw index 49ff79d180e..166171e58d0 100644 --- a/src/cascadia/TerminalApp/Resources/en-US/Resources.resw +++ b/src/cascadia/TerminalApp/Resources/en-US/Resources.resw @@ -281,6 +281,16 @@ Launch the window in fullscreen mode + + Move focus to the adjacent pane in the specified direction + + + An alias for the "move-focus" subcommand. + {Locked="\"move-focus\""} + + + The direction to move focus in + Press the button to open a new terminal tab with your default profile. Open the flyout to select which profile you want to open. From 5de201644b2f6f83fe77b8e1b6f0ba59ead1a381 Mon Sep 17 00:00:00 2001 From: Mike Griese Date: Fri, 11 Dec 2020 11:32:05 -0600 Subject: [PATCH 5/9] You know, it might be helpful to actually commit changes and push them _before_ opening the PR --- src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp | 2 +- src/cascadia/TerminalApp/Pane.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp b/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp index c0c087933a4..710f95d2a1e 100644 --- a/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp +++ b/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp @@ -1100,7 +1100,7 @@ namespace TerminalAppLocalTests } { AppCommandlineArgs appArgs{}; - std::vector rawCommands{ L"wt.exe", subcommand, L"thisIsNotADirection" }; + std::vector rawCommands{ L"wt.exe", subcommand, L"badDirection" }; Log::Comment(NoThrowString().Format( L"move-focus with an invalid direction should fail.")); _buildCommandlinesExpectFailureHelper(appArgs, 1u, rawCommands); diff --git a/src/cascadia/TerminalApp/Pane.cpp b/src/cascadia/TerminalApp/Pane.cpp index 9aada6aa7ef..137b8578ebc 100644 --- a/src/cascadia/TerminalApp/Pane.cpp +++ b/src/cascadia/TerminalApp/Pane.cpp @@ -586,7 +586,7 @@ void Pane::_FocusFirstChild() { if (_root.ActualWidth() == 0 && _root.ActualHeight() == 0) { - // When these sizes are 0, then the pane might sitll be in startup, + // When these sizes are 0, then the pane might still be in startup, // and doesn't yet have a real size. In that case, the control.Focus // event won't be handled until _after_ the startup events are all // processed. THis will lead to the Tab not being notified that the From 3fbf984eb6dbb9bc5344a0c68dcaaa23ba830845 Mon Sep 17 00:00:00 2001 From: Mike Griese Date: Wed, 16 Dec 2020 07:13:36 -0600 Subject: [PATCH 6/9] cleanup merge shrapnel --- src/cascadia/TerminalApp/AppCommandlineArgs.cpp | 7 ------- src/cascadia/TerminalApp/Pane.cpp | 2 +- 2 files changed, 1 insertion(+), 8 deletions(-) diff --git a/src/cascadia/TerminalApp/AppCommandlineArgs.cpp b/src/cascadia/TerminalApp/AppCommandlineArgs.cpp index f08c9be129c..9c626db2bd5 100644 --- a/src/cascadia/TerminalApp/AppCommandlineArgs.cpp +++ b/src/cascadia/TerminalApp/AppCommandlineArgs.cpp @@ -371,19 +371,12 @@ void AppCommandlineArgs::_buildMoveFocusParser() subcommand->callback([&, this]() { if (_moveFocusDirection != Direction::None) { - // auto moveFocusAction = winrt::make_self(); - - // moveFocusAction->Action(ShortcutAction::MoveFocus); - // auto args = winrt::make_self(); MoveFocusArgs args{ _moveFocusDirection }; - // ActionAndArgs actionAndArgs {args}; ActionAndArgs actionAndArgs{}; actionAndArgs.Action(ShortcutAction::MoveFocus); actionAndArgs.Args(args); - // args->Direction(_moveFocusDirection); - // moveFocusAction->Args(*args); _startupActions.push_back(std::move(actionAndArgs)); } }); diff --git a/src/cascadia/TerminalApp/Pane.cpp b/src/cascadia/TerminalApp/Pane.cpp index 9686d0454b0..5c2f99721da 100644 --- a/src/cascadia/TerminalApp/Pane.cpp +++ b/src/cascadia/TerminalApp/Pane.cpp @@ -589,7 +589,7 @@ void Pane::_FocusFirstChild() // When these sizes are 0, then the pane might still be in startup, // and doesn't yet have a real size. In that case, the control.Focus // event won't be handled until _after_ the startup events are all - // processed. THis will lead to the Tab not being notified that the + // processed. This will lead to the Tab not being notified that the // focus moved to a different Pane. // // In that scenario, trigger the event manually here, to correctly From 9a9d74b8b5ebdacd0f2cdd75d71ff3a0cdbd33d1 Mon Sep 17 00:00:00 2001 From: Mike Griese Date: Thu, 17 Dec 2020 06:51:02 -0600 Subject: [PATCH 7/9] fix a merge with main --- src/cascadia/TerminalApp/AppCommandlineArgs.cpp | 14 +++++++------- src/cascadia/TerminalApp/AppCommandlineArgs.h | 2 +- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/src/cascadia/TerminalApp/AppCommandlineArgs.cpp b/src/cascadia/TerminalApp/AppCommandlineArgs.cpp index 55efa9c894c..01c2b5eeb28 100644 --- a/src/cascadia/TerminalApp/AppCommandlineArgs.cpp +++ b/src/cascadia/TerminalApp/AppCommandlineArgs.cpp @@ -351,11 +351,11 @@ void AppCommandlineArgs::_buildMoveFocusParser() _moveFocusShort = _app.add_subcommand("mf", RS_A(L"CmdMFDesc")); auto setupSubcommand = [this](auto* subcommand) { - std::map map = { - { "left", Direction::Left }, - { "right", Direction::Right }, - { "up", Direction::Up }, - { "down", Direction::Down } + std::map map = { + { "left", FocusDirection::Left }, + { "right", FocusDirection::Right }, + { "up", FocusDirection::Up }, + { "down", FocusDirection::Down } }; auto* directionOpt = subcommand->add_option("direction", @@ -369,7 +369,7 @@ void AppCommandlineArgs::_buildMoveFocusParser() // that `this` will still be safe - this function just lets us know this // command was parsed. subcommand->callback([&, this]() { - if (_moveFocusDirection != Direction::None) + if (_moveFocusDirection != FocusDirection::None) { MoveFocusArgs args{ _moveFocusDirection }; @@ -522,7 +522,7 @@ void AppCommandlineArgs::_resetStateToDefault() _focusNextTab = false; _focusPrevTab = false; - _moveFocusDirection = Direction::None; + _moveFocusDirection = FocusDirection::None; // DON'T clear _launchMode here! This will get called once for every // subcommand, so we don't want `wt -F new-tab ; split-pane` clearing out // the "global" fullscreen flag (-F). diff --git a/src/cascadia/TerminalApp/AppCommandlineArgs.h b/src/cascadia/TerminalApp/AppCommandlineArgs.h index c30fe0c8e0e..b33b058850f 100644 --- a/src/cascadia/TerminalApp/AppCommandlineArgs.h +++ b/src/cascadia/TerminalApp/AppCommandlineArgs.h @@ -84,7 +84,7 @@ class TerminalApp::AppCommandlineArgs final std::string _startingTitle; std::string _startingTabColor; - winrt::Microsoft::Terminal::Settings::Model::Direction _moveFocusDirection{ winrt::Microsoft::Terminal::Settings::Model::Direction::None }; + winrt::Microsoft::Terminal::Settings::Model::FocusDirection _moveFocusDirection{ winrt::Microsoft::Terminal::Settings::Model::FocusDirection::None }; // _commandline will contain the command line with which we'll be spawning a new terminal std::vector _commandline; From 96151a121ec38d558c35c25ffc8a9bed114162cf Mon Sep 17 00:00:00 2001 From: Mike Griese Date: Fri, 8 Jan 2021 07:05:09 -0600 Subject: [PATCH 8/9] Fix build break --- .../LocalTests_TerminalApp/CommandlineTest.cpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp b/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp index 710f95d2a1e..10a06284536 100644 --- a/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp +++ b/src/cascadia/LocalTests_TerminalApp/CommandlineTest.cpp @@ -1045,7 +1045,7 @@ namespace TerminalAppLocalTests VERIFY_IS_NOT_NULL(actionAndArgs.Args()); auto myArgs = actionAndArgs.Args().try_as(); VERIFY_IS_NOT_NULL(myArgs); - VERIFY_ARE_EQUAL(winrt::TerminalApp::Direction::Left, myArgs.Direction()); + VERIFY_ARE_EQUAL(FocusDirection::Left, myArgs.FocusDirection()); } { AppCommandlineArgs appArgs{}; @@ -1062,7 +1062,7 @@ namespace TerminalAppLocalTests VERIFY_IS_NOT_NULL(actionAndArgs.Args()); auto myArgs = actionAndArgs.Args().try_as(); VERIFY_IS_NOT_NULL(myArgs); - VERIFY_ARE_EQUAL(winrt::TerminalApp::Direction::Right, myArgs.Direction()); + VERIFY_ARE_EQUAL(FocusDirection::Right, myArgs.FocusDirection()); } { AppCommandlineArgs appArgs{}; @@ -1079,7 +1079,7 @@ namespace TerminalAppLocalTests VERIFY_IS_NOT_NULL(actionAndArgs.Args()); auto myArgs = actionAndArgs.Args().try_as(); VERIFY_IS_NOT_NULL(myArgs); - VERIFY_ARE_EQUAL(winrt::TerminalApp::Direction::Up, myArgs.Direction()); + VERIFY_ARE_EQUAL(FocusDirection::Up, myArgs.FocusDirection()); } { AppCommandlineArgs appArgs{}; @@ -1096,7 +1096,7 @@ namespace TerminalAppLocalTests VERIFY_IS_NOT_NULL(actionAndArgs.Args()); auto myArgs = actionAndArgs.Args().try_as(); VERIFY_IS_NOT_NULL(myArgs); - VERIFY_ARE_EQUAL(winrt::TerminalApp::Direction::Down, myArgs.Direction()); + VERIFY_ARE_EQUAL(FocusDirection::Down, myArgs.FocusDirection()); } { AppCommandlineArgs appArgs{}; @@ -1120,14 +1120,14 @@ namespace TerminalAppLocalTests VERIFY_IS_NOT_NULL(actionAndArgs.Args()); auto myArgs = actionAndArgs.Args().try_as(); VERIFY_IS_NOT_NULL(myArgs); - VERIFY_ARE_EQUAL(winrt::TerminalApp::Direction::Left, myArgs.Direction()); + VERIFY_ARE_EQUAL(FocusDirection::Left, myArgs.FocusDirection()); actionAndArgs = appArgs._startupActions.at(2); VERIFY_ARE_EQUAL(ShortcutAction::MoveFocus, actionAndArgs.Action()); VERIFY_IS_NOT_NULL(actionAndArgs.Args()); myArgs = actionAndArgs.Args().try_as(); VERIFY_IS_NOT_NULL(myArgs); - VERIFY_ARE_EQUAL(winrt::TerminalApp::Direction::Right, myArgs.Direction()); + VERIFY_ARE_EQUAL(FocusDirection::Right, myArgs.FocusDirection()); } } From 67166fa0283005f5468defbad67b84e62b9eefd2 Mon Sep 17 00:00:00 2001 From: Mike Griese Date: Mon, 11 Jan 2021 12:17:39 -0600 Subject: [PATCH 9/9] Apply suggestions from code review Co-authored-by: Carlos Zamora --- src/cascadia/TerminalApp/AppCommandlineArgs.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/cascadia/TerminalApp/AppCommandlineArgs.cpp b/src/cascadia/TerminalApp/AppCommandlineArgs.cpp index af624841eb1..1aaa0af1bc4 100644 --- a/src/cascadia/TerminalApp/AppCommandlineArgs.cpp +++ b/src/cascadia/TerminalApp/AppCommandlineArgs.cpp @@ -343,8 +343,8 @@ void AppCommandlineArgs::_buildFocusTabParser() } // Method Description: -// - Adds the `focus-tab` subcommand and related options to the commandline parser. -// - Additionally adds the `ft` subcommand, which is just a shortened version of `focus-tab` +// - Adds the `move-focus` subcommand and related options to the commandline parser. +// - Additionally adds the `mf` subcommand, which is just a shortened version of `move-focus` // Arguments: // - // Return Value: