canvas 实现画板(四)线条粗细,路径圆滑效果(2021/5/12)

<!DOCTYPE html>
<html lang="en">

<head>
        <meta charset="UTF-8">
        <meta http-equiv="X-UA-Compatible" content="IE=edge">
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <title>canvas 实现画板</title>
        <style>
                * {
                        margin: 0;
                        padding: 0;
                        box-sizing: border-box;
                }

                body {
                        width: 100vw;
                        height: 100vh;
                        display: flex;
                        flex-direction: column;
                        justify-items: flex-start;
                }

                .caidan {
                        height: 100px;
                        width: 100vw;
                        display: flex;
                        border-bottom: 3px solid #ccc;
                        justify-content: space-around;
                        align-items: center;
                }

                #canvas {
                        flex: 1;
                        width: 100vw;
                }

                .btn ,.btn1{
                        width: 150px;
                        height: 50px;
                        border: 1px solid #CCC;
                        border-radius: 20px;
                        text-align: center;
                        line-height: 50px;
                        color: #ccc;
                }

                .btn.active {
                        box-shadow: 0 0 20px deepskyblue;
                        border: 1px solid deepskyblue;
                }
                .btn1.active {
                        box-shadow: 0 0 20px deepskyblue;
                        border: 1px solid deepskyblue;
                }
        </style>
</head>

<body>
        <div class="caidan">
                <div class="btn" id="huabi">画笔</div>
                <div class="btn" id="rect">矩形</div>
                <div class="btn">圆形</div>
                <div class="btn1 line xi active">细</div>
                <div class="btn1 line normal">普通</div>
                <div class="btn1 line cu">粗</div>
                <!-- 颜色选择器 -->
                <div class="btn1"><input type="color" name="color" id="color" value=""></div>
        </div>
        <canvas id="canvas"></canvas>
        <!--画板的宽度,高度通过js来获取实时的-->
        <script>
                var allBtn = document.querySelectorAll('.btn')
                var canvas = document.querySelector('#canvas')
                var ctx = canvas.getContext('2d')
                canvas.setAttribute('width', canvas.offsetWidth)
                canvas.setAttribute('height', canvas.offsetHeight)
                var huaban = {
                        type: 'none',
                        isDraw: false,
                        beginX: 0, //矩形描绘的开始位置
                        beginY: 0,
                        lineWidth:6,
                        imageData:null, //用于保存之前画板的内容
                        huabiFn: function (e) {
                                var x = e.pageX - canvas.offsetLeft
                                var y = e.pageY - canvas.offsetTop
                                ctx.lineWidth = huaban.lineWidth
                                ctx.lineCap = 'round'
                                ctx.lineJoin = 'round'
                                ctx.lineTo(x,y)
                                ctx.stroke()
                        },
                        rectFn: function (e) {
                                ctx.beginPath()
                                var x = e.pageX - canvas.offsetLeft
                                var y = e.pageY - canvas.offsetTop
                                ctx.clearRect(0, 0, canvas.offsetWidth, canvas.offsetHeight) //每一次清除画板的矩形
                                // 一开始是空的
                                if(huaban.imageData != null){
                                        ctx.putImageData(huaban.imageData,0,0,0,0,canvas.offsetWidth, canvas.offsetHeight); //参数:内容、位置、数据位置、宽高
                                }
                                ctx.rect(huaban.beginX, huaban.beginY, x - huaban.beginX, y - huaban.beginY)
                                ctx.stroke()
                                ctx.closePath()
                        }
                }

                var huabiBtn = document.querySelector('#huabi')
                huabiBtn.onclick = function () {
                        allBtn.forEach((item, index) => {
                                item.classList.remove('active')
                        })
                        huabiBtn.classList.add('active')
                        huaban.type = 'huabi'
                }

                // 监听鼠标按下事件
                canvas.onmousedown = function (e) {
                        huaban.isDraw = true
                        if (huaban.type == 'rect') {
                                var x = e.pageX - canvas.offsetLeft
                                var y = e.pageY - canvas.offsetTop
                                huaban.beginX = x;
                                huaban.beginY = y;
                        }
                        if (huaban.type == 'huabi') {
                                var x = e.pageX - canvas.offsetLeft
                                var y = e.pageY - canvas.offsetTop
                                huaban.beginX = x;
                                huaban.beginY = y;
                                ctx.beginPath() //画笔操作的开始
                                ctx.moveTo(x,y) //移动到x,y的位置
                        }
                }
                // 监听鼠标抬起事件
                canvas.onmouseup = function () {
                        huaban.isDraw = false
                        huaban.imageData = ctx.getImageData(0,0,canvas.offsetWidth,canvas.offsetHeight) //保存之前画板描绘的内容
                        if(huaban.type == 'huabi'){ //抬起关闭描绘
                                ctx.closePath()
                        }
                }

                canvas.onmousemove = function (e) {
                        if (huaban.isDraw) { //调用不同的函数执行按钮时间
                                huaban[huaban.type + 'Fn'](e)//调用对象里的函数
                        }
                }


                var rectBtn = document.querySelector('#rect')
                rectBtn.onclick = function () {
                        allBtn.forEach((item, index) => {
                                item.classList.remove('active')
                        })
                        rectBtn.classList.add('active')
                        huaban.type = 'rect'
                }

                var lineDivs = document.querySelectorAll('.line')
                lineDivs.forEach((item,i) =>{
                        item.onclick  = function(){ //遍历清除所有按钮的样式
                                lineDivs.forEach((a,b)=>{
                                        a.classList.remove('active')
                                })
                                item.classList.add("active")
                                if(i == 0) {
                                        huaban.lineWidth = 6
                                }else if(i == 1){
                                        huaban.lineWidth = 16
                                }else{
                                        huaban.lineWidth = 32
                                }
                        }
                })

        </script>
</body>

</html>
上一篇:a 标签的四种样式


下一篇:oracle 数据库连接池策略