This is how I wanted to solve the color scheme setting, previewing, but UpdateAppearance ends up getting called immediately after so it blows it away. Dustin had a crazy idea...

This commit is contained in:
Mike Griese 2021-10-21 15:35:27 -05:00
parent 888e1572d2
commit 17829f438b
10 changed files with 198 additions and 11 deletions

View file

@ -451,7 +451,31 @@ namespace winrt::TerminalApp::implementation
{
if (const auto scheme = _settings.GlobalSettings().ColorSchemes().TryLookup(realArgs.SchemeName()))
{
const auto res = _ApplyToActiveControls([&](auto& /*control*/) {
const auto res = _ApplyToActiveControls([&](auto& control) {
Core::Scheme coreScheme{};
coreScheme.Foreground = scheme.Foreground();
coreScheme.Background = scheme.Background();
coreScheme.CursorColor = scheme.CursorColor();
coreScheme.SelectionBackground = scheme.SelectionBackground();
coreScheme.Black = scheme.Table()[0];
coreScheme.Red = scheme.Table()[1];
coreScheme.Green = scheme.Table()[2];
coreScheme.Yellow = scheme.Table()[3];
coreScheme.Blue = scheme.Table()[4];
coreScheme.Purple = scheme.Table()[5];
coreScheme.Cyan = scheme.Table()[6];
coreScheme.White = scheme.Table()[7];
coreScheme.BrightBlack = scheme.Table()[8];
coreScheme.BrightRed = scheme.Table()[9];
coreScheme.BrightGreen = scheme.Table()[10];
coreScheme.BrightYellow = scheme.Table()[11];
coreScheme.BrightBlue = scheme.Table()[12];
coreScheme.BrightPurple = scheme.Table()[13];
coreScheme.BrightCyan = scheme.Table()[14];
coreScheme.BrightWhite = scheme.Table()[15];
control.ColorScheme(coreScheme);
//// Start by getting the current settings of the control
//auto controlSettings = control.Settings().as<TerminalSettings>();
//auto parentSettings = controlSettings;
@ -479,7 +503,7 @@ namespace winrt::TerminalApp::implementation
// We'll need a dedicated method for this. The Control's
// settings are hosted in the Core, which could be OOP.
// We'll need to manually tell the control to update its
// core's scheme.
// core's scheme.
});
args.Handled(res);
}

View file

@ -159,6 +159,7 @@ NewTerminalArgs Pane::GetTerminalArgsForPane() const
// TODO!: Will we be able to persist this? Or will runtime-changed settings
// always be lost? Think like, changing the font size with an action. That's
// lost.
// Come back to this after previewing. May end up with some data we can use there.
//
// if (controlSettings.AppliedColorScheme())
// {

View file

@ -1595,4 +1595,51 @@ namespace winrt::Microsoft::Terminal::Control::implementation
return VerifyVersionInfoW(&osver, VER_BUILDNUMBER, dwlConditionMask) != FALSE;
}
Core::Scheme ControlCore::ColorScheme() const noexcept
{
auto s = _terminal->GetColorScheme();
// This might be a tad bit of a hack. This only evet gets called by set
// color scheme / preview color scheme, and in that case, we know the
// control _is_ focused.
s.SelectionBackground = _settings->FocusedAppearance()->SelectionBackground();
return s;
}
void ControlCore::ColorScheme(Core::Scheme scheme) const noexcept
{
_terminal->ApplyScheme(scheme);
// _settings->FocusedAppearance()->DefaultForeground(colorScheme.Foreground);
// _settings->FocusedAppearance()->DefaultBackground(colorScheme.Background);
// _settings->FocusedAppearance()->CursorColor(colorScheme.CursorColor);
// _settings->FocusedAppearance()->SelectionBackground(colorScheme.SelectionBackground);
// // _defaultFg = colorScheme.Foreground;
// // // Set the default background as transparent to prevent the
// // // DX layer from overwriting the background image or acrylic effect
// // til::color newBackgroundColor{ colorScheme.Background };
// // _defaultBg = newBackgroundColor.with_alpha(0);
// _settings->FocusedAppearance()->Table()[0] = scheme.Black;
// _settings->FocusedAppearance()->Table()[1] = scheme.Red;
// _settings->FocusedAppearance()->Table()[2] = scheme.Green;
// _settings->FocusedAppearance()->Table()[3] = scheme.Yellow;
// _settings->FocusedAppearance()->Table()[4] = scheme.Blue;
// _settings->FocusedAppearance()->Table()[5] = scheme.Purple;
// _settings->FocusedAppearance()->Table()[6] = scheme.Cyan;
// _settings->FocusedAppearance()->Table()[7] = scheme.White;
// _settings->FocusedAppearance()->Table()[8] = scheme.BrightBlack;
// _settings->FocusedAppearance()->Table()[9] = scheme.BrightRed;
// _settings->FocusedAppearance()->Table()[10] = scheme.BrightGreen;
// _settings->FocusedAppearance()->Table()[11] = scheme.BrightYellow;
// _settings->FocusedAppearance()->Table()[12] = scheme.BrightBlue;
// _settings->FocusedAppearance()->Table()[13] = scheme.BrightPurple;
// _settings->FocusedAppearance()->Table()[14] = scheme.BrightCyan;
// _settings->FocusedAppearance()->Table()[15] = scheme.BrightWhite;
// _buffer->GetCursor().SetColor(til::color{ colorScheme.CursorColor });
_renderer->TriggerRedrawAll();
}
}

View file

@ -65,6 +65,8 @@ namespace winrt::Microsoft::Terminal::Control::implementation
};
Control::IControlAppearance FocusedAppearance() const { return *_settings->FocusedAppearance(); };
Control::IControlAppearance UnfocusedAppearance() const { return *_settings->UnfocusedAppearance(); };
winrt::Microsoft::Terminal::Core::Scheme ColorScheme() const noexcept;
void ColorScheme(winrt::Microsoft::Terminal::Core::Scheme scheme) const noexcept;
void SizeChanged(const double width, const double height);
void ScaleChanged(const double scale);

