似曾相识的标题,没错,本年年初就发布过一篇《兔年了,一重用Compose来画兔子吧》的文章,那是我刚开始学习Compose发布的榜首篇文章,没放链接的原因是兔子太丑就别点进去看了,辣眼睛辣眼睛,那篇文章首要是针对Compose里面的Canvas做针对性操练,了解一下怎样制造各种形状的几何图形,而在前不久华为推出了HarmonyOS NEXT之后,关于我们Android开发者来讲,所要把握的技能栈里面毫无疑问又多了一个开发言语,那就是ArkTS,所以跟Compose相同,我学习ArkTS的榜首步也从学习它的Canvas开始,今天我也用ArkTS来画一只跟年初差不多画风的兔子,眼睛就再辣一次吧,学习基础知识最重要

准备作业

首要来创建我们的自定义组件,命名为Rabbit

兔年了,一重用ArkTS来画兔子吧

@Entry@Component都是装饰器,@Component标明这个是自定义组件,@Entry标明该组件为进口组件,在build()办法中我们就可以写首要的UI代码,这一点与Flutter类似,至于怎样选择我们界面上的父组件,由于毕竟这儿只会有一个Canvas,所以父组件怎样选择没有太大要求,我直接将官方api文档里面的样式代码复制过来了

兔年了,一重用ArkTS来画兔子吧

父组件用的是弹性组件Flex,这儿设置的是主轴方向是FlexDirection.ColumnalignItems标明里面子组件在穿插轴方向上的对齐办法,这儿设置的是ItemAlign.Center居中对齐,justifyContent标明子组件在主轴方向上的对齐办法,这儿设置的是FlexAlign.Center居中对齐,然后在组件后边是设置的组件本身的一些特征,这儿设置的是宽高,都是占满全屏,这种特征的设置办法类似于Compose里面的Modifier,创建好父组件之后,我们接下来就是创建我们子组件Canvas

兔年了,一重用ArkTS来画兔子吧

这儿Canvas的创建办法不得不让我有点槽点不吐不快

  • 槽点一:这儿创建了一个RenderingContextSettings方针和一个CanvasRenderingContext2D,可以了解为就是Canvas的画布方针,但是关于Canvas来说最首要的东西为什么不在Canvas组件内部创建结束往后经过onReady函数回调出来呢,非得让开发者手动new出来再传到Canvas里面去,这个声明式ui也不是特别的“声明”
  • 槽点二:在槽点一里面说了Canvas的创建进程需求new一个CanvasRenderingContext2D方针后传到Canvas的结构函数里面去,但是我发现假定不传参数的话,也不会编译报错,乃至可以run起来,那会我还没看Canvas源码,揣摩着难道Canvas里面还有一个默许的CanvasRenderingContext2D方针吗,效果一看模拟器界面,一片空白。。。好吧,我知道了,有必要传~
  • 槽点三:在组件内部运用组件的局部变量时分,必定要用this去指向这个变量,否则编译器会报错,说找不到它了,横竖毕竟整只兔子画完我是this麻了

创建完Canvas之后,由于制造的进程根柢上是核算各种坐标的进程,所以需求知道整个画布的宽和高,我们在添加两个变量来标明画布的宽高

兔年了,一重用ArkTS来画兔子吧

这儿screenXscreenY分别标明画布的宽和高,我们看到在这俩变量前面也有一个装饰器@State润饰,被这个装饰器润饰的变量我们叫它状态变量,当它的值发生变化的时分会触发ui改写,类似于Flutter的setState,Compose的remember,所以我们在onReader函数里面将画布的宽高设置到screenXscreenY里面去

开始制造

这儿的头部我们就用一个圆圈来标明,在ArkTS里面运用arc函数来制造圆圈,这个函数既可以制造圆圈,也可以画圆弧,供应如下几个参数

兔年了,一重用ArkTS来画兔子吧

前两个参数代表圆心坐标,radius标明圆弧或许圆的半径大小,毕竟一个参数couterclockwise标明制造圆弧的方向,默许是逆时针,最要害的是startAngleendAngle这俩个参数,我们留心看这俩参数后边的描绘写的是弧线的开始弧度于连续弧度,单位是弧度而不是角度,所以你假定想画个半圆,传的是0和180的话,出来的依然仍是个圆,正确的做法是运用核算弧度的公式来做

弧度=度数*/180

知道要害点往后就要开始画这个圆了,先设置一下画笔的粗细与色彩

兔年了,一重用ArkTS来画兔子吧

接着就调用arc函数来画这个圆,我们圆的中心点就定在了画布的中心点方位,也就是screenX/2screenY/2

兔年了,一重用ArkTS来画兔子吧

