微信下方导航栏最最最简单实现

一、概述

因为公司项目的下方导航栏太普通了,想着仿照微信的导航栏做个效果。

二、思考

据我观察,我们可以通过有色图(选中项显示效果)叠在灰色图(未选中项显示效果),然后通过改变有色图的透明度来实现效果。
1、肯定要监听这个过程,
2、根据这个过程变化图片与文本颜色。

监听这个过程

因为是我用的是上面ViewPager+下面LinearLayout里面4个RelativeLayout来实现的导航栏效果。所以要监听OnPageChangeListener的onPageScrolled。

viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
            @Override
            public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
            }

            @Override
            public void onPageSelected(int position) {
            }

            @Override
            public void onPageScrollStateChanged(int state) {
            }
        });
        

根据这个过程变化图片与文本颜色

观察里面的参数有三个,这里有点坑,害我走了点弯路,一开始我以为其中position是当前页面下标(其实不是)。因为我要监听滑动的过程,自然而然就没去理会这个参数。positionOffset是一个进度值,手指向右滑动这个值从1趋向0,手指向左滑动这个值从0趋向1,然后突变为0(突变的时候position也会相应变更了,所以放心,这个突变并不影响我们的实现).positionOffsetPixels是一个像素值,变化情况可以类比positionOffset

这里是弯路思考可以忽略(也可以实现,但比较复杂):
这里理所当然的选择了positionOffset
这个过程中首先我得提供当前要变化的是导航栏的哪两个item,以及分别变化的值。
但是由于进度值的变化都在0到1这个区间,无法单单通过当前值来得到当前画面是在左侧还是右侧,无法得知要改变的是哪两个item。所以我们通过保存上一个positionOffset来比较当前positionOffset,获得当前变化是变大(手指向左滑动)还是变小(手指向右滑动)。
开始positionOffset变小,则记录在左侧;-》变化当前item和左侧item,根据positionOffset变化透明度
开始positionOffset变大,则记录在右侧;-》变化当前item和右侧item,根据positionOffset变化透明度
在左侧positionOffset变大,且positionOffset突变(差值大于0.5f),则记录在右侧;-》变化当前和右
在右侧positionOffset变小,且positionOffset突变(差值大于0.5f),则记录在左侧;-》变化当前和左

其实position并不是当前页面下标,它的变化规律为是,当前页面手指向右滑动,position为左侧页面下标。当前页面手指向左滑动,position为当前页面下标。没有具体去看源码,但是我是这样理解的,它这个坐标指的是当前显示页面的第一个页面所在的下标(滑动的时候会显示两个页面,也就是左侧这个页面的下标,停止滑动的时候只会显示一个页面,当前页面也就是最左侧的页面了,也就是当前页面的下标了),通过position我们就能知道当前要变化的是哪两个item,然后通过positionOffset,变化item的透明度实现效果。

        viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
            @Override
            public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
                switch (viewPager.getCurrentItem()) {
                    //在第一个页面
                    case 0:
                        //在右侧
                        rlyIndexP.setAlpha(1.0f - positionOffset);
                        rlyDeviceP.setAlpha(positionOffset);
                        break;
                    //在第二个页面
                    case 1:
                        //在左侧
                        if (position == 0) {
                            rlyIndexP.setAlpha(1.0f - positionOffset);
                            rlyDeviceP.setAlpha(positionOffset);
                        } else {
                            //在右侧
                            rlyDeviceP.setAlpha(1.0f - positionOffset);
                            rlyShopP.setAlpha(positionOffset);
                        }
                        break;
                    //在第三个页面
                    case 2:
                        //在左侧
                        if (position == 1) {
                            rlyDeviceP.setAlpha(1.0f - positionOffset);
                            rlyShopP.setAlpha(positionOffset);
                        } else {
                            //在右侧
                            rlyShopP.setAlpha(1.0f - positionOffset);
                            rlyMeP.setAlpha(positionOffset);
                        }
                        break;
                    //在第四个页面
                    case 3:
                        //在左侧
                        if (position == 2) {
                            rlyShopP.setAlpha(1.0f - positionOffset);
                            rlyMeP.setAlpha(positionOffset);
                        }
                        break;
                }
            }

            @Override
            public void onPageSelected(int position) {
                ChangeImageBg(position);

            }

            @Override
            public void onPageScrollStateChanged(int state) {
            }
        });
        
    private void ChangeImageBg(int index) {
        rlyIndexP.setAlpha(index == SELECTED_INDEX ? 1.0f : 0.0f);
        rlyDeviceP.setAlpha(index == SELECTED_DEVICE ? 1.0f : 0.0f);
        rlyShopP.setAlpha(index == SELECTED_SHOW ? 1.0f : 0.0f);
        rlyMeP.setAlpha(index == SELECTED_ME ? 1.0f : 0.0f);
    }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值