1 前言

之前开发过一个TextView的滚动显示,但是局限性比较大,只能显示文字,不能显示图片等其他View。对比淘宝App的淘宝头条,发现显示的内容挺丰富的。网上搜索了下资料发现android自带的有控件ViewFlipper来实现。于是记录下来。

2 ViewFlipper简介

ViewFlipper是android系统提供的使View滚动的控件,ViewFlipper直译就是View快速滚动。打开源码发现它继承ViewAnimator,而ViewAnimator又继承FrameLayout。因此可以把ViewFlipper当FrameLayout使用。

ViewFlipper的用法如下:

1 常用 xml属性:

android:autoStart:设置是否自动加载下一个View
android:flipInterval:设置View之间切换的时间间隔,单位为ms
android:inAnimation:设置切换View的进入动画
android:outAnimation:设置切换View的退出动画

我的demo用法如下:

            <ViewFlipper
                android:layout_width="match_parent"android:layout_height="wrap_content"android:layout_margin="20dp"android:id="@+id/view_flipper"android:autoStart="true"android:flipInterval="3000"android:inAnimation="@anim/in_animation"android:outAnimation="@anim/out_animation"android:background="#f0fef0"></ViewFlipper>

如上,我们设置为自动加载下一个View,时间间隔为3s,进入和出去的动画为上次滚动TextView的两个动画,详细见我的博客android 自定义View开发实战(五) TextView滚动显示

2 常用方法:

boolean isFlipping(): 判断View切换是否正在进行
void setAutoStart(boolean autoStart):设置是否自动加载下一个View
void setFlipInterval(int milliseconds):设置View之间切换的时间间隔
void startFlipping():开始View的切换,而且会循环进行
void stopFlipping():停止View的切换
void setOutAnimation(Animation outAnimation):设置切换View的退出动画
void setInAnimation(Animation inAnimation):设置切换View的进入动画
void showNext(): 显示ViewFlipper里的下一个View
void showPrevious():显示ViewFlipper里的上一个View

可以看到,基本上对应了xml中的属性。当然,如果你对动画xml比较熟悉,自己可以实现更多好看的效果。

有了以上知识,我们就可以自定义属于自己的广告滚动条了。

3 自定义ViewFlipper的广告条

废话不多说,直接上干活:
xml:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"xmlns:tools="http://schemas.android.com/tools"xmlns:app="http://schemas.android.com/apk/res-auto"android:id="@+id/activity_main"android:layout_width="match_parent"android:layout_height="match_parent"android:orientation="vertical"android:paddingBottom="@dimen/activity_vertical_margin"android:paddingLeft="@dimen/activity_horizontal_margin"android:paddingRight="@dimen/activity_horizontal_margin"android:paddingTop="@dimen/activity_vertical_margin"tools:context="com.qiyei.javatest.MainActivity"><ScrollView
        android:layout_width="match_parent"android:layout_height="match_parent"><LinearLayout
            android:layout_width="match_parent"android:layout_height="wrap_content"android:orientation="vertical"><ViewFlipper
                android:layout_width="match_parent"android:layout_height="wrap_content"android:layout_margin="20dp"android:id="@+id/view_flipper"android:autoStart="true"android:flipInterval="3000"android:inAnimation="@anim/in_animation"android:outAnimation="@anim/out_animation"android:background="#f0fef0"></ViewFlipper><TextView
                android:layout_width="wrap_content"android:layout_height="wrap_content"android:background="@color/colorAccent"android:id="@+id/tv"android:text="Hello World!" /><Button
                android:layout_width="match_parent"android:layout_height="wrap_content"android:id="@+id/button"android:text="测试"/><ImageView
                android:layout_width="wrap_content"android:layout_height="wrap_content"android:id="@+id/imv"/><com.qiyei.javatest.VoiceControlBar
                android:layout_width="300dp"android:layout_height="300dp"android:layout_margin="30dp"app:bottomColor="@color/colorPrimary"app:topColor="@color/colorAccent"app:count="30"app:splitAngle="20"app:circleWidth="5dp"app:bg="@drawable/icon_alipay_main_icon"/><Button
                android:layout_width="match_parent"android:layout_height="wrap_content"android:id="@+id/button2"android:text="测试动画"/></LinearLayout></ScrollView></LinearLayout>

