一篇文章让你彻底搞懂Material Design

Material Design越来越流行了,然而从来没有人整理一份比较好的MD 学习文档,而自己也不怎么熟悉,所以这篇文档就诞生了。

声明: 本文是参考郭神出版的《Android第二行代码》第12章Material Design实战编写,在此基础上做了一些取舍与提起。

转载请标明出处:
http://blog.csdn.net/u014702332/article/details/53731511
本文出自:【扫地僧的博客】

1. ToolBar

使用ToolBar需要注意以下几点

1. 主题需要修改一下,需要继承NoActionBar,而不要用DarkActionBar,这样会导致ActionBar重复,程序崩溃

2. 颜色样式 :

     1. colorPrimary   指定标题栏背影色
     2. colorPrimaryDrak   指定状态栏颜色
     3. textColorPrimary   指定标题文字颜色
     4. windowBackground   背景色
     5. navigationBarColor 指定状态导航条颜色
     6. colorAccent  比较特殊,指定浮动按钮颜色  


    <!--<style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar"> -->
    <style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">
        <!-- Customize your theme here. -->
        <item name="colorPrimary">@color/colorPrimary</item>
        <item name="colorPrimaryDark">@color/colorPrimaryDark</item>
        <item name="colorAccent">@color/colorAccent</item>
    </style>

效果图

3. 注意引用主题 theme popupTheme


<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent">


    <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:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"
        />
</FrameLayout>

看起来非常单调,这个时候我要插入按钮了。

4.插入菜单按钮


<?xml version="1.0" encoding="utf-8"?>
<menu
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    >

    <item
        android:id="@+id/back_up"
        android:icon="@drawable/ic_backup"
        android:title="back up"
        app:showAsAction="always"
        />

    <item
        android:id="@+id/delete"
        android:icon="@drawable/ic_delete"
        android:title="delete"
        app:showAsAction="ifRoom"
        />

    <item
        android:id="@+id/settings"
        android:icon="@drawable/ic_settings"
        android:title="settings"
        app:showAsAction="never"
        />

</menu>

  1. always 表示永远显示,如果屏幕空间不够则不显示
  2. ifRoom 表示屏幕空间足够的情况下显示在ToolBar中,不够就显示在菜单中。
  3. never 则表示永远显示在菜单中。
  4. 注意 ToolBar中的action按钮只会显示按钮,菜单中的action按钮,只会显示文字

效果图
5.菜单的点击事件

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


    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        switch (item.getItemId()) {

            case R.id.back_up:
                Toast.makeText(this, "You clicked Backup", Toast.LENGTH_SHORT).show();
                break;
            case R.id.delete:
                Toast.makeText(this, "You clicked Delete", Toast.LENGTH_SHORT).show();
                break;
            case R.id.settings:
                Toast.makeText(this, "You clicked Settings", Toast.LENGTH_SHORT).show();
                break;
            default:
        }
        return true;
    }

当然ToolBar功能远不止这些,我这里只是列出常用的功能。一般项目够用。

2. 滑动菜单

2.1 DrawerLayout

用法:首先他是一个布局,在布局中允许放入2个直接子控件,第一个子控件是主屏幕显示的内容,第二个子控件是滑动菜单中显示的内容

<?xml version="1.0" encoding="utf-8"?>
<android.support.v4.widget.DrawerLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/drawer_layout"
    android:layout_width="match_parent"
    android:layout_height="match_parent">


    <FrameLayout

        android:layout_width="match_parent"
        android:layout_height="match_parent">


        <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:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar" />
    </FrameLayout>


    <TextView
        android:id="@+id/tv_menu"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_gravity="start"
        android:text="this is menu"
        android:textSize="30sp"
        android:background="#FFF"

        />
</android.support.v4.widget.DrawerLayout>

这里需要指定下TextView的 android:layout_gravity=”start” 告诉滑动菜单是在屏幕左边,还是右边,left,表示在左边,right在右边,这里我用start,会根据系统语言来从左往右。

