自己本身android不咋地,没事就这里看看,哪里看看,把自己认为不错的写写,上网查点代码,理解理解,这不,今天就写自定义TextView,类似跑马灯效果

要写出带跑马灯效果的TextView,我们的先去了解一下知识:

android shader类 matrix类

shader类专门用来渲染图像以及一些几何图形,shader包含几个直接之类

BitmapShader 渲染图像

LinearGradient 线性渲染

RadialGradient 环形渲染

SweepGradient 梯度渲染

ComposeShader 混合渲染,可以和上面的组合使用

shader类的使用,都需要选构造shader对象,然后通过paint的setshader方法设置渲染对象

这里我们使用LinearGradient

matrix类用来处理图片,matrix是一个3x3的矩阵,有以下类

Translate 平移

Scale 缩放

Rotate 旋转

Skew 错切

这里我们使用Translate

因为我们是自定义TextView,所以我们新建一个CustomTextView,并继承TextView

public class CustomTextView extends TextView {

	public CustomTextView(Context context, AttributeSet attrs, int defStyle) {
		super(context, attrs, defStyle);
	}

	public CustomTextView(Context context, AttributeSet attrs) {
		super(context, attrs);
	}

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

重写onSizeChanged()方法,进行一些对象的初始化操作

@Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
	super.onSizeChanged(w, h, oldw, oldh);

}

接着重写onDraw()方法,效果都在这里实现

@Override
protected void onDraw(Canvas canvas) {
	super.onDraw(canvas);

}

定义一些组件

Paint mPaint;//画笔
int mViewWidth = 0;//当前TextView的宽
LinearGradient mLinearGradient;
Matrix matrix;
int mTranslate = 0;//每次平移距离

初始化我们定义的组件

@Override
	protected void onSizeChanged(int w, int h, int oldw, int oldh) {
		super.onSizeChanged(w, h, oldw, oldh);
		if (mViewWidth == 0) {
			mViewWidth = getMeasuredWidth();//获取当前TextView的宽
			if (mViewWidth > 0) {
				mPaint = getPaint();//获取当前TextView的Paint对象
				mLinearGradient = new LinearGradient(
						0,//开始x位置
						0,//开始y位置
						mViewWidth,//结束x位置,因为我们的textview是横向的,所以只需要设置X就可以
						0, //结束y位置
						new int[]{Color.BLUE,0xffffffff,Color.RED},//渐变的颜色,头颜色,中间色,尾颜色
						null,//颜色分布比例
						Shader.TileMode.MIRROR//渲染方式:CLAMP 渲染器超出原始边界,则复制范围内颜色 MIRROR 以平铺的方式重复渲染  REPEAT 以镜像方式重复渲染
						);
				mPaint.setShader(mLinearGradient);//给paint设置渲染属性
				matrix = new Matrix();//实例化matrix
			}
		}
	}

在onDraw中绘制

@Override
	protected void onDraw(Canvas canvas) {
		super.onDraw(canvas);
		if (matrix != null) {
			mTranslate += mViewWidth/5;//每次平移的距离
			if (mTranslate > 2*mViewWidth) {
				mTranslate =-mViewWidth;
			}
			matrix.setTranslate(mTranslate, 0);//设置平移属性
			mLinearGradient.setLocalMatrix(matrix);//给渲染增加平移动作
			postInvalidateDelayed(100);//每0.1秒更新一次界面
		}
	}

在xml中使用我们自定义的TextView

<lliwei.android.hero.CustomTextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="@string/hello_world"
        android:textSize="30sp" />

效果如下:

Android NestedScrollView 自定义高度_ide

差不多反正就这里意思

完整的代码我贴出来

import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.LinearGradient;
import android.graphics.Matrix;
import android.graphics.Paint;
import android.graphics.RadialGradient;
import android.graphics.Shader;
import android.util.AttributeSet;
import android.widget.TextView;

public class CustomTextView extends TextView {
	
	Paint mPaint;//画笔
	int mViewWidth = 0;//当前TextView的宽
	LinearGradient mLinearGradient;
	RadialGradient mGradient;
	Matrix matrix;
	int mTranslate = 0;//每次平移距离

	public CustomTextView(Context context, AttributeSet attrs, int defStyle) {
		super(context, attrs, defStyle);
	}

	public CustomTextView(Context context, AttributeSet attrs) {
		super(context, attrs);
	}

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

	
	@Override
	protected void onDraw(Canvas canvas) {
		super.onDraw(canvas);
		if (matrix != null) {
			mTranslate += mViewWidth/5;//每次平移的距离
			if (mTranslate > 2*mViewWidth) {
				mTranslate =-mViewWidth;
			}
			matrix.setTranslate(mTranslate, 0);//设置平移属性
			mLinearGradient.setLocalMatrix(matrix);//给渲染增加平移动作
			postInvalidateDelayed(100);//每0.1秒更新一次界面
		}
	}
	
	@Override
	protected void onSizeChanged(int w, int h, int oldw, int oldh) {
		super.onSizeChanged(w, h, oldw, oldh);
		if (mViewWidth == 0) {
			mViewWidth = getMeasuredWidth();//获取当前TextView的宽
			if (mViewWidth > 0) {
				mPaint = getPaint();//获取当前TextView的Paint对象
				mLinearGradient = new LinearGradient(
						0,//开始x位置
						0,//开始y位置
						mViewWidth,//结束x位置,因为我们的textview是横向的,所以只需要设置X就可以
						0, //结束y位置
						new int[]{Color.BLUE,0xffffffff,Color.RED},//渐变的颜色,头颜色,中间色,尾颜色
						null,//颜色分布比例
						Shader.TileMode.MIRROR//渲染方式:CLAMP 渲染器超出原始边界,则复制范围内颜色 MIRROR 以平铺的方式重复渲染  REPEAT 以镜像方式重复渲染
						);
				mPaint.setShader(mLinearGradient);//给paint设置渲染属性
				matrix = new Matrix();//实例化matrix
			}
		}
	}

}