7

ソフトウェアにはタイムライン機能があります。さまざまな時点のデータを示す小さなブロブの行が表示されます。コードは c#、.Net 4、および WPF です。ブロブを表示するために、現在境界線を作成し (ブラシを指定)、それをグリッドに追加しています。このグリッドは、行を形成する親グリッドに追加されます。

タイムラインに表示される BLOB の数が比較的少ない場合はこれで問題ありませんが、データが非常に混雑している場合は、レンダリングが遅くなり、メモリの使用量が増え、UI が応答しなくなります。(驚くべきことではありません)。

私たちはこれを最善の方法で行っていないことを知っています.wpfでこのようなグラフィックを表示する最良の方法は何ですか?

編集:以下の返信ありがとうございます - これらのオプションを調査します。ただし、それぞれに大量の再コーディングが必要であり、ここでの私の質問はより単純です。リソースコストが低いボーダーを置き換えるために使用できるコントロールまたは効果はありますか?

4

3 に答える 3

4

このようなデータの視覚化には、DynamicDataDisplayが本当に好きです。このコンポーネントは現在、Silverlight用にのみ保守/開発されていますが、WPF用のオープンソース(リンク内)バージョンがあり、これは本当に素晴らしいライブラリです。

ライブラリはIObservableコレクションを使用し、DateTime軸の値をサポートします。

組み込みのマーカーグラフタイプがあります(以下の例)。

カスタムマーカーを使用でき、ズームとスクロール、その他の多くの優れた機能などをサポートします。また、非常に大量のデータセットがある場合でも、非常に高速です。

データセットはIObservableグラフコンポーネントであるため、基になるデータセットの変更に動的に応答するため、データコレクションが更新されるたびにグラフが更新されます。

編集

次に例を示します。

使用:

using System.ComponentModel;
using Microsoft.Research.DynamicDataDisplay;
using Microsoft.Research.DynamicDataDisplay.Charts;
using Microsoft.Research.DynamicDataDisplay.DataSources;
using Microsoft.Research.DynamicDataDisplay.PointMarkers;

主要 :

 public Window1()
    {
        InitializeComponent();
        //
        const int N = 100;
        List<double> x = new List<double>();
        List<double> y = new List<double>();

        DateTimeAxis dtAxis = new DateTimeAxis();
        _plotter.HorizontalAxis = dtAxis;

        Random rand = new Random();
        for (int i = 0; i < N; i++)
        {   //generate some random data
            x.Add(dtAxis.ConvertToDouble(DateTime.Now.AddDays(i)));
            y.Add(rand.Next(N));
        }

        EnumerableDataSource<double> gX = new EnumerableDataSource<double>(x);
        EnumerableDataSource<double> gY = new EnumerableDataSource<double>(y);
        _MarkerGraph.DataSource = new CompositeDataSource(gX,gY);

        //no scaling - identity mapping
        gX.XMapping = xx => xx;
        gY.YMapping = yy => yy;

        CirclePointMarker mkr = new CirclePointMarker();
        mkr.Fill = new SolidColorBrush(Colors.Red);
        mkr.Pen = new Pen(new SolidColorBrush(Colors.Black),2.0);
        _MarkerGraph.Marker = mkr;
    }

XAML:

<Window x:Class="WpfApplication1.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d3="clr-namespace:Microsoft.Research.DynamicDataDisplay;assembly=DynamicDataDisplay"
Title="Window1" Height="481" Width="651">
<Grid>
    <d3:ChartPlotter Name="_plotter">
        <d3:MarkerPointsGraph Name="_MarkerGraph"/>
    </d3:ChartPlotter>
</Grid>

出力: プログラムが実行されます...

DateTime軸は美しくスケーリングし、目盛りを日、月、時間、秒など適切なものに調整します。やさしい!

このパッケージを使用する場合は、ソースをダウンロードして、ソリューションに2番目のプロジェクトとして追加することを強くお勧めします。ドキュメントはD3には非常に貧弱であり、プロジェクトにソースがあると、物事がどのように機能するかを理解するのに役立ちます。また、必要に応じて、追加や拡張を非常に簡単に行うことができます。コンパイルされたDLLではなく、これを行う場合は、必ずソリューション内のプロジェクトを参照してください。

また、利用可能なドキュメントやオンラインの例の多くは、開いているWPFコンポーネントではなく、保守されているSilverlightコンポーネントを対象としていることにも注意してください。コンポーネントの多くはこれら2つのバージョン間で異なるため、WPFコンポーネントを調べて、そこに何があるかを確認する必要があります。上記の例は、v0.3WPFコンポーネント用です。

于 2012-04-16T15:59:57.067 に答える
3

絶えず変化するビジュアルを多数描画する場合、WPF が提供する最速の方法は、オーバーライドOnRenderして に描画することDrawingContextです。

ビジュアルがほとんど静的であるが、時々変化する可能性がある場合、最速の方法はDrawingVisualfor each を作成し、必要に応じて変更できるようにすることです。

詳細については、この質問、リンクされた記事、および回答を参照してください。

于 2012-04-16T16:14:22.187 に答える