所以我尝试了这里的代码:Creating an ImageView with a mask .我使用以下图像作为原始图像和蒙版:
但是,我得到的结果是这样的:
请注意,窗口背景不是黑色,而是全息光(在银河系中看起来像非常淡的灰色,而不是完全白色)。第二张图片是我在 ListView 中选择项目时得到的结果。
如果我使用相同的算法创建一个新的位图,然后将其传递给 ImageView 而不是覆盖 onDraw(),它会正确绘制:
Canvas canvas = new Canvas();
Bitmap mainImage = //get original image
Bitmap maskImage = //get mask image
Bitmap result = Bitmap.createBitmap(mainImage.getWidth(), mainImage.getHeight(), Bitmap.Config.ARGB_8888);
canvas.setBitmap(result);
Paint paint = new Paint();
paint.setFilterBitmap(false);
canvas.drawBitmap(mainImage, 0, 0, paint);
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.DST_IN));
canvas.drawBitmap(maskImage, 0, 0, paint);
paint.setXfermode(null);
imageView.setImageBitmap(result);
我得到了预期的结果:
请注意淡入淡出已正确应用。这在进行选择时会更加明显。
那么 ImageView 的 onDraw 方法是怎么回事来创建这个黑色背景而不是让窗口背景显示出来呢?有趣的是,如果原始图像本身具有一定的透明度,则尊重该透明度,例如:
我自己想不通。我宁愿能够在 onDraw 上执行此操作,而不是预先创建位图,因为它仅适用于作为源和掩码的位图。我希望能够使用渐变和纯色等其他可绘制对象来做到这一点,但在这些情况下,宽度和高度没有设置。
最佳答案
在研究了所有 stackoverflow 帖子后,我找到了创建没有黑色边框的 mask 的完美组合。它非常适合我的目的。
目前我正在使用一个普通图像和一个 mask 图像(具有透明度的 png)创建一个可拖动 View ,因此我需要覆盖 onDraw 函数。
private Bitmap mImage = ...;
private Bitmap mMask = ...; // png mask with transparency
private int mPosX = 0;
private int mPosY = 0;
private final Paint maskPaint;
private final Paint imagePaint;
public CustomView (final Context context) {
maskPaint = new Paint();
maskPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR));
imagePaint = new Paint();
imagePaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.DST_OVER));
}
/* TODO
if you have more constructors, make sure you initialize maskPaint and imagePaint
Declaring these as final means that all your constructors have to initialize them.
Failure to do so = your code won't compile.
*/
@Override
public void onDraw(Canvas canvas) {
super.onDraw(canvas);
canvas.save();
canvas.drawBitmap(mMask, 0, 0, maskPaint);
canvas.drawBitmap(mImage, mPosX, mPosY, imagePaint);
canvas.restore();
}
关于Android如何在ImageView上应用蒙版?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14801075/