Material Design:Toolbar的使用

前言:
顾名思义,Toolbar就是应用的工具栏,是android L引入的新控件, 用来替代ActionBar一个Activity可以有多个Toolbar,你也可以把toolbar放在任何位置,因为它是作为一个ViewGroup来定义使用的。
Toolbar配合官方Material Design支持库能展示很酷炫的效果,比如配合AppBar,CoordinatorLayout,NestedScorllView,Collapsing Toolbar Layout等。本文将介绍Toolbar的全方位使用,至于那些酷炫的效果,期待我以后的文章放出吧。
参考文档:

Toolbar.png

(一)建立Toolbar

  • extend AppCompatAcitivity
  • NoActionBar主题
  • setSupportActionBar()
1. 加入v7 appcompat库

在build.gradle(Model:app)中声明

dependencies {
 compile 'com.android.support:appcompat-v7:23.3.0'  
}

2. 继承AppCompatAcitivity

public class MainActivity extends AppCompatActivity {
  // ...
}

3. 设置manifest或styles

在manifest中,把<application>中的主题设置为NoActionBar主题,用以取消系统默认的ActionBar

<application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:supportsRtl="true"
        android:theme="@style/Theme.AppCompat.Light.NoActionBar">
        <!--      ...      -->
</application>

当然,你也可以直接在values/styles定制自己的style,并且在manifest中引用这个style,具体代码如下:

<application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:supportsRtl="true"
        android:theme="@style/AppTheme">
        <!--      ...      -->
</application>
<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,则style中的主题必须定为NoActionBar主题

4. 在layout中加入Toolbar组件

MainActivity的layout布局如下:

<?xml version="1.0" encoding="utf-8"?>   
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"     
        android:layout_width="match_parent"       
        android:layout_height="match_parent"       
        android:orientation="vertical">       
   
        <include layout="@layout/toolbar_layout"/>   
</LinearLayout>

为了方便Toolbar的调用,可以把Toolbar封装成一个单独的layout,并且在需要使用到它的时候在布局中include这个layout,封装的Toolbar layout如下:

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

<android.support.v7.widget.Toolbar      
        xmlns:android="http://schemas.android.com/apk/res/android"      
        xmlns:app="http://schemas.android.com/apk/res-auto"      
        android:id="@+id/toolbar"      
        android:layout_width="match_parent"      
        android:layout_height="?attr/actionBarSize"      
        android:background="?attr/colorPrimary"      
        android:theme="@style/ThemeOverlay.AppCompat.ActionBar"      
        app:popupTheme="@style/ThemeOverlay.AppCompat.Light">  
  
</android.support.v7.widget.Toolbar>

5. 自定义Toolbar

可以自定义Toolbar各个部分的颜色,自定义的地方包括:
Toolbar可以自定义的地方包括:

状态栏颜色(Status Bar/colorPrimaryDark)(只在api21及以上有效)
标题栏背景颜色(ToolBar/colorPrimary)
弹出菜单背景颜色(OptionMenu)
内容区域背景颜色(Background)
导航栏颜色(NavigationBar)(只在api21及以上有效)
标题文字颜色 (TitleBarTextColor/TextColorPrimary)
弹出菜单文字颜色(TextColor)
内容文字颜色(TextColor)
控件颜色(ColorAccent)

自定义toolbar.jpg

可以在res/values/下修改color.xml文件,并添加使用到的颜色建议参考google给出的color style 规范(自备梯子),然后再在Toolbar的布局下添加各项属性。

6. 建立Toolbar

在Activity中的onCreate()方法中,调用setSupportActionBar() 方法建立Toolbar

@Override
 protected void onCreate(Bundle savedInstanceState) {  
        setContentView(R.layout.activity_main);  
        Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);  
        setSupportActionBar(toolbar);   
        //...   
}

通过以上步骤,你已经在Activity中建立了一个Toolbar,这时候你可以通过V7 appcompat支持库的ActionBar类提供的各种实用方法。这种方法可以让你做一些有用的事情,如隐藏和显示应用程序栏。
要使用这些实用方法,需要你调用活动的getsupportactionbar()方法,此方法返回一个appcompat ActionBar对象引用。一旦你获得了该对象引用,你可以调用任何的ActionBar的方法调整应用程序栏。例如,调用ActionBar.hide()方法隐藏应用程序栏,建议可以看一下关于ActionBar类的官方API文档 (自备梯子)。


(二)在Toolbar中添加操作按钮

  • menu
  • onCreateOptionsMenu()
  • onOptionsItemSelected()

1. 添加操作按钮

Toolbar上所有的操作按钮和下拉条目都需要在menu中定义,res/menu/目录下新建一个xml文件,在该文件下定义Toolbar所需要的操作按钮,代码如下:

<menu xmlns:android="http://schemas.android.com/apk/res/android" >   
  
         <!-- "Mark Favorite", should appear as action button if possible --> 
        <item  
                android:id="@+id/action_favorite"  
                android:icon="@drawable/ic_favorite_black_48dp"  
                android:title="@string/action_favorite"  
                app:showAsAction="ifRoom"/>  
   
        <!-- Settings, should always be in the overflow -->  
        <item   
                android:id="@+id/action_settings"   
                android:title="@string/action_settings"   
                app:showAsAction="never"/>
  
</menu>

app:showAsAction属性指定了这个操作按钮是否显示在Toolbar上。 ifRoom作用是:如果Toolbar上有足够的空间,则在Toolbar上显示为一个操作按钮;如果没有足够的空间,则在下拉菜单列表中。never的作用是:设置操作按钮在下拉菜单中显示,而不在Toolbar中显示。

