canvas的常用api

canvas

标签

<canvas width="600" height="400" id="canvas"></canvas>

不给宽高的话默认是300+150

怎么用

//拿到canvas
var canvas = document.getElementById("canvas");
//创建画图工具
var context = canvas.getContext("2d");

相关的api及用法

//画线
context.moveTo(100, 100);
context.lineTo(300, 100);
context.lineTo(300, 200);

//画第二条线
//画第二条线
context.moveTo(100, 300);
context.lineTo(300, 300);

//最后要描边才会出效果
context.stroke();

//创建一张新的玻璃纸
context.beginPath();	
//画第三条线
context.moveTo(500, 100);
context.lineTo(500, 300);

//只要执行stroke,都会玻璃纸上的图形重复印刷一次
context.stroke();

//填充
context.fill();

//设置描边色
context.strokeStyle = "red"; //颜色的写法和css写法是一样的
context.stroke();

//填充
//设置填充色
context.fillStyle = "yellowgreen";
context.fill();

//把路径闭合
context.closePath();

//设置线条的粗细, 不需要加px
context.lineWidth = 15;
//线条的头部的设置
context.lineCap = "round"; //默认是butt, 记住round

非零填充原则

在由路径围成的区域内部,任意一个点, 拉一条射线。 看和这个射线相交的路径有几条。 路径的方向是顺时针,就是1. 如果逆时针,就是-1, 把所有的值相加, 如果是0, 就不填充, 如是非0, 就填充

画矩形

//直接传入 x, y, width, height, 就可以绘制一个矩形
//画在玻璃纸上

context.rect(100, 100, 200, 200);
context.strokeStyle = "red";
context.stroke();
context.fillStyle = "yellow";
context.fill();

//直接创建一个填充的矩形
//创建玻璃纸, 画矩形路径, 填充, 把玻璃纸销毁
context.fillRect(100, 100, 200, 200);

//黄色的边不会显示,是因为上面那一句,画完之后,就把玻璃纸销毁了
context.strokeStyle = "yellow";
context.stroke();
//如果放在fillRect上面就可以实现

圆形绘制

//x轴是0度开始
//x, y: 圆心位置;radius: 半径的长度; startRadian, endRadian 代表的是起始弧度和结束弧度;dircetion代表的圆形的路径的方向,默认是顺时针(是否逆时针, 默认值是false),如果传true就是逆时针,最后一个参数是可以不传的, 默认就是顺时针

context.arc(x, y, radius, startRadian, endRadian, direction);

//从31度的地方,画到81度的地方
context.arc(300, 200, 100, 31/180*Math.PI, 81/180*Math.PI);	

画飞镖转盘

var canvas = document.getElementById("canvas");
var context = canvas.getContext("2d");
for (var i = 0; i < 10; i++) {
    context.moveTo(320+i*20,200);
    // i % 2代表是奇数还是偶数, 偶数就逆时针, 奇数就顺时针
    context.arc(300, 200, 20 + i * 20, 0, 2*Math.PI, i%2==0);
    
}
context.fillStyle = "green";
context.fill();
context.stroke();

线性渐变

//1. 需要创建出一个渐变对象
//    var gradient = context.createLinearGradient(100, 100, 300, 100);
//参数代表哪个点到哪个点,这里写的是左上角到右下角的意思
var gradient = context.createLinearGradient(100, 100, 300, 380);

//2. 添加渐变颜色
gradient.addColorStop(0, "red");
gradient.addColorStop(0.5, "hotpink");
gradient.addColorStop(1, "yellowgreen");

//3. 将渐变对象设为填充色
context.fillStyle = gradient;

//4. 画一个矩形
context.fillRect(100, 100, 200, 280);

径向渐变

//1. 创建渐变对象
//内圆
var c1 = {x: 260, y: 160, r: 0};
//外圆
var c2 = {x: 300, y: 200, r: 120};

