I'm trying to have a selection wheel appear when the user holds down the Shift key.
The wheel should be centred on the mouse's position.
However when I test this, pageX and clientX are both undefined on the event object.
Is it possible to get the mouse coordinates on a keyboard event?
No, simply track mousemove events and continuously save the current position in case you get a keyboard event.
Cache mouse position in a global variable in every mousemove event and use it when a key event fires:
var mousePosition = {x:0, y:0};
$(document).bind('mousemove',function(mouseMoveEvent){
mousePosition.x = mouseMoveEvent.pageX;
mousePosition.y = mouseMoveEvent.pageY;
});
$(document).bind('keyup', function(keyUpEvent){
$('body').append($('<p/>').text('x:' + mousePosition.x + ' * y: ' + mousePosition.y));
});
JSBIN: http://jsbin.com/uxecuj/4
JavaScript without jQuery:
var mousePosition = {x:0, y:0};
document.addEventListener('mousemove', function(mouseMoveEvent){
mousePosition.x = mouseMoveEvent.pageX;
mousePosition.y = mouseMoveEvent.pageY;
}, false);
document.addEventListener('keyup', function(keyUpEvent){
var divLog = document.querySelector('#log'),
log = 'x:' + mousePosition.x + ' * y: ' + mousePosition.y,
p = document.createElement('p').innerHTM = log;
divLog.appendChild(p);
}, false);
Here's the POJS equivalent of other answers that is cross browser back to IE 6 (and probably IE 5 but I don't have it to test any more). No global variables even:
function addEvent(el, evt, fn) {
if (el.addEventListener) {
el.addEventListener(evt, fn, false);
} else if (el.attachEvent) {
el.attachEvent('on' + evt, fn);
}
}
(function () {
var x, y;
window.onload = function() {
addEvent(document.body, 'mousemove', function(e) {
// Support IE event model
e = e || window.event;
x = e.pageX || e.clientX;
y = e.pageY || e.clientY;
});
// Show coords, assume element with id "d0" exists
addEvent(document.body, 'keypress', function() {
document.getElementById('d0').innerHTML = x + ',' + y;
});
}
}());
But there are bigger issues. Key events are only dispatched if an element that can receive keyboard input is focused (input, textarea, and so on). Also, if the user scrolls the screen without moving the mouse, the coordinates will probably be wrong.
An alternative solution is to use CSS to replace the cursor with a custom animation.
If you're using jQuery, you can do the following (assuming you have an image with id="wheelImage" and whose position is set to absolute), write the following inside your keydown event. Here we use the global properties pageX and pageY that are passed to any handler. You can also use jQuery's shiftKey property to check if the shift key has been pressed.
$().keydown(function(e) {
if (e.shiftKey) {
e.preventDefault();
$('#wheelImage').css('left',e.pageX ).css('top', e.pageY);
}
});
Cache the mouse position.
var x = 0, y = 0;
document.addEventListener('mousemove', function(e){
x = e.pageX
y = e.pageY;
}, false);
document.addEventListener('keyup', function(e){
console.log(x + ' ' + y);
}, false);
Or with JS Ninja Library.
var x = 0, y = 0;
$(document).mousemove(function(e){
x = e.pageX
y = e.pageY;
});
$(document).keypressed(function() {
console.log(x + ' ' + y);
});
Related
How can a function, which is triggered by another function, get the mouse's position? Here's my code:
function myFunction(e){
setTimeout(function(){
if(isMouseDown == true){
mouseX = e.clientX;
mouseY = e.clientY;
document.getElementById('myElement').innerHTML = mouseX + ' , ' + mouseY;
myFunction(event);
} else {}
}, 100);
}
What this does is to display the coordinates when clicked. I need it to display them every 100ms if isMouseDown == true.
Thanks
There is no way in Javascript for a random Javascript function to get the mouse position. The current mouse position only comes from an event object for a mouse-related event. So, if you want to keep track of the mouse position, then you can register an event handler for the mousemove event and for mousedown and mouseup to keep track of the button state.
If you only want to display the mouse position, ever 100ms, then you can set a timer so that it is only displayed that often, but you will need to keep track of the current mouse position in a mousemove event handler.
Here's a simple code example:
var lastMouseX = 0, lastMouseY = 0;
document.addEventListener("mousemove", function(e) {
lastMouseX = e.clientX;
lastMouseY = e.clientY;
});
var mouseTimer;
document.addEventListener("mousedown", function() {
if (!mouseTimer) {
mouseTimer = setInterval(function() {
document.getElementById("x").innerHTML = lastMouseX;
document.getElementById("y").innerHTML = lastMouseY;
}, 100);
}
});
document.addEventListener("mouseup", function() {
clearInterval(mouseTimer);
mouseTimer = null;
});
<div id="x"></div>
<div id="y"></div>
It's a bit fuzzy what you're trying to achieve, however you're not going to get a periodic event if you're usingsetTimeout(). It sounds like you're looking for setInterval(). See the below example:
var mouseX = 0;
var mouseY = 0;
var isMouseDown = true;
document.onmousemove = function(e){
mouseX = e.pageX;
mouseY = e.pageY;
}
setInterval("myFunction()", 100);
function myFunction(){
if(isMouseDown) {
document.getElementById('myElement').innerHTML = mouseX + ' , ' + mouseY;
}
}
<div id="myElement"></div>
I have a jQuery function that is running on mousemove event. Actually, I have to separate image one is main image and one shadow image. I am using mousemove event to reflect the shadow image. Everything is working fine but I want to stop the mousemove event when I will hover over the main image. Again It will run when I will release the mouse form the image. How can I get that. Here is link - http://zakirinfo.com/mouse/
HTML
<div style="width:100%">
<img id="shadow-img" style="position:absolute;"src="./assets/img/slsshadow.jpg"></img>
<img id="center-img" style="position:absolute;left:50%;top:50%;margin-left:-204px;margin-top:-204px" src="./assets/img/slslogo.jpg"></img>
</div>
jQuery
(function() {
var shadowImg = document.getElementById('shadow-img');
var centerImg = document.getElementById('center-img');
document.onmousemove = handleMouseMove;
function handleMouseMove(event) {
var center = {
x : centerImg.getBoundingClientRect().left + 204,
y : centerImg.getBoundingClientRect().top
};
console.log(center);
var shadowPos = {
x : (1.8 * center.x) - event.pageX,
y : (2.2 * center.y) - event.pageY,
};
shadowImg.style.transform = 'translate(' + shadowPos.x + 'px,' + shadowPos.y +'px)';
};
})();
Here is the working code (if i understood you correctly):
(function() {
var shadowImg = document.getElementById('shadow-img');
var centerImg = document.getElementById('center-img');
document.addEventListener("mousemove", handleMouseMove);
centerImg.addEventListener("mouseenter", function() {
document.removeEventListener("mousemove", handleMouseMove);
});
centerImg.addEventListener("mouseleave", function() {
document.addEventListener("mousemove", handleMouseMove);
});
function handleMouseMove(event) {
var center = {
x : centerImg.getBoundingClientRect().left + 204,
y : centerImg.getBoundingClientRect().top
};
console.log(center);
var shadowPos = {
x : (1.8 * center.x) - event.pageX,
y : (2.2 * center.y) - event.pageY,
};
shadowImg.style.transform = 'translate(' + shadowPos.x + 'px,' + shadowPos.y +'px)';
};
})();
HTML is unchanged. Also here is a jsfiddle: http://jsfiddle.net/wbkdrdpk/2/
Explanation:
First of all I use addEventListener to assign the events.
document.addEventListener("mousemove", handleMouseMove);
This does pretty much the same as your line but it has the advantage that you can call the removeEventListener function to remove the handler
Now I add two event listener to the image to remove and re-add the move handler:
centerImg.addEventListener("mouseenter", function() {
document.removeEventListener("mousemove", handleMouseMove);
});
centerImg.addEventListener("mouseleave", function() {
document.addEventListener("mousemove", handleMouseMove);
});
pretty simple stuff.
Edit: i removed all jquery code since you don't actually use jquery even though you tagged your question with "jquery". I removed the tag too since it's misleading ;)
I have a text that when I long press the mouse button (700 ms), I will activate an text editor over that text. During this time (when the mouse is pressed) I have to check if the mouse position has moved. The problem is, that I only have one event, mouse down pressed event.
How do I found out if the mouse has been moved?
I have tried to take a new event but I am a beginner to jquery so I couldn't achieve what I wanted to.
this is the function where i get the event.
onTaskItemMouseDown: function (event) {
// We only check the left click
if (event.button !== 0) { return true; }
var that = this,
initialX = event.pageX,
initialY = event.pageY;
// Set timeout
console.log("x=" + initialX);
console.log("y=" + initialY);
this.pressTimer = window.setTimeout(function () {
clearTimeout(that.pressTimer);
that.pressTimer = 0;
that.onEditTask(event, that.$(event.currentTarget).closest(".task").find(".dropdown-container").data("task-id"));
}, MindomoUtils.longClickDuration);
return true;
},
You probably are looking for mousemove event.
I can see you already using jQuery so here is an example for you.
HTML for output
<ul class="output"></ul>
jQuery
$(document).on('mousedown', onMouseDown)
$(document).on('mousemove', onMouseMove)
$(document).on('mouseup', onMouseUp)
var mouseIsDown = false
function onMouseDown(event) {
// set boolean true
mouseIsDown = true
$('.output').append($('<li>').text('Mouse down - x: ' + event.pageX + ' y: ' + event.pageY))
}
function onMouseMove(event) {
if(mouseIsDown) {
$('.output').append($('<li>').text('Mouse moving - x: ' + event.pageX + ' y: ' + event.pageY))
}
}
function onMouseUp(event) {
// set boolean false again
mouseIsDown = false
$('.output').append($('<li>').text('Mouse up - x: ' + event.pageX + ' y: ' + event.pageY))
}
Here you can play with it yourself.
This question already has answers here:
How to get mouse position in jQuery without mouse-events?
(7 answers)
Closed 3 years ago.
In Javascript, within the Javascript event handler for onMouseMove how do I get the mouse position in x, y coordinates relative to the top of the page?
if you can use jQuery, then this will help:
<div id="divA" style="width:100px;height:100px;clear:both;"></div>
<span></span><span></span>
<script>
$("#divA").mousemove(function(e){
var pageCoords = "( " + e.pageX + ", " + e.pageY + " )";
var clientCoords = "( " + e.clientX + ", " + e.clientY + " )";
$("span:first").text("( e.pageX, e.pageY ) - " + pageCoords);
$("span:last").text("( e.clientX, e.clientY ) - " + clientCoords);
});
</script>
here is pure javascript only example:
var tempX = 0;
var tempY = 0;
function getMouseXY(e) {
if (IE) { // grab the x-y pos.s if browser is IE
tempX = event.clientX + document.body.scrollLeft;
tempY = event.clientY + document.body.scrollTop;
}
else { // grab the x-y pos.s if browser is NS
tempX = e.pageX;
tempY = e.pageY;
}
if (tempX < 0){tempX = 0;}
if (tempY < 0){tempY = 0;}
document.Show.MouseX.value = tempX;//MouseX is textbox
document.Show.MouseY.value = tempY;//MouseY is textbox
return true;
}
This is tried and works in all browsers:
function getMousePos(e) {
return {x:e.clientX,y:e.clientY};
}
Now you can use it in an event like this:
document.onmousemove=function(e) {
var mousecoords = getMousePos(e);
alert(mousecoords.x);alert(mousecoords.y);
};
NOTE: The above function will return the mouse co-ordinates relative to the viewport, which is not affected by scroll. If you want to get co-ordinates including scroll, then use the below function.
function getMousePos(e) {
return {
x: e.clientX + document.body.scrollLeft,
y: e.clientY + document.body.scrollTop
};
}
It might be a bit overkill to use d3.js just for finding mouse coordinates, but they have a very useful function called d3.mouse(*container*). Below is an example of doing what you want to do:
var coordinates = [0,0];
d3.select('html') // Selects the 'html' element
.on('mousemove', function()
{
coordinates = d3.mouse(this); // Gets the mouse coordinates with respect to
// the top of the page (because I selected
// 'html')
});
In the above case, the x-coordinate would be coordinates[0], and the y-coordinate would be coordinates[1]. This is extremely handy, because you can get the mouse coordinates with respect to any container you want to by exchanging 'html' with the tag (e.g. 'body'), class name (e.g. '.class_name'), or id (e.g. '#element_id').
Especially with mousemove events, that fire fast and furious, its good to pare down the handlers before you use them-
var whereAt= (function(){
if(window.pageXOffset!= undefined){
return function(ev){
return [ev.clientX+window.pageXOffset,
ev.clientY+window.pageYOffset];
}
}
else return function(){
var ev= window.event,
d= document.documentElement, b= document.body;
return [ev.clientX+d.scrollLeft+ b.scrollLeft,
ev.clientY+d.scrollTop+ b.scrollTop];
}
})()
document.ondblclick=function(e){alert(whereAt(e))};
I've attached a focus listener to window (using prototype syntax):
Event.observe( window, 'focus', focusCb.bindAsEventListener( this ) );
I want to determine the mouse position when the window is focused. Unfortunately, in my focusCb method, I don't seem to have access to pageX, pageY, clientX or clientY.
Using quirksmode code:
function doSomething(e) {
var posx = 0;
var posy = 0;
if (!e) var e = window.event;
if (e.pageX || e.pageY) {
posx = e.pageX;
posy = e.pageY;
}
else if (e.clientX || e.clientY) {
posx = e.clientX + document.body.scrollLeft
+ document.documentElement.scrollLeft;
posy = e.clientY + document.body.scrollTop
+ document.documentElement.scrollTop;
}
// posx and posy contain the mouse position relative to the document
// Do something with this information
}
I always get 0, 0.
I thought the focus event would have the mouse position information.
Why doesn't the focus event have this information?
More importantly, how should get I get the mouse position when the window is focused?
IE has clientX and clientY in the event object; though it may be the only one.
Yeah, this is looking pretty horrible. See the section on this page about Mouse Position. I think he does a pretty thorough job of examining it.
Okay, I see you're actually already using his script. Sigh.
Depending on the circumstances, it might not exactly be what you're looking for, but you could, after the focus, wait for the next mousemove event and use that coordinates, something along this line:
var x = 0, y = 0, window_got_focus = false;
window.onfocus = function () { window_got_focus = true };
document.onmousemove = function (event) {
if (window_got_focus) {
window_got_focus = false;
x = event.clientX;
y = event.clentY;
}
};
Drawback is, of course, that you get the coordinates only as soon as the user moves the mouse after focussing.
You can capture the window onclick event and throw the position into a globally scoped variable.
EDIT: Also if you're using prototype you should have access to the pointerX and pointerY methods of the event object.
call doSomething() function on mouse move
document.onmousemove = function (e)
{
doSomething(e);
};