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

Aktuelle Zeit: Do Jul 10, 2025 22:50

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



Ein neues Thema erstellen Auf das Thema antworten  [ 8 Beiträge ] 
Autor Nachricht
 Betreff des Beitrags: Quaternion aus 2 Vektoren berechnen?
BeitragVerfasst: Mo Jun 02, 2008 17:52 
Offline
DGL Member
Benutzeravatar

Registriert: Di Dez 03, 2002 22:12
Beiträge: 2105
Wohnort: Vancouver, Canada
Programmiersprache: C++, Python
Hi,

ich muß aus zwei vektoren ein Quaternion berechnen, bzw genauergesagt:

Ich habe vektor A und B (beides richtungsvektoren).
Das Quaternion Q soll jetzt die rotation beschreiben um von A auf B zu kommen.

Beispiel:

A = (0, 1, 0)
B = (1, 0, 0)

Jetzt soll Q die rotation von A -> B darstellen, so das wenn ich Q auf A anwenden würde A == B wäre.

Ich hab das bisher immer einfach mit meiner Quaternionlib in Maya gemachjt, aber die kann ich leider nicht benutzen :(

Aya~


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mo Jun 02, 2008 19:26 
Offline
DGL Member
Benutzeravatar

Registriert: Di Okt 03, 2006 14:07
Beiträge: 1277
Wohnort: Wien
Mit einer einfachen Rechnung kann ich leider nicht dienen. Aber ich kann Dir Sourcecode aus meiner selbstgebastelten 3DMathUnit zur Verfügung stellen:

Das erste hat mit Quaternionen noch nichts zu tun, es berechnet lediglich die Rotation, wie man von einem Vektor zum anderen kommt; daher zunächst die Definition des Rotations-Records (das ist die Winkel/Achse-Repräsentation) und auch des Quaternions:

Code:
  1. TStdRotation = Record
  2.    Angle: TFloat32;
  3.    Vector: TStdVector4D; // sollte auch 3D möglich sein
  4. End;


Code:
  1. TStdQuaternion = Record
  2.    RealW,ImagX,ImagY,ImagZ: TFloat32;
  3. End;



Dann die Berechnung (die ist bei mir dauernd in Gebrauch, sollte daher OK sein), wie man Skalar- und Kreuzprodukt ausrechnet, weißt Du, nehm ich an:
Code:
  1. //********************************************************************
  2. // Calculates the rotation record between the two vectors
  3. // If the two vectors are equal or inverse the default axis is used
  4. // ATTENTION: no zerovectors allowed
  5. Function VectorRotation(FromVector,ToVector,
  6.                         DefaultAxis: TStdVector4D): TStdRotation;
  7. Begin
  8.    With Result Do Begin
  9.       Angle:= VectorAngle(FromVector,ToVector); // Skalarprodukt
  10.       Vector:= VectorAxis(FromVector,ToVector); // Kreuzprodukt
  11.       If IsNan(Vector.X) Then Vector:= DefaultAxis;
  12.    End;
  13. End;


Dann die Umrechnung von Winkel/Achse nach Quaternion samt Quelle, wo ich es herhabe:
Code:
  1. //********************************************************************
  2. Function RotationToQuaternion(ARotation: TStdRotation): TStdQuaternion;
  3. Var
  4.    CosHalfAngle,SinHalfAngle: TFloat32;
  5. Begin
  6.    With ARotation Do Begin
  7.       CosHalfAngle:= Cos(Angle/2*PiDiv180);
  8.       SinHalfAngle:= Sin(Angle/2*PiDiv180);
  9.  
  10.       With Result Do Begin
  11.          RealW:= CosHalfAngle;
  12.          ImagX:= Vector.X*SinHalfAngle;
  13.          ImagY:= Vector.Y*SinHalfAngle;
  14.          ImagZ:= Vector.Z*SinHalfAngle;
  15.       End;
  16.    End;
  17. End;
  18.  


Vermutlich kann man es kürzer auch rechnen. Da weiß ich aber über Quaternionen zu wenig Bescheid.
Traude


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mo Jun 02, 2008 19:39 
Offline
DGL Member

Registriert: Do Mai 30, 2002 18:48
Beiträge: 1617
Quaternionen bekommt man sehr leicht, wenn man die Rotationsachse und den Winkel kennt. Ist also im Prinzip ganz einfach. Die Rotationsachse steht senkrecht zur Ebene in der A und B liegen, sprich du rechnest (A kreuz B), normierst und kennst die Rotationsachse. Dann brauchst du noch sinus und cosinus des winkels von A nach B. Den Cosinus schenkt dir das Punktprodukt, den Sinus gibts aus den Umrechnungsformeln der trigonometrie und ein biserl denken - hab ich jetzt nicht gemacht :-) Irgendwann stand auch mal im Nachsitzen Tut ein Beispiel in dem Stand wie das geht, scheint aber leider verlorengegangen sein - also selber denken...

