0

私はWindows Phone 7カメラアプリで作業しています。キャプチャしたストリームを変換し、exifヘルパーを使用して回転を修正し、品質、方向、出力サイズパラメーターを使用してjpegとして保存する必要があります 。回転を修正するためにexif回転の記事に従いました。しかし、中心的な問題は、画像をメディア ライブラリに保存するために、最初にストリームを jpeg にデコードしてから、前述のように回転修正を実行する必要があることです。

次のコードを使用します。

private WriteableBitmap DecodeImage(Stream photo, int angle)
 {
            WriteableBitmap source = PictureDecoder.DecodeJpeg(photo);

            photo.Seek(0, SeekOrigin.Begin);           

            System.GC.Collect();

            UiDispatcher.BeginInvoke(() =>
            {
                MessageBox.Show(App.LogMemory("after decode"));
            });
            switch (angle)
            {
                case 90:
                case 270:
                    return RotateBitmap(source, source.PixelHeight,
                        source.PixelWidth, angle);
                case 180:
                    return RotateBitmap(source, source.PixelWidth,
                        source.PixelHeight, angle);
                default:
                    return source;
            }
            return null;
        }

RotateBitMap メソッドには、リンクで指定された回転ロジックがありますが、次のようにソースから新しい WritableBitmap オブジェクトを作成します。

WritablBitmap target = new WritableBitmap(soure.width,source.height); //source is the bitmap passed in argument.

問題は

PictureDecoder.decodejpeg -- カメラでキャプチャしたストリームに 30 mb を消費し、回転ストリーム メソッドで新しいビットマップを作成すると、さらに 30 mb を消費します。その結果、60 mb のアプリケーション メモリが増加します。

これにより、ローエンド (256 MB) の Windows Phone デバイスのメモリが原因で、アプリケーションがクラッシュします。jpeg のデコードに 30MB かかり、ストリームのローテーションに 30MB かかるのはなぜですか。 ??

任意のアイデア..?これらの場合にメモリ消費を最適化する方法???

注:出力サイズ、品質でjpegとして保存するには、そのビットマップを使用する必要があるため、結果としてrotatestreamメソッドからビットマップを取得する必要があります。

4

1 に答える 1

1

JPEG デコードを使用すると、通常、フルサイズの写真になります。8MP (約 8000000 ピクセル) のカメラで撮影した場合、計算は次のようになります。

8000000 * 32 ビット = 256 000 000 ビット (メモリ内の 1 つの画像に相当) (およそ 30MB 程度)

(HTC Titan II には 16MP のカメラが搭載されているので、写真をフル サイズで使用すると、約 62MB のメモリが必要になることを思い出してください!!)

明らかに、WriteableBitmap を 1 つだけ作成するには、30MB 必要です。写真を何らかの方法で操作するために、通常はその場で行うことはできません。つまり、コピーを作成する必要があり、それが重複する理由です。Windows Phone では、読み込んだ画像の解像度を自動的に下げることで、このような大量のメモリ消費を防ぐ方法がありますが、それは BitmapImage と JPEG ストリームをパラメーターとして受け取る SetSource メソッドで使用する場合に限られます。

以前、 Windows Phone で大きな写真を開いて操作する方法という記事でそれについて書きましたが、 Windows Phone のパフォーマンスに関する考慮事項で言及されています。

したがって、基本的には、ロードされた写真のサイズを縮小する必要があります (とにかくフルサイズが必要ですか?)。BitmapImage クラスを使用すると、自動的に 2000x2000 ピクセル (最大) である 2000x2000 ピクセル未満に簡単に縮小できます。それを気にしたくないなら、あなたは大丈夫なはずです。

于 2013-01-06T01:21:30.947 に答える