xamarin android toolbar(踩坑完全入门详解)

网上关于toolbar的教程有很多,很多新手,在使用toolbar的时候踩坑实在太多了,不好好总结一下,实在浪费。如果你想学习toolbar,你肯定会去去搜索androd toolbar,既然你能看到这篇文章,说明还是搜了xamarin android toolbar。那么这篇文章就好好总结一下toolbar在xamarin android中如何使用,减少大家踩坑的时间。

了解Toolbar

android3.0推了ActionBar这个控件,android5.0开始推出Materal Design,其中就有ToolBar控件。可能官方觉得ActionBar限制app开发设计的弹性,google非常推荐大家使用ToolBar来作为客户端的导航栏,以此来取代ActionBar。
ToolBar使用更灵活,设计更多样性。主要的优点有1.可以设置导航栏图标、Logo、标题和子标题等属性; 2可添加自定义控件;3.支持Action Menu;4.可随意设置位置

xamarin android中使用Toolbar

官方为了将toolbar这一控件向下兼容,推出了兼容版的toolbar,所以首先的引入Android.Support.V7.AppCompat。我们先来看看最终完成的整体的效果图

写第一个Toolbar例子,然后我们看一下布局文件:
  1. <?xml version= "1.0" encoding= "utf-8"?>
  2. <LinearLayout xmlns:android= "http://schemas.android.com/apk/res/android"
  3. xmlns:app= "http://schemas.android.com/apk/res-auto"
  4. android:orientation= "vertical"
  5. android:layout_width= "match_parent"
  6. android:layout_height= "match_parent"
  7. android:background= "@color/color_white"
  8. android:fitsSystemWindows= "true">
  9. <android.support.v7.widget.Toolbar
  10. android:id= "@+id/toolbar"
  11. android:layout_width= "match_parent"
  12. android:layout_height= "60dp"
  13. android:background= "@color/color_primary"
  14. android:navigationIcon= "@drawable/icon2"
  15. android:logo= "@drawable/icon"
  16. android:subtitle= "子标题"
  17. android:title= "标题"
  18. android:titleTextColor= "@color/color_white">
  19. <TextView
  20. android:layout_width= "wrap_content"
  21. android:layout_height= "wrap_content"
  22. android:text= "自定义文本">
  23. </TextView>
  24. </android.support.v7.widget.Toolbar>
  25. </LinearLayout>
记得在Activity继承AppCompatActivity,现在运行的结果是并没有看到标题、子标题、logo等属性。
  1. <style name="AppTheme" parent="AppTheme.Base">
  2. </style>
  3. <style name="AppTheme.Base" parent="Theme.AppCompat.Light.NoActionBar">
  4. </style>


往下看怎么解决。

坑1:设置Toolbar属性不能使用android:**** 而使用app:*****

我们没有看到这些设置的属性很正常,我们使用android:*** 找不到的属性,应该使用Toolbar这个控件自带的属性。所以我在根布局加了
xmlns:app="http://schemas.android.com/apk/rs-auto" 使用app:***来设置属性如下
  1. <android.support.v7.widget.Toolbar
  2. android:id= "@+id/toolbar"
  3. android:layout_width= "match_parent"
  4. android:layout_height= "60dp"
  5. android:background= "@color/color_primary"
  6. android:navigationIcon= "@drawable/icon2"
  7. android:logo= "@drawable/icon"
  8. android:subtitle= "子标题"
  9. android:title= "标题"
  10. android:titleTextColor= "@color/color_white">
现在我们能看到已经设置白色的标题文本,navigationIcon、logo、子标题。但是尴尬的是子标题的颜色subTitleTextColor属性报错,虽然可以通过代码SetSubtitleTextColor方法设置,但是这个子标题文本颜色这个subTitleTextColor属性不能通过编译有点难以理解。后来才发现subTitleTextColor属性Title要小写,jbwy,也就是这样app:subtitleTextColor

添加ActionMenu 菜单项

