Ich erstelle eine zufällig generierte Umgebung für ein Spiel, das ich entwickle. Ich benutze OpenGL
und codiere in Java
.
Ich versuche, zufällig Bäume in meiner Welt zu platzieren (um einen Wald zu erstellen), aber ich möchte nicht, dass sich die Modelle überlappen (was passiert, wenn zwei Bäume zu nahe beieinander stehen). Hier ist ein Bild von dem, wovon ich spreche:
Ich kann bei Bedarf mehr Code bereitstellen, aber hier sind die wesentlichen Ausschnitte. Ich lagere meine Objekte in einem ArrayList
mit List<Entity> entities = new ArrayList<Entity>();
. Ich füge dieser Liste dann Folgendes hinzu:
Random random = new Random();
for (int i = 0; i < 500; i++) {
entities.add(new Entity(tree, new Vector3f(random.nextFloat() * 800 - 400,
0, random.nextFloat() * -600), 0, random.nextFloat() * 360, 0, 3, 3, 3);
}
Dabei Entity
folgt jeder der folgenden Syntax:
new Entity(modelName, positionVector(x, y, z), rotX, rotY, rotZ, scaleX, scaleY, scaleZ);
rotX
ist die Drehung entlang der x-Achse und scaleX
ist die Skala in x-Richtung usw.
Sie können sehen , dass ich diese Bäume zufällig bin Platzierung random.nextFloat()
für die x
und z
Positionen, und begrenzen den Bereich , so dass die Bäume in der gewünschten Position angezeigt werden. Ich möchte diese Positionen jedoch irgendwie steuern, sodass beim Versuch, einen Baum zu nahe an einem zuvor platzierten Baum zu platzieren, eine neue zufällige Position neu berechnet wird. Ich dachte, dass jeder Baum Entity
ein anderes Feld haben könnte, wie zum Beispiel treeTrunkGirth
, und wenn ein Baum in der Entfernung zwischen dem Standort eines anderen Baums und treeTrunkGirth
seinem Platz platziert wird, berechnet er eine neue Position neu. Gibt es eine Möglichkeit, dies zu erreichen?
Gerne füge ich bei Bedarf weitere Codefragmente und Details hinzu.
treeTrunkGirth
anstelle einer Konstante auch den Mindestabstand zum Platzieren eines Baums, wenn dieser variieren muss.Antworten:
Mit einer Poisson-Disk-Sampling- Verteilung können Sie zufällige Punkte in einem Mindestabstand auswählen. Ihre Situation ähnelt dieser Frage , aber da Ihre Bäume keine idealisierten Punkte sind, müssen Sie die Entfernungsprüfung wie folgt ändern: Die Entfernung zwischen einem potenziellen neuen Baum und einem vorhandenen Baum muss kleiner sein als die Summe ihrer Radien .
Der Bridson-Algorithmus kann das Problem in O (n) effizient lösen, aber es kann etwas umständlich sein, es für variable Entfernungen zu optimieren. Wenn Ihre Parameter niedrig sind und / oder Sie Ihr Gelände vorberechnen, kann Ihnen eine Brute-Force-Lösung genauso gut helfen. Hier ist ein Beispielcode, der das Problem durch Brute erzwingt, indem jede potenzielle neue Baumplatzierung mit allen zuvor platzierten Bäumen verglichen wird:
Mit folgenden Parametern:
Ich konnte in weniger als einer Sekunde zwischen 400 und 450 Bäume zufällig platzieren und rendern. Hier ist ein Beispiel:
quelle
tree.r + other tree.r
, 2, anstelle von math.sqrt zu verwenden, sqrt ist normalerweise langsamer als powMath.pow(x,2)
ist nicht unbedingt besser / anders als die Verwendung vonx*x
wie hier diskutiert .