Skip to content

Commit 0f23bc1

Browse files
committed
WIP: Add support for resetting colors
Refs #18695 Closes #3719
1 parent 6eb6512 commit 0f23bc1

File tree

9 files changed

+90
-6
lines changed

9 files changed

+90
-6
lines changed

src/renderer/base/RenderSettings.cpp

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -112,6 +112,13 @@ COLORREF RenderSettings::GetColorTableEntry(const size_t tableIndex) const
112112
return _colorTable.at(tableIndex);
113113
}
114114

115+
// Routine Description:
116+
// - Returns one color table entry to the value saved in SaveDefaultSettings.
117+
void RenderSettings::RestoreDefaultColorTableEntry(const size_t tableIndex)
118+
{
119+
_colorTable.at(tableIndex) = _defaultColorTable.at(tableIndex);
120+
}
121+
115122
// Routine Description:
116123
// - Sets the position in the color table for the given color alias and updates the color.
117124
// Arguments:

src/renderer/inc/RenderSettings.hpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@ namespace Microsoft::Console::Render
3737
void ResetColorTable() noexcept;
3838
void SetColorTableEntry(const size_t tableIndex, const COLORREF color);
3939
COLORREF GetColorTableEntry(const size_t tableIndex) const;
40+
void RestoreDefaultColorTableEntry(const size_t tableIndex);
4041
void SetColorAlias(const ColorAlias alias, const size_t tableIndex, const COLORREF color);
4142
COLORREF GetColorAlias(const ColorAlias alias) const;
4243
void SetColorAliasIndex(const ColorAlias alias, const size_t tableIndex) noexcept;

src/terminal/adapter/ITermDispatch.hpp

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -78,8 +78,9 @@ class Microsoft::Console::VirtualTerminal::ITermDispatch
7878
virtual void TabSet(const VTParameter setType) = 0; // DECST8C
7979
virtual void SetColorTableEntry(const size_t tableIndex, const DWORD color) = 0; // OSCSetColorTable
8080
virtual void RequestColorTableEntry(const size_t tableIndex) = 0; // OSCGetColorTable
81-
virtual void SetXtermColorResource(const size_t resource, const DWORD color) = 0; // OSCSetDefaultForeground, OSCSetDefaultBackground, OSCSetCursorColor, OSCResetCursorColor
81+
virtual void SetXtermColorResource(const size_t resource, const DWORD color) = 0; // OSCSetDefaultForeground, OSCSetDefaultBackground, OSCSetCursorColor
8282
virtual void RequestXtermColorResource(const size_t resource) = 0; // OSCGetDefaultForeground, OSCGetDefaultBackground, OSCGetCursorColor
83+
virtual void ResetXtermColorResource(const size_t resource) = 0; // OSCResetForegroundColor, OSCResetBackgroundColor, OSCResetCursorColor, OSCResetHighlightColor
8384
virtual void AssignColor(const DispatchTypes::ColorItem item, const VTInt fgIndex, const VTInt bgIndex) = 0; // DECAC
8485

8586
virtual void EraseInDisplay(const DispatchTypes::EraseType eraseType) = 0; // ED

src/terminal/adapter/adaptDispatch.cpp

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3292,6 +3292,29 @@ void AdaptDispatch::RequestColorTableEntry(const size_t tableIndex)
32923292
}
32933293
}
32943294

3295+
// Method Description:
3296+
// - Restores a single color table entry to its default user-specified value
3297+
// Arguments:
3298+
// - tableIndex: The VT color table index
3299+
void AdaptDispatch::ResetColorTableEntry(const size_t tableIndex)
3300+
{
3301+
_renderSettings.RestoreDefaultColorTableEntry(tableIndex);
3302+
3303+
if (_renderer)
3304+
{
3305+
// If we're updating the background color, we need to let the renderer
3306+
// know, since it may want to repaint the window background to match.
3307+
const auto backgroundIndex = _renderSettings.GetColorAliasIndex(ColorAlias::DefaultBackground);
3308+
const auto backgroundChanged = (tableIndex == backgroundIndex);
3309+
3310+
// Similarly for the frame color, the tab may need to be repainted.
3311+
const auto frameIndex = _renderSettings.GetColorAliasIndex(ColorAlias::FrameBackground);
3312+
const auto frameChanged = (tableIndex == frameIndex);
3313+
3314+
_renderer->TriggerRedrawAll(backgroundChanged, frameChanged);
3315+
}
3316+
}
3317+
32953318
// Method Description:
32963319
// - Sets one Xterm Color Resource such as Default Foreground, Background, Cursor
32973320
void AdaptDispatch::SetXtermColorResource(const size_t resource, const DWORD color)
@@ -3338,6 +3361,25 @@ void AdaptDispatch::RequestXtermColorResource(const size_t resource)
33383361
}
33393362
}
33403363