toolbar可以添加菜单项,在Resources文件下建一个menu文件夹专门放菜单。先来看一下actionMenu.xml 菜单项文件,然后在代码实现方法。
  1. <?xml version="1.0" encoding="utf-8" ?>
  2. <menu xmlns:android="http://schemas.android.com/apk/res/android"
  3. xmlns:app= "http://schemas.android.com/apk/res-auto">
  4. <item android:id="@id/menu_edit"
  5. android:icon= "@drawable/edit"
  6. android:title= "编辑"
  7. app:showAsAction= "ifRoom"/>
  8. <item android:id="@id/menu_search"
  9. android:icon= "@drawable/search"
  10. android:title= "搜索"
  11. app:showAsAction= "ifRoom"/>
  12. <item android:id="@id/menu_add"
  13. android:icon= "@drawable/add"
  14. android:title= "添加"
  15. app:showAsAction= "ifRoom"/>
  16. </menu>
MainActivity代码如下:
  1. using Android.App;
  2. using Android.Views;
  3. using Android.Widget;
  4. using Android.OS;
  5. using Android.Support.V7.App;
  6. namespace ToolbarDemo
  7. {
  8. [ Activity(Label = "ToolbarDemo", MainLauncher = true, Icon = "@drawable/icon",Theme ="@style/AppTheme")]
  9. public class MainActivity : AppCompatActivity
  10. {
  11. protected override void OnCreate(Bundle bundle)
  12. {
  13. base.OnCreate(bundle);
  14. SetContentView(Resource.Layout.Main);
  15. Android.Support.V7.Widget.Toolbar toolbar = FindViewById<Android.Support.V7.Widget.Toolbar>(Resource.Id.toolbar);
  16. toolbar.InflateMenu(Resource.Menu.actionMenu); //填充actionMenu菜单项
  17. toolbar.MenuItemClick += (s, e) => //菜单项单击事件
  18. {
  19. switch (e.Item.ItemId)
  20. {
  21. case Resource.Id.menu_add:
  22. Toast.MakeText( this, "添加菜单项", ToastLength.Short).Show();
  23. break;
  24. case Resource.Id.menu_edit:
  25. Toast.MakeText( this, "编辑菜单项", ToastLength.Short).Show();
  26. break;
  27. case Resource.Id.menu_search:
  28. Toast.MakeText( this, "搜索菜单项", ToastLength.Short).Show();
  29. break;
  30. }
  31. };
  32. }
  33. public override bool OnCreateOptionsMenu(IMenu menu)
  34. {
  35. return base.OnCreateOptionsMenu(menu);
  36. }
  37. }
  38. }
关于showAsAction 展现在Action条目中的几个属性值有这几个:
  1. always:使菜单项一直显示在ToolBar上。 
  2. ifRoom:如果有足够的空间,这个值会使菜单项显示在ToolBar上。 
  3. never:使菜单项永远都不出现在ToolBar上,在…的子项中显示。 
  4. withText:使菜单项和它的图标,菜单文本一起显示。

坑2:toolbar中使用setSupportActionBar方法菜单项不见了

如果在onCreate方法里面使用兼容包的方法SetSupportActionBar(toolbar) 后发现菜单项不显示了,这就有点尴尬了,所以要在OnCreateOptionsMenu方法中加上一句代码加载菜单项才能显示
  1. public override bool OnCreateOptionsMenu(IMenu menu)
  2. {
  3. MenuInflater.Inflate(Resource.Menu.actionMenu,menu);
  4. return base.OnCreateOptionsMenu(menu);
  5. }

toolbar中设置菜单项图标颜色、自定义菜单图标、设置菜单项文字颜色

对于设置各种颜色,我们先来看看这张图,我是盗图的......,然后结合style文件看看如何设置这些颜色。原文地址http://blog.csdn.net/u012702547/article/details/50932090

  1. <style name="AppTheme.NoActionBar">
  2. <!--状态栏颜色-->
  3. <item name="colorPrimaryDark">@color/colorPrimaryDark </item>
  4. <!--控制各个控件被选中时的颜色-->
  5. <item name="colorAccent">@color/colorAccent </item>
  6. <!--页面背景色-->
  7. <item name="android:windowBackground">@color/windowBackg </item>
  8. <!--底部导航栏颜色-->
  9. <item name="android:navigationBarColor">@color/navigationColor </item>
  10. <!--Appbar背景色-->
  11. <item name="android:colorPrimary">@color/colorPrimary </item>
  12. <!--ToolBar上的Title颜色-->
  13. <item name="android:textColorPrimary">@color/textColorPrimary </item>
  14. <!--各个控制控件的默认颜色-->
  15. <item name="android:colorControlNormal">@color/colorControlNormal </item>
  16. </style>

