Android 一步步教你從ActionBar遷移到ToolBar

希爾瓦娜斯女神發表於2015-08-17

谷歌的材料設計也釋出了有一段時間了,包括官方的support庫 相信大家也熟悉了不少,今天就把actionbar 遷移到toolbar的 經驗發出來。

這個地方要注意 我用的圖示都是studio裡的一個外掛提供的,我隨便選的圖示,大家知道意思就行 不要在意圖示的意義。。。。。。美術不好 見諒。。

先上一個actionbar的demo,裡面基本上包括了actionbar的主要功能點。

比如 選單,二級選單,一鍵返回主介面,action provider,tab,和searchview的結合 等。

 

主介面的程式碼:

 1 package com.example.administrator.actionbartest;
 2 
 3 import android.app.ActionBar;
 4 import android.app.Activity;
 5 import android.os.Bundle;
 6 import android.view.Menu;
 7 import android.view.MenuItem;
 8 import android.widget.Toast;
 9 
10 public class MainActivity extends Activity {
11 
12 
13     @Override
14     protected void onCreate(Bundle savedInstanceState) {
15         super.onCreate(savedInstanceState);
16         setContentView(R.layout.activity_main);
17         getActionBar().setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
18         ActionBar.Tab tab1 = getActionBar().newTab().setText("藝術家").setTabListener(new TabListener<AritistFragment>(this, "artist", AritistFragment.class));
19         ActionBar.Tab tab2 = getActionBar().newTab().setText("專輯名").setTabListener(new TabListener<AlbumFragment>(this, "album", AlbumFragment.class));
20         ActionBar.Tab tab3 = getActionBar().newTab().setText("公司名").setTabListener(new TabListener<CompanyFragment>(this, "company", CompanyFragment.class));
21         getActionBar().addTab(tab1);
22         getActionBar().addTab(tab2);
23         getActionBar().addTab(tab3);
24 
25 
26     }
27 
28     @Override
29     public boolean onCreateOptionsMenu(Menu menu) {
30         // Inflate the menu; this adds items to the action bar if it is present.
31         getMenuInflater().inflate(R.menu.menu_main, menu);
32 
33 
34         return super.onCreateOptionsMenu(menu);
35     }
36 
37 
38     @Override
39     public boolean onOptionsItemSelected(MenuItem item) {
40         // Handle action bar item clicks here. The action bar will
41         // automatically handle clicks on the Home/Up button, so long
42         // as you specify a parent activity in AndroidManifest.xml.
43         int id = item.getItemId();
44         String msg = "";
45         switch (id) {
46             case R.id.action_search:
47                 msg = "action_search";
48                 break;
49             case R.id.action_intent:
50                 msg = "action_intent";
51                 break;
52             case R.id.action_settings:
53                 msg = "action_settings";
54                 break;
55             default:
56                 break;
57 
58         }
59         Toast.makeText(this, msg, Toast.LENGTH_SHORT).show();
60 
61         return super.onOptionsItemSelected(item);
62     }
63 }

manifest檔案

 1 <?xml version="1.0" encoding="utf-8"?>
 2 <manifest xmlns:android="http://schemas.android.com/apk/res/android"
 3     package="com.example.administrator.actionbartest">
 4 
 5     <application
 6         android:allowBackup="true"
 7         android:icon="@mipmap/ic_launcher"
 8         android:label="@string/app_name"
 9         android:logo="@drawable/ic_account_circle_red_300_18dp"
10         android:theme="@android:style/Theme.Holo.Light">
11         <activity
12             android:name=".MainActivity"
13             android:label="@string/app_name">
14             <intent-filter>
15                 <action android:name="android.intent.action.MAIN" />
16 
17                 <category android:name="android.intent.category.LAUNCHER" />
18             </intent-filter>
19         </activity>
20         <activity
21             android:name=".Main2Activity"
22             android:label="@string/title_activity_main2"></activity>
23         <activity
24             android:name=".Main3Activity"
25             android:label="@string/title_activity_main3"
26             android:parentActivityName=".MainActivity">
27 
28         </activity>
29     </application>
30 
31 </manifest>

