Files |  Tutorials |  Articles |  Links |  Home |  Team |  Forum |  Wiki |  Impressum

Aktuelle Zeit: So Jul 13, 2025 23:06

Foren-Übersicht » Programmierung » Einsteiger-Fragen
Unbeantwortete Themen | Aktive Themen



Ein neues Thema erstellen Auf das Thema antworten  [ 17 Beiträge ]  Gehe zu Seite 1, 2  Nächste
Autor Nachricht
 Betreff des Beitrags: Bitte um Hilfe bez. Frustum...
BeitragVerfasst: Do Okt 27, 2005 12:20 
Offline
DGL Member

Registriert: Do Okt 20, 2005 17:28
Beiträge: 51
hi :)

yay, mein erster beitrag *G*

ich hab eine frage... ich benutze TFrustumClass (wozu das Rad 1000mal neu erfinden, außerdem hab ich keine Ahnung
von der mathematik *g*) aber ich bräuchte eine kleine änderung.

Bild

die schwarze linie ist der berechnete frustum, also das tatsächliche blickfeld (was so nicht ganz stimmt, weil die berechnung ungenau ist). ich bräuchte als ergebnis aber so etwas wie die rote linie... also quasi ein vergrößertes frustum, das die
"kamera" und auch die fläche um das blickfeld einbezieht.

ist das verständlich? *g* kann mir da jemand helfen? ich muß mich mit anderen dingen herumschlagen, als das ich mich
jetzt eingehend mit matrizen usw beschäftigen könnte (effizientes terrain-culling zB).

dankeschön :)

EDIT: BBCode aktivieren nicht vergessen, damit man das Bild sieht lol


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Do Okt 27, 2005 19:25 
Offline
DGL Member
Benutzeravatar

Registriert: Di Nov 26, 2002 22:12
Beiträge: 259
Wohnort: Dresden
Am einfachsten ist es das Volumen mit dem du den Test durchführst zu vergrößern. Bei einer Kugel brauchst du z.B. einfach nur den Radius verändern und erhälst genau den von dir beschriebenen Effekt.

Wobei sich mir die Frage stellt wofür du das brauchst. Ich kenne die TFrustumClass-Klasse nicht, aber eigentlich sollten die Berechnungen genau sein.

_________________
Nichts auf der Welt ist so gerecht verteilt wie der Verstand. Denn jederman ist überzeugt, dass er genug davon habe.
Rene Descartes, frz. Mathematiker u. Philosoph, 1596-1650


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Do Okt 27, 2005 21:14 
Offline
Guitar Hero
Benutzeravatar

Registriert: Do Sep 25, 2003 15:56
Beiträge: 7810
Wohnort: Sachsen - ERZ / C
Programmiersprache: Java (, Pascal)
Ist das nicht die Klasse von Sascha? (DelphiGL.de)

_________________
Blog: kevin-fleischer.de und fbaingermany.com


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Fr Okt 28, 2005 14:00 
Offline
DGL Member

Registriert: Do Okt 20, 2005 17:28
Beiträge: 51
ok, meine frage war wohl doch zu ungenau.

das volumen für den test vergrößern hilft mir nichts, weil ich nur punkte-tests mach. sprich "isPointWithin". und ja, die klasse ist die öffentliche, die jeder
benutzen kann und wenn der coder sascha heißt ists auch gut *gg*

mir gehts darum, das das frustum punkte am rand des blickfelds (sprich: das gerenderte bild) nicht als punkte im frustrum erkennt ... was dazu führt, das
das frustum rechnerisch etwas vergrößert werden müßte, ich aber keinen schimmer darüber hab, wie das funktioniert.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Fr Okt 28, 2005 15:17 
Offline
DGL Member
Benutzeravatar

Registriert: So Feb 06, 2005 17:29
Beiträge: 187
Programmiersprache: C, C++
Hallo,

ich hab mich jetzt mal etwas mehr mit Frustum beschäftigt und es geschafft ein eigenes FrustumCulling zu implementieren *stolz sei* :D
Vorher habe ich immer die Klasse von Sascha benutzt, wusste aber nie genau wie das jetzt funktionier (habe ich auch jetzt noch nicht verstanden). Meine Lösung ist zwar vielleicht "Hausgemachter", oder im Endeffekt sogar irgendwie die gleiche, Hauptsache es funktioniert. Ein Nachteil ist, dass man diese Methode am besten mit glFrustum statt mit gluPerspective benutzt. Sollte aber eigentlich kein Problem sein.