3364+
// Method Description:
3365+
// - Restores to the original user-provided value one Xterm Color Resource such as Default Foreground, Background, Cursor
3366+
void AdaptDispatch::ResetXtermColorResource(const size_t resource)
3367+
{
3368+
assert(resource >= 10);
3369+
const auto mappingIndex = resource - 10;
3370+
const auto& oscMapping = XtermResourceColorTableMappings.at(mappingIndex);
3371+
if (oscMapping.ColorTableIndex > 0)
3372+
{
3373+
if (oscMapping.AliasIndex >= 0) [[unlikely]]
3374+
{
3375+
// If this color reset applies to an aliased color, point the alias back at the original color
3376+
_renderSettings.SetColorAliasIndex(static_cast<ColorAlias>(oscMapping.AliasIndex), oscMapping.ColorTableIndex);
3377+
}
3378+
3379+
ResetColorTableEntry(oscMapping.ColorTableIndex);
3380+
}
3381+
}
3382+
33413383
// Method Description:
33423384
// DECAC - Assigns the foreground and background color indexes that should be
33433385
// used for a given aspect of the user interface.

src/terminal/adapter/adaptDispatch.hpp

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -133,8 +133,10 @@ namespace Microsoft::Console::VirtualTerminal
133133
void SetColorTableEntry(const size_t tableIndex,
134134
const DWORD color) override; // OSCSetColorTable
135135
void RequestColorTableEntry(const size_t tableIndex) override; // OSCGetColorTable
136-
void SetXtermColorResource(const size_t resource, const DWORD color) override; // OSCSetDefaultForeground, OSCSetDefaultBackground, OSCSetCursorColor, OSCResetCursorColor
136+
void ResetColorTableEntry(const size_t tableIndex) /*override*/; // OSCResetColorTable
137+
void SetXtermColorResource(const size_t resource, const DWORD color) override; // OSCSetDefaultForeground, OSCSetDefaultBackground, OSCSetCursorColor
137138
void RequestXtermColorResource(const size_t resource) override; // OSCGetDefaultForeground, OSCGetDefaultBackground, OSCGetCursorColor
139+
void ResetXtermColorResource(const size_t resource) override; // OSCResetForegroundColor, OSCResetBackgroundColor, OSCResetCursorColor, OSCResetHighlightColor
138140
void AssignColor(const DispatchTypes::ColorItem item, const VTInt fgIndex, const VTInt bgIndex) override; // DECAC
139141

140142
void WindowManipulation(const DispatchTypes::WindowManipulationType function,

src/terminal/adapter/termDispatch.hpp

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,8 +71,9 @@ class Microsoft::Console::VirtualTerminal::TermDispatch : public Microsoft::Cons
7171
void TabSet(const VTParameter /*setType*/) override {} // DECST8C
7272
void SetColorTableEntry(const size_t /*tableIndex*/, const DWORD /*color*/) override {} // OSCSetColorTable
7373
void RequestColorTableEntry(const size_t /*tableIndex*/) override {} // OSCGetColorTable
74-
void SetXtermColorResource(const size_t /*resource*/, const DWORD /*color*/) override {} // OSCSetDefaultForeground, OSCSetDefaultBackground, OSCSetCursorColor, OSCResetCursorColor
74+
void SetXtermColorResource(const size_t /*resource*/, const DWORD /*color*/) override {} // OSCSetDefaultForeground, OSCSetDefaultBackground, OSCSetCursorColor
7575
void RequestXtermColorResource(const size_t /*resource*/) override {} // OSCGetDefaultForeground, OSCGetDefaultBackground, OSCGetCursorColor
76+
void ResetXtermColorResource(const size_t /*resource*/) override {}; // OSCResetForegroundColor, OSCResetBackgroundColor, OSCResetCursorColor, OSCResetHighlightColor
7677
void AssignColor(const DispatchTypes::ColorItem /*item*/, const VTInt /*fgIndex*/, const VTInt /*bgIndex*/) override {} // DECAC
7778

7879
void EraseInDisplay(const DispatchTypes::EraseType /* eraseType*/) override {} // ED

src/terminal/parser/OutputStateMachineEngine.cpp

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -810,10 +810,18 @@ bool OutputStateMachineEngine::ActionOscDispatch(const size_t parameter, const s
810810
}
811811
break;
812812
}
813+
case OscActionCodes::ResetForegroundColor:
814+
case OscActionCodes::ResetBackgroundColor:
813815
case OscActionCodes::ResetCursorColor:
816+
case OscActionCodes::ResetHighlightColor:
817+
// **CANNOT BE CHAINED** in xterm; ignored if chained (!)
818+
// xterm allows chaining 104 (reset color index); if chained, only reset the colors within
819+
// if not chained, reset all colors
820+
// gets weird in conhost - we use aliases to set the dfault bg/fg in default config
821+
// so overwriting the aliases makes the background **white** instead
814822
{
815823
// The reset codes for xterm dynamic resources are the set codes + 100
816-
_dispatch->SetXtermColorResource(parameter - 100u, INVALID_COLOR);
824+
_dispatch->ResetXtermColorResource(parameter - 100u);
817825
break;
818826
}
819827
case OscActionCodes::Hyperlink:

src/terminal/parser/OutputStateMachineEngine.hpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -214,9 +214,10 @@ namespace Microsoft::Console::VirtualTerminal
214214
SetHighlightColor = 17,
215215
DECSWT_SetWindowTitle = 21,
216216
SetClipboard = 52,
217-
ResetForegroundColor = 110, // Not implemented
218-
ResetBackgroundColor = 111, // Not implemented
217+
ResetForegroundColor = 110,
218+
ResetBackgroundColor = 111,
219219
ResetCursorColor = 112,
220+
ResetHighlightColor = 117,
220221
FinalTermAction = 133,
221222
VsCodeAction = 633,
222223
ITerm2Action = 1337,

src/terminal/parser/ut_parser/OutputEngineTest.cpp

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1401,6 +1401,11 @@ class StatefulDispatch final : public TermDispatch
14011401
_xtermResourcesRequested.push_back(resource);
14021402
}
14031403

1404+
void ResetXtermColorResource(const size_t resource) override
1405+
{
1406+
_xtermResourcesReset.push_back(resource);
1407+
}
1408+
14041409
void SetClipboard(wil::zwstring_view content) noexcept override
14051410
{
14061411
_copyContent = content;
@@ -1476,6 +1481,7 @@ class StatefulDispatch final : public TermDispatch
14761481
std::vector<size_t> _xtermResourcesChanged;
14771482
std::vector<DWORD> _xtermResourceValues;
14781483
std::vector<size_t> _xtermResourcesRequested;
1484+
std::vector<size_t> _xtermResourcesReset;
14791485
bool _setColorTableEntry;
14801486
std::vector<size_t> _colorTableEntriesRequested;
14811487
bool _hyperlinkMode;
@@ -3221,6 +3227,21 @@ class StateMachineExternalTest final
32213227
pDispatch->ClearState();
32223228
}
32233229

3230+
TEST_METHOD(TestOscXtermResourceReset)
3231+
{
3232+
auto dispatch = std::make_unique<StatefulDispatch>();
3233+
auto pDispatch = dispatch.get();
3234+
auto engine = std::make_unique<OutputStateMachineEngine>(std::move(dispatch));
3235+
StateMachine mach(std::move(engine));
3236+
3237+
mach.ProcessString(L"\033]110\033\\");
3238+
VERIFY_ARE_EQUAL(0u, pDispatch->_xtermResourcesChanged.size());
3239+
VERIFY_ARE_EQUAL(0u, pDispatch->_xtermResourcesRequested.size());
3240+
VERIFY_ARE_EQUAL(0u, pDispatch->_xtermResourcesReset.size());
3241+
VERIFY_ARE_EQUAL(10u, pDispatch->_xtermResourcesReset[0]);
3242+
pDispatch->ClearState();
3243+
}
3244+
32243245
TEST_METHOD(TestOscSetWindowTitle)
32253246
{
32263247
BEGIN_TEST_METHOD_PROPERTIES()

0 commit comments

Comments
 (0)