2. 设置操作按钮的监听事件

在menu设置了显示在Toolbar上的item之后,需要把Toolbar和menu关联才能显示定义的item,重写Activity提供的onCreateOptionsMenu()方法可以关联Toolbar和menu。

@Override
public boolean onCreateOptionsMenu(Menu menu) {      
        // Inflate the menu; this adds items to the action bar if it is present.      
        getMenuInflater().inflate(R.menu.menu_main,menu);      
        return true;  
}

这样,你就能在Toolbar上看到你关联的item了,然后重写onOptionsItemSelected()方法就可以对Toolbar的按钮设置监听。

@Override
 protected boolean onOptionsItemSelected(MenuItem item) {  
        Intent intent;  
        switch (item.getItemId()) {  
        case R.id.action_favorite:    
            // User chose the "Favorite" action, mark the current item
            // as a favorite...
            return true;   
        case R.id.action_favorite: 
            // User chose the "Favorite" action, mark the current item    
            // as a favorite...            
            return true;        
        default:            
            // If we got here, the user's action was not recognized.   
            // Invoke the superclass to handle it.            
            return super.onOptionsItemSelected(item);
        }  
}

(三)添加Toolbar的返回按钮

  • getSupportActionBar()
  • setDisplayHomeAsUpEnabled(true)
@Override
 protected void onCreate(Bundle savedInstanceState) {  
        setContentView(R.layout.activity_main);  
        Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);  
        setSupportActionBar(toolbar);     
        if(getSupportActionBar() != null)  
                // Enable the Up button 
                getSupportActionBar().setDisplayHomeAsUpEnabled(true);   
        }
        //...   
}

(四)添加Action View和Action Provider按钮

本节介绍如何添加两种通用组件——action view 和 action provider

action view是一个能提供的丰富功能的组件。例如,搜索视图(search action view)允许用户在Toolbar中输入搜索文本,而不用改变Activity或Fragment。

action provider是一个可定制的布局的组件,当用户点击它,它能控制支配你想以任何方式定义的操作。例如,action provider能够响应一个点击事件来展示菜单项。

安卓的支持库提供了一些专门的action view和action provider。例如,使使用SearchView控件实现搜索查询功能,使用ShareActionProvider控件与其他应用程序共享信息。你也可以定义自己的action view和action provider。

1.action view:

在Toolbar关联的menu中创建新的<item>来添加action view
(1)actionViewClass:实现该控件的类。
(2)actionLayout:描述该空间的布局资源。
设置showAsAction属性为"ifRoom|collapseActionView"或者"never|collapseActionView"。collapseActionView标志指明当用户不再和它交互时控件该如何展示:在Toolbar上以小图标显示,在下拉菜单下以一个菜单项显示。当用户和action view交互时,它将在Toolbar上扩展。
例如下面添加一个SearchView:

<item android:id="@+id/action_search"
     android:title="@string/action_search"
     android:icon="@drawable/ic_search"
     app:showAsAction="ifRoom|collapseActionView"
     app:actionViewClass="android.support.v7.widget.SearchView" />
SearchView.png

如果你需要配置控件,那么在onCreateOptionsMenu()回调函数下,通过调用静态getActionView()方法获取action views的对象引用。例如,下面代码中对SearchView的对象引用:

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    getMenuInflater().inflate(R.menu.main_activity_actions, menu);    
   MenuItem searchItem = menu.findItem(R.id.action_search);  
    SearchView searchView =
             (SearchView)MenuItemCompat.getActionView(searchItem);   
    MenuItemCompat.getActionView(searchItem);
    // Configure the search info and add any event listeners...      
    return super.onCreateOptionsMenu(menu); 
}
响应action view的扩展
  • onMenuItemActionCollapse()
  • onMenuItemActionExpand()

设置监听,当SearchView折叠和扩展时的响应事件,代码如下:

@Override
public boolean onCreateOptionsMenu(Menu menu) { 
     getMenuInflater().inflate(R.menu.options, menu);    
     // Define the listener    
    OnActionExpandListener expandListener = new OnActionExpandListener() {            
        @Override   
        public boolean onMenuItemActionCollapse(MenuItem item) {   
            // Do something when action item collapses      
             return true;     //Return true to collapse action view   
        }
        @Override  
        public boolean onMenuItemActionExpand(MenuItem item) {   
             // Do something when expanded   
             return true;      // Return true to expand action view  
        }   
};
// Get the MenuItem for the action item   MenuItem actionMenuItem = menu.findItem(R.id.myActionItem);    
// Assign the listener to that action item    
MenuItemCompat.setOnActionExpandListener(actionMenuItem, expandListener);    
// Any other things you have to do when creating the options menu…    
return true;  
}

2.action provider:

下面将声明一个ShareActionProvider,这是一种在支持库中定义的允许当前应用与其他应用分享数据的控件,和action view差不多,直接贴代码:

<item android:id="@+id/action_share"        
    android:title="@string/share"    
    app:showAsAction="ifRoom"   
    app:actionProviderClassapp:actionProviderClass="  
    android.support.v7.widget.ShareActionProvider" />

这里不需要为控件声明一个图标,因为ShareActionProvider提供自己的图标。


总结:Toolbar的基本用法差不多到此结束,以后将继续推出有关user interface(用户界面)的文章,刚入门安卓,也是第一次发表文章,有错误请指正,共同进步,与诸君共勉。

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

推荐阅读更多精彩内容