Android 可以自定义速度的跑马灯效果
16lz
2021-01-23
android:singleLine="true" android:ellipsize="marquee" android:focusable="true"
这三个属性就可以实现跑马灯的效果,但是这种做法只适用于一个TextView,如果想让两个以上的TextView跑起来就需要自定义TextView。
让两个以上的TextView以默认的滚动方式、滚动速度跑起来很简单,只需要在自定义TextView中重写isFocused方法,然后将返回值改为true,代码如下:
public class CarouselTextView extends TextView{ public CarouselTextView(Context context) { super(context); } public CarouselTextView(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); } public CarouselTextView(Context context, AttributeSet attrs) { super(context, attrs); } /** * 获取焦点,不重写不能滚动 */ @Override public boolean isFocused() { return true; }
布局如下:
其中android:marqueeRepeatLimit="marquee_forever" 这个属性是设置无限重复,如果不设置的话,默认会在3次之后停止不动了。
android.widget.TextView类里设置的属性如下:
private int mMarqueeRepeatLimit = 3;/** * Sets how many times to repeat the marquee animation. Only applied if the * TextView has marquee enabled. Set to -1 to repeat indefinitely. * * @see #getMarqueeRepeatLimit() * * @attr ref android.R.styleable#TextView_marqueeRepeatLimit */ public void setMarqueeRepeatLimit(int marqueeLimit) { mMarqueeRepeatLimit = marqueeLimit; }
下面再来说说自定义速度的跑马灯效果:
其实,跑马灯效果就是不断的滚动位置,而自定义速度的跑马灯就是以自定义的时间间隔去滚动位置,明白了这个思想之后,做起来就比较的简单了。
首先以自定义的时间间隔去滚动位置,就需要不断地执行滚动的操作,所以我们可以用一个线程来执行这个滚动的操作,这里用的方法是实现Runnable接口,重写run方法来实现的。
/** * 执行滚动 */ @Override public void run() { Log.d(TAG, "run"); currentScrollX += speed; // 滚动速度每次加几个点 scrollTo(currentScrollX, 0); // 滚动到指定位置 if(isStop){ return; } if(currentScrollX >= endX){ // 如果滚动的位置大于最大限度则滚动到初始位置 scrollTo(firstScrollX, 0); currentScrollX = firstScrollX; // 初始化滚动速度 postDelayed(this, SCROLL_DELAYED); // SCROLL_DELAYED毫秒之后重新滚动 }else { postDelayed(this, delayed); // delayed毫秒之后再滚动到指定位置 } }
其次,在显示TextView控件的过程中,会有一些回调方法,而滚动的属性和参数都需要进行初始化,所以,我们可以通过这些回调方法中进行初始化操作。代码如下:
@Override protected void onTextChanged(CharSequence text, int start, int lengthBefore, int lengthAfter) { super.onTextChanged(text, start, lengthBefore, lengthAfter); Log.d(TAG , "onTextChanged"); isStop = true; // 停止滚动 this.removeCallbacks(this); // 清空队列 currentScrollX = firstScrollX; // 滚动到初始位置 this.scrollTo(currentScrollX, 0); super.onTextChanged(text, start, lengthBefore, lengthAfter); // 需要重新设置参数 isFirstDraw = true; isStop = false; postDelayed(this, SCROLL_DELAYED); }@Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); if (isFirstDraw) { Log.d(TAG , "isFirstDraw=="+isFirstDraw); getTextWidth(); firstScrollX = getScrollX(); // 获取第一次滑动的X轴距离 System.out.println("firstScrollX======"+firstScrollX); currentScrollX = firstScrollX; mWidth = this.getWidth(); // 获取文本宽度,如果文本宽度大于屏幕宽度,则为屏幕宽度,否则为文本宽度 Log.d(TAG , "mWidth======"+mWidth); endX = firstScrollX + textWidth - mWidth/2; // 滚动的最大距离,可根据需要来定 Log.d(TAG , "endX========"+endX); isFirstDraw = false; } }
另外将一些滚动速度的一些属性和控制滚动速度的操作贴出来:
private static final String TAG = "CarouselTextView"; private int currentScrollX = 0; // 当前滚动位置 X轴 private int firstScrollX = 0; // 初始位置 private boolean isStop = false; // 开始停止的标记 private int textWidth; // 文本宽度 private int mWidth = 0; // 控件宽度 private int speed = 2; // 默认是两个点 private int delayed = 1000; // 默认是1秒 private int endX; // 滚动到哪个位置 private boolean isFirstDraw=true; // 当首次或文本改变时重置 private static final int SCROLL_DELAYED = 4 * 1000;/** * @param 滚动速度 */ public void setSpeed(int speed) { this.speed = speed; } /** * @param 滚动时间间隔 */ public void setDelayed(int delayed) { this.delayed = delayed; } /** * 开始滚动 */ public void startScroll() { isStop = false; this.removeCallbacks(this); // 清空队列 postDelayed(this, SCROLL_DELAYED); // 4秒之后滚动到指定位置 } /** * 停止滑动 */ public void stopScroll() { isStop = true; } /** * 从头开始滑动 */ public void startFor(){ currentScrollX = 0; // 将当前位置置为0 startScroll(); }
最后贴上布局设置:
效果图如下:
test.gif注意:如果设置了android:marqueeRepeatLimit="marquee_forever"属性之后,所有的速度设置都是无效的。
做这个效果之前,本人在网上找了许多篇博客,上面的这些代码也是从别人的博客中找来的,然后根据自己的理解,写下这个博客,给大家做个参考,如果有说的不对的地方,欢迎指出。
更多相关文章
- android studio修改配置文件(.android .gradle .AndroidStudio)
- 浅析Android位置权限以及数组寻找索引的坑
- Android 动态布局 动态生成 销毁控件 改变控件的位置等
- Android 获取View的位置参数:x,y和相对父容器的偏移量以及中心点
- Android自定义对话框(Dialog)位置,大小
- android位置服务
- Android arm模拟器的速度提升方法
- Android 自定义dialog 设置宽度
- Android PopupWindow显示位置和显示大小