Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/wpf/12.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如何在WPF中保存控件的非模糊图像?_C#_Wpf_Render_Blurry_Rendertargetbitmap - Fatal编程技术网

C# 如何在WPF中保存控件的非模糊图像?

C# 如何在WPF中保存控件的非模糊图像?,c#,wpf,render,blurry,rendertargetbitmap,C#,Wpf,Render,Blurry,Rendertargetbitmap,我正在使用DrawingContext来绘制图像。然后将结果渲染为RenderTargetBitmap。我还将画布渲染为相同的RenderTargetBitmap。即使屏幕上的像素边界很清晰,但保存后会变得模糊 在下面的屏幕截图中,您可以看到问题(BitmapScalingMode=NearestNeighbor) 这里是BitmapScalingMode=HighQuality。它比较光滑,但不干净。 这是我代码的相关部分。您可以看到,我尝试在多个位置设置渲染,但似乎没有效果

我正在使用DrawingContext来绘制图像。然后将结果渲染为RenderTargetBitmap。我还将画布渲染为相同的RenderTargetBitmap。即使屏幕上的像素边界很清晰,但保存后会变得模糊

在下面的屏幕截图中,您可以看到问题(BitmapScalingMode=NearestNeighbor)

这里是BitmapScalingMode=HighQuality。它比较光滑,但不干净。

这是我代码的相关部分。您可以看到,我尝试在多个位置设置渲染,但似乎没有效果

        DrawingVisual drawingVisual = new DrawingVisual();
        RenderTargetBitmap result = new RenderTargetBitmap((int)size.Width, (int)size.Height, 96, 96, PixelFormats.Pbgra32);

        RenderOptions.SetBitmapScalingMode(drawingVisual, BitmapScalingMode.NearestNeighbor);   // This forces the scaling to be on even-pixel boundaries
        RenderOptions.SetBitmapScalingMode(drawCanvas, BitmapScalingMode.NearestNeighbor);  // This forces the scaling to be on even-pixel boundaries
        RenderOptions.SetBitmapScalingMode(result, BitmapScalingMode.NearestNeighbor);  // This forces the scaling to be on even-pixel boundaries

        using (DrawingContext context = drawingVisual.RenderOpen()) {
            context.DrawRectangle(Brushes.Black, null, new Rect(new Point(), new Size(size.Width, size.Height)));

            if (layers.Count >= 1 && layers[0].LayerImage != null && layers[0].LayerImage.Source != null && gridImage.Children[1].Visibility == System.Windows.Visibility.Visible)
                context.DrawImage(layers[0].LayerImage.Source, new Rect(size)); // Draw first image.

            context.Close();
        }

        result.Render(drawingVisual);

        drawCanvas.Measure(drawCanvas.RenderSize);
        drawCanvas.Arrange(new Rect(drawCanvas.RenderSize));

        for (int i = 0; i < drawCanvas.Children.Count; i++) {
            RenderOptions.SetBitmapScalingMode(drawCanvas.Children[i], BitmapScalingMode.NearestNeighbor);  // This forces the scaling to be on even-pixel boundaries
        }

        result.Render(drawCanvas);

        BitmapEncoder encoder = new PngBitmapEncoder();
        if (result!= null) {
            encoder.Frames.Add(BitmapFrame.Create((BitmapSource)result));
            encoder.Save(fileStream);
        }
