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

Aktuelle Zeit: Sa Jul 05, 2025 22:39

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



Ein neues Thema erstellen Auf das Thema antworten  [ 14 Beiträge ] 
Autor Nachricht
 Betreff des Beitrags: Texturen mischen
BeitragVerfasst: Sa Okt 25, 2008 16:43 
Offline
DGL Member

Registriert: Mi Mär 28, 2007 17:45
Beiträge: 131
Hallo,

bin in Sachen Texturen noch ziemlich grün und habe eine Frage, die wahrscheinlich schon irgendwie gestellt und beantwortet wurde, ich finde nur nichts passendes. Also, ich möchte im Gelände dort, wo verschiedene Bodentexturen zusammenstoßen, mischen, und zwar mit diversen Masken. Mit einem Grafikprogramm simuliert, sieht es so aus:

Bild

Hier ist es eine ziemlich weiche Maske, der weiße Teil ist transparent (oder umgekehrt). Vielleicht ein Tipp, wie ich an die Sache herangehen muss?


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Sa Okt 25, 2008 17:58 
Offline
DGL Member
Benutzeravatar

Registriert: Mi Aug 13, 2008 12:39
Beiträge: 26
Wohnort: Berlin
also, ich selbst als OpenGL Noob würde einfach mal so das Wort "Blending" in den Raum werfen, siehe Tutorial 7 ist es glaube ich.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: So Okt 26, 2008 21:54 
Offline
DGL Member
Benutzeravatar

Registriert: Do Dez 05, 2002 10:35
Beiträge: 4234
Wohnort: Dortmund
Also wenn du nur Texturen das Problem sind, dann kannst du auch Multitexturing benutzen. Das würde ich auch empfehlen.

Was die Texturen angeht. Der Sand und das Gras sind ja normale RGB Texturen. Den Übergang kannst du da entweder als Alphakanal in der darüberliegenden Textur (Gras) packen oder aber als seperate Graustufentextur. In etwa so wie das was du da hast. Nur du musst darauf achten, dass im Grafikprogramm auch wirklich Grausstufentextur steht. Beim Laden musst du diese Textur dann auch als GL_ALPHA laden. Bzw können einige Loader damit nicht umgehen. Ich würde eher das erstere Empfehlen. Also Alphakanal einbetten. Aber das ist etwas statischer.

Für alles Andere sollte das Tutorial genug Aussagekraft haben. Wenn nicht fragen. ;)


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mo Okt 27, 2008 10:24 
Offline
DGL Member
Benutzeravatar

Registriert: Di Mai 18, 2004 16:45
Beiträge: 2623
Wohnort: Berlin
Programmiersprache: Go, C/C++
Es gibt da eine sehr beliebte Technik über 4 Texturen und einer Blendingmap oder Verticecolor.
Dabei wird ein sehr simpler Shader verwendet, welcher einfach nur nach der Texelfarbe nachfragt und dann diese auseinander nimmt.
Rot, Grün, Blau und Alpha sind jeweils ein Blendingkanal, welche den jeweiligen Anteil an Textur 1-4 sind.
Wenn du also 255,255,255,255 nimmst, dann blendet er alle Texturen zu 1/4.
Wieso 1/4, weil man nach dem auslesen der Texelfarbe noch eine Normalisierung drüber schickt, die dann die summe aller Farbkomponenten zu 1.0 macht.
Das macht man, weil wenn alle Farben zusammen über 1.0 gehen würden, was Colorbleeding zufolge hätte.
So kann man Über Texturen oder über die Verticecolor blendings mache, dies ist sehr flexibel :)
Geht natürlich nur gut, wenn du dich geringfügig in shader einliest, was vom aufwand wohl der gleiche ist, wenn du blending über multitexturing machst(in den Shadertuts ist ein Beispiel mit dabei). http://www.youtube.com/watch?v=PrIQdcT4CCE Das Video ist von ein Kumpel und da benutzt er Vertice Color, um die Texturen zu blenden.

_________________
"Wer die Freiheit aufgibt um Sicherheit zu gewinnen, der wird am Ende beides verlieren"
Benjamin Franklin

Projekte: https://github.com/tak2004


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mo Okt 27, 2008 10:52 
Offline
DGL Member

Registriert: Mi Mär 28, 2007 17:45
Beiträge: 131
Danke, so komme ich der Sache schon näher.