java代码:

public class MainActivity extends AppCompatActivity {private final static String TAG = "MainActivity";private TextView textView;private Button button;private Button button2;private ImageView imageView;private Context context;private ViewFlipper viewFlipper;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);context = this;initView();//put();//get();//removeTestEquals();testObserver();SortUtil.testInsertSort();SortUtil.testShellSort();rxjava();}private void initView() {textView = (TextView) findViewById(R.id.tv);button = (Button) findViewById(R.id.button);imageView = (ImageView) findViewById(R.id.imv);button2 = (Button) findViewById(R.id.button2);button.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View v) {testAnimator();}});button2.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View v) {Intent intent = new Intent(MainActivity.this,TestActivity.class);startActivity(intent);}});viewFlipper = (ViewFlipper) findViewById(R.id.view_flipper);//viewFlipper.addView(view);for (int i = 0;i < 10; i ++){View view = LayoutInflater.from(this).inflate(R.layout.view_advertisement,null);TextView tv1 = (TextView) view.findViewById(R.id.tv1);tv1.setText("这个是支付宝打的广告哈:" + i);TextView tv2 = (TextView) view.findViewById(R.id.tv2);tv2.setText("这个是我打的广告哈:" + i);viewFlipper.addView(view);}viewFlipper.startFlipping();//viewFlipper.stopFlipping();}private void put(){SharedPreferences preferences = getSharedPreferences("test",MODE_PRIVATE);SharedPreferences.Editor editor = preferences.edit();for (int i = 0 ; i < 500 ; i++){editor.putInt("key" + i,2).apply();}//editor.commit();}private void get(){SharedPreferences preferences = getSharedPreferences("test",MODE_PRIVATE);for (int i = 0 ; i < 500 ; i++){String key = "key" + i;Log.d(TAG,"value " + i +":" +preferences.getInt(key,0));}}private void removeTestEquals(){List<Employee> empList = new ArrayList<Employee>();empList.add(new Employee(1,"jack"));Employee emp1 = new Employee(2,"tom");empList.add(emp1);//jackEmployee emp11 = new Employee(1,"jack");//调用的是emp的equals方法empList.remove(emp11);Iterator it = empList.iterator();while(it.hasNext()){Employee emp = (Employee)it.next();System.out.println("name:"+emp.getName());}}private void testObserver(){MyObservable observable = new MyObservable();MyObserver observer1 = new MyObserver("aaaa");MyObserver observer2 = new MyObserver("bbbb");observable.addObserver(observer1);observable.addObserver(observer2);observable.postMessage("news");}private void testAnimator(){
//        ValueAnimator animator = ValueAnimator.ofFloat(0f,20f,10f,-30f);
//        animator.setDuration(6000);
//        animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {//            @Override
//            public void onAnimationUpdate(ValueAnimator animation) {//                textView.setText(""+(float)animation.getAnimatedValue());
//            }
//        });
//        animator.setRepeatCount(3);
//        animator.start();float curTranslationX = textView.getTranslationX();//ObjectAnimator animator = ObjectAnimator.ofFloat(textView,"alpha",1f,0f,1f);ObjectAnimator animator = ObjectAnimator.ofFloat(textView,"translationX",curTranslationX,-500f,curTranslationX);animator.setDuration(2000);animator.start();}/*** 测试 Rxjava的例子*/private void rxjava(){Observer<String> observer = new Observer<String>() {@Overridepublic void onCompleted() {Logger.d("onCompleted");}@Overridepublic void onError(Throwable e) {Logger.d("onError" + e);}@Overridepublic void onNext(String s) {Logger.d(s);}};Subscriber<String> subscriber = new Subscriber<String>() {@Overridepublic void onStart() {super.onStart();}@Overridepublic void onCompleted() {Logger.d("onCompleted");}@Overridepublic void onError(Throwable e) {Logger.d("onError" + e);}@Overridepublic void onNext(String s) {Logger.d(s);}};Observable observable = Observable.create(new Observable.OnSubscribe<String>(){@Overridepublic void call(Subscriber<? super String> subscriber) {subscriber.onStart();subscriber.onNext("hello");subscriber.onNext("world");subscriber.onNext("12345678");subscriber.onCompleted();}});observable.subscribe(observer);observable.subscribe(subscriber);Action0 action0 = new Action0(){@Overridepublic void call() {Logger.d("send OnCompleted");}};Action1<Throwable> onErrorAction = new Action1<Throwable>(){@Overridepublic void call(Throwable throwable) {Logger.d("send throwable");}};Action1<String> stringAction1 = new Action1<String>(){@Overridepublic void call(String s) {Logger.d("send s");}};observable.subscribe(stringAction1);observable.subscribe(stringAction1,onErrorAction);observable.subscribe(stringAction1,onErrorAction,action0);//打印名字String[] names = new String[]{"123","hdhdh","bhsh","shsh","65789"};Observable.from(names).subscribe(new Action1<String>() {@Overridepublic void call(String s) {Log.d(TAG,"call:" + s);}});final int resId = R.drawable.icon_alipay_main_icon;Observable.create(new Observable.OnSubscribe<Drawable>() {@Overridepublic void call(Subscriber<? super Drawable> subscriber) {Drawable drawable = getDrawable(resId);subscriber.onNext(drawable);subscriber.onCompleted();}}).subscribe(new Observer<Drawable>() {@Overridepublic void onCompleted() {Log.d(TAG,"onCompleted");}@Overridepublic void onError(Throwable e) {Log.d(TAG,"onError");}@Overridepublic void onNext(Drawable drawable) {imageView.setImageDrawable(drawable);}});Observable.create(new Observable.OnSubscribe<String>(){@Overridepublic void call(Subscriber<? super String> subscriber) {subscriber.onNext("中国人");}}).subscribeOn(Schedulers.io())     //io线程.observeOn(AndroidSchedulers.mainThread())    //主线程.subscribe(new Observer<String>() {@Overridepublic void onCompleted() {}@Overridepublic void onError(Throwable e) {}@Overridepublic void onNext(String s) {Log.d(TAG,"content:" + s);}});Integer[] array = new Integer[]{1,2,3,4,5,6,7,8,9};Observable.from(array).map(new Func1<Integer, String>() {@Overridepublic String call(Integer i) {return "hello:" + i;}}).subscribe(new Observer<String>() {@Overridepublic void onCompleted() {}@Overridepublic void onError(Throwable e) {}@Overridepublic void onNext(String s) {Log.d(TAG,s);}});}}

