Quaternions for the hp49/ hp50

Installation:
copy the library to the stack , then do 2 STO.
The library can be stored in eitherd port 0,1 or 2.
then do a warm start.


Quaternions can be conveniently displayed as 4D vectors on the HP calculator
This library include most standard functions together with symbolic handling
 of basic aritmetic and various conversion utilities.
When working symbolics set the calc in exact mode. Otherwise numeric mode is recommended.

credits:
Hans Milton for betatesting
Some references:
QuaternionsI.pdf, Tutorial, Louis Ibanez
Quaternions2.pdf, Tutorial, Louis Ibanez
Quaternions For TheMasses, , Harry J. Smith
Quaterions and their Applications to Rotation in 3D Space, Matt Gravelle
Museum of hpcalculators, Quaternion for hp cv41, has a nice manual.
Generally when doing web searches allow for some different spelling variation. 

For bug reports and suggestions , please send an email to gjermund_skailand@yahoo.no

Gjermund Skailand
2007-07-19


Summary 


Quaternions can be conveniently displayed as 4D vectors on the HP calculator


However it is more useful to consider quaternions e.g. as 
- scalar part and 3D vector
- extension of complex numbers, real part and three imaginary numbers each
- rotation vector, scalar is angle rotation about axis defined from 3D vector


Define 
a == a0 + i*a1 + j*a2 + k*a3 == [ a0, a1, a2, a3 ] == {a0, [a1,a2,a3]== {a0,av}
b ...

Unit quaternions are I=[ 1 0 0 0 ], i=[ 0 1 0 0 ], j=[ 0 0 1 0 ], k=[ 0 0 0 1 ]
Similar as for complex numbers: I^2 =1, i^2=-1, j^2=-1, k^2=-1
real part RE(a)= a0
vector or imaginary part (a) = [a1, a2,a3] = av

Scalar multiplication as for vectors
Length as for vectors = sqrt(dot(a,a)) 
Length as for complex numbers sqrt(conj(a) * a))
Addition as for vectors
Subtraction as for vectors
Negation as for vectors
Conjugate as for imaginary numbers, ie. Conj(a)={a0, -[a1, a2, a3]}=[a0, -a1, -a2, -a3]  
Multiplication is combination of complex multiplication and vector cross-product.
a*b= {a,av}*{b,bv}={a0*b0*- DOT(av,bv), a0*bv+b0*av+ CROSS(av,bv))
due to cross-product generally not commutative. 
Note as an exception a^n is commutative since cross-product is 0.
Inverse is similar as complex numbers inv(a)=conj(a)/(conj(a)*a)=conj(a)/length(a)^2 

Division is in *this* text defined similar as matrix division a/b = inv(b)*a, 
thus be careful when using division as it is ambiguous in most cases. 

Functions can generally be treated as an extension of complex functions. 
The library actually decompile and slightly modify the corresponding complex functions
already in ROM. Thus most calculations are carried out in extended precision of 15 digits.
If you have a quaterion with only one imaginary component, e.g [a,0, b,0] 
then all results shall be equal to the complex number (a,b), within +/-1 of last digit. 

Also, identities like sin(x)^2 + cos(x)^2 = 1 are valid both for real, imaginary and quaterions.
If my understanding is correct, then all identities built by functions (of one variable) 
which can expressed as power series will hold.
E.g. take power series for sin and cos , use quaternion instead of real or complex values.
 

Note a Quaternion can also be expressed as a complex 2x2 matrix, 
then the following applies for hp48 or hp49 calculator:

A= [[ (a0,a1) (a2,a3) ]
    [(-a2,a3) (a0,-a1)]]
then, 
	the number is in row 1.
	a*b == AxB  , matrix multiplication
	a/b == A/B  , matrix division
	a+b == A+B  
	a-b == A-B
	a*b*c== AxBxC
	conj(a)=[a0,-a1,-a2,-a3] == TRN(A)
	sxa==axs == sxA==Axs
	inv(a) = 1/X
length=	ABS(a)/sqrt(2)=sqrt((GET(TRN(A)*A),{1,1}))


Functions in the library:
- input are real numbers or real numeric vectors/arrays when otherwise not mentioned.
- basic functions can also be symbolic handled. Swith to exact mode and use symbolic 
 matrixes.
  These functions are indicated by (symbolic).
For one argument function, if input is symbolic, program will try symbolic computation.
For two argument function, if one of the inputs are symbolic, program will try symbolic 
computation. 

For intended real calculations, if you get error messages, change to numeric mode, 
and convert input to numeric arrays with e.g.  ->NUM 

A, B, C, D : complex 2D matrixes representations of a,b,c,d
L = length

V3 = [ v1,v2,v3 ]
L3 = length(V3) 
V3' = [ 0, V3],  V3 augmented with 0

s : scalar
c33 : matrix{3,3}


QMult (symbolic) 
- Quaterion multiplication and 
- scalar multiplication
qa qb -> qc
s qa ->  qb
qa s -> qb


Qdiv (symbolic)
Quaterion division
qa qb -> qc
NOte qa/qb defined as inv(qb)*qa, similar as for matrix divison on HPcalc.

