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

Aktuelle Zeit: Mi Jul 16, 2025 21:37

Foren-Übersicht » Programmierung » OpenGL
Unbeantwortete Themen | Aktive Themen



Ein neues Thema erstellen Auf das Thema antworten  [ 8 Beiträge ] 
Autor Nachricht
BeitragVerfasst: Do Dez 01, 2011 16:28 
Offline
DGL Member

Registriert: Do Apr 22, 2010 17:17
Beiträge: 543
Moinsen,

bin gerade wieder über meinem DFS Shader.. Aktuell rendere ich die Szene mittels MRT > Normal, color, Depth in 8 Bit Texturen und rechne im Shader dann aus der Tiefentextur und Projektionsmatrix die 3D Position zurück.. So nun kommt es bei mir jedoch auf eine große anzahl von Lampen an.. Mehr als 1 Lampe pro Durchgang kann ich nicht rendern da ich sonst zuviele Texturen reinladen müsste (Projektionstexturen, etc)..

Nun frage ich mich was es bringt wenn ich gleich in 16Bit Texturen rendere und direkt die 3D Position schreibe.. Lediglich der Speicherkonsum des GBuffers dürfte um das Doppelte ansteigen oder?

So berechne ich aktuell die 3D Position:
Code:
  1.  
  2.         vec2 texcoord = vec2(gl_TexCoord[0]);  
  3.         vec4 vColor = texture2D(colorMap, texcoord);       
  4.         float fDepth = texture2D(depthMap, texcoord).x;            
  5.         vec4 vNormal = texture2D(normalMap, texcoord);             
  6.         vNormal.xyz = vNormal.xyz * 2.0 - 1.0; 
  7.         vec4 vVertex;      
  8.         vVertex.xy = gl_TexCoord[0].st  * 2.0 - 1.0 ;                          
  9.         vVertex.z = fDepth * 2.0 - 1.0;            
  10.         vVertex.w = 1.0;
  11.         vVertex =  proM * vVertex;         
  12.         vVertex /= vVertex.w;  
  13.         vec4 vEye;                 
  14.         vEye.xyz   = vVertex.xyz  * 1.00001;
  15.      
  16.         vec4 posWorld = InvViewMat * vec4(vEye.xyz, 1.0);  
  17.  


was meint ihr?


Nach oben
 Profil  
Mit Zitat antworten  
BeitragVerfasst: Do Dez 01, 2011 20:04 
Offline
DGL Member
Benutzeravatar

Registriert: Do Dez 29, 2005 12:28
Beiträge: 2249
Wohnort: Düsseldorf
Programmiersprache: C++, C#, Java
Ich denke es ist sinnvoller die Tiefe zusammen mit der Normale im Alphakanal zu speichern. Dann sparst du einen Texturzugriff, ein MRT und eine Textur.

_________________
Yeah! :mrgreen:


Nach oben
 Profil  
Mit Zitat antworten  
BeitragVerfasst: Fr Dez 02, 2011 07:02 
Offline
DGL Member

