0

WinRT アプリで画像のヒストグラム表現を作成する際に問題が発生しています。私が作りたいのは、画像の赤、緑、青、明度の 4 つのヒストグラム プロットで構成されています。

私の主な問題は、そのヒストグラムの画像を実際に描画して、画面に表示できるようにする方法です。これまでの私のコードはかなり... 乱雑です。このトピックをたくさん検索しました。ほとんどの結果は Java のコードで構成されていました。これをどうにかして C# に翻訳しようとしていますが、API はかなり異なります... AForgeからも試みがありましたが、それはwinformsです...

これが私の厄介なコードです。見た目が悪いことはわかっていますが、最初にこれを機能させるよう努めています。

public static WriteableBitmap CreateHistogramRepresentation(long[] histogramData, HistogramType type)
    {
        //I'm trying to determine a max height of a histogram bar, so
        //I could determine a max height of the image that then I'll remake it
        //at a lower resolution :
        var max = histogramData[0];

        //Determine the max value, the highest bar in the histogram, the initial height of the image.
        for (int i = 0; i < histogramData.Length; i++)
        {
            if (histogramData[i] > max)
                max = histogramData[i];
        }

        var bitmap = new WriteableBitmap(256, 500);

        //Set a color to draw with according to the type of the histogram :
        var color = Colors.White;
        switch (type)
        {
            case HistogramType.Blue :
                {
                    color = Colors.RoyalBlue;
                    break;
                }
            case HistogramType.Green:
                {
                    color = Colors.OliveDrab;
                    break;
                }
            case HistogramType.Red:
                {
                    color = Colors.Firebrick;
                    break;
                }
            case HistogramType.Luminosity:
                {
                    color = Colors.DarkSlateGray;
                    break;
                }
        }

        //Compute a scaler to scale the bars to the actual image dimensions :
        var scaler = 1;
        while (max/scaler > 500)
        {
            scaler++;
        }

        var stream = bitmap.PixelBuffer.AsStream();
        var streamBuffer = new byte[stream.Length];

        //Make a white image initially :
        for (var i = 0; i < streamBuffer.Length; i++)
        {
            streamBuffer[i] = 255;
        }

        //Color the image :
        for (var i = 0; i < 256; i++) // i = column
        {
            for (var j = 0; j < histogramData[i] / scaler; j++) // j = line
            {
                streamBuffer[j*256*4 + i] = color.B; //the image has a  256-pixel width
                streamBuffer[j*256*4 + i + 1] = color.G;
                streamBuffer[j*256*4 + i + 2] = color.R;
                streamBuffer[j*256*4 + i + 2] = color.A;
            }
        }

        //Write the Pixel Data into the Pixel Buffer of the future Histogram image :
        stream.Seek(0, 0);
        stream.Write(streamBuffer, 0, streamBuffer.Length);

        return bitmap.Flip(WriteableBitmapExtensions.FlipMode.Horizontal);
    }

これにより、かなり悪いヒストグラム表現が作成され、対応する色で色付けさえされません...正しく機能していません。修正するために取り組んでいます...

リンクで貢献できる場合は、WinRT アプリのヒストグラム表現のコードを知っているか、その他すべてが大歓迎です。

4

1 に答える 1

0

JP Aliotoが指摘したように、チャートコントロールを使用することもできますが、ヒストグラムは多くのデータを表す傾向があります。サンプルだけで、256本のバー* 4軸(R、G、B、L)をレンダリングしています。チャートコントロールの問題は、通常、ハイドレイトされたデータのコレクション(または配列)を渡されることを好み、それを描画し、メモリに保持する傾向があることです。あなたのようなヒストグラムは、メモリ内に1024個のオブジェクト(256 * 4)があり、全体としてチャートに渡される必要があります。これは、メモリ管理の適切な使用法ではありません。

もちろん、別の方法は自分で描くことです。しかし、ご存知のように、ピクセルごとの描画は少し面倒な場合があります。私の意見では、最良の答えはShaharに同意し、CodePlexでWriteableBitmapExを使用することをお勧めすることです。

http://writeablebitmapex.codeplex.com

WriteableBitmapExには、非常に高速な線や長方形などの形状を描画するためのメソッドが含まれています。データを列挙しながら(一度にすべてをメモリに保存する代わりに)描画でき、その結果、すでに「ビットマップキャッシュ」されている(つまり、データがないため非常に高速にレンダリングされる)コンパクトな画像が得られます。各フレームで再描画します)。

開発サポート、設計サポート、そして途中でのより素晴らしい良さ:http: //bit.ly/winappsupport

于 2013-02-28T20:41:20.587 に答える