ich weiß ich hab mir da ein wirklich schwieriges Thema ausgesucht. Ich möchte/muss eine Art 3D Visualisierung für Scheinwerfer programmieren. Es hapert momentan nur an dem Licht selbst. Es handelt sich hauptsächlich um Spots, welche beweglich sind. Dazu muss es möglich sein ein "GOBO" - (Projektion) für den Lichtstrahl zu definieren. D.h. ich geb ein PNG oder ICO vor und das Licht soll dann durch die transparenten stellen "durchscheinen". Damit das auch echt aussieht reicht ein einfacher Kegel für den für das Licht nicht aus, ein Modell muss her. Ich habe einen Ansatz von einem DX Programmierer bekommen:
Zitat:
- Das ganze läuft wie eine Schattenberechnung nur eben anders herum. Ich lege ein Gobo Mesh direkt vor die Linse der Lampe und Projeziere einen Schatten (Stencil) in die Umgebung. Dieser ist dann allerdings nicht dunkel sondern in der Farbe des Lichtes. Bei einer normalen Schattenberechnung werden die Projezierenden Polygone die vom Ursprung bis zum auftreffenden Ziel gehen normalerweise unsichtbar gemacht. Ich lasse diese dann halbtransparent sichtbar. So hat man genau einen passenden Beam zum passenden Gobo. Und der zweite vorteil ist, Das das Gobo auch auf komplizierte Körper richtig Projeziert wird.
So nochmal zusammenfassend brauche ich: - Lichtstrahl endsprechend des Gobos - Der "Abstrahlwinkel" muss veränderbar sein - Eine zusätzliche Schattenberechnung soll auch noch kommen - und zu guter letzt auch noch eine möglichkeit die ganze Sache Soft- oder Hart zustellen d.h. fokussieren - mehrere Lichter (>50) müssen ohne Probleme gerendert werden können
Soo. Eine Morts aufgabe, jedoch übersteigt diese noch meine Möglichkeiten mit OGL. Nun kann mir hier vielleicht jemand bissl auf die Sprünge helfen? Auf manche Sachen kann ich erstmal verzichten.. wie z.B. das Fokussieren..
Registriert: Mo Sep 23, 2002 19:27 Beiträge: 5812
Programmiersprache: C++
Also prinzipiell ist dass was du machen willst kein Problem. Allerdings sind 50 (oder mehr) Lichter hier das Problem, da wirst du mit einem normalen Forward-Renderer keine brauchbare Performance bekommen. Wenn du also wirklich mehr als 50 Lichtquellen mit Projektor und Schattenberechnung willst, dann musst du dir einen Deffered-Renderer (oder gar inferred) (such danach mal in google, gibt einige gute PDFs dazu, und in unserem Wiki steht auch was, Stichwort G-Buffer) schreiben, der ist für viele gleichzeitig sichtbare Lichtquelle viel besser geeignet. Der Stencil fällt dann übrigens auch flach, denn Stencilschatten werden auf der CPU berechnet, und bei 50 Lichtquellen wird das happig. Ausserdem benötigen Schatten mittels Stencil extrem viel Füllrate, was bei so vielen Lichtern auch eine High-End Karte in die Knie zwingen dürfte. Bei so vielen Lichtquellen muss also eine andere Schattentechnik her, z.b. Shadowmaps (die es ja in vielen Formen gibt).
Wenn du allerdings nur Projektoren brauchst, dann reicht Texturenprojekten mehr als aus, das geht z.b. ganz einfach über Shader oder zur Not auch via glTexnEnv, also der eingebauten Funktion um Texturen auf Objekte zu projezieren.
Nun wenn wir den Schattenwurf erstmal ausser Acht lassen würden, dann gibt es ja im eigentlichen Sinne kein wirkliches "Licht" sondern nur ein Modell entsprechend des vorgegebenen Gobos, welches einfach entsprechend "extrudiert" wird oder verstehe ich das falsch? Hier mal ein Bild wie es mal aussehen soll:
Registriert: Do Sep 02, 2004 19:42 Beiträge: 4158
Programmiersprache: FreePascal, C++
Das Problem wird sein, so hübsch bekommst du es auf anhieb nicht hin. Du hast da ja Volumenlicht (so nennt sich das ganze), was mit einem Rasterizer wie OpenGL nur schwer zu implementieren ist (und dann meistens auch nicht performant). Du wirst zwar die Umrisse des Lichtstrahls sehen können, aber er wird nicht wie im Bild mit zunehmender Dicke des Lichtes stärker bzw mit abnehmender Dicke schwächer zu sehen sein.
greetings
_________________ If you find any deadlinks, please send me a notification – Wenn du tote Links findest, sende mir eine Benachrichtigung. current projects: ManiacLab; aioxmpp zombofant network • my photostream „Writing code is like writing poetry“ - source unknown
„Give a man a fish, and you feed him for a day. Teach a man to fish and you feed him for a lifetime. “ ~ A Chinese Proverb
Das Problem wird sein, so hübsch bekommst du es auf anhieb nicht hin. Du hast da ja Volumenlicht (so nennt sich das ganze), was mit einem Rasterizer wie OpenGL nur schwer zu implementieren ist (und dann meistens auch nicht performant). Du wirst zwar die Umrisse des Lichtstrahls sehen können, aber er wird nicht wie im Bild mit zunehmender Dicke des Lichtes stärker bzw mit abnehmender Dicke schwächer zu sehen sein.
greetings
Mhh dachte immer das man mit OpenGL das gleiche hin bekommt wie mit DX? So ganz wie im Bild muss es ja nicht sein. Nur halt so gut wie möglich..
Registriert: Mo Sep 23, 2002 19:27 Beiträge: 5812
Programmiersprache: C++
Sowas wie auf dem Bild da oben zu machen ist rein technisch kein Problem, weder in OpenGL, noch in DirectX. Problem ist allerdings dass ganze bei 50+ Lichtquellen performant darzustellen. Volumetrische Lichter gibts schon lange, und auf der Seite von humus gibts dazu auch ne Demo. Allerdings ist bei solchen Lichtern die Füllrate der limitierende Faktor, also 50 solcher Lichtquellen zerren da stark an der Performance.
Ansonsten würde ich obige Szene nicht so implementieren wie die Person die du zitiert hast, denn dafür benötigt man nicht zwingend den Stencil (auch hier Thema Füllrate). Die Projektion auf den Boden kann man einfacher und performanter mit einer projezierten Textur machen (Szene aus Sicht der Lichtquelle rendern), und den Lichtschaft könnte man mit Billboards simulieren. Klar wäre es mittels Stencil einfacher zu implementieren, aber dann müsste bei jeder Lichtänderung (z.b. Position oder Ziel) auf der CPU die Silhoutte für das Stencilvolumen neu berechnet werden, was aufwendig ist. Wenn du das aber mal probieren willst, schau in unser Wiki, da steht drin wie man volumetrische Schatten macht und auch deren Silhoutten und Volumen berechnet (wichtig : Meshes müssen dafür geschlossen sein), und für die Lichtquellen musst du dann nur die Stencilfunktion und das Rendering leicht anpassen.
Nun wie gesagt 50 Lichter sind schon ein extremfall, aber möglich. Ich frage da mal ganz frech, .. hätte jemand Lust mir dazu mal ein Beispiel zu schreiben? Habe das Gefühl, bei euch dauert das kleine 20min
also so spontan wüsste ich nicht wie man das linkte volume mit Stencil hinbekommen soll.. also es würde damit schwer werden dieses zum rand hin schwächer werden zu lassen.
Ich denke das gezeigte Bild ist "gefaked".. also kein Stencil, sondern eine Projezierter Textur und der Lichtkegel selbst ist einfach ein Billboard. Sieht man auch am linken lichtkegel - denn eigentlich müßte der helle kreis am boden auch zum rand hin schwächer werden. Wenn er genauso berechnet wird wie der lichtkegel selbst, würde er das vermutlich tun
Also, einfach ein bisschen tricksen... Textur auf den boden Projezieren und dann einfach z.B. die mittlere Zeile der Textur als 1D-Billboard Textur benutzen.
Damit das realistisch aussieht könnte man den Lichtkegel beispielsweise durch Slices rendern. Also ganz viele Quads mit der Gobo-Textur übereinander.
Eine andere Möglichkeit wäre das Volumen zu konstruieren. Ich muss da übrigens Sascha widersprechen, das macht man heute nicht mehr auf der CPU, das geht auch im Vertexshader wenn man die Daten vorher entsprechend vorbereitet. Wie auch immer, der Stencilbuffer hilft hier nicht weiter, aber eine Technik die sich glaube ich "Surface Scattering" nennt. Die Grundidee ist, dass man für jeden Backface-Pixel die Entfernung zur Kamera aufaddiert und für jeden Frontface-Pixel subtrahiert. Das Ergebnis ist genau die dicke des Objektes bzw. in diesem Fall die Stärke des Lichtkegels. Funktioniert für beliebig komplexe Gobo-Bilder.
Dann stellt sich natürlich die Frage wie man den subtrahieren soll, das geht nämlich nicht über normales Blending. Der Trick ist mit additivem Blending in eine Rot-Grün-Floattextur zu rendern. Rot für Backfaces, Grün für Frontfaces. Später, wenn man dann den Lichtkegel rendert, subtrahiert man einfach Rot und Grün voneinander. Natürlich müssen die Entfernungen so skaliert werden, dass jede Summe immer zwischen 0 und 1 liegt, da die Grafikkarte bekanntlich clampt.
Bei beiden Ansätzen bezweifele ich, dass das mit 50 Lichtquellen flüssig läuft.
für mich sieht das so aus als wenn hier einfach mehrere Kegel gerendert werden, und je weiter nach aussen, je transparenter werden die dargestellt. Wie die das mit den Gobos machen weiss ich jedoch nicht. Ich habs bei dem Programm grad mal probiert 50 Lampen zu setzen. Läuft hier flüssig.. auch mit Gobos und Schatten..
Registriert: Mo Sep 23, 2002 19:27 Beiträge: 5812
Programmiersprache: C++
Frag doch mal nach wie sie es gemacht haben. Evtl. bauen die ja Kegel basierend auf der Form der Gobos und rendern die wirklich ineinander. Wenn man dass mit der korrekten Renderreihenfolge macht (bei Transparenz sehr wichtig), dann könnte man damit den gewollten Effekt erreichen. Und Schatten via Shadowmaps sind ja auch recht flott und man kann dort viel optimieren (auf dem Screenshot sieht man z.b. nicht ob Schattenwerfer selbst auch Schatten empfangen, also Selbstschattierung der Figur). Machbar ist sowas, auch mit 50 Lichtern, nur um es performant zu gestalten wird man ein wenig tricksen müssen.
nun mein Problem ist aktuell nur das ich nicht weiss wie ich einen mit glCylinder gezeichneten Kegel in verschiedenen Werten Transparent machen kann.. mit glBlendFunc(GL_ONE, GL_ONE) hab ich ihn zwar transparent bekommen, jedoch nur 50%...
Das mit dem Textur projezieren wird auch noch kompliziert..
Registriert: Mo Sep 23, 2002 19:27 Beiträge: 5812
Programmiersprache: C++
Nimm Abstand von gluCylinder und schreib dir deine eigene Routine. Auf die Vertexdaten von gluCylinder hast du ja keinen Einfluss und kannst dementsprechend nur global (OpenGL ist ja ne Statemachine) die Transparenz für diesen Kegel setzen, in einer eigenen Funktion (die recht einfach zu schreiben ist) kannst du genau sagen welcher Eckpunkt des Kegels wie stark sichtbar sein soll, etc.
Aber eins ist mir am Screenshot gerade aufgefallen : Man schaue mal auf den Kreis den z.B. der grüne Spot auf den Boden wirft. Der Lichtkegel ist nach Aussen hin schwächer, müsste da nicht auch der auf dem Boden sichtbare Kreis nach Aussen hin dunkler werden? Genauso beim gelben Symbol an der Wand, das komplett gleich beleuchtet ist, es aber rein physikalisch nicht sein sollte? Wenn ich richtig liege wird hier wirklich mit einer einfachen Projektion getrickst, und die Lichtkegel sind dann evtl. auch nur 2D und via Billboarding gemacht, und zwar evtl. mehrerer Billboards übereinander mit unterschiedlicher Transparenz.
Mitglieder in diesem Forum: 0 Mitglieder und 0 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.