Registriert: Do Apr 22, 2010 17:17
Beiträge: 543
mhh nun problem is das Specular in alpha von der Normaltextur schon speichere :(


Nach oben
 Profil  
Mit Zitat antworten  
BeitragVerfasst: Fr Dez 02, 2011 14:11 
Offline
DGL Member
Benutzeravatar

Registriert: Do Sep 02, 2004 19:42
Beiträge: 4158
Programmiersprache: FreePascal, C++
Der Farbalphakanal hilft dir beim Deferred Shading eh nicht mehr wirklich (zumindest wenn ich das Konzept richtig durchschaut habe), warum also nicht das Specular da reinpacken?

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 networkmy 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


Nach oben
 Profil  
Mit Zitat antworten  
BeitragVerfasst: Fr Dez 02, 2011 20:58 
Offline
DGL Member

Registriert: Fr Okt 03, 2008 13:32
Beiträge: 367
Ich mach das bei mir so das ich erst das Licht zusammenaddiere was auf eine Fläche fällt und erst zuletzt diese Summe mit der Oberflächenfarbe multipliziere. Dadurch brauch ich für den Beleuchtungsshader nur Normale und Tiefe (und Shininesswert für Specular, welcher mit bei der Normale dabei ist). Der Nachteil ist das man Diffuse und Specular-Beleuchtung trennen muss.
Bei vielen Lichtern spart man sich so einige Texturlookups.

Kann man nicht die Matrizen für die projezierten Texturen schon so vorbereiten, dass man direkt aus dem Eye-Vektor in den Texturraum transformieren kann? Und die Multiplikation mit der Projektionsmatrix, um den Eye-Vektor zu erhalten, kann man in den Vertexshader verlagern.
Wenn man das beides macht, dann wäre der Gewinn durch eine bereits transformierte Position aus einer Textur nurnoch minimal.

Was mich in der Beziehung aber auch interessieren würde, wäre ob es länger dauert sich aus einer Textur 3 statt 1 Farbkanal zu holen oder ob es einen Unterschied macht wieviel Bit der Kanal hat.


Nach oben
 Profil  
Mit Zitat antworten  
BeitragVerfasst: Fr Dez 02, 2011 22:24 
Offline
DGL Member
Benutzeravatar

Registriert: Do Dez 29, 2005 12:28
Beiträge: 2249
Wohnort: Düsseldorf
Programmiersprache: C++, C#, Java
Zitat:
Was mich in der Beziehung aber auch interessieren würde, wäre ob es länger dauert sich aus einer Textur 3 statt 1 Farbkanal zu holen oder ob es einen Unterschied macht wieviel Bit der Kanal hat.

Ein Lookup holt immer den kompletten Pixel, also alle Farbkanäle die in der Textur vorhanden sind. Wenn ein Pixel kleiner ist weil weniger Bit pro Kanal gibt oder es nicht alle Kanäle gibt ist das aber natürlich schneller. Der Grafikspeicher kann eben nur so und soviel GB/sek verarbeiten. Nebeneinander liegende Pixel werden schneller gelesen, weil dann der Cache genutzt werden kann (*).
=> Ich denke man kann sicher sagen das ein vec4 Zugriff deutlich schneller ist als zwei vec2 Zugriff oder gar vier Zugriffe auf einen Kanal.



(*) ich hatte das damals mal gemessen: auf meiner GraKa kann ein Nachbarpixel doppelt so schnell gelesen werden wie ein zufälliger Pixel.

_________________
Yeah! :mrgreen:


Nach oben
 Profil  
Mit Zitat antworten  
BeitragVerfasst: Sa Dez 03, 2011 07:04 
Offline
DGL Member

Registriert: Do Apr 22, 2010 17:17
Beiträge: 543
Zitat:
Ich mach das bei mir so das ich erst das Licht zusammenaddiere was auf eine Fläche fällt und erst zuletzt diese Summe mit der Oberflächenfarbe multipliziere. Dadurch brauch ich für den Beleuchtungsshader nur Normale und Tiefe (und Shininesswert für Specular, welcher mit bei der Normale dabei ist).


näää, ich brauch da schon die Farbtextur.. Kannst ja nich einfach später Beleuchtung mit Szene Addieren.. das sieht unrealistisch aus.. da dunkle Flächen weniger beleuchtet werden die Helleflächen.. Ich nehme den Farbwert (ohne Ambientlicht) und multipliziere das mit der "Lichtfarbe" und addiere diese ergebnisse aller Lampen dann.. Das sieht viel realistischer aus.

Zitat:
Kann man nicht die Matrizen für die projezierten Texturen schon so vorbereiten, dass man direkt aus dem Eye-Vektor in den Texturraum transformieren kann? Und die Multiplikation mit der Projektionsmatrix, um den Eye-Vektor zu erhalten, kann man in den Vertexshader verlagern.


Ich wüsste nicht wie ich das vorbereiten könnte.. Die projektion (vec4 projCoord = TexGenMat * posWorld;) muss ja pro Fragment gemacht werden und ist je Lampe unterschiedlich.. Und im VertexShader kann ich da auch nix machen.

Was wäre denn wenn ich wirklich einfach eine 16er Textur nehmen würde und da direkt die Eye-Position reinschreibe.. Dann spar ich mir doch den ganzen teil hier:
Code:
  1.  
  2.     vVertex.xy = gl_TexCoord[0].st  * 2.0 - 1.0 ;                          
  3.         vVertex.z = fDepth * 2.0 - 1.0;            
  4.         vVertex.w = 1.0;
  5.         vVertex =  proM * vVertex;         
  6.         vVertex /= vVertex.w;  
  7.         vec4 vEye;                 
  8.         vEye.xyz   = vVertex.xyz  * 1.00001;
  9.  


Die Frage ist nur was aufwändiger ist.. Pro Fragment die o.g. berechnungen oder das verwalten der Doppelt großen Textur.. Dazu muss ich sagen das ich die ganzen Daten auch bei SSAO brauche.. und auch da wird das obige erst aus tiefe errechnet..

Aber auf die Ideee den Specular in die Alphatextur der Colortex zu packen bin ihc noch nich gekommen :P Das werd ich mal probieren.


Nach oben
 Profil  
Mit Zitat antworten  
BeitragVerfasst: Sa Dez 03, 2011 18:43 
Offline
DGL Member

Registriert: Fr Okt 03, 2008 13:32
Beiträge: 367
Thmfrnk hat geschrieben:
näää, ich brauch da schon die Farbtextur.. Kannst ja nich einfach später Beleuchtung mit Szene Addieren.. das sieht unrealistisch aus.. da dunkle Flächen weniger beleuchtet werden die Helleflächen.. Ich nehme den Farbwert (ohne Ambientlicht) und multipliziere das mit der "Lichtfarbe" und addiere diese ergebnisse aller Lampen dann.. Das sieht viel realistischer aus.

Ich meinte nicht mit der Szenenfarbe addieren sondern multiplizieren, also mathematisch ausgedrückt:
Code:
  1. Farbe = Lichtfarbe[0] * Oberflächenfarbe + Lichtfarbe[1] * Oberflächenfarbe + ... Lichtfarbe[n] * Oberflächenfarbe //so ist es bei dir
  2.       = Oberflächenfarbe * (Lichtfarbe[0] + Lichtfarbe[1] + ... + Lichtfarbe[n]) //was ich meinte

Thmfrnk hat geschrieben:
Ich wüsste nicht wie ich das vorbereiten könnte.. Die projektion (vec4 projCoord = TexGenMat * posWorld;) muss ja pro Fragment gemacht werden und ist je Lampe unterschiedlich.. Und im VertexShader kann ich da auch nix machen.

Zu dem mit der Matrix:
Code:
  1. vec4 posWorld = InvViewMat * vec4(vEye.xyz, 1.0);
  2. vec4 projCoord = TexGenMat * posWorld;
  3. =>
  4. vec4 projCoord = TexGenMat * InvViewMat * vec4(vEye.xyz, 1.0);
  5. =>
  6. mat4 NeueMatrix = TexGenMat * InvViewMat;
  7. vec4 projCoord = NeueMatrix * vec4(vEye.xyz, 1.0);
Die "NeueMatrix" wird dann von der CPU vorberechnet bevor sie an den Shader geht. Auf die Weise brauch man die Position in Weltkoordinaten nicht mehr.

Der Teil mit dem Vertexshader den ich meinte, ist ein bisschen komplizierter. Im Programm berechne ich eine Matrix die an den Vertex-Shader geht:
Code:
  1. Matrix:=Matrixf4Mult(Matrixf4Invert(Projektionsmatrix_Kamera),Projektionsmatrix_Fullscreenquad);

Der Vertexshader sieht dann so aus:
Code:
  1. uniform mat4 matrix;
  2. varying vec3 vector;
  3.  
  4. void main(void)
  5. {
  6.     gl_Position = ftransform();
  7.     gl_TexCoord[0]  = gl_TextureMatrix[0] * gl_MultiTexCoord0;
  8.     vec4 tempv = matrix*gl_Vertex;
  9.     vector= tempv.xyz/tempv.w;
  10. }

Und im Fragment-Shader muss noch folgendes berechnet werden:
Code:
  1. varying vec3 vector;
  2. //ClipPlanes der Projektionsmatrix des Fullscreen-Quads
  3. const float FarClip = 100.0;
  4. const float NearClip = 0.1;
  5.  
  6. void main(void)
  7. {
  8.     float depthvalue = texture2D(depth, vec2(gl_TexCoord[0])).x;
  9.     float a = FarClip/(FarClip-NearClip);
  10.     float b = FarClip*NearClip/(NearClip-FarClip);
  11.     float rd=b/(depthvalue-a);
  12.     vec3 eye=vector*rd;
  13.     [...]
  14. }

Die Werte "a" und "b" sollten automatisch als Konstanten vorberechnet werden, wodurch man letztlich nur die Berechnung von "rd" und die Multplikation mit "vector" hat.


Nach oben
 Profil  
Mit Zitat antworten  
Beiträge der letzten Zeit anzeigen:  Sortiere nach  
Ein neues Thema erstellen Auf das Thema antworten  [ 8 Beiträge ] 
Foren-Übersicht » Programmierung » OpenGL


Wer ist online?

Mitglieder in diesem Forum: 0 Mitglieder und 7 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.008s | 16 Queries | GZIP : On ]