tablistener

 1 package com.example.administrator.actionbartest;
 2 
 3 import android.app.ActionBar;
 4 import android.app.Activity;
 5 import android.app.Fragment;
 6 import android.app.FragmentTransaction;
 7 
 8 /**
 9  * Created by Administrator on 2015/8/14.
10  */
11 public class TabListener<T extends Fragment> implements ActionBar.TabListener {
12 
13     private Fragment fragment;
14     private final Activity mActivity;
15     private final String mTag;
16     private final Class<T> mClass;
17 
18     public TabListener(Activity mActivity, String mTag, Class<T> mClass) {
19         this.mActivity = mActivity;
20         this.mTag = mTag;
21         this.mClass = mClass;
22     }
23 
24     @Override
25     public void onTabSelected(ActionBar.Tab tab, FragmentTransaction ft) {
26 
27         if (fragment == null) {
28             fragment = Fragment.instantiate(mActivity, mClass.getName());
29             ft.add(android.R.id.content, fragment, mTag);
30 
31         } else {
32             ft.attach(fragment);
33         }
34 
35 
36     }
37 
38     @Override
39     public void onTabUnselected(ActionBar.Tab tab, FragmentTransaction ft) {
40         if (fragment != null) {
41             ft.detach(fragment);
42         }
43     }
44 
45     @Override
46     public void onTabReselected(ActionBar.Tab tab, FragmentTransaction ft) {
47 
48     }
49 }

自定義的actionprovider

 1 package com.example.administrator.actionbartest;
 2 
 3 import android.content.Context;
 4 import android.view.ActionProvider;
 5 import android.view.MenuItem;
 6 import android.view.SubMenu;
 7 import android.view.View;
 8 import android.widget.Toast;
 9 
10 /**
11  * Created by Administrator on 2015/8/14.
12  */
13 public class MyActionProvider extends ActionProvider {
14 
15 
16     private Context context;
17 
18     public MyActionProvider(Context context) {
19         super(context);
20         this.context = context;
21 
22     }
23 
24     @Override
25     public View onCreateActionView() {
26         return null;
27     }
28 
29     @Override
30     public boolean hasSubMenu() {
31         return true;
32     }
33 
34     @Override
35     public void onPrepareSubMenu(SubMenu subMenu) {
36         subMenu.clear();
37         subMenu.add("sub item1").setIcon(R.drawable.ic_queue_black_18dp).setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {
38                                                                                                         @Override
39                                                                                                         public boolean onMenuItemClick(MenuItem item) {
40                                                                                                             Toast.makeText(context, "item1", Toast.LENGTH_SHORT).show();
41 
42                                                                                                             return false;
43                                                                                                         }
44                                                                                                     }
45         );
46 
47         subMenu.add("sub item2").setIcon(R.drawable.ic_account_circle_red_300_18dp).setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {
48                                                                                                                    @Override
49                                                                                                                    public boolean onMenuItemClick(MenuItem item) {
50                                                                                                                        Toast.makeText(context, "item2", Toast.LENGTH_SHORT).show();
51 
52                                                                                                                        return false;
53                                                                                                                    }
54                                                                                                                }
55         );
56 
57 
58         super.onPrepareSubMenu(subMenu);
59     }
60 }

最後是選單佈局

 1 <menu xmlns:android="http://schemas.android.com/apk/res/android"
 2     xmlns:tools="http://schemas.android.com/tools"
 3     tools:context=".MainActivity">
 4 
 5     <item
 6         android:id="@+id/action_search"
 7         android:actionViewClass="android.widget.SearchView"
 8         android:icon="@drawable/ic_queue_black_18dp"
 9         android:showAsAction="ifRoom|collapseActionView"
10         android:title="search" />
11     <item
12         android:id="@+id/action_intent"
13         android:actionProviderClass="com.example.administrator.actionbartest.MyActionProvider"
14         android:icon="@drawable/ic_account_circle_red_300_18dp"
15         android:showAsAction="ifRoom"
16         android:title="share" />
17     <item
18         android:id="@+id/delete"
19         android:icon="@drawable/ic_picture_in_picture_black_18dp"
20         android:showAsAction="ifRoom"
21         android:title="delete" />
22 
23 
24     <!-- 永遠顯示在overflow中-->
25     <item
26         android:id="@+id/action_settings"
27         android:showAsAction="never"
28         android:title="@string/action_settings" />
29 </menu>

 

