@ -43,11 +43,17 @@ struct IF<true, L, R> { typedef L type; };
# define LINEAR_AXIS_CODE(V...) CODE_N(LINEAR_AXES, V)
# define LINEAR_AXIS_LIST(V...) LIST_N(LINEAR_AXES, V)
# define LINEAR_AXIS_ARRAY(V...) { LINEAR_AXIS_LIST(V) }
# define LINEAR_AXIS_ARGS(T...) LINEAR_AXIS_LIST(T x, T y, T z, T i, T j, T k)
# define LINEAR_AXIS_ELEM(O) LINEAR_AXIS_LIST(O.x, O.y, O.z, O.i, O.j, O.k)
# define LINEAR_AXIS_DEFS(T,V) LINEAR_AXIS_LIST(T x=V, T y=V, T z=V, T i=V, T j=V, T k=V)
# define LOGICAL_AXIS_GANG(E,V...) LINEAR_AXIS_GANG(V) GANG_ITEM_E(E)
# define LOGICAL_AXIS_CODE(E,V...) LINEAR_AXIS_CODE(V) CODE_ITEM_E(E)
# define LOGICAL_AXIS_LIST(E,V...) LINEAR_AXIS_LIST(V) LIST_ITEM_E(E)
# define LOGICAL_AXIS_ARRAY(E,V...) { LOGICAL_AXIS_LIST(E,V) }
# define LOGICAL_AXIS_ARGS(T...) LOGICAL_AXIS_LIST(T e, T x, T y, T z, T i, T j, T k)
# define LOGICAL_AXIS_ELEM(O) LOGICAL_AXIS_LIST(O.e, O.x, O.y, O.z, O.i, O.j, O.k)
# define LOGICAL_AXIS_DECL(T,V) LOGICAL_AXIS_LIST(T e=V, T x=V, T y=V, T z=V, T i=V, T j=V, T k=V)
# if HAS_EXTRUDERS
# define LIST_ITEM_E(N) , N
@ -69,37 +75,37 @@ struct IF<true, L, R> { typedef L type; };
enum AxisEnum : uint8_t {
// Linear axes may be controlled directly or indirectly
LINEAR_AXIS_LIST ( X_AXIS , Y_AXIS , Z_AXIS ) ,
LINEAR_AXIS_LIST ( X_AXIS , Y_AXIS , Z_AXIS , I_AXIS , J_AXIS , K_AXIS )
// Extruder axes may be considered distinctly
# define _EN_ITEM(N) E##N##_AXIS,
# define _EN_ITEM(N) , E##N##_AXIS
REPEAT ( EXTRUDERS , _EN_ITEM )
# undef _EN_ITEM
// Core also keeps toolhead directions
# if IS_CORE
X_HEAD , Y_HEAD , Z_HEAD ,
, X_HEAD , Y_HEAD , Z_HEAD
# endif
// Distinct axes, including all E and Core
NUM_AXIS_ENUMS ,
, NUM_AXIS_ENUMS
// Most of the time we refer only to the single E_AXIS
# if HAS_EXTRUDERS
E_AXIS = E0_AXIS ,
, E_AXIS = E0_AXIS
# endif
// A, B, and C are for DELTA, SCARA, etc.
A_AXIS = X_AXIS ,
, A_AXIS = X_AXIS
# if LINEAR_AXES >= 2
B_AXIS = Y_AXIS ,
, B_AXIS = Y_AXIS
# endif
# if LINEAR_AXES >= 3
C_AXIS = Z_AXIS ,
, C_AXIS = Z_AXIS
# endif
// To refer to all or none
ALL_AXES_ENUM = 0xFE , NO_AXIS_ENUM = 0xFF
, ALL_AXES_ENUM = 0xFE , NO_AXIS_ENUM = 0xFF
} ;
typedef IF < ( NUM_AXIS_ENUMS > 8 ) , uint16_t , uint8_t > : : type axis_bits_t ;
@ -241,9 +247,16 @@ struct XYval {
struct { T a , b ; } ;
T pos [ 2 ] ;
} ;
// Set all to 0
FI void reset ( ) { x = y = 0 ; }
// Setters taking struct types and arrays
FI void set ( const T px ) { x = px ; }
FI void set ( const T px , const T py ) { x = px ; y = py ; }
FI void set ( const T ( & arr ) [ XY ] ) { x = arr [ 0 ] ; y = arr [ 1 ] ; }
# if HAS_Y_AXIS
FI void set ( const T px , const T py ) { x = px ; y = py ; }
FI void set ( const T ( & arr ) [ XY ] ) { x = arr [ 0 ] ; y = arr [ 1 ] ; }
# endif
# if LINEAR_AXES > XY
FI void set ( const T ( & arr ) [ LINEAR_AXES ] ) { x = arr [ 0 ] ; y = arr [ 1 ] ; }
# endif
@ -253,10 +266,15 @@ struct XYval {
FI void set ( const T ( & arr ) [ DISTINCT_AXES ] ) { x = arr [ 0 ] ; y = arr [ 1 ] ; }
# endif
# endif
FI void reset ( ) { x = y = 0 ; }
// Length reduced to one dimension
FI T magnitude ( ) const { return ( T ) sqrtf ( x * x + y * y ) ; }
// Pointer to the data as a simple array
FI operator T * ( ) { return pos ; }
// If any element is true then it's true
FI operator bool ( ) { return x | | y ; }
// Explicit copy and copies with conversion
FI XYval < T > copy ( ) const { return * this ; }
FI XYval < T > ABS ( ) const { return { T ( _ABS ( x ) ) , T ( _ABS ( y ) ) } ; }
FI XYval < int16_t > asInt ( ) { return { int16_t ( x ) , int16_t ( y ) } ; }
@ -268,17 +286,27 @@ struct XYval {
FI XYval < float > asFloat ( ) { return { static_cast < float > ( x ) , static_cast < float > ( y ) } ; }
FI XYval < float > asFloat ( ) const { return { static_cast < float > ( x ) , static_cast < float > ( y ) } ; }
FI XYval < float > reciprocal ( ) const { return { _RECIP ( x ) , _RECIP ( y ) } ; }
// Marlin workspace shifting is done with G92 and M206
FI XYval < float > asLogical ( ) const { XYval < float > o = asFloat ( ) ; toLogical ( o ) ; return o ; }
FI XYval < float > asNative ( ) const { XYval < float > o = asFloat ( ) ; toNative ( o ) ; return o ; }
// Cast to a type with more fields by making a new object
FI operator XYZval < T > ( ) { return { x , y } ; }
FI operator XYZval < T > ( ) const { return { x , y } ; }
FI operator XYZEval < T > ( ) { return { x , y } ; }
FI operator XYZEval < T > ( ) const { return { x , y } ; }
// Accessor via an AxisEnum (or any integer) [index]
FI T & operator [ ] ( const int n ) { return pos [ n ] ; }
FI const T & operator [ ] ( const int n ) const { return pos [ n ] ; }
// Assignment operator overrides do the expected thing
FI XYval < T > & operator = ( const T v ) { set ( v , v ) ; return * this ; }
FI XYval < T > & operator = ( const XYZval < T > & rs ) { set ( rs . x , rs . y ) ; return * this ; }
FI XYval < T > & operator = ( const XYZEval < T > & rs ) { set ( rs . x , rs . y ) ; return * this ; }
// Override other operators to get intuitive behaviors
FI XYval < T > operator + ( const XYval < T > & rs ) const { XYval < T > ls = * this ; ls . x + = rs . x ; ls . y + = rs . y ; return ls ; }
FI XYval < T > operator + ( const XYval < T > & rs ) { XYval < T > ls = * this ; ls . x + = rs . x ; ls . y + = rs . y ; return ls ; }
FI XYval < T > operator - ( const XYval < T > & rs ) const { XYval < T > ls = * this ; ls . x - = rs . x ; ls . y - = rs . y ; return ls ; }
@ -315,6 +343,10 @@ struct XYval {
FI XYval < T > operator > > ( const int & v ) { XYval < T > ls = * this ; _RS ( ls . x ) ; _RS ( ls . y ) ; return ls ; }
FI XYval < T > operator < < ( const int & v ) const { XYval < T > ls = * this ; _LS ( ls . x ) ; _LS ( ls . y ) ; return ls ; }
FI XYval < T > operator < < ( const int & v ) { XYval < T > ls = * this ; _LS ( ls . x ) ; _LS ( ls . y ) ; return ls ; }
FI const XYval < T > operator - ( ) const { XYval < T > o = * this ; o . x = - x ; o . y = - y ; return o ; }
FI XYval < T > operator - ( ) { XYval < T > o = * this ; o . x = - x ; o . y = - y ; return o ; }
// Modifier operators
FI XYval < T > & operator + = ( const XYval < T > & rs ) { x + = rs . x ; y + = rs . y ; return * this ; }
FI XYval < T > & operator - = ( const XYval < T > & rs ) { x - = rs . x ; y - = rs . y ; return * this ; }
FI XYval < T > & operator * = ( const XYval < T > & rs ) { x * = rs . x ; y * = rs . y ; return * this ; }
@ -328,6 +360,8 @@ struct XYval {
FI XYval < T > & operator * = ( const int & v ) { x * = v ; y * = v ; return * this ; }
FI XYval < T > & operator > > = ( const int & v ) { _RS ( x ) ; _RS ( y ) ; return * this ; }
FI XYval < T > & operator < < = ( const int & v ) { _LS ( x ) ; _LS ( y ) ; return * this ; }
// Exact comparisons. For floats a "NEAR" operation may be better.
FI bool operator = = ( const XYval < T > & rs ) { return x = = rs . x & & y = = rs . y ; }
FI bool operator = = ( const XYZval < T > & rs ) { return x = = rs . x & & y = = rs . y ; }
FI bool operator = = ( const XYZEval < T > & rs ) { return x = = rs . x & & y = = rs . y ; }
@ -340,8 +374,6 @@ struct XYval {
FI bool operator ! = ( const XYval < T > & rs ) const { return ! operator = = ( rs ) ; }
FI bool operator ! = ( const XYZval < T > & rs ) const { return ! operator = = ( rs ) ; }
FI bool operator ! = ( const XYZEval < T > & rs ) const { return ! operator = = ( rs ) ; }
FI XYval < T > operator - ( ) { XYval < T > o = * this ; o . x = - x ; o . y = - y ; return o ; }
FI const XYval < T > operator - ( ) const { XYval < T > o = * this ; o . x = - x ; o . y = - y ; return o ; }
} ;
//
@ -350,111 +382,144 @@ struct XYval {
template < typename T >
struct XYZval {
union {
struct { T LINEAR_AXIS_LIST ( x , y , z ) ; } ;
struct { T LINEAR_AXIS_LIST ( a , b , c ) ; } ;
struct { T LINEAR_AXIS_ARGS ( ) ; } ;
struct { T LINEAR_AXIS_LIST ( a , b , c , u , v , w ) ; } ;
T pos [ LINEAR_AXES ] ;
} ;
// Set all to 0
FI void reset ( ) { LINEAR_AXIS_GANG ( x = , y = , z = , i = , j = , k = ) 0 ; }
// Setters taking struct types and arrays
FI void set ( const T px ) { x = px ; }
FI void set ( const T px , const T py ) { x = px ; y = py ; }
FI void set ( const XYval < T > pxy ) { x = pxy . x ; y = pxy . y ; }
FI void set ( const XYval < T > pxy , const T pz ) { x = pxy . x ; y = pxy . y ; z = pz ; }
FI void set ( const XYval < T > pxy , const T pz ) { LINEAR_AXIS_CODE ( x = pxy . x , y = pxy . y , z = pz , NOOP , NOOP , NOOP ) ; }
FI void set ( const T ( & arr ) [ XY ] ) { x = arr [ 0 ] ; y = arr [ 1 ] ; }
FI void set ( const T ( & arr ) [ LINEAR_AXES ] ) { LINEAR_AXIS_CODE ( x = arr [ 0 ] , y = arr [ 1 ] , z = arr [ 2 ] ) ; }
# if HAS_Z_AXIS
FI void set ( LINEAR_AXIS_LIST ( const T px , const T py , const T pz ) )
{ LINEAR_AXIS_CODE ( x = px , y = py , z = pz ) ; }
FI void set ( const T ( & arr ) [ LINEAR_AXES ] ) { LINEAR_AXIS_CODE ( x = arr [ 0 ] , y = arr [ 1 ] , z = arr [ 2 ] , i = arr [ 3 ] , j = arr [ 4 ] , k = arr [ 5 ] ) ; }
FI void set ( LINEAR_AXIS_ARGS ( const T ) ) { LINEAR_AXIS_CODE ( a = x , b = y , c = z , u = i , v = j , w = k ) ; }
# endif
# if LOGICAL_AXES > LINEAR_AXES
FI void set ( const T ( & arr ) [ LOGICAL_AXES ] ) { LINEAR_AXIS_CODE ( x = arr [ 0 ] , y = arr [ 1 ] , z = arr [ 2 ] ) ; }
FI void set ( LOGICAL_AXIS_LIST ( const T , const T px , const T py , const T pz ) )
{ LINEAR_AXIS_CODE ( x = px , y = py , z = pz ) ; }
FI void set ( const T ( & arr ) [ LOGICAL_AXES ] ) { LINEAR_AXIS_CODE ( x = arr [ 0 ] , y = arr [ 1 ] , z = arr [ 2 ] , i = arr [ 3 ] , j = arr [ 4 ] , k = arr [ 5 ] ) ; }
FI void set ( LOGICAL_AXIS_ARGS ( const T ) ) { LINEAR_AXIS_CODE ( a = x , b = y , c = z , u = i , v = j , w = k ) ; }
# if DISTINCT_AXES > LOGICAL_AXES
FI void set ( const T ( & arr ) [ DISTINCT_AXES ] ) { LINEAR_AXIS_CODE ( x = arr [ 0 ] , y = arr [ 1 ] , z = arr [ 2 ] ) ; }
FI void set ( const T ( & arr ) [ DISTINCT_AXES ] ) { LINEAR_AXIS_CODE ( x = arr [ 0 ] , y = arr [ 1 ] , z = arr [ 2 ] , i = arr [ 3 ] , j = arr [ 4 ] , k = arr [ 5 ] ) ; }
# endif
# endif
FI void reset ( ) { LINEAR_AXIS_GANG ( x = , y = , z = ) 0 ; }
FI T magnitude ( ) const { return ( T ) sqrtf ( LINEAR_AXIS_GANG ( x * x , + y * y , + z * z ) ) ; }
# if LINEAR_AXES >= 4
FI void set ( const T px , const T py , const T pz ) { x = px ; y = py ; z = pz ; }
# endif
# if LINEAR_AXES >= 5
FI void set ( const T px , const T py , const T pz , const T pi ) { x = px ; y = py ; z = pz ; i = pi ; }
# endif
# if LINEAR_AXES >= 6
FI void set ( const T px , const T py , const T pz , const T pi , const T pj ) { x = px ; y = py ; z = pz ; i = pi ; j = pj ; }
# endif
// Length reduced to one dimension
FI T magnitude ( ) const { return ( T ) sqrtf ( LINEAR_AXIS_GANG ( x * x , + y * y , + z * z , + i * i , + j * j , + k * k ) ) ; }
// Pointer to the data as a simple array
FI operator T * ( ) { return pos ; }
FI operator bool ( ) { return LINEAR_AXIS_GANG ( z , | | x , | | y ) ; }
// If any element is true then it's true
FI operator bool ( ) { return LINEAR_AXIS_GANG ( x , | | y , | | z , | | i , | | j , | | k ) ; }
// Explicit copy and copies with conversion
FI XYZval < T > copy ( ) const { XYZval < T > o = * this ; return o ; }
FI XYZval < T > ABS ( ) const { return LINEAR_AXIS_ARRAY ( T ( _ABS ( x ) ) , T ( _ABS ( y ) ) , T ( _ABS ( z ) ) ) ; }
FI XYZval < int16_t > asInt ( ) { return LINEAR_AXIS_ARRAY ( int16_t ( x ) , int16_t ( y ) , int16_t ( z ) ) ; }
FI XYZval < int16_t > asInt ( ) const { return LINEAR_AXIS_ARRAY ( int16_t ( x ) , int16_t ( y ) , int16_t ( z ) ) ; }
FI XYZval < int32_t > asLong ( ) { return LINEAR_AXIS_ARRAY ( int32_t ( x ) , int32_t ( y ) , int32_t ( z ) ) ; }
FI XYZval < int32_t > asLong ( ) const { return LINEAR_AXIS_ARRAY ( int32_t ( x ) , int32_t ( y ) , int32_t ( z ) ) ; }
FI XYZval < int32_t > ROUNDL ( ) { return LINEAR_AXIS_ARRAY ( int32_t ( LROUND ( x ) ) , int32_t ( LROUND ( y ) ) , int32_t ( LROUND ( z ) ) ) ; }
FI XYZval < int32_t > ROUNDL ( ) const { return LINEAR_AXIS_ARRAY ( int32_t ( LROUND ( x ) ) , int32_t ( LROUND ( y ) ) , int32_t ( LROUND ( z ) ) ) ; }
FI XYZval < float > asFloat ( ) { return LINEAR_AXIS_ARRAY ( static_cast < float > ( x ) , static_cast < float > ( y ) , static_cast < float > ( z ) ) ; }
FI XYZval < float > asFloat ( ) const { return LINEAR_AXIS_ARRAY ( static_cast < float > ( x ) , static_cast < float > ( y ) , static_cast < float > ( z ) ) ; }
FI XYZval < float > reciprocal ( ) const { return LINEAR_AXIS_ARRAY ( _RECIP ( x ) , _RECIP ( y ) , _RECIP ( z ) ) ; }
FI XYZval < T > ABS ( ) const { return LINEAR_AXIS_ARRAY ( T ( _ABS ( x ) ) , T ( _ABS ( y ) ) , T ( _ABS ( z ) ) , T ( _ABS ( i ) ) , T ( _ABS ( j ) ) , T ( _ABS ( k ) ) ) ; }
FI XYZval < int16_t > asInt ( ) { return LINEAR_AXIS_ARRAY ( int16_t ( x ) , int16_t ( y ) , int16_t ( z ) , int16_t ( i ) , int16_t ( j ) , int16_t ( k ) ) ; }
FI XYZval < int16_t > asInt ( ) const { return LINEAR_AXIS_ARRAY ( int16_t ( x ) , int16_t ( y ) , int16_t ( z ) , int16_t ( i ) , int16_t ( j ) , int16_t ( k ) ) ; }
FI XYZval < int32_t > asLong ( ) { return LINEAR_AXIS_ARRAY ( int32_t ( x ) , int32_t ( y ) , int32_t ( z ) , int32_t ( i ) , int32_t ( j ) , int32_t ( k ) ) ; }
FI XYZval < int32_t > asLong ( ) const { return LINEAR_AXIS_ARRAY ( int32_t ( x ) , int32_t ( y ) , int32_t ( z ) , int32_t ( i ) , int32_t ( j ) , int32_t ( k ) ) ; }
FI XYZval < int32_t > ROUNDL ( ) { return LINEAR_AXIS_ARRAY ( int32_t ( LROUND ( x ) ) , int32_t ( LROUND ( y ) ) , int32_t ( LROUND ( z ) ) , int32_t ( LROUND ( i ) ) , int32_t ( LROUND ( j ) ) , int32_t ( LROUND ( k ) ) ) ; }
FI XYZval < int32_t > ROUNDL ( ) const { return LINEAR_AXIS_ARRAY ( int32_t ( LROUND ( x ) ) , int32_t ( LROUND ( y ) ) , int32_t ( LROUND ( z ) ) , int32_t ( LROUND ( i ) ) , int32_t ( LROUND ( j ) ) , int32_t ( LROUND ( k ) ) ) ; }
FI XYZval < float > asFloat ( ) { return LINEAR_AXIS_ARRAY ( static_cast < float > ( x ) , static_cast < float > ( y ) , static_cast < float > ( z ) , static_cast < float > ( i ) , static_cast < float > ( j ) , static_cast < float > ( k ) ) ; }
FI XYZval < float > asFloat ( ) const { return LINEAR_AXIS_ARRAY ( static_cast < float > ( x ) , static_cast < float > ( y ) , static_cast < float > ( z ) , static_cast < float > ( i ) , static_cast < float > ( j ) , static_cast < float > ( k ) ) ; }
FI XYZval < float > reciprocal ( ) const { return LINEAR_AXIS_ARRAY ( _RECIP ( x ) , _RECIP ( y ) , _RECIP ( z ) , _RECIP ( i ) , _RECIP ( j ) , _RECIP ( k ) ) ; }
// Marlin workspace shifting is done with G92 and M206
FI XYZval < float > asLogical ( ) const { XYZval < float > o = asFloat ( ) ; toLogical ( o ) ; return o ; }
FI XYZval < float > asNative ( ) const { XYZval < float > o = asFloat ( ) ; toNative ( o ) ; return o ; }
// In-place cast to types having fewer fields
FI operator XYval < T > & ( ) { return * ( XYval < T > * ) this ; }
FI operator const XYval < T > & ( ) const { return * ( const XYval < T > * ) this ; }
FI operator XYZEval < T > ( ) const { return LINEAR_AXIS_ARRAY ( x , y , z ) ; }
// Cast to a type with more fields by making a new object
FI operator XYZEval < T > ( ) const { return LINEAR_AXIS_ARRAY ( x , y , z , i , j , k ) ; }
// Accessor via an AxisEnum (or any integer) [index]
FI T & operator [ ] ( const int n ) { return pos [ n ] ; }
FI const T & operator [ ] ( const int n ) const { return pos [ n ] ; }
// Assignment operator overrides do the expected thing
FI XYZval < T > & operator = ( const T v ) { set ( ARRAY_N_1 ( LINEAR_AXES , v ) ) ; return * this ; }
FI XYZval < T > & operator = ( const XYval < T > & rs ) { set ( rs . x , rs . y ) ; return * this ; }
FI XYZval < T > & operator = ( const XYZEval < T > & rs ) { set ( LINEAR_AXIS_LIST ( rs . x , rs . y , rs . z ) ) ; return * this ; }
FI XYZval < T > operator + ( const XYval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , NOOP ) ; return ls ; }
FI XYZval < T > operator + ( const XYval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , NOOP ) ; return ls ; }
FI XYZval < T > operator - ( const XYval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , NOOP ) ; return ls ; }
FI XYZval < T > operator - ( const XYval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , NOOP ) ; return ls ; }
FI XYZval < T > operator * ( const XYval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , NOOP ) ; return ls ; }
FI XYZval < T > operator * ( const XYval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , NOOP ) ; return ls ; }
FI XYZval < T > operator / ( const XYval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , NOOP ) ; return ls ; }
FI XYZval < T > operator / ( const XYval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , NOOP ) ; return ls ; }
FI XYZval < T > operator + ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z ) ; return ls ; }
FI XYZval < T > operator + ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z ) ; return ls ; }
FI XYZval < T > operator - ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z ) ; return ls ; }
FI XYZval < T > operator - ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z ) ; return ls ; }
FI XYZval < T > operator * ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z ) ; return ls ; }
FI XYZval < T > operator * ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z ) ; return ls ; }
FI XYZval < T > operator / ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z ) ; return ls ; }
FI XYZval < T > operator / ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z ) ; return ls ; }
FI XYZval < T > operator + ( const XYZEval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z ) ; return ls ; }
FI XYZval < T > operator + ( const XYZEval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z ) ; return ls ; }
FI XYZval < T > operator - ( const XYZEval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z ) ; return ls ; }
FI XYZval < T > operator - ( const XYZEval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z ) ; return ls ; }
FI XYZval < T > operator * ( const XYZEval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z ) ; return ls ; }
FI XYZval < T > operator * ( const XYZEval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z ) ; return ls ; }
FI XYZval < T > operator / ( const XYZEval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z ) ; return ls ; }
FI XYZval < T > operator / ( const XYZEval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z ) ; return ls ; }
FI XYZval < T > operator * ( const float & v ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = v , ls . y * = v , ls . z * = v ) ; return ls ; }
FI XYZval < T > operator * ( const float & v ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = v , ls . y * = v , ls . z * = v ) ; return ls ; }
FI XYZval < T > operator * ( const int & v ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = v , ls . y * = v , ls . z * = v ) ; return ls ; }
FI XYZval < T > operator * ( const int & v ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = v , ls . y * = v , ls . z * = v ) ; return ls ; }
FI XYZval < T > operator / ( const float & v ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = v , ls . y / = v , ls . z / = v ) ; return ls ; }
FI XYZval < T > operator / ( const float & v ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = v , ls . y / = v , ls . z / = v ) ; return ls ; }
FI XYZval < T > operator / ( const int & v ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = v , ls . y / = v , ls . z / = v ) ; return ls ; }
FI XYZval < T > operator / ( const int & v ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = v , ls . y / = v , ls . z / = v ) ; return ls ; }
FI XYZval < T > operator > > ( const int & v ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( _RS ( ls . x ) , _RS ( ls . y ) , _RS ( ls . z ) ) ; return ls ; }
FI XYZval < T > operator > > ( const int & v ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( _RS ( ls . x ) , _RS ( ls . y ) , _RS ( ls . z ) ) ; return ls ; }
FI XYZval < T > operator < < ( const int & v ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( _LS ( ls . x ) , _LS ( ls . y ) , _LS ( ls . z ) ) ; return ls ; }
FI XYZval < T > operator < < ( const int & v ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( _LS ( ls . x ) , _LS ( ls . y ) , _LS ( ls . z ) ) ; return ls ; }
FI XYZval < T > & operator + = ( const XYval < T > & rs ) { LINEAR_AXIS_CODE ( x + = rs . x , y + = rs . y , NOOP ) ; return * this ; }
FI XYZval < T > & operator - = ( const XYval < T > & rs ) { LINEAR_AXIS_CODE ( x - = rs . x , y - = rs . y , NOOP ) ; return * this ; }
FI XYZval < T > & operator * = ( const XYval < T > & rs ) { LINEAR_AXIS_CODE ( x * = rs . x , y * = rs . y , NOOP ) ; return * this ; }
FI XYZval < T > & operator / = ( const XYval < T > & rs ) { LINEAR_AXIS_CODE ( x / = rs . x , y / = rs . y , NOOP ) ; return * this ; }
FI XYZval < T > & operator + = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x + = rs . x , y + = rs . y , z + = rs . z ) ; return * this ; }
FI XYZval < T > & operator - = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x - = rs . x , y - = rs . y , z - = rs . z ) ; return * this ; }
FI XYZval < T > & operator * = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x * = rs . x , y * = rs . y , z * = rs . z ) ; return * this ; }
FI XYZval < T > & operator / = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x / = rs . x , y / = rs . y , z / = rs . z ) ; return * this ; }
FI XYZval < T > & operator + = ( const XYZEval < T > & rs ) { LINEAR_AXIS_CODE ( x + = rs . x , y + = rs . y , z + = rs . z ) ; return * this ; }
FI XYZval < T > & operator - = ( const XYZEval < T > & rs ) { LINEAR_AXIS_CODE ( x - = rs . x , y - = rs . y , z - = rs . z ) ; return * this ; }
FI XYZval < T > & operator * = ( const XYZEval < T > & rs ) { LINEAR_AXIS_CODE ( x * = rs . x , y * = rs . y , z * = rs . z ) ; return * this ; }
FI XYZval < T > & operator / = ( const XYZEval < T > & rs ) { LINEAR_AXIS_CODE ( x / = rs . x , y / = rs . y , z / = rs . z ) ; return * this ; }
FI XYZval < T > & operator * = ( const float & v ) { LINEAR_AXIS_CODE ( x * = v , y * = v , z * = v ) ; return * this ; }
FI XYZval < T > & operator * = ( const int & v ) { LINEAR_AXIS_CODE ( x * = v , y * = v , z * = v ) ; return * this ; }
FI XYZval < T > & operator > > = ( const int & v ) { LINEAR_AXIS_CODE ( _RS ( x ) , _RS ( y ) , _RS ( z ) ) ; return * this ; }
FI XYZval < T > & operator < < = ( const int & v ) { LINEAR_AXIS_CODE ( _LS ( x ) , _LS ( y ) , _LS ( z ) ) ; return * this ; }
FI bool operator = = ( const XYZEval < T > & rs ) { return true LINEAR_AXIS_GANG ( & & x = = rs . x , & & y = = rs . y , & & z = = rs . z ) ; }
FI bool operator = = ( const XYZEval < T > & rs ) const { return true LINEAR_AXIS_GANG ( & & x = = rs . x , & & y = = rs . y , & & z = = rs . z ) ; }
FI XYZval < T > & operator = ( const XYZEval < T > & rs ) { set ( LINEAR_AXIS_ELEM ( rs ) ) ; return * this ; }
// Override other operators to get intuitive behaviors
FI XYZval < T > operator + ( const XYval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , NOOP , NOOP , NOOP , NOOP ) ; return ls ; }
FI XYZval < T > operator + ( const XYval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , NOOP , NOOP , NOOP , NOOP ) ; return ls ; }
FI XYZval < T > operator - ( const XYval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , NOOP , NOOP , NOOP , NOOP ) ; return ls ; }
FI XYZval < T > operator - ( const XYval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , NOOP , NOOP , NOOP , NOOP ) ; return ls ; }
FI XYZval < T > operator * ( const XYval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , NOOP , NOOP , NOOP , NOOP ) ; return ls ; }
FI XYZval < T > operator * ( const XYval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , NOOP , NOOP , NOOP , NOOP ) ; return ls ; }
FI XYZval < T > operator / ( const XYval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , NOOP , NOOP , NOOP , NOOP ) ; return ls ; }
FI XYZval < T > operator / ( const XYval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , NOOP , NOOP , NOOP , NOOP ) ; return ls ; }
FI XYZval < T > operator + ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z , ls . i + = rs . i , ls . j + = rs . j , ls . k + = rs . k ) ; return ls ; }
FI XYZval < T > operator + ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z , ls . i + = rs . i , ls . j + = rs . j , ls . k + = rs . k ) ; return ls ; }
FI XYZval < T > operator - ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z , ls . i - = rs . i , ls . j - = rs . j , ls . k - = rs . k ) ; return ls ; }
FI XYZval < T > operator - ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z , ls . i - = rs . i , ls . j - = rs . j , ls . k - = rs . k ) ; return ls ; }
FI XYZval < T > operator * ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z , ls . i * = rs . i , ls . j * = rs . j , ls . k * = rs . k ) ; return ls ; }
FI XYZval < T > operator * ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z , ls . i * = rs . i , ls . j * = rs . j , ls . k * = rs . k ) ; return ls ; }
FI XYZval < T > operator / ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z , ls . i / = rs . i , ls . j / = rs . j , ls . k / = rs . k ) ; return ls ; }
FI XYZval < T > operator / ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z , ls . i / = rs . i , ls . j / = rs . j , ls . k / = rs . k ) ; return ls ; }
FI XYZval < T > operator + ( const XYZEval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z , ls . i + = rs . i , ls . j + = rs . j , ls . k + = rs . k ) ; return ls ; }
FI XYZval < T > operator + ( const XYZEval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z , ls . i + = rs . i , ls . j + = rs . j , ls . k + = rs . k ) ; return ls ; }
FI XYZval < T > operator - ( const XYZEval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z , ls . i - = rs . i , ls . j - = rs . j , ls . k - = rs . k ) ; return ls ; }
FI XYZval < T > operator - ( const XYZEval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z , ls . i - = rs . i , ls . j - = rs . j , ls . k - = rs . k ) ; return ls ; }
FI XYZval < T > operator * ( const XYZEval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z , ls . i * = rs . i , ls . j * = rs . j , ls . k * = rs . k ) ; return ls ; }
FI XYZval < T > operator * ( const XYZEval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z , ls . i * = rs . i , ls . j * = rs . j , ls . k * = rs . k ) ; return ls ; }
FI XYZval < T > operator / ( const XYZEval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z , ls . i / = rs . i , ls . j / = rs . j , ls . k / = rs . k ) ; return ls ; }
FI XYZval < T > operator / ( const XYZEval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z , ls . i / = rs . i , ls . j / = rs . j , ls . k / = rs . k ) ; return ls ; }
FI XYZval < T > operator * ( const float & v ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = v , ls . y * = v , ls . z * = v , ls . i * = v , ls . j * = v , ls . k * = v ) ; return ls ; }
FI XYZval < T > operator * ( const float & v ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = v , ls . y * = v , ls . z * = v , ls . i * = v , ls . j * = v , ls . k * = v ) ; return ls ; }
FI XYZval < T > operator * ( const int & v ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = v , ls . y * = v , ls . z * = v , ls . i * = v , ls . j * = v , ls . k * = v ) ; return ls ; }
FI XYZval < T > operator * ( const int & v ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = v , ls . y * = v , ls . z * = v , ls . i * = v , ls . j * = v , ls . k * = v ) ; return ls ; }
FI XYZval < T > operator / ( const float & v ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = v , ls . y / = v , ls . z / = v , ls . i / = v , ls . j / = v , ls . k / = v ) ; return ls ; }
FI XYZval < T > operator / ( const float & v ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = v , ls . y / = v , ls . z / = v , ls . i / = v , ls . j / = v , ls . k / = v ) ; return ls ; }
FI XYZval < T > operator / ( const int & v ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = v , ls . y / = v , ls . z / = v , ls . i / = v , ls . j / = v , ls . k / = v ) ; return ls ; }
FI XYZval < T > operator / ( const int & v ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = v , ls . y / = v , ls . z / = v , ls . i / = v , ls . j / = v , ls . k / = v ) ; return ls ; }
FI XYZval < T > operator > > ( const int & v ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( _RS ( ls . x ) , _RS ( ls . y ) , _RS ( ls . z ) , _RS ( ls . i ) , _RS ( ls . j ) , _RS ( ls . k ) ) ; return ls ; }
FI XYZval < T > operator > > ( const int & v ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( _RS ( ls . x ) , _RS ( ls . y ) , _RS ( ls . z ) , _RS ( ls . i ) , _RS ( ls . j ) , _RS ( ls . k ) ) ; return ls ; }
FI XYZval < T > operator < < ( const int & v ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( _LS ( ls . x ) , _LS ( ls . y ) , _LS ( ls . z ) , _LS ( ls . i ) , _LS ( ls . j ) , _LS ( ls . k ) ) ; return ls ; }
FI XYZval < T > operator < < ( const int & v ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( _LS ( ls . x ) , _LS ( ls . y ) , _LS ( ls . z ) , _LS ( ls . i ) , _LS ( ls . j ) , _LS ( ls . k ) ) ; return ls ; }
FI const XYZval < T > operator - ( ) const { XYZval < T > o = * this ; LINEAR_AXIS_CODE ( o . x = - x , o . y = - y , o . z = - z , o . i = - i , o . j = - j , o . k = - k ) ; return o ; }
FI XYZval < T > operator - ( ) { XYZval < T > o = * this ; LINEAR_AXIS_CODE ( o . x = - x , o . y = - y , o . z = - z , o . i = - i , o . j = - j , o . k = - k ) ; return o ; }
// Modifier operators
FI XYZval < T > & operator + = ( const XYval < T > & rs ) { LINEAR_AXIS_CODE ( x + = rs . x , y + = rs . y , NOOP , NOOP , NOOP , NOOP ) ; return * this ; }
FI XYZval < T > & operator - = ( const XYval < T > & rs ) { LINEAR_AXIS_CODE ( x - = rs . x , y - = rs . y , NOOP , NOOP , NOOP , NOOP ) ; return * this ; }
FI XYZval < T > & operator * = ( const XYval < T > & rs ) { LINEAR_AXIS_CODE ( x * = rs . x , y * = rs . y , NOOP , NOOP , NOOP , NOOP ) ; return * this ; }
FI XYZval < T > & operator / = ( const XYval < T > & rs ) { LINEAR_AXIS_CODE ( x / = rs . x , y / = rs . y , NOOP , NOOP , NOOP , NOOP ) ; return * this ; }
FI XYZval < T > & operator + = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x + = rs . x , y + = rs . y , z + = rs . z , i + = rs . i , j + = rs . j , k + = rs . k ) ; return * this ; }
FI XYZval < T > & operator - = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x - = rs . x , y - = rs . y , z - = rs . z , i - = rs . i , j - = rs . j , k - = rs . k ) ; return * this ; }
FI XYZval < T > & operator * = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x * = rs . x , y * = rs . y , z * = rs . z , i * = rs . i , j * = rs . j , k * = rs . k ) ; return * this ; }
FI XYZval < T > & operator / = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x / = rs . x , y / = rs . y , z / = rs . z , i / = rs . i , j / = rs . j , k / = rs . k ) ; return * this ; }
FI XYZval < T > & operator + = ( const XYZEval < T > & rs ) { LINEAR_AXIS_CODE ( x + = rs . x , y + = rs . y , z + = rs . z , i + = rs . i , j + = rs . j , k + = rs . k ) ; return * this ; }
FI XYZval < T > & operator - = ( const XYZEval < T > & rs ) { LINEAR_AXIS_CODE ( x - = rs . x , y - = rs . y , z - = rs . z , i - = rs . i , j - = rs . j , k - = rs . k ) ; return * this ; }
FI XYZval < T > & operator * = ( const XYZEval < T > & rs ) { LINEAR_AXIS_CODE ( x * = rs . x , y * = rs . y , z * = rs . z , i * = rs . i , j * = rs . j , k * = rs . k ) ; return * this ; }
FI XYZval < T > & operator / = ( const XYZEval < T > & rs ) { LINEAR_AXIS_CODE ( x / = rs . x , y / = rs . y , z / = rs . z , i / = rs . i , j / = rs . j , k / = rs . k ) ; return * this ; }
FI XYZval < T > & operator * = ( const float & v ) { LINEAR_AXIS_CODE ( x * = v , y * = v , z * = v , i * = v , j * = v , k * = v ) ; return * this ; }
FI XYZval < T > & operator * = ( const int & v ) { LINEAR_AXIS_CODE ( x * = v , y * = v , z * = v , i * = v , j * = v , k * = v ) ; return * this ; }
FI XYZval < T > & operator > > = ( const int & v ) { LINEAR_AXIS_CODE ( _RS ( x ) , _RS ( y ) , _RS ( z ) , _RS ( i ) , _RS ( j ) , _RS ( k ) ) ; return * this ; }
FI XYZval < T > & operator < < = ( const int & v ) { LINEAR_AXIS_CODE ( _LS ( x ) , _LS ( y ) , _LS ( z ) , _LS ( i ) , _LS ( j ) , _LS ( k ) ) ; return * this ; }
// Exact comparisons. For floats a "NEAR" operation may be better.
FI bool operator = = ( const XYZEval < T > & rs ) { return true LINEAR_AXIS_GANG ( & & x = = rs . x , & & y = = rs . y , & & z = = rs . z , & & i = = rs . i , & & j = = rs . j , & & k = = rs . k ) ; }
FI bool operator = = ( const XYZEval < T > & rs ) const { return true LINEAR_AXIS_GANG ( & & x = = rs . x , & & y = = rs . y , & & z = = rs . z , & & i = = rs . i , & & j = = rs . j , & & k = = rs . k ) ; }
FI bool operator ! = ( const XYZEval < T > & rs ) { return ! operator = = ( rs ) ; }
FI bool operator ! = ( const XYZEval < T > & rs ) const { return ! operator = = ( rs ) ; }
FI XYZval < T > operator - ( ) { XYZval < T > o = * this ; LINEAR_AXIS_CODE ( o . x = - x , o . y = - y , o . z = - z ) ; return o ; }
FI const XYZval < T > operator - ( ) const { XYZval < T > o = * this ; LINEAR_AXIS_CODE ( o . x = - x , o . y = - y , o . z = - z ) ; return o ; }
} ;
//
@ -463,109 +528,137 @@ struct XYZval {
template < typename T >
struct XYZEval {
union {
struct { T LOGICAL_AXIS_LIST ( e , x , y , z ) ; } ;
struct { T LINEAR _AXIS_LIST ( a , b , c ) ; } ;
struct { T LOGICAL_AXIS_ARGS ( ) ; } ;
struct { T LOGICAL _AXIS_LIST ( _e , a , b , c , u , v , w ) ; } ;
T pos [ LOGICAL_AXES ] ;
} ;
FI void reset ( ) { LOGICAL_AXIS_GANG ( e = , x = , y = , z = ) 0 ; }
FI T magnitude ( ) const { return ( T ) sqrtf ( LOGICAL_AXIS_GANG ( + e * e , + x * x , + y * y , + z * z ) ) ; }
FI operator T * ( ) { return pos ; }
FI operator bool ( ) { return false LOGICAL_AXIS_GANG ( | | e , | | x , | | y , | | z ) ; }
FI void set ( const T px ) { x = px ; }
FI void set ( const T px , const T py ) { x = px ; y = py ; }
FI void set ( const XYval < T > pxy ) { x = pxy . x ; y = pxy . y ; }
FI void set ( const XYZval < T > pxyz ) { set ( LINEAR_AXIS_LIST ( pxyz . x , pxyz . y , pxyz . z ) ) ; }
// Reset all to 0
FI void reset ( ) { LOGICAL_AXIS_GANG ( e = , x = , y = , z = , i = , j = , k = ) 0 ; }
// Setters taking struct types and arrays
FI void set ( const T px ) { x = px ; }
FI void set ( const T px , const T py ) { x = px ; y = py ; }
FI void set ( const XYval < T > pxy ) { x = pxy . x ; y = pxy . y ; }
FI void set ( const XYZval < T > pxyz ) { set ( LINEAR_AXIS_ELEM ( pxyz ) ) ; }
# if HAS_Z_AXIS
FI void set ( LINEAR_AXIS_LIST ( const T px , const T py , const T pz ) ) {
LINEAR_AXIS_CODE ( x = px , y = py , z = pz ) ;
}
FI void set ( LINEAR_AXIS_ARGS ( const T ) ) { LINEAR_AXIS_CODE ( a = x , b = y , c = z , u = i , v = j , w = k ) ; }
# endif
# if LOGICAL_AXES > LINEAR_AXES
FI void set ( LOGICAL_AXIS_LIST ( const T pe , const T px , const T py , const T pz ) ) {
LOGICAL_AXIS_CODE ( e = pe , x = px , y = py , z = pz ) ;
}
FI void set ( const XYval < T > pxy , const T pe ) { set ( pxy ) ; e = pe ; }
FI void set ( const XYZval < T > pxyz , const T pe ) { set ( pxyz ) ; e = pe ; }
FI void set ( const XYval < T > pxy , const T pe ) { set ( pxy ) ; e = pe ; }
FI void set ( const XYZval < T > pxyz , const T pe ) { set ( pxyz ) ; e = pe ; }
FI void set ( LOGICAL_AXIS_ARGS ( const T ) ) { LOGICAL_AXIS_CODE ( _e = e , a = x , b = y , c = z , u = i , v = j , w = k ) ; }
# endif
FI XYZEval < T > copy ( ) const { XYZEval < T > o = * this ; return o ; }
FI XYZEval < T > ABS ( ) const { return LOGICAL_AXIS_ARRAY ( T ( _ABS ( e ) ) , T ( _ABS ( x ) ) , T ( _ABS ( y ) ) , T ( _ABS ( z ) ) ) ; }
FI XYZEval < int16_t > asInt ( ) { return LOGICAL_AXIS_ARRAY ( int16_t ( e ) , int16_t ( x ) , int16_t ( y ) , int16_t ( z ) ) ; }
FI XYZEval < int16_t > asInt ( ) const { return LOGICAL_AXIS_ARRAY ( int16_t ( e ) , int16_t ( x ) , int16_t ( y ) , int16_t ( z ) ) ; }
FI XYZEval < int32_t > asLong ( ) { return LOGICAL_AXIS_ARRAY ( int32_t ( e ) , int32_t ( x ) , int32_t ( y ) , int32_t ( z ) ) ; }
FI XYZEval < int32_t > asLong ( ) const { return LOGICAL_AXIS_ARRAY ( int32_t ( e ) , int32_t ( x ) , int32_t ( y ) , int32_t ( z ) ) ; }
FI XYZEval < int32_t > ROUNDL ( ) { return LOGICAL_AXIS_ARRAY ( int32_t ( LROUND ( e ) ) , int32_t ( LROUND ( x ) ) , int32_t ( LROUND ( y ) ) , int32_t ( LROUND ( z ) ) ) ; }
FI XYZEval < int32_t > ROUNDL ( ) const { return LOGICAL_AXIS_ARRAY ( int32_t ( LROUND ( e ) ) , int32_t ( LROUND ( x ) ) , int32_t ( LROUND ( y ) ) , int32_t ( LROUND ( z ) ) ) ; }
FI XYZEval < float > asFloat ( ) { return LOGICAL_AXIS_ARRAY ( static_cast < float > ( e ) , static_cast < float > ( x ) , static_cast < float > ( y ) , static_cast < float > ( z ) ) ; }
FI XYZEval < float > asFloat ( ) const { return LOGICAL_AXIS_ARRAY ( static_cast < float > ( e ) , static_cast < float > ( x ) , static_cast < float > ( y ) , static_cast < float > ( z ) ) ; }
FI XYZEval < float > reciprocal ( ) const { return LOGICAL_AXIS_ARRAY ( _RECIP ( e ) , _RECIP ( x ) , _RECIP ( y ) , _RECIP ( z ) ) ; }
FI XYZEval < float > asLogical ( ) const { XYZEval < float > o = asFloat ( ) ; toLogical ( o ) ; return o ; }
FI XYZEval < float > asNative ( ) const { XYZEval < float > o = asFloat ( ) ; toNative ( o ) ; return o ; }
FI operator XYval < T > & ( ) { return * ( XYval < T > * ) this ; }
FI operator const XYval < T > & ( ) const { return * ( const XYval < T > * ) this ; }
FI operator XYZval < T > & ( ) { return * ( XYZval < T > * ) this ; }
FI operator const XYZval < T > & ( ) const { return * ( const XYZval < T > * ) this ; }
FI T & operator [ ] ( const int n ) { return pos [ n ] ; }
FI const T & operator [ ] ( const int n ) const { return pos [ n ] ; }
FI XYZEval < T > & operator = ( const T v ) { set ( LIST_N_1 ( LINEAR_AXES , v ) ) ; return * this ; }
FI XYZEval < T > & operator = ( const XYval < T > & rs ) { set ( rs . x , rs . y ) ; return * this ; }
FI XYZEval < T > & operator = ( const XYZval < T > & rs ) { set ( LINEAR_AXIS_LIST ( rs . x , rs . y , rs . z ) ) ; return * this ; }
FI XYZEval < T > operator + ( const XYval < T > & rs ) const { XYZEval < T > ls = * this ; ls . x + = rs . x ; ls . y + = rs . y ; return ls ; }
FI XYZEval < T > operator + ( const XYval < T > & rs ) { XYZEval < T > ls = * this ; ls . x + = rs . x ; ls . y + = rs . y ; return ls ; }
FI XYZEval < T > operator - ( const XYval < T > & rs ) const { XYZEval < T > ls = * this ; ls . x - = rs . x ; ls . y - = rs . y ; return ls ; }
FI XYZEval < T > operator - ( const XYval < T > & rs ) { XYZEval < T > ls = * this ; ls . x - = rs . x ; ls . y - = rs . y ; return ls ; }
FI XYZEval < T > operator * ( const XYval < T > & rs ) const { XYZEval < T > ls = * this ; ls . x * = rs . x ; ls . y * = rs . y ; return ls ; }
FI XYZEval < T > operator * ( const XYval < T > & rs ) { XYZEval < T > ls = * this ; ls . x * = rs . x ; ls . y * = rs . y ; return ls ; }
FI XYZEval < T > operator / ( const XYval < T > & rs ) const { XYZEval < T > ls = * this ; ls . x / = rs . x ; ls . y / = rs . y ; return ls ; }
FI XYZEval < T > operator / ( const XYval < T > & rs ) { XYZEval < T > ls = * this ; ls . x / = rs . x ; ls . y / = rs . y ; return ls ; }
FI XYZEval < T > operator + ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z ) ; return ls ; }
FI XYZEval < T > operator + ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z ) ; return ls ; }
FI XYZEval < T > operator - ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z ) ; return ls ; }
FI XYZEval < T > operator - ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z ) ; return ls ; }
FI XYZEval < T > operator * ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z ) ; return ls ; }
FI XYZEval < T > operator * ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z ) ; return ls ; }
FI XYZEval < T > operator / ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z ) ; return ls ; }
FI XYZEval < T > operator / ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z ) ; return ls ; }
FI XYZEval < T > operator + ( const XYZEval < T > & rs ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e + = rs . e , ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z ) ; return ls ; }
FI XYZEval < T > operator + ( const XYZEval < T > & rs ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e + = rs . e , ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z ) ; return ls ; }
FI XYZEval < T > operator - ( const XYZEval < T > & rs ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e - = rs . e , ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z ) ; return ls ; }
FI XYZEval < T > operator - ( const XYZEval < T > & rs ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e - = rs . e , ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z ) ; return ls ; }
FI XYZEval < T > operator * ( const XYZEval < T > & rs ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e * = rs . e , ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z ) ; return ls ; }
FI XYZEval < T > operator * ( const XYZEval < T > & rs ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e * = rs . e , ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z ) ; return ls ; }
FI XYZEval < T > operator / ( const XYZEval < T > & rs ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e / = rs . e , ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z ) ; return ls ; }
FI XYZEval < T > operator / ( const XYZEval < T > & rs ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e / = rs . e , ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z ) ; return ls ; }
FI XYZEval < T > operator * ( const float & v ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e * = v , ls . x * = v , ls . y * = v , ls . z * = v ) ; return ls ; }
FI XYZEval < T > operator * ( const float & v ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e * = v , ls . x * = v , ls . y * = v , ls . z * = v ) ; return ls ; }
FI XYZEval < T > operator * ( const int & v ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e * = v , ls . x * = v , ls . y * = v , ls . z * = v ) ; return ls ; }
FI XYZEval < T > operator * ( const int & v ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e * = v , ls . x * = v , ls . y * = v , ls . z * = v ) ; return ls ; }
FI XYZEval < T > operator / ( const float & v ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e / = v , ls . x / = v , ls . y / = v , ls . z / = v ) ; return ls ; }
FI XYZEval < T > operator / ( const float & v ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e / = v , ls . x / = v , ls . y / = v , ls . z / = v ) ; return ls ; }
FI XYZEval < T > operator / ( const int & v ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e / = v , ls . x / = v , ls . y / = v , ls . z / = v ) ; return ls ; }
FI XYZEval < T > operator / ( const int & v ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e / = v , ls . x / = v , ls . y / = v , ls . z / = v ) ; return ls ; }
FI XYZEval < T > operator > > ( const int & v ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( _RS ( ls . e ) , _RS ( ls . x ) , _RS ( ls . y ) , _RS ( ls . z ) ) ; return ls ; }
FI XYZEval < T > operator > > ( const int & v ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( _RS ( ls . e ) , _RS ( ls . x ) , _RS ( ls . y ) , _RS ( ls . z ) ) ; return ls ; }
FI XYZEval < T > operator < < ( const int & v ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( _LS ( ls . e ) , _LS ( ls . x ) , _LS ( ls . y ) , _LS ( ls . z ) ) ; return ls ; }
FI XYZEval < T > operator < < ( const int & v ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( _LS ( ls . e ) , _LS ( ls . x ) , _LS ( ls . y ) , _LS ( ls . z ) ) ; return ls ; }
FI XYZEval < T > & operator + = ( const XYval < T > & rs ) { x + = rs . x ; y + = rs . y ; return * this ; }
FI XYZEval < T > & operator - = ( const XYval < T > & rs ) { x - = rs . x ; y - = rs . y ; return * this ; }
FI XYZEval < T > & operator * = ( const XYval < T > & rs ) { x * = rs . x ; y * = rs . y ; return * this ; }
FI XYZEval < T > & operator / = ( const XYval < T > & rs ) { x / = rs . x ; y / = rs . y ; return * this ; }
FI XYZEval < T > & operator + = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x + = rs . x , y + = rs . y , z + = rs . z ) ; return * this ; }
FI XYZEval < T > & operator - = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x - = rs . x , y - = rs . y , z - = rs . z ) ; return * this ; }
FI XYZEval < T > & operator * = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x * = rs . x , y * = rs . y , z * = rs . z ) ; return * this ; }
FI XYZEval < T > & operator / = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x / = rs . x , y / = rs . y , z / = rs . z ) ; return * this ; }
FI XYZEval < T > & operator + = ( const XYZEval < T > & rs ) { LOGICAL_AXIS_CODE ( e + = rs . e , x + = rs . x , y + = rs . y , z + = rs . z ) ; return * this ; }
FI XYZEval < T > & operator - = ( const XYZEval < T > & rs ) { LOGICAL_AXIS_CODE ( e - = rs . e , x - = rs . x , y - = rs . y , z - = rs . z ) ; return * this ; }
FI XYZEval < T > & operator * = ( const XYZEval < T > & rs ) { LOGICAL_AXIS_CODE ( e * = rs . e , x * = rs . x , y * = rs . y , z * = rs . z ) ; return * this ; }
FI XYZEval < T > & operator / = ( const XYZEval < T > & rs ) { LOGICAL_AXIS_CODE ( e / = rs . e , x / = rs . x , y / = rs . y , z / = rs . z ) ; return * this ; }
FI XYZEval < T > & operator * = ( const T & v ) { LOGICAL_AXIS_CODE ( e * = v , x * = v , y * = v , z * = v ) ; return * this ; }
FI XYZEval < T > & operator > > = ( const int & v ) { LOGICAL_AXIS_CODE ( _RS ( e ) , _RS ( x ) , _RS ( y ) , _RS ( z ) ) ; return * this ; }
FI XYZEval < T > & operator < < = ( const int & v ) { LOGICAL_AXIS_CODE ( _LS ( e ) , _LS ( x ) , _LS ( y ) , _LS ( z ) ) ; return * this ; }
FI bool operator = = ( const XYZval < T > & rs ) { return true LINEAR_AXIS_GANG ( & & x = = rs . x , & & y = = rs . y , & & z = = rs . z ) ; }
FI bool operator = = ( const XYZval < T > & rs ) const { return true LINEAR_AXIS_GANG ( & & x = = rs . x , & & y = = rs . y , & & z = = rs . z ) ; }
FI bool operator ! = ( const XYZval < T > & rs ) { return ! operator = = ( rs ) ; }
FI bool operator ! = ( const XYZval < T > & rs ) const { return ! operator = = ( rs ) ; }
FI XYZEval < T > operator - ( ) { return LOGICAL_AXIS_ARRAY ( - e , - x , - y , - z ) ; }
FI const XYZEval < T > operator - ( ) const { return LOGICAL_AXIS_ARRAY ( - e , - x , - y , - z ) ; }
# if LINEAR_AXES >= 4
FI void set ( const T px , const T py , const T pz ) { x = px ; y = py ; z = pz ; }
# endif
# if LINEAR_AXES >= 5
FI void set ( const T px , const T py , const T pz , const T pi ) { x = px ; y = py ; z = pz ; i = pi ; }
# endif
# if LINEAR_AXES >= 6
FI void set ( const T px , const T py , const T pz , const T pi , const T pj ) { x = px ; y = py ; z = pz ; i = pi ; j = pj ; }
# endif
// Length reduced to one dimension
FI T magnitude ( ) const { return ( T ) sqrtf ( LOGICAL_AXIS_GANG ( + e * e , + x * x , + y * y , + z * z , + i * i , + j * j , + k * k ) ) ; }
// Pointer to the data as a simple array
FI operator T * ( ) { return pos ; }
// If any element is true then it's true
FI operator bool ( ) { return 0 LOGICAL_AXIS_GANG ( | | e , | | x , | | y , | | z , | | i , | | j , | | k ) ; }
// Explicit copy and copies with conversion
FI XYZEval < T > copy ( ) const { XYZEval < T > o = * this ; return o ; }
FI XYZEval < T > ABS ( ) const { return LOGICAL_AXIS_ARRAY ( T ( _ABS ( e ) ) , T ( _ABS ( x ) ) , T ( _ABS ( y ) ) , T ( _ABS ( z ) ) , T ( _ABS ( i ) ) , T ( _ABS ( j ) ) , T ( _ABS ( k ) ) ) ; }
FI XYZEval < int16_t > asInt ( ) { return LOGICAL_AXIS_ARRAY ( int16_t ( e ) , int16_t ( x ) , int16_t ( y ) , int16_t ( z ) , int16_t ( i ) , int16_t ( j ) , int16_t ( k ) ) ; }
FI XYZEval < int16_t > asInt ( ) const { return LOGICAL_AXIS_ARRAY ( int16_t ( e ) , int16_t ( x ) , int16_t ( y ) , int16_t ( z ) , int16_t ( i ) , int16_t ( j ) , int16_t ( k ) ) ; }
FI XYZEval < int32_t > asLong ( ) { return LOGICAL_AXIS_ARRAY ( int32_t ( e ) , int32_t ( x ) , int32_t ( y ) , int32_t ( z ) , int32_t ( i ) , int32_t ( j ) , int32_t ( k ) ) ; }
FI XYZEval < int32_t > asLong ( ) const { return LOGICAL_AXIS_ARRAY ( int32_t ( e ) , int32_t ( x ) , int32_t ( y ) , int32_t ( z ) , int32_t ( i ) , int32_t ( j ) , int32_t ( k ) ) ; }
FI XYZEval < int32_t > ROUNDL ( ) { return LOGICAL_AXIS_ARRAY ( int32_t ( LROUND ( e ) ) , int32_t ( LROUND ( x ) ) , int32_t ( LROUND ( y ) ) , int32_t ( LROUND ( z ) ) , int32_t ( LROUND ( i ) ) , int32_t ( LROUND ( j ) ) , int32_t ( LROUND ( k ) ) ) ; }
FI XYZEval < int32_t > ROUNDL ( ) const { return LOGICAL_AXIS_ARRAY ( int32_t ( LROUND ( e ) ) , int32_t ( LROUND ( x ) ) , int32_t ( LROUND ( y ) ) , int32_t ( LROUND ( z ) ) , int32_t ( LROUND ( i ) ) , int32_t ( LROUND ( j ) ) , int32_t ( LROUND ( k ) ) ) ; }
FI XYZEval < float > asFloat ( ) { return LOGICAL_AXIS_ARRAY ( static_cast < float > ( e ) , static_cast < float > ( x ) , static_cast < float > ( y ) , static_cast < float > ( z ) , static_cast < float > ( i ) , static_cast < float > ( j ) , static_cast < float > ( k ) ) ; }
FI XYZEval < float > asFloat ( ) const { return LOGICAL_AXIS_ARRAY ( static_cast < float > ( e ) , static_cast < float > ( x ) , static_cast < float > ( y ) , static_cast < float > ( z ) , static_cast < float > ( i ) , static_cast < float > ( j ) , static_cast < float > ( k ) ) ; }
FI XYZEval < float > reciprocal ( ) const { return LOGICAL_AXIS_ARRAY ( _RECIP ( e ) , _RECIP ( x ) , _RECIP ( y ) , _RECIP ( z ) , _RECIP ( i ) , _RECIP ( j ) , _RECIP ( k ) ) ; }
// Marlin workspace shifting is done with G92 and M206
FI XYZEval < float > asLogical ( ) const { XYZEval < float > o = asFloat ( ) ; toLogical ( o ) ; return o ; }
FI XYZEval < float > asNative ( ) const { XYZEval < float > o = asFloat ( ) ; toNative ( o ) ; return o ; }
// In-place cast to types having fewer fields
FI operator XYval < T > & ( ) { return * ( XYval < T > * ) this ; }
FI operator const XYval < T > & ( ) const { return * ( const XYval < T > * ) this ; }
FI operator XYZval < T > & ( ) { return * ( XYZval < T > * ) this ; }
FI operator const XYZval < T > & ( ) const { return * ( const XYZval < T > * ) this ; }
// Accessor via an AxisEnum (or any integer) [index]
FI T & operator [ ] ( const int n ) { return pos [ n ] ; }
FI const T & operator [ ] ( const int n ) const { return pos [ n ] ; }
// Assignment operator overrides do the expected thing
FI XYZEval < T > & operator = ( const T v ) { set ( LIST_N_1 ( LINEAR_AXES , v ) ) ; return * this ; }
FI XYZEval < T > & operator = ( const XYval < T > & rs ) { set ( rs . x , rs . y ) ; return * this ; }
FI XYZEval < T > & operator = ( const XYZval < T > & rs ) { set ( LINEAR_AXIS_ELEM ( rs ) ) ; return * this ; }
// Override other operators to get intuitive behaviors
FI XYZEval < T > operator + ( const XYval < T > & rs ) const { XYZEval < T > ls = * this ; ls . x + = rs . x ; ls . y + = rs . y ; return ls ; }
FI XYZEval < T > operator + ( const XYval < T > & rs ) { XYZEval < T > ls = * this ; ls . x + = rs . x ; ls . y + = rs . y ; return ls ; }
FI XYZEval < T > operator - ( const XYval < T > & rs ) const { XYZEval < T > ls = * this ; ls . x - = rs . x ; ls . y - = rs . y ; return ls ; }
FI XYZEval < T > operator - ( const XYval < T > & rs ) { XYZEval < T > ls = * this ; ls . x - = rs . x ; ls . y - = rs . y ; return ls ; }
FI XYZEval < T > operator * ( const XYval < T > & rs ) const { XYZEval < T > ls = * this ; ls . x * = rs . x ; ls . y * = rs . y ; return ls ; }
FI XYZEval < T > operator * ( const XYval < T > & rs ) { XYZEval < T > ls = * this ; ls . x * = rs . x ; ls . y * = rs . y ; return ls ; }
FI XYZEval < T > operator / ( const XYval < T > & rs ) const { XYZEval < T > ls = * this ; ls . x / = rs . x ; ls . y / = rs . y ; return ls ; }
FI XYZEval < T > operator / ( const XYval < T > & rs ) { XYZEval < T > ls = * this ; ls . x / = rs . x ; ls . y / = rs . y ; return ls ; }
FI XYZEval < T > operator + ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z , ls . i + = rs . i , ls . j + = rs . j , ls . k + = rs . k ) ; return ls ; }
FI XYZEval < T > operator + ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z , ls . i + = rs . i , ls . j + = rs . j , ls . k + = rs . k ) ; return ls ; }
FI XYZEval < T > operator - ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z , ls . i - = rs . i , ls . j - = rs . j , ls . k - = rs . k ) ; return ls ; }
FI XYZEval < T > operator - ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z , ls . i - = rs . i , ls . j - = rs . j , ls . k - = rs . k ) ; return ls ; }
FI XYZEval < T > operator * ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z , ls . i * = rs . i , ls . j * = rs . j , ls . k * = rs . k ) ; return ls ; }
FI XYZEval < T > operator * ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z , ls . i * = rs . i , ls . j * = rs . j , ls . k * = rs . k ) ; return ls ; }
FI XYZEval < T > operator / ( const XYZval < T > & rs ) const { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z , ls . i / = rs . i , ls . j / = rs . j , ls . k / = rs . k ) ; return ls ; }
FI XYZEval < T > operator / ( const XYZval < T > & rs ) { XYZval < T > ls = * this ; LINEAR_AXIS_CODE ( ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z , ls . i / = rs . i , ls . j / = rs . j , ls . k / = rs . k ) ; return ls ; }
FI XYZEval < T > operator + ( const XYZEval < T > & rs ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e + = rs . e , ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z , ls . i + = rs . i , ls . j + = rs . j , ls . k + = rs . k ) ; return ls ; }
FI XYZEval < T > operator + ( const XYZEval < T > & rs ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e + = rs . e , ls . x + = rs . x , ls . y + = rs . y , ls . z + = rs . z , ls . i + = rs . i , ls . j + = rs . j , ls . k + = rs . k ) ; return ls ; }
FI XYZEval < T > operator - ( const XYZEval < T > & rs ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e - = rs . e , ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z , ls . i - = rs . i , ls . j - = rs . j , ls . k - = rs . k ) ; return ls ; }
FI XYZEval < T > operator - ( const XYZEval < T > & rs ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e - = rs . e , ls . x - = rs . x , ls . y - = rs . y , ls . z - = rs . z , ls . i - = rs . i , ls . j - = rs . j , ls . k - = rs . k ) ; return ls ; }
FI XYZEval < T > operator * ( const XYZEval < T > & rs ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e * = rs . e , ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z , ls . i * = rs . i , ls . j * = rs . j , ls . k * = rs . k ) ; return ls ; }
FI XYZEval < T > operator * ( const XYZEval < T > & rs ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e * = rs . e , ls . x * = rs . x , ls . y * = rs . y , ls . z * = rs . z , ls . i * = rs . i , ls . j * = rs . j , ls . k * = rs . k ) ; return ls ; }
FI XYZEval < T > operator / ( const XYZEval < T > & rs ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e / = rs . e , ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z , ls . i / = rs . i , ls . j / = rs . j , ls . k / = rs . k ) ; return ls ; }
FI XYZEval < T > operator / ( const XYZEval < T > & rs ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e / = rs . e , ls . x / = rs . x , ls . y / = rs . y , ls . z / = rs . z , ls . i / = rs . i , ls . j / = rs . j , ls . k / = rs . k ) ; return ls ; }
FI XYZEval < T > operator * ( const float & v ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e * = v , ls . x * = v , ls . y * = v , ls . z * = v , ls . i * = v , ls . j * = v , ls . k * = v ) ; return ls ; }
FI XYZEval < T > operator * ( const float & v ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e * = v , ls . x * = v , ls . y * = v , ls . z * = v , ls . i * = v , ls . j * = v , ls . k * = v ) ; return ls ; }
FI XYZEval < T > operator * ( const int & v ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e * = v , ls . x * = v , ls . y * = v , ls . z * = v , ls . i * = v , ls . j * = v , ls . k * = v ) ; return ls ; }
FI XYZEval < T > operator * ( const int & v ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e * = v , ls . x * = v , ls . y * = v , ls . z * = v , ls . i * = v , ls . j * = v , ls . k * = v ) ; return ls ; }
FI XYZEval < T > operator / ( const float & v ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e / = v , ls . x / = v , ls . y / = v , ls . z / = v , ls . i / = v , ls . j / = v , ls . k / = v ) ; return ls ; }
FI XYZEval < T > operator / ( const float & v ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e / = v , ls . x / = v , ls . y / = v , ls . z / = v , ls . i / = v , ls . j / = v , ls . k / = v ) ; return ls ; }
FI XYZEval < T > operator / ( const int & v ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e / = v , ls . x / = v , ls . y / = v , ls . z / = v , ls . i / = v , ls . j / = v , ls . k / = v ) ; return ls ; }
FI XYZEval < T > operator / ( const int & v ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( ls . e / = v , ls . x / = v , ls . y / = v , ls . z / = v , ls . i / = v , ls . j / = v , ls . k / = v ) ; return ls ; }
FI XYZEval < T > operator > > ( const int & v ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( _RS ( ls . e ) , _RS ( ls . x ) , _RS ( ls . y ) , _RS ( ls . z ) , _RS ( ls . i ) , _RS ( ls . j ) , _RS ( ls . k ) ) ; return ls ; }
FI XYZEval < T > operator > > ( const int & v ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( _RS ( ls . e ) , _RS ( ls . x ) , _RS ( ls . y ) , _RS ( ls . z ) , _RS ( ls . i ) , _RS ( ls . j ) , _RS ( ls . k ) ) ; return ls ; }
FI XYZEval < T > operator < < ( const int & v ) const { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( _LS ( ls . e ) , _LS ( ls . x ) , _LS ( ls . y ) , _LS ( ls . z ) , _LS ( ls . i ) , _LS ( ls . j ) , _LS ( ls . k ) ) ; return ls ; }
FI XYZEval < T > operator < < ( const int & v ) { XYZEval < T > ls = * this ; LOGICAL_AXIS_CODE ( _LS ( ls . e ) , _LS ( ls . x ) , _LS ( ls . y ) , _LS ( ls . z ) , _LS ( ls . i ) , _LS ( ls . j ) , _LS ( ls . k ) ) ; return ls ; }
FI const XYZEval < T > operator - ( ) const { return LOGICAL_AXIS_ARRAY ( - e , - x , - y , - z , - i , - j , - k ) ; }
FI XYZEval < T > operator - ( ) { return LOGICAL_AXIS_ARRAY ( - e , - x , - y , - z , - i , - j , - k ) ; }
// Modifier operators
FI XYZEval < T > & operator + = ( const XYval < T > & rs ) { x + = rs . x ; y + = rs . y ; return * this ; }
FI XYZEval < T > & operator - = ( const XYval < T > & rs ) { x - = rs . x ; y - = rs . y ; return * this ; }
FI XYZEval < T > & operator * = ( const XYval < T > & rs ) { x * = rs . x ; y * = rs . y ; return * this ; }
FI XYZEval < T > & operator / = ( const XYval < T > & rs ) { x / = rs . x ; y / = rs . y ; return * this ; }
FI XYZEval < T > & operator + = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x + = rs . x , y + = rs . y , z + = rs . z , i + = rs . i , j + = rs . j , k + = rs . k ) ; return * this ; }
FI XYZEval < T > & operator - = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x - = rs . x , y - = rs . y , z - = rs . z , i - = rs . i , j - = rs . j , k - = rs . k ) ; return * this ; }
FI XYZEval < T > & operator * = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x * = rs . x , y * = rs . y , z * = rs . z , i * = rs . i , j * = rs . j , k * = rs . k ) ; return * this ; }
FI XYZEval < T > & operator / = ( const XYZval < T > & rs ) { LINEAR_AXIS_CODE ( x / = rs . x , y / = rs . y , z / = rs . z , i / = rs . i , j / = rs . j , k / = rs . k ) ; return * this ; }
FI XYZEval < T > & operator + = ( const XYZEval < T > & rs ) { LOGICAL_AXIS_CODE ( e + = rs . e , x + = rs . x , y + = rs . y , z + = rs . z , i + = rs . i , j + = rs . j , k + = rs . k ) ; return * this ; }
FI XYZEval < T > & operator - = ( const XYZEval < T > & rs ) { LOGICAL_AXIS_CODE ( e - = rs . e , x - = rs . x , y - = rs . y , z - = rs . z , i - = rs . i , j - = rs . j , k - = rs . k ) ; return * this ; }
FI XYZEval < T > & operator * = ( const XYZEval < T > & rs ) { LOGICAL_AXIS_CODE ( e * = rs . e , x * = rs . x , y * = rs . y , z * = rs . z , i * = rs . i , j * = rs . j , k * = rs . k ) ; return * this ; }
FI XYZEval < T > & operator / = ( const XYZEval < T > & rs ) { LOGICAL_AXIS_CODE ( e / = rs . e , x / = rs . x , y / = rs . y , z / = rs . z , i / = rs . i , j / = rs . j , k / = rs . k ) ; return * this ; }
FI XYZEval < T > & operator * = ( const T & v ) { LOGICAL_AXIS_CODE ( e * = v , x * = v , y * = v , z * = v , i * = v , j * = v , k * = v ) ; return * this ; }
FI XYZEval < T > & operator > > = ( const int & v ) { LOGICAL_AXIS_CODE ( _RS ( e ) , _RS ( x ) , _RS ( y ) , _RS ( z ) , _RS ( i ) , _RS ( j ) , _RS ( k ) ) ; return * this ; }
FI XYZEval < T > & operator < < = ( const int & v ) { LOGICAL_AXIS_CODE ( _LS ( e ) , _LS ( x ) , _LS ( y ) , _LS ( z ) , _LS ( i ) , _LS ( j ) , _LS ( k ) ) ; return * this ; }
// Exact comparisons. For floats a "NEAR" operation may be better.
FI bool operator = = ( const XYZval < T > & rs ) { return true LINEAR_AXIS_GANG ( & & x = = rs . x , & & y = = rs . y , & & z = = rs . z , & & i = = rs . i , & & j = = rs . j , & & k = = rs . k ) ; }
FI bool operator = = ( const XYZval < T > & rs ) const { return true LINEAR_AXIS_GANG ( & & x = = rs . x , & & y = = rs . y , & & z = = rs . z , & & i = = rs . i , & & j = = rs . j , & & k = = rs . k ) ; }
FI bool operator ! = ( const XYZval < T > & rs ) { return ! operator = = ( rs ) ; }
FI bool operator ! = ( const XYZval < T > & rs ) const { return ! operator = = ( rs ) ; }
} ;
# undef _RECIP