2012-03-06 8 views
2

私はその一部が画像のグリッドを表示することをアプリに持っています。 各ImageViewは200x150ですが、画像自体は1024x768です。 私はそれらの画像を設定しようとすると、すぐに私はメモリの警告を取得し、おそらく殺される。contentScaleFactorを使用して安全にメモリを節約できますか?

一方、コード内でこれらの画像のサイズを変更するとCPUコストが高くなり、多くの時間がかかります。

今、「Apple WWDC」セッションのビデオの1つを見ました。そこにいる人は、ビューを表示するために割り当てられた実際のビットマップメモリ​​の量を担当するUIViewのcontentScaleFactorについて言及しました。私のImageViewのは、はるかに少ないメモリを割り当てます。このように

// Make sure not to divide by zero 
if (image.size.width > 0 && image.size.height > 0) 
{ 
    CGFloat widthRatio = self.imageView.frame.size.width/image.size.width; 
    CGFloat heightRatio = self.imageView.frame.size.height/image.size.height; 
    CGFloat aspectFitRatio = MAX(widthRatio, heightRatio); 
    aspectFitRatio = MIN(1, aspectFitRatio); 
    [self.imageView setContentScaleFactor:aspectFitRatio]; 
} 

:彼らは唯一のより大きなスケールファクタの例を言及し、私は1より小さい値に設定する気に文書で

私の質問は - 私は正しいのですか? 本当にメモリを節約できますか? contentScaleFactorを<の値に設定することも "合法"ですか?

ありがとうございます!

答えて

0

私は助けてくれると恐れています。多くはです。問題は、UIViewは、そのサイズが何であれ、画像を保持していることです。したがって、ビューが存在する限り、イメージはRAMを占有します。 contentScaleFactorはこの事実を変更しません。実際にメモリフットプリントを減らすには、UIViewに割り当てる前に画像を再サンプリングする必要があります。

ただし、contentScaleFactorはレンダリングに使用されるバッキングストアのサイズに影響します。現時点では、iOSデバイスには2つのカテゴリしかなく、これらのデバイスには1.0または2.0のスケールファクタが使用されているため、contentScaleFactorをRetinaデバイスで単に1.0にすることができます。他のデバイスでは何も行いません。

+0

イメージオブジェクトはそれほど大きくありません。メモリを食べるレンダリング用のバッキングストアです。例えば、1024x768のサイズのjpgイメージは300kbのようなものです。これは、jpg形式が圧縮されているためです。このイメージを表示したいときは、各ピクセルをそれ自身のバイト(少なくとも)で表現しなければならないので、このイメージのレンダリングに必要なメモリは1024x768 = 786kbになります。だから、バッキングストアのメモリフットプリントを減らすことは、メモリの総面積に顕著な影響を与えるはずです。 –

+0

@Avrahamshuk大きな疑問は(そして実装_detail_と見なされます)、イメージが解凍されたときです。レンダリングする必要があるたびに圧縮解除されると、メモリーはほとんど消費されませんが、再描画するには非常にコストがかかります。ディスクから読み取ったときに解凍された場合、その逆が真です。現在の実装では遅延ロード(最初に描画されたときに画像を伸長する)を行い、高速で再描画するために圧縮解除されたイメージをRAMに保持していると思います。しかし、私は間違っているかもしれません、そして、それはどんなiOSのリリースでも変わるかもしれません。 – Costique

+0

あなたの前提は理にかなっています。ですから、イメージが最初に描画される前にcontentScaleFactorが設定されていることを確認できれば、私はたくさんのメモリを節約します。しかし、私はまだあなたの答えを受け入れることができません...今度は、UIKitの描画プロセスを詳しく見ていきます。 –

関連する問題