设置菜单项图标颜色:

通过上面的图和代码已经知道android:colorControlNormal设置各种控件的默认颜色,在Activity中Theme中这样写就可以了:

  1. <style name="AppTheme.Base" parent="Theme.AppCompat.Light.NoActionBar">
  2. <item name="colorControlNormal">@color/color_white </item>
  3. </style>

为什么要在Activity的主题里面设置?能不能直接Toolbar的主题设置,当然可以,直接通过设置Toolbar控件的android:theme=“****”就可以了。主题样式如下

  1. <style name="ActionMenuTheme" parent="Theme.AppCompat.Light.NoActionBar">
  2. <item name="colorControlNormal">@color/color_white </item>
  3. <!--改变菜单项文字颜色-->
  4. <item name="android:textColorPrimary">@color/color_red </item>
  5. <item name="android:textSize">12sp </item>
  6. </style>
toolbar 设置菜单项文字颜色
 上面的toolbar的主题ActionMenuTheme 中的<item name="adnroid:textColorPrimary">@color/color_red</item>就是这事菜单项文字的颜色。效果如下:


toolbar 溢出菜单项图标的设置

如果你觉tollbar 的溢出菜单三个点不符合的审美感觉,你可以可以自定义一个图标来修改,同样我们设置toolbar的android:theme来做这件事情

  1. <style name="ActionMenuTheme" parent="Theme.AppCompat.Light.NoActionBar">
  2. <item name="colorControlNormal">@color/color_white </item>
  3. <!--改变菜单项文字颜色-->
  4. <item name="android:textColorPrimary">@color/color_red </item>
  5. <item name="android:textSize">12sp </item>
  6. <!--设置溢出菜单项图标-->
  7. <item name="actionOverflowButtonStyle">@style/ActionButton.Overflow.Custom </item>
  8. </style>
  9. <style name="ActionButton.Overflow.Custom" parent="android:style/Widget.Holo.Light.ActionButton.Overflow">
  10. <item name="android:src">@drawable/add_white </item>
  11. </style>


toolbar自定义溢出菜单样式

虽然上面我们进行了图标颜色,自定义图标,菜单文字颜色的修改,但是这和我们一般的app上的ToolBar还是有一定差距,菜单项挡住了toolbar,正常的做法应该往下移才合理一点。如图所示:

添加以下样式
  1. <!--溢出菜单项下移-->
  2. <style name="OverflowMenuStyle" parent="@style/Widget.AppCompat.PopupMenu.Overflow">
  3. <!-- 是否覆盖锚点,默认为true,即盖住Toolbar -->
  4. <item name="overlapAnchor">false </item>
  5. <!-- 弹出层背景颜色 -->
  6. <item name="android:popupBackground">@color/color_primary </item>
  7. <!-- 弹出层垂直方向上的偏移,即在竖直方向上距离Toolbar的距离,值为负则会盖住Toolbar -->
  8. <item name="android:dropDownVerticalOffset">10dp </item>
  9. <!-- 弹出层水平方向上的偏移,即距离屏幕左边的距离,负值会导致右边出现空隙 -->
  10. <item name="android:dropDownHorizontalOffset">-10dp </item>
  11. </style>
然后再Activity中的Theme中添加以下style
  1. <style name="AppTheme.Base" parent="Theme.AppCompat.Light.NoActionBar">
  2. <item name="actionOverflowMenuStyle">@style/OverflowMenuStyle </item>
  3. <item name="actionOverflowButtonStyle">@style/ActionButton.Overflow.Custom </item>
  4. <item name="android:textColorPrimary">@color/color_white </item>
  5. <item name="android:textSize">15sp </item>
  6. </style>

坑3:无法再Toolbar中设置app:popopTheme自定义溢出菜单样式

看了android的做法这个溢出菜单下移OverflowMenuStyle样式可以写在Toolbar 的属性app:popupTheme但是没有效果,如果知道怎么解决,欢迎评论指出。

坑4:toolbar菜单项无法同时显示图标和文字

