Canvas2D基础

什么是Canvas

<canvas>是H5中最受欢迎的元素,在页面上划出一片区域,利用JS在上面画出图形,起初由Apple公司提出,各大浏览器厂商也对其做了不同程度上的实现。canvas中规定了了2D context和3D context(WebGL),目前绝大部分浏览器支持2D context。WebGL的发展还比较缓慢。

基本使用

1、toDataURL() 将画好的图像输出为图片

//get data URI of the image
var imgURI = drawing.toDataURL("image/png");
//display the image
var image = document.createElement("img");
image.src = imgURI;
document.body.appendChild(image);

2、原点是基于canvas元素左上角
3、2D Context的两个基本绘画操作 fill and stroke

Rectangles(矩形)

1、fillRect()

image.png

context.fillRect(10, 10, 50, 50);
//draw a blue rectangle that’s semi-transparent
context.fillStyle = "rgba(0,0,255,0.5)";
context.fillRect(30, 30, 50, 50);

2、strokeRect()

image.png

//draw a red outlined rectangle
context.strokeStyle = "#ff0000";
context.strokeRect(10, 10, 50, 50);
//draw a blue outlined rectangle that’s semi-transparent
context.strokeStyle = "rgba(0,0,255,0.5)";
context.strokeRect(30, 30, 50, 50);

3、clearRect()

image.png

//draw a red rectangle
context.fillStyle = "#ff0000";
context.fillRect(10, 10, 50, 50);
//draw a blue rectangle that’s semi-transparent
context.fillStyle = "rgba(0,0,255,0.5)";
context.fillRect(30, 30, 50, 50);
//clear a rectangle that overlaps both of the previous rectangles
context.clearRect(40, 40, 10, 10);

Drawing Paths

1、如何画一个表盘

var drawing = document.getElementById("drawing");
//make sure <canvas> is completely supported
if(drawing.getContext) {
   var context = drawing.getContext("2d");
   //start the path
   context.beginPath();
   //draw outer circle
   context.arc(100, 100, 99, 0, 2 * Math.PI, false);
   //draw inner circle
   context.moveTo(194, 100); //将光标移动这个内圆绘制的起点上
   context.arc(100, 100, 94, 0, 2 * Math.PI, false);
   //draw minute hand
   context.moveTo(100, 100);
   context.lineTo(100, 15); // 从最后绘制点到(100,15)绘制一条线
   //draw hour hand
   context.moveTo(100, 100);
   context.lineTo(35, 100);
   //stroke the path
   context.stroke();
}
image.png

2、判断一个坐标点是否在绘制路线上
context.isPointInPath(100, 100) // true

Drawing Text

1、fillText() 、 strokeText() 后者很少用
2、3个属性font、 textAlign、 textBaseline
3、Demo


image.png
context.font = "bold 14px Arial";
context.textAlign = "center";
context.textBaseline = "middle";
context.fillText("12", 100, 20);
//start-aligned
context.textAlign = "start";
context.fillText("12", 100, 40);
//end-aligned
context.textAlign = "end";
context.fillText("12", 100, 60);

4、measureText()的使用 可以度量文字大小

// 如果文字的长度大于140,就将字体缩小
var fontSize = 100;
context.font = fontSize + "px Arial";
while(context.measureText("Hello world!").width > 140) {
    fontSize--;
    context.font = fontSize + "px Arial";
}
context.fillText("Hello world!", 10, 10);
context.fillText("Font size is " + fontSize + "px", 10, 50);
image.png

Transformations

  1. 图像变换方法
    rotate(angle)
    scale(scaleX, scaleY)
    translate(x, y)
    transform(m1_1, m1_2, m2_1, m2_2, dx, dy)
    setTransform(m1_1, m1_2, m2_1, m2_2, dx, dy)

  2. 可用translate重新定义原点的位置,
    在画圆的时候,可将原点位置移动圆心位置,这样在画圆定位过程中比较方便

  3. context.rotate 注意是将坐标轴进行旋转


    image.png

Drawing Images 图片绘制

  1. 从当前canvasd的坐标(10,10)的位置将图片插入进来(注意,如果图片在canvas中装不下,那么图片是插入不进来的)
var image = document.images[0];
 context.drawImage(image, 10, 10);
  1. 指定区域内插入 -- 执行在从(10,10)开始,宽90,高90的区域内绘制图像