然後我們來看看toolbar 怎麼做。以及他們之間的區別。實際上你仔細觀察以後就能發現,toolbar 比actionbar 效果更好,尤其是增加了很多動畫效果。

此外toolbar 是沒有tab的,他需要結合support庫裡的tablayout來完成原來actionbar裡的tab功能。除此之外,你在使用toolbar的時候要先遮蔽掉

actionbar否則會報錯。另外就是toolbar實際上放在哪都是可以的,actionbar 則固定在頂端位置。另外就是一些xml檔案的引數在寫的時候要多注意

字首。最後就是同樣一個類 不要用4.x自帶的,要用v4 或者v7的,不然會有很多錯。

主介面程式碼

  1 package com.example.administrator.toolbartest;
  2 
  3 import android.os.Bundle;
  4 import android.support.design.widget.TabLayout;
  5 import android.support.v4.app.Fragment;
  6 import android.support.v4.app.FragmentManager;
  7 import android.support.v4.app.FragmentStatePagerAdapter;
  8 import android.support.v4.view.MenuItemCompat;
  9 import android.support.v4.view.ViewPager;
 10 import android.support.v7.app.AppCompatActivity;
 11 import android.support.v7.widget.Toolbar;
 12 import android.view.Menu;
 13 import android.view.MenuItem;
 14 import android.widget.Toast;
 15 
 16 public class MainActivity extends AppCompatActivity {
 17 
 18     private Toolbar toolbar;
 19 
 20     private TabLayout tabLayout;
 21 
 22 
 23     private ViewPager viewPager;
 24 
 25     private PagerAdapter adapter;
 26 
 27     @Override
 28     protected void onCreate(Bundle savedInstanceState) {
 29         super.onCreate(savedInstanceState);
 30         setContentView(R.layout.activity_main);
 31         toolbar = (Toolbar) this.findViewById(R.id.toolBar);
 32         tabLayout = (TabLayout) this.findViewById(R.id.tabLayout);
 33         tabLayout.addTab(tabLayout.newTab().setText("Tab 1"));
 34         tabLayout.addTab(tabLayout.newTab().setText("Tab 2"));
 35         tabLayout.addTab(tabLayout.newTab().setText("Tab 3"));
 36         tabLayout.setTabGravity(TabLayout.GRAVITY_FILL);
 37         viewPager = (ViewPager) findViewById(R.id.viewpager);
 38         adapter = new PagerAdapter
 39                 (getSupportFragmentManager(), tabLayout.getTabCount());
 40         viewPager.setAdapter(adapter);
 41         viewPager.addOnPageChangeListener(new TabLayout.TabLayoutOnPageChangeListener(tabLayout));
 42         tabLayout.setOnTabSelectedListener(new TabLayout.OnTabSelectedListener() {
 43             @Override
 44             public void onTabSelected(TabLayout.Tab tab) {
 45                 viewPager.setCurrentItem(tab.getPosition());
 46             }
 47 
 48             @Override
 49             public void onTabUnselected(TabLayout.Tab tab) {
 50 
 51             }
 52 
 53             @Override
 54             public void onTabReselected(TabLayout.Tab tab) {
 55 
 56             }
 57         });
 58         toolbar.setTitle("ToolBar");
 59 
 60         setSupportActionBar(toolbar);
 61         //有些語句得寫在setSupportActionBar 之後才有效果
 62 
 63         toolbar.setNavigationIcon(R.drawable.ic_account_circle_red_500_18dp);
 64         toolbar.setOnMenuItemClickListener(new Toolbar.OnMenuItemClickListener() {
 65 
 66 
 67             @Override
 68             public boolean onMenuItemClick(MenuItem menuItem) {
 69                 int id = menuItem.getItemId();
 70                 String msg = "";
 71                 switch (id) {
 72                     case R.id.action_search:
 73                         msg = "action_search";
 74                         break;
 75                     case R.id.action_intent:
 76                         msg = "action_intent";
 77                         //這個地方要注意使用這種方式增加actionprovider不然會報錯
 78                         MenuItemCompat.setActionProvider(menuItem, new MyActionProvider(MainActivity.this));
 79                         break;
 80                     default:
 81                         break;
 82 
 83                 }
 84                 Toast.makeText(MainActivity.this, msg, Toast.LENGTH_SHORT).show();
 85 
 86                 return false;
 87             }
 88         });
 89     }
 90 
 91     class PagerAdapter extends FragmentStatePagerAdapter {
 92 
 93         int numOfTabs;
 94 
 95         public PagerAdapter(FragmentManager fm, int numOfTabs) {
 96             super(fm);
 97             this.numOfTabs = numOfTabs;
 98         }
 99 
100         @Override
101         public Fragment getItem(int position) {
102 
103             switch (position) {
104                 case 0:
105                     TabFragment1 tab1 = new TabFragment1();
106                     return tab1;
107                 case 1:
108                     TabFragment2 tab2 = new TabFragment2();
109                     return tab2;
110                 case 2:
111                     TabFragment3 tab3 = new TabFragment3();
112                     return tab3;
113                 default:
114                     return null;
115             }
116         }
117 
118         @Override
119         public int getCount() {
120             return numOfTabs;
121         }
122     }
123 
124 
125     @Override
126     public boolean onCreateOptionsMenu(Menu menu) {
127         // Inflate the menu; this adds items to the action bar if it is present.
128         getMenuInflater().inflate(R.menu.menu_main, menu);
129         return true;
130     }
131 
132     @Override
133     public boolean onOptionsItemSelected(MenuItem item) {
134         // Handle action bar item clicks here. The action bar will
135         // automatically handle clicks on the Home/Up button, so long
136         // as you specify a parent activity in AndroidManifest.xml.
137 
138         return super.onOptionsItemSelected(item);
139     }
140 }

