Accuracy: Euler vs Quaternion

I'm using a Trinket M0 w/ a BNO055 to act as a mouse, which will give the most precision, Euler or Quaternion?

Precision is the same either way.

Thanks, any opinion on which is easier to program with?

About the same, but Euler angles cannot uniquely represent all possible 3D orientations.

What does the body 3D orientation have to do with mouse function?

I’m trying to make a head mouse. All I actually need is the x,y axis and acceleration for pointer speed. I’m using a pro micro/mpu9250 but it’s not great w/ small motions, i.e typing. I have a trinketm0 and bno055 , I’ll see if that works better. Here’s the promicro sketch if you’re curious

/

#include<Wire.h>
#include<Mouse.h>


const int MPU=0x68;
int16_t GyX, GyY, GyZ, AcX, AcY, AcZ, BAcX, BAcY, BAcZ, TAcX, TAcY, TAcZ;

int buttonGyro = 6;
int buttonAccel = 4;
int buttonState = 0;

int gyroLock = 0;
int AccelLock = 0;
int AccelLockToggle = 0;
int AccelLockSide = 0;
int GyroLockToggle = 0;
int GyroLockSide = 0;
int i = 0;
int i2 = 0;
int w = 0, a = 0, j = 0;
int threshold = 1;
int X, Y, Z;
int minX, maxX, minY, maxY, minZ, maxZ;
int accelLock = 0;
int TGY = 0;
void setup(){

  pinMode(buttonGyro, INPUT);
  digitalWrite(buttonGyro, HIGH);
  pinMode(buttonAccel, INPUT);
  digitalWrite(buttonAccel, HIGH);
  
  Wire.begin();
  Wire.beginTransmission(MPU);
  Wire.write(0x6B);  
  Wire.write(0);     
  Wire.endTransmission(true);
  Serial.begin(1);
  Mouse.begin();
}
void loop(){
  gyroLock = digitalRead(buttonGyro);
  if (gyroLock == LOW) {
    if (GyroLockSide == 0) {
      GyroLockSide = 1;
      if (GyroLockToggle == 0) {
        GyroLockToggle = 1;
      }
      else {
        GyroLockToggle = 0;
      }
    }
  }
  else {
    if (GyroLockSide == 1) {
      GyroLockSide = 0;
    }
  }
  if (GyroLockToggle == 0) {
    Wire.beginTransmission(MPU);
    Wire.write(0x43);  
    Wire.endTransmission(false);
    Wire.requestFrom(MPU,6,true);
    GyX = Wire.read()<<8|Wire.read();
    GyY = Wire.read()<<8|Wire.read();
    GyZ = Wire.read()<<8|Wire.read();// 
    if (AccelLockToggle == 1) {
      Mouse.move( -GyZ / 1000, GyX / 1000, 0 );
    }
    else {
      Mouse.move( -GyZ / 2000, GyX / 2000, 0 );
    }
    TGY -= GyY / 1000;
    if (AccelLockToggle == 1) {
      if (TGY > 1000) {

      }
      else if (TGY < -1000) {
        //
      }
    }
    else {
      TGY = 0;
    }
    if (GyX > 2000 || GyY > 2000 || GyZ > 2000) {
      accelLock = 0;
    }
    else {
      accelLock = 1;
    }
  }
  AccelLock = digitalRead(buttonAccel);
  if (AccelLock == LOW) {
    if (AccelLockSide == 0) {
      AccelLockSide = 1;
      if (AccelLockToggle == 0) {
        AccelLockToggle = 1;
      }
      else {
        AccelLockToggle = 0;
      }
    }
  }
  else {
    if (AccelLockSide == 1) {
      AccelLockSide = 0;
    }
  }
  if (AccelLockToggle == 1) {
    if (true) {
      if (i == 0) {
        Wire.beginTransmission(MPU);
        Wire.write(0x3B);  
        Wire.endTransmission(false);
        Wire.requestFrom(MPU, 6, true);  // 
        BAcX=Wire.read()<<8|Wire.read();// 0x3B     
        BAcY=Wire.read()<<8|Wire.read();
        BAcZ=Wire.read()<<8|Wire.read();// 0x40
        i = 1;
        minX = BAcX;
        maxX = BAcX;
        minY = BAcY;
        maxY = BAcY;
        minZ = BAcZ;
        maxZ = BAcZ;
        BAcX /= 500;
        BAcY /= 500;
        BAcZ /= 500;
      }
      Wire.beginTransmission(MPU);
      Wire.write(0x3B);  // 
      Wire.endTransmission(false);
      Wire.requestFrom(MPU, 6, true);  // 
      AcX=Wire.read()<<8|Wire.read();// 0x3B     
      AcY=Wire.read()<<8|Wire.read();
      AcZ=Wire.read()<<8|Wire.read();// 0x40
      if (AcX < minX) {
        minX = AcX;
      }
      else if (AcX > maxX) {
        maxX = AcX;
      }
      if (AcY < minY) {
        minY = AcY;
      }
      else if (AcY > maxY) {
        maxY = AcY;
      }
      if (AcZ < minZ) {
        minZ = AcZ;
      }
      else if (AcZ > maxZ) {
        maxZ = AcZ;
      }
//    
      AcX /= 8000;
      TAcX = AcX;
      AcX -= BAcX;
      BAcX = TAcX;
      AcY /= 8000;
      TAcY = AcY;
      AcY -= BAcY;
      BAcY = TAcY;
      AcZ /= 8000;
      TAcZ = AcZ;
      AcZ -= BAcZ;
      BAcZ = TAcZ;
      Y = -AcX;
      X = -AcY;
      Z = AcZ;
      Y = 0;
 
      if (X > threshold) {
        if (w == 0) {
          w = 1;
        }
        else if (w == -1) {
          w = -2;
        }
        else if (w == 4) {
          w = 0;
        }
        else if (w == -3) {
          w = -4;
        }
      }
      else if (X < -threshold) {
        if (w == 1) {
          w = 2;
        }
        else if (w == 0) {
          w = -1;
        }
        else if (w == 3) {
          w = 4;
        }
        else if (w == -4) {
          w = 0;
        }
      }
      else {
        if (w == 2) {
          w = 3;
        }
        else if (w == -2) {
          w = -3;
        }
      }
      if (Y > threshold) {
        if (a == 0) {
          a = 1;
        }
        else if (a == -1) {
          a = -2;
        }
        else if (a == 4) {
          a = 0;
        }
        else if (a == -3) {
          a = -4;
        }
      }
      else if (Y < -threshold) {
        if (a == 1) {
          a = 2;
        }
        else if (a == 0) {
          a = -1;
        }
        else if (a == 3) {
          a = 4;
        }
        else if (a == -4) {
          a = 0;
        }
      }
      else {
        if (a == 2) {
          a = 3;
        }
        else if (a == -2) {
          a = -3;
        }
      }
      if (Z > threshold) {
        if (j == 0) {
          j = 1;
        }
        else if (j == -1) {
          j = -2;
        }
        else if (j == 4) {
          j = 0;
        }
        else if (j == -3) {
          j = -4;
        }
      }
      else if (Z < -threshold) {
        if (j == 1) {
          j = 2;
        }
        else if (j == 0) {
          j = -1;
        }
        else if (j == 3) {
          j = 4;
        }
        else if (j == -4) {
          j = 0;
        }
      }
      else {
        if (j == 2) {
          j = 3;
        }
        else if (j == -2) {
          j = -3;
        }
      }
    }
    }
  
  
  delay(0);
}

try a look at this info https://os.mbed.com/users/onehorse/

jremington:
About the same, but Euler angles cannot uniquely represent all possible 3D orientations.

Euler angles cannot be used easily to handle arbitrary rotations due to the gimbal lock problem,
you'd avoid using them for calculation, only for presenting the results.

Unit quaternions or DCM (direction cosine matrix) are the representations to use internally, Quaternions
being more compact. Both are reasonably stable computationally if you re-normalize after each operation, re-normalizing is easy with quarterions.

BTW unit quarternions have double cover over 3D rotation/orientation, so they cannot uniquely represent them
either, but its not an issue, the maths always works - rotating clockwise about up is the same as rotating
anticlockwise about down.