CoordinatorLayout嵌套AppBarLayout的使用

CoordinatorLayout嵌套AppBarLayout的使用

实现的效果图:
coordinator

要实现这种联动的效果图,就需要使用CoordinatorLayout,这是一个专门为联动而生的控件。在这种效果图中,我们先来学习下TabLayout的使用。

一、TabLayout的基本使用
1、TabLayout的声明。
public class TabLayout extends HorizontalScrollView

可以看到是继承HorizontalScrollView而开发的一个控件。它就是用来实现我们的顶部Tab页。

2、常用属性。
  • app:tabIndicatorColor:Tab页指示器的颜色
  • app:tabSelectedTextColor:Tab页选中时的颜色
  • app:tabTextColor:Tab页上文本的颜色
  • app:tabMode:Tab页的展示形式,有两种形式:MODE_FIXED、MODE_SCROLLABLE。Fixed是填充模式,也就是默认模式,表示TabLayout不可滚动,其宽度有一个最大值,所有的Tab则会挤在这个宽度中。MODE_SCROLLABLE是可以滚动的,不会拥挤的排在一起。
3、基本使用:

TabLayout的使用,需要添加Tab页进行。这里的Tab类是TabLayout的一个静态内部类,并且其构造方法是包内可访问的,也就是说你无法在外部构造其实例,只能通过TabLayout的newTab方法。

4、简单使用:
    tabLayout = (TabLayout) findViewById(R.id.tabs);

    TabLayout.Tab tabFirst = tabLayout.newTab();
    tabFirst.setText("TabFirst");
    tabLayout.addTab(tabFirst);

    TabLayout.Tab tabSecond = tabLayout.newTab();
    tabSecond.setText("tabSecond");
    tabLayout.addTab(tabSecond);

    TabLayout.Tab tabThird = tabLayout.newTab();
    tabThird.setText("tabThird");
    tabLayout.addTab(tabThird);

效果图:
mobile_tablayout_normal

virtur_easy_test

一个是在我手机真机上的效果,一个是在模拟器上的效果,同样版本的api17,不知道为什么效果差别如此之大。

5、TabLayout结合ViewPager的使用

如果能将TabLayout与ViewPager绑定那效果美的让人难以想象,在也不用那么复杂处理Indicator了。TabLayout中已经给我们提供setupWithViewPager方法让我们来绑定了。

(1)、先来看布局文件:

    <android.support.design.widget.CoordinatorLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
        android:layout_height="match_parent" android:fitsSystemWindows="true"
        tools:context=".MainActivity">

        <android.support.design.widget.AppBarLayout
            android:layout_height="wrap_content"
            android:layout_width="match_parent"
            android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar">

            <android.support.v7.widget.Toolbar
                android:id="@+id/toolbar"
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                android:background="?attr/colorPrimary"
                app:popupTheme="@style/ThemeOverlay.AppCompat.Light"
                app:layout_scrollFlags="scroll|enterAlways"/>
            <android.support.design.widget.TabLayout
                android:id="@+id/tabs"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                app:tabIndicatorColor="#FF0000"
                app:tabSelectedTextColor="#00FF00"
                app:tabTextColor="#FFFFFF"
                app:tabMode="fixed"/>
        </android.support.design.widget.AppBarLayout>

        <android.support.v4.view.ViewPager
            android:id="@+id/viewPager"
            android:layout_height="match_parent"
            android:layout_width="match_parent"
            app:layout_behavior="@string/appbar_scrolling_view_behavior"
            />

        <android.support.design.widget.FloatingActionButton android:id="@+id/fab"
            android:layout_width="wrap_content" android:layout_height="wrap_content"
            android:layout_gravity="bottom|end" android:layout_margin="@dimen/fab_margin"
            android:src="@android:drawable/ic_dialog_email"
            app:borderWidth="0dp"/>

    </android.support.design.widget.CoordinatorLayout>

