Javascript - 跟踪鼠标位置

时间:2011-10-17 07:44:25

标签: javascript

我希望每隔t毫秒定期跟踪鼠标光标的位置。基本上,当一个页面加载时 - 这个跟踪器应该开始,并且(例如)每100毫秒,我应该获得posX和posY的新值并在表单中打印出来。

我尝试了以下代码 - 但是值没有刷新 - 只有posX和posY的初始值显示在表单框中。关于如何启动和运行的任何想法?

<html>
<head>
<title> Track Mouse </title>
<script type="text/javascript">
function mouse_position()
{
    var e = window.event;

    var posX = e.clientX;
    var posY = e.clientY;

    document.Form1.posx.value = posX;
    document.Form1.posy.value = posY;

    var t = setTimeout(mouse_position,100);

}
</script>

</head>

<body onload="mouse_position()">
<form name="Form1">
POSX: <input type="text" name="posx"><br>
POSY: <input type="text" name="posy"><br>
</form>
</body>
</html>

15 个答案:

答案 0 :(得分:152)

鼠标的位置在event事件的处理程序收到的mousemove对象上报告,您可以将其附加到窗口(事件气泡):

(function() {
    document.onmousemove = handleMouseMove;
    function handleMouseMove(event) {
        var eventDoc, doc, body;

        event = event || window.event; // IE-ism

        // If pageX/Y aren't available and clientX/Y are,
        // calculate pageX/Y - logic taken from jQuery.
        // (This is to support old IE)
        if (event.pageX == null && event.clientX != null) {
            eventDoc = (event.target && event.target.ownerDocument) || document;
            doc = eventDoc.documentElement;
            body = eventDoc.body;

            event.pageX = event.clientX +
              (doc && doc.scrollLeft || body && body.scrollLeft || 0) -
              (doc && doc.clientLeft || body && body.clientLeft || 0);
            event.pageY = event.clientY +
              (doc && doc.scrollTop  || body && body.scrollTop  || 0) -
              (doc && doc.clientTop  || body && body.clientTop  || 0 );
        }

        // Use event.pageX / event.pageY here
    }
})();

(请注意,if的正文只能在旧IE上运行。)

Example of the above in action - 当您将鼠标拖到页面上时,它会绘制点。 (在IE8,IE11,Firefox 30,Chrome 38上测试过。)

如果你真的需要一个基于计时器的解决方案,你可以将它与一些状态变量结合起来:

(function() {
    var mousePos;

    document.onmousemove = handleMouseMove;
    setInterval(getMousePosition, 100); // setInterval repeats every X ms

    function handleMouseMove(event) {
        var dot, eventDoc, doc, body, pageX, pageY;

        event = event || window.event; // IE-ism

        // If pageX/Y aren't available and clientX/Y are,
        // calculate pageX/Y - logic taken from jQuery.
        // (This is to support old IE)
        if (event.pageX == null && event.clientX != null) {
            eventDoc = (event.target && event.target.ownerDocument) || document;
            doc = eventDoc.documentElement;
            body = eventDoc.body;

            event.pageX = event.clientX +
              (doc && doc.scrollLeft || body && body.scrollLeft || 0) -
              (doc && doc.clientLeft || body && body.clientLeft || 0);
            event.pageY = event.clientY +
              (doc && doc.scrollTop  || body && body.scrollTop  || 0) -
              (doc && doc.clientTop  || body && body.clientTop  || 0 );
        }

        mousePos = {
            x: event.pageX,
            y: event.pageY
        };
    }
    function getMousePosition() {
        var pos = mousePos;
        if (!pos) {
            // We haven't seen any movement yet
        }
        else {
            // Use pos.x and pos.y
        }
    }
})();

据我所知,如果没有看到事件,你就无法获得鼠标位置,this answer to another Stack Overflow question似乎确认了这一点。

旁注:如果您要每100毫秒(10次/秒)做一些事情,请尝试保持您在该功能中执行的实际处理非常非常有限。这对于浏览器来说是很多工作,尤其是较旧的Microsoft浏览器。是的,在现代计算机上看起来并不多,但浏览器中有很多...例如,如果位置没有,你可以跟踪你处理的最后一个位置并立即从处理程序保释改变了。

答案 1 :(得分:60)

这是一个基于jQuery和鼠标事件监听器(比常规轮询要好得多)的解决方案:

$("body").mousemove(function(e) {
    document.Form1.posx.value = e.pageX;
    document.Form1.posy.value = e.pageY;
})

答案 2 :(得分:34)

onmousemove = function(e){console.log("mouse location:", e.clientX, e.clientY)}

打开控制台(Ctrl + Shift + J),复制粘贴上面的代码并在浏览器窗口上移动鼠标。

答案 3 :(得分:12)

我相信我们正在过度思考这个问题,

function mouse_position(e)
{
//do stuff
}
<body onmousemove="mouse_position(event)"></body>

答案 4 :(得分:8)

我认为他只想知道光标的X / Y位置而不是为什么答案很复杂。

// Getting 'Info' div in js hands
var info = document.getElementById('info');

// Creating function that will tell the position of cursor
// PageX and PageY will getting position values and show them in P
function tellPos(p){
  info.innerHTML = 'Position X : ' + p.pageX + '<br />Position Y : ' + p.pageY;
}
addEventListener('mousemove', tellPos, false);
* {
  padding: 0:
  margin: 0;
  /*transition: 0.2s all ease;*/
  }
#info {
  position: absolute;
  top: 10px;
  right: 10px;
  background-color: black;
  color: white;
  padding: 25px 50px;
}
<!DOCTYPE html>
<html>
  
  <body>
    <div id='info'></div>
        </body>
  </html>

答案 5 :(得分:2)

无论浏览器如何,下面的行都可以帮助我获取正确的鼠标位置。

event.clientX - event.currentTarget.getBoundingClientRect().left event.clientY - event.currentTarget.getBoundingClientRect().top

答案 6 :(得分:2)

基于ES6的代码:

let handleMousemove = (event) => {
  console.log(`mouse position: ${event.x}:${event.y}`);
};

document.addEventListener('mousemove', handleMousemove);

如果需要限制鼠标移动,请使用:

let handleMousemove = (event) => {
  console.warn(`${event.x}:${event.y}\n`);
};

let throttle = (func, delay) => {
  let prev = Date.now() - delay;
  return (...args) => {
    let current = Date.now();
    if (current - prev >= delay) {
      prev = current;
      func.apply(null, args);
    }
  }
};

// let's handle mousemoving every 500ms only
document.addEventListener('mousemove', throttle(handleMousemove, 500));

这里是example

答案 7 :(得分:2)

我没有足够的声誉来发表评论,但是我选择了TJ Crowder的excellent answer和完全定义的the code on a 100ms timer。 (他留下了一些想像的细节。)

感谢OP提出问题,感谢TJ给出答案!你们俩都是很大的帮助。代码作为isbin的镜像嵌入在下面。

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <title>Example</title>
  <style>
    body {
      height: 3000px;
    }
    .dot {
      width: 2px;
      height: 2px;
      background-color: black;
      position: absolute;
    }
  </style>
</head>
<body>
<script>
(function() {
    "use strict";
    var mousePos;

    document.onmousemove = handleMouseMove;
    setInterval(getMousePosition, 100); // setInterval repeats every X ms

    function handleMouseMove(event) {
        var eventDoc, doc, body;

        event = event || window.event; // IE-ism

        // If pageX/Y aren't available and clientX/Y are,
        // calculate pageX/Y - logic taken from jQuery.
        // (This is to support old IE)
        if (event.pageX == null && event.clientX != null) {
            eventDoc = (event.target && event.target.ownerDocument) || document;
            doc = eventDoc.documentElement;
            body = eventDoc.body;

            event.pageX = event.clientX +
              (doc && doc.scrollLeft || body && body.scrollLeft || 0) -
              (doc && doc.clientLeft || body && body.clientLeft || 0);
            event.pageY = event.clientY +
              (doc && doc.scrollTop  || body && body.scrollTop  || 0) -
              (doc && doc.clientTop  || body && body.clientTop  || 0 );
        }

        mousePos = {
            x: event.pageX,
            y: event.pageY
        };
    }
    function getMousePosition() {
        var pos = mousePos;
		
        if (!pos) {
            // We haven't seen any movement yet, so don't add a duplicate dot 
        }
        else {
            // Use pos.x and pos.y
            // Add a dot to follow the cursor
            var dot;
            dot = document.createElement('div');
            dot.className = "dot";
            dot.style.left = pos.x + "px";
            dot.style.top = pos.y + "px";
            document.body.appendChild(dot);
        }
    }
})();
</script>
</body>
</html>

