SOURCE

console 命令行工具 X clear

                    
>
console
const init = () => {
    let canvas = document.getElementById('ash')
    const ctx = canvas.getContext('2d')
    return {canvas, ctx}
}
const {canvas, ctx} = init()

const drawLine = (start, end) => {
    ctx.beginPath()
    ctx.moveTo(...start);
    ctx.lineTo(...end);
    ctx.stroke()
    ctx.closePath()
}
const drawText = (text, pos, size = 16) => {
    ctx.font = `${size}px serif`;
    ctx.fillText(text, ...pos)
}
const drawGrid = (scale = 10) => {
    
    let width = canvas.width
    let height = canvas.height
    let padding = 10
    let x = Math.floor(width / scale)
    let y = Math.floor(height / scale)
    // x
    drawLine([padding, height - padding], [width - padding,  height - padding])
    // arrow
    drawLine([width - padding,  height - padding], [width - padding - 10, height - padding - 10])
    drawLine([width - padding,  height - padding], [width - padding - 10, height - padding + 10])
    ctx.beginPath()
    ctx.font = "32px serif";
    ctx.fillText("x", width - padding - 10 - 10, height - padding - 10)


    
    // y
    drawLine([padding, height - padding], [padding,  padding])
    // arrow
    drawLine([padding,  padding], [padding + 10, padding + 10])
    drawLine([padding,  padding], [padding - 10, padding + 10])

    ctx.font = "32px serif";
    ctx.fillText("y", padding + 10 , padding + 10 + 10)
 
    // grid
    ctx.strokeStyle = "#aaa";
    for(let i = 2 * padding; i <= width - padding; i += padding) {
        drawLine([i, height - padding], [i, padding])
    }
    for(let i =  padding; i <= height - padding; i +=padding) {
        drawLine([padding,i ], [width - padding, i])
    }
    // 刻度
    for(let i = 1; i <= x; i++) {
        if(i % 10 === 0) {
            ctx.strokeStyle = "#000";
            drawLine([i * scale,height - padding], [i * scale, height - 2 * padding])
            drawText(i, [i * scale - 10,height ], 10)
        }
        
    }
    for(let i = 1; i < y; i++) {
        if(i % 10 === 0) {
            ctx.strokeStyle = "#000";
            drawLine([padding,height  - i * scale], [2 * padding, height  - i * scale])
            drawText(i, [0,height  - i * scale +4], 10)
        }
    }
}
let padding = 10
const random = (min, max) => Math.floor(Math.random() * (max - min) + min) 
const animation = () => {
    let height = canvas.height;
    let width = canvas.width
    ctx.clearRect(0,0,width,height)
    drawGrid()
    let x = random(padding, width - padding)
    let y = random(padding, height - padding)
    x = Math.floor(x / 10) * 10
    y = Math.floor(y / 10) * 10
    ctx.fillStyle = 'rgba(0,0,0,0.4)';
    ctx.fillRect(x, y, padding, padding)
    requestAnimationFrame(animation)
}

animation()
// drawGrid()
let prePost = []

// canvas.addEventListener('mousemove', (e) => {
//     let {offsetX: x, offsetY: y} = e
//     let height = canvas.height;
//     let width = canvas.width
//     if(x >= padding && x <= width && y >=padding && y <=height - padding) {
//         ctx.clearRect(0,0,width,height)
//         ctx.restore()
//         drawGrid()
        
//         
//         x = Math.floor(x / 10) * 10
//         y = Math.floor(y / 10) * 10
//         ctx.fillRect(x, y, padding, padding)
       
//     }
    
// })
<canvas id='ash' width="600" height="480"></canvas>
canvas{
    background: #fff;
}