Berechnung der Normalenvektoren



  • Ich möchte eine Art „Wasseroberfläche“ darstellen die 100x100 Vertices besitzt. Da ja eine Wasseroberfläche in den meisten Fälle nicht gerade stillsteht und sich verändert, müssen die Normalenvektoren bei jedem Render-Vorgang neu berechnet werden.
    Meine Lösungs-Idee war es dies mit Winkelberechnungen durchzuführen sprich SIN, COS, TAN. Dies hat dann auch den gewünschten Effekt erzielt, aber leider musste ich Festellen, dass die Berechnungen sehr viel Zeit in Anspruch nehmen.
    Jetzt seid ihr gefragt…

    Welcher Algorithmus eignet sich hierfür am besten?

    Schon mal Danke



  • Kreuzprodukt?

    Edit: Rechtsschreibung.



  • Shader



  • Mich interessiert mal deine formel, poste mal bitte!



  • Shader

    Wie würde es denn damit funktionieren?



  • Brutal :o

    Machs halt so:

    gegeben: Vector v1, v2
    Ergebnisvektor v3
    
    v3.vx=v1.vy*v2.vz-v1.vz*v2.vy
    v3.vy=v1.vz*v2.vx-v1.vx*v2.vz
    v3.vz=v1.vx*v2.vy-v1.vy*v2.vx
    

    hab ich ausm kopf gemacht, dürfte in etwa so sein.



  • @tggc: [OT]



  • randa schrieb:

    Brutal :o

    Machs halt so:

    gegeben: Vector v1, v2
    Ergebnisvektor v3
    
    v3.vx=v1.vy*v2.vz-v1.vz*v2.vy
    v3.vy=v1.vz*v2.vx-v1.vx*v2.vz
    v3.vz=v1.vx*v2.vy-v1.vy*v2.vx
    

    hab ich ausm kopf gemacht, dürfte in etwa so sein.

    was sind denn v1/v2? der alte und der neue vertex?



  • otze schrieb:

    was sind denn v1/v2? der alte und der neue vertex?

    Da steht doch Vector, nicht Vertex.
    Da stehts doch: v1, v2 sind die benötigten vektoren, v3 ist der normalvektor der rauskommt.



  • sorry vertan mit vector/vertex
    aber was sind die benötigten vectoren? die alte und die neue position?



  • Bitte lesen. Danke.

    Bye, TGGC (Reden wie die Großen)



  • otze schrieb:

    sorry vertan mit vector/vertex
    aber was sind die benötigten vectoren? die alte und die neue position?

    😃
    Da gibts nix mit alt und neu. Eine normale baust du auf zwei vorhandenen (und mindestens zwei) Vektoren auf. Diese stellen eine ebene dar, und davon ausgehend berechnest du die normale, die im 90° Winkel zur ebene steht.

    Du weisst scheinbar nicht was vektoren/normalen sind also solltest du vielleicht googeln 😉



  • randa schrieb:

    Du weisst scheinbar nicht was vektoren/normalen sind also solltest du vielleicht googeln 😉

    Ich bin mir sicher otze weiß was das ist... 🙄 🙂



  • also doch den ebenennormalvector berechnen, sagt das doch gleich^^
    wobei man dann doch mindestens 3 punkte brauch weil die ebene doch nur mit 3 punkten sicher berechnet werden kann oder?



  • jepp, aber zwei Vektoren reichen auch aus. Wenn du zum beispiel zwei Kanten an einer ecke eines Tisches nimmst, reicht das um die ebene des tisches zu bestimmen. die kanten kannst du dir auch als vektoren denken. Die Vektoren können beliebig ausgerichtet sein, nur nicht kollinear.



  • randa schrieb:

    Brutal :o

    Machs halt so:

    gegeben: Vector v1, v2
    Ergebnisvektor v3
    
    v3.vx=v1.vy*v2.vz-v1.vz*v2.vy
    v3.vy=v1.vz*v2.vx-v1.vx*v2.vz
    v3.vz=v1.vx*v2.vy-v1.vy*v2.vx
    

    hab ich ausm kopf gemacht, dürfte in etwa so sein.

    Hmm, der Normalenvektor müsste jetzt aber noch normiert werden.

    Außerdem wird das nicht sonderlich hübsch aussehen, weil der Normalenvektor
    ja zu einem Punkt gehört und nicht zu einer Ebene, d.h. eigentlich
    müsste er die Normalen aller an den Punkt angrenzenden Ebenen bestimmen
    und daraus den Mittelwert bilden!

    d.h pro Punkt: 8x Kreuzprodukt + 9x Vektor normieren

    Ich würde empfehlen, entweder die Animation vorzuberechnen oder aber wie
    bereits gesagt wurde Shader zu benutzen.

    Viele Grüße
    Fischi



  • in einem Regelmässigen Gitter kann man aber auch gradienten berechnen indem man es einfach wie ein Rasterbild behandelt.
    man approximiert einfach die neun Punkte mit einer ebene
    a*x+b*y+c=z;
    Gradient in x=a und in y=b

    [g1][g2][g3]
      [g4][g5][g6]
      [g7][g8][g9]
    
      rx= -g1-g4-g7+g3+g5+g9
      ry= -g1-g2-g3+g7+g8+g9
      n= rx X ry;
    


  • Das ist nun der neue Code mit dem Kreuzprodukt:

    D3DXVECTOR3 v1;
    D3DXVECTOR3 v2;
    float laenge;
    
    // m_Vertices[m_EffectCountX][m_EffectCountZ]
    Vertices = m_Vertices + m_EffectCountZ + 1;
    for(x = 1; x < m_EffectCountX - 1; x++)
    {
    	for(z = 1; z < m_EffectCountZ - 1; z++)
    	{
    		v1 = D3DXVECTOR3(
    			(Vertices + 1)->X - Vertices->X,
    			(Vertices + 1)->Y - Vertices->Y,
    			(Vertices + 1)->Z - Vertices->Z);
    
    		v2 = D3DXVECTOR3(
    			(Vertices + m_EffectCountZ)->X - Vertices->X,
    			(Vertices + m_EffectCountZ)->Y - Vertices->Y,
    			(Vertices + m_EffectCountZ)->Z - Vertices->Z);
    
    		Vertices->nX = (v1.y * v2.z) - (v1.z * v2.y);
    		Vertices->nY = (v1.z * v2.x) - (v1.x * v2.z);
    		Vertices->nZ = (v1.x * v2.y) - (v1.y * v2.x);
    
    		laenge =
    			sqrtf(powf(Vertices->nX,2) +
    			powf(Vertices->nY,2) +
    			powf(Vertices->nZ,2));
    
    		Vertices->nX /= laenge;
    		Vertices->nY /= laenge;
    		Vertices->nZ /= laenge;
    
    		Vertices++;
    	}
    	Vertices += 2;
    }
    

    Ja klappt nun alles... bin euch echt dankbar



  • Welche Optimierungen könnte man denn an diesem Code durchführen, um die Geschwindigkeit zu verbessern?


  • Mod

    Anfaenger2003 schrieb:

    Welche Optimierungen könnte man denn an diesem Code durchführen, um die Geschwindigkeit zu verbessern?

    nur einmal bei der initialisierung durchführen und dann nie wieder.

    rapso->greets();



  • normierung ist unnötig


Anmelden zum Antworten