14

データ テンプレートに小さなアイコンが表示された TreeView があります。RenderTargetBitmap を使用して Treeview を PNG として保存しようとしています。

イメージは小さなデータ セットで正しく保存されます。ただし、データ セットが大きくなりすぎると、一部のアイコンが最終イメージから除外されます。マジックナンバーは200アイテムらしい。ツリーが深いか広いかは関係ないようです。200 個のアイテムの後、アイコンはレンダリングされません。

追加されたコード

これが、画像を作成するために使用している私のコードです。

        RenderTargetBitmap targetBitmap = new RenderTargetBitmap(
            (int)_treeView.ActualWidth,
            (int)_treeView.ActualHeight,
            96, 96, PixelFormats.Default);

        targetBitmap.Render(_treeView);

スクリーンショットを追加

ツリーの右側にアイコンが表示されていないことに注意してください。 欠落しているアイコンのスクリーン ショット

ここで、いくつかのブランチを折りたたんで他のアイコンの一部を非表示にすると、これらのアイコンが含まれます。RenderTargetBitmap.Render には、すべてのアイコンをレンダリングする機能がありません。または、仮想パネルと関係があるかもしれません。 含まれているアイコンのスクリーンショット

ここで詳しく見てみましょう。 ここに画像の説明を入力

4

2 に答える 2

4

あなたが巨大なイメージを持っていることにすぐに気づきました。横幅12000。そこまで迫るとは驚きです。

MSDN が述べているように、テクスチャの幅/高さは DirectX テクスチャの制限によって制限されています。

XAML ビジュアル ツリーの最大レンダリング サイズは、Microsoft DirectX テクスチャの最大サイズによって制限されます。詳細については、「リソースの制限 (Direct3D)」を参照してください。この制限は、アプリが実行されるハードウェアによって異なる場合があります。この制限を超える非常に大きなコンテンツは、収まるようにスケーリングされる場合があります。スケーリング制限がこのように適用される場合、スケーリング後のレンダリング サイズは、PixelWidth プロパティと PixelHeight プロパティを使用してクエリできます。たとえば、10000 x 10000 ピクセルの XAML ビジュアル ツリーは、4096 x 4096 ピクセルにスケーリングされる場合があります。これは、アプリが実行されるハードウェアによって強制される特定の制限の例です。 http://msdn.microsoft.com/library/windows/apps/dn298548

私はこれらのことを疑っています:

  • 仮想化はいくつかのことを切り離しています - 私は過去に DataGrid で正確な問題を抱えていましたが、問題は仮想化でした。しかし、あなたのケースはそうではないようです。
  • テクスチャが大きすぎると、未定義の動作が発生する可能性があります。

ハードウェアアクセラレーションを無効にしてみてください。このことは、ハードコアなバグをほとんど引き起こしません。http://msdn.microsoft.com/en-us/library/system.windows.media.renderoptions.processrendermode.aspx

それ以外は、トリッキーですが、うまく機能することは間違いありません。

1) ルート オブジェクトから開始し、1000 x 1000 未満のオブジェクトが見つかるまで、ルート オブジェクトの子を再帰的にトラバースします。RenderTargetBitmap(BMP) を使用してその写真を撮り、IN-MEMORY-BMP にマージします。子どもたち一人ひとりに行います。

これらすべてを計算できるはずです。

于 2013-11-27T22:40:38.800 に答える
1

記録のために: 回避策があります。

RenderTargetBitmap を使用して Visual を直接レンダリングする代わりに、一時的な DrawingVisual を使用します。VisualBrush を使用して Visual を DrawingVisual にペイントし、RenderTargetBitmap を DrawingVisual で使用します。

このような:

    public BitmapSource RenderVisualToBitmap(Visual visual)
    {
        var contentBounds = VisualTreeHelper.GetContentBounds(visual);

        var drawingVisual = new DrawingVisual();
        using (var drawingContext = drawingVisual.RenderOpen())
        {
            var visualBrush = new VisualBrush(visual);
            drawingContext.DrawRectangle(visualBrush, null, contentBounds);
        }

        var renderTargetBitmap = new RenderTargetBitmap((int)contentBounds.Width, (int)contentBounds.Height, 96, 96, PixelFormats.Default);
        renderTargetBitmap.Render(drawingVisual);

        return renderTargetBitmap;
    }

ただし、VisualBrush が大きくなるにつれて、結果の画像がますますぼやけてしまうことに注意してください (高 DPI でレンダリングする場合)。この問題を回避するには、 https ://srndolha.wordpress.com/2012/10/16/exported-drawingvisual-quality-when-using-visualbrush/ で説明されているように、一連の小さな VisualBrush "タイル" を使用します。

于 2015-09-02T07:40:04.660 に答える