需要注意的是,这里我调用了viewFlipper的addView(View view)方法来添加子View,也可以调用void addView(View child, int index, ViewGroup.LayoutParams params)来添加子View。

子View布局:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"android:orientation="vertical" android:layout_width="match_parent"android:layout_height="match_parent"><LinearLayout
        android:layout_width="match_parent"android:layout_height="wrap_content"android:layout_marginTop="10dp"android:orientation="horizontal"><ImageView
            android:layout_width="wrap_content"android:layout_height="wrap_content"android:src="@drawable/icon_alipay_main_icon"/><TextView
            android:layout_width="wrap_content"android:layout_height="wrap_content"android:id="@+id/tv1"android:layout_gravity="center_vertical"android:text="这个是支付宝打的广告哈"/></LinearLayout><LinearLayout
        android:layout_width="match_parent"android:layout_height="wrap_content"android:layout_marginTop="10dp"android:orientation="horizontal"><ImageView
            android:layout_width="wrap_content"android:layout_height="wrap_content"android:src="@drawable/manager"/><TextView
            android:layout_width="wrap_content"android:layout_height="wrap_content"android:id="@+id/tv2"android:layout_gravity="center_vertical"android:text="这个是我打的广告哈"/></LinearLayout></LinearLayout>

最终运行效果如下:

Demo下载

