如何去掉BottomNavigationView的Item大于3个时的动画效果
来源:互联网 发布:模拟地理位置的软件 编辑:程序博客网 时间:2024/05/20 05:25
前言
官方的导航栏BottomNavigationView出来已经有一段时间了,使用也非常简单,这里就不再说它的使用了!当我们底部导航为3个时,感觉体验还是很舒服的,但是一旦大于3个时,就只显示选中的item了,其他的变很小,而且没有显示标题,切换的时候,也十分夸张,显得很别扭!
为什么这样
在查看了源码之后,发现它的设计有点类似MVP模式,所涉及到的类有5个:
BottomNavigationView
BottomNavigationMenu
BottomNavigationItemView
BottomNavigationMenuView
BottomNavigationPresenter
具体全部的源码分析,可以参考这篇文章:
BottomNavigationView
我们这里只说一下,item大于3个的显示奇怪的情况。
首先在BottomNavigationMenuView
中,有一个全局变量:mShiftingMode
,然后在创建Menu的时候buildMenuView()
public void buildMenuView() { ... mShiftingMode = mMenu.size() > 3; ...}
当size>3时候,设为ture。
然后在BottomNavigationItemView
,设置check的时候:
@Override public void setChecked(boolean checked) { ViewCompat.setPivotX(mLargeLabel, mLargeLabel.getWidth() / 2); ViewCompat.setPivotY(mLargeLabel, mLargeLabel.getBaseline()); ViewCompat.setPivotX(mSmallLabel, mSmallLabel.getWidth() / 2); ViewCompat.setPivotY(mSmallLabel, mSmallLabel.getBaseline()); if (mShiftingMode) { if (checked) { LayoutParams iconParams = (LayoutParams) mIcon.getLayoutParams(); iconParams.gravity = Gravity.CENTER_HORIZONTAL | Gravity.TOP; iconParams.topMargin = mDefaultMargin; mIcon.setLayoutParams(iconParams); mLargeLabel.setVisibility(VISIBLE); ViewCompat.setScaleX(mLargeLabel, 1f); ViewCompat.setScaleY(mLargeLabel, 1f); } else { LayoutParams iconParams = (LayoutParams) mIcon.getLayoutParams(); iconParams.gravity = Gravity.CENTER; iconParams.topMargin = mDefaultMargin; mIcon.setLayoutParams(iconParams); mLargeLabel.setVisibility(INVISIBLE); ViewCompat.setScaleX(mLargeLabel, 0.5f); ViewCompat.setScaleY(mLargeLabel, 0.5f); } mSmallLabel.setVisibility(INVISIBLE); } else { if (checked) { LayoutParams iconParams = (LayoutParams) mIcon.getLayoutParams(); iconParams.gravity = Gravity.CENTER_HORIZONTAL | Gravity.TOP; iconParams.topMargin = mDefaultMargin + mShiftAmount; mIcon.setLayoutParams(iconParams); mLargeLabel.setVisibility(VISIBLE); mSmallLabel.setVisibility(INVISIBLE); ViewCompat.setScaleX(mLargeLabel, 1f); ViewCompat.setScaleY(mLargeLabel, 1f); ViewCompat.setScaleX(mSmallLabel, mScaleUpFactor); ViewCompat.setScaleY(mSmallLabel, mScaleUpFactor); } else { LayoutParams iconParams = (LayoutParams) mIcon.getLayoutParams(); iconParams.gravity = Gravity.CENTER_HORIZONTAL | Gravity.TOP; iconParams.topMargin = mDefaultMargin; mIcon.setLayoutParams(iconParams); mLargeLabel.setVisibility(INVISIBLE); mSmallLabel.setVisibility(VISIBLE); ViewCompat.setScaleX(mLargeLabel, mScaleDownFactor); ViewCompat.setScaleY(mLargeLabel, mScaleDownFactor); ViewCompat.setScaleX(mSmallLabel, 1f); ViewCompat.setScaleY(mSmallLabel, 1f); } } refreshDrawableState(); }
根据是不是shiftMode
执行不同的逻辑,所以产生了这样奇葩的效果!
解决方案
官方并没有暴露接口,来外部禁掉这种模式,然后在stackoverflow上面找到一个回答:
How to disable BottomNavigationView shift mode?
上代码:
public class BottomNavigationViewHelper { public static void disableShiftMode(BottomNavigationView view) { BottomNavigationMenuView menuView = (BottomNavigationMenuView) view.getChildAt(0); try { Field shiftingMode = menuView.getClass().getDeclaredField("mShiftingMode"); shiftingMode.setAccessible(true); shiftingMode.setBoolean(menuView, false); shiftingMode.setAccessible(false); for (int i = 0; i < menuView.getChildCount(); i++) { BottomNavigationItemView item = (BottomNavigationItemView) menuView.getChildAt(i); //noinspection RestrictedApi item.setShiftingMode(false); // set once again checked value, so view will be updated //noinspection RestrictedApi item.setChecked(item.getItemData().isChecked()); } } catch (NoSuchFieldException e) { Log.e("BNVHelper", "Unable to get shift mode field", e); } catch (IllegalAccessException e) { Log.e("BNVHelper", "Unable to change value of shift mode", e); } }}
然后使用:
BottomNavigationView bottomNavigationView = (BottomNavigationView) findViewById(R.id.bottom_navigation_bar);BottomNavigationViewHelper.disableShiftMode(bottomNavigationView);
需要注意的一点:
就是我们打包混淆的时候,不能混淆这个成员变量!!!!
-keepclassmembers class android.support.design.internal.BottomNavigationMenuView { boolean mShiftingMode; }
第三方控件
Github上面有很多类似的控件,使用更加的灵活,UI体验上面也有更多的效果可以使用!如star数最多的BottomNavigation
传送门:BottomNavigation
- 如何去掉BottomNavigationView的Item大于3个时的动画效果
- 如何去掉BottomNavigationView的动画效果
- BottomNavigationView去掉动画效果
- 当使用BottomNavigationView菜单项多于3个时,去除动画效果,显示菜单项文字
- 去掉activity切换时的动画效果
- ListView的item动画效果
- Android丨BottomNavigationView项目大于3切换效果
- 去掉RecyclerView的默认item动画
- wince如何去掉APP窗口的动画显示效果
- Android Launcher如何去掉进入应用时的动画效果?
- 去掉CE程序启动时的动画效果
- Activity 去掉默认的动画效果
- extjs4 去掉window的动画效果
- 去掉activity默认动画效果的方法
- Activity去掉默认的动画效果方法:
- 去掉LitView 中Item的默认点击的效果
- android中如何去掉pulltorefreshlistview点击item时的背景颜色,与item外边距设置
- android中如何去掉pulltorefreshlistview点击item时的背景颜色,与item外边距设置
- Eclipse去除js验证
- python中编码问题
- ajax的使用及传值
- Add bricks in the wall UVA
- 个人学习笔记1
- 如何去掉BottomNavigationView的Item大于3个时的动画效果
- 线程
- 26. OP-TEE驱动篇----libteec和tee_supplicant调用驱动流程和重要结构体
- KCF_ROS + TLD_ROS 原理以及源码分析
- 窗口过程_框架基础
- InfluxDB查询问题
- 忽略证书验证的CloseableHttpClient
- junit4_SpringMVC_Dubbo
- 文章标题