DrawingVisual DrawingVisual=新建DrawingVisual();
RenderTargetBitmap结果=新的RenderTargetBitmap((int)size.Width,(int)size.Height,96,96,PixelFormats.Pbgra32);
RenderOptions.SetBitmapScalingMode(drawingVisual,BitmapScalingMode.NearestNeighbork);//这将强制缩放在偶数像素边界上
RenderOptions.SetBitmapScalingMode(drawCanvas,BitmapScalingMode.NearestNeighbork);//这将强制缩放在偶数像素边界上
RenderOptions.SetBitmapScalingMode(结果,BitmapScalingMode.NearestNeighbor);//这将强制缩放在偶数像素边界上
使用(DrawingContext=drawingVisual.Renderropen()){
DrawRectangle(Brushes.Black,null,new Rect(new Point(),new Size(Size.Width,Size.Height));
如果(layers.Count>=1&&layers[0]。LayerImage!=null&&layers[0]。LayerImage.Source!=null&&gridImage.Children[1]。可见性==System.Windows.Visibility.Visible)
context.DrawImage(层[0]。LayerImage.Source,新Rect(大小));//绘制第一个图像。
context.Close();
}
结果:渲染(drawingVisual);
drawCanvas.Measure(drawCanvas.RenderSize);
Arrange(新的Rect(drawCanvas.RenderSize));
for(int i=0;i
我不知道您是否已经修复了该功能,但该功能在我这边运行得非常好

    public BitmapSource SnapShotPNG(UIElement source)
    {
        double actualWidth = source.RenderSize.Width;
        double actualHeight = source.RenderSize.Height;

        RenderTargetBitmap renderTarget = new RenderTargetBitmap((int)actualWidth, (int)actualHeight, 96, 96, PixelFormats.Pbgra32);


        DrawingVisual visual = new DrawingVisual();

        using (DrawingContext context = visual.RenderOpen())
        {
            VisualBrush sourceBrush = new VisualBrush(source);
            context.DrawRectangle(sourceBrush, null, new Rect(new Point(0, 0), new Point(actualWidth, actualHeight)));
        }
        source.Measure(source.RenderSize); //Important
        source.Arrange(new Rect(source.RenderSize)); //Important

        renderTarget.Render(visual);

        try
        {
            return new CroppedBitmap(renderTarget, new Int32Rect(0, 0, (int)actualWidth, (int)actualHeight));
        }
        catch (Exception ex)
        {
            Console.WriteLine(ex.Message);
            return null;
        }
    }

尝试将您的
BitmapScalingMode
更改为
HighQuality
上次我认为我有这个问题时,它实际上是一个IfranView显示选项。@lll:我尝试了HighQuality,但没有真正的帮助。请参见上面编辑中的屏幕截图。@TAW:我在许多程序中试用过它,包括我自己的程序,它们看起来都一样,所以我认为这是我的保存代码,而不是查看器。@TAW您不能将System.Drawing和WPFThanks混用!我试试看。还没有,对不起!我的代码在我发布这篇文章后已经被重新格式化,所以我需要对它进行反褶积,以找出如何测试您的函数。敬请期待!我已经使用类似的东西有一段时间了,但实际上必须运行measure+arrange,宽度和高度都要大1个像素,然后以正确的大小再次运行它。如果你在没有渲染的情况下看到任何奇怪的东西,那么试试[sic]
 public static BitmapSource CaptureScreen(this UIElement visualElement, int? desiredLongestEdge = null)
    {
        double scale = 1;
        if (desiredLongestEdge.HasValue)
        {
            if (visualElement.RenderSize.Width > visualElement.RenderSize.Height)
            {
                scale = desiredLongestEdge.Value/ visualElement.RenderSize.Width;
            }
            else
            {
                scale = desiredLongestEdge.Value / visualElement.RenderSize.Height ;
            }
        }

        var targetBitmap =
                     new RenderTargetBitmap(
                        (int) Math.Ceiling(scale * (visualElement.RenderSize.Width + 1)),
                         (int) Math.Ceiling(scale * (visualElement.RenderSize.Height + 1)),
                                                       scale * 96,
                                                       scale * 96,
                                                        PixelFormats.Pbgra32);

        visualElement.Measure(visualElement.RenderSize); //Important
        visualElement.Arrange(new Rect(visualElement.RenderSize)); //Important

        targetBitmap.Render(visualElement);

        return targetBitmap;
    }