但是这样弄完还有一个缺陷,用户可能不知道有这个侧滑菜单,所以我们需要添加一个按钮来告诉用户,官方推荐是在导航栏加入一个按钮。

      drawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
        ActionBar actionBar = getSupportActionBar();
        if (null != actionBar){
            actionBar.setDisplayHomeAsUpEnabled(true);
            actionBar.setHomeAsUpIndicator(R.drawable.ic_menu);
        }
    }

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


    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        switch (item.getItemId()) {

            case android.R.id.home:
                drawerLayout.openDrawer(GravityCompat.START);
                break;

2.2 NavigationView

但上面的菜单栏显示与我们实际想要的效果还差很完,还好官方提供了Navigation控件,让我们很好的把菜单栏处理一下,几行代码就可以集成。

<?xml version="1.0" encoding="utf-8"?>
<android.support.v4.widget.DrawerLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/drawer_layout"
    android:layout_width="match_parent"
    android:layout_height="match_parent">


    <FrameLayout

        android:layout_width="match_parent"
        android:layout_height="match_parent">


        <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:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar" />
    </FrameLayout>

    <android.support.design.widget.NavigationView
        android:id="@+id/nav_view"
        android:layout_gravity ="start"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        app:menu="@menu/nav_menu"
        app:headerLayout="@layout/header_layout"

        />

</android.support.v4.widget.DrawerLayout>

官方提供了NavigationView控件,我们只需要指定app:menu与app:headerLayout就可以设置菜单栏与头部栏目。

nav_menu布局文件如下:

<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
    <group android:checkableBehavior="single">

        <item
            android:id="@+id/nav_call"
            android:icon="@drawable/nav_call"
            android:title="call" />
        <item
            android:id="@+id/nav_friends"
            android:icon="@drawable/nav_friends"
            android:title="friends" />
        <item
            android:id="@+id/nav_location"
            android:icon="@drawable/nav_location"
            android:title="location" />
        <item
            android:id="@+id/nav_mail"
            android:icon="@drawable/nav_mail"
            android:title="mail" />
        <item
            android:id="@+id/nav_task"
            android:icon="@drawable/nav_task"
            android:title="task" />


    </group>
</menu>

以及header_layout.xml布局如下:

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

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="180dp"
    android:background="?attr/colorPrimary"
    android:padding="10dp">


    <de.hdodenhof.circleimageview.CircleImageView
        android:id="@+id/icon_image"
        android:layout_width="70dp"
        android:layout_height="70dp"
        android:layout_centerInParent="true"
        android:src="@drawable/nav_icon" />

    <TextView
        android:id="@+id/username"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentBottom="true"
        android:text="tonygreendev@gmail.com"
        android:textColor="#FFF"
        android:textSize="14sp" />

    <TextView
        android:id="@+id/mail"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_above="@id/username"
        android:text="Tony Green"
        android:textColor="#FFF"
        android:textSize="14sp" />

</RelativeLayout>

这里写图片描述

3.悬浮按钮和可交互提示

3.1 FloatingActionButton

这个按钮感觉用处好像和普通按钮没有多大区别,不知道官方为什么会弄这个这样的按钮,完全必要似的啊,但不管吧,也给大家看一下

这里面布局文件有一个属性 android:elevation=”8dp” 指定高度值,高度值越大,投资范围越大,感觉没有什么用似的。直接用默认的就够了。

直接上代码吧:


    <FrameLayout

        android:layout_width="match_parent"
        android:layout_height="match_parent">


        <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:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar" />


        <android.support.design.widget.FloatingActionButton
           android:id="@+id/fab"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_margin="16dp"
            android:src="@drawable/ic_done"
            android:layout_gravity="bottom|end"
            android:elevation="8dp"
            />


    </FrameLayout>


        final FloatingActionButton floatingActionButton = (FloatingActionButton) findViewById(R.id.fab);
        floatingActionButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Toast.makeText(A12Activity.this, "Fab click", Toast.LENGTH_SHORT).show();
            }
        });

3.2 Snackbar

首先要明确的是SnackBar并不是Toast的替代器,他们两者之间有不同的应用场景,Toast的作用是告诉用户现在发生了什么事件,但同时用户只能被动接收这个事情,而SnackBar除了有Toast显示 的功能外,还可以在这基础上做其它的操作,打比方,我删除了一条数据,用SnackBar可以撤销这个操作。
具体用法如下,非常简单:


        Snackbar.make(view,"Data delete!",Snackbar.LENGTH_LONG)
                .setAction("撤销",new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Snackbar.make(view,"撤销了",Snackbar.LENGTH_LONG).show();
            }
        }).show();

感觉比Toast好看些,另外如果你需要在这基础上作撤销操作,可以setAction。 个人感觉这个setAction并无卵用。

这里写图片描述

另外我们这个时候发现,SnackBar弹出View把悬浮按钮挡住了,效果不好看,好在Material Design给出了解决方案,这就是,CoordinatorLayout

3.3 CoordinatorLayout