答案 8 :(得分:2)

只是@T.J. Crowder@RegarBoy的答案的简化版本。

我认为更少。

查看onmousemove event以获得有关该事件的更多信息。

Image mouse tracker

每次鼠标根据水平和垂直坐标移动时,都会有一个新的值google.auth.exceptions.DefaultCredentialsError: could not automatically determine credentials. Please set GOOGLE_APPLICATION_CREDENTIALS or explicitly create credentials and re-run the application. For more information, please see https://cloud.google.com/docs/authentication/getting-startedposX

posY

答案 9 :(得分:0)

如果只想直观地跟踪鼠标移动:

<!DOCTYPE html>
<html>
<head>
<title></title>
</head>
<style type="text/css">
* { margin: 0; padding: 0; }
html, body { width: 100%; height: 100%; overflow: hidden; }
</style>
<body>
<canvas></canvas>

<script type="text/javascript">
var
canvas    = document.querySelector('canvas'),
ctx       = canvas.getContext('2d'),
beginPath = false;

canvas.width  = window.innerWidth;
canvas.height = window.innerHeight;

document.body.addEventListener('mousemove', function (event) {
	var x = event.clientX, y = event.clientY;

	if (beginPath) {
		ctx.lineTo(x, y);
		ctx.stroke();
	} else {
		ctx.beginPath();
		ctx.moveTo(x, y);
		beginPath = true;
	}
}, false);
</script>
</body>
</html>

答案 10 :(得分:0)

这是两个要求的结合:每100毫秒跟踪一次鼠标位置:

var period = 100,
    tracking;

window.addEventListener("mousemove", function(e) {
    if (!tracking) {
        return;
    }

    console.log("mouse location:", e.clientX, e.clientY)
    schedule();
});

schedule();

function schedule() {
    tracking = false;

    setTimeout(function() {
        tracking = true;
    }, period);
}

这会跟踪并作用于鼠标的位置,但仅每个周期毫秒。

答案 11 :(得分:0)

这是跟踪鼠标位置的最简单方法

HTML

<body id="mouse-position" ></body>

js

document.querySelector('#mouse-position').addEventListener('mousemove', (e) => {
        console.log("mouse move X: ", e.clientX);
        console.log("mouse move X: ", e.screenX);


    }, );

know more

答案 12 :(得分:0)

我们最近必须找到当前的 x,y 位置来枚举光标悬停在其上的元素,而与 z-index 无关。我们最终只是将 mousemove 事件侦听器附加到文档,例如,

function findElements(e) {
  var els = document.elementsFromPoint(e.clientX, e.clientY);

  // do cool stuff with els
  console.log(els);

  return;
}

document.addEventListener("mousemove", findElements);

答案 13 :(得分:0)

这是一个解决方案

document.onmousemove = showCoords;
function showCoords(event) {
var x = event.clientX;
var y = event.clientY;
var coords = "X coords: " + x + ", Y coords: " + y;
document.getElementById("box1").innerHTML = coords;
}

答案 14 :(得分:0)

         document.addEventListener('mousemove', (event) => {
          document.getElementById("line").style.top = event.clientY+'px';
          document.getElementById("lineY").style.left = event.clientX+'px';
          document.getElementById("pos").style.top = (event.clientY -50)+'px';
          document.getElementById("pos").style.left = (event.clientX-50)+'px';
         
         });
      <style>
         body {
         position: relative;
         height: auto;
         min-height: 100% !important;
         background-color: lightblue;
         }
         h1 {
         color: white;
         text-align: center;
         }
         p {
         font-family: verdana;
         font-size: 20px;
         }
         .abs{
         position:relative;
           
         }
         .lineY
         {
         display: flex;
         position:relative;
         left:0px;
         background-color:black;
         width:2px;
         height: 100vh;
         min-height:100%
         }
         .line
         {
         display: flex;
         position:relative;
         background-color:black;
         min-height:2px;
         width:100%;
         }
         .circle
         {
         display: flex;
         position:absolute;
         left:0px;
         top:0px;
         }
      </style>
<!DOCTYPE html>
<html>
   <head>
      
   </head>
   <body>
      <div class='line' id="line"></div>
      <div class='lineY' id="lineY"></div>
      <svg height="100" width="100" id="pos" class="circle" >
  <circle cx="50" cy="50" r="40" stroke="black" stroke-width="3" fill="transparent" />
</svg>
   </body>
</html>