So ersteinmal die Definitionen:

Code:
  1. TMatrix = array[0..15] of single;
  2.  
  3. TVertex = record
  4.   x,
  5.   y,
  6.   z: single;
  7. end;
  8.  
  9. TClippingPlane = record;
  10.   Width,
  11.   Height,
  12.   Distance: single;
  13. end;
  14.  
  15. TFrustum = object
  16.   FarClippingPlane,
  17.   NearClippingPlane: TClippingPlane;
  18.   function IsPointIn(x,y,z: single): boolean;
  19.   procedure SetFrustum(NCWidth, NCHeight, NCDistance, FCDistance);
  20.   function IsPointIn(PointX, PointY, PointZ: single): boolean;
  21. end;

Es wird zwar nicht alles gebraucht (z.B Width und Height der FarClippingPlane), aber so gibt es Möglichkeiten für Erweiterungen. Ich hoffe die Begriffe sind alle selbsterklärend \":?\" .

Kommen wir zum nächsten Teil:
Code:
  1. procedure TFrustum.SetFrustum(NCWidth: single; NCHeight: single; NCDistance: single; FCDistance: single);
  2. begin
  3.   NearClippingPlane.Width := NCWidth;
  4.   NearClippingPlane.Height := NCHeight;
  5.   NearClippingPlane.Distance := -NCDistance;
  6.   FarClippingPlane.Distance := -FCDistance;
  7. end;

Jetzt fragt mancher sich vielleicht, warum ich die Entfernungen der ClippingPlanes vom Betrachter negiere. Das ist nur dazu da, damit die Parameterübergabe zu glFrustum identisch ist. Eigentlich ist es unnötig und man könnte direkt negative Parameter übergeben, aber so gefällts mir halt \":roll:\"

Nun kommt die eigentliche Frustumüberprüfung:
Code:
  1. function TFrustum.IsPointIn(PointX, PointY, PointZ: single): boolean;
  2. var Vertex: TVertex; Matrix: TMatrix;
  3. begin
  4.   glGetFloatv(GL_MODELVIEW_MATRIX, @Matrix);
  5.  
  6.   Vertex.z := PointX*Matrix[2] + PointY*Matrix[6] + PointZ*Matrix[10] + Matrix[14];
  7.  
  8.   if (Vertex.z < 0) and (Vertex.z > FarClippingPlane.Distance) then
  9.   begin
  10.    
  11.     Vertex.x := PointX*Matrix[0] + PointY*Matrix[4] + PointZ*Matrix[8] + Matrix[12];
  12.     Vertex.y := PointX*Matrix[1] + PointY*Matrix[5] + PointZ*Matrix[9] + Matrix[13];
  13.  
  14.     if (abs(Vertex.x) < Vertex.z*NearClippingPlane.Width/NearClippingPlane.Distance) and
  15.        (abs(Vertex.y) < Vertex.z*NearClippingPlane.Height/NearClippingPlane.Distance) then result := TRUE
  16.        else result := FALSE;
  17.  
  18.   end;
  19. end;

Das muss ich vielleicht etwas genauer erklären. Also erstmal wird die Modelviewmatrix von OpenGL geholt. Zu Matrizen gibt es hier bei DGL ein sehr gutes Tutorial (unter Mathematisches wars glaube ich), außerdem muss mann darauf achten, dass eine Matrix in OpenGL wie folgt aussieht (Ich meine hier die Indexe des Arrays):
0 4 8 12
1 5 9 13
2 6 10 14
3 7 11 15

Nun errechnen wir erstmal mit der Modelviewmatrix, an welcher Z-Position sich unser Point nach den von OpenGL durchgeführten Translationen und Rotationen befindet.

Dann wird zuerst abgefragt, ob sich diese Z-Position zwischen dem Betrachter und der FarClippingPlane befindet. Wenn nicht, wird im Else-Teil result auf FALSE gesetzt und die Procedure ist zuende, der Punkt ist nicht sichtbar.

Sollte der Punkt doch dazwischen liegen, müssen wir noch prüfen, ob er nicht über, unter oder neben unserem Frustum liegt. Dazu berechnen wir erstmal noch die \"echten\" X- und Y-Positionen.