(2)、在MainActivity中进行处理。

    public class MainActivity extends AppCompatActivity {
        private ViewPager viewPager;
        private TabLayout tabLayout;
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
            setSupportActionBar(toolbar);
            FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
            fab.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View view) {
                    Snackbar.make(view, "Replace with your own action", Snackbar.LENGTH_LONG)
                            .setAction("Action", null).show();
                }
            });

            viewPager = (ViewPager) findViewById(R.id.viewPager);
            viewPager.setAdapter(new PagerAdapter() {

                @Override
                public int getCount() {
                    return 3;
                }

                @Override
                public boolean isViewFromObject(View view, Object object) {
                    return view == object;
                }

                @Override
                public Object instantiateItem(ViewGroup container, int position) {
                    container.addView(new ListViewLayout(getApplication()), position);
                    return container.getChildAt(position);
                }

                @Override
                public void destroyItem(ViewGroup container, int position, Object object) {
                    container.removeViewAt(position);
                }
            });
            initTabLayout();
        }

        private void initTabLayout(){
            tabLayout = (TabLayout) findViewById(R.id.tabs);

            TabLayout.Tab tabFirst = tabLayout.newTab();
            tabFirst.setText("TabFirst");
            tabLayout.addTab(tabFirst);

            TabLayout.Tab tabSecond = tabLayout.newTab();
            tabSecond.setText("tabSecond");
            tabLayout.addTab(tabSecond);

            TabLayout.Tab tabThird = tabLayout.newTab();
            tabThird.setText("tabThird");
            tabLayout.addTab(tabThird);
            tabLayout.setupWithViewPager(viewPager);
        }

        @Override
        public boolean onCreateOptionsMenu(Menu menu) {
            getMenuInflater().inflate(R.menu.menu_main, menu);
            return true;
        }

        @Override
        public boolean onOptionsItemSelected(MenuItem item) {
            int id = item.getItemId();
            if (id == R.id.action_settings) {
                return true;
            }
            return super.onOptionsItemSelected(item);
        }
    }

在上例中我们使用了一个还有ListView的视图View来填充ViewPager。
看下效果图。
viewpager

我们确实实现了效果,但是却没有了Tab页的标题。这是为什么呢?我们需要看下setupWithViewPager(ViewPager viewPager)的源码。

     public void setupWithViewPager(ViewPager viewPager) {
        PagerAdapter adapter = viewPager.getAdapter();
        if(adapter == null) {
            throw new IllegalArgumentException("ViewPager does not have a PagerAdapter set");
        } else {
            this.setTabsFromPagerAdapter(adapter);
            viewPager.addOnPageChangeListener(new TabLayout.TabLayoutOnPageChangeListener(this));
            this.setOnTabSelectedListener(new TabLayout.ViewPagerOnTabSelectedListener(viewPager));
        }
    }

在该方法中首先判断viewPager的adapter是否为null,如果为null抛出异常。所以我们在使用这个方法前,应该给viewpager设置好adapter才行。接着我们看this.setTabsFromPagerAdapter(adapter)这个方法。

    public void setTabsFromPagerAdapter(PagerAdapter adapter) {
        this.removeAllTabs();
        int i = 0;
        for(int count = adapter.getCount(); i < count; ++i) {
            this.addTab(this.newTab().setText(adapter.getPageTitle(i)));
        }
    }

在这个方法中,使用removeAllTabs()方法删除所有的Tab页,然后遍历adapter进行生成tab页,这里调用adapter的getPageTitle方法设置tab页的名称。所以我们的adapter需要重写getPageTitle方法。

由于我们没有重写该方法,所以导致title无法显示,同样,我们也不需要手动添加tab页,只需要在getPageTitle方法中进行判断即可。

修改后的:

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);
        FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
        fab.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Snackbar.make(view, "Replace with your own action", Snackbar.LENGTH_LONG)
                        .setAction("Action", null).show();
            }
        });

        viewPager = (ViewPager) findViewById(R.id.viewPager);
        viewPager.setAdapter(new PagerAdapter() {

            @Override
            public int getCount() {
                return 3;
            }

            @Override
            public boolean isViewFromObject(View view, Object object) {
                return view == object;
            }

            @Override
            public Object instantiateItem(ViewGroup container, int position) {
                container.addView(new ListViewLayout(getApplication()), position);
                return container.getChildAt(position);
            }

            @Override
            public void destroyItem(ViewGroup container, int position, Object object) {
                container.removeViewAt(position);
            }

            @Override
            public CharSequence getPageTitle(int position) {
                if (position % 3 == 0) {
                    return "新闻世界";
                } else if (position % 3 == 1) {
                    return "IT新闻";
                } else {
                    return "Mr_dsw博客";
                }
            }
        });
        tabLayout = (TabLayout) findViewById(R.id.tabs);
        tabLayout.setupWithViewPager(viewPager);
    }