Qadd (symbolic)
Quaterion addition
qa qb -> qc
similar as 4D vector addition on HPcalc

Qsub (symbolic)
Quaterion divsion
qa qb -> qc
similar as 4D vector subtraction on HPcalc

Qinv (symbolic)
Quaterion inverse
qa -> qc
qa*qc=qc*qa=1
Qinv(qa)=Qconj(qa)/(length(qa)^2) 


QVrot (symbolic)
Quaterion rotate
Qa V3 -> V3'
QVrot(qa)= ((V3')*qa)/qa= [(1/ABS(Qa)^2)*Qconj(qa')*(v3')*qa]
Note
 
- does not choose principal direction
- scales automatically Qa

Qconj (symbolic)
Quaterion conjugate
qa -> qb
{a0,av} -> {a0, -av}

Qsign (symbolic)
Quaterion unit value (normalized)
qa -> s

Qsq (symbolic)
Quaterion squared
qa -> qa*qa

Conversion utilities

Cmat (symbolic)
Quaterion to 3x3 direction cosine matrix (rotation matrix)
qa -> c33

Cmat->
3x3 cosine matrix to quaterion
c33 -> qa

Q->SV3
Quaterion split to scalar and 3d vector
qa -> q0 qv

SV3->Q
scalar and 3d vector to "augmented" quaterion
q0 qv -> qa

Q->rot
Quaterion to rotation vector (eigen angle, eigen vector) 
qa -> qb
note qa automatically scaled 


rot->Q
rotation vector to normalized quaterion
qa -> qb

Q->C22
Quaterion to complex 2x2 matrix reprentation


Qr->P
Quaterion rectangular (standard) to polar representation
A quaterion can be expressed as length and three angles
[a,b,c,d] -> [L,p,q,r]
L = length[a,b,c,d]
a= L* cos(p),
b= L*sin(p)*cos(q)
c= L*sin(p)*sin(q)cos(r)
d= L*sin(p)*sin(q)sin(r)

Qp->r
Quaterion polar to rectangular representation.
Reverse of Qr->p
Note all other funtions assume rectangular form

Emat
Euler angles (roll, pitch, yaw)  to Quaterion
r p y -> Qa
Note  
 - Emat is reverse of "rpt" 
 - Uses Deg/Rad/Grad setting for input
 - returns angles with   -90 < pitch < 90  
 - breakdown if  pitch +/- 90 degs
 
"rpt" (some greek letters)
Quaterion to euler angles (roll, pitch, yaw)
qa -> r p y 
Uses Deg/Rad/Grad setting for output
--------------------------

Qexp
Quaterion exponentiation
qa -> qa'

Qln
Quaterion logarithm
qa -> qa'
NOte  qa * qb is generally not equal to Qexp(Qln(a)+Qln(B)) as for real and complex variables.


sin,cos,tan,asin,acos,atan,sinh, cosh,tanh,asinh,acosh,atanh:
calculated as follows:

f(a)=f((a0,i*av)) equivalent to complex  re(f(a0, ib)) + im(f(a0,ib))*sign(av)
 where
b = length(av)
sign(av)=av/b

-------------------


Some equivalent notes:
Assume rotation qa, then qb, then qc, the following are equivalent:

= QVrot(qc,QVrot(qb,QVrot(qa,V3)))  
= Cmat(qc) x ( Cmat(qb) x ( Cmat(qa)  x V3))


= Cmat(qc) x Cmat(qb) x Cmat(qa)  x V3
= Cmat(qa*qb*qc) X V3
= QVrot((qa*qb*qc),V3)
-------------------------

matrix (multiplication) rotations stack on left, 
quaterions (multiplications) stack on right

The resulting eigen rotation and rotation axis 
 Q->rot(qa*qb*qc)

check: a=[ 1 -2 3 -4], b =[ 5 -1 -2 3 ], c=[ 3 -6 1 2]
v =['5/2' '15/2' '3*sqrt(26)/2']
[(32395-2184*sqrt(26))/5850 (5965+1092*sqrt(26))/1170) -((-14140+6513*sqrt(26))/5850]  
= (multiple precision)          [3.63397288587 9.85737547764 -3.25981437471 ] 
= (->NUM)                       [3.63397288586 9.85737547761 -3.2598143747 ] 
Using numeric mode
Q->rot(((a*b)*c),v):            [3.63397288586 9.85737547762 -3.25981437471 ], .25 sec  (4.8)
Cmat(((a*b)*c),v)*V:            [3.63397288586 9.85737547762 -3.25981437471 ], .21 sec (2.7)
Q->rot(c,Q->rot(b,Q->rot(a,v))):[3.63397288584 9.85737547758 -3.25981437468 ], .50 sec (17.8)
Cmat(c)*(Cmat(b)*(Cmat(a)*v))) :[3.63397288585 9.85737547767 -3.25981437469 ], .40 sec
(Cmat(c)*(Cmat(b)*(Cmat(a)))*v :[3.63397288585 9.85737547758 -3.2598143747  ], .47 sec (4.7)
Numbers in () refer to symbolic computation. Most of time is spent in CAS simplification.