Da wir ja ein perspektivisches Frustum haben, müssen wir die Breite und Höhe davon anhand der Z-Position unseres Punktes herausfinden. Dafür wurden die Stahlensätze erfunden \":P\" . Ich weiss jetzt nicht wie ich das jetzt verständlich erklören soll, aber auf Anfrage werde ich es gerne versuchen. Ich bin übrigens davon ausgegangen, dass man ein symetrisches Frustum besitzt, also z.B glFrustum(-4,4, -3,3, 5,100) und nicht glFrustum(-9,3, -6,7, 5,100) \":!:\" .


Der Rest dürfte so dann auch klar sein. Ist die If-Abfrage erfüllt wird, dann liegt der Punkt im Frustum und wenn nicht, dann halt nicht \":lol:\" .

Im Programm muss man dann irgendwo beim initialisieren nur noch SetFrustum aufrufen.
Code:
  1.  ...
  2. glFrustum(-4, 4, -3, 3, 5, 100);
  3. Frustum.SetFrustum(8, 6, 5, 100);
  4. ...

Zeichnen dann folgendermaßen:
Code:
  1. ...
  2. if Frustum.IsPointIn(PosX, PosY, PosZ) then
  3. begin
  4.   //Zeichne etwas an Position(PosX, PosY, PosZ) ...
  5. end;
  6. ...


Das ist zwar nur ein Überprüfung für einzelne Punkte, aber auch Kugeln und Würfel sind kein Problem, siehe TFrustumClass von Sascha. Das überlasse ich dann noch an Arbeit :wink: .
FrustumCulling benutzt sowieso am besten zusammen mit einem Octree oder Ähnlichem, bringt noch einmal unheimlich viel Performance.

Ich gebe ja zu, dass dieser Post jetzt ein kleines (nur ein kleines) bisschen lang geworden ist. Hoffe ich habe nicht gelangweilt und konnte helfen. Würde mich über Feedback freuen.


PS: Der Code könnte Tippfehler enthalten, da ich ihn von nem anderen Rechner abgeschrieben hab und nicht mit Copy&Paste eingefügt hab.

_________________
Flummi: Projektseite und Projektthread


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Fr Okt 28, 2005 15:42 
Offline
DGL Member
Benutzeravatar

Registriert: So Dez 21, 2003 17:36
Beiträge: 141
Akira hat geschrieben:
mir gehts darum, das das frustum punkte am rand des blickfelds (sprich: das gerenderte bild) nicht als punkte im frustrum erkennt ... was dazu führt, das
das frustum rechnerisch etwas vergrößert werden müßte, ich aber keinen schimmer darüber hab, wie das funktioniert.

Wenn du sowieso nur Punkte testest und du den Bereich vergrößern willst, der als Frustum zählt, dann kannst du doch einfach statt der Punkte Spheres nehmen! Dann hast du einen bestimmten Radius der Kugeln, und wenn der Punkt also mit dem Radius drinnen liegt im Frustum (oder die Ebenen schneidet), wird dir ja automatisch True zurückgegeben, und hast deine Toleranzgrenze somit auch erweitert :)

PS: Hab AI's Post nicht gelesen, sorry falls du es schon so gelöst haben solltest :)


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Fr Okt 28, 2005 16:08 
Offline
DGL Member

Registriert: Do Okt 20, 2005 17:28
Beiträge: 51
hey danke A.I, ich werd mir das beizeiten genauer ansehen und mich dann melden :) muß derzeit mein Zimmer wegen Staubbelastung reinigen *ggg*
das glGetFloatV stört mich etwas, muß mir da den Speed ansehen.. ist es echt notwendig, diese matrize bei jedem punkt neu auszulesen?

lol danke Mr. Fletcher, daran hab ich gar nicht gedacht... hab den Code verglichen, ist genau das gleiche, nur das ein Radius getestet wird. werd mir das
auch zu gemüte führen (war wohl echt blind) und dann testen.

übrigens... ja, frustum culling ist super für terrain-culling, aber ich benutze weder quadtrees noch octtrees dafür, weil ich das als fürchterlich ineffizient anseh.

wie viele tests pro frame (bzw blickwinkelveränderung) habt ihr durchschnittlich im quad-/oct-tree (nodes)? und wie viele frustum-tests?


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Fr Okt 28, 2005 17:56 
Offline
Forenkatze
Benutzeravatar

