天天看点

使用ViewPager+Fragment来实现带滚动条的多屏滑动-IndicatorFragmentActivity

转载请注明出处:http://blog.csdn.net/singwhatiwanna/article/details/17201587

在android应用中,多屏滑动是一种很常见的风格,博主之前也写过一些多屏滑动的demo,比如滚动banner(http://blog.csdn.net/singwhatiwanna/article/details/8875241)和仿tabhost的控件。这次给大家介绍一种效果更好的风格:带滚动条的多屏滑动,类似于google play里面的风格。如果你看过我之前写的banner,你就会发现那个banner是原生的,没有采用viewpager啥的,所以代码很长,如果采用viewpager,代码就会短很多,但是使用viewpager也有弊端:需要导入android-support-v4.jar、细节无法控制。不过现在情况已经不一样了,android-support-v4中提供了很多实用的功能,以至于现在新建一个android工程默认都会导入这个jar包。那我们就也采用viewpager来做滑动吧。另外一个概念就是fragment和fragmentactivity,fragment是一个特殊的类,有着和activity一致的生命周期和view一致的界面,也就是fragment就等于具有生命周期的view,但是,要注意的是:fragment并不是view,它和view没有继承关系。使用fragment的好处是:fragment可以重用,而且每个fragment可以在内部处理自己的业务就像activity一样,这样模块间耦合较低,比把所有的业务都写在一个activity内部逻辑要清晰很多。还有就是,由于每个模块的业务都在fragment内部来实现,这样activity只要管理好几个fragment就行了,不需要做和业务相关的事情,最后,fragment可以用来做不同分辨率机型的适配。fragment在sdk(android

3.0及更高)和android-support-v4里面都有,但是由于兼容性的问题,我们只能使用android-support-v4里面的fragment,除非你想你的apk只跑在3.0以后的android手机上,fragmentactivity的情况和fragment类似。关于fragment和fragmentactivity,其实有一些基本的用法需要了解一下,但是考虑到fragment不是本文的重点,所以这里就不介绍了,另外,本文只用fragment做了一个简单的界面,大家应该一看就懂,好了,言归正传。

使用ViewPager+Fragment来实现带滚动条的多屏滑动-IndicatorFragmentActivity

viewpagercompat.java:这是一个viewpager的加强类,主要是为了解决滑动冲突的问题。不然的话,在viewpager内部加入listview等可滑动控件,两者之间会产生干扰。

在这里想多说一下,关于此类问题,解决办法是:重写父控件的onintercepttouchevent函数,在move的时候根据需要返回true,比如左右滑动返回true,其他情况均返回false。这样,当左右滑动的时候,由于onintercepttouchevent返回了true,父控件就能处理,其他情况,事件将传递到listview中,listview自身可以处理上下滑动。

[java] view

plaincopy

使用ViewPager+Fragment来实现带滚动条的多屏滑动-IndicatorFragmentActivity
使用ViewPager+Fragment来实现带滚动条的多屏滑动-IndicatorFragmentActivity

public class viewpagercompat extends viewpager {  

    //mviewtouchmode表示viewpager是否全权控制滑动事件,默认为false,即不控制  

    private boolean mviewtouchmode = false;  

    public viewpagercompat(context context, attributeset attrs) {  

        super(context, attrs);  

    }  

