-
Notifications
You must be signed in to change notification settings - Fork 721
Fixes #4229 Support transparent foreground/background in v2 #4234
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
base: v2_develop
Are you sure you want to change the base?
Conversation
thank you for this fix, it looks like a creative patch when set the background color to explicit black (default console color)! |
BTW, this makes me uncomfortably happy. |
We could also just say if the background color has Alpha of 0 we do this. And add a color member for Transparent if we dont already have one. That might be more elegant as it would let you still use black as normal and not have surprises e.g. if users terminal default color is white for bg |
I guess we should instead be using the |
- Add StandardColor.Trnsparent StandardColor is enum so limited to int which cannot model A 0xFF000000 is too many bytes for int32. So instead we use 0xF000000 and 'special case' it in Color constructor.
…dColor uint so it can have FF for alpha on all values
Ok StandardColor being vanilla enum means you can't have alpha modelled. So all current values are just actually RGB. And in fact when passed to Color struct, results in an A of 0! I've changes it to uint enum and added 0xFF000000 to all values except Transparent. This should mean we get correct A values when mapping this enum to Color. And hence we can correctly distinguish 0xFF000000 (black) from 0x00000000 (Transparent). Probably will blow up a lot of unit tests though 😓 |
So this test fails when setting background color to Transparent. Its confusing because test seems only to be checking the Foreground but I'm changing the background - so can't understand why it would fail. [Fact]
public void View_Resolves_Attributes_From_Scheme ()
{
View view = new Label { SchemeName = "Base" };
foreach (VisualRole role in Enum.GetValues<VisualRole> ())
{
Attribute attr = view.GetAttributeForRole (role);
Assert.NotEqual (default, attr.Foreground); // Defensive: avoid all-defaults
}
view.Dispose ();
} Specifically: Scheme CreateBase ()
{
return new ()
{
- Normal = new (StandardColor.LightBlue, StandardColor.RaisinBlack)
+ Normal = new (StandardColor.LightBlue, StandardColor.Transparent)
};
} |
Ah I see the issue, // Derivation algorithm as documented
Attribute result = role switch
{
VisualRole.Focus =>
GetAttributeForRoleCore (VisualRole.Normal, stack) with
{
Foreground = GetAttributeForRoleCore (VisualRole.Normal, stack).Background,
Background = GetAttributeForRoleCore (VisualRole.Normal, stack).Foreground
}, |
…was Transparent then instead use Black
As simplest solution and probably most sensible I've just set this explicitly as a rule Transparent now means 'clear color' - that means that for background your likely to get either black (default terminal color) or black + semi transparent (user has configured % transparency). But transparent foreground is also 'clear color' but likely to be... well the inverse of the background anyway (i.e. white terminal with black text or black terminal with white text). |
{ new Color(118, 118, 118), ColorName16.DarkGray }, | ||
{ new Color(169, 169, 169), ColorName16.DarkGray }, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That correspond adding 20% of the opacity (118+255*0.20=118+51=169), which may be the opacity percentage used by the StandardColor
? It's possible to comprove with a unit test the opacity percentage (20%) for all StandardColor
?
@@ -306,7 +306,7 @@ private Attribute GetAttributeForRoleCore (VisualRole role, HashSet<VisualRole> | |||
VisualRole.Focus => | |||
GetAttributeForRoleCore (VisualRole.Normal, stack) with | |||
{ | |||
Foreground = GetAttributeForRoleCore (VisualRole.Normal, stack).Background, | |||
Foreground = SwapTransparentForBlack(GetAttributeForRoleCore (VisualRole.Normal, stack).Background), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Otherwise a text in a transparent foreground with a opaque background is unreadable, correct?
/// <param name="redrawTextStyle">Style</param> | ||
protected virtual void AppendOrWriteAttribute (StringBuilder output, Attribute attr, TextStyle redrawTextStyle) | ||
{ | ||
if (attr.Foreground == Color.Transparent) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please, don' forget to consider the Force16Colors
in v2net:
if (Application.Force16Colors)
{
output.Append (EscSeqUtils.CSI_SetForegroundColor (attr.Foreground.GetAnsiColorCode ()));
output.Append (EscSeqUtils.CSI_SetBackgroundColor (attr.Background.GetAnsiColorCode ()));
}
else
{
...
}
Fixes #4229 - Transparent foreground/background
This is the simplest way to get transparent background. It uses console native background on
Color.Transparent
(0,0,0,0).Applies to both net and win
When the background color is Transparent we use
CSI 49m
instead of explicitly mark it 0,0,0,0 color. Similarly for foreground color.Proposed Changes/Todos
Pull Request checklist:
CTRL-K-D
to automatically reformat your files before committing.dotnet test
before commit///
style comments)