Android 给BottomNavigationView添加未

作者: SwitchLife | 来源:发表于2018-05-29 14:47 被阅读1次

    开篇

      在开发Android应用中,为应用添加BottomNavigationBar是一件司空见惯的事情。为此,google团队在android.support.design包中就专门提供了快速实现BottomNavigationBar的控件:BottomNavigationView,而BottomNavigationView并没有提供显示未读消息红点提示功能。本文主要讲解如何在BottomNavigationView上实现显示未读消息红点提示功能。当然,市面上很多大神开源了第三方的BottomNavigationBar框架,这里暂不展开讨论。不过这里还是推荐一个优秀的BottomNavigationBar开源项目:https://github.com/Ashok-Varma/BottomNavigation

    效果截屏

    立即体验

    扫描以下二维码下载体验App(从0.2.3版本开始,体验App内嵌版本更新检测功能):


    JSCKit库传送门:https://github.com/JustinRoom/JSCKit

    实施步骤

    在添加未读消息红点提示之前,分析BottomNavigationView源码

    • 1、从构造函数着手
    public BottomNavigationView(Context context, AttributeSet attrs, int defStyleAttr) {
            super(context, attrs, defStyleAttr);
            ...
            mMenuView = new BottomNavigationMenuView(context);
            ...
            mPresenter.setBottomNavigationMenuView(mMenuView);
            ...
            if (a.hasValue(R.styleable.BottomNavigationView_menu)) {
                inflateMenu(a.getResourceId(R.styleable.BottomNavigationView_menu, 0));
            }
            ...
        }
    

    a、创建BottomNavigationMenuView实例:mMenuView
    b、 BottomNavigationPresenter绑定mMenuView
    c、 调用方法inflateMenu(int resId)解析xml菜单文件

    • 2、inflateMenu(int resId)方法:
        public void inflateMenu(int resId) {
            mPresenter.setUpdateSuspended(true);
            getMenuInflater().inflate(resId, mMenu);
            mPresenter.setUpdateSuspended(false);
            mPresenter.updateMenuView(true);
        }
    

    从方法字面上不难看出updateMenuView就是用来更新菜单视图的。

    • 3、updateMenuView(boolean cleared)方法:
        @Override
        public void updateMenuView(boolean cleared) {
            if (mUpdateSuspended) return;
            if (cleared) {
                mMenuView.buildMenuView();
            } else {
                mMenuView.updateMenuView();
            }
        }
    

    它调用了mMenuView.buildMenuView()构建菜单视图,而mMenuView就是在BottomNavigationView构造函数中BottomNavigationPresenter绑定的BottomNavigationMenuView的实例。

    • 4、buildMenuView()方法:
        public void buildMenuView() {
            ...
            for (int i = 0; i < mMenu.size(); i++) {
                mPresenter.setUpdateSuspended(true);
                mMenu.getItem(i).setCheckable(true);
                mPresenter.setUpdateSuspended(false);
                BottomNavigationItemView child = getNewItem();
                mButtons[i] = child;
                child.setIconTintList(mItemIconTint);
                child.setTextColor(mItemTextColor);
                child.setItemBackground(mItemBackgroundRes);
                child.setShiftingMode(mShiftingMode);
                child.initialize((MenuItemImpl) mMenu.getItem(i), 0);
                child.setItemPosition(i);
                child.setOnClickListener(mOnClickListener);
                addView(child);
            }
        }
    

    到这里,我们不难看出,每一个menu就是一个BottomNavigationItemView示例:

    public class BottomNavigationItemView extends FrameLayout implements MenuView.ItemView {
    }
    

    所以,整个流程看下来,我们知道:
    BottomNavigationView添加了一个BottomNavigationMenuView实例,而BottomNavigationMenuView实例添加了N个BottomNavigationItemView实例。
    很明显,我们要给每个menu添加未读消息红点提示其实就是在BottomNavigationItemView实例上添加一个显示未读消息的view。

    在BottomNavigationItemView上添加未读消息红点提示view

    • 1、找到BottomNavigationMenuView
            private BottomNavigationView navigation;
    
            BottomNavigationMenuView menuView = null;
            for (int i = 0; i < navigation.getChildCount(); i++) {
                View child = navigation.getChildAt(i);
                if (child instanceof BottomNavigationMenuView) {
                    menuView = (BottomNavigationMenuView) child;
                    break;
                }
            }
    
    • 2、找到BottomNavigationItemView并添加未读消息红点view
          if (menuView != null) {
                int dp8 = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 8, getResources().getDisplayMetrics());
                dotViews = new DotView[menuView.getChildCount()];
                for (int i = 0; i < menuView.getChildCount(); i++) {
                    BottomNavigationItemView.LayoutParams params = new BottomNavigationItemView.LayoutParams(i == menuView.getChildCount() - 1 ? dp8 : dp8 * 2, 0);
                    params.gravity = Gravity.CENTER_HORIZONTAL;
                    params.leftMargin = dp8 * 3;
                    params.topMargin = dp8 / 2;
                    BottomNavigationItemView itemView = (BottomNavigationItemView) menuView.getChildAt(i);
                    DotView dotView = new DotView(this);
                    itemView.addView(dotView, params);
                    if (i < menuView.getChildCount() - 1) {
                        dotView.setUnReadCount(new Random().nextInt(20));
                    }
                    dotViews[i] = dotView;
                }
            }
    

    运行后看效果。

    这里是详细实现实例:
    https://github.com/JustinRoom/JSCKit/blob/master/app/src/main/java/jsc/exam/jsckit/ui/BottomNavigationViewActivity.java

    篇尾

      原创不易,给个爱心,谢谢!QQ:1006368252

    勿问成功的秘诀为何,且尽全力做你应该做的事吧。——美华纳

    相关文章

      网友评论

        本文标题:Android 给BottomNavigationView添加未

        本文链接:https://www.haomeiwen.com/subject/ngbojftx.html