/**
* Returns an immutable bitmap from subset of the source bitmap,
* transformed by the optional matrix. The new bitmap may be the
* same object as source, or a copy may have been made. It is
* initialized with the same density as the original bitmap.
*
* If the source bitmap is immutable and the requested subset is the
* same as the source bitmap itself, then the source bitmap is
* returned and no new bitmap is created.
*
* @param source The bitmap we are subsetting
* @param x The x coordinate of the first pixel in source
* @param y The y coordinate of the first pixel in source
* @param width The number of pixels in each row
* @param height The number of rows
* @param m Optional matrix to be applied to the pixels
* @param cm Color matrix to be applied to the pixels
* @param filter true if the source should be filtered.
* Only applies if the matrix contains more than just
* translation.
* @return A bitmap that represents the specified subset of source
* @throws IllegalArgumentException if the x, y, width, height values are
* outside of the dimensions of the source bitmap, or width is <= 0,
* or height is <= 0
*/
public static Bitmap createBitmap(Bitmap source, int x, int y, int width, int height,
Matrix m,ColorMatrix cm, boolean filter) {
checkXYSign(x, y);
checkWidthHeight(width, height);
if (x + width > source.getWidth()) {
throw new IllegalArgumentException("x + width must be <= bitmap.width()");
}
if (y + height > source.getHeight()) {
throw new IllegalArgumentException("y + height must be <= bitmap.height()");
}
if (!source.isMutable() && x == 0 && y == 0 && width == source.getWidth() &&
height == source.getHeight() && (m == null || m.isIdentity())) {
return source;
}
int neww = width;
int newh = height;
Canvas canvas = new Canvas();
Bitmap bitmap;
Paint paint;
Rect srcR = new Rect(x, y, x + width, y + height);
RectF dstR = new RectF(0, 0, width, height);
Config newConfig = Config.ARGB_8888;
final Config config = source.getConfig();
// GIF files generate null configs, assume ARGB_8888
if (config != null) {
switch (config) {
case RGB_565:
newConfig = Config.RGB_565;
break;
case ALPHA_8:
newConfig = Config.ALPHA_8;
break;
//noinspection deprecation
case ARGB_4444:
case ARGB_8888:
default:
newConfig = Config.ARGB_8888;
break;
}
}
if (m == null || m.isIdentity()) {
bitmap = Bitmap.createBitmap(neww, newh, newConfig);
paint = null; // not needed
} else {
final boolean transformed = !m.rectStaysRect();
RectF deviceR = new RectF();
m.mapRect(deviceR, dstR);
neww = Math.round(deviceR.width());
newh = Math.round(deviceR.height());
bitmap = Bitmap.createBitmap(neww, newh, transformed ? Config.ARGB_8888 : newConfig);
canvas.translate(-deviceR.left, -deviceR.top);
canvas.concat(m);
paint = new Paint();
paint.setColorFilter(new ColorMatrixColorFilter(cm));
paint.setFilterBitmap(filter);
if (transformed) {
paint.setAntiAlias(true);
}
}
// The new bitmap was created from a known bitmap source so assume that
// they use the same density
bitmap.setDensity(source.getDensity());
bitmap.setHasAlpha(source.hasAlpha());
bitmap.setPremultiplied(source.isPremultiplied());
canvas.setBitmap(bitmap);
canvas.drawBitmap(source, srcR, dstR, paint);
canvas.setBitmap(null);
return bitmap;
}
/**
* Common code for checking that x and y are >= 0
*
* @param x x coordinate to ensure is >= 0
* @param y y coordinate to ensure is >= 0
*/
private static void checkXYSign(int x, int y) {
if (x < 0) {
throw new IllegalArgumentException("x must be >= 0");
}
if (y < 0) {
throw new IllegalArgumentException("y must be >= 0");
}
}
/**
* Common code for checking that width and height are > 0
*
* @param width width to ensure is > 0
* @param height height to ensure is > 0
*/
private static void checkWidthHeight(int width, int height) {
if (width <= 0) {
throw new IllegalArgumentException("width must be > 0");
}
if (height <= 0) {
throw new IllegalArgumentException("height must be > 0");
}
}
BitMap同时绘制Matrix和ColorMatrix
最新推荐文章于 2018-04-09 14:26:19 发布
该代码段展示了如何从源Bitmap中创建一个不可变的子集Bitmap,并可选地应用矩阵和颜色矩阵变换。如果源Bitmap不可变且请求的子集与源Bitmap相同,则直接返回源Bitmap。同时,检查坐标和尺寸是否在源Bitmap范围内,以防止越界异常。
摘要由CSDN通过智能技术生成