制造圆弧的代码就这一行结束了,但是我们作业一遍代码后发现模拟器上什么都没有,原因是我们少加了一行代码,在ArkTS中你需求显式的标明你画的图形是空心的仍是实心的,分别用下面两个函数来标明

兔年了,一重用ArkTS来画兔子吧

这看似是一句配备类型的代码,但你在后边会发现每调用一次制造函数就要写一下stroke()或许fill(),不调用的话制造的效果就不出来,假定你不信我们接下来就做个试验,来画两个圆,一个在调用好arc函数往后调用了stroke,另一个没有调用,代码是这个姿态的

兔年了,一重用ArkTS来画兔子吧

我们在原本兔头的圆心方位下面又添加了一个略小一点的圆,我们作业下代码看看实际效果怎样

兔年了,一重用ArkTS来画兔子吧

可以看见屏幕上确实只需一个圆,只需当我们把下面那个圆的stroke函数补充好,那个略小一点的圆才呈现了

兔年了,一重用ArkTS来画兔子吧

兔年了,一重用ArkTS来画兔子吧

一个好消息,一个坏消息,好消息是俩圆都出来了,坏消息是,咋俩圆之间还有根黑线呢?咱也没画啥剩下的线啊,查了下api文档才知道,我们又少加代码了,文档里面说,假定一个途径画完了要开始下一个途径了,需求调用beginPath函数,否则就是像我们这俩圆相同,两个途径还有一处相连的当地,它认为你榜首笔还没有画完,毕竟当我把beginPath函数加到代码里面之后,毕竟效果才正常了

兔年了,一重用ArkTS来画兔子吧
兔年了,一重用ArkTS来画兔子吧

好了,槽点再多,这个也毕竟是语法,我们将小一点的圆去调持续来画兔子

鼻子

现在开始画兔子的鼻子,这儿我方案运用三角形来标明鼻子,但是在现有的api中没有现成的函数来画三角,我们只能经过画path来结束,画path同我们曾经在Android里面画path根柢相同,先调用moveTo供认起点,然后调用lineTo来画途径,毕竟画完往后调用closePath结束当时途径构成一个封闭途径,代码如下所示

兔年了,一重用ArkTS来画兔子吧

兔年了,一重用ArkTS来画兔子吧

鼻子很简略,我们接下来画兔唇

兔唇

兔唇分左兔唇与右兔唇,其实就是两个圆弧,我们可以运用之前用过的arc函数来结束,但是我们这儿运用另一个函数来画圆弧,那个就是arcTo,用法如下所示

兔年了,一重用ArkTS来画兔子吧

这个函数是依据圆弧经过的点和半径大小来供认整个圆弧的样式,在调用这个函数之前还有必要调用moveTo来供认圆弧的起点,所以画一个圆弧需求供认好三个点,至于怎样找出这三个点,这个同制造二阶贝塞尔曲线的思路是相同的,moveTo是榜首个固定点,arcTo函数前两个参数标明曲线控制点的xy坐标,后边两个参数标明曲线连续固定点的xy坐标,这姿态应该了解起来会便当一些,所以我们左右兔唇的制造代码和效果图如下所示

兔年了,一重用ArkTS来画兔子吧

兔年了,一重用ArkTS来画兔子吧

眼球与眼眶

然后我们在兔子脑袋偏上方位画眼球,眼球就是两个实心圆,圆的制造办法现已知道了,这儿是需求留心一下假定希望兔子眼球的色彩同线条色彩不相同,就需求设置一下画笔实心的色彩,一起制造结束需求调用fill函数来标明当时制造的是实心图形,下面就是制造左右眼球的代码

兔年了,一重用ArkTS来画兔子吧

作业一下看看效果

兔年了,一重用ArkTS来画兔子吧

只需眼球子的话看起来较显板滞,所以需求在眼球子上面画上眼眶,眼眶现在画起来就简略多了,那就是个半圆,起点与结束的y坐标与眼球子一起,然后x坐标左右各加上点偏移量就好了,中心的控制点的x坐标与眼球子的x坐标一起,y坐标向上偏移一点就好,代码如下

兔年了,一重用ArkTS来画兔子吧

现在再看看效果

兔年了,一重用ArkTS来画兔子吧

现在看起来有神了,我们接着下一步

耳朵

记住在之前用Compose画兔子的时分,耳朵是用两个椭圆来结束的,然后椭圆的底部重复调整才跟脑袋连在一起,办法有点太sa了,这次不方案这么做,首要兔子耳朵不可能直溜溜的竖在脑袋上的,肯定会歪斜一点,其次兔子的耳朵严峻来讲并不能用椭圆来标明,毕竟挨近脑袋部分并不相连在一起,假定连在一起了,我们拽兔子耳朵的时分,就很简略拽断了。。。更形象的应该是兔子脑袋上找出两个点,然后各自向上画曲线,毕竟在一个点连在一起构成一只耳朵,所以一只耳朵其实是由两根三阶贝塞尔曲线构成,那么榜首步需求先找出两根曲线的起点,这个起点在脑袋上,那么就需求依据半径与角度核算出一个圆周上某一个点的坐标,下面是左耳的两个起点坐标的核算代码

