Ich möchte eine kleine Mal-App mit Leinwand machen. Also muss ich die Position der Maus auf der Leinwand finden.
javascript
Ben Shelock
quelle
quelle
Antworten:
Für Benutzer von JQuery:
Wenn Sie verschachtelte Elemente haben, von denen eines mit dem Ereignis verknüpft ist, kann es manchmal verwirrend sein, zu verstehen, was Ihr Browser als übergeordnetes Element ansieht. Hier können Sie angeben, welcher Elternteil.
Sie nehmen die Mausposition und subtrahieren sie dann von der Versatzposition des übergeordneten Elements.
Wenn Sie versuchen, die Mausposition auf einer Seite in einem Bildlaufbereich zu ermitteln:
Oder die Position relativ zur Seite:
Beachten Sie die folgende Leistungsoptimierung:
Auf diese Weise muss JQuery nicht
#element
für jede Zeile nachschlagen .Aktualisieren
Es gibt eine neuere JavaScript-Version von @anytimecoder für Browser, die getBoundingClientRect () unterstützen .
quelle
var y = (evt.pageY - $('#element').offset().left) + $(window).scrollTop();
zuvar y = (evt.pageY - $('#element').offset().top) + $(window).scrollTop();
Da ich keine jQuery-freie Antwort gefunden habe, die ich kopieren / einfügen konnte, habe ich folgende Lösung verwendet:
JSFiddle des vollständigen Beispiels
quelle
e.currentTarget
nicht e.target. Andernfalls werden Kinderelemente davon betroffen seinIm Folgenden wird die Mauspositionsbeziehung zum Canvas-Element berechnet:
In diesem Beispiel
this
bezieht sich auf dasexample
Element unde
ist dasonmousemove
Ereignis.quelle
var example = document.getElementById('example'); example.onmousemove = function(e) { var X = e.pageX - this.offsetLeft; var Y = e.pageY - this.offsetTop; }
this
ane.currentTarget
, dass Sie die Position in Bezug auf das Element erhalten , dass Sie den Ereignis - Listener hinzugefügt.In reinem Javascript gibt es keine Antwort, die relative Koordinaten zurückgibt, wenn das Referenzelement in anderen verschachtelt ist, was absolut positioniert sein kann. Hier ist eine Lösung für dieses Szenario:
quelle
html
Element Offsetwhile(reference !== undefined)
durchwhile(reference)
. Zumindest in Chrome wird der offsetParent nichtundefined
, sondernnull
. Nur zu überprüfen, obreference
es wahr ist, stellt sicher, dass es mit beidenundefined
und funktioniertnull
.offsetParent
Eigenschaft gibt, die sich auch in anderen Situationen als sehr nützlich herausstellt!scrollLeft
undscrollTop
kompensieren.Eine gute Beschreibung der Schwierigkeit dieses Problems finden Sie hier: http://www.quirksmode.org/js/events_properties.html#position
Mit der dort beschriebenen Technik finden Sie die Position der Maus im Dokument. Dann überprüfen Sie einfach, ob es sich innerhalb des Begrenzungsrahmens Ihres Elements befindet, den Sie durch Aufrufen
element.getBoundingClientRect()
eines Objekts mit den folgenden Eigenschaften finden können :{ bottom, height, left, right, top, width }
. Von dort aus ist es trivial herauszufinden, ob das überhaupt in Ihrem Element passiert ist oder nicht.quelle
Ich habe alle diese Lösungen ausprobiert und aufgrund meines speziellen Setups mit einem matrixtransformierten Container (Panzoom-Bibliothek) hat keiner funktioniert. Dies gibt den korrekten Wert zurück, auch wenn gezoomt und geschwenkt wird:
Aber nur, wenn keine untergeordneten Elemente im Weg sind. Dies kann umgangen werden, indem sie mithilfe von CSS für das Ereignis "unsichtbar" gemacht werden:
quelle
Ich kam in dieser Frage, aber um es für meinen Fall arbeiten zu lassen (mit dragover- auf einem DOM-Elemente (nicht in meinem Fall sein Leinwand)), fand ich , dass Sie nur noch verwenden
offsetX
undoffsetY
auf dem dragover-Maus - Ereignisse .quelle
Ich +1 'Mark van Wyks Antwort, als sie mich in die richtige Richtung brachte, aber nicht ganz für mich löste. Ich hatte immer noch einen Versatz beim Malen in Elementen, die in einem anderen Element enthalten waren.
Fllowing löste es für mich:
Mit anderen Worten - ich habe einfach alle Offsets aller verschachtelten Elemente gestapelt
quelle
Keine der oben genannten Antworten ist IMO zufriedenstellend, daher verwende ich Folgendes:
Und wenn Sie jemals die aktuelle Y-Bildlaufposition der Seite kennen müssen:
quelle
Wenn Sie regelmäßig Websites oder PWAs (Progressive Web Apps) für mobile Geräte und / oder Laptops / Monitore mit Touchscreens entwickeln, sind Sie hier gelandet, weil Sie möglicherweise an Mausereignisse gewöhnt sind und die manchmal schmerzhafte Erfahrung von Touch noch nicht kennen Ereignisse ... yay!
Es gibt nur 3 Regeln:
mousemove
oder während dertouchmove
Veranstaltungen so wenig wie möglich .mousedown
oder während dertouchstart
Veranstaltungen so viel wie möglich .Es ist unnötig zu erwähnen, dass
touch
Ereignisse komplizierter sind , da es mehrere geben kann und sie flexibler (komplizierter) sind als Mausereignisse. Ich werde hier nur eine einzige Berührung behandeln. Ja, ich bin faul, aber es ist die häufigste Art der Berührung.Verwenden Sie lieber Vue.js ? Ich mache! Dann würde Ihr HTML so aussehen:
quelle
Sie können es durch bekommen
quelle
Entnommen aus diesem Tutorial , mit Korrekturen dank des Top-Kommentars:
Verwenden Sie auf einer Leinwand wie folgt:
quelle
Mir ist klar, dass ich etwas spät dran bin, aber dies funktioniert mit PURE-Javascript und gibt Ihnen sogar die Koordinaten des Zeigers innerhalb des Elements an, wenn das Element größer als das Ansichtsfenster ist und der Benutzer einen Bildlauf durchgeführt hat.
Als erstes ermitteln wir die Position des HTML-Elements (des Inhaltsbereichs) relativ zum aktuellen Ansichtsfenster. Wenn die Seite Bildlaufleisten hat und gescrollt wird, wird die Nummer von zurückgegeben
getBoundingClientRect().left
für das HTML-Tag zurückgegebene negativ. Wir verwenden diese Zahl dann, um den Abstand zwischen dem Element und der linken Seite des Inhaltsbereichs zu berechnen. Mitelement_offset_x = element.getBoundingClientRect().left......;
Kenntnis des Abstands des Elements vom Inhaltsbereich.
event.clientX
gibt uns den Abstand des Zeigers vom Ansichtsfenster. Es ist wichtig zu verstehen, dass das Ansichtsfenster und der Inhaltsbereich zwei verschiedene Entitäten sind. Das Ansichtsfenster kann verschoben werden, wenn die Seite gescrollt wird. Daher gibt clientX die gleiche Nummer zurück, auch wenn die Seite gescrollt wird.Um dies zu kompensieren, müssen wir die x-Position des Zeigers (relativ zum Ansichtsfenster) zur x-Position des Ansichtsfensters (relativ zum Inhaltsbereich) hinzufügen. Die X-Position des Ansichtsfensters wird mit gefunden
window.pageXOffset.
quelle
Basierend auf der Lösung von @ Spider lautet meine Nicht-JQuery-Version wie folgt:
Dies funktioniert sowohl beim Scrollen als auch beim Zoomen (in diesem Fall werden manchmal Floats zurückgegeben).
quelle
Die Mauskoordinaten innerhalb einer Zeichenfläche können dank event.offsetX und event.offsetY abgerufen werden. Hier ist ein kleiner Ausschnitt, um meinen Standpunkt zu beweisen:
quelle
HTMLElement.offsetLeft
Die
HTMLElement.offsetLeft
schreibgeschützte Eigenschaft gibt die Anzahl der Pixel zurück, um die die obere linke Ecke des aktuellen Elements innerhalb der nach links versetzt istHTMLElement.offsetParent
Knotens .Für Block-Elemente,
offsetTop
,offsetLeft
,offsetWidth
, undoffsetHeight
die Grenze Kasten eines Elements relativ zum beschreibenoffsetParent
.Für Elemente auf Inline-Ebene (z. B.
span
), die von einer Zeile zur nächsten umbrechen könnenoffsetTop
undoffsetLeft
die Positionen des ersten Rahmenrahmens beschreiben (verwendenElement.getClientRects()
, um dessen Breite und Höhe zu ermitteln), währendoffsetWidth
undoffsetHeight
die Abmessungen des Begrenzungsrahmens beschreiben (verwendenElement.getBoundingClientRect()
, um seine Position zu erhalten). Daher ist ein Kasten mit der linken, oberen, Breite und HöheoffsetLeft
,offsetTop
,offsetWidth
undoffsetHeight
nicht ein Begrenzungsrahmen für eine Spanne mit umwickeltem Text sein.HTMLElement.offsetTop
Die
HTMLElement.offsetTop
schreibgeschützte Eigenschaft gibt den Abstand des aktuellen Elements zum oberen Rand desoffsetParent
Knotens zurück.MouseEvent.pageX
Die
pageX
schreibgeschützte Eigenschaft gibt die X-Koordinate (horizontal) in Pixel des Ereignisses relativ zum gesamten Dokument zurück. Diese Eigenschaft berücksichtigt jedes horizontale Scrollen der Seite.MouseEvent.pageY
Die
MouseEvent.pageY
schreibgeschützte Eigenschaft gibt die Y-Koordinate (vertikal) in Pixel des Ereignisses relativ zum gesamten Dokument zurück. Diese Eigenschaft berücksichtigt jedes vertikale Scrollen der Seite.Weitere Erläuterungen finden Sie im Mozilla Developer Network:
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
quelle
page
undoffset
wäre für mich sehr hilfreich. Vielen Dank, dass Sie diese Anfrage berücksichtigt haben!Ich habe eine andere Lösung implementiert, die ich für sehr einfach halte, also dachte ich, ich würde sie mit euch teilen.
Das Problem für mich war also, dass das gezogene Div für den Mauszeiger auf 0,0 springen würde . Also musste ich die Position der Maus auf dem Div erfassen, um die neue Position des Divs anzupassen.
Ich lese die Divs PageX und PageY und setze den oberen und linken Rand entsprechend ein. Um dann die Werte zum Anpassen der Koordinaten zu erhalten, um den Cursor an der Anfangsposition im Div zu halten, verwende ich einen onDragStart-Listener und speichere das e.nativeEvent .layerX und e.nativeEvent.layerY , die nur im anfänglichen Trigger die Position der Maus innerhalb des ziehbaren Div angeben.
Beispielcode:
Ich hoffe, das hilft jemandem, der die gleichen Probleme hatte wie ich :)
quelle
das funktioniert ok!
quelle
Sie müssen die Struktur Ihrer Seite kennen, denn wenn Ihre Leinwand ein Kind eines Div ist, das wiederum ein Kind eines anderen Div ist, wird die Geschichte komplizierter. Hier ist mein Code für eine Leinwand, die sich innerhalb von 2 Ebenen von div s befindet:
});
quelle
Ursprüngliche Antwort sagte, es in einen Iframe zu setzen. Die bessere Lösung besteht darin, die Ereignisse offsetX und offsetY auf einer Zeichenfläche zu verwenden, deren Auffüllung auf 0px festgelegt ist.
quelle
Hier ist was ich habe.
quelle
Sie können
getBoudingClientRect()
dasrelative
übergeordnete Element verwenden.quelle