Blurry text in WPF with ClearTypeHinting enabled?

I have a grid with this template and styles in WPF / XAML:

<Setter Property="TextOptions.TextFormattingMode" Value="Display" /> <Setter Property="RenderOptions.ClearTypeHint" Value="Enabled" /> <Setter Property="Template"> <Setter.Value> <ControlTemplate TargetType="{x:Type DataGridCell}"> <Border Padding="{TemplateBinding Padding}" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Background="{TemplateBinding Background}" SnapsToDevicePixels="True"> <ContentPresenter x:Name="CellContent" SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" RenderOptions.ClearTypeHint="Enabled" /> </Border> <ControlTemplate.Triggers> <Trigger Property="IsSelected" Value="True"> <Setter TargetName="CellContent" Property="TextOptions.TextFormattingMode" Value="Display" /> <Setter TargetName="CellContent" Property="RenderOptions.ClearTypeHint" Value="Enabled" /> <Setter TargetName="CellContent" Property="Effect"> <Setter.Value> <DropShadowEffect ShadowDepth="2" BlurRadius="2" Color="Black" RenderingBias="Quality" /> </Setter.Value> </Setter> </Trigger> </ControlTemplate.Triggers> </ControlTemplate> </Setter.Value> </Setter> 

DropShadowEffect I have, when you select a grid line, it seems that the blur of the text is blurry (gray smoothing):

enter image description here

When I remove the shadow effect, it looks clear, because now it uses ClearType, not gray sub-pixel anti-aliasing:

enter image description here

I tried applying RenderOptions.ClearTypeHint="Enabled" to ContentPresenter as shown above, but this does not help.

How to get WPF to display text that displays with shadow effect to keep Cleartype antialiasing instead of this ugly blurry gray subpixel anti-aliasing?

Some people think that this is blurry due to the shadow - it is not. It is blurred only because ClearType is not used. This is how it looks in Firefox when shadow AND ClearType:

enter image description here

Text with ClearType enabled is bright - but this blurry text is missing because it does not use ClearType - it uses anti-aliasing anti-subpixels and ClearType does not work: http://en.wikipedia.org/wiki/ClearType

Question: how to enable ClearType for this text?

+6
source share
6 answers

DropShadowEffect cannot work with ClearType. This is indicated on the MSDN page. How to create text with shadow :

These shadow effects do not pass through the presentation of the Windows Text Preparation Pipeline (WPF). As a result, ClearType is disabled when using these effects.

After all, DropShadowEffect is a bitmap effect, not a text effect.

+4
source

How to set TextOptions.TextFormattingMode to Display , as well as from RenderOptions.BitmapScalingMode to NearestNeighbor ? The latter is new in WPF 3.5 SP1, and I usually use it to remove blur. :)

  <TextBlock Text="Hello world" TextOptions.TextFormattingMode="Display" RenderOptions.BitmapScalingMode="NearestNeighbor" HorizontalAlignment="Center" TextWrapping="Wrap" VerticalAlignment="Center" Foreground="White" FontFamily="Microsoft Sans Serif"> <TextBlock.Effect> <DropShadowEffect ShadowDepth="2" BlurRadius="2" Color="Black" RenderingBias="Quality"/> </TextBlock.Effect> </TextBlock> 

The following shows how it looks.

enter image description here

And this is how it looks in FireFox.

enter image description here

+12
source

To achieve a similar result without using an effect, you can visualize the text twice, slightly offset from another:

 <Grid> <TextBlock Text="Here is some sample text" Foreground="Black" Margin="1,1,0,0"/> <TextBlock Text="Here is some sample text" Foreground="White"/> </Grid> 

This gives the desired result:

enter image description here

enter image description here

You can also encapsulate this in a control (called ShadowTextBlock , perhaps) so that you don't have to repeat yourself everywhere.

+3
source

How about combining two ideas. Draw the text with DropShadowEffect and overlay it on the same text without effect, as shown on the third line:

text

Still not perfect, and I find him a little bold. But perhaps you could live with something. XAML:

 <StackPanel Background="LightSteelBlue" RenderOptions.ClearTypeHint="Enabled" SnapsToDevicePixels="True" > <Grid Margin="5"> <TextBlock Foreground="Black" Text="Here is some sample text" Margin="1"/> <TextBlock Foreground="White" Text="Here is some sample text"/> </Grid> <TextBlock Margin="5" Foreground="White" Text="Here is some sample text"> <TextBlock.Effect> <DropShadowEffect ShadowDepth="2" BlurRadius="2" Color="Black" RenderingBias="Quality"/> </TextBlock.Effect> </TextBlock> <Grid Margin="5"> <TextBlock Foreground="White" Text="Here is some sample text"> <TextBlock.Effect> <DropShadowEffect ShadowDepth="2" BlurRadius="2" Color="Black" RenderingBias="Quality"/> </TextBlock.Effect> </TextBlock> <TextBlock Foreground="White" Text="Here is some sample text"/> </Grid> </StackPanel> 
+3
source

The reason this does not work, and the reason you cannot get it working, is related to the sensitivity of ClearType to what it does on top. In order for ClearType to look correct, it essentially has to do alpha blending in each component. That is, a separate alpha value for red, green and blue (usually alpha refers to all 3). This means that ClearType absolutely needs to be displayed in a bitmap that is already opaque (all alpha values ​​are 255) (you will notice that the header headers still have ClearType, but some top-secret tricks are used for this).

The next step to understanding this is that WPF acts on the first render to an off-screen bitmap and then combines with what is lower (in this case, solid white or possibly blue if selected).

So, the text is first displayed in a transparent, transparent bitmap. Since he has no idea what will ultimately be lower, it should be displayed using grayscale instead of ClearType. The effect is then applied to this bitmap. Then the bitmap is drawn at the place where you expect it to be on the screen, and there is no way to get ClearType, even if it is on top of a solid color without transparency.

As a possible workaround, try using 2 copies of the text. First, apply the effect to the "lower" version of the text ("below", I mean that it should have a lower Z-index value, and this is so if it is "first" in XAML). Then draw plain text on top of it (which will get ClearType). I think this will work, but I have not tried it, and you will probably have to experiment until you get the desired visual result.

+2
source

I know this post is old, but if someone has problems with blurry text, the shadow of the border may be the culprit. I have custom panels with a shadow, and only when they were next to each other, the text was blurry. I found the answer from this. Why is everything in WPF blurry? message. The solution for me was the ereif answer, not the accepted answer. Add this to your control

  UseLayoutRounding="True" RenderOptions.BitmapScalingMode="NearestNeighbor" SnapsToDevicePixels="True RenderOptions.ClearTypeHint="Enabled" 
0
source

Source: https://habr.com/ru/post/913233/


All Articles