I'm working on a drag and drop lib and i would like to add the mouse's position variation to the dragged element's actual position instead of just setting it's position to the current cursor position in the window. This would allow me not to use position: fixed and be able to drag position relative/absolute; elements.
To know the old position of the mouse (before the mousemove handler is called) i can just store the position in a variable in the previous call to that handler using e.pageX and pageY. But what about the first time the mouse handler is moved ? How can i know the old mouse position to determine it's variation when i havn't stored that old position yet ?
A piece of code :
var $dragged = null,
$window = $(window),
oldMouseX = null,
oldMouseY = null;
var mouseMoveHandler = function(e) {
var curTop = $dragged.css('top'),
curLeft = $dragged.css('left');
$dragged.css({
top : curTop + e.pageY - oldMouseY,
left : curLeft + e.pageX - oldMouseX,
});
oldMouseX = e.pageX;
oldMouseY = e.pageY;
};
$('.Draggable')
.attr('draggable', true)
.css({userSelect: 'none'})
.on('mousedown', function() {
$dragged = $(this);
$window.bind('mousemove', mouseMoveHandler);
})
.on('mouseup', function() {
$dragged = null;
$window.unbind('mousemove', mouseMoveHandler);
})
Related
I want to make a mobile phone theme effect on the browser, and I need to make the icon get the current mouse position when it is dragged. In order to judge whether the user wants to insert the currently dragged icon at the mouse position, but I use the event object (#drag($event) ) of the drag method in the Firefox browser to get the mouse coordinates (event. pageX, event.screenX), it shows (0,0) or a fixed value, but when I use Google Chrome, the above situation does not occur, it immediately gives me the coordinates of the current mouse. Regarding the problem of the value of layerXY in the picture, this value will only be updated once at the beginning of dragging, and will not change at the rest of the time. Since I personally like to use the Firefox browser, I want to solve this problem, can anyone help me? Or give me some other suggestions to implement this function (my English is not very good, from google translate)
You could update the mouse coordinate on a global variable when the mouse moves so that it will be ready for you when mouse is down.
let drag = document.querySelector('.note');
var pageX, pageY
drag.onmousedown = function(e) {
let coord = getCoord(drag);
let shiftX = pageX - coord.left;
let shiftY = pageY - coord.top;
drag.style.position = 'absolute';
document.body.appendChild(drag);
moveNote(e);
drag.style.zIndex = 1000;
function moveNote(e) {
drag.style.left = pageX - shiftX + 'px';
drag.style.top = pageY - shiftY + 'px';
var position = {
x: drag.style.left,
y: drag.style.top
}
}
document.onmousemove = function(e) {
moveNote(e);
};
drag.onmouseup = function() {
document.onmousemove = null;
drag.onmouseup = null;
};
}
function getCoord(elem) {
let main = elem.getBoundingClientRect();
return {
top: main.top,
left: main.left
};
}
window.onload = function() {
document.addEventListener("mousemove", function(e) {
pageX = e.pageX
pageY = e.pageY
});
drag.style.position = 'absolute';
document.body.appendChild(drag);
drag.style.display = 'block'
}
.note {
width: 50px;
height: 50px;
background: red;
display: none;
}
<div class="note"></div>
Is it possible to know if mouse has left specific portion of the window? The values are given below:
var cursorX;
var cursorY;
document.onmousemove = function(e){
cursorX = e.pageX;
cursorY = e.pageY;
}
document.addEventListener('mouseout', function(e) {
var dims = elem.getBoundingClientRect();
var top = window.scrollY + dims.top;
var left = dims.left;
var width = dims.width;
var bottom = dims.height;
if (what condition should be here) {
console.log('yes mouse has left that portion')
document.getElementById('div-in-the-end-of-body').style .display = 'none';
}
});
For example values of dims in console log are ClientRect {top: 155.375, right: 621, bottom: 540.375, left: 313, width: 308…}
Here is visual of what I'm trying to achieve.
Edit: That div at the end of the body has absolute position and it hovers on the images. If I hover at that div images consider mouse has left it and hides the div. This is the reason I want to do it this way.
Edit # 2: Here is the solution
elem.onmouseout=function(){
var dims = this.getBoundingClientRect();
var top = window.scrollY + dims.top;
var left = dims.left;
var width = dims.width;
var bottom = dims.height;
if(top > 10 || left > 10 || width > 10 || bottom > 10){
document.getElementById('div-in-the-end-of-body').style .display = 'none';
}
}
Have a look at the mouseout event. Alternatively, you could capture mouse events as soon as your mouse has entered your specific region.
You can bind event listeners to the "regions" you want to check. As your regions are objects in javascript, there are event listeners built in or you can using obj.call to call functions not belong to the object you created. For instance,
let rects[] // this is your list of regions
for (let rect of rects) {
rect.onMouseMove((e) => {
// do something when mouse cursor is moving
})
rect.onMouseEnter((e) => {
// do somthing when mouse cursor enters the area
})
rect.onMouseLeave((e) => {
// do something when mouse cursor exits the area
})
}
Ok, I've figured out the solution. Here is working code for those who might need.
elem.onmouseout=function(){
var dims = this.getBoundingClientRect();
var top = window.scrollY + dims.top;
var left = dims.left;
var width = dims.width;
var bottom = dims.height;
if(top > 10 || left > 10 || width > 10 || bottom > 10){
console.log('yay!! ship has left the dock')
}
}
I am trying to create an overlay effect on mouseover of all elements. I wrote this js code, it works for most of the scenarios and fails under some conditions.
JS Code
$(function() {
var overlay = $("<div id='overlay'></div>").css({position:"absolute","display":"none","background":"red"});
$("body").append(overlay);
$("body").on("mouseover", function(e) {
var t = e.target;
var offset = $(t).offset();
var top = offset.top;
var left = offset.left;
var scrollx = $(window).scrollTop();
var scrolly = $(window).scrollLeft();
top -= scrolly;
left -= scrollx;
console.log(overlay); overlay.css({"top":top,"left":left,"width":"50px","height":"2px"});
overlay.show();
});
});
JS Fiddle
https://fiddle.jshell.net/go2j4fk7/12/show/light/
Failure Conditions
Trying to mouseover element inside an iframe. I use $("iframe").contents().mouseover() to bind event.
If parent element has scroll
If element is in fixed position.
How to create an overlay for any element?
How to make a element draggable without using jQuery UI?
I have this code:
<script type="text/javascript">
function show_coords(event)
{
var x=event.clientX;
var y=event.clientY;
var drag=document.getElementById('drag');
drag.style.left=x;
drag.style.top=y
}
</script>
<body style="height:100%;width:100%" onmousemove="show_coords(event)">
<p id="drag" style="position:absolute">drag me</p>
</body>
The problem is that I want to drag while the user the pressing the mouse button. I tried onmousedown but results were negative.
It will be quite easy as you get the concept.
function enableDragging(ele) {
var dragging = dragging || false, //Setup a bunch of variables
x, y, Ox, Oy,
enableDragging.z = enableDragging.z || 1,
current;
ele.onmousedown = function(ev) { //When mouse is down
current = ev.target;
dragging = true; //It is dragging time
x = ev.clientX; //Get mouse X and Y and store it
y = ev.clientY; // for later use.
Ox = current.offsetLeft; //Get element's position
Oy = current.offsetTop;
current.style.zIndex = ++enableDragging.z; //z-index thing
window.onmousemove = function(ev) {
if (dragging == true) { //when it is dragging
var Sx = ev.clientX - x + Ox, //Add the difference between
Sy = ev.clientY - y + Oy; // 2 mouse position to the
current.style.top = Sy + "px"; // element.
current.style.left = Sx + "px";
return false; //Don't care about this.
}
};
window.onmouseup = function(ev) {
dragging && (dragging = false); //Mouse up, dragging done!
}
};
}
enableDragging(document.getElementById("drag")); //draggable now!
var ele = document.getElementsByTagName("div");
for(var i = 0; i < ele.length; i++){ //Every div's is draggable
enableDragging(ele[i]); // (only when its "position"
} // is set to "absolute" or
// "relative")
http://jsfiddle.net/DerekL/NWU9G/
The reason why your code is not working is because the <div> will always follow where your cursor goes, and you are not actually dragging it. The top left corner will always follow your cursor, and this is not we wanted.
UPDATE
Now if you only want a grabber or something similar, just change this part of the script:
ele.onmousedown = function(ev) {
current = ev.target;
to
var grabber = document.createElement("div");
grabber.setAttribute("class", "grabber");
ele.appendChild(grabber);
grabber.onmousedown = function(ev) {
current = ev.target.parentNode;
Now you can only click on the grabber to start the dragging process.
http://jsfiddle.net/DerekL/NWU9G/7/
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);
};