Registriert: Mi Okt 22, 2003 18:30
Beiträge: 1945
Wohnort: Närnberch
Programmiersprache: Scala, Java, C*
In einem Octree wird ja auch nur mit Frustrum getestet. Höchstens noch über Occlusion Queries, wobei ich mich mit denen net auskenn' ;) Aber wie willst du eine Landschaft mit Frustrum Culling schneller darstellen ohne Octree / Quad-? Irgendwie musst du es ja unterteilen, sonst bringt's dir gar nix ;) Und Octrees sind schon verdammt schnell. Ich bekomm' damit einen Geschwindigkeitszuwachs von ca. 800%. Und das ist nicht wenig ;)

_________________
"Für kein Tier wird so viel gearbeitet wie für die Katz'."


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Fr Okt 28, 2005 18:40 
Offline
DGL Member

Registriert: Do Okt 20, 2005 17:28
Beiträge: 51
hi ... eine kurze antwort *g* bin noch nicht dazu gekommen, mir den code anzusehen... zimmer und so *g*

das kommt drauf an, wie man das sieht ... ich muss die landschaft nicht unterteilen, wenn ich sowieso weiß, wo ich bin. verständlich? *g*
ist eh ganz logisch... wenns funktioniert, werd ichs auf jeden fall posten... was mich interessiert (damit ich einen vergleich hab) ist, wie viele
tests in euren routinen so durchgeführt werden. ich plane einen test pro "schritt" (=drehung links/rechts, schritt vor/zurück). aufsteigen (y-koordinate)
müßte genauso funktionieren, falls jemand denkt ich beschränk mich hier auf ne flache landschaft *g* aber das muß erst getestet werden.

kann sein, das ich kryptisch rede, aber ich stell mir alles immer irgendwie vor und der code ploppt dann heraus *g* und wenns nicht funktioniert ists
mir auch egal... ich hab immer versucht, mir eigenes zu überlegen, bevor ich das nutze, was alle nutzen *g* darum hab ich mich früher auch mit
voxel-engines beschäftigt lol


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Fr Okt 28, 2005 18:53 
Offline
Forenkatze
Benutzeravatar

Registriert: Mi Okt 22, 2003 18:30
Beiträge: 1945
Wohnort: Närnberch
Programmiersprache: Scala, Java, C*
Voxel sind ja auch cool ;)

Aber nur weil du weißt, wo du bist, weißt du ja noch nicht, was denn gerendert werden muss ^^

_________________
"Für kein Tier wird so viel gearbeitet wie für die Katz'."


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Fr Okt 28, 2005 19:59 
Offline
DGL Member

Registriert: Do Okt 20, 2005 17:28
Beiträge: 51
ja, voxel sind voll cool *g* ich dachte mir aber, ich versuch mal was anderes... ist ja auch schon "ewig" her *g*

hm ... du siehst das falsch. wenn ich weiß wo ich bin, kann ich auch "sehen" was gerendert werden muß *ggggg* wir werden ja sehen, noch ist es nicht
fertig :)

an die arbeit ^^


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Fr Okt 28, 2005 20:58 
Offline
DGL Member

Registriert: Do Okt 20, 2005 17:28
Beiträge: 51
also, der code von fletcher funktioniert nicht... und ja, die fehler hab ich bemerkt und ausgebessert.

das mit dem sphärentest geht auch nicht, weil ich da 1. nicht genau weiß welche punkte genau inkludiert sind und ich, wenn ich einen hack einbaun würd
damit ich es weiß, letzten endes zu viele punkte hätte....

zurück zum 1. beitrag... *g*

muß schaun, das mir ein hack einfällt, wenn das so nicht funktioniert. oder vielleicht doch mal matrizen ansehen *raunz* *gg*

ist es so kompliziert, die berechnung zu erweitern? *hmpf*


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Sa Okt 29, 2005 01:33 
Offline
DGL Member
Benutzeravatar

Registriert: So Feb 06, 2005 17:29
Beiträge: 187
Programmiersprache: C, C++
Hi Akira, ich vermute dann also mal, dass du ne Landschaft hast. Ich hab zwar keine Ahnung, wie du das dann ohne Unterteilung (Octtree, Quadtree o.ä.), schneller machen willst, als mit. Lass mich mal überraschen 8) .

