Android SensorManager dziwne, jak remapowaćCoordinateSystem

Dema API -> Grafika ->Kompas

Działa tylko poprawnie, dopóki nie zmienisz naturalnej orientacji urządzenia. W większości telefonów jest portret, a większość 10-calowych tabletów to krajobraz. Jeśli zmienisz, musisz obrócić to o 90 stopni. Chciałbym zobaczyć poprawkę 3D dla tego systemu.

100% pewności użyciaremapCoordinateSystem () metoda.

Chciałbym zobaczyć, jak (kod), gdybym mógł zobaczyć wyjaśnienie, w jaki sposób obliczane jest mapowanie osi (matematyka teoretyczna) byłoby miło.

Próbowałem zrozumieć, ale zapomniałem o całej algebrze liniowej.

Tutaj mówi, dlaczego musimy używać, ale nie mówi jak!

float R[] = new float[9];
// X  (product of Y and Z) and roughly points East
// Y: points to Magnetic NORTH and tangential to ground
// Z: points to SKY and perpendicular to ground
float I[] = new float[9];
boolean success = SensorManager.getRotationMatrix(R, I, mGravity, mGeomagnetic);

Wygląda na to, że współrzędne znajdują się w tej pozycji: - urządzenie mówi w tabeli (osie xi y znajdują się na stole)

Tylko i tylko wtedy

getWindowManager().getDefaultDisplay().getRotation() == Surface.ROTATION_0

Pytanie brzmi, jak wypełnić ten kod: - te gałęzie przypadków

switch (mScreenRotation) {
    case Surface.ROTATION_0:
    Log.v("SurfaceRemap", "0 degree");
    axisX = SensorManager.AXIS_X;// is this valid?
    axisY = SensorManager.AXIS_Y;// is this valid?
    break;

    case Surface.ROTATION_90:
    Log.v("SurfaceRemap", "90 degree");
    // examples says remapCoordinateSystem(inR, AXIS_Y, AXIS_MINUS_X, outR);
    axisX = SensorManager.AXIS_Y;
    axisY = SensorManager.AXIS_MINUS_X;
    break;

    case Surface.ROTATION_180:
    Log.v("SurfaceRemap", "180 degree");
    break;

    case Surface.ROTATION_270:
    Log.v("SurfaceRemap", "270 degree");
    break;

    default:
    Log.v("SurfaceRemap", "don't know the mScreenRotation value: "+mScreenRotation+" you should never seen this message!");
    break;
}


boolean remapped = SensorManager.remapCoordinateSystem(R, axisX, axisY, R);

float orientation[] = new float[3];

SensorManager.getOrientation(R, orientation);// All three angles above are in radians and positive in the counter-clockwise direction.
inclination = SensorManager.getInclination(I);

Edytuj: Napisałem małą aplikację testową, w której na ekranie wyświetla się obrót ekranu: 0, 90, 270 stopni (nie można teraz zrobić 180)

Wydaje się, że jeśli Rotacja 0 pozostanie niezmieniona (axisX = SensorManager.AXIS_X;axisY = SensorManager.AXIS_Y;) niż 90 stopni powinno być:

axisX = SensorManager.AXIS_MINUS_Y;
axisY = SensorManager.AXIS_X;

niż dokumentacja Google mówi gdzieś złe wartości! Pytanie brzmi: gdzie?

getRotationMatrix zwróć to:

X jest zdefiniowany jako produkt wektorowy Y.Z (jest styczny do ziemi w bieżącej lokalizacji urządzenia i z grubsza wskazuje na wschód).

Y jest styczna do ziemi w bieżącym położeniu urządzenia i wskazuje na magnetyczny biegun północny.

Z wskazuje na niebo i jest prostopadły do ​​ziemi.

Zobacz telefon powyżej! Chcę od prawej do lewej, z tylną kamerą do ziemi.

getOrientation zwróć to:

X jest zdefiniowany jako produkt wektorowy Y.Z (Jest styczny do ziemi w bieżącej lokalizacji urządzenia i z grubsza wskazuje Zachód).

Y jest styczna do ziemi w bieżącym położeniu urządzenia i wskazuje na magnetyczny biegun północny.

Z wskazuje środek Ziemi i jest prostopadły do ​​ziemi.

values[0]: azymut, obrót wokół osi Z.

values[1]: pitch, obrót wokół osi X.

values[2]: rolka, obrót wokół osi Y.

Jak powinien być telefon?

Na koniec chciałbym mieć wartości kątów jak samoloty. Mój telefon (ja) kierujący się na północ: (odchylenie to azymut)

              if ScreenRotation = 0 degree
Pitch axis = -orientationAxisX  =  rotationAxisX
Roll axis  =  orientationAxisY  =  rotationAxisY 
Yaw axis   =  orientationAxisZ  = -rotationAxisZ

questionAnswers(5)

yourAnswerToTheQuestion