View file

@ -22,5 +22,7 @@ namespace Microsoft.Terminal.Control
Boolean BracketedPasteEnabled { get; };
Microsoft.Terminal.TerminalConnection.ConnectionState ConnectionState { get; };
Microsoft.Terminal.Core.Scheme ColorScheme { get; set; };
};
}

View file

@ -1501,13 +1501,13 @@ namespace winrt::Microsoft::Terminal::Control::implementation
_blinkTimer->Start();
}
// Only update the appearance here if an unfocused config exists -
// if an unfocused config does not exist then we never would have switched
// appearances anyway so there's no need to switch back upon gaining focus
if (_core.UnfocusedAppearance())
{
UpdateAppearance(_core.FocusedAppearance());
}
// // Only update the appearance here if an unfocused config exists -
// // if an unfocused config does not exist then we never would have switched
// // appearances anyway so there's no need to switch back upon gaining focus
// if (_core.UnfocusedAppearance())
// {
// UpdateAppearance(_core.FocusedAppearance());
// }
}
// Method Description:
@ -2594,4 +2594,14 @@ namespace winrt::Microsoft::Terminal::Control::implementation
{
return _core.ReadEntireBuffer();
}
Core::Scheme TermControl::ColorScheme() const noexcept
{
return _core.ColorScheme();
}
void TermControl::ColorScheme(Core::Scheme scheme) const noexcept
{
_core.ColorScheme(scheme);
}
}

View file

@ -112,6 +112,9 @@ namespace winrt::Microsoft::Terminal::Control::implementation
hstring ReadEntireBuffer() const;
winrt::Microsoft::Terminal::Core::Scheme ColorScheme() const noexcept;
void ColorScheme(winrt::Microsoft::Terminal::Core::Scheme scheme) const noexcept;
// -------------------------------- WinRT Events ---------------------------------
// clang-format off
WINRT_CALLBACK(FontSizeChanged, Control::FontSizeChangedEventArgs);

View file

