【问题标题】:Canvas Rect Mouse Hover on Chart画布矩形鼠标悬停在图表上
【发布时间】:2020-02-10 10:52:23
【问题描述】:

迭代plotData会根据条件在图表上的特定值周围创建一个矩形。

plotData.forEach( (each, index) => {

    if ( each.a > each.b ) {
       try {
            ctx.beginPath();
            ctx.fillStyle = 'yellow';
            ctx.rect(zone[index].x, zone[index].y, zone[index].width, zone[index].height);
            ctx.closePath();
            ctx.fill();
       }
       ...

当鼠标悬停在矩形上时,我想更改矩形的颜色。该图表是可滚动和可缩放的,因此矩形坐标会动态变化。

【问题讨论】:

    标签: javascript canvas


    【解决方案1】:

    首先,在这个函数之外,在文档代码的其他地方,事实上:在代码的最顶部,定义一个变量来跟踪鼠标的位置,以及它是否被点击:

    var mouseInfo = {x:0, y:0, clicked: false};
    

    现在,在其他地方创建一些事件侦听器来跟踪该位置(在创建画布元素之后的某个时间),我假设画布元素存储在一个名为 canvas 的变量中:

    canvas.addEventListener("mousemove", e=> {
        mouseInfo.x = e.offsetX;
        mouseInfo.y = e.offsetY;
    });
    

    接下来,另外 2 个来跟踪鼠标是否按下(不一定要在 canvas 元素上,事实上,最好是在 window 元素上):

    window.addEventListener("mousedown", e=> {
         mouseInfo.clicked = true;
    });
    
    window.addEventListener("mouseup", e=> {
         mouseInfo.clicked = false;
    });
    

    现在创建一个函数来确定一个点是否与一个矩形相交,假设一个矩形是一个具有 x、y、宽度、高度的对象:

    function isPointInRet(point, rect) {
        return (
            point.x > rect.x &&
            point.x < rect.x + rect.width && 
            point.y > rect.y && 
            point.y < rect.y + rect.height
        );
    }
    

    现在,回到上面引用的函数:

    plotData.forEach( (each, index) => {
    
        if ( each.a > each.b ) {
           try {
                ctx.beginPath();
                ctx.fillStyle = 'yellow';
                ctx.rect(zone[index].x, zone[index].y, zone[index].width, zone[index].height);
                ctx.closePath();
                ctx.fill();
           }
    

    因此,在 fillStyle 部分之前,将其全部更改为以下内容:

    var x = zone[index].x,
        y = zone[index].y,
        width = zone[index].width,
        height = zone[index].height;
    if(isPointInRect(mouseInfo, {x, y, width, height}) {
         //perhaps if you want to make a hover color, do that here, just un-comment if you want:
         /*ctx.fillStyle = "#ffaaee";*/
         if(mouseInfo.clicked) {
             ctx.fillStyle = "ff0000"; //red
         }
    }
    ctx.fillStyle = 'yellow';
    ctx.rect(x, y, width, height);
    ...
    

    (警告:未经测试的代码);

    让我知道这是否有帮助,以及它是否适用于缩放等。

    【讨论】:

    • 这真是太棒了。谢谢它对我帮助很大。我对这种帆布材料很陌生。真的很感激!尽情享受周末时光吧
    • @mondego 也刚刚意识到你可以进一步缩短它,将对象作为 {x, y, width, height} 传递,如果变量值与键相同(jsut 发现了这个哈哈),不会改变功能,只是一个很酷的补充
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-12-29
    • 1970-01-01
    • 1970-01-01
    • 2012-03-01
    • 1970-01-01
    • 2012-05-10
    • 2016-04-29
    相关资源
    最近更新 更多