CoordinatorLayout 可以说是一个加强版的FrameLayout,在普通情况下的作用和FrameLayout基本一致,事实上CoordinatorLayout可以监听其所有了控件的各种事件,然后自动帮助我们做出最为合理的响应。举个简单例子,弹出SnackBar提示将悬浮按钮遮挡住了,如果我们让CoordinatorLayout监听到SnackBar的弹出事件,那么它会自动将内部的FloatingActionButton身上偏移,从而确保不会被SnackBar遮挡.
直接用CoordinatorLayout来替换FrameLayout就好了:

...
    <android.support.design.widget.CoordinatorLayout

        android:layout_width="match_parent"
        android:layout_height="match_parent">


        <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:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar" />


        <android.support.design.widget.FloatingActionButton
           android:id="@+id/fab"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_margin="16dp"
            android:src="@drawable/ic_done"
            android:layout_gravity="bottom|end"
            android:elevation="8dp"
            />


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

下面我写了两份基本相同的代码SnackBar中传入的第一个参数,做了改动,如果用drawerLayout,,他不是CoordinatorLayout的子控件,所以无法坚挺变化,这个时候悬浮按钮还是会被挡住。

                Snackbar.make(drawerLayout,"Data delete!",Snackbar.LENGTH_LONG)
                        .setAction("撤销",new View.OnClickListener() {
                            @Override
                            public void onClick(View view) {
                                Snackbar.make(drawerLayout,"撤销了",Snackbar.LENGTH_LONG).show();
                            }
                        }).show();

                Snackbar.make(view,"Data delete!",Snackbar.LENGTH_LONG)
                        .setAction("撤销",new View.OnClickListener() {
                            @Override
                            public void onClick(View view) {
                                Snackbar.make(view,"撤销了",Snackbar.LENGTH_LONG).show();
                            }
                        }).show();

4. 卡片式布局

4.1 CardView

CardView也是一个FrameLayout,只是额外提供了圆角和阴影等效果。这里没有什么好讲的,贴代码吧。


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

<android.support.v7.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android"

    xmlns:app="http://schemas.android.com/apk/res-auto"

    android:orientation="vertical"

    android:layout_width="match_parent"

    android:layout_height="match_parent"

    app:cardCornerRadius="4dp"

    android:elevation="5dp"

    >

    <TextView

        android:id="@+id/tv_info"

        android:layout_width="match_parent"

        android:layout_height="wrap_content" />



</android.support.v7.widget.CardView>

app:cardCornerRadius属性指定卡片圆角的弧度,数值越大,弧度越大,另外还可以通过app:elevation属性来指定卡片的高度,高度数值越大,投影ailfbn越大,但是投影效果越淡,高度值越小,投影范围也越小,但是投影效果越浓。

4.2 AppBarLayout

上面会造成RecyclerView把ToolBar挡住,由于RecyclerView和ToolBar都是放在CoordinatorLayout中的,我们知道CoordinatorLayout就是一个加强版的FrameLayout,在不进行明确定位的情况下,默认都会放在左上角,从而产生遮挡。由于我们使用的是CoodinatorLayout,而不是FrameLayout所以我们有更加巧妙的解决办法。
好在官方也给出方案使用AppBarLayout,它实际上是一个垂直方向的LinearLayout,它在内部做了很多滚动事件的封装,并应用了Material Design设计理念
我们现在来解决之前覆盖的问题

  1. 将ToolBar嵌套到AppBarLayout中,
  2. 给RecyclerView指定一个布局行为, app:layout_behavior=”@string/appbar_scrolling_view_behavior”。
  3. 但这还没有完,还需要在ToolBar中添加一个属性 app:layout_scrollFlags=”scroll|enterAlways|snap”
    1. scroll 表示当RecyclerView身上滚动的时候,ToolBar会跟着向上滚动并实现隐藏
    2. enterAlways 表示当RecyclerView向下滚动的时候,ToolBar会跟着一起向下滚动,并重新显示
    3. snap表示当ToolBar还没有完全隐藏或者显示的时候,会根据当前滚动的距离,自动选择隐藏还是显示

代码如下:


    <android.support.design.widget.CoordinatorLayout

        android:layout_width="match_parent"

        android:layout_height="match_parent">



        <android.support.design.widget.AppBarLayout

            android:layout_width="match_parent"

            android:layout_height="wrap_content">



            <android.support.v7.widget.Toolbar

                android:id="@+id/toolbar"

                android:layout_width="match_parent"

                android:layout_height="?attr/actionBarSize"

                android:background="?attr/colorPrimary"

                android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"

                app:popupTheme="@style/ThemeOverlay.AppCompat.Light"

                app:layout_scrollFlags="scroll|enterAlways|snap" />

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

        <android.support.v7.widget.RecyclerView
            android:id="@+id/recycler_view"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            app:layout_behavior="@string/appbar_scrolling_view_behavior"
            />
            ...

