Android 自定义View (四)

本文深入探讨了Android中的Xfermode图像混合模式类及其子类AvoidXfermode的原理与应用,包括如何通过setXferMode方法调整图像绘制效果,同时介绍了AvoidXfermode类的构造方法、参数解释及不同模式下的具体行为,并提供了自定义View的实现案例,旨在帮助开发者掌握图像混合与避免绘图的技术细节。

命运就像自己的掌纹,虽然弯弯曲曲,却永远掌握在自己手中。


本讲内容:Xfermode 图像混合模式类(和ColorFilter有点相似的方法


Xfermode 类的三个子类分别是AvoidXfermode, PixelXorXfermode和PorterDuffXfermode

AvoidXfermode  指定了一个颜色和容差,强制Paint避免在它上面绘图(或者只在它上面绘图)。

PixelXorXfermode  当覆盖已有的颜色时,应用一个简单的像素XOR操作。

PorterDuffXfermode  这是一个非常强大的转换模式,使用它,可以使用图像合成的18条Porter-Duff规则的任意一条来控制Paint如何与已有的Canvas图像进行交互。

要应用转换模式,可以使用setXferMode方法,如下所示:

AvoidXfermode avoid = new AvoidXfermode(Color.BLUE, 10, AvoidXfermode.Mode. AVOID);    borderPen.setXfermode(avoid);


一、AvoidXfermode类(只有一个含参的构造方法

<span style="font-size:18px;">AvoidXfermode(int opColor, int tolerance, AvoidXfermode.Mode mode)</span>

第一个opColor表示一个16进制的可以带透明通道的颜色值例如0x12345678,第二个参数tolerance表示容差值,最后一个参数表示AvoidXfermode的具体模式,其可选值只有两个:AvoidXfermode.Mode.TARGET或者  AvoidXfermode.Mode.AVOID

二者区别:

1、AvoidXfermode.Mode.TARGET:在该模式下Android会判断画布上的颜色是否会有与pColor一样的颜色,如果有,则把该区域“染”上一层我们画笔定义的颜色,否则不“染”色

2、而AVOID是在该模式下Android会判断画布上的颜色是否会有与pColor不一样的颜色,……

示例一:

     

注意:因为这个AvoidXfermode类不支持硬件加速在API 16已经过时(会出现图一效果),如果要使用,必须在应用或手机设置中关闭硬件加速在应用中我们可以通过在AndroidManifest.xml文件中设置application节点下的android:hardwareAccelerated属性为false来关闭硬件加速:

<application  
    android:allowBackup="true"  
    android:hardwareAccelerated="false"  
    android:icon="@drawable/ic_launcher"  
    android:label="@string/app_name"  
    android:theme="@android:style/Theme.Black.NoTitleBar.Fullscreen" >  
    <activity  
        android:name="com.aigestudio.customviewdemo.activities.MainActivity"  
        android:label="@string/app_name" >  
        <intent-filter>  
            <action android:name="android.intent.action.MAIN" />  
  
            <category android:name="android.intent.category.LAUNCHER" />  
        </intent-filter>  
    </activity>  
</application>  

在AndroidManifest.xml文件中关闭硬件加速那么我们整个应用都将不支持硬件加速,这显然是不科学的,如果可以只针对某个View关闭硬件加速那岂不是很好么?当然,Android也给我们提供了这样的功能,我们可以在View中通过

setLayerType(LAYER_TYPE_SOFTWARE, null);  

下面是自定义CustomTitleView.java文件:

public class CustomView extends View {
	private Paint mPaint;// 画笔
	private Context mContext;// 上下文环境引用 
	private Bitmap bitmap;// 位图  
	private AvoidXfermode avoidXfermode;// AV模式 
	
	private int x,y,w,h;// 位图绘制时左上角的起点坐标

	public CustomView(Context context) {
		super(context, null);
	}

	public CustomView(Context context, AttributeSet attrs) {
		super(context, attrs);
		this.mContext = context;

		initPaint();// 初始化画笔
		initRes(context);//初始化资源
	}
	
	//初始化资源 
	private void initRes(Context context) {
		// 获取位图  
		bitmap=BitmapFactory.decodeResource(context.getResources(), R.drawable.p);
		
		 /* 
         * 计算位图绘制时左上角的坐标使其位于屏幕中心 
         * 屏幕坐标x轴向左偏移位图一半的宽度 
         * 屏幕坐标y轴向上偏移位图一半的高度 
         */  
		x=MeasureUtil.getScreenSize((Activity)mContext)[0]/2-bitmap.getWidth()/2;
		y = MeasureUtil.getScreenSize((Activity) mContext)[1] / 2 - bitmap.getHeight() / 2;  
		w = MeasureUtil.getScreenSize((Activity) mContext)[0] / 2 + bitmap.getWidth() / 2;  
	        h = MeasureUtil.getScreenSize((Activity) mContext)[1] / 2 + bitmap.getHeight() / 2;  
	}
	
	// 初始化画笔
	private void initPaint() {
		// 实例化画笔并打开抗锯齿
		mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
		
		//当画布中有跟0XFFFFFFFF(白)色一样的地方时候才“染”色
		//avoidXfermode = new AvoidXfermode(0XFFFFFFFF, 0, AvoidXfermode.Mode.TARGET);
		//当画布中有跟0XFFFFFFFF色相差很100内(有点接近)的地方时候才“染”色
		avoidXfermode = new AvoidXfermode(0XFFFFFFFF, 100, AvoidXfermode.Mode.TARGET);
	}
	
	protected void onDraw(Canvas canvas) {
		super.onDraw(canvas);
		// 绘制位图 从资源获取一个Bitmap绘制在画布上
		canvas.drawBitmap(bitmap, x, y,mPaint);
		// “染”什么色是由我们自己决定的 
		mPaint.setARGB(255, 215, 53, 243);
		// 设置AV模式  
		mPaint.setXfermode(avoidXfermode);
		// 画一个位图大小一样的矩形  
                canvas.drawRect(x, y, w, h, mPaint);  
	}

}

二、PixelXorXfermode类(与AvoidXfermode一样也在API 16过时了,只有一个含参的构造方法

PixelXorXfermode(int opColor)
该类的计算实现公式是:op ^ src ^ dst,像素色值的按位异或运算


Take your time and enjoy it 路过的、学习过的请留个言,顶个呗~~




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值