Android控件——ViewFlipper的使用,垂直滚动广告条相关推荐

  1. Android自定义View——仿1号店垂直滚动广告条实现

    效果图 原理分析 整个过程都是基于坐标Y的增加和交换进行处理的,Y值都会一直增加到endY,然后进行交换逻辑 实现步骤 1.初始化变量 由于1号店是两句话的滚动,所以我们也是使用两句话来实现的 pub ...

  2. Android基础控件——ViewFlipper的使用,仿淘宝头条垂直滚动广告条

    ViewFlipper的使用,仿淘宝头条垂直滚动广告条 学习,学习,学以致用 ViewFlipper是安卓自带的控件,很多人可能很少知道这个控件,这个控件很简单,也很好理解,能不能用上实战就看你们的本 ...

  3. Android 垂直滚动广告条,仿淘宝头条垂直滚动展示最新消息

    最新的项目有个新需求,就是要去垂直滚动去展示最新发布的消息,类似淘宝头条的那种 1.功能实现其实很简单,就用到Android 的原生控件ViewFlipper <ViewFlipperandro ...

  4. Android【垂直滚动广告条】仿淘宝头条1号店京东—垂直滚动广告条

    文章为博主原创,欢迎大家进行阅读和转载,转载请注明出处:http://blog.csdn.net/sophie237/article/details/54911349 淘宝头条是淘宝App中很经典的一 ...

  5. 自定义控件(视图)2期笔记03:自定义控件之使用系统控件(优酷案例之广告条Viewpager)...

    1.首先我们看看运行效果,如下: 2. 下面就是详细实现这个效果的过程: (1)新建一个Android工程,命名为"广告条的效果",如下: (2)这里用到一个控件ViewPager ...

  6. Android 原生控件ViewFlipper实现淘宝头条垂直滚动广告条

    showPrevious():          显示ViewFlipper里的上一个View 四.ViewFlipper的详细使用设置View 1.首先在xml中声明ViewFlipper < ...

  7. Android——仿淘宝头条垂直滚动广告

    淘宝App大家用的都比较多了哈,最近看淘宝头条比较多,就来写个小例子吧. 垂直滚动广告的实现原理其实比较简单,就是定时更新列表内容嘛,然后列表切换的时候再加点炫酷的动画就OK了.如果对Android控 ...

  8. android控件属性

    android控件属性 控件属性: android属性 Android功能强大,界面华丽,但是众多的布局属性就害苦了开发者,下面这篇文章结合了网上不少资料, 第一类:属性值为true或false an ...

  9. Android控件布局属性全解(一看就会)

    Android有太多的布局属性繁琐又晦涩,下面结合了网上很多资料汇总. 内容太多,可以Ctrl+F进行搜索 第一类:属性值为true或false android:layout_centerHrizon ...

最新文章

  1. 辽宁鞍山与中国联通签订智慧城市大数据云计算中心项目
  2. java矩阵三元组相减_实现稀疏矩阵(采用三元组表示)的基本运算
  3. 22、UPDATE多表关联更新
  4. 针对Python 实例方法、类方法和静态方法的详解
  5. the code place where the binding is converted to final value displayed in ui
  6. 玩游戏该怎么选择硬盘
  7. 半兽人野性重新觉醒 当初掘金将其放弃 如今野兽感恩回报火箭
  8. 在线CSV转XML/JSON工具
  9. python for mac下载_Python for Mac
  10. Illustrator 教程,如何在 Illustrator 中创建及应用图案?
  11. L2-007 家庭房产 (25 point(s))
  12. IKM 线上测试JavaScript
  13. Manjaro 常用软件安装
  14. 爬虫小练(刷访问量)(python+requests(headers+proxy)+Queue+threading)
  15. SSD接口类型小知识
  16. 斐波那契数列(剑指offer 10-I)
  17. 未授权下载导致的信息泄露
  18. Nacos 常见问题及解决方法
  19. android sdk 需要下载安装哪些
  20. JS escape()和unescape()函数的介绍

热门文章

  1. java http url 401 unauthorized_接口测试:401 Unauthorized
  2. 在windows中,更改计算机的日期和时间的方法有,windows10系统修改时间和日期方法介绍...
  3. 360浏览器非法上传用户隐私全程解析
  4. Java 静态方法读取 yml
  5. Docker+HomeAssistant+HACS+设备接入教程
  6. 通过表单设计器动态生成数据库表以及动态查询的功能实现
  7. 深度学习面经 - Attention、Transformer
  8. CSDN博客访问量问题
  9. 1024程序员节|FFmpeg 调整声道数、采样率、码率
  10. 学习记录671@项目管理之项目收尾管理