RenderTargetBitmap:无法释放/处置句柄

时间:2015-04-10 11:26:41

标签: c# dispose rendertargetbitmap imagebrush drawingvisual

抱歉我的英语不好。

我想将DrawingVisual渲染为位图,以便创建DiffuseMaterial。我这样做:

public DiffuseMaterial GetDiffuseMaterial(string text, string font, double fontSize, Brush brush)
{
    FormattedText formattedText = new FormattedText(text, CultureInfo.InvariantCulture, FlowDirection.LeftToRight, new Typeface(font), fontSize, brush);
    DrawingVisual drawingVisual = new DrawingVisual();
    using (DrawingContext drawingContext = drawingVisual.RenderOpen())
        drawingContext.DrawText(formattedText, new Point(0, 0));

    RenderTargetBitmap bmp = new RenderTargetBitmap((int)(text.Length * fontSize), (int)fontSize, 96, 96, PixelFormats.Pbgra32);
    bmp.Render(drawingVisual);

    DiffuseMaterial mat = new DiffuseMaterial(new ImageBrush(bmp));
    mat.Freeze();
    return mat;
}

但是...

  • 如果我使用方法GetDiffuseMaterial 10000次,应用程序将停止。这是“正常的”,因为每个应用程序都可以有maximum 10000 GDI handles,RenderTargetBitmap每次创建时都会使用1个GDI句柄。
  • 解决此问题的方法是释放RenderTargetBitmap对象。但我没有做到这一点。我试过这个(在mat.Freeze()和返回垫之间; ):

           bmp.Freeze();  
           bmp = null;  
           GC.Collect();  
           GC.WaitForPendingFinalizers();  
           GC.Collect();  
    
  • 另一种方法是只使用一个RenderTargetBitmap并将其作为参数提供给GetDiffuseMaterial。
    但是如果我调用两次GetDiffuseMaterial,我会有两个相同的材质,因为句柄是共享的,而材质是最后一次修改。 (所以即使text参数不一样!)

我没有看到用RenderTargetBitmap做我想要的其他方法。
NB :GetDiffuseMaterial可以被调用100万次......

RenderTargetBitmap是我发现从String文本创建DiffuseMaterial的最快方法。其他技术非常慢:使用带有TextBlock的VisualBrush,使用DrawingBrush,例如:使用RenderTargetBitmap对GetDiffuseMaterial的5000次调用比其他技术快至少10倍。

感谢您的帮助。

0 个答案:

没有答案