    public void setviewtouchmode(boolean b) {  

        if (b && !isfakedragging()) {  

            //全权控制滑动事件  

            beginfakedrag();  

        } else if (!b && isfakedragging()) {  

            //终止控制滑动事件  

            endfakedrag();  

        }  

        mviewtouchmode = b;  

    /** 

     * 在mviewtouchmode为true的时候,viewpager不拦截点击事件,点击事件将由子view处理 

     */  

    @override  

    public boolean onintercepttouchevent(motionevent event) {  

        if (mviewtouchmode) {  

            return false;  

        return super.onintercepttouchevent(event);  

    public boolean ontouchevent(motionevent ev) {  

        try {  

            return super.ontouchevent(ev);  

        } catch (exception e) {  

     * 在mviewtouchmode为true或者滑动方向不是左右的时候,viewpager将放弃控制点击事件, 

     * 这样做有利于在viewpager中加入listview等可以滑动的控件,否则两者之间的滑动将会有冲突 

    public boolean arrowscroll(int direction) {  

        if (mviewtouchmode) return false;  

        if (direction != focus_left && direction != focus_right) return false;  

        return super.arrowscroll(direction);  

}  

下面两个文件代码有点多,没有粘出来,后面附有下载地址,大家可以下载下来看看,代码都做了注释的。有什么疑问欢迎交流。

titleindicator.java:这个一个带滚动条的选项卡,会随着viewpager的滑动而滑动,其实现思想是这样的:每个选项卡是一个view,根据需要可以add多个view也就是多个选项卡进来,选项卡下部还有一个滚动条,滚动条是用canvas画出来的。所有的invalidate方法均会触发ondraw,当页面滚动的时候,会有一个滚动距离,然后ondraw被触发后,就会在新位置重新画上滚动条(其实就是画线)。

indicatorfragmentactivity.java:这是indicatorfragmentactivity的主界面,用于管理上述两个view,对子类提供protected abstract int supplytabs(list<tabinfo> tabs)接口来生成页面。

下面主要介绍下如何使用这个indicatorfragmentactivity。

请按如下步骤:

使用ViewPager+Fragment来实现带滚动条的多屏滑动-IndicatorFragmentActivity
使用ViewPager+Fragment来实现带滚动条的多屏滑动-IndicatorFragmentActivity

public class mainactivity extends indicatorfragmentactivity {  

    public static final int fragment_one = 0;  

    public static final int fragment_two = 1;  

    public static final int fragment_three = 2;  

    protected void oncreate(bundle savedinstancestate) {  

        super.oncreate(savedinstancestate);  

    //在这里提供数据来进行初始化  

    protected int supplytabs(list<tabinfo> tabs) {  

        tabs.add(new tabinfo(fragment_one, getstring(r.string.fragment_one),  

                fragmentone.class));  

        tabs.add(new tabinfo(fragment_two, getstring(r.string.fragment_two),  

                fragmenttwo.class));  

        tabs.add(new tabinfo(fragment_three, getstring(r.string.fragment_three),  

                fragmentthree.class));  

        //返回的下标表示界面初始化的时候所指向的fragment的序号  

        return fragment_two;  

最简单的fragment,啥都不做,就加载一个layout然后初始化一个listview。其实我的demo里有3个界面一样的fragment,但是博主为了偷懒,直接写了一个basefragment,让它们3个都继承这个basefragment,反正界面都一样嘛。

使用ViewPager+Fragment来实现带滚动条的多屏滑动-IndicatorFragmentActivity
使用ViewPager+Fragment来实现带滚动条的多屏滑动-IndicatorFragmentActivity

public class basefragment extends fragment {  

    protected view mmainview;  

    protected static arraylist<map<string, object>> mlistitems;  

    protected context mcontext;  

    static {  

        mlistitems = new arraylist<map<string, object>>();  

        for (int i = 0; i < 20; i++) {  

            map<string, object> map = new hashmap<string, object>();  

            map.put("name", "name#" + i);  

            map.put("sex", i % 2 == 0 ? "male" : "female");  

            mlistitems.add(map);  

    public basefragment() {  

        super();  

    public void onattach(activity activity) {  

        super.onattach(activity);  

        mcontext = activity.getapplicationcontext();  

    public view oncreateview(layoutinflater inflater, viewgroup container, bundle savedinstancestate) {  

        mmainview = inflater.inflate(r.layout.fragment_one, container, false);  

        listview listview = (listview) mmainview.findviewbyid(r.id.list);  

        simpleadapter adapter = new simpleadapter(mcontext, mlistitems,  

                r.layout.listview_item, new string[] {  

                        "name", "sex"  

                }, new int[] {  

                        r.id.name, r.id.download  

                });  

        listview.setadapter(adapter);  

        return mmainview;  

这样就ok了,是不是挺简单的,也就是说,如果你想要这种效果的话,只要导入ui包里面的3个类,然后再按上述2个步骤去做就行了,效果也是很好的。另外就是选项卡的颜色以及滚动条的颜色都是可以调的,而且每个选项卡上面是支持显示其他标识的,比如一个小红点啥的,就类似于那种有新消息的状态。有什么问题,欢迎大家在下面留言和我交流。

使用ViewPager+Fragment来实现带滚动条的多屏滑动-IndicatorFragmentActivity

代码下载:http://download.csdn.net/detail/singwhatiwanna/6680173

继续阅读