Zitat:
also, ich selbst als OpenGL Noob würde einfach mal so das Wort "Blending" in den Raum werfen, siehe Tutorial 7 ist es glaube ich.

Was das Tutorial betrifft, ich hatte es vorher schon mehrmals gelesen. Genau an der entscheidenden Stelle wird es aber ziemlich vage. Der Effekt wird gezeigt, ein paar undeutliche Hinweise, dann hört's abrupt auf und es geht ins nächste Kapitel (Lichterkarten). Das soll keine Kritik an dem Tutorial sein, man kann ja nicht jedes Detail bis ins Kleinste beschreiben, aber wer darauf verweist, sollte eigentlich sicher sein, dass es die Frage auch beantwortet.

Außerdem geht es ja nicht nur darum, in einem Quad mal die eine oder andere Blendfunktion auszuprobieren, sondern es müssen tausende von (triangulierten) Tiles möglichst schnell und effektiv überblendet werden. Dabei darf z.B. die Helligkeit auch in den Mischbereichen nicht verschoben werden.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mo Okt 27, 2008 12:09 
Offline
DGL Member

Registriert: Mi Mär 28, 2007 17:45
Beiträge: 131
Zitat:
Den Übergang kannst du da entweder als Alphakanal in der darüberliegenden Textur (Gras) packen oder aber als seperate Graustufentextur.


Ein unregelmäßiger Übergang macht m.E. nur Sinn, wenn verschiedene Masken verwendet und per Zufall zugeordnet werden, sonst wird doch wieder ein Muster sichtbar. Wenn die Masken in die obere Texturschicht "eingelagert" werden, muss ja ein Unmenge an verschiedenen Texturen gebastelt werden. Überlegung: Ich habe 10 verschiedene Texturen, jede mit jeder gemischt, das Ganze dann mal 6 Masken ... Obwohl das verlockend ist, denn das alles muss ja nicht zur Laufzeit geschehen.

Kleine Nebenfrage: Wie kann ich feststellen, ob und wieweit der Texturspeicher der Grafikkarte voll ist?


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mo Okt 27, 2008 13:20 
Offline
DGL Member
Benutzeravatar

Registriert: Di Mai 18, 2004 16:45
Beiträge: 2623
Wohnort: Berlin
Programmiersprache: Go, C/C++
Wo wir wieder beim Shader wären ^^, du kannst im Shader z.B. durch modulation oder ähnliches die wiederholung stark reduzieren.
Dabei musst du deine Textur nicht nur Kantengleich machen sondern alle Kanten müssen zueinander passen, dann kannst du die Textur für jedes Feld mit 4 verschiedenen Winkeln (0,90,180,270) zeichnen, somit reduziert man die sichtbare wiederholung stark und in Kombination mit dem Blending im Shader und der möglichkeit das Shading über die Normals zu machen, hast du alles Performant und kompakt in einen Shader.
Also bräuchtest du Texturen, bei den alle Kanten zueinander Passen(nicht verschiedene Texturen unterinander), die Blendingwerte als Verticecolor und einen Shader. Dann bindest du die 4 Texturen, setzt sie für den Shader, startest das VBO.
Nun muss der Shader zuerst die Verticecolor raus lesen, dann kann die Position(Global) ermittelt werden und ein Zufallswert(darf nicht wirklich zufällig sein, sondern immer die gleiche Zahlenreihe zurückgeben).
Statt nun einfach den Texel aus den 4 Texturen zu lesen, wird die UV koordinate rotiert(abhängig der Zufallszahl), damit haben wir ein recht einfach realisierten abwechselnde Variation. Nun kann man den Texel für jede Textur lesen.
Jetzt wird jeder Texel mit einer der Komponenten, des Farbvektors(normalisierung vorher nicht vergessen) multipliziert.
Nun kann man die alle addieren und hat die Difuse Texelfarbe.
Für ein Bischen Licht kann man noch die Normale und die Lichtquelle herran ziehen und dann den berechneten Shadingwert mit der Texturfarbe multiplizieren.
Damit hast du das ganze in den Shader verlagert und der wird vom Treiber ordentlich optimiert, wärend eine auf der veralteten Blending API basierten Variante nicht nur langsamer sondern auch Codetechnisch ziemlich schwer zu debuggen und entwickeln ist. Denn den Shader kannst zur Laufzeit einfach ändern und neu compilieren(ohne die App neu zu starten). Mit Tools wie Shader Monkey oder Lumina kannst du auch ohne eine Zeile Code schon mal das ganze testen, du schreibst nur den Shader, packst 2-3 Planes rein, fügst 4 texturen hinzu und legst die Verticecolor per Hand fest.

