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

Aktuelle Zeit: Mi Jul 16, 2025 20:38

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



Ein neues Thema erstellen Auf das Thema antworten  [ 20 Beiträge ]  Gehe zu Seite 1, 2  Nächste
Autor Nachricht
 Betreff des Beitrags: Shadows - Licht Entfernung
BeitragVerfasst: So Mai 13, 2012 23:38 
Offline
DGL Member

Registriert: Di Aug 09, 2011 07:33
Beiträge: 163
Programmiersprache: C/C++
Hey Leute,

Ich musste leider feststellen, dass Schatten, bei einer größerer Entfernungen zur Lichtquelle, immer unschwärfer werden.
Das liegt wohl am Depthbuffer, da die Genauigkeit mit steigender Entfernung abnimmt. Doch wie löst man sowas? Gerade bei Sonnenlicht geht man ja (theoretisch) von einer unendlich entfernten Lichtquelle aus aber da gehts ja schon los. Wie setz ich sowas um?


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Mo Mai 14, 2012 08:44 
Offline
DGL Member
Benutzeravatar

Registriert: Mo Nov 08, 2010 18:41
Beiträge: 769
Programmiersprache: Gestern
Das lässt sich so einfach nicht beantworten da es von der räumlichen Aufteilung abhängt. Bei einen BSP-baum ala id-software lässt sich das relativ einfach gestalten da hier deine Geometrie immer innerhalb eines Würfels liegt. Dadurch kannst du für jeden Würfel ganz leicht den Inhalt, hierachisch nach außen oder umgekehrt projezieren. Die jeweiligen verschiebungen der Projektionsebene ergeben dann die Eigentliche Entfernung. Im Falle von Sonne kann dies sogar soweit gehen das man nachschaut was der Pixel von der Skybox empfängt.

Einige alte RPGs benutzen sowas ähnliches für die Sprites, nur halt auf XY Ebene.

_________________
Meine Homepage


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Di Mai 15, 2012 20:12 
Offline
DGL Member

Registriert: Di Aug 09, 2011 07:33
Beiträge: 163
Programmiersprache: C/C++
Okay das macht durchaus Sinn. Danke.


Dann nochmal eine kleine Frage: Seit ich meine Shadows auf Shader umgestellt habe, werden Schatten leider komplett auf die Geometrie angewandt und Alpha-Texturen werden nicht berücksichtigt. Das man dann bei Bäumen nur was Viereckiges sieht ist dann eher weniger schön :roll:
Ich konnte nur leider nix finden wie ich das behebe?

Wenn ich jetzt im Shader bei der texture2DProj den den Alphawert checke (.a), dann kriege ich halt den Wert von dem Baum z.B. raus (also wo der Transparent ist) aber das hilft mir ja leider nicht wirklich weiter! Ich will ja schließlich den projezierten Schatten auf dem Boden ermitteln. Hoffe das Problem wird deutlich :?


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Di Mai 15, 2012 20:52 
Offline
DGL Member

Registriert: Fr Okt 03, 2008 13:32
Beiträge: 367
Für Lichtquellen wie die Sonne, bei denen die Strahlen (annähernd) parallel sind, kann man für die Shadowmap eine orthogonale Projektion wählen, dann ist der Tiefenbuffer linear. Die tatsächliche Entfernung der Lichtquelle interessiert dann nicht, solange sie weit genug entfernt ist um alle schattenwerfenden Objekte im Blickfeld zu haben. Außerdem nimmt die Lichtintensität mit der Entfernung dann nicht ab, außer durch Absorbtion in der Atmosphäre, wodurch man das auch ignorieren kann.

Zu dem Problem mit den Bäumen: Wenn du die Shadowmap erzeugst musst du den Alphatest benutzen, sodass nur die Pixel einen Schatten werfen, die nicht durchsichtig sind. Man hat dann natürlich keine Halbschatten oder so, aber andere genauere Verfahren sind wiederum sehr rechenintensiv.
Beim Zeichnen der Schatten auf die Geometrie, wird der Schatten/die Beleuchtung nur auf die 3 Farbkanäle angewandt und der Alphakanal bleibt der Wert den man aus der Textur für das Objekt gelesen hat. Dadurch beeinflusst das Licht nicht die Transparenz, was zwar interessant aussieht, aber eigentlich falsch ist.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Di Mai 15, 2012 22:44 
Offline
DGL Member