这里写图片描述

5 下拉刷新

这个控件算是我们比较常用的控件了,但这里我是需要再做一下说明


        <android.support.design.widget.AppBarLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content">

            <android.support.v7.widget.Toolbar
                android:id="@+id/toolbar"
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                android:background="?attr/colorPrimary"
                android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"
                app:popupTheme="@style/ThemeOverlay.AppCompat.Light"
                app:layout_scrollFlags="scroll|enterAlways|snap" />
        </android.support.design.widget.AppBarLayout>

        <android.support.v4.widget.SwipeRefreshLayout
            android:id="@+id/swipe_refresh"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            app:layout_behavior="@string/appbar_scrolling_view_behavior">

            <android.support.v7.widget.RecyclerView
                android:id="@+id/recycler_view"
                android:layout_width="match_parent"
                android:layout_height="match_parent" />
        </android.support.v4.widget.SwipeRefreshLayout>

这里需要注意一下由于RecyclerView变成了SwipeRefreshLayout的子控件了,所以之前使用的app:layout_behavior 声明布局行为也要列表SwipeRefreshLayout中才行
这里我需要说明几个SwipeRefreshLayout所用到的方法

  1. setColorSchemeResources(R.color.colorPrimary); 来设置下拉刷新的颜色
  2. setOnRefreshListener 来做下拉刷新监听。
  3. 最后需要设置setRefreshing(false) 来结束刷新事件,并隐藏刷新进度条。

代码如下:

    private SwipeRefreshLayout swipeRefresh;
        swipeRefresh = (SwipeRefreshLayout) findViewById(R.id.swipe_refresh);
        swipeRefresh.setColorSchemeResources(R.color.colorPrimary);
        swipeRefresh.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
            @Override
            public void onRefresh() {
                refreshFruits();
            }
        });
    }

    private void refreshFruits() {
        new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    Thread.sleep(2000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                runOnUiThread(new Runnable() {
                    @Override
                    public void run() {
                        initFruits();
                        adapter.notifyDataSetChanged();
                        swipeRefresh.setRefreshing(false);
                    }
                });
            }
        }).start();
    }

6 可折叠式标题栏

6.1 CollapsingToolBarLaout

  1. 顾名思义 CollapsingToolBarLayout是一个作用于ToolBar基础之上的布局,他不能独立存在的,
  2. 它在设计的时候就被限定只能作为AppBarLayout的直接子布局来使用,而AppBarLayout又必须是CoodinatorLayout的子布局。

所以我们可以这么表现他们的层级
   CoodinatorLayout
        AppBarLayout
             CollapsingToolBarLayout             

<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:orientation="vertical" 
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <android.support.design.widget.AppBarLayout
        android:id="@+id/appbar"
        android:layout_width="match_parent"
        android:layout_height="250dp">

        <android.support.design.widget.CollapsingToolbarLayout
            android:id="@+id/collapsing_toolbar"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:theme="@style/ThemeOverlay.AppCompat.ActionBar"
            app:contentScrim="?attr/colorPrimary"
            app:layout_scrollFlags="exitUntilCollapsed|scroll"
            >

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

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

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

对上述代码解释

  1. android:theme 指定了一个主题,
  2. app:contentScrim=”?attr/colorPrimary” 用于指定CollapsingToolbarLayout在趋于折叠状态以驻折叠之后的背影色,其实,CollapsingToolbarLayout 在折叠之后就是一个普通的ToolBar,那么背景色应该是colorPrimary
  3. app:layout_scrollFlags=”exitUntilCollapsed|scroll” scroll表示CollapsingToolbarLayout会随着滚动完成折叠之后留在界面上,不再移出屏幕。4

另外:

<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:orientation="vertical"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <android.support.design.widget.AppBarLayout
        android:id="@+id/appbar"
        android:layout_width="match_parent"
        android:layout_height="250dp">

        <android.support.design.widget.CollapsingToolbarLayout
            android:id="@+id/collapsing_toolbar"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:theme="@style/ThemeOverlay.AppCompat.ActionBar"
            app:contentScrim="?attr/colorPrimary"
            app:layout_scrollFlags="exitUntilCollapsed|scroll"
            >


            <ImageView
                android:id="@+id/iv_img"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:scaleType="centerCrop"
                app:layout_collapseMode="parallax"
                />

            <android.support.v7.widget.Toolbar
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                app:layout_collapseMode="pin"
                />


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

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