@ -50,6 +50,37 @@ namespace Microsoft.Terminal.Core
UInt32 Value;
};
struct Scheme
{
Microsoft.Terminal.Core.Color Foreground;
Microsoft.Terminal.Core.Color Background;
Microsoft.Terminal.Core.Color SelectionBackground;
Microsoft.Terminal.Core.Color CursorColor;
// Table: A WinRT struct doesn't allow pointers (like an array) in
// structs, but we very much would like this object to be a struct. So
// we'll call out each color individually. There's only 16, it's not
// that bad.
Microsoft.Terminal.Core.Color Black;
Microsoft.Terminal.Core.Color Red;
Microsoft.Terminal.Core.Color Green;
Microsoft.Terminal.Core.Color Yellow;
Microsoft.Terminal.Core.Color Blue;
Microsoft.Terminal.Core.Color Purple;
Microsoft.Terminal.Core.Color Cyan;
Microsoft.Terminal.Core.Color White;
Microsoft.Terminal.Core.Color BrightBlack;
Microsoft.Terminal.Core.Color BrightRed;
Microsoft.Terminal.Core.Color BrightGreen;
Microsoft.Terminal.Core.Color BrightYellow;
Microsoft.Terminal.Core.Color BrightBlue;
Microsoft.Terminal.Core.Color BrightPurple;
Microsoft.Terminal.Core.Color BrightCyan;
Microsoft.Terminal.Core.Color BrightWhite;
};
declare
{
// Forward declare this parameterized specialization so that it lives

View file

@ -170,13 +170,14 @@ void Terminal::UpdateSettings(ICoreSettings settings)
// - appearance: an ICoreAppearance with new settings values for us to use.
void Terminal::UpdateAppearance(const ICoreAppearance& appearance)
{
_intenseIsBright = appearance.IntenseIsBright();
_adjustIndistinguishableColors = appearance.AdjustIndistinguishableColors();
// Set the default background as transparent to prevent the
// DX layer from overwriting the background image or acrylic effect
til::color newBackgroundColor{ appearance.DefaultBackground() };
_defaultBg = newBackgroundColor.with_alpha(0);
_defaultFg = appearance.DefaultForeground();
_intenseIsBright = appearance.IntenseIsBright();
_adjustIndistinguishableColors = appearance.AdjustIndistinguishableColors();
for (int i = 0; i < 16; i++)
{
@ -1292,3 +1293,65 @@ const size_t Microsoft::Terminal::Core::Terminal::GetTaskbarProgress() const noe
{
return _taskbarProgress;
}
Scheme Terminal::GetColorScheme() const noexcept
{
Scheme s;
s.Foreground = til::color{ _defaultFg };
s.Background = til::color{ _defaultBg };
// SelectionBackground is stored in the ControlAppearance
// s.SelectionBackground;
s.CursorColor = til::color{ _buffer->GetCursor().GetColor() };
s.Black = til::color{ _colorTable[0] };
s.Red = til::color{ _colorTable[1] };
s.Green = til::color{ _colorTable[2] };
s.Yellow = til::color{ _colorTable[3] };
s.Blue = til::color{ _colorTable[4] };
s.Purple = til::color{ _colorTable[5] };
s.Cyan = til::color{ _colorTable[6] };
s.White = til::color{ _colorTable[7] };
s.BrightBlack = til::color{ _colorTable[8] };
s.BrightRed = til::color{ _colorTable[9] };
s.BrightGreen = til::color{ _colorTable[10] };
s.BrightYellow = til::color{ _colorTable[11] };
s.BrightBlue = til::color{ _colorTable[12] };
s.BrightPurple = til::color{ _colorTable[13] };
s.BrightCyan = til::color{ _colorTable[14] };
s.BrightWhite = til::color{ _colorTable[15] };
return s;
}
void Terminal::ApplyScheme(Scheme colorScheme)
{
_defaultFg = colorScheme.Foreground;
// Set the default background as transparent to prevent the
// DX layer from overwriting the background image or acrylic effect
til::color newBackgroundColor{ colorScheme.Background };
_defaultBg = newBackgroundColor.with_alpha(0);
_colorTable[0] = til::color{ colorScheme.Black };
_colorTable[1] = til::color{ colorScheme.Red };
_colorTable[2] = til::color{ colorScheme.Green };
_colorTable[3] = til::color{ colorScheme.Yellow };
_colorTable[4] = til::color{ colorScheme.Blue };
_colorTable[5] = til::color{ colorScheme.Purple };
_colorTable[6] = til::color{ colorScheme.Cyan };
_colorTable[7] = til::color{ colorScheme.White };
_colorTable[8] = til::color{ colorScheme.BrightBlack };
_colorTable[9] = til::color{ colorScheme.BrightRed };
_colorTable[10] = til::color{ colorScheme.BrightGreen };
_colorTable[11] = til::color{ colorScheme.BrightYellow };
_colorTable[12] = til::color{ colorScheme.BrightBlue };
_colorTable[13] = til::color{ colorScheme.BrightPurple };
_colorTable[14] = til::color{ colorScheme.BrightCyan };
_colorTable[15] = til::color{ colorScheme.BrightWhite };
_buffer->GetCursor().SetColor(til::color{ colorScheme.CursorColor });
if (_adjustIndistinguishableColors)
{
_MakeAdjustedColorArray();
}
}

View file

@ -30,6 +30,7 @@ namespace winrt::Microsoft::Terminal::Core
{
struct ICoreSettings;
struct ICoreAppearance;
struct Scheme;
}
namespace Microsoft::Terminal::Core
@ -221,6 +222,9 @@ public:
const std::optional<til::color> GetTabColor() const noexcept;
til::color GetDefaultBackground() const noexcept;
winrt::Microsoft::Terminal::Core::Scheme GetColorScheme() const noexcept;
void ApplyScheme(winrt::Microsoft::Terminal::Core::Scheme scheme);
Microsoft::Console::Render::BlinkingState& GetBlinkingState() const noexcept;
const size_t GetTaskbarState() const noexcept;