Android实现美团外卖底部导航栏动画

作者:甜梦_ 时间:2022-09-21 20:09:13 

体验了一下美团外卖的底部导航栏,感觉动画很流畅,分割线被顶起,还有图标的动画,可能用的lottie,觉得分割线被顶起可以自己写动画,所以试着写了一下 。

Android实现美团外卖底部导航栏动画

想自定义view点击实现动画效果,自定义view的区域一定比背景需要被顶起的线要高,所以布局如下:

Android实现美团外卖底部导航栏动画

开始绘制view,被顶起的曲线分三段,前后两端曲线对称的,用path绘制曲线,中间段绘制贝塞尔曲线。

Android实现美团外卖底部导航栏动画

那么我们分别绘制三段曲线,用ValueAnimator实现效果,


private void initAnim() {
 value = startValue;
 animator = ValueAnimator.ofInt(startValue, halfValue, endValue);
//  animator.setInterpolator(new DecelerateInterpolator());
 animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
  @Override
  public void onAnimationUpdate(ValueAnimator valueAnimator) {
   value = (int) valueAnimator.getAnimatedValue();
   invalidate();
  }
 });
 animator.setDuration(ANIM_TIME);
 animator.start();
}

动画执行过程中有个回弹,那么value的变化需要一个中间值,


startValue = 0;
halfValue = -DensityUtils.dp2px(context, 35);
endValue = -DensityUtils.dp2px(context, 25);

在onDraw中绘制曲线代码如下,


rectF = new RectF((((float)width - (float)contentSize) / 2),
   lineToTop + value,
   (float) width - ((float)width - (float)contentSize) / 2,
   height + value);

if (value < 0 ) {
  Path path = new Path();
  //绘制第一段圆弧
  path.moveTo(rectF.left - 20, lineToTop);
  float firstCubicHight = ((float) lineToTop - rectF.top) / 4;
  float end = (float) lineToTop - firstCubicHight;
  path.cubicTo(
    rectF.left - 10,
    (float) lineToTop - firstCubicHight / 16,
    rectF.left,
    (float) lineToTop - firstCubicHight / 12,
    rectF.left + 10,
    end
  );

//绘制第二段圆弧

path.quadTo(
    rectF.left + contentSize / 2,
    rectF.top * 0.9f,
    rectF.right - 10,
    end
  );
  //绘制第三段圆弧,和第一段对称

path.cubicTo(
    rectF.right,
    (float) lineToTop - firstCubicHight / 12,
    rectF.right + 10,
    (float) lineToTop - firstCubicHight / 16,
    rectF.right + 20,
    lineToTop
  );

Path pathBg = new Path();
  pathBg.addPath(path);

pathBg.lineTo(rectF.right + 20, height);
  pathBg.lineTo(rectF.left - 20, height);
  pathBg.lineTo(rectF.left - 20, lineToTop);
  canvas.drawPath(pathBg, paintBg);//绘制白色背景

canvas.drawPath(path, paintBgStroke);//绘制曲线

}

最后在onDraw()中画上图片也用属性动画移动就成功啦。

因为有曲线衔接贝塞尔曲线,感觉弧度有时候改变曲线不是很流畅,大家应该会有更好的办法 欢迎补充!

来源:https://blog.csdn.net/tm1989tm/article/details/103276641

标签:Android,导航栏
0
投稿

猜你喜欢

  • SpringBoot导入Druid运行失败问题

    2023-02-14 03:35:41
  • 深入浅析SpringBoot中的自动装配

    2021-08-21 17:45:11
  • Java数组越界问题实例解析

    2023-10-25 18:16:23
  • MyBatis Xml映射文件之字符串替换方式

    2022-03-23 00:06:39
  • 详解Android Studio无法检测新版本问题解决

    2021-08-01 08:45:05
  • C# 判断字符串为空的几种办法

    2023-05-21 16:06:44
  • C#提取网页中超链接link和text部分的方法

    2023-02-24 02:04:14
  • Kotlin操作符重载实例详解

    2022-11-28 14:25:32
  • Java实现验证码的产生和验证

    2022-10-30 22:41:39
  • Android 详解沉浸式状态栏的实现流程

    2023-12-18 23:03:31
  • C#画笔Pen绘制光滑模式曲线的方法

    2021-11-26 05:13:33
  • Android使用Gallery实现照片拖动的特效

    2022-12-31 23:04:22
  • 如何安装系统认证签名过的APK

    2023-07-24 21:35:40
  • 从java中调用matlab详细介绍

    2023-08-01 14:04:17
  • Java从JDK源码角度对Object进行实例分析

    2022-04-09 20:12:22
  • Java中自动装箱、拆箱引起的耗时详解

    2023-01-11 11:42:42
  • Java8之lambda最佳实践_动力节点Java学院整理

    2023-11-28 00:07:28
  • ionic监听android返回键实现“再按一次退出”功能

    2021-12-24 10:22:57
  • C#提取PPT文本和图片的实现方法

    2022-10-28 08:02:59
  • PageHelper在springboot+mybatis框架中的使用步骤及原理解析

    2023-07-28 21:40:09
  • asp之家 软件编程 m.aspxhome.com