Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add the ability to show the tab bar in fullscreen #18171

Open
wants to merge 10 commits into
base: main
Choose a base branch
from
5 changes: 5 additions & 0 deletions doc/cascadia/profiles.schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -2526,6 +2526,11 @@
"description": "When set to true, the Terminal's tab row will display a shield icon when the Terminal is running with administrator privileges",
"type": "boolean"
},
"showTabsFullscreen": {
"default": false,
"description": "When set to true, tabs remain visible in fullscreen mode. When set to false, tabs will be hidden when entering fullscreen mode.",
"type": "boolean"
},
"useAcrylicInTabRow": {
"default": false,
"description": "When set to true, the tab row will have an acrylic material background with 50% opacity.",
Expand Down
10 changes: 6 additions & 4 deletions src/cascadia/TerminalApp/TabManagement.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -243,10 +243,12 @@ namespace winrt::TerminalApp::implementation
// - Handle changes in tab layout.
void TerminalPage::_UpdateTabView()
{
// Never show the tab row when we're fullscreen. Otherwise:
// Show tabs when there's more than 1, or the user has chosen to always
// show the tab bar.
const auto isVisible = (!_isFullscreen && !_isInFocusMode) &&
// The tab row should only be visible if:
// - we're not in focus mode
// - we're not in full screen, or the user has enabled fullscreen tabs
// - there is more than one tab, or the user has chosen to always show tabs
const auto isVisible = !_isInFocusMode &&
(!_isFullscreen || _showTabsFullscreen) &&
(_settings.GlobalSettings().ShowTabsInTitlebar() ||
(_tabs.Size() > 1) ||
_settings.GlobalSettings().AlwaysShowTabs());
Expand Down
34 changes: 34 additions & 0 deletions src/cascadia/TerminalApp/TerminalPage.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -270,6 +270,7 @@ namespace winrt::TerminalApp::implementation
_layoutUpdatedRevoker = _tabContent.LayoutUpdated(winrt::auto_revoke, { this, &TerminalPage::_OnFirstLayout });

_isAlwaysOnTop = _settings.GlobalSettings().AlwaysOnTop();
_showTabsFullscreen = _settings.GlobalSettings().ShowTabsFullscreen();

// DON'T set up Toasts/TeachingTips here. They should be loaded and
// initialized the first time they're opened, in whatever method opens
Expand Down Expand Up @@ -3605,6 +3606,8 @@ namespace winrt::TerminalApp::implementation
_isAlwaysOnTop = _settings.GlobalSettings().AlwaysOnTop();
AlwaysOnTopChanged.raise(*this, nullptr);

_showTabsFullscreen = _settings.GlobalSettings().ShowTabsFullscreen();

// Settings AllowDependentAnimations will affect whether animations are
// enabled application-wide, so we don't need to check it each time we
// want to create an animation.
Expand Down Expand Up @@ -4029,6 +4032,37 @@ namespace winrt::TerminalApp::implementation
return _isAlwaysOnTop;
}

// Method Description:
// - Returns true if the tab row should be visible when we're in full screen
// state.
// Arguments:
// - <none>
// Return Value:
// - true if the tab row should be visible in full screen state
bool TerminalPage::ShowTabsFullscreen() const
{
return _showTabsFullscreen;
}

// Method Description:
// - Updates the visibility of the tab row when in fullscreen state.
void TerminalPage::SetShowTabsFullscreen(bool newShowTabsFullscreen)
{
if (_showTabsFullscreen == newShowTabsFullscreen)
{
return;
}

_showTabsFullscreen = newShowTabsFullscreen;

// if we're currently in fullscreen, update tab view to make
// sure tabs are given the correct visibility
if (_isFullscreen)
{
_UpdateTabView();
}
}

void TerminalPage::SetFullscreen(bool newFullscreen)
{
if (_isFullscreen == newFullscreen)
Expand Down
3 changes: 3 additions & 0 deletions src/cascadia/TerminalApp/TerminalPage.h
Original file line number Diff line number Diff line change
Expand Up @@ -135,6 +135,8 @@ namespace winrt::TerminalApp::implementation
bool FocusMode() const;
bool Fullscreen() const;
bool AlwaysOnTop() const;
bool ShowTabsFullscreen() const;
void SetShowTabsFullscreen(bool newShowTabsFullscreen);
void SetFullscreen(bool);
void SetFocusMode(const bool inFocusMode);
void Maximized(bool newMaximized);
Expand Down Expand Up @@ -244,6 +246,7 @@ namespace winrt::TerminalApp::implementation
bool _isFullscreen{ false };
bool _isMaximized{ false };
bool _isAlwaysOnTop{ false };
bool _showTabsFullscreen{ false };

std::optional<uint32_t> _loadFromPersistedLayoutIdx{};

Expand Down
10 changes: 10 additions & 0 deletions src/cascadia/TerminalApp/TerminalWindow.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -288,6 +288,11 @@ namespace winrt::TerminalApp::implementation
return _settings.GlobalSettings().AlwaysOnTop();
}

bool TerminalWindow::GetInitialShowTabsFullscreen()
{
return _settings.GlobalSettings().ShowTabsFullscreen();
}

bool TerminalWindow::GetMinimizeToNotificationArea()
{
return _settings.GlobalSettings().MinimizeToNotificationArea();
Expand Down Expand Up @@ -1009,6 +1014,11 @@ namespace winrt::TerminalApp::implementation
return _root ? _root->AlwaysOnTop() : false;
}

bool TerminalWindow::ShowTabsFullscreen() const
{
return _root ? _root->ShowTabsFullscreen() : false;
}

void TerminalWindow::SetSettingsStartupArgs(const std::vector<ActionAndArgs>& actions)
{
for (const auto& action : actions)
Expand Down
2 changes: 2 additions & 0 deletions src/cascadia/TerminalApp/TerminalWindow.h
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,7 @@ namespace winrt::TerminalApp::implementation
bool Fullscreen() const;
void Maximized(bool newMaximized);
bool AlwaysOnTop() const;
bool ShowTabsFullscreen() const;
bool AutoHideWindow();

void IdentifyWindow();
Expand All @@ -112,6 +113,7 @@ namespace winrt::TerminalApp::implementation
Microsoft::Terminal::Settings::Model::LaunchMode GetLaunchMode();
bool GetShowTabsInTitlebar();
bool GetInitialAlwaysOnTop();
bool GetInitialShowTabsFullscreen();
float CalcSnappedDimension(const bool widthOrHeight, const float dimension) const;

Windows::UI::Xaml::UIElement GetRoot() noexcept;
Expand Down
2 changes: 2 additions & 0 deletions src/cascadia/TerminalApp/TerminalWindow.idl
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ namespace TerminalApp
void Maximized(Boolean newMaximized);
Boolean AlwaysOnTop { get; };
Boolean AutoHideWindow { get; };
Boolean ShowTabsFullscreen { get; };

void IdentifyWindow();
void SetPersistedLayoutIdx(UInt32 idx);
Expand All @@ -86,6 +87,7 @@ namespace TerminalApp
Microsoft.Terminal.Settings.Model.LaunchMode GetLaunchMode();
Boolean GetShowTabsInTitlebar();
Boolean GetInitialAlwaysOnTop();
Boolean GetInitialShowTabsFullscreen();
Single CalcSnappedDimension(Boolean widthOrHeight, Single dimension);
void TitlebarClicked();
void CloseWindow();
Expand Down
7 changes: 7 additions & 0 deletions src/cascadia/TerminalApp/TitlebarControl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@

#include "TitlebarControl.g.cpp"

using namespace winrt::Windows::UI::Xaml;

namespace winrt::TerminalApp::implementation
{
TitlebarControl::TitlebarControl(uint64_t handle) :
Expand Down Expand Up @@ -77,6 +79,11 @@ namespace winrt::TerminalApp::implementation
}
}

void TitlebarControl::FullscreenChanged(const bool fullscreen)
{
MinMaxCloseControl().Visibility(fullscreen ? Visibility::Collapsed : Visibility::Visible);
}

void TitlebarControl::_OnMaximizeOrRestore(byte flag)
{
POINT point1 = {};
Expand Down
1 change: 1 addition & 0 deletions src/cascadia/TerminalApp/TitlebarControl.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ namespace winrt::TerminalApp::implementation

void SetWindowVisualState(WindowVisualState visualState);
void Root_SizeChanged(const IInspectable& sender, const Windows::UI::Xaml::SizeChangedEventArgs& e);
void FullscreenChanged(const bool fullscreen);

void Minimize_Click(const winrt::Windows::Foundation::IInspectable& sender, const winrt::Windows::UI::Xaml::RoutedEventArgs& e);
void Maximize_Click(const winrt::Windows::Foundation::IInspectable& sender, const winrt::Windows::UI::Xaml::RoutedEventArgs& e);
Expand Down
1 change: 1 addition & 0 deletions src/cascadia/TerminalApp/TitlebarControl.idl
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ namespace TerminalApp
{
TitlebarControl(UInt64 parentWindowHandle);
void SetWindowVisualState(WindowVisualState visualState);
void FullscreenChanged(Boolean fullscreen);

void HoverButton(CaptionButton button);
void PressButton(CaptionButton button);
Expand Down
6 changes: 6 additions & 0 deletions src/cascadia/TerminalSettingsEditor/GlobalAppearance.xaml
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,12 @@
Style="{StaticResource ToggleSwitchInExpanderStyle}" />
</local:SettingContainer>

<!-- Show tabs in full screen -->
<local:SettingContainer x:Uid="Globals_ShowTabsFullscreen">
<ToggleSwitch IsOn="{x:Bind ViewModel.ShowTabsFullscreen, Mode=TwoWay}"
Style="{StaticResource ToggleSwitchInExpanderStyle}" />
</local:SettingContainer>

<!-- Show Acrylic in Tab Row -->
<local:SettingContainer x:Uid="Globals_AcrylicTabRow">
<ToggleSwitch IsOn="{x:Bind ViewModel.UseAcrylicInTabRow, Mode=TwoWay}"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ namespace winrt::Microsoft::Terminal::Settings::Editor::implementation
void ShowTitlebarToggled(const winrt::Windows::Foundation::IInspectable& sender, const winrt::Windows::UI::Xaml::RoutedEventArgs& args);

PERMANENT_OBSERVABLE_PROJECTED_SETTING(_GlobalSettings, AlwaysShowTabs);
PERMANENT_OBSERVABLE_PROJECTED_SETTING(_GlobalSettings, ShowTabsFullscreen);
PERMANENT_OBSERVABLE_PROJECTED_SETTING(_GlobalSettings, ShowTabsInTitlebar);
PERMANENT_OBSERVABLE_PROJECTED_SETTING(_GlobalSettings, UseAcrylicInTabRow);
PERMANENT_OBSERVABLE_PROJECTED_SETTING(_GlobalSettings, ShowTitleInTitlebar);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ namespace Microsoft.Terminal.Settings.Editor
void ShowTitlebarToggled(IInspectable sender, Windows.UI.Xaml.RoutedEventArgs args);

PERMANENT_OBSERVABLE_PROJECTED_SETTING(Boolean, AlwaysShowTabs);
PERMANENT_OBSERVABLE_PROJECTED_SETTING(Boolean, ShowTabsFullscreen);
PERMANENT_OBSERVABLE_PROJECTED_SETTING(Boolean, ShowTabsInTitlebar);
PERMANENT_OBSERVABLE_PROJECTED_SETTING(Boolean, UseAcrylicInTabRow);
PERMANENT_OBSERVABLE_PROJECTED_SETTING(Boolean, ShowTitleInTitlebar);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1961,6 +1961,14 @@
<value>Display a shield in the title bar when Windows Terminal is running as Administrator</value>
<comment>Header for a control to toggle displaying a shield in the title bar of the app. "Admin" refers to elevated sessions like "run as Admin"</comment>
</data>
<data name="Globals_ShowTabsFullscreen.Header" xml:space="preserve">
<value>Show tabs in full screen</value>
<comment>Header for a control to toggle if the app should show the tabs when in full screen state.</comment>
</data>
<data name="Globals_ShowTabsFullscreen.HelpText" xml:space="preserve">
<value>When enabled, the tab bar will be visible when the app is full screen</value>
<comment>A description for what the "show tabs in full screen" setting does.</comment>
</data>
<data name="Profile_PathTranslationStyle.[using:Windows.UI.Xaml.Automation]AutomationProperties.Name" xml:space="preserve">
<value>Path translation</value>
<comment>Name for a control to select how file and directory paths are translated.</comment>
Expand Down
1 change: 1 addition & 0 deletions src/cascadia/TerminalSettingsModel/GlobalAppSettings.idl
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ namespace Microsoft.Terminal.Settings.Model
INHERITABLE_SETTING(Int32, InitialRows);
INHERITABLE_SETTING(Int32, InitialCols);
INHERITABLE_SETTING(Boolean, AlwaysShowTabs);
INHERITABLE_SETTING(Boolean, ShowTabsFullscreen);
INHERITABLE_SETTING(NewTabPosition, NewTabPosition);
INHERITABLE_SETTING(Boolean, ShowTitleInTitlebar);
INHERITABLE_SETTING(Boolean, ConfirmCloseAllTabs);
Expand Down
3 changes: 2 additions & 1 deletion src/cascadia/TerminalSettingsModel/MTSMSettings.h
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,8 @@ Author(s):
X(winrt::Windows::Foundation::Collections::IVector<Model::NewTabMenuEntry>, NewTabMenu, "newTabMenu", winrt::single_threaded_vector<Model::NewTabMenuEntry>({ Model::RemainingProfilesEntry{} })) \
X(bool, AllowHeadless, "compatibility.allowHeadless", false) \
X(bool, IsolatedMode, "compatibility.isolatedMode", false) \
X(hstring, SearchWebDefaultQueryUrl, "searchWebDefaultQueryUrl", L"https://www.bing.com/search?q=%22%s%22")
X(hstring, SearchWebDefaultQueryUrl, "searchWebDefaultQueryUrl", L"https://www.bing.com/search?q=%22%s%22") \
X(bool, ShowTabsFullscreen, "showTabsFullscreen", false)

// Also add these settings to:
// * Profile.idl
Expand Down
2 changes: 2 additions & 0 deletions src/cascadia/WindowsTerminal/AppHost.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -300,6 +300,7 @@ void AppHost::Initialize()

_window->SetAlwaysOnTop(_windowLogic.GetInitialAlwaysOnTop());
_window->SetAutoHideWindow(_windowLogic.AutoHideWindow());
_window->SetShowTabsFullscreen(_windowLogic.GetInitialShowTabsFullscreen());

// MORE EVENT HANDLERS HERE!
// MAKE SURE THEY ARE ALL:
Expand Down Expand Up @@ -1212,6 +1213,7 @@ void AppHost::_HandleSettingsChanged(const winrt::Windows::Foundation::IInspecta

_window->SetMinimizeToNotificationAreaBehavior(_windowLogic.GetMinimizeToNotificationArea());
_window->SetAutoHideWindow(_windowLogic.AutoHideWindow());
_window->SetShowTabsFullscreen(_windowLogic.ShowTabsFullscreen());
_updateTheme();
}

Expand Down
5 changes: 5 additions & 0 deletions src/cascadia/WindowsTerminal/IslandWindow.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -992,6 +992,11 @@ void IslandWindow::ShowWindowChanged(const bool showOrHide)
}
}

void IslandWindow::SetShowTabsFullscreen(const bool newShowTabsFullscreen)
{
_showTabsFullscreen = newShowTabsFullscreen;
}

// Method Description
// - Flash the taskbar icon, indicating to the user that something needs their attention
void IslandWindow::FlashTaskbar()
Expand Down
3 changes: 3 additions & 0 deletions src/cascadia/WindowsTerminal/IslandWindow.h
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,7 @@ class IslandWindow :
void FullscreenChanged(const bool fullscreen);
void SetAlwaysOnTop(const bool alwaysOnTop);
void ShowWindowChanged(const bool showOrHide);
virtual void SetShowTabsFullscreen(const bool newShowTabsFullscreen);

void FlashTaskbar();
void SetTaskbarProgress(const size_t state, const size_t progress);
Expand Down Expand Up @@ -112,6 +113,7 @@ class IslandWindow :
bool _borderless{ false };
bool _alwaysOnTop{ false };
bool _fullscreen{ false };
bool _showTabsFullscreen{ false };
bool _fWasMaximizedBeforeFullscreen{ false };
RECT _rcWindowBeforeFullscreen{};
RECT _rcWorkBeforeFullscreen{};
Expand All @@ -123,6 +125,7 @@ class IslandWindow :

virtual void _SetIsBorderless(const bool borderlessEnabled);
virtual void _SetIsFullscreen(const bool fullscreenEnabled);

void _RestoreFullscreenPosition(const RECT& rcWork);
void _SetFullscreenPosition(const RECT& rcMonitor, const RECT& rcWork);

Expand Down
41 changes: 32 additions & 9 deletions src/cascadia/WindowsTerminal/NonClientIslandWindow.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1137,7 +1137,7 @@ void NonClientIslandWindow::_SetIsBorderless(const bool borderlessEnabled)

// Method Description:
// - Enable or disable fullscreen mode. When entering fullscreen mode, we'll
// need to manually hide the entire titlebar.
// need to check whether to hide the titlebar.
// - See also IslandWindow::_SetIsFullscreen, which does additional work.
// Arguments:
// - fullscreenEnabled: If true, we're entering fullscreen mode. If false, we're leaving.
Expand All @@ -1146,27 +1146,50 @@ void NonClientIslandWindow::_SetIsBorderless(const bool borderlessEnabled)
void NonClientIslandWindow::_SetIsFullscreen(const bool fullscreenEnabled)
{
IslandWindow::_SetIsFullscreen(fullscreenEnabled);
if (_titlebar)
{
_titlebar.Visibility(_IsTitlebarVisible() ? Visibility::Visible : Visibility::Collapsed);
}
_UpdateTitlebarVisibility();
// GH#4224 - When the auto-hide taskbar setting is enabled, then we don't
// always get another window message to trigger us to remove the drag bar.
// So, make sure to update the size of the drag region here, so that it
// _definitely_ goes away.
_ResizeDragBarWindow();
}

void NonClientIslandWindow::SetShowTabsFullscreen(const bool newShowTabsFullscreen)
{
IslandWindow::SetShowTabsFullscreen(newShowTabsFullscreen);

// don't waste time recalculating UI elements if we're not
// in fullscreen state - this setting doesn't affect other
// window states
if (_fullscreen)
{
_UpdateTitlebarVisibility();
}
}

void NonClientIslandWindow::_UpdateTitlebarVisibility()
{
if (!_titlebar)
{
return;
}

const auto showTitlebar = _IsTitlebarVisible();
_titlebar.Visibility(showTitlebar ? Visibility::Visible : Visibility::Collapsed);
_titlebar.FullscreenChanged(_fullscreen);
}

// Method Description:
// - Returns true if the titlebar is visible. For things like fullscreen mode,
// borderless mode (aka "focus mode"), this will return false.
// - Returns true if the titlebar is visible. For borderless mode (aka "focus mode"),
// this will return false. For fullscreen, this will return false unless the user
// has enabled fullscreen tabs.
// Arguments:
// - <none>
// Return Value:
// - true iff the titlebar is visible
// - true if the titlebar is visible
bool NonClientIslandWindow::_IsTitlebarVisible() const
{
return !(_fullscreen || _borderless);
return !_borderless && (!_fullscreen || _showTabsFullscreen);
}

void NonClientIslandWindow::SetTitlebarBackground(winrt::Windows::UI::Xaml::Media::Brush brush)
Expand Down
2 changes: 2 additions & 0 deletions src/cascadia/WindowsTerminal/NonClientIslandWindow.h
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,7 @@ class NonClientIslandWindow : public IslandWindow
void OnApplicationThemeChanged(const winrt::Windows::UI::Xaml::ElementTheme& requestedTheme) override;

void SetTitlebarBackground(winrt::Windows::UI::Xaml::Media::Brush brush);
void SetShowTabsFullscreen(const bool newShowTabsFullscreen) override;

virtual void UseMica(const bool newValue, const double titlebarOpacity) override;

Expand Down Expand Up @@ -97,6 +98,7 @@ class NonClientIslandWindow : public IslandWindow
void _UpdateFrameMargins() const noexcept;
void _UpdateMaximizedState();
void _UpdateIslandPosition(const UINT windowWidth, const UINT windowHeight);
void _UpdateTitlebarVisibility();

struct Revokers
{
Expand Down
Loading