2019-10-30 自定义轮播图

构思:

轮播图-生活-高清完整正版视频在线观看-优酷

明确目标:

根据录制的视频,先明确轮播图的实际效果,视频中图片定时切换的控件是实现轮播图的关键,那么根据对控件的了解,我们猜测实现这一实际效果的控件和viewpager十分相似,viewpager是一个可以滑动页面的控件,那么结合我们的实际情况进行对比,发现需要在viewpager已知的功能上实现:1、定时切换图片2、添加图片上的文字和圆点3、可以向左右随意滑动切换图片(viewpager在第一张图片时向右滑动不了)。4、设置图片的点击监听事件。

功能实现:

1、新建一个android项目,默认生成一个MainActivity继承自AppCompatActivity,实现方法onCreate,这一步默认会实现,你会发现默认加载了一个启动布局:activity_main.xml

@Override

protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

    setContentView(R.layout.activity_main);


}

2、我们首先开始在activity_main下写布局,需要写viewpager控件、textview控件和Linearlayout三个控件,分别放图片、文字、圆点,根据实际效果分析,他们是层叠的,所以用帧布局,布局代码如下:

<?xml version="1.0" encoding="utf-8"?>

<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"

    android:layout_width="match_parent"

    android:layout_height="190dp"

    android:orientation="vertical">

<android.support.v4.view.ViewPager

        android:id="@+id/viewpager"

        android:layout_width="match_parent"

        android:layout_height="match_parent"

        android:background="@color/colorAccent" />

<LinearLayout

    android:layout_width="match_parent"

    android:layout_height="25dp"

    android:orientation="horizontal"

    android:layout_gravity="bottom"

    android:gravity="center_vertical"

    android:background="#33000000"

    >

<TextView

        android:id="@+id/textView"

        android:layout_width="wrap_content"

        android:layout_height="wrap_content"

        android:text="@string/title"

        android:textColor="#ffffffff"

        android:layout_gravity="left"

        android:layout_marginLeft="10dp"

        />

<LinearLayout

        android:id="@+id/dotView"

        android:layout_width="match_parent"

        android:layout_height="wrap_content"

        android:orientation="horizontal"

        android:gravity="right"

        android:layout_marginRight="30dp"

        />

</LinearLayout>

</FrameLayout>

3、初始化布局控件到MainActivity类中,代码如下:

@Override

protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

    setContentView(R.layout.activity_main);

    viewPager = findViewById(R.id.viewpager);

    dotViews = findViewById(R.id.dotView);

    textView = findViewById(R.id.textView);

}

4、实现viewpager放置图片,手动滑动切换图片,此时第一张图片向右是不可滑动的:

viewPager.setAdapter(new MyAdapter(imageViews));//viewPager是控件;new MyAdapter(imageViews)看成是数据,实际是自定义适配器,里面可以理解为处理图片数据的一个机制,处理好了放viewPager控件上显示图片

5、自定义MyAdapter适配器,理解成:实现图片数据处理机制,自定义MyAdapter适配器代码如下:

public class MyAdapter extends PagerAdapter {

private ArrayList arrayList;

    public MyAdapter(ArrayList arrayList) {

this.arrayList = arrayList;

    }

@Override

    public int getCount() {

//设置可视图数量

        return Integer.MAX_VALUE;

    }

@Override

    public boolean isViewFromObject(View view, Object object) {

return view == object;//object是承载图片的控件imageView,父控件是View

    }

@Override

    public ObjectinstantiateItem(ViewGroup container, int position) {

//给container添加内容~图片

        container.addView(arrayList.get(position %arrayList.size()));

        return arrayList.get(position %arrayList.size());

    }

@Override

    public void destroyItem(ViewGroup container, int position, Object object) {

//  super.destroyItem(container, position, object);

//销毁对应位置上的object

            container.removeView((View) object);

    }

}

6、添加图片资源到一个int数组,R.drawable.timg, R.drawable.timg1, R.drawable.timg2,R.drawable.timg1是res/drawable文件下的图片资源,将数组转成集合传到MyAdapter适配器:

public class MainActivity extends AppCompatActivity {


    private int[]imagers;


    @Override

    protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

imagers =new int[]{R.drawable.timg, R.drawable.timg1, R.drawable.timg2,R.drawable.timg1};

ArrayList <ImageView >    imageViews =new ArrayList <ImageView > ();

ImageView imageView;

for (int i =0; i<imagers.length;i++){

imageView =new ImageView(MainActivity.this);

    imageView.setBackgroundResource(imagers[i]);

    imageViews.add(imageView);


}



}


}


小结:目前viewpager控件显示图片了,可以滑动切换显示图片了。

下一目标:让图片定时切换

1、onCreate函数下开线程设置定时器,代码如下:

new Thread() {

public void run() {

boolean running =true;

        while (running) {

try {

Thread.sleep(5000);//5S切换下一张图片

            }catch (InterruptedException e) {

e.printStackTrace();

            }

runOnUiThread(new Runnable() {

@Override

                public void run() {

viewPager.setCurrentItem(viewPager.getCurrentItem() +1);//当前图片为下一张图片,即实现了图片的切换

                }

});

        }

}

}.start();

下一目标:实现向右滑动切换功能,代码如下:

// 把ViewPager设置为默认选中Integer.MAX_VALUE / t2,从十几亿次开始轮播图片,达到无限循环目的(那么我们开始看到的第一张图片就是第十几亿次的图片,从而达到向右滑动的目的);

int m = (Integer.MAX_VALUE /2) %imageViews.size();

int currentPosition = Integer.MAX_VALUE /2 - m;

viewPager.setCurrentItem(currentPosition);

下一目标:添加文字:

public class MainActivityextends AppCompatActivity {

private TextView textView;

private String[] textString;

@Override

protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

    setContentView(R.layout.activity_main);

    textView = findViewById(R.id.textView);

textString =new String[]{

"text1", "text2", "text3","text4"

};

textView.setText(textString[0]);//默认设置显示为:text1

//viewpager切换时,文字显示对应也完成切换

viewPager.setOnPageChangeListener(new ViewPager.OnPageChangeListener() {

@Override

    public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {

// Toast.makeText(MainActivity.this,"onPageScrolled",Toast.LENGTH_LONG).show();

    }

@Override

    public void onPageSelected(int position) {

//Toast.makeText(MainActivity.this,"onPageSelected",Toast.LENGTH_LONG).show();

        int currentPage = position %imageViews.size();//记录切换后的当前页的index

        textView.setText(textString[currentPage]);//根据当前页的index取对应的文字显示,完成图片文字的同步显示

    }

@Override

    public void onPageScrollStateChanged(int state) {

//Toast.makeText(MainActivity.this,"onPageScrollStateChanged",Toast.LENGTH_LONG).show();

    }

});

}

}

下一目标:添加圆点:

1、将两种颜色的图片添加到项目,顾名思义,一张是显示的灰色圆点,一张是白色的(选中状态):

2、设置圆形图片切换的状态,选中时为白色,默认为灰色,新建dot.xml文件,代码如下:

<?xml version="1.0" encoding="utf-8"?>

<selector xmlns:android="http://schemas.android.com/apk/res/android">

    <item android:drawable="@drawable/white_dot" android:state_enabled="true"/>

    <item android:drawable="@drawable/gray_dot"  android:state_enabled="false"/>

</selector>

3、实现切换页面时,小圆点切换同步显示:

public class MainActivityextends AppCompatActivity {

private LinearLayout dotViews;

private int defaultPage =0;

@Override

    protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_main);

    dotViews = findViewById(R.id.dotView);

//因为图片切换时,圆点对应切换,所以图片的张数决定圆点的个数,将圆点的图片放在for循环下面生成viewpager图片张数的圆点控件View,添加到LinearLayout控件,圆点图片默认为禁止选中状态,为灰色

for (int i =0; i <imagers.length; i++){

    layoutParams =new LinearLayout.LayoutParams(30, 30);//控件大小设置

    dotView =new View(this);//承载显示圆点图片的控件

    dotView.setBackgroundResource(R.drawable.dot);//状态切换

    dotView.setEnabled(false);//禁止选中状态

    dotViews.addView(dotView, layoutParams);//将控件View添加到LinearLayout

}

dotViews.getChildAt(0).setEnabled(true);//显示第一个圆点为选中状态,白色