Dann musst Du daraus noch ein Quaternion basteln. Steht aber hier:
http://wiki.delphigl.com/index.php/Quat ... rien_auf_V

besodners die formel unter "Man kann Q sehr leicht zerlegen in:".
Oben noch schauen was V ist - aha die echten Quaternionen.
Klar?

Achso... Bemerk ich jetzt erst - Traude macht genau das :-)


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Di Jun 03, 2008 10:07 
Offline
DGL Member
Benutzeravatar

Registriert: Di Dez 03, 2002 22:12
Beiträge: 2105
Wohnort: Vancouver, Canada
Programmiersprache: C++, Python
Hi,

klappt leider nochnicht ganz :(

Ich brauch das ganze für ein Plugin für 3ds max.
Sagen wir ich habe einen würfel mit der höhe 5 der gerade auf dem boden steht.

Jetzt möchte ich das er auf den punkt [5,5,5] zeigt mit seiner spitze.

= mein From-Vektor ist [0,1,0].
und mein To-Vector ist [5,5,5] (normalisiert dann).

richtig?

Wenn ich das dann in die formeln oben einsetze und daraus ein Quaternion berechne, welches ich dann im 3ds max SDK dem würfel als rotations-wert zuweise, ist er nicht richtig rotiert.. :/ Also er zeigt nicht auf den punkt wo er eigentlich hinzeigen sollte :(

Hab ich da evlt nen denk fehler?

Aya~


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Di Jun 03, 2008 14:15 
Offline
DGL Member
Benutzeravatar

Registriert: Di Okt 03, 2006 14:07
Beiträge: 1277
Wohnort: Wien
Mir ist nicht ganz klar, was Du willst

Nehmen wir mal OpenGl-Verhältnisse an, und Du hast einen Würfel mit der Kantenlänge 5, und dessen Eckpunkte so benannt sind, wie im Bild unten.

Ich nehme mal OpenGl-Verhältnisse an, also ZPlus zeigt aus dem Bildschirm heraus auf Dich.

Du sagtest, der Würfel steht "am Boden". Ich nehme also einen Koordinatenursprung sagen wir mal im Punkt F an Der erste Vektor zeigt dann praktisch auf G, richtig? Der zweite Vektor würde dann auf C zeigen.

Die Drehung erfolgt dann in der Ebene, die durch das Dreieck FGC definiert wird Es sollte dann so aussehen, als ob er schräg nach vorne fallen würde.


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


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Di Jun 03, 2008 15:21 
Offline
DGL Member
Benutzeravatar

Registriert: So Jun 04, 2006 12:54
Beiträge: 263
um ein Quaternion zu bekommen welches die drehung eine vectors A zu einem zweitem B beschreibt ist ganz einfach:

Die dreh achse bekommt man mit hilfe des crossproduktes beider normalisierten vektoren. Um den cosinus des halbem winkels zu berechnen einfach das dot produkt zwischen einem der beiden normalisiertem vektor und dem normalisierten summe beider vektoren berechnen. Die richtung ist bereits in der richtung des vectors aus dem cross produktes enthalten. Nun diesen mit dem cos des winkels multiplizieren um die x,y und Z componente des quaterniosn zu erhalten, zum schluss noch mit dem pytagoras zum cos des winkels den sinus berechnen, der dann als Skalar anteil dient. Pseudo code:

A = normalize(A);
B = normalize(B);
vec3 d = normalize(cross(A,B)); //normlize hinzugefügt
float co = dot(normalize(A+B),A);
float si = sqrt(1.0 - co*co);
return vec4(d * si, co);

_________________
Lumina plattform unabhängige GLSL IDE


Zuletzt geändert von oc2k1 am Fr Jun 06, 2008 16:11, insgesamt 1-mal geändert.

Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Do Jun 05, 2008 16:08 
Offline
DGL Member

Registriert: Di Jun 06, 2006 09:59
Beiträge: 474
ist es Absicht dass du cross(A,B) nicht normierst?
Außerdem würde ich den skalaranteil x0 eher vorne als hinten schreiben.

_________________
Bild


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Fr Jun 06, 2008 16:10 
Offline
DGL Member
Benutzeravatar

Registriert: So Jun 04, 2006 12:54
Beiträge: 263
Stimmt da fehlt ein normalisieren. Bei GLSL macht es allerdings sinn den skalaranteil in der 4ten komponente zu specihern, da der vektor anteil sonst aus den komponenten yzw besteht, was noch verwirrender ist.

_________________
Lumina plattform unabhängige GLSL IDE


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 » Allgemein


Wer ist online?

Mitglieder in diesem Forum: 0 Mitglieder und 10 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 | 17 Queries | GZIP : On ]