【问题标题】:Using RenderTargetBitmap to save a portion of the displayed images使用 RenderTargetBitmap 保存部分显示的图像
【发布时间】:2012-02-18 08:54:14
【问题描述】:

我有一个简单的 WPF 应用程序,我在其中显示一个非常大的图像 (9000x2875),并在其上显示许多小图像 (64x64)。

为此,我有一个Canvas 和一个Image,然后我以编程方式在小图像到达时添加它们。

现在我正在尝试将部分合成图像保存为png 文件。我想我会使用RenderTargetBitmap 来渲染我想要的Canvas 部分。我的问题是我找不到保存图像正确部分的好方法。这是我目前的 hack:

private static void SaveImage(Canvas canvas, string file, int x, int y, int width, int height)
{
  //changing 0,0 on the canvas so RenderTargetBitmap works as expected.
  canvas.RenderTransform = new MatrixTransform(1d, 0d, 0d, 1d, -x, -y);
  canvas.UpdateLayout();
  RenderTargetBitmap bmp = new RenderTargetBitmap(width, height, 96d, 96d, Pixelformats.Pbgra32);
  bmp.Render(canvas);
  PngBitmapEncoder encoder = new PngBitmapEncoder();
  encoder.Frames.Add(BitmapFrame.Create(bmp));
  using(Stream s = File.Create(file))
  {
    encoder.Save(s);
  }
}

这样做的明显问题是显示会因RenderTransform 而改变。它还使应用程序变慢。我确实尝试过对整个画布进行 RenderTargetBitmap,但这比这样做要慢得多。

所以我的问题是:
有没有更简单的方法可以只保存已查看图像的一部分?
如果没有,是否有人建议以更好的方式解决此问题? (我已经尝试过单个WriteableBitmap,但这与整个画布的RenderTargetBitmap 一样慢。

【问题讨论】:

    标签: c# wpf


    【解决方案1】:

    您要使用的是CroppedBitmap,它可以让您保存图像的裁剪部分。

    // (BitmapSource bmps)
    CroppedBitmap crop = new CroppedBitmap(bmps, new Int32Rect(selRect.X, selRect.Y, selRect.Width, selRect.Height));
    

    编辑:由于似乎没有办法让它在 WPF 中按照您想要的方式执行,我建议使用 GDI+(不显示)预先裁剪大图像并加载该区域你想把它放到一个较小的画布上。

    【讨论】:

    • 在这种情况下,我没有BitmapSource,我有Canvas。当我在整个Canvas 中使用RenderTargetBitmap 时,我使用的是CroppedBitmap,但正如我所提到的,这非常慢。
    • 您在问题中没有提到这一点。您是否尝试过制作较小的 Canvas,并设置 left 和 top 以使其仅显示您要渲染的图像部分?
    • 我尝试在我的画布中制作一个较小的画布,但效果不佳。我没有尝试让我的大画布变小。我会试试看。
    • 秘诀是用一个小的 VirtualizingStackPanel 替换我的 Canvas(从技术上讲,我保留了一个画布以供查看,并有一个单独的 VirtualizingStackPanel 用于文件创建)。这使得 UpdateLayout 速度非常快,值得这样做。如果您编辑答案以提及 VirtualizingStackPanel,我会将其标记为正确。谢谢。
    • 好的。我现在觉得自己不像个白痴了。回到CroppedBitmap。鉴于我有一个单独的画布供查看,因此无需将整个巨大的图像放在第二个画布中。一旦我知道我需要裁剪的区域,我只需将该区域放入画布中,添加也在裁剪区域中的任何较小的图像,然后 RenderTargetBitmap 。现在效果好多了。
    猜你喜欢
    • 2021-09-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-11
    • 2021-06-12
    • 1970-01-01
    相关资源
    最近更新 更多