WPF着色器效果-抗锯齿未显示

3

我遇到了一个问题,我有一个WPF着色器效果(从Rene Schulte修改而来),用于模拟点阵显示屏(DMD)。一切都很好,但所有的点都是锯齿状的。

请参见附图。 enter image description here

我尝试了WPF中的许多功能,以实现抗锯齿,但没有任何作用。

在构造函数中(将图像放入文本框);

RenderOptions.SetBitmapScalingMode(MarqueeTB, BitmapScalingMode.HighQuality);
RenderOptions.SetEdgeMode(MarqueeTB, EdgeMode.Unspecified);
RenderOptions.SetClearTypeHint(MarqueeTB, ClearTypeHint.Enabled);

我认为问题不在于我的显卡或Windows配置。我在两台电脑上进行了测试,结果相同;分别是Windows 8.1和Windows 7。

我不知道该怎么继续下去。如果有任何帮助或建议,都将不胜感激。

提前致谢,问候, 着色器代码:

//   Project:           Shaders
//
//   Description:       Mosaic Shader for Coding4Fun.
//
//   Changed by:        $Author$
//   Changed on:        $Date$
//   Changed in:        $Revision$
//   Project:           $URL$
//   Id:                $Id$
//
//
//   Copyright (c) 2010 Rene Schulte
//

/// <description>Mosaic Shader for Coding4Fun.</description>

/// <summary>The number pixel blocks.</summary>
/// <type>Single</type>
/// <minValue>2</minValue>
/// <maxValue>500</maxValue>
/// <defaultValue>50</defaultValue>
float BlockCount : register(C0);

/// <summary>The rounding of a pixel block.</summary>
/// <type>Single</type>
/// <minValue>0</minValue>
/// <maxValue>1</maxValue>
/// <defaultValue>0.45</defaultValue>
float Max : register(C2);

/// <summary>The aspect ratio of the image.</summary>
/// <type>Single</type>
/// <minValue>0</minValue>
/// <maxValue>10</maxValue>
/// <defaultValue>1</defaultValue>
float AspectRatio : register(C3);

// Sampler
sampler2D input : register(S0);

// Static computed vars for optimization
static float2 BlockCount2 = float2(BlockCount, BlockCount  / AspectRatio);
static float2 BlockSize2 = 1.0f / BlockCount2; 

// Shader
float4 main(float2 uv : TEXCOORD) : COLOR
{
     // Calculate block center
     float2 blockPos = floor(uv * BlockCount2);
     float2 blockCenter = blockPos * BlockSize2 + BlockSize2 * 0.5;

     // Scale coordinates back to original ratio for rounding
     float2 uvScaled = float2(uv.x * AspectRatio, uv.y);
     float2 blockCenterScaled = float2(blockCenter.x * AspectRatio, blockCenter.y);

     // Round the block by testing the distance of the pixel coordinate to the center
     float dist = length(uvScaled - blockCenterScaled) * BlockCount2;
     if(dist < 0 || dist > Max)
     {
         return 1;
     }

     // Sample color at the calculated coordinate
     return tex2D(input, blockCenter);
}

我猜你需要将颜色值乘以 alpha,但已经有一段时间了。 - Joey
好的,我已经解决了。我不确定这是否是“正确”的方法,但它起作用了。以下是对我有用的解决方案:http://gamedev.stackexchange.com/questions/34582/how-do-i-use-screen-space-derivatives-to-antialias-a-parametric-shape-in-a-pixel - Jean Yves Cadieux
抗锯齿只适用于 WPF 中的矢量图形,如文本和形状。如果您想要抗锯齿,我建议在您的点纹理中预先计算它。(不是很有趣的)事实:直接在形状上设置着色器效果会导致抗锯齿无法应用。为了解决这个问题,您需要将着色器效果应用于包围 WPF 元素(如空白边框)-这就是我来到这里的原因。 - JVal90
2个回答

1

我不确定这是否是最好的解决方案,但它有效。请参见this答案中的antialiasedCircle部分。

//  Project:           Dot Matrix Display (DMD) Shader
//  Inspired from From Mosaic shader Copyright (c) 2010 Rene Schulte


/// <summary>The number pixel blocks.</summary>
/// <type>Single</type>
/// <minValue>2</minValue>
/// <maxValue>500</maxValue>
/// <defaultValue>34</defaultValue>


float BlockCount : register(C0);

/// <summary>The rounding of a pixel block.</summary>
/// <type>Single</type>
/// <minValue>0</minValue>
/// <maxValue>1</maxValue>
/// <defaultValue>0.45</defaultValue>
float Max : register(C2);

/// <summary>The aspect ratio of the image.</summary>
/// <type>Single</type>
/// <minValue>0</minValue>
/// <maxValue>10</maxValue>
/// <defaultValue>1.55</defaultValue>
float AspectRatio : register(C3);

/// <summary>The monochrome color used to tint the input.</summary>
/// <defaultValue>Yellow</defaultValue>
float4 FilterColor : register(C1);

/// <summary>monochrome.</summary>
/// <defaultValue>1</defaultValue>
float IsMonochrome : register(C4);

// Sampler
sampler2D input : register(S0);

// Static computed vars for optimization
static float2 BlockCount2 = float2(BlockCount, BlockCount  / AspectRatio);
static float2 BlockSize2 = 1.0f / BlockCount2; 

float4 setMonochrome(float4 color) : COLOR
{
   float4 monochrome= color;
   if(((int)IsMonochrome) == 1)
   {
      float3 rgb = color.rgb;
      float3 luminance = dot(rgb, float3(0.30, 0.59, 0.11));
     monochrome= float4(luminance * FilterColor.rgb, color.a);
   }
    return monochrome;
}

float4 SetDMD(float2 uv : TEXCOORD, sampler2D samp) : COLOR
{
     // Calculate block center
     float2 blockPos = floor(uv * BlockCount2);
     float2 blockCenter = blockPos * BlockSize2 + BlockSize2 * 0.5;
     
     // Scale coordinates back to original ratio for rounding
     float2 uvScaled = float2(uv.x * AspectRatio, uv.y);
     float2 blockCenterScaled = float2(blockCenter.x * AspectRatio, blockCenter.y);
         
     // Round the block by testing the distance of the pixel coordinate to the center
     float dist = length(uvScaled - blockCenterScaled) * BlockCount2;
     
      float4 insideColor= tex2D(samp, blockCenter);
       
     float4 outsideColor = insideColor; 
         outsideColor.r = 0; 
         outsideColor.g = 0; 
         outsideColor.b = 0; 
         outsideColor.a = 1; 
         
      float distFromEdge = Max - dist;  // positive when inside the circle
     float thresholdWidth = .22;  // a constant you'd tune to get the right level of softness
     float antialiasedCircle = saturate((distFromEdge / thresholdWidth) + 0.5);
     
     return lerp(outsideColor, insideColor, antialiasedCircle);
}

// Shader
float4 main(float2 uv : TEXCOORD) : COLOR
{
     float4 DMD= SetDMD(uv, input);
     DMD = setMonochrome(DMD);
       
     return DMD;
}

这是一个成功解决方案的图片:enter image description here

0

是布局舍入吗?尝试 MarqueeTB.UseLayoutRounding = false;


“MarqueeTB.UseLayoutRounding = false”尝试后并没有带来帮助。但还是谢谢。另一方面,我在画布上绘制了一个简单的形状(圆)。这个圆在应用着色器效果之前具有抗锯齿功能。 - Jean Yves Cadieux

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接