_________________
"Wer die Freiheit aufgibt um Sicherheit zu gewinnen, der wird am Ende beides verlieren"
Benjamin Franklin

Projekte: https://github.com/tak2004


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mo Okt 27, 2008 20:15 
Offline
DGL Member

Registriert: Mi Mär 28, 2007 17:45
Beiträge: 131
Hallo,

das ist ein starkes Plädoyer für Shader, und obwohl ich zur Zeit noch keine Ahnung davon habe, klingen die Gründe überzeugend. Ich werde mich mit Sicherheit in Kürze damit beschäftigen. Vorerst aber muss ich das Blendung durchschauen. Deshalb die Stelle, wo ich einfach hängen bleibe. Zuerst zeichne ich die Grundtextur, ohne Blending:

Code:
  1.     glTranslatef (0, 0, -3);   
  2.     glDisable (GL_BLEND);
  3.    
  4.     glColor4f (1, 1, 1, 1);
  5.     glBindTexture (GL_TEXTURE_2D, texid1);  // Sand
  6.     glBegin (GL_QUADS);
  7.              glTexCoord ... glVertex ... wie üblich
  8.     glEnd ();
  9.  


Dann lege ich die Maske darüber (Graustufen mit Alpha, linkes Bild). Das Ergebnis sieht wie im rechten Bild so aus wie gewollt.
Code:
  1.     glColor4f (1, 1, 1, 1);
  2.     glEnable (GL_BLEND);
  3.     glBlendFunc (GL_ONE, GL_SRC_ALPHA);
  4.     glBindTexture (GL_TEXTURE_2D, mask1);
  5.     glBegin (GL_QUADS);
  6.               ...
  7.     glEnd ();
  8.  


Bild

Das war's dann, alle Versuche, nun das Gras an die freie Stelle zu bekommen, scheitern. Etliche Blendfunktionen habe ich versucht, vielleicht auch einige übersehen. Entweder kommt nichts oder das Gras überdeckt alles, oder es vermischt sich mit dem Sand.

Code:
  1.     glColor4f (1, 1, 1, 1);
  2.     glBlendFunc (GL_ONE_MINUS_DST_ALPHA, GL_ONE);
  3.     glBindTexture (GL_TEXTURE_2D, texid2);
  4.     glBegin (GL_QUADS);
  5.              ...
  6.     glEnd ();
  7.  


Mir erscheint GL_ONE_MINUS_DST_ALPHA am sinnvollsten, weil von Source das übernommen werden soll, was in Destination per Alpha unterdrückt ist. Nur - Fehlanzeige.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Di Okt 28, 2008 10:06 
Offline
DGL Member
Benutzeravatar

Registriert: Do Dez 05, 2002 10:35
Beiträge: 4234
Wohnort: Dortmund
Beim Blenden GL_DST_ALPHA oder GL_ONE_MINUS_DST_ALPHA zu verwenen ist gefährlich. Denn es passiert häufig, dass der Alphakanal im Framebuffer nicht erzeugt wird. Und selbst, wenn man möchte, dass der Alphakanal erzeugt wird, dann gibt es keine Garantie, dass er das auch wirklich wird.

Und das Problem an deiner Stelle ist, dass du das MultiPass Verfahren anwendest. Also jede Textur auf ein einzelnes Quad zu zeichnen. Es wäre aber besser, wenn du Multitexturing anwenden würdest. Da es später mehr werden würde ich dir in jedem Fall dazu raten kein halbes Multitexturing zu verwenden sondern ausschließlich nur darauf zu setzen, denn bei 10 Texturen + 6 Verläufen wirst du ohne Shader nicht mehr auskommen. In der FixedFunction werden maximal 4-8 Texturen unterstützt.

Beim Multitexturing würdest du 3-4 Texturen binden (siehe Tutorial aus meinem ersten Post) und würdest nur ein einziges Quad zeichnen. Denn aktuell sieht es so aus, dass du 3 Texturen hast. Gras (RGB), Sand (RGB) und einen Verlauf (Alpha). Wenn du eine RGB und eine Alphatextur miteinander bindest dann werden diese beiden Texturen moduliert (multipliziert) und es erscheint wie eine einzige Textur. Der Alphakanal wird dann einfach nur in die andere Textur eingefügt.