Registriert: Di Aug 09, 2011 07:33
Beiträge: 163
Programmiersprache: C/C++
Das macht durchaus Sinn :D Also schonmal danke!
Nochmal eine Frage zu der Orthogonalen Projektion:

Ich habe jetzt einfach mal gluPerspective mit glOrtho ersetzt aber wie ich es schon erwartet habe, läuft es nicht.
So sieht erstmal die glOrtho Zeile aus:
glOrtho(0, ShadowMapSize, 0, ShadowMapSize, 1, 1000);

Die Szene ist halt komplett schwarz (so sieht es auch, wenn Objekte hinter der Blickrichtung der Kamera von der Lichtquelle liegen. Ich habe nämlich die Blickrichtung der Sonne mit gluLookAt bestimmt, meine aber mal gelesen zu haben, dass glOrtho und gluLookAt sich nicht so gut vertragen sollen.
Was muss ich also noch anpassen damit es läuft?


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Mi Mai 16, 2012 06:56 
Offline
DGL Member

Registriert: Do Apr 22, 2010 17:17
Beiträge: 543
mit glOrtho hab ich noch keine Shadows gemacht, aber um die Transparenz der Bäume hinzubekommen, könntest du beim Rendern der ShadowMap einfach den Alphatest aktivieren.

EDIT: SORRY hatte nich gelesen das dies schon beantwortet wurde :roll:


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Mi Mai 16, 2012 07:23 
Offline
DGL Member

Registriert: Di Aug 09, 2011 07:33
Beiträge: 163
Programmiersprache: C/C++
Das mit dem Alphatest läuft schon. Einfach während der Erstellung der ShadowMap einen Shader aktiviert, der das jeweils überprüft. Klappt also :)

Nur die Orthogonale Projektion will nicht laufen.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Mi Mai 16, 2012 11:46 
Offline
DGL Member
Benutzeravatar

Registriert: Sa Aug 18, 2007 18:47
Beiträge: 694
Wohnort: Köln
Programmiersprache: Java
Beim Erzeugen der Shadowmap verwende ich einen Shader der nur dann erfolgreich abschliesst wenn der Alphatest durchläuft (Schwellwert 0.5) und ansonsten den Pixel einfach mittels 'discard' verwirft.

Bei glOrtho verwende ich für die Tiefe angepasste Werte. Im Moment sind sie noch statisch und eben auf die Szene angepasst, so dass alles mehr oder weniger beleuchtet wird.

z.B.
Code:
  1.  
  2. width = shadowSettings.width * Math.pow(2, pcfIndex); // pcfIndex 0-2
  3. depth = shadowSettings.depth * 16; // range 1-8
  4. glOrtho(-width, width, -width, width, -depth, depth);


Mittels gluLookAt wird die Sonnenkamera dann auf einen Punkt, der 'shadowSettings.width' Einheiten entfernt in der Blickrichtung der Szenenkamera liegt, gerichtet.

_________________
Es werde Licht.
glEnable(GL_LIGHTING);
Und es ward Licht.


Zitat aus einem Java Buch: "C makes it easy to shoot yourself in the foot; C++ makes it harder, but when you do it blows your whole leg off"

on error goto next


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Mi Mai 16, 2012 15:43 
Offline
DGL Member

Registriert: Fr Okt 03, 2008 13:32
Beiträge: 367
Das mit dem gluLookAt klappt schon, man muss es nur ein bischen anders angehen:
Code:
  1. glViewport(0, 0, ShadowMapWidth, ShadowMapHeight);
  2. glMatrixMode(GL_PROJECTION);
  3. glLoadIdentity;
  4. glOrtho(-0.5*Width,0.5*Width,-0.5*Height,0.5*Height,NearClipping,FarClipping);
  5. glMatrixMode(GL_MODELVIEW);
  6. glLoadIdentity;
  7. gluLookAt(pos[0],pos[1],pos[2],pos[0]+look[0],pos[1]+look[1],pos[2]+look[2],up[0],up[1],up[2]);

Width und Height sind die Breite und Höhe des Bereiches den die Shadowmap abdecken soll, im Koordinatensystem deiner Welt. Die Abmessungen der Shadowmap sind natürlich ShadowMapWidth und ShadowMapHeight, die wiederum in Pixel angegeben sind.
pos, look und up sind jeweils die Position der Lichtquelle, deren Richtung und ein Vektor der "nach Oben" zeigt und für die Ausrichtung der Shadowmap entlang der Richtung dient.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Mi Mai 16, 2012 16:15 
Offline
DGL Member