主介面佈局檔案

 1 <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
 2     xmlns:tools="http://schemas.android.com/tools"
 3     android:layout_width="match_parent"
 4     android:layout_height="match_parent"
 5     tools:context=".MainActivity">
 6 
 7 
 8     <android.support.v7.widget.Toolbar
 9         android:id="@+id/toolBar"
10         android:layout_width="match_parent"
11         android:layout_height="wrap_content"
12         android:background="?attr/colorPrimary"
13         android:minHeight="?attr/actionBarSize"></android.support.v7.widget.Toolbar>
14 
15     <android.support.design.widget.TabLayout
16         android:id="@+id/tabLayout"
17         android:layout_width="match_parent"
18         android:layout_height="wrap_content"
19         android:layout_below="@id/toolBar"
20         android:background="?attr/colorPrimary"></android.support.design.widget.TabLayout>
21 
22     <android.support.v4.view.ViewPager
23         android:id="@+id/viewpager"
24         android:layout_width="match_parent"
25         android:layout_height="match_parent"
26         android:layout_below="@id/tabLayout" />
27 
28 
29 </RelativeLayout>

manifest配置檔案

 1 <?xml version="1.0" encoding="utf-8"?>
 2 <manifest xmlns:android="http://schemas.android.com/apk/res/android"
 3     package="com.example.administrator.toolbartest" >
 4 
 5     <application
 6         android:allowBackup="true"
 7         android:icon="@mipmap/ic_launcher"
 8         android:label="@string/app_name"
 9         android:theme="@style/AppTheme" >
10         <activity
11             android:name=".MainActivity"
12             android:label="@string/app_name" >
13             <intent-filter>
14                 <action android:name="android.intent.action.MAIN" />
15 
16                 <category android:name="android.intent.category.LAUNCHER" />
17             </intent-filter>
18         </activity>
19     </application>
20 
21 </manifest>

用於遮蔽actionbar的style檔案

 1 <resources>
 2 
 3     <!-- Base application theme. -->
 4     <style name="AppTheme" parent="AppTheme.Base">
 5         <!-- Customize your theme here. -->
 6     </style>
 7 
 8     <style name="AppTheme.Base" parent="Theme.AppCompat">
 9         <item name="windowActionBar">false</item>