Nur zum Verständniss. Halbes Multitexturing (Mischung aus Multipass und Multitexturing): Dabei würdest du das Sand Quad ganz normal zeichnen. Anschließend sowohl die Gras als auch die Alphatextur binden und noch ein Quad zeichnen. Damit würde es sich so verhalten als wäre der Alphakanal bereits in der Grastextur enthalten. Das würde zwar jetzt funktionieren aber auf langer Sicht würde das für dich nicht genügen! Deswegen nur zum Verständniss.

Bei reinem Multitexturing würdest du sowohl Sand, Gras als auch die Alphatextur binden und ein Quad zeichnen. Hier müsstest du OpenGL jetzt sagen was er zu tun hat. Denn normal würde er alle Texturen miteinander Modulieren. Und das ist nicht das was du haben willst. Dazu gibt es unter anderem die Erweiterung GL_ARB_texture_env_combine. Ganz unten gibt es auch ein Beispiel aber das ist nicht ganz das was du haben willst. Denn dort wird anstelle der Alphatext nur ein fixer Wert benutzt. Ich meine man kann bei den Operatoren aber auch direkt eine Textur angeben.

Wobei das aber auf lange Sicht dein Problem auch nicht lösen würde. Denn du kannst damit nicht alle Texturen ansprechen. Also da solltest du dir die Frage stellen ob du zu erst auf etwas setzen möchtest was du letzten Endes sowieso austauschen musst oder lieber gleich etwas ganz neues macht. Ich traue mir da sogar fast zu behaupten, dass Shader auch einfacher zu verstehen sind als die Logik hinter den Combinern. ;)


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mi Okt 29, 2008 20:14 
Offline
DGL Member

Registriert: Mi Mär 28, 2007 17:45
Beiträge: 131
Erst mal danke für eure ausführlichen Erklärungen. Es schien auf den ersten Blick so einfach zu sein, aber da steckt ja noch einiges dahinter. Ich werde nun systematisch vorgehen und zuerst die Möglichkeiten von Multitexturing erkunden, na ja, und wahrscheinlich wird es dann auf Shader hinauslaufen.

Nur noch 'ne Verständnisfrage: Habe ich dich richtig verstanden, dass man beim Multitexturing Texturen außerhalb des Framebuffers miteinander mischen kann? Das wäre natürlich schon ein guter Ansatz, denn die Verkettung im Framebuffer scheint enorme Probleme zu machen.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Do Okt 30, 2008 09:04 
Offline
DGL Member
Benutzeravatar

Registriert: Do Dez 05, 2002 10:35
Beiträge: 4234
Wohnort: Dortmund
Ja so in etwa stimmt das. Nur ist das nicht nur beim Multitexturing so. Das ist immer so. Es wird zu erst die Farbe des Fragmentes berechnet. Die kann auch immer noch mit aus der OpenGL Farbe etc bestehen. Und die berechnete Fragmentfarbe wird anschließend mit dem Framebuffer verrechnet. Beim Multitexturing ist es dann aber so, dass sich die Fragmentfarbe aus mehr als einer Textur zusammensetzen kann.

Das Multipassverfahren stammt noch aus einer Zeit wo die Grafikkarten nur 1-2 Texturen konnten. Und das ist selten genug. Du wirst mit transparenten Fragmenten wohl auch recht schnell echte Probleme bekommen. Bzw muss dabei auch immer die Geometrie doppelt und dreifach gezeichnet werden.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Do Okt 30, 2008 10:30 
Offline
DGL Member

Registriert: Mi Mär 28, 2007 17:45
Beiträge: 131
Ich versuche mal eine Zusammenfassung (rein theoretisch noch):

- Multi pass (das, was ich versucht habe): überholt und tückisch
- halbes Multitexturing (nur Maske und obere Textur): schon besser, aber begrenzt
- volles Multitexturing: gut, fehlt aber noch die Möglichkeit, richtig hinzulangen
- Shader: auf Dauer die flexibelste Lösung

