图形变换(Transformations)

默认的变换

Glide包含两种默认的图像变换方式,fitCenter和centerCrop。如果开发者需要其他类型的变换,可以考虑使用这个独立的变换库

Fit center

FitCenter会按原始比例缩小图像,使图像可以在放在给定的区域内。FitCenter会尽可能少地缩小图片,使宽或者高的一边等于给定的值。另外一边会等于或者小于给定值。 FitCenter和Android中的ScaleType.FIT_CENTER效果相同。

CenterCrop

CenterCrop会按原始比例缩小图像,使宽或者高的一边等于给定的值,另外一边会等于或者大于给定值。CenterCrop会裁剪掉多余部分。 CenterCrop和Android中的ScaleType.CENTER_CROP效果相同。

使用

fit center效果使用.fitCenter()

Glide.with(yourFragment)
    .load(yourUrl)
    .fitCenter()
    .into(yourView);

center crop效果使用.centerCrop()

Glide.with(yourFragment)
    .load(yourUrl)
    . centerCrop()
    .into(yourView);

如果你只加载Bitmap或者Gif,也可以使用这个变换:

// For Bitmaps:
Glide.with(yourFragment)
    .load(yourUrl)
    .asBitmap()
    .centerCrop()
    .into(yourView);

// For gifs:
Glide.with(yourFragment)
    .load(yourUrl)
    .asGif()
    .fitCenter()
    .into(yourView);

当在类型间转码时,也可以使用这些变换。例如,获取一个变形后的jpeg图片的bytes数据:

Glide.with(yourFragment)
    .load(yourUrl)
    .asBitmap()
    .toBytes()
    .centerCrop()
    .into(new SimpleTarget<byte[]>(...) { ... });

自定义变换 除了两个内置的变换,你还可以自定义变换。 最简单的方式是继承BitmapTransformation。

private static class MyTransformation extends BitmapTransformation {

    public MyTransformation(Context context) {
       super(context);
    }

    @Override
    protected Bitmap transform(BitmapPool pool, Bitmap toTransform,
            int outWidth, int outHeight) {
       Bitmap myTransformedBitmap = ... // apply some transformation here.
       return myTransformedBitmap;
    }

    @Override
    public String getId() {
        // Return some id that uniquely identifies your transformation.
        return "com.example.myapp.MyTransformation";
    }
}

之后一就可以用同样的方式使用它。使用.transform(...)代替.fitCenter()/.centerCrop()

// For the default drawable type:
Glide.with(yourFragment)
    .load(yourUrl)
    .transform(new MyTransformation(context))
    .into(yourView);

// For Bitmaps:
Glide.with(yourFragment)
    .load(yourUrl)
    .asBitmap()
    .transform(new MyTransformation(context))
    .into(yourView);

// For Gifs:
Glide.with(yourFragment)
    .load(yourUrl)
    .asGif()
    .transform(new MyTransformation(context))
    .into(yourView);

调整大小

你可能注意到上面的例子没有传入具体的尺寸,那么,Transformation中的尺寸是如何获得的呢? Transformation中的尺寸就是View或者Target的大小。Glide会根据布局文件中的weight,match_parent或者具体值算出View的大小。,当你拥有View/Target的具体大小,又拥有原始图片的大小时,就可以通过图像变换生成一个正确大小的图片。 如果你想指定View/Target的自定义大小,可以使用.override(int, int)方法,如果你想加载一个图片有其他用途,而不是显示在View中,请查看『自定义Target』章节。

Bitmap 复用

为了减少垃圾回收,你可以说使用BitmapPool接口来释放不想要的Bitmap或者复用存在的Bitmap。一个在Transformation中复用Bitmap典型的例子:从pool中获取Bitmap,使用该Bitmap创建一个Canvas,然后使用Matrix/Paint/Shader来变换图像并绘制到Canvas上。为了正确有效地在Transformation中复用Bitmap中,遵守下面的规则:

  1. transform()不要回收资源或者把Bitmap放入Bitmap池中,这些步骤会自动完成。
  2. 如果你从Bitmap池中获取了多个Bitmap,或者没有使用从pool中获取到的Bitmap,确保把多余的Bitmap放回pool中。
  3. 如果你的Trasformation并没有替换调原始图片(比如,图片已经满足你要求的大小,直接返回了),请在transform()方法中返回原始的资源或者Bitmap。

一个典型的用法如下:

protected Bitmap transform(BitmapPool bitmapPool, Bitmap original, int width, int height) {
    Bitmap result = bitmapPool.get(width, height, Bitmap.Config.ARGB_8888);
    // If no matching Bitmap is in the pool, get will return null, so we should allocate.
    if (result == null) {
        // Use ARGB_8888 since we're going to add alpha to the image.
        result = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
    }
    // Create a Canvas backed by the result Bitmap.
    Canvas canvas = new Canvas(result);
    Paint paint = new Paint();
    paint.setAlpha(128);
    // Draw the original Bitmap onto the result Bitmap with a transformation.
    canvas.drawBitmap(original, 0, 0, paint);
    // Since we've replaced our original Bitmap, we return our new Bitmap here. Glide will
    // will take care of returning our original Bitmap to the BitmapPool for us.  
    return result;
}