Da ich in meinem Testprogramm jeden Punkt mit gltranslatef gesetzt habe, muss ich auch bei jedem Punkt mit glGetFloatv die ModelviewMatrix neu holen. Der Aufruf von glGetFloatv ist auch nicht wirklich teuer.
Allerdings hast du recht, wenn man ein großes Landschaftsmesh hat, bei dem die Vertexpositionen direkt angegeben werden, dann reicht es die Matrix einmal, nachdem die Betrachterposition und Drehung festgelegt wurden, zu holen.

Das gleiche gilt wenn man Würfel auf Sichtbarkeit testet (einfach schauen, ob einer der 8 Eckpunkte im Frustum liegt), die Eckpunkte sollen dann ja alle die gleiche Position und Drehung (in Relation zueinander) haben. Man kann sie also auch alle nacheinander durch die gleiche Matrix schicken.

Die Lösung mit dem Frustum einfach etwas vergrößern finde ich irgendwie "unsauber" :roll: . Andererseits wundert es mich auch, denn vorher habe ich auch immer TFrustumClass benutzt und keine Probleme gehabt.
Allerdings ist mir (nachdem ich es nochmal getestet hatte) aufgefallen, dass meine Methode viel schneller läuft. Kann es sein das ich Saschas Klasse falsch benutze? So FrustumCulling allein bringt da zwar ein bisschen, aber nicht wirklich viel Geschwindigkeit.
In nem anderen Programm von mir, zusammen mit nem Octtree rockt es aber.

Zitat:
also, der code von fletcher funktioniert nicht... und ja, die fehler hab ich bemerkt und ausgebessert.
Meinst du meinen Code, oder welchen von Mr.Fletcher?

Übrigens, was meint eigentlich dein Nick? Ich hab letzten Monat einen japanischen Austauschschüler kennengelernt, der hieß genauso.

_________________
Flummi: Projektseite und Projektthread


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Sa Okt 29, 2005 17:04 
Offline
DGL Member

Registriert: Do Okt 20, 2005 17:28
Beiträge: 51
ähm... ich meinte deinen code, nicht den von fletcher. hab mich vertan *g*

ich wollte bescheid sagen, das ich einen anderen weg gefunden habe, mir auszurechnen, was ich brauche. mir wäre zwar die "unsaubere" (hä? *g*) lösung
mittels frustum lieber gewesen (weil einfacher), aber wenn das nicht einfach so klappen will, dann nicht. wenn dein code schneller ist, ists gut. das heißt ja
nicht, das du was falsch machst ^^

danke nochmal :) wenn ich hab, was ich wollt, werd ichs posten. und wenns nicht klappt, auch *g*


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Sa Okt 29, 2005 19:05 
Offline
Guitar Hero
Benutzeravatar

Registriert: Do Sep 25, 2003 15:56
Beiträge: 7810
Wohnort: Sachsen - ERZ / C
Programmiersprache: Java (, Pascal)
Woher willst du wissen was du siehst, wenn du keine Struktur gebaut hast die dir sagt was du siehst. Octrees sind gar nicht soooo aufwendig (wenn man nicht solchen quark codet wie ich damals :oops: ;) )

_________________
Blog: kevin-fleischer.de und fbaingermany.com


Nach oben
 Profil  
Mit Zitat antworten  
Beiträge der letzten Zeit anzeigen:  Sortiere nach  
Ein neues Thema erstellen Auf das Thema antworten  [ 17 Beiträge ]  Gehe zu Seite 1, 2  Nächste
Foren-Übersicht » Programmierung » Einsteiger-Fragen


Wer ist online?

Mitglieder in diesem Forum: 0 Mitglieder und 5 Gäste


Du darfst keine neuen Themen in diesem Forum erstellen.
Du darfst keine Antworten zu Themen in diesem Forum erstellen.
Du darfst deine Beiträge in diesem Forum nicht ändern.
Du darfst deine Beiträge in diesem Forum nicht löschen.
Du darfst keine Dateianhänge in diesem Forum erstellen.

Suche nach:
Gehe zu:  
  Powered by phpBB® Forum Software © phpBB Group
Deutsche Übersetzung durch phpBB.de
[ Time : 0.011s | 15 Queries | GZIP : On ]