Master Android ImageView: src, background, alpha, foreground & scaleType
This article provides a comprehensive, source‑code‑driven guide to correctly using Android ImageView's src, background, transparency methods, foreground handling, adjustViewBounds, and scaleType attributes, helping developers avoid common pitfalls and achieve the desired visual effects.
Introduction
This article introduces important ImageView methods and analyzes confusing issues from the source‑code perspective.
1. Proper use of ImageView src and background
src : the original image content stored at its intrinsic size, not stretched. background : the view background that is stretched to match the ImageView's dimensions.
You can set both src and background simultaneously; use android:scaleType to scale src, and you may also adjust background opacity.
2. Correctly setting ImageView transparency
Is calling mImageView.setAlpha(100) sufficient? The answer is not straightforward.
Three ways to set transparency on ImageView:
setAlpha(@FloatRange(from=0.0, to=1.0) float alpha) – provided by View.
setAlpha(int alpha) – deprecated.
setImageAlpha(int alpha) – API >= 16.
setImageAlpha internally calls setAlpha(int), which applies only to the image drawable, not the background. Drawable and Paint also use setAlpha(int).
Correct answer: android:src affects ImageView when using setAlpha(int) . android:background does not affect ImageView when using setAlpha(int) .
Why? Because setAlpha(int) targets the image drawable. The source code shows the implementation:
setAlpha(int alpha) method
Figure 1: ImageView setAlpha()
applyColorMod implementation
Figure 2: ImageView applyColorMod()
How mDrawable is obtained:
Figure 3: ImageView constructor fetching src image
In setImageDrawable(Drawable d), updateDrawable(Drawable d) assigns mDrawable:
Figure 4: ImageView updateDrawable()
Therefore, using setAlpha(int) may sometimes have no effect.
Why Drawable.mutate() is used in applyColorMod()
From Drawable.mutate() Javadoc: Make this drawable mutable. This operation cannot be reversed. A mutable drawable is guaranteed to not share its state with any other drawable. This is especially useful when you need to modify properties of drawables loaded from resources. By default, all drawables loaded from the same resource share a common state; if you modify one instance, all others receive the same modification. Calling this method on a mutable Drawable will have no effect.
Thus, mutating a drawable ensures that changes such as alpha adjustments are not shared.
mImageView.setBackgroundDrawable(mDrawable);
mImageView.getBackground().setAlpha(100);The above code works only if the drawable is not shared; otherwise other places may also change opacity.
Correct usage:
mImageView.setBackgroundDrawable(mDrawable.mutate());
mImageView.getBackground().setAlpha(100);Summary
Setting ImageView transparency involves many pitfalls; using the View‑provided setAlpha(float) is generally the safest approach.
3. Properly setting ImageView foreground
When a design requires overlaying a layer (e.g., gray) on an ImageView, distinguish between static and asynchronous ImageViews.
Static ImageView
Use src (foreground) and background appropriately.
Asynchronous ImageView
Use the View method setForeground(Drawable foreground).
Figure 5: View setForeground() method
Figure 6: ForegroundInfo creation in View constructor
Using setForeground() requires targetSdkVersion >= 23. For lower targets, a custom implementation (e.g., ExtendImageView in the AFC framework) is needed.
4. Correct use of android:adjustViewBounds
Set this to true if you want the ImageView to adjust its bounds to preserve the aspect ratio of its drawable. Note: If the app targets API level 17 or lower, adjustViewBounds will allow the drawable to shrink the view bounds, but not grow to fill available measured space in all cases. This is for compatibility with legacy MeasureSpec and RelativeLayout behavior.
To set a maximum height, combine setAdjustViewBounds(true) with maxWidth, maxHeight, and use wrap_content for layout dimensions.
Set setAdjustViewBounds to true.
Set maxWidth and maxHeight.
Set layout_width and layout_height to wrap_content.
5. Correct use of android:scaleType
The android:scaleType attribute only affects the src drawable.
Original image
ScaleType.CENTER_CROP
Designers may want the image to shift slightly downward; only FIT_XY achieves that.
ScaleType.FIT_XY
The image moves down but becomes stretched.
ScaleDrawable.CROP_START
ScaleDrawable provides 11 additional cropping options:
(1) CROP_CENTER
(2) CROP_START
(3) CROP_END
(4) FIT_CENTER
(5) FIT_START
(6) FIT_END
(7) MATCH_WIDTH_TOP
(8) MATCH_WIDTH_BOTTOM
(9) MATCH_WIDTH_CENTER
(10) CENTER
(11) CROP_BY_PIVOTXML example for android:scaleType="fitXY":
Figure: XML setting scaleType
Java code setting ScaleDrawable.CROP_START still requires android:scaleType="fitXY" in XML to take effect.
Why fitXY is required
setScaleType() must be FIT_XY for the custom ScaleDrawable cropping to work because configBounds() only uses view width/height when the drawable dimensions are non‑zero.
Figure: setScaleType() method
Figure: updateDrawMatrix() method
Figure: configBounds() method
Conclusion
The analysis may have omissions or errors; please point them out if found.
Tencent TDS Service
TDS Service offers client and web front‑end developers and operators an intelligent low‑code platform, cross‑platform development framework, universal release platform, runtime container engine, monitoring and analysis platform, and a security‑privacy compliance suite.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.
