make a draggable function in jquery - javascript

I made a function that allow user to drag any element inside body. The problem I am having is when user move the mouse too fast, it lost track of the position. Is there a better way to track the mouse ?
here is my functions
$(this).on("mousedown",function(event){
//$(this).on("click",function(event){
$(this).css("cursor","move");
mouseX = event.pageX;
mouseY = event.pageY;
xx = mouseX - $(this).position().left;
yy = mouseY - $(this).position().top;
console.log(" mouseX : " +mouseX+ " mouseY : " +mouseY ) ;
console.log(" XX : " +xx+ " YY : " +yy ) ;
$(this).on("mousemove",function(event){
startX = event.pageX;
startY = event.pageY;
console.log("after move page X : " +startX+ " page Y : " +startY ) ;
console.log("before left : " + $(this).position().left + " top : " + $(this).position().top ) ;
dragging = true;
if(dragging){
//this.style.top = startY - yy + 'px';
//this.style.left = startX - xx + 'px';
// $(this).animate({"left":(startX - xx),"top":(startY - yy)},0);
$(this).css("top",(startY - yy));
$(this).css("left",(startX - xx));
console.log("after left : " + this.style.left + " top : " + this.style.top ) ;
}
});
});
it did move with the cursor but can't follow up with fast movement.

Related

Getting an ID and setting a function on mouse moving not working

Here I'm trying to set a function on mouse moving, but it doesn't work.
var btn = document.getElementById('giveUpDiv')
btn.onmousemove = function(e) {
var x = e.pageX - btn.offsetLeft - btn.offsetParent.offsetLeft
var y = e.pageY - btn.offsetTop - btn.offsetParent.offsetTop
btn.style.setProperty('--x', x + 'px')
btn.style.setProperty('--y', y + 'px')
}
const btn = document.querySelector("#giveUpDiv");
btn.addEventListener("mousemove", (e) => {
var x = e.pageX - btn.offsetLeft - btn.offsetParent.offsetLeft
var y = e.pageY - btn.offsetTop - btn.offsetParent.offsetTop
btn.style.setProperty('--x', x + "px");
btn.style.setProperty('--y', y + "px");
});

Get correct click position on scaled image

This is how I get the click position when clicking on an image to do some image transformation. But my problem is, that the image has the CSS attribute max-width: 1000px. So the code works only for images which are smaller. For larger images the position result is not the real pixel which was clicked on.
My question is, if it is possible to calculate the correct click position for the natural sized image. An alternative would be to set some data attributes with the real image size like data-width: '1200px' and data-height: '1000px'. But still I have to do some calculation.
parentPosition = getPosition(event.currentTarget),
x = event.clientX - parentPosition.x,
y = event.clientY - parentPosition.y;
function getPosition(element) {
var xPosition = 0;
var yPosition = 0;
while (element) {
xPosition += (element.offsetLeft - element.scrollLeft + element.clientLeft);
yPosition += (element.offsetTop - element.scrollTop + element.clientTop);
element = element.offsetParent;
}
return { x: xPosition, y: yPosition };
}
If you know natural size and current size, i think you can just do this:
naturalClickPosX = (naturalWidth / currentWidth) * currentClickPosX;
naturalClickPosY = (naturalHeight / currentHeight) * currentClickPosY;
Have a look at this JSFiddle
HTML
<img src="http://placehold.it/1200x1000" width="1000">
JavaScript
$('img').on("click", function(e){
var $img = $(this);
var currentClickPosX = e.pageX - $img.offset().left;
var currentClickPosY = e.pageY - $img.offset().top;
var currentWidth = $img.width();
var currentHeight = $img.height();
var naturalWidth = this.naturalWidth;
var naturalHeight = this.naturalHeight;
var naturalClickPosX = ((naturalWidth / currentWidth) * currentClickPosX).toFixed(0);
var naturalClickPosY = ((naturalHeight / currentHeight) * currentClickPosY).toFixed(0);
alert("Current X: " + currentClickPosX + " Current Y: " + currentClickPosY +
"\r\nNatural X: " + naturalClickPosX + " Natural Y: " + naturalClickPosY);
});
try this , will work on all sizes
$('.img-coordinate').click(function(e){
var parentOffset = $(e.target).parent().offset();
// here the X and Y on Click
X = e.pageX - $(e.target).offset().left;
Y = e.pageY - $(e.target).offset().top;
alert(X + ' , ' + Y );
});
working fiddel : https://jsfiddle.net/h09kfsoo/

jQuery : Get All DOM elements come under the selected part (Rectangle) like zooming plugins of jQuery

I want all the DOM elements (which can be overlapped by others too) to be listed out which falls under the selection. The thing I tried giving me at a fixed coordinate (with overlapped ones) but I need it to give me for full rectangle.
https://jsfiddle.net/mantrig/3tqqy0gt/
var flag=0;
$("#enable-show").click(function(){
if(flag==0) {
$(document).bind('mousemove', function(e){
$('#tail').css({
left: e.pageX - 80,
top: e.pageY-50,
});
var $elements = GetAllElementsAt( e.pageX , e.pageY);
var html="";
$elements.each(function() {
html += $(this)[0].id + "<br />";
$("#result").html(html);
});
$("#tail").show();
});
flag++;
}
else {
$(document).bind('mousemove', function(e){
$("#tail").hide();
});
flag=0;
}
});
function GetAllElementsAt(x, y) {
var $elements = $("body *").map(function() {
var $this = $(this);
var offset = $this.offset();
var l = offset.left;
var t = offset.top;
var h = $this.height();
var w = $this.width();
var maxx = l + w;
var maxy = t + h;
$("ul").append("<li>" + $this[0].id + " (" + $this[0].tagName + ")" + " [l:=" + l + ",t:=" + t + ",h:=" + h + ",w:=" + w + ",maxx:=" + maxx + ",maxy:=" + maxy + "]</li>");
return (y <= maxy && y >= t) && (x <= maxx && x >= l) ? $this : null;
});
return $elements;
}
Can anyone help with it?