viewPager.setOnPageChangeListener(new ViewPager.OnPageChangeListener() {

@Override

    public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {

// Toast.makeText(MainActivity.this,"onPageScrolled",Toast.LENGTH_LONG).show();

    }

@Override

    public void onPageSelected(int position) {

//Toast.makeText(MainActivity.this,"onPageSelected",Toast.LENGTH_LONG).show();


//ViewPager切换的过程,比如说:默认第一个圆点是选中状态为白色,对应第一个页面index=0,现在由第一个页面切换到第二个页面index=1,会触发到onPageSelected这个函数,切换的过程要实现如下代码操作

        int currentPage = position %imageViews.size();

//切换后的页面,当前页index

        dotViews.getChildAt(defaultPage).setEnabled(false);

//将index=0的第一个页面的圆点变成未选中状态,灰色

        dotViews.getChildAt(currentPage).setEnabled(true);;

//将index=1的页面的圆点变成选中状态,白色

        defaultPage = currentPage;

//记录index=1的页面为默认页面(第一个页面index=0),为了完成下一页面的切换index=2的页面为下一个切换后的页面(相当于上一个步骤(index为0和1页面的切换)的index=1)

    }

@Override

    public void onPageScrollStateChanged(int state) {

//Toast.makeText(MainActivity.this,"onPageScrollStateChanged",Toast.LENGTH_LONG).show();

    }

});

}


小结:目前完成页面切换后小圆点切换的同步,小圆点选中的状态是白色,其余小圆点都为灰色,一次只有一个小圆点为选中状态显示为白色



下一目标:设置每一张图片的点击监听事件:

具体实现:

1、添加pages.xml文件,目的是为了添加id值:


代码:

<?xml version="1.0" encoding="utf-8"?>

    <item name="pager_img1" type="id"/>

    <item name="pager_img2" type="id"/>

    <item name="pager_img3" type="id"/>

    <item name="pager_img4" type="id"/>

    <item name="pager_img5" type="id"/>

</resources>



2、因为图片显示控件是动态添加的,所以没有对应的控件ID,需要动态添加控件id,并且需要与各个图片一一对应,
public class MainActivityextends AppCompatActivity {

private int[] imagerId;

@Override

    protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_main);

imagerId=new int[]{

        R.id.pager_img1,

        R.id.pager_img2,

        R.id.pager_img3,

        R.id.pager_img4,

        R.id.pager_img5

};

ImageView imageView;

for (int i =0; i <imagers.length;i++){

imageView =new ImageView(MainActivity.this);

//图片添加到ImageView 控件已经省略,上面步骤已经实现

    imageView.setId(imagerId[i]);//图片控件和id同步

    imageView.setOnClickListener(new pagerOnClickListener(MainActivity.this));//设置图片点击监听

    imageViews.add(imageView);

}

}

}

3、设置图片点击监听事件类,代码如下,具体业务逻辑在各个case下面写,目前显示的是一个弹窗窗口:


public class pagerOnClickListener implements View.OnClickListener{

Contextm  Context;

    public pagerOnClickListener(Context mContext){

this.mContext=mContext;

    }

@Override

    public void onClick(View v) {

switch (v.getId()) {

case R.id.pager_img1:

Toast.makeText(mContext, "图片1被点击", Toast.LENGTH_SHORT).show();

break;

            case R.id.pager_img2:

Toast.makeText(mContext, "图片2被点击", Toast.LENGTH_SHORT).show();

break;

            case R.id.pager_img3:

Toast.makeText(mContext, "图片3被点击", Toast.LENGTH_SHORT).show();

break;

            case R.id.pager_img4:

Toast.makeText(mContext, "图片4被点击", Toast.LENGTH_SHORT).show();

break;

            case R.id.pager_img5:

Toast.makeText(mContext, "图片5被点击", Toast.LENGTH_SHORT).show();

break;

        }

}

}


总结:目前所有功能都已经实现了,您弄懂了吗?

 

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 206,126评论 6 481
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 88,254评论 2 382
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 152,445评论 0 341
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 55,185评论 1 278
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 64,178评论 5 371
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,970评论 1 284
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,276评论 3 399
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,927评论 0 259
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 43,400评论 1 300
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,883评论 2 323
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,997评论 1 333
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,646评论 4 322
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,213评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,204评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,423评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,423评论 2 352
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,722评论 2 345

推荐阅读更多精彩内容