</android.support.design.widget.CoordinatorLayout>
  1. 我们可以看到CollapsingToolbarLayout中定义了一个ImageView和Toolbar也就意味着,这个高级版的标题将是由普通的标题栏加上图片组合而成的。
  2. app:layout_collapseMode=”” 指定成pin表示在折叠的过程中位置始终保持不变,而指定成parallax表示会在折叠过程中产生一定的错位偏移。

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_fruit);
        Intent intent = getIntent();
        String fruitName = intent.getStringExtra(FRUIT_NAME);
        int fruitImageId = intent.getIntExtra(FRUIT_IMAGE_ID, 0);
        Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
         CollapsingToolbarLayout collapsingToolbar = (CollapsingToolbarLayout)          findViewById(R.id.collapsing_toolbar);
        ImageView fruitImageView = (ImageView) findViewById(R.id.fruit_image_view);
        TextView fruitContentText = (TextView) findViewById(R.id.fruit_content_text);
        setSupportActionBar(toolbar);
        ActionBar actionBar = getSupportActionBar();
        if (actionBar != null) {
            actionBar.setDisplayHomeAsUpEnabled(true);
        }
        collapsingToolbar.setTitle(fruitName);
        Glide.with(this).load(fruitImageId).into(fruitImageView);
        String fruitContent = generateFruitContent(fruitName);
        fruitContentText.setText(fruitContent);
    }

    private String generateFruitContent(String fruitName) {
        StringBuilder fruitContent = new StringBuilder();
        for (int i = 0; i < 500; i++) {
            fruitContent.append(fruitName);
        }
        return fruitContent.toString();
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        switch (item.getItemId()) {
            case android.R.id.home:
                finish();
                return true;
        }
        return super.onOptionsItemSelected(item);
    }

说明

  1. collapsingToolbar.setTitle()设置标题,
  2. 获取ActionBar,并且使 actionBar.setDisplayHomeAsUpEnabled(true); 因为默认图标就是一个返回剪头,所以无需另外设置。

这里写图片描述

6.2 充分利用系统状态栏空间

我们发现背景图片与系统的状态栏总有一些不搭的感觉,这时我们可以融合一下就好了。
只给ImageView设置


<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:orientation="vertical"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:fitsSystemWindows="true"
    >

    <android.support.design.widget.AppBarLayout
        android:id="@+id/appbar"
        android:layout_width="match_parent"
        android:layout_height="250dp"
        android:fitsSystemWindows="true"
        >

        <android.support.design.widget.CollapsingToolbarLayout
            android:id="@+id/collapsing_toolbar"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:theme="@style/ThemeOverlay.AppCompat.ActionBar"
            app:contentScrim="?attr/colorPrimary"
            app:layout_scrollFlags="exitUntilCollapsed|scroll"
            android:fitsSystemWindows="true"
            >


            <ImageView
                android:id="@+id/iv_img"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:scaleType="centerCrop"
                android:fitsSystemWindows="true"
                app:layout_collapseMode="parallax"
                android:src="@drawable/nav_friends"
                />

            <android.support.v7.widget.Toolbar
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                app:layout_collapseMode="pin"
                />

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

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

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

为了图片与状态栏融合需要做以下几条:

  1. 把Imageview以及其父控件的属性 android:fitsSystemWindows=”true” 全部设置为true
  2. 还必须把程序的主题中状态栏颜色指定成透明色,android:statusBarColor 属性指定成透明 @android:color/transparent就可以,但问题在于android:statusBarColor的属性是从API21,也就是5.0系统 才有的。如果实现差异性功能呢。

右击res目录-》new–>Directory创建values-v21目录 然后创建一个styles.xml

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

    <style name="FruitActivityTheme" parent="AppTheme">
        <item name="android:statusBarColor">@android:color/transparent</item>
    </style>

</resources>

专门指定了一个FruitActivityTheme主题,给FruitActivity使用。由于values-v21目录只有Android5.0及以上系统才会读取,因此不会有问题。

另外还需要兼容5.0以前的版本,因为5.0之前的系统无法指定状态栏颜色,因此wftcbn不用设置

<resources>

    <!-- Base application theme. -->
    <style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">
        <!-- Customize your theme here. -->
        <item name="colorPrimary">@color/colorPrimary</item>
        <item name="colorPrimaryDark">@color/colorPrimaryDark</item>
        <item name="colorAccent">@color/colorAccent</item>
    </style>

    <style name="FruitActivityTheme" parent="AppTheme">
    </style>

</resources>

代码地址

注:效果图片是事后才补上的,mac上没有找到好的做Gif图工具,当时就没有做,另外gif图片比较大,后面几张图不怎么好看,凑合着看一下吧

评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值