Registriert: Di Aug 09, 2011 07:33
Beiträge: 163
Programmiersprache: C/C++
Hm also irgendwie will das nicht :?
Wenn ich am Anfang das FBO initalisiere, dann erstelle ich die Projectionsmatrix auch einmal und pack die Werte in ein Array:
Code:
  1.     glLoadIdentity();
  2. //  gluPerspective(5.0f, 1.0f, 10.0f, 5000.0f);
  3.     glOrtho(-0.5 * ShadowMapSize, 0.5 * ShadowMapSize, -0.5 * ShadowMapSize, 0.5* ShadowMapSize, 1, 2500);
  4.     glGetFloatv(GL_MODELVIEW_MATRIX, LightProjMatrix);
  5.  

Mit der gluPerspective Variante funktioniert es ohne Probleme.

Im Code selbst dann halt nur noch die Matrix laden:
Code:
  1.         glMatrixMode(GL_PROJECTION);
  2.         glPushMatrix();
  3.         glLoadMatrixf(LightProjMatrix);
  4.  



Danach kommt gleich gluLookAt:
Code:
  1.         glMatrixMode(GL_MODELVIEW);
  2.         glPushMatrix();
  3.  
  4.         glLoadIdentity();
  5.         gluLookAt(SunPosition[0], SunPosition[1], SunPosition[2], x_change, y_change, z_change, 0.0f, 1.0f, 0.0f);
  6.  



Den Viewport passe ich dann nach dem binden des FBO's an, was aber nicht weiter schlimm sein sollte.
Und so sieht das dann ingame aus (mit glOrtho) - die Geometrie ist komplett schwarz:


Du hast keine ausreichende Berechtigung, um die Dateianhänge dieses Beitrags anzusehen.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Mi Mai 16, 2012 20:47 
Offline
DGL Member

Registriert: Fr Okt 03, 2008 13:32
Beiträge: 367
Code:
  1. glLoadIdentity();
  2. //gluPerspective(5.0f, 1.0f, 10.0f, 5000.0f);
  3. glOrtho(-0.5 * ShadowMapSize, 0.5 * ShadowMapSize, -0.5 * ShadowMapSize, 0.5* ShadowMapSize, 1, 2500);
  4. glGetFloatv(GL_MODELVIEW_MATRIX, LightProjMatrix);

Hier holst du die ModelView-Matrix und später setzt du damit die Projection-Matrix.
Ansonsten könnte es vllt auch am Shader liegen. Bin mir nicht sicher ob man dann noch texture2DProj verwenden muss.

Zum Debuggen vllt noch ein paar Tipps: Um zu überprüfen ob die Shadowmap richtig befüllt wird, kannst du sie mal auf ein Quad oder deine Geometrie ausgeben. Dann erhält man im Normalfall ein Graustufenbild.
Außerdem kannst du mal die Texturkoordinaten der Shadowmap als Farbe auf den zu beleuchtenden Objekten ausgeben. Die Werte müssten zwischen 0 und 1 liegen, ansonsten sind die Koordinaten falsch.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Mi Mai 16, 2012 21:06 
Offline
DGL Member

Registriert: Di Aug 09, 2011 07:33
Beiträge: 163
Programmiersprache: C/C++
Ja wie gesagt, ich erstelle die Projektionsmatrix einmal zu begin. Da ist gerade die Modelview Matrix aktiv, wodurch ich die Werte halt darin berechne! Bei gluPerspective nehm ich ja auch die Modelview Matrix und es geht.

texture2DProj nutze ich Shader, die Idee mit der DepthMap ausgeben auf einem Quad werde ich aber mal probieren.
Ich finde es halt merkwürdig, dass der Code eben vorher komplett funktioniert und eben nur der Austausch von gluPerspective durch glOrtho den Fehler verursacht.

Durch die Bias-Matrix sollten die Koordinaten auch zwischen 0 und 1 liegen.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Do Mai 17, 2012 14:28 
Offline
DGL Member

Registriert: Di Aug 09, 2011 07:33
Beiträge: 163
Programmiersprache: C/C++
Ich habe mir zum Debuggen die beiden Depth-Textures mal ausgeben lasse aber mit sehr unterschiedlichem Ergebnis.
Im Anhang ist einmal mit gluPerspective und einmal mit glOrtho - bei Ortho ist die gesamte Szene in der Depthtexture und das aus meiner Sicht unerklärlichen Position, zumal die Szene auch wirklich sehr klein ist in der DepthTexture.

