关于前端:canvas排版的实践

10次阅读

共计 2187 个字符,预计需要花费 6 分钟才能阅读完成。

demo 放在首位:https://dante.jdtj.top/gent/

​ 我依赖 pixijs,编写了一个用于 canvas 排版的库。

​ 这里的排版不同于 html2canvas 之类的库,它们是生成一张图片,这里的排版是要整个页面用 canvas 绘制,包含动画、交互等等 (相似 react-canvas,外国小红书搞进去的货色,曾经凉了)

​ 做这个货色,次要是优化长列表和加强交互成果。长列表的 dom 计划有虚构列表只渲染可视区的节点,然而在疾速滚动的时候,高低会留白。然而如果用 canvas 来解决,能够失去一个简直完满的成果。举个例子:https://chart.caihongduoduo.com/chart?lotteryId=1000&lotteryL…(在手机上关上)。能够看到,canvas 解决后的长列表十分晦涩。

页面都用 canvas 排版后,能实现什么成果:

  1. 外部自带优化计划,解决海量节点渲染的性能问题。

    两种优化方法:

    ​ 其一:不在可视区的内容,跳过渲染。不影响它的节点对象,在它不被渲染时也能够对其属性进行操作

    ​ 其二:对页面部分进行缓存,在页面重排重绘时,缩小渲染

  2. 页面成果更丰盛

    一、封装补间动画办法,实现相似 css 动画的成果

      /**
       *
       * @param params
       * name 动画名称
       * duration 动画执行时长 ms
       * delay 提早多久执行
       * func 补间动画执行的 贝塞尔办法名 或者 动画模板名称
       * attr{} 动画操作的属性
       * callback 动画执行结束后的回调
       */
    regKeyFrames(params)
 

 二、在节点上调用 ```regCustomRender(canvas: HTMLCanvasElement)``` 后,会用传入的 canvas 笼罩节点自身的渲染,在联合 ```getSnapshoot('base64')``` 获得节点的渲染后果能够实现炫酷的成果。这是 demo 的录屏:https://dante.jdtj.top/gent/demo.mp4
  1. 原滋原味的截图,不会有兼容问题和失真。但也要留神图像的跨域问题

页面如何便捷排版

节点

​ 想要齐全实现 dom 的排版体验比拟艰难。我目前实现了一套简略的排版形式:

Graph      裸露一个 pixiJS 的 Graphics 对象,充当 "canvas" 的角色
Text      文本
Image     图片
Input     输入框,对 input 进行包装,反对 type = ['text', 'password', 'number']    
Video      视频渲染
Select      下拉框
Option      下拉框的选项

ScrollY   纵向滚动容器,主动计算内容高度和滚动条
ScrollX   横向向滚动容器,主动计算内容宽度和滚动条
HorLinearLayout 横向线性布局, 外部元素都是程度排列
VerLinearLayout 纵向线性布局,外部元素都是垂直排列
AbsoluteLayout" 相对定位布局,外部元素基于 AbsoluteLayout 定位,AbsoluteLayout 基于父级定位
FixedLayout 固定定位布局,外部元素基于 FixedLayout 定位,FixedLayout 基于 app 挂载对象定位 

​ 这些个布局容器能够互相嵌套,尽管写法比拟啰嗦,但曾经能够实现大部分的页面布局。

属性

​ 在属性上,也反对了 %,px,calc,auto。这些外面最难实现的是 auto。其余几个的子父级影响都能够认为是单向的,都是子级依赖父级的尺寸进行计算,而 auto,它就须要子级尺寸变动时影响父级的尺寸,父级又会影响父级的父级和父级的子级,引起大量的计算。这样的影响,直到传递到尺寸不受影响的节点为止,因为它没有被这次从新计算扭转尺寸,那么它就不会影响它的子级和父级,影响进行于此。

目前实现了以下的属性:

width
height
marginLeft
marginRight
marginTop
marginBottom
borderLeftWidth
borderRightWidth
borderTopWidth
borderBottomWidth
borderLeftColor
borderRightColor
borderTopColor
borderBottomColor
rotate 旋转角度 0-360
anchor 锚点,rotate 和 scale 受它的影响
bgColor 背景色
top AbsoluteLayout,FixedLayout 和他们的子节点可用。HorLinearLayout 的子节点可用
bottom AbsoluteLayout,FixedLayout 和他们的子节点可用。HorLinearLayout 的子节点可用
left AbsoluteLayout,FixedLayout 和他们的子节点可用。VerLinearLayout 的子节点可用
right AbsoluteLayout,FixedLayout 和他们的子节点可用。VerLinearLayout 的子节点可用
id 通过 getElementById 找到节点
groupId 通过 getElementsByGroupId 找到节点组,相似 getElementsByClassName

// text 特有属性
lineHeight 行高
fontSize 字号
fontColor 文字色彩
text 文字内容
fontFamily 
wordWrap
breakWords
其余

​ 所有的节点都自带 overflow: hidden 成果

正文完
 0