Sechseckige Gitter, wie finden Sie die Sechskant-ein Punkt ist?
Habe ich eine Karte aus Zeilen und Spalten von Sechsecken
Dies ist nicht ein Bild von der hex-Karte, die ich verwende, verwendet aber die gleiche Größe und Form Sechsecke
Ich muss in der Lage sein zu sagen, die man mit der Maus ist vorbei, wenn der Benutzer klickt,
Jedes Sechseck wird repräsentiert durch eine Instanz einer "Kachel" - Klasse, allerdings ist dieser nicht für jeden Standort spezifische Daten, oder auch ein polygon aus, also im Grunde der einzige Weg, zu sagen, wo ein bestimmtes Sechseck ist, ist es zu wissen, die position in der 2D-array.
Habe ich verwendet einem quadratischen raster vor, und es war relativ einfach, herauszufinden, welcher Platz wurde ausgewählt, da die Pixel sind auch quadratische,
//example where each square is 10 by 10 pixels:
private void getClickedSquare(MouseEvent me)
{
int mouseX = me.getX();//e.g. 25
int mouseY = me.getY();//e.g. 70
int squareX= (int) (mouseX /10);//in this case 2
int squareY= (int) (mouseY /10);//in this case 7
//then to access the tile I would do
map.squares[squareX][squareY].whatever();
}
Aber ich bin mir auch nicht sicher, wo Sie anfangen mit Sechsecken, hat jemand irgendwelche Erfahrungen?
Kann ich nicht verwenden, Polygone (Java), als wenn ich auf die Karte um auf dem Bildschirm, und die Erhöhung der Größe werde ich Probleme mit der Aktualisierung Unmengen von Polygonen jedes Bild. Obwohl dann könnte ich nur überprüfen, ob ein Punkt in der map tile Polygone!
Im moment die Sechsecke dargestellt sind nur BufferedImages.
Wenn Sie wissen möchten, mehr Informationen bitte Fragen,
Vielen Dank für deine Zeit 😀
InformationsquelleAutor der Frage Troyseph | 2011-10-09
Du musst angemeldet sein, um einen Kommentar abzugeben.
(AKTUALISIERT: Refactoring code zu machen, verständlicher und effizienter)
(AKTUALISIERT: Reduzierte Antwort Länge, behoben Fehler im code, bessere Qualität von Bildern)
Dieses Bild zeigt die linke Obere Ecke des hexagonalen Gitters und überlagert ist ein blaues Quadrat-raster. Es ist leicht zu finden, welcher die Quadrate ein Punkt drin ist, und das würde für eine grobe Näherung an die hexagon zu. Die weißen Teile der Sechsecke zeigen, wo die quadratische und hexagonale Gitter teilen den gleichen Koordinaten und die grauen Teile der Sechsecke zeigen, wo Sie es nicht tun.
Die Lösung ist nun so einfach wie der Suche nach dem Feld ein Punkt, und klicken Sie dann überprüfen, um zu sehen, wenn der Punkt in einem der beiden Dreiecke, und die Korrektur der Antworten, wenn nötig.
In diesem Punkt haben wir uns die Zeile und Spalte der box unser Punkt ist, nächste müssen wir testen unser Punkt gegen die beiden oberen Kanten des Sechsecks zu sehen, ob unser Punkt liegt in einem der Sechsecke oben:
Mit relativen Koordinaten, macht den nächsten Schritt einfacher.
Wie im Bild oben, wenn das y unsere > mx + c wir wissen, dass unser Punkt liegt oberhalb der Linie, und in unserem Fall, das Sechseck, oben und auf der linken Seite der aktuellen Zeile und Spalte. Beachten Sie, dass das Koordinatensystem in java hat y beginnend bei 0 in der linken oberen Bildschirmrand und nicht unten Links, wie üblich in der Mathematik, daher der negative gradient verwendet, für die linke Seite und der positiven Steigung für das Recht.
Einer kurzen Erläuterung der verwendeten Variablen im obigen Beispiel:
m ist die Steigung, also m = c /Halbbreite
InformationsquelleAutor der Antwort Troyseph
EDIT: diese Frage ist schwieriger als ich dachte erst, ich werde umschreiben, meine Antwort mit einigen arbeiten, aber ich bin mir nicht sicher, ob die Lösung Pfad ist eine Verbesserung auf die anderen Antworten.
Die Frage wäre anders formuliert: gegeben x,y finden, das Sechseck, dessen Zentrum am nächsten ist, x,y
d.h. Minimierung dist_squared( Hex[n].center, (x,y) ) über n (squared bedeutet, dass Sie nicht brauchen, um über Wurzeln, das spart etwas CPU)
Aber zunächst sollten wir eingrenzen der Anzahl von Sechsecken zu überprüfen, - können wir eingrenzen, zu einem maximum von 5 durch die folgende Methode:
So, der erste Schritt ist, äußern Sie Ihre Punkt (x,y) im UV-Raum
d.h. (x,y) = lambdaU + muV, so dass = (lambda, mu) im UV-Raum
Ist das nur eine 2D-matrix-Transformation (http://playtechs.blogspot.co.uk/2007/04/hex-grids.html hilfreich sein können, wenn Sie nicht verstehen, lineare Transformationen).
Nun einen Punkt (lambda, mu), wenn wir Runde beide auf die nächste ganze Zahl, dann haben wir dies:
Überall innerhalb der Grünen Quadrat-Karten zurück (2,1)
Also die meisten Punkte in das Grüne Quadrat wird richtig sein, D. H. Sie sind in Sechseck (2,1).
Aber einige Punkte sollte die Rückkehr der hexagon # (2,2), ich.e:
Ebenso sollte die Rückkehr der hexagon # (3,1). Und dann auf der gegenüberliegenden Ecke, die grünen Parallelogramm, es werden 2 weitere Regionen.
Also, um zusammenzufassen, wenn int(lambda,mu) = (p,q), dann sind wir wohl im inneren Sechseck (p,q), aber wir könnten auch drinnen sein Sechsecke (p+1,q), (p,q+1), (p-1,q) oder (p,q-1)
Mehrere Möglichkeiten, um festzustellen, welche von diesen ist der Fall. Das einfachste wäre, zu konvertieren, die Zentren aller dieser 5 Sechsecke zurück in das ursprüngliche Koordinatensystem, und finden, die am nächsten zu unserem Ausgangspunkt.
Aber es stellt sich heraus, Sie kann schmal, dass bis auf ~50% der Zeit tun, keine Distanz prüft, ~25% der Zeit damit, eine Entfernung überprüfen, und die restlichen ~25% der Zeit mit 2 Distanz-Kontrollen (ich vermute, dass die zahlen durch den Blick auf die Bereiche, die jedem check funktioniert):
Und letzten test kann aufgeräumt werden:
Nun haben wir verengt Sie sich auf eine andere mögliche Sechskant, wir müssen Sie nur finden, die näher ist:
Einen Dist2_hexSpace(A,B) - Funktion würde ordentlich die Dinge noch.
InformationsquelleAutor der Antwort P i
Dies ist ein Nachtrag zu SebastianTroy Antwort. Ich würde es nicht als Kommentar, sondern ich nicht genug Ruf noch.
Wenn Sie möchten, implementieren Sie eine axiale Koordinatensystem, wie hier beschrieben:
http://www.redblobgames.com/grids/hexagons/
Können Sie machen eine leichte änderung des Codes.
Statt
verwenden Sie diese
Dadurch wird die Koordinate (0, 2) auf der gleichen diagonalen Spalte als (0, 0) und (0, 1) statt direkt unten (0, 0).
InformationsquelleAutor der Antwort NeoShaman
Begann ich durch das betrachten von @pi 's Antwort https://stackoverflow.com/a/23370350/5776618 und dachte, es wäre interessant, zu versuchen, etwas ähnliches im cube-Koordinaten und UVW-Raum (anstelle der 2D -, axial -, UV-Raum).
Den folgenden Gleichungen Karte (x,y) => (u,v,w)
Dann ist es so einfach wie Rundung u, v und w auf die nächste Ganzzahl, und die Konvertierung zurück zu x,y. Es gibt jedoch einen großen Haken...
In der Antwort oben, es ist anzumerken, dass die Rundung im UV-Raum haben ein paar Bereiche, die Karte falsch:
Dies geschieht immer noch bei der Verwendung cube Koordinaten:
Einem Bereich in der orange Dreiecke ist >0,5 Einheiten von der Mitte des Sechsecks und wenn abgerundet wird die Runde von der Mitte WEG. Dies ist oben gezeigt wird, wie alles, was in dem roten Dreieck (auf der linken Seite des u=1.5-Linie) wird u nicht korrekt gerundet u=1 statt u=2.
Einige der wichtigsten Beobachtungen hier, aber...
1. Die orange/rot problem Bereiche sind nicht-überlappende
2. Im cube-Koordinaten, gültige hex-Zentren haben u + v + w = 0
In dem code unten, u, v und w, sind alle abgerundet, von Anfang an als Rundung nur ein Problem, wenn die gerundeten Koordinaten Summe nicht null.
Wenn diese Summe nicht null, da die Problemzonen nicht überlappen, gibt es nur die 1-Koordinate, dass ist nicht richtig gerundet. Diese Koordinate wird auch die Koordinate, die abgerundet wurde die meisten.
Nachdem das problem Koordinate zu finden ist, sondern gerundet in die andere Richtung. Die endgültige (x,y) berechnet dann gerundet/korrigiert (u,v,w).
InformationsquelleAutor der Antwort Steve Ladavich
Hatte, habe ich einen anderen Blick auf http://playtechs.blogspot.co.uk/2007/04/hex-grids.html und es ist sehr sauber mathematisch.
Jedoch Sebastian Ansatz scheint auf den Punkt, und die Aufgabe in erstaunlich wenigen Zeilen code.
Wenn Sie Lesen Sie die Kommentare Abschnitt können Sie feststellen, dass jemand geschrieben hat, eine Python-Implementierung in http://gist.github.com/583180
Werde ich repaste, dass hier für die Nachwelt:
InformationsquelleAutor der Antwort P i
Ich weiß nicht, ob es hilft niemandem, aber ich habe eine viel einfachere Lösung. Wenn ich meine Hexagon im-nur um einen mittleren Punkt und durch die Suche nach dem nächsten mittleren Punkt mit der Maus coordonate, die ich finden kann, die man im auf !
InformationsquelleAutor der Antwort user5021355