专栏首页jianhuicode关于贝塞尔曲线的故事

关于贝塞尔曲线的故事

概述

  • 在开始本故事的之前,先来介绍下故事的背景。话说几百年前,从天而降一座神山,远远看去像一天光滑的丝带,它的名字叫做:“贝塞尔曲线"。有大法师预言登上这座神山可以发现天地大秘但是前途艰险。

定义

  • 摘自百科 贝塞尔曲线(Bézier curve),又称贝兹曲线或贝济埃曲线,是应用于二维图形应用程序的数学曲线。一般的矢量图形软件通过它来精确画出曲线,贝兹曲线由线段与节点组成,节点是可拖动的支点,线段像可伸缩的皮筋,我们在绘图工具上看到的钢笔工具就是来做这种矢量曲线的。 “贝赛尔曲线”是由法国数学家Pierre Bézier所发明,由此为计算机矢量图形学奠定了基础。它的主要意义在于无论是直线或曲线都能在数学上予以描述。

公式

  • 由于应用用到主要以二阶贝塞尔曲线为主,贴下二阶的公式: 二次方公式 二次方贝兹曲线的路径由给定点P0、P1、P2的函数B(t):

如何应用?

  • 为了前往"贝塞尔曲线山",向那些从前登上神山的老前辈请教;

所需的Android知识

  • 画笔(paint),路径(path),画布(canvas)类的api要熟悉
  • View绘制的生命周期 简单来看:测量-measure 摆放-layout 绘制-draw
  • Android触摸事件 这里需要了解onTouchEvent方法可以捕捉到触屏的事件

用手势画光滑的曲线

  • 路途艰险,在这里我碰到了大白虎,史前巨兽猛犸象,海天鲲鹏,经历了生死考验终于登上神山,恍然大悟,天地大秘原来在此。
  • 让我们想一想画东西需要什么?答案:一块白板,一只笔。
  • 这里的关键是手势与光滑,处理手势的话就是前面讲的重写Android触摸事件,聪明的你一定想到了通过二阶贝塞尔曲线去做到光滑。
  • 画一条二阶贝塞尔曲线需要3个点,两个数据点一个控制点,那么手势落下的点--起始点(x1,y1)与不断移动的手的触点是数据点,控制点需要自己创造,那线段的中点是最好计算的,假设第一个手滑动到的点(x2,y2),那么中点就是((x1+x2)/2,(y1+y2)/2)。
  • 重写Android触摸事件需要捕捉MOVE类型与DOWN类型的事件,DOWN类型的事件中需要记录起始点的位置,而MOVE类型事件需要缓冲上一次移动的位置。
  • 1.声明控制点,曲线,起始点,以及判定滑动的距离
private  Paint controlPaint;

private Path mCurrentPath;

private float startPointX;
private float startPointY;
//画贝塞尔曲线的标识--可以自定义值
private float offset = ViewConfiguration.get(getContext()).getScaledTouchSlop();
  • 2.初始化画笔与路径
  public PaintBeSaiErView(Context context, @Nullable AttributeSet attrs) {
    super(context, attrs);
    //建立路径
    mCurrentPath = new Path();
    //绘制时抗锯齿
    controlPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
    //设置画笔样式
    controlPaint.setStyle(Paint.Style.STROKE);
    //设置画笔的粗细
    controlPaint.setStrokeWidth(8);
    //设置画笔颜色
    controlPaint.setColor(Color.RED);

}
  • 3.重写onTouchEvent,记录手势起始点与移动位置并绘制贝塞尔曲线,通过invalidate方法更新UI视图
  @Override
public boolean onTouchEvent(MotionEvent event) {
    switch (event.getAction()){
        case MotionEvent.ACTION_DOWN:
            //为了方便测试,每次下落之前清空路径
            mCurrentPath.reset();
            float x = event.getX();
            float y = event.getY();
            startPointX = x;
            startPointY = y;
            //移动到起始点
            mCurrentPath.moveTo(x, y);
            invalidate();
            break;
        case MotionEvent.ACTION_MOVE:
            float curX= event.getX();
            float curY= event.getY();
            float preX= startPointX;
            float preY= startPointY;
            if(Math.abs(preX-curX)>=offset||Math.abs(preX-curY)>=offset) {
                mCurrentPath.quadTo((curX + preX) / 2, (curY + preY) / 2, curX, curY);
                startPointX = curX;
                startPointY = curY;
            }
            invalidate();
            break;
    }
    return  true;
}
  • 4.下面对比使用线段画lineTo(curX, curY)与贝塞尔曲线画quadTo(avgX,avgY)的效果 左图为线段画的,右图为贝塞尔曲线画的,看起来更圆润!why?其实,用线段画基本上看是一个折线图,而贝塞尔函数画是一段段曲线
  • 当然,贝塞尔曲线的应用十分广泛,上面是简单的例子,后面将讲如何应用模拟翻页。

总结

  • 总以为登上神山才是最大的收获,原来一路走来更有收获。
  • 去了解一个事物的时候,要善于思考,记忆中越来越深刻的,往往思考的越透彻。

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • com.android.ddmlib.InstallException: Unable to upload some APKs?

    真机调试时,cmd命令中执行react-native run-android时出现com.android.ddmlib.InstallException: Un...

    用户1148881
  • ERROR 1045 (28000): Access denied for user 'root'@'localhost' (using password: NO)

    使用如下方法即可解决,本人已验证可行。 #1.停止mysql数据库 /etc/init.d/mysqld stop #2.执行如下命令 mysqld_safe...

    用户1148881
  • 仿腾讯课堂固定滚动列表ReactNative组件

    前言 由于业务需要做成类似腾讯课堂课程详情滚动的效果,考虑到后面有可能有新的呈现方式,RN提供的组件没有这种滚动控件,不如自己封装,其实去年已经写了一篇但是写的...

    用户1148881
  • 金融工程高度概览

    整个流程图分为 6 大模块,除了开始的“数据参数”模块,后 5 个模块都有相对应的函数。

    用户5753894
  • Android 贝塞尔曲线实战之网易云音乐鲸云特效

    APP开发市场已经告别“野蛮生长”时代,人们不再满足于APP外形创新,而将目光转向全方面的用户体验上。在这过程中,动效化作为移动互联网产品的新趋势,如何实现酷炫...

    个推君
  • View绘制系列(8)-Canvas贝塞尔曲线绘制

    宁从直中来,不从曲中求,虽然直线应用很多,但曲线亦然。在Path类说明的部分,我们就聊到其主要作用是用来描述直线段,二次曲线及三次曲线所组成的复合几何路径,在前...

    小海编码日记
  • MySQL里面的group by问题浅析

    mysql> select backup_date ,count(*) piece_no from redis_backup_result;

    jeanron100
  • 贝塞尔曲线开发的艺术

    用户1907613
  • Dart核心基础List概述

    题记:不到最后时刻,千万别轻言放弃,无论结局成功与否,只要你拼博过,尽力过,一切问心无愧

    早起的年轻人
  • Prometheus + Granafa 构建高大上的MySQL监控平台

    对于MySQL的监控平台,相信大家实现起来有很多了:基于天兔的监控,还有基于zabbix相关的二次开发。相信很多同行都应该已经开始玩起来了。我这边的选型是Pro...

    黄泽杰

扫码关注云+社区

领取腾讯云代金券