var gradient = context.createRadialGradient(c1.x, c1.y, c1.r, c2.x, c2.y, c2.r);
gradient.addColorStop(0, "red");
gradient.addColorStop(0.3, "yellow");
gradient.addColorStop(0.6, "green");
gradient.addColorStop(1, "orange");

//2. 把渐变对象设为填充色
context.fillStyle = gradient;

//3. 画圆并填充
//内圆的部分是用0的位置填充的; 内圆的边到外圆的边所发生的渐变叫, 径向渐变
context.arc(c2.x, c2.y, c2.r, 0, 2*Math.PI);
context.fill();

径向渐变画球

//1. 创建一个径向渐变
c1 = {x: 240, y: 160, r: 0};
c2 = {x: 300, y: 200, r: 120};

var gradient = context.createRadialGradient(c1.x, c1.y, c1.r, c2.x, c2.y, c2.r);
gradient.addColorStop(1, "gray");
gradient.addColorStop(0, "lightgray");

//2. 将渐变对象设为填充色
context.fillStyle = gradient;

//3. 画圆并填充
context.arc(c2.x, c2.y, c2.r, 0, 2*Math.PI);
context.fill();

径向渐变画彩虹

//实现彩虹,给里面的圆一个半径80是关键
var c1 = {x: 300, y: 200, r: 80};
var c2 = {x: 300, y: 200, r: 150};
var gradient = context.createRadialGradient(c1.x, c1.y, c1.r, c2.x, c2.y, c2.r);
gradient.addColorStop(1, "red");
gradient.addColorStop(6/7, "orange");
gradient.addColorStop(5/7, "yellow");
gradient.addColorStop(4/7, "green");
gradient.addColorStop(3/7, "cyan");
gradient.addColorStop(2/7, "skyblue");
gradient.addColorStop(1/7, "purple");
gradient.addColorStop(0, "white");

//设为填充色
context.fillStyle = gradient;

//画圆并填充
context.arc(c2.x, c2.y, c2.r, 0, 2*Math.PI);
context.fill();

//遮挡下半部分
context.fillStyle = "white";
context.fillRect(0, 200, 600, 200);

阴影效果

//和css3相比, 阴影只能设一个, 不能设内阴影
//水平偏移, 垂直的偏移, 模糊程度, 阴影的颜色

//设置阴影的参数
context.shadowOffsetX = 10;
context.shadowOffsetY = 10;
context.shadowBlur = 10;
context.shadowColor = "yellowgreen";

//画一个矩形
context.fillStyle = "red";
context.fillRect(100, 100, 300, 200);

绘制文字api

//绘制文字
//text就是要绘制的文字, x, y就是从什么地方开始绘制
//context.strokeText("text", x, y)

context.font = "60px 微软雅黑";
//context.strokeText("hello, world", 100, 100);
context.fillText("hello, world", 100, 100);

文字对齐方式

基线在文字的那个方向

水平方向

//默认在left
//关键api:context.textAlign = "left";
context.textAlign = "left";
context.fillText("left", 300, 120);

context.textAlign = "center";
context.fillText("center", 300, 190);

context.textAlign = "right";
context.fillText("right", 300, 260);

实现文字在画布的右上方

1.	先设置right
2.	给canvas.width,0即可

context.font = "60px 微软雅黑";
context.textAlign = "right";
context.textBaseline = "top";
context.fillText("hello, world", canvas.width, 0);

垂直方向

//默认是top
//关键api:context.textBaseline = "top";

context.fillText("default", 50, 200);

context.textBaseline = "top";
context.fillText("top", 150, 200);

context.textBaseline = "middle";
context.fillText("middle", 251, 200);

context.textBaseline = "bottom";
context.fillText("bottom", 400, 200);

图片的绘制

3参模式: 将img从x, y的地方开始绘制, 图片有多大,就绘制多大,超出canvas的部分就不显示了

//context.drawImage(img, x, y)

var image = new Image();
image.src = "./img/gls.jpg";

//必须要等到图片加载出来,才能进行绘制的操作
image.onload = function () {
    context.drawImage(image, 100, 200);
}

