以下是通过实例讲解 Glide 图片变换(Transformation)的常见应用场景,涵盖基础到高级用法,帮助开发者实现多样化的图片展示效果。
1. 圆角图片(内置变换)
场景:显示圆角图片,如卡片式 UI 设计。
实现:使用 Glide 内置的 RoundedCorners 或 CenterCrop + RoundedCorners 组合。
Glide.with(context)
.load(url)
.transform(RoundedCorners(16)) // 圆角半径 16px
.into(imageView)
// 若需同时保证图片居中裁剪且圆角
Glide.with(context)
.load(url)
.transform(CenterCrop(), RoundedCorners(16))
.into(imageView)
2. 圆形头像(内置变换)
场景:用户头像的圆形显示。
实现:直接使用 CircleCrop 内置变换。
Glide.with(context)
.load(url)
.transform(CircleCrop()) // 圆形裁剪
.into(imageView)
3. 高斯模糊(自定义变换)
场景:模糊背景图(如对话框背景)。
实现:自定义 BitmapTransformation,结合 RenderScript 实现高效模糊。
class BlurTransformation(private val radius: Int = 25) : BitmapTransformation() {
override fun transform(pool: BitmapPool, toTransform: Bitmap, outWidth: Int, outHeight: Int): Bitmap {
// 1. 复用 BitmapPool 中的 Bitmap 减少内存分配
val bitmap = pool.get(outWidth, outHeight, Bitmap.Config.ARGB_8888)
// 2. 使用 RenderScript 实现高斯模糊
val rs = RenderScript.create(context)
val input = Allocation.createFromBitmap(rs, toTransform)
val output = Allocation.createTyped(rs, input.type)
val script = ScriptIntrinsicBlur.create(rs, Element.U8_4(rs))
script.setRadius(radius.toFloat())
script.setInput(input)
script.forEach(output)
output.copyTo(bitmap)
// 3. 回收原始 Bitmap 到 BitmapPool
pool.put(toTransform)
return bitmap
}
// 4. 必须重写此方法,保证缓存唯一性
override fun updateDiskCacheKey(messageDigest: MessageDigest) {
messageDigest.update("blur_$radius".toByteArray())
}
}
// 使用
Glide.with(context)
.load(url)
.transform(BlurTransformation())
.into(imageView)
4. 黑白滤镜(自定义变换)
场景:将图片转为黑白效果(如商品售罄状态)。
实现:通过颜色矩阵调整实现灰度化。
class GrayscaleTransformation : BitmapTransformation() {
override fun transform(pool: BitmapPool, source: Bitmap, outWidth: Int, outHeight: Int): Bitmap {
val result = pool.get(outWidth, outHeight, Bitmap.Config.ARGB_8888)
val canvas = Canvas(result)
val paint = Paint()
val colorMatrix = ColorMatrix().apply { setSaturation(0f) } // 饱和度设为 0
paint.colorFilter = ColorMatrixColorFilter(colorMatrix)
canvas.drawBitmap(source, 0f, 0f, paint)
return result
}
override fun updateDiskCacheKey(messageDigest: MessageDigest) {
messageDigest.update("grayscale".toByteArray())
}
}
// 使用
Glide.with(context)
.load(url)
.transform(GrayscaleTransformation())
.into(imageView)
5. 多变换组合
场景:先裁剪为圆形,再添加边框。
实现:通过 MultiTransformation 组合多个变换。
// 自定义边框变换
class BorderTransformation(private val borderWidth: Int, private val borderColor: Int) : BitmapTransformation() {
override fun transform(pool: BitmapPool, source: Bitmap, outWidth: Int, outHeight: Int): Bitmap {
val borderedBitmap = Bitmap.createBitmap(source.width, source.height, source.config)
val canvas = Canvas(borderedBitmap)
val paint = Paint(Paint.ANTI_ALIAS_FLAG)
// 绘制原图
canvas.drawBitmap(source, 0f, 0f, null)
// 绘制边框
paint.style = Paint.Style.STROKE
paint.strokeWidth = borderWidth.toFloat()
paint.color = borderColor
canvas.drawCircle(source.width / 2f, source.height / 2f, source.width / 2f - borderWidth / 2f, paint)
return borderedBitmap
}
override fun updateDiskCacheKey(messageDigest: MessageDigest) {
messageDigest.update("border_${borderWidth}_$borderColor".toByteArray())
}
}
// 组合变换:圆形裁剪 + 边框
Glide.with(context)
.load(url)
.transform(
MultiTransformation(
CircleCrop(),
BorderTransformation(4, Color.WHITE)
)
)
.into(imageView)
6. 自定义形状(如三角形、菱形)
场景:非规则形状图片显示(如徽章图标)。
实现:通过 BitmapTransformation 和 Canvas 绘制路径。
class DiamondTransformation : BitmapTransformation() {
override fun transform(pool: BitmapPool, source: Bitmap, outWidth: Int, outHeight: Int): Bitmap {
val size = min(source.width, source.height)
val bitmap = pool.get(size, size, Bitmap.Config.ARGB_8888)
val canvas = Canvas(bitmap)
val path = Path().apply {
moveTo(size / 2f, 0f) // 顶点
lineTo(size.toFloat(), size / 2f) // 右点
lineTo(size / 2f, size.toFloat()) // 底点
lineTo(0f, size / 2f) // 左点
close()
}
canvas.clipPath(path)
canvas.drawBitmap(source, (size - source.width) / 2f, (size - source.height) / 2f, null)
return bitmap
}
override fun updateDiskCacheKey(messageDigest: MessageDigest) {
messageDigest.update("diamond".toByteArray())
}
}
// 使用
Glide.with(context)
.load(url)
.transform(DiamondTransformation())
.into(imageView)
7. 动态缩放与剪裁
场景:根据容器尺寸动态调整图片显示区域。
实现:结合 override 和 CenterCrop。
Glide.with(context)
.load(url)
.override(300, 300) // 强制加载为 300x300 像素
.transform(CenterCrop())
.into(imageView)
最佳实践与注意事项
- 优先使用内置变换:如
CircleCrop、RoundedCorners,性能更优。 - 复用 BitmapPool:在自定义变换中通过
BitmapPool.get()复用 Bitmap,避免内存抖动。 - 避免过度变换:复杂变换(如高斯模糊)可能影响性能,建议在子线程预处理。
- 唯一缓存标识:必须重写
updateDiskCacheKey,否则不同参数变换可能共用缓存导致错误。 - 组合顺序:
MultiTransformation按添加顺序执行变换,需注意逻辑顺序。
总结:常见场景与对应方案
| 场景 | 推荐变换 |
|---|---|
| 圆角图片 | RoundedCorners |
| 圆形头像 | CircleCrop |
| 背景模糊 | 自定义 BlurTransformation |
| 黑白滤镜 | 自定义 GrayscaleTransformation |
| 组合效果(圆角+边框) | MultiTransformation |
| 非规则形状 | 自定义 Path + Canvas.clipPath() |
通过灵活使用 Glide 的变换功能,可以轻松实现多样化的视觉效果,同时需注意性能与内存优化。
当前文章价值8.67元,扫一扫支付后添加微信提供帮助!(如不能解决您的问题,可以申请退款)

评论已关闭!