zoukankan      html  css  js  c++  java
  • canvas 实现画板功能

    <!DOCTYPE html>
    <html lang="en">
    
    <head>
        <meta charset="UTF-8">
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <meta http-equiv="X-UA-Compatible" content="ie=edge">
        <title>canvas</title>
    </head>
    <style>
        .toolbar {
            width: 200px;
            float: left;
        }
    
        .canvas1 {
            position: absolute;
            left: 200px;
            z-index: 101;
        }
    
        .canvas2 {
            background: #03A9F4;
            position: absolute;
            left: 200px;
            z-index: 100;
        }
    </style>
    
    <body>
        <div id="toolbar" class="toolbar">
            <h2>工具栏</h2>
            <input onclick="switchMark(1)" type="button" value="画笔" /><br />
            <input onclick="switchMark(2)" type="button" value="矩形" /><br />
            <input onclick="switchMark(3)" type="button" value="圆形" /><br />
            <input onclick="switchMark(4)" type="button" value="文字" /><br />
            <div id="inputText">
                <input id="text" type="input" style=" 100px;" />
                <button onclick="inputText()">确定</button><br />
            </div>
            <input onclick="switchMark(0)" type="button" value="撤销" /><br />
        </div>
        <canvas id="canvas1" class="canvas1" width="400px" height="400px">您的浏览器不支持画布!</canvas>
        <canvas id="canvas2" class="canvas2" width="400px" height="400px">您的浏览器不支持画布!</canvas>
    
        <script>
            var canvas1 = document.getElementById("canvas1");
            var context1 = canvas1.getContext("2d");
    
            var canvas2 = document.getElementById("canvas2");
            var context2 = canvas2.getContext("2d");
    
            var text = document.getElementById('inputText');
            text.style.display = 'none';
    
            var canvasWidth = 400;
            var canvasHeight = 400;
            // 图片索引
            var canvasIndex = -1;
            // 图片数据
            var canvasData = [];
            // 轨迹结束判断
            var isSameMove = false;
            // 标注类型
            var switchMarkType = null;
            // 鼠标按下状态
            var isMouseDown = false;
            // 鼠标坐标
            var mouseXY = { x1: 0, y1: 0, x2: 0, y2: 0 };
    
            // 保存初始图片
            canvasIndex++;
            canvasData.push(canvas2.toDataURL());
    
            // 标注类型切换
            function switchMark(markType) {
                if (markType === 0) {
                    undo();
                }
                if (markType !== 4) {
                    text.style.display = 'none';
                }
                if (switchMarkType === markType || markType === 0) {
                    switchMarkType = null;
                    return;
                }
                switchMarkType = markType;
            }
            // 输入文字标注
            function inputText() {
                var str = document.getElementById('text').value;
                context1.font = '24px Arial';
                context1.fillText(str, mouseXY.x1, mouseXY.y1);
                setCanvasImage(context2, canvas2, canvas1.toDataURL(), canvasWidth, canvasHeight, (url) => {
                    context1.clearRect(0, 0, canvasWidth, canvasHeight);
                    canvasIndex++;
                    canvasData.push(url);
                })
                text.style.display = 'none';
            }
            // 撤销
            function undo() {
                if (canvasIndex > 0) {
                    canvasData.pop();
                    canvasIndex--;
                    context2.clearRect(0, 0, canvasWidth, canvasHeight);
                    setCanvasImage(context2, canvas2, canvasData[canvasIndex], canvasWidth, canvasHeight, (url) => {
                        return;
                    });
                } else {
                    console.log('不能再继续撤销了');
                }
            }
            // 鼠标按下
            canvas1.onmousedown = function (e) {
                isMouseDown = true;
                context1.lineWidth = '2';
                context1.strokeStyle = 'red';
                context1.fillStyle = 'red';
                setMouseXY(true, e);
                // 绘制线
                if (switchMarkType === 1) {
                    context1.beginPath();
                    context1.moveTo(mouseXY.x1, mouseXY.y1);
                }
                // 绘制文字
                if (switchMarkType === 4) {
                    text.style.display = 'block';
                }
            }
            // 鼠标向上
            canvas1.onmouseup = function (e) {
                isMouseDown = false;
                if (switchMarkType === null || switchMarkType === 4) {
                    return;
                }
                setCanvasImage(context2, canvas2, canvas1.toDataURL(), canvasWidth, canvasHeight, (url) => {
                    context1.clearRect(0, 0, canvasWidth, canvasHeight);
                    canvasIndex++;
                    canvasData.push(url);
                })
            }
            // 鼠标移动
            canvas1.onmousemove = function (e) {
                if (isMouseDown) {
                    // 清除canvas1上的图像
                    context1.clearRect(0, 0, canvasWidth, canvasHeight);
                    // 绘制线
                    if (switchMarkType === 1) {
                        // 记录起点坐标
                        setMouseXY(true, e);
                        context1.lineTo(mouseXY.x1, mouseXY.y1);
                        context1.stroke();
                        context1.save();
                    }
                    // 记录终点坐标
                    setMouseXY(false, e);
                    // 绘制矩形
                    if (switchMarkType === 2) {
                        context1.strokeRect(mouseXY.x1, mouseXY.y1, mouseXY.x2 - mouseXY.x1, mouseXY.y2 - mouseXY.y1);
                    }
                    // 绘制圆形
                    if (switchMarkType === 3) {
                        context1.beginPath();
                        var cx = (mouseXY.x1 + mouseXY.x2) / 2;
                        var cy = (mouseXY.y1 + mouseXY.y2) / 2;
                        var rx = Math.abs((mouseXY.x1 - mouseXY.x2) / 2);
                        var ry = Math.abs((mouseXY.y1 - mouseXY.y2) / 2);
                        context1.ellipse(cx, cy, rx, ry, 0, 0, Math.PI * 2);
                        context1.stroke();
                    }
                    // 在canvas1上绘制图像
                    context1.drawImage(canvas1, 0, 0, canvasWidth, canvasHeight);
                }
            }
            // 根据宽高生成canvas图像
            function setCanvasImage(context, canvas, base64PImg, canvasWidth, canvasHeight, callback) {
                let img = new Image();
                img.onload = function () {
                    context.drawImage(img, 0, 0, canvasWidth, canvasHeight);
                    callback(canvas.toDataURL());
                }
                img.src = base64PImg;
            }
            // 求鼠标坐标函数
            function windowToCanvas(canvas, x, y) {
                const rect = canvas.getBoundingClientRect();
                return {
                    x: x - rect.left * (canvas.width / rect.width),
                    y: y - rect.top * (canvas.height / rect.height)
                };
            }
            // 记录坐标
            function setMouseXY(start, e) {
                const ele = windowToCanvas(canvas1, e.clientX, e.clientY);
                if (start) {
                    mouseXY.x1 = ele.x;
                    mouseXY.y1 = ele.y;
                } else {
                    mouseXY.x2 = ele.x;
                    mouseXY.y2 = ele.y;
                }
            }
        </script>
    </body>
    
    </html>
  • 相关阅读:
    cocos2dx注意点
    [转]优化Cocos2d程序的内存消耗
    [转]Cocosdx中介者模式
    [转]Cocos2dx委托模式
    [转]cocos2dx场景切换时内存过高导致crash解决方法
    SQL语句字符串处理大全(转)
    C#不区分大小写的字符串替换(Replace)函数(转)
    lucene.net 分词 搜索
    起点上的页面传值js,有空研究下
    正则表达式取网页链接以及标题,包含单、双引号,以及没有引号的情况
  • 原文地址:https://www.cnblogs.com/chendongbky/p/12016602.html
Copyright © 2011-2022 走看看