How to resize a div based on mouse location?

I'm trying to make a div that expands left, right, up, and down depending on where the mouse is. But when I move the mouse, the div just pops up and doesn't do anything. What is wrong in what I'm doing?
(function() {
document.onmousemove = function(e) {
draw(e);
};
function draw(e) {
var method = [
e.pageX ? e.pageX : e.clientX,
e.pageY ? e.pageY : e.clientY
];
var X = method[0],
Y = method[1];
var html = '<div class="box" style="padding-top:' + Y + ';padding-bottom:' + Y + ';padding-left:' + X + ';padding-right:' + X + '"></div>'
;
document.body.innerHTML = html;
}
})();​
You forgot the unit px:
(function() {
document.onmousemove = function(e) {
draw(e);
};
function draw(e) {
var method = [
e.pageX ? e.pageX : e.clientX,
e.pageY ? e.pageY : e.clientY
];
var X = method[0],
Y = method[1];
var html = '<div class="box" style="background-color:red;padding-top:' + Y + 'px;padding-bottom:' + Y + 'px;padding-left:' + X + 'px;padding-right:' + X + 'px"></div>'
;
document.body.innerHTML = html;
}
})();​
(I've also added a red background in order to make the DIV visible)
jsFiddle: http://jsfiddle.net/8LUwp/
X and Y are numbers. CSS lengths require units. Add some px.
CSS length attributes (padding, margin, height, width etc.) require units - px, em etc. So just having:
padding-top:10
is invalid. Instead you need to add units:
padding-top:10px
So in your case the line setting the html should read:
var html = '<div class="box" style="padding-top:' + Y + 'px;padding-bottom:' + Y + 'px;padding-left:' + X + 'px;padding-right:' + X + 'px"></div>';
You were missing px suffix with the x and Y
(function() {
document.onmousemove = function(e) {
draw(e);
};
function draw(e) {
var method = [
e.pageX ? e.pageX : e.clientX,
e.pageY ? e.pageY : e.clientY
];
var X = method[0],
Y = method[1];
var html = '<div class="box" style="padding-top:' + Y +"px" + ';padding-bottom:' + Y +"px" + ';padding-left:' + X +"px" + ';padding-right:' + X +"px" + '"></div>'
;
document.body.innerHTML = html;
}
})();​

Use jQuery set .css RIGHT if #foo + offset left is greater than page width

Ok, so I am trying to use jQuery to get the innerWidth() of an element #preview. I want to create a conditional that says IF x offset LEFT + #preview width is greater than page width, give it style right: z where z = #preview width + xOffset.
I apologize my code below is a mess and the syntax for .css ("right", (rightFloat + xOffset) + "px") (line 125) is off, but that's part of my problem.
<script>
$(document).ready(function(){
//append "gallery" class to all items with "popup" class
imagePreview();
$(".popup").addClass("gallery");
});
//The overlay or pop-up effect
this.imagePreview = function() { /* CONFIG */
xOffset = 40;
yOffset = 40;
// these 2 variable determine popup's distance from the cursor
// you might want to adjust to get the right result
/* END CONFIG */
$("a.preview").click(function(e) {
return false;
});
$("a.preview").hover(function(e) {
this.t = this.title;
this.title = "";
var c = (this.t != "") ? "<br/>" + this.t : "";
var rightFloat = e.pageX + ("#preview").innerWidth;
$("body").append("<p id='preview'><img src='" + this.href + "' alt='Image preview' />" + c + "</p>");
$("#preview").hide().css("top", (e.pageY - yOffset) + "px").css("left", (e.pageX + xOffset) + "px").fadeIn("2000");
while ((left + 400) > window.innerWidth) {.css("right", (rightFloat + xOffset) + "px")
}
}, function() {
this.title = this.t;
$("#preview").remove();
});
$("a.preview").mousemove(function(e) {
var top = e.pageY - yOffset;
var left = e.pageX + xOffset;
var rightFloat = e.pageX + ("#preview").innerWidth;
//flips the image if it gets too close to the right side
while ((left + 400) > window.innerWidth) {.css("right", +(rightFlaot + xOffset) + "px")
}
$("#preview").css("top", top + "px").css("left", left + "px");
});
};
</script>
Try using http://api.jquery.com/offset/
if($('#preview').offset().right<0){
var right = parseInt($(window).width()) - e.pageX + xOffset;
$("#preview").css("top", top + "px").css("right", right + "px");
}else{
var left = e.pageX + xOffset;
$("#preview").css("top", top + "px").css("left", left + "px");
}
I made these fixes because I couldn't get your code to work in jsfiddle:
var xOffset = 40;
var yOffset = 40;
$("a.preview").bind('mouseover',function(e){
var rightFloat = parseFloat(e.pageX)+$("#preview").innerWidth();
var ptop = parseFloat(e.pageY) - yOffset;
var pleft = parseFloat(e.pageX) + xOffset;
$("#preview").css({"top":ptop + "px","left":pleft + "px"});
});
There's the fixes for the top half but I have no idea what you're trying to do with the bottom part (with the while loop). Can you explain what functionality you want?

Categories