效果图就是这样子。
this

二、CoordinatorLayout的基本使用

仔细的同学,可以看到我们设置了以下属性:

(1)、app:layout_scrollFlags:它有四个值,分别是:

  • scroll: 所有想滚动出屏幕的view都需要设置这个flag, 没有设置这个flag的view将被固定在屏幕顶部。例如,TabLayout 没有设置这个值,将会停留在屏幕顶部。
  • enterAlways: 设置这个flag时,向下的滚动都会导致该view变为可见,启用快速“返回模式”。
  • enterAlwaysCollapsed: 当你的视图已经设置minHeight属性又使用此标志时,你的视图只能已最小高度进入,只有当滚动视图到达顶部时才扩大到完整高度。
  • exitUntilCollapsed: 滚动退出屏幕,最后折叠在顶端。

(2)、app:layout_behavior:为了ToolBar可以滚动,CoordinatorLayout里面,放一个带有可滚动的View.CoordinatorLayout包含的子视图中带有滚动属性的View需要设置app:layout_behavior属性。

但是我们设置了该属性但是依旧无法实现需要的伸缩,后来无果,我将ListView改为RecyclerView,竟然可以滚动了,这点我也不晓得怎么个情况。

看下RecycerView的布局:

    <?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">
        <android.support.v7.widget.RecyclerView
            android:id="@+id/recycler_view"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:scrollbars="vertical"
            />
    </LinearLayout>

我们自定义一个View。

    /**
     * Created by dsw on 2015/11/8.
     */
    public class RecyclerViewLayout extends LinearLayout {
        public RecyclerViewLayout(Context context, AttributeSet attrs) {
            super(context, attrs);
            initView(context);
        }

        public RecyclerViewLayout(Context context) {
            super(context);
            initView(context);
        }

        private void initView(Context context){
            View view = LayoutInflater.from(context).inflate(R.layout.recycler_view,this);
            RecyclerView recyclerView = (RecyclerView) view.findViewById(R.id.recycler_view);
            recyclerView.setLayoutManager(new LinearLayoutManager(getContext()));
            recyclerView.setAdapter(new MyAdapter(context));
        }

        class MyAdapter extends RecyclerView.Adapter<MyAdapter.MyViewHolder>{
            String[] data = new String[]{"A","B","C","D","E",
                    "F","G","H","I","J","K","L","M","N","O","P","Q","R","S","T","U","V","W","Z","Y","Z"};
            Context context;
            public MyAdapter(Context context){
                this.context = context;
            }
            @Override
            public MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
                TextView textView = new TextView(context);
                textView.setTextColor(Color.parseColor("#000000"));
                textView.setTextSize(17*getResources().getDisplayMetrics().scaledDensity);
                textView.setPadding(20,20,20,20);
                return new MyViewHolder(textView);
            }

            @Override
            public void onBindViewHolder(MyViewHolder holder, int position) {
                holder.tv_textView.setText(data[position]);
            }

            @Override
            public int getItemCount() {
                return data.length;
            }

            public class MyViewHolder extends RecyclerView.ViewHolder{
                public TextView tv_textView;
                public MyViewHolder(View itemView) {
                    super(itemView);
                    tv_textView = (TextView) itemView;
                }
            }
        }
    }

我们只需要在PagerAdapter中修改。

     @Override
    public Object instantiateItem(ViewGroup container, int position) {
        container.addView(new RecyclerViewLayout(getApplication()), position);
        return container.getChildAt(position);
    }

这样就可以了。效果图:

result

在来看看模拟器中的怪模样吧!
neusx

源码下载地址:下篇后一起上传吧!

作者:mr_dsw 欢迎转载,与人分享是进步的源泉!

转载请保留地址:http://blog.csdn.net/mr_dsw

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 3
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值