这周因为给朋友的游戏配场景的BGM,没能写什么教程demo(其实就是懒),但是又不能让你们看出我啥也没干,于是就有了这篇应用与优化的话题,同时也是一篇预告贴,下周开始,将会是一期连续的实战 个人头像生成器
原料: vue express mongo canvas node
火候: 每章都会有关核心实现,不会索然无味
周期: 1-2周内完成
特色: 如何根据用户的输入qq邮箱来生成独一无二的个人头像
预告到此结束.......
进入正题
什么时候用dom 什么时候canvas/svg
dom方便操作是因为因为dom具有层级结构与一大堆爽手的交互api,但是在浏览器渲染的时候却并不轻松,大量嵌套dom将增大浏览器深度遍历的时间,所以才有了virtual dom
与diff
的配合利器。
canvas单层渲染,哪怕是如同之前的伪3d中的层级效果,也只是在同一层dom中,并不会因为渲染问题增大浏览器在渲染页面时的耗时。 开发时,我们可以考虑将一些浅交互的效果统一抛给canvas(如轮播图)去处理,这样,我们就可以在增强视觉效果的同时降低浏览器的渲染损耗。
有关getImageData跨域的问题
这个问题也是有很多人在群里问我的,其实一般出现这种问题大多是本地运行的时候,这个问题网上也有答案的,办法有点低俗,就是推荐你换一个浏览器或者挂在服务器上。 因为本地的文件夹默认是没有域名的。
"Uncaught DOMException: Failed to execute 'getImageData' on 'CanvasRenderingContext2D': The canvas has been tainted by cross-origin data.
复制代码
如果你在服务器上也跨域了,那你可以试试
var img = new Image();
img.crossOrigin = '';
img.onload = function () {
ctx.drawImage(this, 0, 0);
ctx.getImageData(0, 0,200,200);
};
复制代码
缓存问题
在使用canvas的时候,可能会存在没有图形被绘制出来的情况,除却代码的问题,则是因为上一帧的图形还未绘制完成,便被clearRect
了,所以我们会需要一个缓存进行来预处理,这里需要的就是离屏处理。
var offscreen = document.createElement("canvas");
offscreen.width = 1000;
offscreen.height = 1000;
var offctx =offscreen.getContext("2d");
复制代码
我们创建了离屏画布后,可以把需要处理绘制的东西交由它处理,绘制后再直接使用drawImage
来将它绘制到主画布上。
当需要处理的对象越多,一个离屏可能也会造成画面卡顿的其情况,这时候,我们就可以把离屏规划给小对象,让每个对象都拥有一个自己的绘制环境,这样,就大大提升了渲染的流畅度。 这里是个测试用例,我不知道你们如何,我这边跑个千把个小球没啥问题
像素处理的选择
当我们要做像素的处理的时候,可以使用bitmap
或者Arradata
,这时我们就需要去做一个选择,bitmap
具有宽高,我们可以较容易对平面内的像素点去进行坐标的定位,但是其同时其时间复杂度与空间复杂度就比Arraydata
要高,所以在选择的时候要根据实际情况来做选择。
如何学习canvas
有人问了我这个问题,canvas的api很少,哪怕webgl都比它要多,只是webgl的难点不在于api,而是在于shader
的编写。
- 如果你打算只做2d,那么可以考虑入手一款软件ps/sketch,算法上不做要求,毕竟我也很菜,但是要有一定的高数与物理基础,以及少量图形学的基础,如果你是PS玩的比较熟的,那就另当别论,我是从初二开始入的PS的坑,上手canvas所以有一定优势。
- 在学canvas的时候,网上有很多比较浅显的视频教程,可以去看一看,更多的是要接触图形引擎(包括包含画面逻辑的游戏),想一想它们如何实现,可以提升逻辑的思维
- 如果向入手webgl,那可以先从
three.js
来上手,再去了解webgl,是真的挺难的,我也是个菜鸡,不过在学习的过程中,可以很大的提升你对图形的绘制渲染了解。
以上几种是常遇到的问题,也有可能我没有提到的,可以向我提问,我会尽可能地为你们解惑。
不定期更新canvas与svg的相关技术教程,有实战型,也会有主原理型的,2d 2.5d 3d都会包含到,同时涉及的有 线性代数 物理 图形学等相关的基础知识。
欢迎各位客官收藏关注 投硬币包养