仿饿了么搜索页面特效

    效果图:

这里写图片描述

    首先,确定一点,这是两个activity,两个activity的共同点就是那个搜索的View。这个View是使用了一种叫做共享元素的概念。Android 5.0自带共享元素的实现,但是有一些缺点比如:不能改变大小, 不能兼容4.X 等等
    什么鬼共享元素,让用户看起来是同一个,其实是两个,两个activity都有各自的布局,id都不相同。共享的只有这个搜索View的位置。而且,这个效果的实现,就是平移+缩放动画,其他的位置就是透明度动画。
    首页跳转搜索页的代码:
Intent intent = new Intent(MainActivity.this,SearchActivity.class);
                int location[] = new int[2];
                tvSearch.getLocationOnScreen(location);//获取搜索框的x,y坐标
                intent.putExtra("x",location[0]);
                intent.putExtra("y",location[1]);
                startActivity(intent);
                overridePendingTransition(0,0);
    如代码所示,首先获取共享元素的横纵坐标,并通过intent传到目标activity;其次就是overridePendingTransition(0,0)这个方法。用来指定Activity之间的切换动画。Activity的切换动画指的是从一个activity跳转到另外一个activity时的动画;要注意两点:1.它必需紧挨着startActivity()或者finish()函数之后调用” 2.它只在android2.0以及以上版本上适用(无视掉)
    再就是SearchActivity了,onCreate方法里面有用的代码就是
tvSearch.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
            @Override
            public void onGlobalLayout() {
                tvSearch.getViewTreeObserver().removeOnGlobalLayoutListener(this);
                performEnterAnimation();
            }
        });
    我们知道在oncreate中View.getWidth和View.getHeight无法获得一个view的高度和宽度,这是因为View组件布局要在onResume回调后完成。所以现在需要使用getViewTreeObserver().addOnGlobalLayoutListener()来获得宽度或者高度。这是获得一个view的宽度和高度的方法之一。
    再就是实现动画的类了
private void performEnterAnimation() {
        //首先,先拿到偶从前面传过来的值xy坐标
        float originY = getIntent().getIntExtra("y", 0);
        int location[] = new int[2];
        tvSearch.getLocationOnScreen(location);
        final float translateY = originY - (float) location[1];
        //其次,放到前一个页面的位置
        tvSearch.setY(tvSearch.getY() + translateY);
        tvHint.setY(tvSearch.getY() + (tvSearch.getHeight() - tvHint.getHeight()) / 2);
        img.setY(tvSearch.getY() + (tvSearch.getHeight() - img.getHeight()) / 2);
        float top = getResources().getDisplayMetrics().density * 20;
        //然后开始三种动画,平移动画(至于坐标位置的算法,你自己算啊)
        final ValueAnimator translateVa = ValueAnimator.ofFloat(tvSearch.getY(), top);
        translateVa.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
            @Override
            public void onAnimationUpdate(ValueAnimator valueAnimator) {
                tvSearch.setY((Float) valueAnimator.getAnimatedValue());
                img.setY(tvSearch.getY() + (tvSearch.getHeight() - img.getHeight()) / 2);
                tvHint.setY(tvSearch.getY() + (tvSearch.getHeight() - tvHint.getHeight()) / 2);
                tvTextSearch.setY(tvSearch.getY() + (tvSearch.getHeight() - tvTextSearch.getHeight()) / 2);
            }
        });
        //缩放动画
        ValueAnimator scaleVa = ValueAnimator.ofFloat(1, 0.8f);
        scaleVa.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
            @Override
            public void onAnimationUpdate(ValueAnimator valueAnimator) {
                tvSearch.setScaleX((Float) valueAnimator.getAnimatedValue());
            }
        });
        //透明度动画
        ValueAnimator alphaVa = ValueAnimator.ofFloat(0, 1f);
        alphaVa.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
            @Override
            public void onAnimationUpdate(ValueAnimator valueAnimator) {
                llContent.setAlpha((Float) valueAnimator.getAnimatedValue());
                tvSearch.setAlpha((Float) valueAnimator.getAnimatedValue());
                img.setAlpha((Float) valueAnimator.getAnimatedValue());
                tvHint.setAlpha((Float) valueAnimator.getAnimatedValue());
            }
        });

        alphaVa.setDuration(500);
        translateVa.setDuration(500);
        scaleVa.setDuration(500);

        alphaVa.start();
        translateVa.start();
        scaleVa.start();
    }
    要说的差不多就这么多,再就是一个返回时候的动画了,跟这个差不多,下载项目去瞅瞅,反正又不要钱

项目链接

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

海晨忆

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值