Edit// Wenn ich so drüber nachdenke, dann macht die Größe ja schon etwas Sinn. Bei gluPerspective wird die Sichtgröße in der Ferne hin immer stärker, wo hingegen es bei Orthogonaler Projektion vom Anfangs bis zum Endpunkt gleich bleibt.
Unter dem Aspekt habe ich zwar letztendlich 2 DepthTextures aber trotzdem keine Schatten :?


Edit2// Vllt. liegt es an der Berechnung der Matrix, welche ich dann an den Shader übergebe:
Code:
  1.     static float Bias[16] = {   0.5f, 0.0f, 0.0f, 0.0f,
  2.                                 0.0f, 0.5f, 0.0f, 0.0f,
  3.                                 0.0f, 0.0f, 0.5f, 0.0f,
  4.                                 0.5f, 0.5f, 0.5f, 1.0f
  5.                             };
  6.  
  7.     glLoadMatrixf(Bias);
  8.     glMultMatrixf(LightProjMatrix);
  9.     glMultMatrixf(LightMatrix);


LightProjMatrix enthält die Informationen von glOrtho und die LightMatrix von gluLookAt.


Du hast keine ausreichende Berechtigung, um die Dateianhänge dieses Beitrags anzusehen.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Do Mai 17, 2012 17:22 
Offline
DGL Member

Registriert: Fr Okt 03, 2008 13:32
Beiträge: 367
Versuch' es auf jeden Fall mal noch mit texture2D, wenn du das noch nicht hast. Das texture2DProj ist dazu da um die perspektivische Korrektur vorzunehmen, weil entfernte Objekte auf der Shadowmap kleiner sind. Bei glOrtho benötigt man das aber nicht.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags: Re: Shadows - Licht Entfernung
BeitragVerfasst: Do Mai 17, 2012 17:29 
Offline
DGL Member

Registriert: Di Aug 09, 2011 07:33
Beiträge: 163
Programmiersprache: C/C++
Reden wir wirklich über texture2D/texture2DProj? Zur Darstellung der Schatten nutze ich nämlich shadow2DProj.

Hier einfach mal der Shader:
Code:
  1. uniform sampler2DShadow ShadowMap;
  2. uniform sampler2D NormalMap;
  3.  
  4. varying vec4 ShadowCoord;
  5. varying vec3 vertex_normal;
  6. varying vec3 vertex_light_position;
  7.  
  8. uniform float xPixelOffset;
  9. uniform float yPixelOffset;
  10.  
  11.  
  12. float lookupNear(vec2 offSet)
  13. {
  14.     return shadow2DProj(ShadowMap, ShadowCoord + vec4(offSet.x * xPixelOffset * ShadowCoord.r, offSet.y * yPixelOffset * ShadowCoord.r, 0.005, 0.0)).r;
  15. }
  16.  
  17.  
  18. void main()
  19. {  
  20.     float shadow=0.0, x, y;
  21.     vec2 o = mod(floor(gl_FragCoord.xy), 2.0);
  22.  
  23.     if (ShadowCoord.w > 1.0)
  24.     {
  25.         shadow = lookupNear(vec2(-1.5, 1.5) + o);
  26.         shadow += lookupNear(vec2( 0.5, 1.5) + o);
  27.         shadow += lookupNear(vec2(-1.5, -0.5) + o);
  28.         shadow += lookupNear(vec2( 0.5, -0.5) + o);
  29.         shadow = (shadow * 0.25) + 0.3;
  30.     }
  31.  
  32.     float diffuse_value = max(dot(vertex_normal, vertex_light_position), 0.0) + 0.3;
  33.     vec4 texel = texture2DProj(NormalMap, gl_TexCoord[0]);
  34.     if (diffuse_value < shadow)
  35.         texel.rgb *= diffuse_value;
  36.     else
  37.         texel.rgb *= shadow;
  38.  
  39.     gl_FragColor = texel * gl_Color;
  40. }


Konnte man den Code hier im Forum nicht irgendwie für C auslegen? Also sowas wie [code=C] oder so?! :?
Edit by i0n0s:
Ja, mit [code=C]...


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


Wer ist online?

Mitglieder in diesem Forum: Bing [Bot] und 2 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:  
cron
  Powered by phpBB® Forum Software © phpBB Group
Deutsche Übersetzung durch phpBB.de
[ Time : 0.012s | 15 Queries | GZIP : On ]