Я хочу сделать небольшое приложение для рисования, используя холст. Поэтому мне нужно найти положение мыши на холсте.Найти положение мыши относительно элемента
ответ
Для людей, использующих JQuery:
Иногда, когда у вас есть вложенные элементы, один из них с событием, прикрепленного к нему, он может ввести в заблуждение, чтобы понять, что ваш браузер видит в качестве родителя. Здесь вы можете указать, какой родитель.
Вы берете положение мыши, а затем вычитаете его из положения смещения родительского элемента.
var x = evt.pageX - $('#element').offset().left;
var y = evt.pageY - $('#element').offset().top;
Если вы пытаетесь получить позицию мыши на странице внутри прокруткой панели:
var x = (evt.pageX - $('#element').offset().left) + self.frame.scrollLeft();
var y = (evt.pageY - $('#element').offset().top) + self.frame.scrollTop();
или положение относительно страницы:
var x = (evt.pageX - $('#element').offset().left) + $(window).scrollLeft();
var y = (evt.pageY - $('#element').offset().top) + $(window).scrollTop();
Обратите внимание на следующее оптимизация производительности:
var offset = $('#element').offset();
// Then refer to
var x = evt.pageX - offset.left;
Таким образом, JQuery не нужно искать #element
для каждой строки.
Это сработало для вас @ben, я бы оценил «Правильный ответ» или комментарий о том, что еще не работает для вас. Может быть, я могу помочь дальше. – Spider
Следует избегать использования $ ('selector') в обработчике событий, если вы не хотите очень вялого кода. Предварительно выберите свой элемент и используйте предварительно выбранную ссылку в вашем обработчике. То же самое для $ (window) делает это один раз и кэширует его. –
Это необязательное упоминание: если вы скопируете приведенный выше код, не забудьте исправить 'var y = (evt.pageY - $ ('# element'). Offset(). Left) + $ (window). scrollTop(); 'to' var y = (evt.pageY - $ ('# element'). offset(). top) + $ (window) .scrollTop(); ' –
вы можете получить его
var element = document.getElementById(canvasId);
element.onmousemove = function(e) {
var xCoor = e.clientX;
var yCoor = e.clientY;
}
Будет ли это работать IE, или IE все еще использует window.event вместо передачи события первому аргументу слушателя? edit - Я думаю, что IE не имеет элемент canvas в любом случае до версии 9, но это все равно должно поддерживать IE из-за таких вещей, как excanvas .... –
Это даст координаты относительно окна браузера, все равно нужно выяснить, в элементе using element.getBoundingClientRect() –
благодарю вас за то, что вы сообщили мне о getBoundingClientRect !!!! Я никогда не понимал, что есть такая вещь! –
Хороший подправить от сложности этой проблемы можно найти здесь: http://www.quirksmode.org/js/events_properties.html#position
Используя методику, описанную здесь вы можете найти позицию Мышки в документ. Затем вы просто проверяете, находится ли он в ограничивающей рамке вашего элемента, который вы можете найти, вызвав element.getBoundingClientRect(), который вернет объект со следующими свойствами: {снизу, высота, левая, правая, верхняя, ширина }. Оттуда тривиально выяснить, произошло ли даже внутри вашего элемента или нет.
К сожалению, это не удается, если происходит какой-либо поворот – Eric
Ниже вычисляет положение мыши относительно элемента холста:
var example = document.getElementById('example');
example.onmousemove = function(e) {
var x = e.pageX - this.offsetLeft;
var y = e.pageY - this.offsetTop;
}
В этом примере, this
относится к example
элементу, и e
является onmousemove
событием.
Что? IE9 поддерживает Canvas, что вы делаете неправильно? – Andrea
Может быть, это я, но две строки кодов, которые используют контекст «этот» недостаток? – Deratrius
Определенно недостающий контекст. «e» - это событие, а «this» - это элемент, связанный с событием 'var example = document.getElementById ('example'); example.onmousemove = function (e) { var X = e.pageX - this.offsetLeft; var Y = e.pageY - this.offsetTop; } ' –
I +1 'Ответ Марка ван Вайка, поскольку он меня в правильном направлении, но не совсем решил его для меня. У меня все еще было смещение при рисовании в элементах, содержащихся в другом элементе.
СЛЕДУЮЩИЙ решил это для меня:
x = e.pageX - this.offsetLeft - $(elem).offset().left;
y = e.pageY - this.offsetTop - $(elem).offset().top;
Других слов - я просто укладываюсь все смещения от всех элементов, вложенных
+1 для вас! Это тот ответ, который я искал. У меня было два холста, наложенных друг на друга, и все координаты были неправильными из-за других div. Я знал, что это проблема, но не знает логики/уравнения, чтобы компенсировать это. Вы тоже исправили мою проблему! = D спасибо! – Partack
Это работает для меня. Благодаря! – user359519
Я нашел этот вопрос, заданный в 2010 году, но никто не кажется, удовлетворенный его : в чистом javascript нет ответа, который возвращает относительные координаты, когда ссылочный элемент вложен внутри других, который может быть с абсолютным позиционированием.Вот мое решение:
var container = myReferenceElement;
function getRelativeCoordinates (e) {
var pos = {}, offset = {}, ref;
ref = container.offsetParent;
pos.x = !! e.touches ? e.touches[ 0 ].pageX : e.pageX;
pos.y = !! e.touches ? e.touches[ 0 ].pageY : e.pageY;
offset.left = container.offsetLeft;
offset.top = container.offsetTop;
while (ref) {
offset.left += ref.offsetLeft;
offset.top += ref.offsetTop;
ref = ref.offsetParent;
}
return {
x : pos.x - offset.left,
y : pos.y - offset.top,
};
}
Я не думаю, что он учитывает смещение элемента 'html' – apieceofbart
Ни один из вышеперечисленных ответов не являются удовлетворительной IMO, так вот что я использую:
// Cross-browser AddEventListener
function ael(e, n, h){
if(e.addEventListener){
e.addEventListener(n, h, true);
}else{
e.attachEvent('on'+n, h);
}
}
var touch = 'ontouchstart' in document.documentElement; // true if touch device
var mx, my; // always has current mouse position IN WINDOW
if(touch){
ael(document, 'touchmove', function(e){var ori=e;mx=ori.changedTouches[0].pageX;my=ori.changedTouches[0].pageY});
}else{
ael(document, 'mousemove', function(e){mx=e.clientX;my=e.clientY});
}
// local mouse X,Y position in element
function showLocalPos(e){
document.title = (mx - e.getBoundingClientRect().left)
+ 'x'
+ Math.round(my - e.getBoundingClientRect().top);
}
И если вы когда-нибудь нужно знать о текущем Y прокрутки положения страницы:
var yscroll = window.pageYOffset
|| (document.documentElement && document.documentElement.scrollTop)
|| document.body.scrollTop; // scroll Y position in page
Как я не нашел JQuery-свободный ответ, который я мог копировать/вставить, вот решение, которое я использовал:
function clickEvent(e) {
// e = Mouse click event.
var rect = e.target.getBoundingClientRect();
var x = e.clientX - rect.left; //x position within the element.
var y = e.clientY - rect.top; //y position within the element.
}
Вам нужно [округлить ограничивающий прямоугольник] (https://stackoverflow.com/questions/40879171/in-javascript-why-does-getboundingclientrect-sometimes- return-floating-point) для обеспечения целочисленных значений с помощью этого метода. –
Координата 'y' выключена, когда прокрутка https://jsfiddle.net/mnpenner/p3w227tg/ – mpen
Новое редактирование должно исправить проблемы прокрутки (с использованием clientX/Y) –
Взятые из this tutorial, с исправлениями сделал благодаря началу комментарий:
function getMousePos(canvas, evt) {
var rect = canvas.getBoundingClientRect();
return {
x: Math.floor((evt.clientX - rect.left)/(rect.right - rect.left) * canvas.width),
y: Math.floor((evt.clientY - rect.top)/(rect.bottom - rect.top) * canvas.height)
};
}
Использование на холсте следующим образом:
var canvas = document.getElementById('myCanvas');
canvas.addEventListener('mousemove', function(evt) {
var mousePos = getMousePos(canvas, evt);
});
Вы должны знать структуру ваша страница, потому что если ваш холст является дочерним элементом div, который, в свою очередь, является дочерним элементом другого div ... тогда история становится более сложной. Вот мой код для холста, который находится внутри 2 уровней div s:
canvas.addEventListener("click", function(event) {
var x = event.pageX - (this.offsetLeft + this.parentElement.offsetLeft);
var y = event.pageY - (this.offsetTop + this.parentElement.offsetTop);
console.log("relative x=" + x, "relative y" + y);
});
Я понимаю, что я немного опоздал, но это работает с Javascript PURE, и даже дает вам координаты указателя внутри элемента, если элемент больше, чем область просмотра, и пользователь прокручивал.
var element_offset_x ; // The distance from the left side of the element to the left of the content area
....// some code here (function declaration or element lookup)
element_offset_x = element.getBoundingClientRect().left - document.getElementsByTagName("html")[0].getBoundingClientRect().left ;
....// code here
function mouseMoveEvent(event)
{
var pointer_location = (event.clientX + window.pageXOffset) - element_offset_x ;
}
Как это работает.
Первое, что мы делаем, это получить местоположение элемента HTML (область содержимого) относительно текущего видового экрана. Если на странице есть полосы прокрутки и прокручивается, то число, возвращаемое getBoundingClientRect().left
для тега html, будет отрицательным. Затем мы используем это число для вычисления расстояния между элементом и левой частью области содержимого. С element_offset_x = element.getBoundingClientRect().left......;
Зная расстояние от элемента из области содержимого. event.clientX
дает нам расстояние от указателя в окне просмотра. Важно понимать, что область просмотра и область содержимого являются двумя разными объектами, просмотр может перемещаться, если страница прокручивается. Следовательно, clientX вернет ТОЛЬКО номер, даже если прокручивается страница.
Чтобы компенсировать это, нам нужно добавить позицию x указателя (относительно окна просмотра) в положение x окна просмотра (относительно области содержимого). Х-положение окна просмотра находится с window.pageXOffset.
Благодарим вас за то, что вы единственный, кто думает о прокрутке. Попробуйте изменить свой ответ, чтобы добавить ось y. – frabjous
Оригинальный ответ сказал, чтобы положить его в iframe. Лучшее решение - использовать события offsetX и offsetY на холсте, который имеет дополнение к 0px.
<html>
<body>
<script>
var main=document.createElement('canvas');
main.width="200";
main.height="300";
main.style="padding:0px;margin:30px;border:thick dashed red";
document.body.appendChild(main);
// adding event listener
main.addEventListener('mousemove',function(e){
var ctx=e.target.getContext('2d');
var c=Math.floor(Math.random()*0xFFFFFF);
c=c.toString(16); for(;c.length<6;) c='0'+c;
ctx.strokeStyle='#'+c;
ctx.beginPath();
ctx.arc(e.offsetX,e.offsetY,3,0,2*Math.PI);
ctx.stroke();
e.target.title=e.offsetX+' '+e.offsetY;
});
// it worked! move mouse over window
</script>
</body>
</html>
Координаты мыши внутри холста могут быть получены благодаря event.offsetX и event.offsetY.Вот небольшой фрагмент кода, чтобы доказать свою точку зрения:
c=document.getElementById("c");
ctx=c.getContext("2d");
ctx.fillStyle="black";
ctx.fillRect(0,0,100,100);
c.addEventListener("mousemove",function(mouseEvt){
// the mouse's coordinates on the canvas are just below
x=mouseEvt.offsetX;
y=mouseEvt.offsetY;
// the following lines draw a red square around the mouse to prove it
ctx.fillStyle="black";
ctx.fillRect(0,0,100,100);
ctx.fillStyle="red";
ctx.fillRect(x-5,y-5,10,10);
});
body {
background-color: blue;
}
canvas {
position: absolute;
top: 50px;
left: 100px;
}
<canvas id="c" width="100" height="100"></canvas>
canvas.onmousedown = function(e) {
pos_left = e.pageX - e.currentTarget.offsetLeft;
pos_top = e.pageY - e.currentTarget.offsetTop;
console.log(pos_left, pos_top)
}
HTMLElement.offsetLeft
HTMLElement.offsetLeft
свойство только для чтения возвращает количество пикселей, в верхнем левом углу текущего элемента смещается влево в пределах узла HTMLElement.offsetParent
.
Для элементов уровня блока, offsetTop
, offsetLeft
, offsetWidth
и offsetHeight
описывают границы блока элемента по отношению к offsetParent
.
Однако для элементов инлайн-уровня (например, span
), который можно обернуть с одной линии на другую, offsetTop
и offsetLeft
описывают позиции первого пограничного ящика (используйте Element.getClientRects()
, чтобы получить его ширину и высоту), в то время как offsetWidth
и offsetHeight
описывают размеры ограничивающего прямоугольника (используйте Element.getBoundingClientRect()
, чтобы получить его положение). Поэтому поле с левым, верхним, шириным и высотой offsetLeft
, offsetTop
, offsetWidth
и offsetHeight
не будет ограничивающей рамкой для пролета с обернутым текстом.
HTMLElement.offsetTop
HTMLElement.offsetTop
свойство только для чтения возвращает расстояние текущего элемента по отношению к верхней части offsetParent
узла.
MouseEvent.pageX
pageX
свойство только для чтения возвращает X (по горизонтали), координаты в пикселях событий относительно всего документа. Это свойство учитывает любую горизонтальную прокрутку страницы.
MouseEvent.pageY
MouseEvent.pageY
свойство только для чтения возвращает Y (по вертикали) координат в пикселях событий относительно всего документа. Это свойство учитывает любую вертикальную прокрутку страницы.
Для более подробного объяснения, обратитесь к сети разработчиков Mozilla:
https://developer.mozilla.org/en-US/docs/Web/API/MouseEvent/pageX https://developer.mozilla.org/en-US/docs/Web/API/MouseEvent/pageY https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/offsetLeft https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/offsetTop
Хотя этот фрагмент кода может решить вопрос, [включая объяснение] (http://meta.stackexchange.com/questions/114762/explaining-entirely-code-based-answers) действительно помогает улучшить качество вашего сообщения. Помните, что вы отвечаете на вопрос читателей в будущем, и эти люди могут не знать причин вашего предложения кода. –
Я действительно надеюсь, что читатели в будущем имеют JS API, который вычисляет это для них. ;-) Это, наверное, самый простой, полный, автономный ответ. Комментирование самоочевидного кода просто отвлекает отходы. – lama12345
I второй запрос PatrickHund для объяснения. Я не эксперт по CSS/JS, и знать больше о взаимоотношениях между, например, 'page' и' offset' было бы очень полезно для меня. Спасибо, что рассмотрели этот запрос! – cxw
на основе @ решения Паука, моя не версия JQuery это:
// Get the container element's bounding box
var sides = document.getElementById("container").getBoundingClientRect();
// Apply the mouse event listener
document.getElementById("canvas").onmousemove = (e) => {
// Here 'self' is simply the current window's context
var x = (e.clientX - sides.left) + self.pageXOffset;
var y = (e.clientY - sides.top) + self.pageYOffset;
}
Это работает как с прокруткой и масштабированием (в этом случае иногда он возвращает flo ATS).
Я бы поднял, но не должны ли это быть минус-знаками для смещения страницы? Либо это, либо круглые скобки вокруг второй части? –
- 1. Javascript: Получить положение мыши относительно родительского элемента
- 2. Найти положение элемента управления относительно другого управления
- 3. Как постоянно находить положение мыши относительно панели?
- 4. Фиксированное положение относительно родительского элемента
- 5. Найти положение мыши относительно контроля, а не экрана
- 6. JS: координаты мыши относительно элемента
- 7. Найти положение сцены относительно экрана?
- 8. Найти положение смартфона относительно компьютера
- 9. Перемещение элемента относительно мыши координаты внутри элемента
- 10. Получить положение мыши относительно уменьшенного значения div
- 11. Как получить положение координаты относительно позиции мыши?
- 12. положение мыши в JDialog относительно JTable
- 13. Как найти положение перетаскиваемого элемента относительно области сбрасывания
- 14. boundingClientRect, чтобы получить положение элемента относительно документа
- 15. получить позицию мыши относительно родительского элемента
- 16. Получить положение элемента относительно монитора с javascript
- 17. найти положение элемента - angularjs
- 18. Найти положение мыши вне JFrame?
- 19. Найти положение мыши в JFrame
- 20. Определить положение элемента относительно окна браузера
- 21. Как использовать абсолютное положение относительно родительского элемента
- 22. Получить положение падения относительно элемента в QTreeWidget
- 23. CSS Фоновое положение относительно документа не элемента?
- 24. Как сделать положение элемента директивы относительно ng-повторного элемента?
- 25. Поиск положения указателя мыши относительно элемента svg
- 26. Как вычислить положение мыши из центра элемента в JQuery
- 27. C# - Перемещение элемента управления в положение мыши
- 28. Установить положение элемента UI на позицию мыши
- 29. Как получить положение мыши?
- 30. Положение блока относительно родительского
Полное решение: http://acko.net/blog/mouse-handling-and-absolute-positions-in-javascript/ –
Мне нравится, как коротка, но объясняет все, что это за сообщение. – dwjohnston
Это действительно старый, но я только что начал проект GitHub, который, помимо всего прочего, делает именно то, что вам нужно: http://brainlessdeveloper.com/mouse-move-interaction-spot-js/ –