Jump to content

  • Log In with Google      Sign In   
  • Create Account


HTML5: Mouse position outside the canvas?


Old topic!
Guest, the last post of this topic is over 60 days old and at this point you may not reply in this topic. If you wish to continue this conversation start a new topic.

  • You cannot reply to this topic
3 replies to this topic

#1 blueshogun96   Crossbones+   -  Reputation: 873

Like
0Likes
Like

Posted 11 April 2014 - 12:10 AM

I've searched on google for a long time now, how do I detect whether the mouse position is outside of the canvas?  Once it's outside, the mouse processing stops.  A key rule of my game is when a user touches the side of the screen, the game is over.  An explosion along the border of the canvas is what's supposed to happen, but using the last known position of the mouse inside the canvas as the explosion point will confuse users.  This is a real pain on HTML5, in spite of how easy the port of my existing game has been from C++.

 

If you don't know what I'm talking about, here's a link to my [unfinished] web port: http://looptil.shogun3d.net (doesn't work on Firefox, yet; use IE, Chrome or Safari).

 

I understand you can use the events 'mouseout' and 'mouseover' to find out when the mouse leaves the canvas and returns, but how do you get the exact position of the mouse when it's outside the canvas?  This sucks.  Any ideas?  Thanks.

 

Shogun.


Follow Shogun3D on the official website: http://shogun3d.net

 

blogger.png twitter.png tumblr_32.png facebook.png


Sponsor:

#2 dr01d3k4   Members   -  Reputation: 402

Like
0Likes
Like

Posted 11 April 2014 - 03:47 AM

In my JavaScript + HTML5 canvas games, I've written and used this file to deal with mouse input:

(function (window) {
	var mouse = {
		down: false,
		x: -1,
		y: -1
	};

	var previousMouse = {
		down: false,
		x: -1,
		y: -1
	};


	var mouseLetGo = false;



	var updateMouse = function () {
		previousMouse.down = mouse.down;
		previousMouse.x = mouse.x;
		previousMouse.y = mouse.y;
		
		if (mouseLetGo) {
			mouse.down = false;
			mouseLetGo = false;
		}
	};



	var getMousePosition = function (event) {
		var x = -1;
		var y = -1;

		if ((event.x === undefined) || (event.y === undefined)) {
			x = event.clientX + document.body.scrollLeft + document.documentElement.scrollLeft;
			y = event.clientY + document.body.scrollTop + document.documentElement.scrollTop;
		} else {
			x = event.x;
			y = event.y;
		}

		x -= canvas.offsetLeft + canvasBorderThickness;
		y -= canvas.offsetTop + canvasBorderThickness;

		return [x, y];
	};



	var setMousePosition = function (event) {
		event = event || window.event;
		var pos = getMousePosition(event);
		mouse.x = pos[0];
		mouse.y = pos[1];

	};



	var onMouseDown = function (event) {
		mouse.down = true;
		setMousePosition(event);
	};



	var onMouseMove = function (event) {
		setMousePosition(event);
	};



	var onMouseUp = function (event) {
		mouseLetGo = true;
		setMousePosition(event);
	};



	var isMouseDown = function () {
		return mouse.down;
	};



	var isMouseUp = function () {
		return !mouse.down
	};



	var getMouseX = function () {
		return mouse.x;
	};



	var getMouseY = function () {
		return mouse.y;
	};



	var isMouseOver = function (x, y, width, height) {
		return ((getMouseX() >= x) && (getMouseX() <= x + width) && (getMouseY() >= y) && (getMouseY() <= y + height));
	};



	var wasMouseDown = function () {
		return previousMouse.down;
	};



	var wasMouseUp = function () {
		return !previousMouse.down;
	};



	var setMouseDown = function (down) {
		mouse.down = down;
	};



	window.updateMouse = updateMouse;
	window.onMouseDown = onMouseDown;
	window.onMouseMove = onMouseMove;
	window.onMouseUp = onMouseUp;
	window.isMouseDown = isMouseDown;
	window.isMouseUp = isMouseUp;
	window.getMouseX = getMouseX;
	window.getMouseY = getMouseY;
	window.isMouseOver = isMouseOver;
	window.wasMouseDown = wasMouseDown;
	window.wasMouseUp = wasMouseUp;
	window.setMouseDown = setMouseDown;
})(window);

In onload, I connect those functions up to the events:

canvas.onmousedown = onMouseDown;
canvas.onmousemove = onMouseMove;
canvas.onmouseup = onMouseUp;

In each frame of the game, I call the updateMouse(); function.

 

The getMouseX/Y() functions return the pixel position of the mouse based on the top left corner of the canvas. This means that if x < 0 or x > canvasWidth (and same for y), then it is out of the screen. The mouse events don't fire once the mouse is outside the canvas though (apart from the first with a -1/canvasWidth + 1/canvasHeight + 1 value).

 

 

 

Using your method, you could try to clamp the last known position of the mouse to the screen.

// Assume mouse closest to left side first
var drawAtX = 0;
var drawAtY = mouse.y;
var shortestDistance = mouse.x;

// If closer to top
if (mouse.y < shortestDistance) {
	shortestDistance = mouse.y;
	drawAtX = mouse.x;
	drawAtY = 0;
}

// Right side
if (canvasWidth - mouse.x < shortestDistance) {
	shortestDistance = canvasWidth - mouse.x;
	drawAtX = canvasWidth;
	drawAtY = mouse.y;
}

// Bottom side
if (canvasHeight - mouse.y < shortestDistance) {
	shortestDistance = canvasHeight - mouse.y;
	drawAtX = mouse.x;
	drawAtY = canvasHeight;
}

Or if you know the 2 last positions of the mouse (and so deltaX and deltaY), you could continue in the direction the mouse was moving until it hits the edge.


Edited by dr01d3k4, 11 April 2014 - 03:53 AM.

Falling block colour flood game thing I'm making: http://jsfiddle/dr01d3k4/JHnCV/


#3 Carsten Germer   Members   -  Reputation: 1120

Like
0Likes
Like

Posted 11 April 2014 - 05:42 AM

I don't have a tested solution, but how about jQuery .mousemove on a surrounding div or .pageX on the document?

http://api.jquery.com/mousemove/

http://api.jquery.com/event.pagex/

http://stackoverflow.com/questions/4517198/how-to-get-mouse-position-in-jquery-without-mouse-events?answertab=active#tab-top

 

Cheers /Carsten



#4 JohnnyCode   Members   -  Reputation: 226

Like
0Likes
Like

Posted 11 April 2014 - 06:52 AM

 

I understand you can use the events 'mouseout' and 'mouseover' to find out when the mouse leaves the canvas and returns, but how do you get the exact position of the mouse when it's outside the canvas?

you can attach another mousemove event to <body> object of document- this event will contain event object knowing position in pattern of document/body. you of course cannot track mouse position outside of the very window, though, you can get window.screen property that is actualy pixel resulution of client computer/device.






Old topic!
Guest, the last post of this topic is over 60 days old and at this point you may not reply in this topic. If you wish to continue this conversation start a new topic.



PARTNERS