兔年了,一重用ArkTS来画兔子吧

这儿就是运用数学公式sin与cos来核算xy坐标,从传值上就能看出,sin与cos函数接纳的也是以弧度为单位的数值,至于这儿的取值,sin与cos函数里面的角度是按照顺时针来核算的,起点在圆的最左边,而我们之前在运用arc函数画圆弧的时分,里面传的角度默许按照逆时针方向旋转的,起点在圆的最右侧,这儿是存在差异的,要留心一下,所以在代码中,leftxlefty是比较挨近脑袋顶部的点,而leftOutXleftOutY是比较靠外侧的点,然后我们以这两个点为参照点,就能将贝塞尔曲线其他几个点找出来,毕竟左耳朵的制造代码如下所示

兔年了,一重用ArkTS来画兔子吧

作业一下代码,左耳朵就有了

兔年了,一重用ArkTS来画兔子吧

我们再以相同的办法将右耳的坐标算出来,代码与效果图如下所示

兔年了,一重用ArkTS来画兔子吧

兔年了,一重用ArkTS来画兔子吧

这只兔子可算开始萌起来了~

身体

兔子的身体在之前Compose的文章里面也是用椭圆来标明的,但是相同感觉如同一拽兔子就能把兔子拽断相同,所以这儿身体的制造同耳朵相同,也是用一个三阶贝塞尔曲线从兔子脑袋下边的一头连到另一头,剩下两个点就选择画布靠下一点的方位,代码如下

兔年了,一重用ArkTS来画兔子吧
兔年了,一重用ArkTS来画兔子吧

效果图就是上面这个姿态了,算是抵达预期要的效果了吧,然后给兔子加上两只爪子

兔爪

兔爪我们用两个椭圆型标明,在ArkTS里面制造椭圆的api我们运用ellipse函数来结束,它需求的参数如下所示

兔年了,一重用ArkTS来画兔子吧

兔年了,一重用ArkTS来画兔子吧

前两个参数同制造圆弧相同,是中心点坐标,第三个参数radiusX是x轴的半径,radiusY是y轴半径,rotation是旋转角度,startAngleendAngle是开始点与连续点坐标,毕竟一个参数相同也是制造的方向,默许是fasle,逆时针,都是比较简略填的参数,其间中心点的x坐标我们参看之前画身体时分第二,三个点的x坐标,再往里偏移一些,而椭圆的y坐标我们就选择screenY * 3/4的高度,这样制造两只爪子的代码就有了

兔年了,一重用ArkTS来画兔子吧

我们看到这儿还将爪子设置成实心的,实心填充色彩设置成纯黑,由于之前兔子眼球是赤色的,所以这儿要留心下眼球与爪子的制造次序,假定眼球在爪子的下面制造,那么眼球也变成黑色的了,除非在制造眼球之前从头设置下fillStyle,再更改下填充色值,现在我们作业下代码,两个爪子就出来了

兔年了,一重用ArkTS来画兔子吧

尾巴

毕竟一个就是画尾巴,尾巴方案用一个圆来标明,圆的话我们上面现已讲过怎样制造了,首要仍是寻觅中心点坐标,这边中心点的x坐标就用之前画身体用到的第三个控制点的x坐标,也就是变量endX,y坐标的高度就确认为四分之三的画布高度,代码如下所示

兔年了,一重用ArkTS来画兔子吧

这儿圆的半径经过重复调试毕竟确认为20,我们现在跑下代码,尾巴就有了

兔年了,一重用ArkTS来画兔子吧

现在我们在优化下,给这个圆加点分割线,让它看起来毛茸茸一点,分割线我们运用setLineDash函数来结束

兔年了,一重用ArkTS来画兔子吧

这个函数接纳一个数组,数组里面榜首个值标明实线长度,第二个值标明空位长度,我们随意设置两个值来看看效果

兔年了,一重用ArkTS来画兔子吧

兔年了,一重用ArkTS来画兔子吧

现在看起来是不是更像一只毛茸茸的尾巴

总结

到这儿我们现已结束了运用ArkTS来制造一只兔子的整个进程,其实兔子本身颜值怎样到不是很重要,这篇文章的要害首要仍是了解一下ArkTS里面的Canvas组件,以及这个组件里面供应的api,尽管只是一个组件就有不少槽点,但每个言语都有每个言语的特性,作为一个技能人,对新出来的技能,特别这个仍是国内自己的技能,应该更多的是去开掘这个技能的利益,以及它与其他言语都有什么异同,这个才是应该做的作业。