5参模式(缩放模式), 就是将图片显示在画布上的某一块区域(x, y, w, h),如果这个区域的宽高和图片不一至,会被压缩或放大

var image = new Image();
image.src = "./img/gls.jpg";

image.onload = function () {
    context.drawImage(image, 100, 100, 100, 100);
}

图片绘制的九参模式, 就是把原图(img)中的某一块(imagex,imagey,imagew,imageh)截取出来, 显示在画布的某个区域(canvasx, canvasy, canvasw, canvash)

//理解关键:
//(imagex,imagey,imagew,imageh)
//(canvasx, canvasy, canvasw, canvash)

var image = new Image();
image.src = "./img/gls.jpg";
image.onload = function () {
    /*
        参数的解释:
        image: 就是大图片本身
        中间的四个参数, 代表从图片的150, 0的位置,截取 150 * 200的一块区域
        后面的四个参数, 将刚才截取的小图, 显示画布上 100, 100, 150, 200的这个区域
     */
    context.drawImage(image, 150, 0, 150, 200,  100, 100, 150, 200);
}

画布中的放大器实现

判断位置的关键api:

context.rect(0, 0, 150, 100);
canvas.onmousemove = function (event) {
    var x = event.offsetX;
    var y = event.offsetY;
}

//1. 加载图片
var image = new Image();
image.src = "./img/gls.jpg";
image.onload = function () {
    //1. 先把大图画在右上角
    context.drawImage(image, 0, 0, 150, 100);

    //创建一个矩形的路径
    context.rect(0, 0, 150, 100);

    //2. 判断当前鼠标是否hover到上面的图片上了
    canvas.onmousemove = function (event) {
        //原图和左上角的图的比例是3: 1
        var x = event.offsetX;
        var y = event.offsetY;

        //if (x >= 0 && x<=150 && y >=0 && y <= 100) {}
        //当前 x, y这个点的位置,是否在玻璃纸上的路径的区域的内部
        if (context.isPointInPath(x, y) == true) {
            console.log("在内部");
			//比例要按照原图的比例来看,这里的小图是原图的1/3,所以*3
            x = x * 3 - 20;
            y = y * 3 - 20;

            //每一次在画之前,先把之前画的擦除
            //某300, 200, 300, 200这个区域的东西全部擦除
            context.clearRect(300, 200, 300, 200);

            //从x, y这个点,截取40*40的局部小图,显示在图布, 300, 200, 80, 80这个区域,就形成了一个放大的效果
			//这里40,40,是因为上面-20的宽和高的原因
            context.drawImage(image, x, y, 40, 40, 300, 200, 120, 120);
        }
        else {
            console.log("不在内部");
        }
    }
}

简单的用计时器实现小人移动

//1. 加载图片
var image = new Image();
image.src = "./img/DMMban.png";

image.onload = function () {
    //第几行图片
    var yindex = 2;
    //某一行的第几张图片
    var xindex = 0;

    //小人的宽和高
    var w = image.width/4;
    var h = image.height/4;

    //小人水平方向的坐标x值
    var x = 0;
    //小人每一步走多远
    var speed = 10;

    var index = 0;

    setInterval(function () {
        index += 1;
        //循环切换图片
        xindex = index % 4;

        //边界的判断
        if (x >= canvas.width - w) {
            speed = -speed; //-10
            yindex = 1;
        }

        if (x < 0) {
            speed = -speed;
            yindex = 2;
        }

        context.clearRect(0, 0, canvas.width, canvas.height);
        context.drawImage(image, xindex * w, yindex * h, w, h, x, 200, w, h);

        //每走一步x要往前移动
        x += speed;
    }, 200);
}

画布的缩放,平移,旋转api

context.scale(0.5, 0.5);
context.translate(300, 200);
context.rotate(30/180*Math.PI);

posted on 2017-12-25 14:01  ouruixi  阅读(1506)  评论(0)    收藏  举报

导航