アイテムの1つがPicassoを使用してロードされたImageView
である垂直LinearLayoutがあります。画像の幅をデバイスの幅全体に広げ、固定の高さ(150dp)でトリミングされた画像の中央部分を表示する必要があります。現在、次のコードがあります。
Picasso.with(getActivity())
.load(imageUrl)
.placeholder(R.drawable.placeholder)
.error(R.drawable.error)
.resize(screenWidth, imageHeight)
.centerInside()
.into(imageView);
screenWidth
とimageHeight
(= 150dp)にはどの値を入れるべきですか?
あなたは探している:
.fit().centerCrop()
これらの意味:
fit
-ImageView
が測定されるまで待機し、イメージをそのサイズに正確に一致するようにサイズ変更します。centerCrop
-アスペクト比を考慮して、サイズがいっぱいになるまで画像を拡大縮小します。サイズが正確に一致するように、上下または左右のいずれかを切り抜きます。このブログ は、ピカソのサイズ変更およびフィット機能の詳細を説明しています: https://futurestud.io/tutorials/picasso-image-resizing-scaling-and-fit 。
resize(x、y)による画像のサイズ変更
通常、サーバーまたはAPIが必要な正確なサイズで画像を配信する場合に最適です。これは、帯域幅、メモリ消費量、および画像品質の完璧なトレードオフです。
残念ながら、完璧なサイズの画像をリクエストすることは常にあなたの管理下にあるとは限りません。画像のサイズが変な場合、resize(horizontalSize、verticalSize)呼び出しを使用して、画像のサイズをより適切なサイズに変更できます。これにより、ImageViewに表示する前に画像のサイズが変更されます。
Picasso
.with(context)
.load(UsageExampleListViewAdapter.eatFoodyImages[0])
.resize(600, 200) // resizes the image to these dimensions (in pixel). does not respect aspect ratio
.into(imageViewResize);
scaleDown()の使用
Resize()オプションを使用すると、Picassoは画像をアップスケールします。画像の品質を改善せずに小さな画像を大きくすると、計算時間が浪費される可能性があるため、scaleDown(true)を呼び出して、元の画像のサイズが目標サイズよりも大きい場合にのみresize()を適用します。
Picasso
.with(context)
.load(UsageExampleListViewAdapter.eatFoodyImages[0])
.resize(6000, 2000)
.onlyScaleDown() // the image will only be resized if it's bigger than 6000x2000 pixels.
.into(imageViewResizeScaleDown);
拡大縮小によるストレッチ画像の回避
これで、他の画像操作と同様に、画像のサイズを変更すると、実際にアスペクト比がゆがみ、画像表示が不鮮明になる可能性があります。ほとんどのユースケースでは、これを防ぐ必要があります。 Picassoでは、centerCrop()またはcenterInside()のいずれかを使用して、2つの緩和策の選択肢を提供します。
CenterCrop
CenterCrop()は、ImageViewの要求された境界を埋めるように画像をスケーリングし、余分な部分をトリミングするトリミング手法です。 ImageViewは完全に塗りつぶされますが、画像全体が表示されない場合があります。
Picasso
.with(context)
.load(UsageExampleListViewAdapter.eatFoodyImages[0])
.resize(600, 200) // resizes the image to these dimensions (in pixel)
.centerCrop()
.into(imageViewResizeCenterCrop);
CenterInside
CenterInside()は、両方の寸法がImageViewの要求された境界以下になるように画像を拡大縮小するトリミング手法です。画像は完全に表示されますが、ImageView全体に表示されない場合があります。
Picasso
.with(context)
.load(UsageExampleListViewAdapter.eatFoodyImages[0])
.resize(600, 200)
.centerInside()
.into(imageViewResizeCenterInside);
最後になりましたが、ピカソのfit()ここで説明するオプションは、画像のサイズ変更とスケーリングに関する機能のニーズをカバーする必要があります。 Picassoの最後のヘルパー機能が1つあります。これは非常に便利です:fit()。
Picasso
.with(context)
.load(UsageExampleListViewAdapter.eatFoodyImages[0])
.fit()
// call .centerInside() or .centerCrop() to avoid a stretched image
.into(imageViewFit);
fit()はターゲットImageViewの寸法を測定しており、resize()を内部的に使用して、画像サイズをImageViewの寸法に縮小します。 fit()について知っておくべきことが2つあります。まず、fit()を呼び出すと、ImageViewのサイズを測定できるようになるまでPicassoが待機する必要があるため、画像リクエストが遅延する可能性があります。第二に、ターゲットとしてImageViewでfit()のみを使用できます(他のターゲットについては後で説明します)。
利点は、画質に影響を与えることなく、画像が可能な限り低い解像度であるということです。解像度が低いほど、キャッシュに保持されるデータが少なくなります。これにより、アプリのメモリフットプリントにおける画像の影響を大幅に減らすことができます。要約すると、少し速いロード時間よりもメモリへの影響を小さくしたい場合、fit()は素晴らしいツールです。
場合によっては、fit()は役に立ちません。幅と高さの測定が終了するまで待つ必要があります。したがって、globallayoutlistenerを使用できます。例えば;
imageView.getViewTreeObserver().addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
public void onGlobalLayout() {
Picasso.with(getActivity())
.load(imageUrl)
.placeholder(R.drawable.placeholder)
.error(R.drawable.error)
.resize(screenWidth, imageHeight)
.fit
.centerInside()
.into(imageView);
view.getViewTreeObserver().removeOnGlobalLayoutListener(this);
}
});