glCullFace anhand der Normale/Shader abbrechen?



  • Tag! 🙂
    Ich berechne im Vertexshader ob man die vorder oder Rückseite eines Polygons sieht. Danach entscheide ich ob ich das Teil malen will oder auch nicht. Dazu müsste ich dann jedoch im vertexShader den Prozess abbrechen können?! 😕

    Ich vermute aber dass das eine miese Lösung ist. Ich sollte wohl eher vorher schon entscheiden ob ich zeichnen will oder nicht - aber ich wollte ein bisschen mehr die GPU in Anspruch nehmen, da die kaum belastet wird....

    Zudem bestimmt bei mir ausnahmslos die Normale wo vorne ist! Jedesmal zu bestimmen ob das Polygon Clockwise oder Counterclockwise ist und danach glCullFace zu setzen stelle ich mir furchtbar unelegant/perfomant vor!!!

    Kurz: Wie geht face culling wenn nur die Normalen zur verfügung stehne?
    oder: Wie kann ich glFrontFace anhand der Normale setzen ohne unschöne berechnungen durchzuführen?
    oder anders: Ist es möglich/sinnvoll das im Vertexshader zu berechnen? Kann man shader abbrechen?

    Help + ty! 🙄 😮



  • Der Vertex-Shader liefert ja die finale Position eines einzelnen Vertex.
    Um die Ausrichtung einer Primitive zu ermitteln muessen also alle dafuer notwendigen Vertices den Shader durchlaufen haben - darum passiert das Culling erst danach.
    Jeder Vertex der in den Shader rein geht kommt auch hinten wieder raus.
    Um dabei Polygone gezielt zu verwerfen kannst Du alle zugehoerigen Vertices an die gleiche Position setzen.
    Um sowas im Vertex-Shader zu entscheiden muss aber jeder Vertex alle dafuer notwendigen Parameter mit sich tragen, die Vertexdaten werden also entsprechend groesser.
    Dadurch ist es meistens performanter zwei entsprechend optimierte Render-Passes zu machen (einen mit Front- und einen mit Backface-Culling) oder einfach jedes Polygon sowohl clockwise als auch counterclockwise zu erzeugen.
    Eine andere Alternative sind Geometry-Shader.



  • <ZENSIERT>

    //Edit: Das mit den 2 render-passes verstehe ich nicht ... Was soll ich da genau machen? 😮

    //Edit2: Der Fehler liegt nicht am shader sondern an meinen normalen-berechnungen ... 🙄



  • verstehe ich nicht ... Was soll ich da genau machen? 😮

    Nun, wenn beispielsweise die Vorderseiten Deiner Polygone anders aussehen sollen als die Rueckenseiten, dann renderst Du erstmal alle Vorderseiten mit Methode A und dann alle Rueckseiten mit Methode B.

    Aber am besten erklaerst Du erstmal, was genau Du ueberhaupt erreichen willst.


  • Mod

    Pigeon schrieb:

    Kurz: Wie geht face culling wenn nur die Normalen zur verfügung stehne?

    wenn du die normale pro vertex hast, dann hast du sie ja schon erstellt als du das dreieck gesetzt hast, das heisst doch, dass du auch einfach das dreieck so erstellen kannst, dass die hardware culling macht fuer dich.

    oder: Wie kann ich glFrontFace anhand der Normale setzen ohne unschöne berechnungen durchzuführen?

    ich weiss nicht was fuer dich ne unschoene berechnung ist. berechne einfach anhand die normale des dreiecks und dann benutzt du deine normale die du auch im shader nutzt und vergleichst ob sie in die selbe oder entgegengesetzte richtung zeigen. falls entgegengesetzt, tauscht du zwei belibige vertices vom dreieck.

    oder anders: Ist es möglich/sinnvoll das im Vertexshader zu berechnen? Kann man shader abbrechen?

    im shader berechnest du ja vermutlich keine normalen, entsprechend steht sie schon vorher fest. an dem punkt wo sie feststeht (und ich gehe mal davon aus dass sie bei dir fuer alle 3 eckpunkt des dreiecks gleich ist), kannst du auch gleich das dreieck richtig winden. das ist ehrlich die einfachste und beste methode.

    falls deine dreiecke einzeln sind, kannst du wie helli sagte das dreieck einfach an den 0 punkt bringen.
    falls die dreiecke nicht einzeln sind, kannst du alphatest einschalten und abhaengig von frontface/backface 0 oder 1 als alpha uebergeben.



  • Beispiel Würfel.
    Zeigen die normalen "nach innen", also sind die Aussenseiten Rückseiten, dann will ich dass diese nicht gezeichnet werden sondern eben nur die eigendlich nicht sichtbaren innenflächen.
    Und da das alles unabhängig vom Uhrzeigersinn ist, geht das auch nicht so ohne weiteres mit glCullFace. 😞

    //Edit: @rapso: ty ... muss ich erstmal verarbeiten ^^



  • So mein Problem ist nun:
    WIe gesagt bestimme ich anhand der Normalen PRO VERTEX ob was gezeichnet werden soll.
    Beispiel Kugel:
    Damit die schön rund aussieht zeigen die normalen in die selbe richtung wie die einzelnen vertices vom Mittelpunkt aus.
    Folglich zeigen die Normalen von einem Face nicht in die selbe Richtung.
    Somit bekomme ich wundervolle Artefakte da bei Entsprechender Ansicht die eine Hälfte der Face gezeichnet wird, die andere jedoch nicht!!
    Wobei "nicht-zeichnen" bedeutet:

    gl_Position = vec4(0.0,0.0,0.0,0.0);

    im Vertex shader....
    Und soweit ich weiß besteht keine Möglichkeit dass der vertexshader sich merkt ob die vorherigen Vertices der selben Face bereits gezeichnet wurden, zudem kann ich auch nicht wissen ob in Zukunft noch Vertices gezeichnet werden!!!!!!

    Aber das Feature nur Polygone zu zeichnen die ich auch von vorne sehe benötige ich unbedingt.
    😞

    //Edit: Falls das was hilft:
    http://h.imagehost.org/0743/shaderbug.jpg



  • Wenn Du das unbedingt im Vertex-Shader machen moechtest, musst Du jedem Vertex die Flaechennormale mitgeben.
    Dadurch versechsfachst Du aber Deine Vertexmenge.
    Lass dass Culling also lieber von der Hardware erledigen.



  • hellihjb schrieb:

    Wenn Du das unbedingt im Vertex-Shader machen moechtest, musst Du jedem Vertex die Flaechennormale mitgeben.
    Dadurch versechsfachst Du aber Deine Vertexmenge.
    Lass dass Culling also lieber von der Hardware erledigen.

    Warum versechsfacht?
    Ausserdem habe ich doch sowieso pro vertex eine Normale. Nicht eine Normale pro face!



  • Du kannst im Vertex-Shader ja immer nur fuer einen Vertex entscheiden ob dieser auf 0 transformiert wird. Um ein Triangle zu entfernen, muessen *alle* zugehoerigen Vertices entfernt werden. Misch-Zustaende fuehren dazu, dass einzelne Vertices eines Polygons auf 0 transformiert werden und ist auch auf Deinem Screenshot zu sehen. Das Kriterium fuer's Culling muss also fuer alle Vertices eines Polygons gleich sein, also nimmt man die Face- und nicht die Vertex-Normale her.
    Auch rein logisch hat eine irgendwie gemittelte Vertex-Normale wenig mit dem Backface-Culling zu tun.

    Warum versechsfacht?

    Im idealisierten Durchschnitt hat ein Objekt circa doppelt so viele Dreiecke wie Vertices. So haettest Du aber gezwungenermassen drei unabhaengige Vertices pro Dreieck (daher Faktor 6).

    das Feature nur Polygone zu zeichnen die ich auch von vorne sehe benötige ich unbedingt.

    Dafuer ist das Backface-Culling da. Wenn Du das nicht nutzen kannst, ist Dein Ansatz irgendwo verkehrt.


Anmelden zum Antworten