根据图上所看到的,显示toolbar上的菜单项是图标,但是显示popupMenu上的只有文字没有图标,我们想要修改一下让图标和文字同时显示在popupMenu上该怎么做呢。使用withText也并有作用,这时要使用app:actionLayout属性了。在menu文件夹的菜单布局下加上app:actionLayout属性
  1. <code class="language-html"><?xml version="1.0" encoding="utf-8" ?>  
  2. <menu xmlns:android="http://schemas.android.com/apk/res/android"  
  3.   xmlns:app="http://schemas.android.com/apk/res-auto">  
  4.   <item android:id="@+id/menu_edit"  
  5.      android:icon="@drawable/edit"  
  6.      android:title="编辑"  
  7.      app:actionLayout="@layout/menu_action_edit"  
  8.      app:showAsAction="withText"/>  
  9.   <item android:id="@+id/menu_search"  
  10.      android:icon="@drawable/search"  
  11.      android:title="搜索"  
  12.      app:showAsAction="always|withText"/>  
  13.   <item android:id="@+id/menu_add"  
  14.      android:icon="@drawable/add_small"  
  15.      android:title="添加"  
  16.      app:showAsAction="always|withText"  
  17.      app:actionLayout="@layout/menu_action_add"  
  18.         />  
  19. </menu></code>  
  1. <?xml version="1.0" encoding="utf-8" ?>
  2. <menu xmlns:android="http://schemas.android.com/apk/res/android"
  3. xmlns:app= "http://schemas.android.com/apk/res-auto">
  4. <item android:id="@+id/menu_edit"
  5. android:icon= "@drawable/edit"
  6. android:title= "编辑"
  7. app:actionLayout= "@layout/menu_action_edit"
  8. app:showAsAction= "withText"/>
  9. <item android:id="@+id/menu_search"
  10. android:icon= "@drawable/search"
  11. android:title= "搜索"
  12. app:showAsAction= "always|withText"/>
  13. <item android:id="@+id/menu_add"
  14. android:icon= "@drawable/add_small"
  15. android:title= "添加"
  16. app:showAsAction= "always|withText"
  17. app:actionLayout= "@layout/menu_action_add"
  18. />
  19. </menu>
actionLayout指向的是一个布局文件,至于menu_action_add.axml。就是一个图标加文本使用drawableLeft属性。 
  
 
  
 
 
  1. <?xml version="1.0" encoding="utf-8"?>
  2. <TextView xmlns:android="http://schemas.android.com/apk/res/android"
  3. android:layout_width= "wrap_content"
  4. android:layout_height= "wrap_content"
  5. android:paddingLeft= "10dip"
  6. android:paddingRight= "10dip"
  7. android:gravity= "center"
  8. android:text= "添加"
  9. android:drawableLeft= "@drawable/add_white"
  10. android:textColor= "@color/color_white"
  11. android:clickable= "true" />
效果图如下,google 默认在overflow中的actionMenu都只显示文字,要同时显示图标和文字,还需要想办法改变这一默认行为。


overflow中的ActionMenu显不显示图标,是有MenuBuilder这个类的setOptionalIconsVisable方法决定的,在菜单展开的时候给这个方法传入true,那每个菜单项的图标和文字都会显示出来,尴尬的是要java的反射方法去做这件事,重写OnMenuOpend方法
  1. public override bool OnMenuOpened(int featureId, IMenu menu)
  2. {
  3. System.Diagnostics.Debug.WriteLine(featureId);
  4. if ( menu != null)
  5. {
  6. var javaObj = (Java.Lang.Object)menu;
  7. var javaClass = javaObj.Class;
  8. if (javaClass.SimpleName.EndsWith( "MenuBuilder"))
  9. {
  10. try {
  11. Java.Lang.Reflect.Method m = javaClass.GetDeclaredMethod( "setOptionalIconsVisible", new Java.Lang.Class[] { Java.Lang.Boolean.Type });
  12. m.Accessible = true;
  13. m.Invoke(javaObj, new Java.Lang.Object[] { true});
  14. }
  15. catch (Java.Lang.NoSuchFieldException e)
  16. {
  17. System.Console.WriteLine( "onMenuOpened:{0}",e.ToString());
  18. }
  19. }
  20. }
  21. return base.OnMenuOpened(featureId, menu);
  22. }
最终效果:

最后总结一句:纸上得来终觉浅,绝知此事要躬行。关于toolbar的更多属性还要仔细去琢磨。
代码下载地址http://download.csdn.net/detail/kebi007/9835823

作者:张林

标题:xamarin android toolbar(踩坑完全入门详解) 原文地址:http://blog.csdn.net/kebi007/article/details/71247295

转载随意注明出处
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值