context.drawImage(image, 10, 10,90,90)
  1. 将图像上指定区域的部分 插入 canvas中的指定区域(相当于剪切原图像上的一部分到canvas中)
//从图像上(0,10)开始,宽150,高385的区域插入到 canvas中从(0,100)开始,宽40,高60的区域内
context.drawImage(image, 0, 10, 150, 385, 0, 100, 40, 60);
image.png
  1. 注意,如果插入进来的图片是在别的域名下的,会报错

shadows 加阴影

DEMO:


image.png
var drawing = document.getElementById("drawing");
var context = drawing.getContext("2d");
context.shadowOffsetX = 5;
context.shadowOffsetY = 5;
context.shadowBlur = 4;
context.shadowColor = "rgba(0, 0, 0, 0.5)";
//draw a red rectangle
context.fillStyle = "#ff0000";
context.fillRect(10, 10, 50, 50);
//draw a blue rectangle
context.fillStyle = "rgba(0,0,255,1)";
context.fillRect(30, 30, 50, 50);

Gradients 渐变色

  1. 线性渐变


    image.png
var gradient = context.createLinearGradient(30, 30, 80, 80);
gradient.addColorStop(0, "white");
gradient.addColorStop(1, "black");
context.fillStyle = gradient;
context.fillRect(30, 30, 50, 50);
  1. 径项渐变


    image.png
var gradient = context.createRadialGradient(55, 55, 10, 55, 55, 30);
gradient.addColorStop(0, "white");
gradient.addColorStop(1, "black");
context.fillStyle = gradient;
context.fillRect(30, 30, 50, 50);

Patterns 模式

  1. 即图像的重复模式 ,跟css一样 “repeat”, “repeat-x”, “repeat-y”, no-repeat”
var context = drawing.getContext("2d");
var image = document.images[0],
    pattern = context.createPattern(image, "repeat");
//draw a rectangle
context.fillStyle = pattern;  // 图像repeat模式仍然是从(0,0)开始的
context.fillRect(30, 0, 150, 150); // 这里的意思是绘制矩形,并让图像repeat模式在该矩形区域显示,并不是说 图片repeat是从绘制该矩形的起点开始的,渐变也是如此
image.png

Working with Image Data 图像原始数据

可以用来做滤镜效果,详细可看 www.html5rocks.com/en/tutorials/canvas/imagefilters/

Compositing 合成

两个图像之间如何纠缠的,这里举一个例子,其他雷同


image.png
var drawing = document.getElementById("drawing");
var context = drawing.getContext("2d");
//draw a red rectangle
context.fillStyle = "#ff0000";
context.fillRect(10, 10, 50, 50);
//change the global alpha
context.globalCompositeOperation = "xor";
//draw a blue rectangle
context.fillStyle = "rgba(0,0,255,1)";
context.fillRect(30, 30, 50, 50);

总结

  1. canvas内容就是上面这些了,就好比设计师能用的颜色就那么多,但是将颜色,图形组合起来,创意真的是无限的,canvas也是如此。
  2. webGL是一个 对OpenGL ES 2.0浏览器实现接口,用于3D绘画,生产阶段最好不要用,可用于实验阶段。
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 213,186评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,858评论 3 387
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 158,620评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,888评论 1 285
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,009评论 6 385
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,149评论 1 291
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,204评论 3 412
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,956评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,385评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,698评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,863评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,544评论 4 335
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,185评论 3 317
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,899评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,141评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,684评论 2 362
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,750评论 2 351

推荐阅读更多精彩内容

  •   HTML5 添加的最受欢迎的功能就是 元素。这个元素负责在页面中设定一个区域,然后就可以通过 JavaScri...
    霜天晓阅读 3,006评论 0 2
  • 本章内容 理解 元素 绘制简单的 2D 图形 使用 WebGL 绘制 3D 图形 这个元素负责在页面中设定一个区域...
    闷油瓶小张阅读 843评论 0 0
  • 一、canvas简介 参考H5之canvasCanvas是HTML5新增的组件,它就像一块幕布,可以用JavaSc...
    合肥黑阅读 6,459评论 0 3
  • 一、canvas简介 1.1 什么是canvas?(了解) 是HTML5提供的一种新标签 Canvas是一个矩形区...
    J_L_L阅读 1,513评论 0 4
  • 当我们出港时,我的第一次霉运也跟随而至。海风开始挂起来,海浪升起到非常可怕的地步。之前我从未出过海,我的身体非常的...
    擂鼓人阅读 189评论 0 0