10         <item name="windowNoTitle">true</item>
11         <!-- Actionbar color -->
12         <item name="colorPrimary">@color/material_blue_grey_800</item>
13         <!--Status bar color-->
14         <item name="colorPrimaryDark">@color/accent_material_light</item>
15         <!--Window color-->
16         <item name="android:windowBackground">@color/dim_foreground_material_dark</item>
17 
18 
19     </style>
20 
21 
22 </resources>

自定義的actionprovider 其實這個和actionbar的那個相比 只是引用的actionprovider不一樣罷了。這個是用的v4包裡的

 1 package com.example.administrator.toolbartest;
 2 
 3 import android.content.Context;
 4 import android.support.v4.view.ActionProvider;
 5 import android.util.Log;
 6 import android.view.MenuItem;
 7 import android.view.SubMenu;
 8 import android.view.View;
 9 import android.widget.Toast;
10 
11 /**
12  * Created by Administrator on 2015/8/14.
13  */
14 public class MyActionProvider extends ActionProvider {
15 
16 
17     private Context context;
18 
19     public MyActionProvider(Context context) {
20         super(context);
21         this.context = context;
22 
23     }
24 
25     @Override
26     public View onCreateActionView() {
27         return null;
28     }
29 
30     @Override
31     public boolean hasSubMenu() {
32         return true;
33     }
34 
35     @Override
36     public void onPrepareSubMenu(SubMenu subMenu) {
37         Log.v("burning","onPrepareSubMenu");
38         subMenu.clear();
39         subMenu.add("sub item1").setIcon(R.drawable.ic_add_shopping_cart_red_500_18dp).setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {
40                                                                                                         @Override
41                                                                                                         public boolean onMenuItemClick(MenuItem item) {
42                                                                                                             Toast.makeText(context, "item1", Toast.LENGTH_SHORT).show();
43 
44                                                                                                             return false;
45                                                                                                         }
46                                                                                                     }
47         );
48 
49         subMenu.add("sub item2").setIcon(R.drawable.ic_assignment_ind_red_500_18dp).setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {
50                                                                                                                    @Override
51                                                                                                                    public boolean onMenuItemClick(MenuItem item) {
52                                                                                                                        Toast.makeText(context, "item2", Toast.LENGTH_SHORT).show();
53 
54                                                                                                                        return false;
55                                                                                                                    }
56                                                                                                                }
57         );
58 
59 
60         super.onPrepareSubMenu(subMenu);
61     }
62 }

然後看一下 選單檔案

 1 <menu xmlns:android="http://schemas.android.com/apk/res/android"
 2     xmlns:app="http://schemas.android.com/apk/res-auto"
 3     xmlns:tools="http://schemas.android.com/tools"
 4     tools:context=".MainActivity">
 5 
 6     <item
 7         android:id="@+id/action_settings"
 8         android:orderInCategory="100"
 9         android:title="@string/action_settings"
10         app:showAsAction="never" />
11 
12     <!-- 注意這個地方searchview的寫法和actionbar的不同 如果用actionbar的寫法會有很多錯誤-->
13     <item
14         android:id="@+id/action_search"
15         android:icon="@drawable/ic_redeem_red_500_18dp"
16         android:title="search"
17         app:actionViewClass="android.support.v7.widget.SearchView"
18         app:showAsAction="ifRoom|collapseActionView" />
19 
20     <item
21         android:id="@+id/action_intent"
22         android:actionProviderClass="com.example.administrator.toolbartest.MyActionProvider"
23         android:icon="@drawable/ic_account_balance_red_500_18dp"
24         app:showAsAction="ifRoom"
25         android:title="share" />
26     <!--
27    <item
28        android:id="@+id/delete"
29        android:icon="@drawable/ic_picture_in_picture_black_18dp"
30        android:showAsAction="ifRoom"
31        android:title="delete" />
32 -->
33 
34 </menu>

基本上就是這些異同了。註釋寫的不多,因為比較簡單。最後如果你要更改一些自定義效果 一定要多看原始碼裡的style檔案

那個裡面包含一切,只是谷歌的話很多你會查不到 因為這東西剛出來不久。

 

相關文章