2012-02-24 19 views
7

Sto facendo qualcosa in cui ho un piano in un coordinatore A con una serie di punti già presenti. Ho anche un vettore normale nello spazio N. Come posso ruotare i punti sulla coordinata A in modo che il piano sottostante abbia la stessa direzione normale di N?Rotazioni 3D di un piano

Chiedersi se qualcuno ha una buona idea su come farlo. Grazie

risposta

16

Se si dispone, o si può calcolare facilmente, il vettore normale sul piano in cui si trovano attualmente i punti, penso che il modo più semplice per farlo sarà quello di ruotare attorno all'asse comune ai due piani. Ecco come mi piacerebbe andare a questo proposito:

  1. Sia M essere il vettore normale al piano attuale, e N il vettore normale al piano da ruotare in. Se M == N puoi fermarti ora e lasciare invariati i punti originali.
  2. calcolare l'angolo di rotazione

    costheta = dot(M,N)/(norm(M)*norm(N)) 
    
  3. Calcolare l'asse di rotazione come

    axis = unitcross(M, N) 
    

    dove unitcross è una funzione che esegue il prodotto vettoriale e normalizza ad un vettore unitario, cioè unitcross(a, b) = cross(a, b)/norm(cross(a, b)). Come indicato da user1318499 in un commento, questo passaggio può causare un errore se M == N, a meno che l'implementazione di unitcross restituisca (0,0,0) quando a == b.

  4. Calcolare la matrice di rotazione dall'asse e angolo come

    c = costheta 
    s = sqrt(1-c*c) 
    C = 1-c 
    rmat = matrix([ x*x*C+c x*y*C-z*s x*z*C+y*s ], 
           [ y*x*C+z*s y*y*C+c y*z*C-x*s ] 
           [ z*x*C-y*s z*y*C+x*s z*z*C+c ]) 
    

    dove x, y, e z sono componenti axis. Questa formula è descritta on Wikipedia.

  5. Per ciascun punto, calcolare il punto corrispondente sulla nuovo piano come

    newpoint = dot(rmat, point) 
    

    dove la funzione dot esegue la moltiplicazione di matrici.

Questo non è univoco, ovviamente; come accennato nella risposta di peterk, ci sono un numero infinito di rotazioni possibili che potrebbero trasformare il piano normale in M nel piano normale a N. Ciò corrisponde al fatto che, dopo aver eseguito i passaggi sopra descritti, è possibile ruotare l'aereo attorno a N ei punti si troveranno in posizioni diverse pur rimanendo sullo stesso piano. (In altre parole, ogni rotazione che puoi fare per soddisfare le tue condizioni corrisponde a fare la procedura descritta sopra seguita da un'altra rotazione attorno allo N.) Ma se non ti interessa dove nell'aereo finiscono i tuoi punti, penso che questa rotazione intorno l'asse comune è il modo più semplice per ottenere solo i punti nel piano li volete a.


Se non si dispone di M, ma avete le coordinate dei punti nel vostro piano di partenza relativa a un'origine in quel piano, è possibile calcolare il vettore normale iniziale dalle posizioni di due punti x1 e x2 come

M = cross(x1, x2) 

(è anche possibile utilizzare unitcross qui ma non fa alcuna differenza). Se si dispone di punti coordinate relative ad un'origine che non è nel piano, si può ancora farlo, ma avrete bisogno di tre punti posizioni:

M = cross(x3-x1, x3-x2) 
+1

+1 buona risposta. L'unica lamentela (nella misura in cui sale al livello di una lamentela, che è discutibile) che ho è che non hai menzionato Quaternion Rotation come possibile alternativa ai passaggi 4 e 5. Sono un po 'più efficienti. – andand

+0

@andand: di solito sto facendo questo genere di cose analiticamente, quindi non ho completamente familiarità con i quaternioni. Ma se avrò tempo lo modifico. –

+1

Un buon sommario è su http://en.wikipedia.org/wiki/Quaternion_rotation – andand

0

Sto pensando di creare un vettore di unità [0,0,1] e utilizzare il prodotto di punti lungo due piani per trovare l'angolo di differenza e spostare tutti i punti di tali angoli. Questo presuppone che tu voglia che l'asse z si allinei con il vettore normale, altrimenti usa solo [1,0,0] o [0,1,0] per x e y rispettivamente.

+0

Non sarebbe questo allineare solo l'asse z ? ci saranno più Dof in x o y – bendervader

1

Un singolo vettore (normale - N) non sarà sufficiente. Avrai bisogno di altri due vettori per le altre due dimensioni. (Immagina che il tuo spazio 3D possa ancora ruotare/ruotare attorno al vettore normale, e hai bisogno di altri 2 vettori per inchiodarlo). Una volta che hai il normale e un altro sull'aereo, il terzo dovrebbe essere facile da trovare (destro o sinistro a seconda del tuo sistema).

Assicurarsi che tutti e tre siano normalizzati (lunghezza di 1) e metterli in una matrice; usa quella matrice per trasformare qualsiasi punto nel tuo spazio 3D (usa la moltiplicazione della matrice). Questo dovrebbe darti le nuove coordinate.

+0

Ha senso! Avrò bisogno di capire un modo per ottenere l'altro vettore: S Grazie! – bendervader

+2

-1: questa risposta è vaga e incompleta. – andand

Problemi correlati