由於須要封裝toolbar,因此完全的研究了下toolbar, 之前只是簡單用用,如今發現徹底用起來不少坑,總結一下.android
1.NavigationIcon 2.Logo 3.Title 4.subTitle 5.menu. 經常使用的:1,3,5bash
getSupportActionBar()必定要在setSupportActionBar(Toolbar toolbar)以後調用app
//設置是否添加顯示NavigationIcon.若是要用
void setDisplayHomeAsUpEnabled(boolean showHomeAsUp);
//設置NavigationIcon的icon.能夠是Drawable ,也能夠是ResId
void setNavigationIcon(@Nullable Drawable icon);
void setNavigationIcon(@DrawableRes int resId)
//設置NavigationIcon的點擊監聽.
void setNavigationOnClickListener(OnClickListener listener);
複製代碼
Toolbar mToolbar = (Toolbar)findViewById(R.id.toolbar)
//設置Toolbar
setSupportActionBar(mToolbar);
//顯示NavigationIcon,這個方法是ActionBar的方法.Toolbar沒有這個方法.
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
//設置icon
mToolbar.setNavigationIcon(drawable);
//設置監聽.必須在setSupportActionBar()以後調用
mToolbar.setNavigationOnClickListener(clickListener);
複製代碼
1.必須先 setSupportActionBar(mToolbar).ide
2.setDisplayHomeAsUpEnabled(true)是ActionBar的方法.佈局
3.setNavigationOnClickListener()必需要在setSupportActionBar()以後調用才能生效.由於setSupportActionBar(Toolbar),會將Toolbar轉換成Acitionbar.點擊監聽也會從新設置.字體
//是否顯示
getSupportActionBar().setDisplayShowTitleEnabled(boolean showTitle);
//設置title.
getSupportActionBar().setTitle(title);
//設置title.
Toolbar.setTitle(title);
//設置Margin邊距.
Toolbar.setTitleMargin();
//設置字體.
Toolbar.setTitleTextAppearance();
//設置字的顏色
Toolbar.setTitleTextColor(int color);
複製代碼
使用比較簡單.基本看方法名就知道是幹嗎的了.也沒什麼坑. Toolbar直接設置title或者getSupportActionBar()再設置title均可以.ui
這玩意用起來有點蛋疼.坑挺多的.spa
@Override
public boolean onCreateOptionsMenu(Menu menu) {
//寫一個menu的資源文件.而後建立就好了.
getMenuInflater().inflate(R.menu.menu,menu);
return super.onCreateOptionsMenu(menu);
}
<menu 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"
tools:context="com.example.acctionbaractivitydemo.MainActivity">
<item
android:id="@+id/menu1"
//圖標
android:icon="@mipmap/ic_launcher"
//名字
android:title=""
app:showAsAction="withText|ifRoom"/>
<item
android:id="@+id/menu2"
android:icon="@mipmap/ic_launcher"
android:title="哈哈"
app:showAsAction="withText"/>
<item
android:id="@+id/menu3"
android:icon="@mipmap/ic_launcher"
android:title="呵呵"
app:showAsAction="withText"/>
</menu>
//showAsAction這個屬性的值有:
//一、always:使菜單項一直顯示在ToolBar上。
//二、ifRoom:若是有足夠的空間,這個值會使菜單項顯示在ToolBar上。
//三、never:使菜單項永遠都不出如今ToolBar上,在…的子項中顯示。
//四、withText:使菜單項和它的圖標,菜單文本一塊兒顯示。
複製代碼
/**
* 菜單項被點擊時調用,也就是菜單項的監聽方法。
* 經過這幾個方法,能夠得知,對於Activity,同一時間只能顯示和監聽一個Menu 對象.
*/
@Override
public boolean onOptionsItemSelected(MenuItem item) {
return super.onOptionsItemSelected(item);
}
//經過設置toolbar進行監聽,在setSupportActionBar(Toolbar toolbar)以前設置可能會失 效.
Toolbar.setOnMenuItemClickListener(new Toolbar.OnMenuItemClickListener() {
@Override
public boolean onMenuItemClick(MenuItem item) {
return false;
}
});
複製代碼
/**
* 每次菜單被關閉時調用.
*菜單被關閉有三種情形:
*1.展開menu的按鈕被再次點擊
*2.back按鈕被點擊
*3.用戶選擇了某一個菜單項
*/
@Override
public void onOptionsMenuClosed(Menu menu) {
super.onOptionsMenuClosed(menu);
}
/**
* 在onCreateOptionsMenu執行後,菜單被顯示前調用;若是菜單已經被建立,則在菜單顯示前被調用。 一樣的,
* 返回true則顯示該menu,false 則不顯示; (能夠經過此方法動態的改變菜單的狀態,好比加載不一樣的菜單等)
*/
@Override
public boolean onPrepareOptionsMenu(Menu menu) {
return super.onPrepareOptionsMenu(menu);
}
/**
* 顯示menu的icon,經過反射,設置Menu的icon顯示.
* @param view
* @param menu
* @return
*/
@Override
protected boolean onPrepareOptionsPanel(View view, Menu menu) {
if (menu != null) {
if (menu.getClass().getSimpleName().equals("MenuBuilder")) {
try{
Method m = menu.getClass().getDeclaredMethod("setOptionalIconsVisible", Boolean.TYPE);
m.setAccessible(true);
m.invoke(menu, true);
} catch (Exception e) {
Log.e(getClass().getSimpleName(), "onMenuOpened...unable to set icons for overflow menu", e);
}
}
}
return super.onPrepareOptionsPanel(view, menu);
}
複製代碼
基本的配置:3d
<style name="toolbar">
<item name="android:layout_width">match_parent</item>
<item name="android:layout_height">wrap_content</item>
//設置toolbar的最小高度.這樣設置的意義,就是解決適配的問題,標準md高度.
<item name="android:minHeight">?attr/actionBarSize</item>
<item name="android:background">@color/colorPrimary</item>
//設置沉浸式,
<item name="android:fitsSystemWindows">true</item>
</style>
複製代碼
style的有些方法必須是Sdk21以上才能用,因此得這樣code
建立一個values-v21的文件夾,再寫一個style. 還得作一些配置. 普通values中的style改爲以下:
<style name="toolbar">
<item name="android:layout_width">match_parent</item>
<item name="android:layout_height">wrap_content</item>
<item name="android:minHeight">?attr/actionBarSize</item>
<item name="android:background">@color/colorPrimary</item>
<item name="android:fitsSystemWindows">true</item>
</style>
<style name="base_toolbar" parent="toolbar"/>
複製代碼
values-v21中的style以下:
<style name="base_toolbar" parent="@style/toolbar">
<item name="android:elevation">3dp</item>
<item name="android:navigationIcon">?attr/homeAsUpIndicator</item>
</style>
複製代碼
使用這個style
style="@style/base_toolbar"
複製代碼
-----------------------------------------------分割線 -----------------------------------------------
<!-- ToolBar樣式 .-->
<style name="toolbar_theme" parent="@style/ThemeOverlay.AppCompat.Dark">
<item name="android:textSize">18sp</item> <!-- 字體大小-->
</style>
<!-- ToolBar菜單樣式.-->
<style name="popup_theme" parent="@style/ThemeOverlay.AppCompat.Dark">
<item name="android:background">@android:color/white</item>
<item name="android:textColor">@android:color/holo_red_dark</item>
</style>
複製代碼
<!-- ToolBar樣式 .-->
<style name="toolbar_theme" parent="@style/ThemeOverlay.AppCompat.Light">
<!--修改toolbar的Title顏色.正確-->
<item name="android:textColorPrimary">@android:color/holo_red_dark</item>
<!--錯誤,網上有些資料是這樣的,然而這樣寫編譯都會報錯-->
<item name="textColorPrimary">@android:color/holo_red_dark</item>
<!--修改toolbar的subtitle(小標題)顏色.正確-->
<item name="subtitleTextColor">@android:color/holo_red_dark</item>
</style>
複製代碼
<style name="toolbar_theme" parent="@style/ThemeOverlay.AppCompat.Light">
<!-正確,這個要求Api大於21-->
<item name="android:colorControlNormal">@android:color/holo_red_dark</item>
<!--這個也正確,用這個吧-->
<item name="colorControlNormal">@android:color/holo_red_dark</item>
</style>
複製代碼
效果圖:
既然是menu菜單的內容,固然是修改popup_theme了.
找了不少資料,發現都不正確. 好比說設置android:actionMenuTextColor這個屬性
<style name="popup_theme" parent="@style/ThemeOverlay.AppCompat.Light">
<!--這個不對,不生效-->
<item name="android:actionMenuTextColor">@android:color/holo_red_dark</item>
</style>
複製代碼
後來乾脆一個個屬性試好了,發現其實沒那麼麻煩..
<!-- ToolBar菜單樣式.-->
<style name="popup_theme" parent="@style/ThemeOverlay.AppCompat.Light">
<!--設置背景-->
<item name="android:background">@android:color/white</item>
<!--設置字體顏色-->
<item name="android:textColor">@android:color/holo_red_dark</item>
</style>
複製代碼
效果:
默認是這樣的:
會遮蓋toolbar能夠修改popuptheme的這個屬性來設置:
<!--設置不覆蓋錨點-->
<item name="overlapAnchor">false</item>
複製代碼
有些資料說要這麼設置:
<!-- ToolBar菜單樣式.-->
<style name="popup_theme" parent="@style/ThemeOverlay.AppCompat.Light">
<item name="actionOverflowMenuStyle">@style/OverflowMenuStyle</item>
</style>
<style name="OverflowMenuStyle"parent="Widget.AppCompat.Light.PopupMenu.Overflow">
<!--設置不覆蓋錨點-->
<item name="overlapAnchor">false</item>
</style>
複製代碼
其實不必,能夠直接在app:popupTheme
的style裏面設置overlapAnchor這個屬性就行了. 可是,必定是要在app:popupTheme
的style裏面設置,而不是app:theme
的style裏面設置.
最終效果以下:
最終效果的style代碼:
<style name="toolbar">
<item name="android:layout_width">match_parent</item>
<item name="android:layout_height">wrap_content</item>
<item name="android:minHeight">?attr/actionBarSize</item>
<item name="android:background">@color/colorPrimary</item>
<item name="android:fitsSystemWindows">true</item>
</style>
<style name="base_toolbar" parent="toolbar"/></style>
<!-- ToolBar樣式.-->
<style name="toolbar_theme" parent="@style/ThemeOverlay.AppCompat.Light">
<!--修改toolbar的Title(大標題)顏色-->
<item name="android:textColorPrimary">@android:color/holo_red_dark</item>
<!--修改toolbar的subtitle(小標題)顏色-->
<item name="subtitleTextColor">@android:color/holo_red_dark</item>
<!--修改toolbar的圖標顏色.-->
<item name="colorControlNormal">@android:color/holo_red_dark</item>
</style>
<!-- ToolBar菜單樣式.-->
<style name="popup_theme" parent="@style/ThemeOverlay.AppCompat.Light">
<!--設置背景-->
<item name="android:background">@android:color/white</item>
<!--設置字體顏色-->
<item name="android:textColor">@android:color/holo_red_dark</item>
<!--設置不覆蓋錨點-->
<item name="overlapAnchor">false</item>
</style>
複製代碼
values-v21的style的代碼:
<style name="base_toolbar" parent="@style/toolbar">
<item name="android:elevation">6px</item>
<item name="android:navigationIcon">?attr/homeAsUpIndicator</item>
</style>
複製代碼
toolbar佈局的代碼
<android.support.v7.widget.Toolbar
android:id="@+id/tl_costom"
style="@style/base_toolbar"
app:theme="@style/toolbar_theme"
app:popupTheme="@style/popup_theme"
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">
</android.support.v7.widget.Toolbar>
複製代碼
------------------------------------------------------------------------------------------`
@Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
super.onCreateOptionsMenu(menu, inflater);
}
複製代碼
setHasOptionsMenu(true);
也不建立,跳個頁面返回回來結果有了.setSupportActionBar()
以前調用//設置popupstyle.好比是否覆蓋描點,背景,字體顏色什麼的.必須在inflateMenu()以前設置
mToolbar.setPopupTheme(R.style.popup_theme);
//用Toolbar建立menu
mToolbar.inflateMenu(R.menu.main_home_menu);
//拿到Menu
Menu menu = mToolbar.getMenu();
//下面的這段代碼是爲了讓menu菜單摺疊樣式時,展開能顯示icon圖標.否則icon圖標不會顯示.(感受很坑)
if (menu != null) {
if (menu.getClass().getSimpleName().equals("MenuBuilder")) {
try {
MenuBuilder menuBuilder = (MenuBuilder) menu;
menuBuilder.setOptionalIconsVisible(true);
} catch (Exception e) {
e.printStackTrace();
}
}
}
複製代碼
您的喜歡與建議是我最大的動力-_-