Frage, da ich mit Shadern noch nicht zu tun hatte: Wie steht es dabei mit der Performance? Das ist beim Rendern von größeren Terrains immer noch wichtig.

Und dann: Ich denke, die Art und Weise, wie ich das Terrain rendern und die Übergänge haben möchte, ist m.E. eine gute Methode, zu natürlichen und optisch ansprechenden Landschaften zu kommen. Welche Masken mit welchen Texturen verwendet werden sollen, kann man sehr gut in einer Datei mit Texturbeschreibungen festlegen und variieren. Wär das nicht mal ein tolles Thema für ein konkretes Shader-Tutorial? Oder gibt es dazu schon was?


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Do Okt 30, 2008 11:52 
Offline
DGL Member
Benutzeravatar

Registriert: Do Dez 05, 2002 10:35
Beiträge: 4234
Wohnort: Dortmund
Also mit halben Multitexturing meinte ich die Vermischung von Multitexturing und Multipass. Das ist manchmal programmiertechnisch einfacher als sich mit diesen ganzen Texturmodis auseinander zu setzen müssen. Allerdings hat man da immer die Probleme der ältesten Technologie am Hals. Also in dem Fall die des Multipassverfahrens.

Shader ersetzen kein Multitexturing. Das ist eher "nur" eine Erweiterung. Multitexting ohne Shader (Fixed Function) hat einen gewissen Funktionsumfang. Wenn du mehr (Texturen, Verrechnungsmodis) braucht hast du pech gehabt. Mit Shadern hast du die Möglichkeit auf mehr Texturen zugreifen zu können und die kannst die Verarbeitung der Daten ganz nach deinen Wünschen anpassen.

Über die Geschwindigkeit würde ich mir nicht unbedingt groß Gedanken machen. Ich meine auf aktuellen Grafikkarten wird die Fixed Function intern auch über Shader gelöst. Je nachdem wie diese Shader dann aufgebaut werden kann es sogar sein, dass du mit eigenen Shadern sogar noch besser fährst, da du eventuell unwichtige Dinge schlicht unter den Tisch fallen kannst und dadurch der GPU arbeit ersparst.

Viel wichtiger dabei sind aber die Hardwareanforderungen. Mit glSlang benötigst du OpenGL 2.0 bzw OpenGL 1.5 mit passender Erweiterung. Wenn deine Zielplatform aber eher Notebooks/Ältere PCs sind könntest du mit den Anforderungen einige Leute ausschließen. An diesem Punkt muss man immer abwägen ob man nicht evtl noch einen anderen Weg sucht um die Anforderungen zu senken (nur dann mehr Texturen benutzen, wenn nötig (zum beispiel an den Übergängen)) oder ob man bewusst sagt alles unter dem geht halt nicht.

Hatte die letzten Tage auch ein bisschen mit Shadern rumgebasstelt und muss sagen. Es ist erfrischend einfach. In deinem Fall müsstest du wohl nur ein paar Texturfarbwerte auslesen (jeweils 1 Funktionsaufruf) und anschließend musst du die Farben anhand der Verläufe multiplizieren und das wars.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Do Okt 30, 2008 18:24 
Offline
DGL Member

Registriert: Mi Mär 28, 2007 17:45
Beiträge: 131
Zitat:
Viel wichtiger dabei sind aber die Hardwareanforderungen. Mit glSlang benötigst du OpenGL 2.0 bzw OpenGL 1.5 mit passender Erweiterung. Wenn deine Zielplatform aber eher Notebooks/Ältere PCs sind könntest du mit den Anforderungen einige Leute ausschließen.

Ich denke, dass lässt sich mit sauberer Programmierung abfangen. Abfrage, ob Unterstützung, und falls nicht, kürzer treten, weniger Masken oder evtl. ein einfacheres, wenn auch nicht so schönes Verfahren. Aber die Rechner mit Grafikarten, die viel älter sind als meine (GForce FX 5200) solten eher selten sein. Und die GForce arbeitet mit Version 2.1, wobei meine GL-Info-Routine u.a. auch GL_ARB_fragment_shader auswirft. Irgendwo muss man m.E. sowieso einen Schlusstrich ziehen. Muss ja nicht so radikal sein wie MS mit seinen Hardwareanforderungen (siehe Flussimulator).

Noch einmal vielen Dank für deine Mühe, mir den richtigen Weg zeigen. Packen wir's an.


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


Wer ist online?

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