Die Android-Plattform bietet mehrere Sensoren, mit denen Sie die Bewegung eines Geräts überwachen können.
Die möglichen Architekturen der Sensoren variieren je nach Sensortyp:
- Schwerkraft, lineare Beschleunigung, Rotationsvektor, signifikante Bewegung, Schritt Zähler- und Schrittdetektorsensoren hardwarebasiert softwarebasiert.
- Der Beschleunigungsmesser und die Gyroskopsensoren sind immer hardwarebasiert.
Die meisten Android-Geräte haben einen Beschleunigungsmesser und viele haben jetzt auch ein Gyroskop. Die Verfügbarkeit der softwarebasierten Sensoren da sie häufig auf einen oder mehrere Hardwaresensoren zurückgreifen, Daten. Je nach Gerät können diese softwarebasierten Sensoren ihre Daten entweder vom Beschleunigungsmesser und Magnetometer oder vom Gyroskop ableiten.
Bewegungssensoren sind nützlich, um Gerätebewegungen wie Neigung, Schüttel, Drehung oder schwingen. Die Bewegung spiegelt in der Regel direkte Nutzereingaben wider (z. B. wenn Nutzende ein ein Auto in einem Spiel oder ein Nutzer, der einen Ball in einem Spiel steuert. der Umgebung, in der sich das Gerät befindet (z. B. wenn Sie sich beim Fahren mit Ihnen bewegen) Ihres Autos). Im ersten Fall wird die Bewegung relativ zum Referenzpunkt des Geräts oder der Anwendung überwacht. Im zweiten Fall wird die Bewegung relativ zum Weltraum überwacht. Bewegungssensoren selbst werden in der Regel nicht zur Überwachung Geräteposition, können aber mit anderen Sensoren verwendet werden, z. B. dem Sensor für geomagnetische Felder, um die Position eines Geräts relativ zum Bezugsrahmen der Welt bestimmen. Weitere Informationen finden Sie unter Positionssensoren. Informationen).
Alle Bewegungssensoren geben für jede SensorEvent
mehrdimensionale Arrays von Sensorwerten zurück. Beispielsweise gibt der Beschleunigungsmesser während eines einzelnen Sensorereignisses
Beschleunigungskraftdaten für die drei Koordinatenachsen und das Gyroskop gibt die Rotationsrate zurück
für die drei Koordinatenachsen. Diese Datenwerte werden zusammen mit anderen SensorEvent
-Parametern in einem float
-Array (values
) zurückgegeben. In Tabelle 1 sind die auf der Android-Plattform verfügbaren Bewegungssensoren zusammengefasst.
Tabelle 1 Bewegungssensoren, die auf der Android-Plattform unterstützt werden
Sensor | Sensorereignisdaten | Beschreibung | Maßeinheiten |
---|---|---|---|
TYPE_ACCELEROMETER |
SensorEvent.values[0] |
Beschleunigungskraft entlang der x-Achse (einschließlich der Schwerkraft). | m/s2 |
SensorEvent.values[1] |
Beschleunigungskraft entlang der Y-Achse (einschließlich Schwerkraft). | ||
SensorEvent.values[2] |
Beschleunigungskraft entlang der Z‑Achse (einschließlich Schwerkraft). | ||
TYPE_ACCELEROMETER_UNCALIBRATED |
SensorEvent.values[0] |
Gemessene Beschleunigung entlang der X-Achse ohne Voreinstellbare Neigungsausgleiche. | m/s2 |
SensorEvent.values[1] |
Gemessene Beschleunigung entlang der Y-Achse ohne Vorabglättung. | ||
SensorEvent.values[2] |
Gemessene Beschleunigung entlang der Z-Achse ohne Verzerrungskompensation. | ||
SensorEvent.values[3] |
Gemessene Beschleunigung entlang der X-Achse mit geschätzter Voreingenommenheitskompensation. | ||
SensorEvent.values[4] |
Gemessene Beschleunigung entlang der Y-Achse mit geschätzter Voreingenommenheitskompensation. | ||
SensorEvent.values[5] |
Gemessene Beschleunigung entlang der Z-Achse mit geschätzter Verzerrungskompensation. | ||
TYPE_GRAVITY |
SensorEvent.values[0] |
Schwerkraft entlang der x-Achse. | m/s2 |
SensorEvent.values[1] |
Schwerkraft entlang der y-Achse. | ||
SensorEvent.values[2] |
Schwerkraft entlang der z-Achse. | ||
TYPE_GYROSCOPE |
SensorEvent.values[0] |
Rotationsrate um die x-Achse. | Rad/s |
SensorEvent.values[1] |
Drehgeschwindigkeit um die y-Achse. | ||
SensorEvent.values[2] |
Rotationsrate um die z-Achse. | ||
TYPE_GYROSCOPE_UNCALIBRATED |
SensorEvent.values[0] |
Drehgeschwindigkeit (ohne Driftkompensation) um die x-Achse. | rad/s |
SensorEvent.values[1] |
Rotationsrate (ohne Driftkompensation) um die y-Achse. | ||
SensorEvent.values[2] |
Drehgeschwindigkeit (ohne Driftkompensation) um die Z‑Achse. | ||
SensorEvent.values[3] |
Geschätzte Abweichung um die x-Achse. | ||
SensorEvent.values[4] |
Geschätzte Abweichung um die Y-Achse. | ||
SensorEvent.values[5] |
Geschätzte Abweichung entlang der Z‑Achse. | ||
TYPE_LINEAR_ACCELERATION |
SensorEvent.values[0] |
Beschleunigungskraft entlang der x-Achse (ohne die Schwerkraft). | m/s2 |
SensorEvent.values[1] |
Beschleunigungskraft entlang der Y-Achse (ohne die Schwerkraft). | ||
SensorEvent.values[2] |
Beschleunigungskraft entlang der Z‑Achse (ohne Schwerkraft). | ||
TYPE_ROTATION_VECTOR |
SensorEvent.values[0] |
Komponente des Drehvektors entlang der X-Achse (x * sin(θ/2)). | Ohne Einheit |
SensorEvent.values[1] |
Komponente des Drehvektors entlang der Y-Achse (y * sin(θ/2)). | ||
SensorEvent.values[2] |
Komponente des Drehvektors entlang der Z‑Achse (z * sin(θ/2)). | ||
SensorEvent.values[3] |
Skalare Komponente des Drehvektors ((cos(θ/2)).1 | ||
TYPE_SIGNIFICANT_MOTION |
– | – | – |
TYPE_STEP_COUNTER |
SensorEvent.values[0] |
Anzahl der Schritte, die der Nutzer seit dem letzten Neustart gemacht hat, während der Sensor aktiviert wurde. | Schritte |
TYPE_STEP_DETECTOR |
– | – | – |
1 Die Skalarkomponente ist ein optionaler Wert.
Der Drehvektorsensor und der Schwerkraftsensor sind die am häufigsten verwendeten Sensoren für die Bewegungserkennung und -überwachung. Der Drehvektorsensor ist besonders vielseitig und kann für eine Vielzahl von bewegungsbezogenen Aufgaben verwendet werden, z. B. für die Erkennung von Gesten, die Überwachung von Winkeländerungen und die Überwachung von Änderungen der relativen Ausrichtung. Der Rotationsvektorsensor ist beispielsweise ideal, ein Spiel, eine Augmented-Reality-App, einen zwei- oder dreidimensionalen Kompass oder eine App zur Kamerastabilisierung verwenden. In den meisten Fällen ist die Verwendung dieser Sensoren die bessere Wahl als die Verwendung Beschleunigungsmesser und den Sensor für geomagnetische Felder oder den Ausrichtungssensor.
Sensoren des Android Open Source-Projekts
Das Android Open Source Project (AOSP) bietet drei softwarebasierte Bewegungssensoren: ein
einen linearen Beschleunigungssensor und einen Rotationsvektorsensor. Diese Sensoren wurden in Android 4.0 aktualisiert und verwenden jetzt zusätzlich zu anderen Sensoren das Gyroskop eines Geräts, um Stabilität und Leistung zu verbessern. Wenn Sie diese Sensoren ausprobieren möchten, können Sie sie mit der getVendor()
-Methode und der getVersion()
-Methode identifizieren. Der Anbieter ist Google LLC und die Versionsnummer ist 3. Die Identifizierung dieser Sensoren anhand von Anbieter und Versionsnummer ist erforderlich, da das Android-System diese drei Sensoren als sekundäre Sensoren betrachtet. Wenn ein Gerätehersteller beispielsweise einen eigenen Gravitationssensor bereitstellt, wird der AOSP-Gravitationssensor als sekundärer Gravitationssensor angezeigt. Alle drei Sensoren benötigen ein Gyroskop: Wenn ein Gerät kein Gyroskop hat, werden diese Sensoren nicht angezeigt und können nicht verwendet werden.
Schwerkraftsensor verwenden
Der Schwerkraftsensor liefert einen dreidimensionalen Vektor, der die Richtung und Größe der Schwerkraft. Normalerweise wird dieser Sensor verwendet, um die relative Ausrichtung des Geräts im Raum zu bestimmen. Im folgenden Code wird gezeigt, wie Sie eine Instanz des Standardgravitationssensors abrufen:
Kotlin
val sensorManager = getSystemService(Context.SENSOR_SERVICE) as SensorManager val sensor: Sensor? = sensorManager.getDefaultSensor(Sensor.TYPE_GRAVITY)
Java
private SensorManager sensorManager; private Sensor sensor; ... sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE); sensor = sensorManager.getDefaultSensor(Sensor.TYPE_GRAVITY);
Die Einheiten sind dieselben wie beim Beschleunigungssensor (m/s2) und das Koordinatensystem ist das gleiche wie beim Beschleunigungssensor.
Hinweis:Wenn sich ein Gerät im Ruhezustand befindet, gibt die Ausgabe des Schwerkraftsensors sollte mit dem Beschleunigungsmesser übereinstimmen.
Linearen Beschleunigungsmesser verwenden
Der lineare Beschleunigungssensor liefert Ihnen einen dreidimensionalen Vektor für die Beschleunigung entlang jeder Geräteachse, ausschließlich der Schwerkraft. Sie können diesen Wert für die Gestenentdeckung verwenden. Der Wert kann auch als Eingabe für ein inertiales Navigationssystem dienen, das die Triangulation verwendet. Im folgenden Code wird gezeigt, wie Sie eine Instanz des Standardsensors für die lineare Beschleunigung abrufen:
Kotlin
val sensorManager = getSystemService(Context.SENSOR_SERVICE) as SensorManager val sensor: Sensor? = sensorManager.getDefaultSensor(Sensor.TYPE_LINEAR_ACCELERATION)
Java
private SensorManager sensorManager; private Sensor sensor; ... sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE); sensor = sensorManager.getDefaultSensor(Sensor.TYPE_LINEAR_ACCELERATION);
Dieser Sensor liefert Ihnen konzeptionell Beschleunigungsdaten gemäß der folgenden Beziehung:
linear acceleration = acceleration - acceleration due to gravity
Sie verwenden diesen Sensor in der Regel, wenn Sie Beschleunigungsdaten ohne Einfluss von Schwerkraft. Mit diesem Sensor können Sie beispielsweise feststellen, wie schnell Ihr Auto fährt. Die lineare Der Beschleunigungssensor hat immer einen Versatz, den Sie entfernen müssen. Am einfachsten geht das, um einen Kalibrierungsschritt in Ihre Anwendung zu integrieren. Während der Kalibrierung können Sie den Nutzer bitten, das Gerät auf einen Tisch zu legen und dann die Abweichungen für alle drei Achsen abzulesen. Diesen Wert können Sie dann subtrahieren, von den direkten Messwerten des Beschleunigungssensors abweichen, um die tatsächliche von Beschleunigungen.
Die Sensor-Koordinate entspricht dem System, das vom Beschleunigungssensor verwendet wird, sowie den Maßeinheiten (m/s2)
Rotationsvektorsensor verwenden
Der Rotationsvektor stellt die Ausrichtung des Geräts als Kombination aus einem Winkel und einem -Achse, an der sich das Gerät durch einen Winkel Θ um eine Achse (x, y oder z) gedreht hat. Die folgenden zeigt Ihnen, wie Sie eine Instanz des Standard-Rotationsvektorsensors abrufen:
Kotlin
val sensorManager = getSystemService(Context.SENSOR_SERVICE) as SensorManager val sensor: Sensor? = sensorManager.getDefaultSensor(Sensor.TYPE_ROTATION_VECTOR)
Java
private SensorManager sensorManager; private Sensor sensor; ... sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE); sensor = sensorManager.getDefaultSensor(Sensor.TYPE_ROTATION_VECTOR);
Die drei Elemente des Rotationsvektors werden wie folgt ausgedrückt:

Dabei ist die Größe des Rotationsvektors gleich sin(Θ/2) und die Richtung des Rotationsvektor entspricht der Richtung der Drehachse.

Abbildung 1: Vom Rotationsvektorsensor verwendetes Koordinatensystem.
Die drei Elemente des Drehvektors entsprechen den letzten drei Komponenten einer Einheitsquaternion (cos(θ/2), x*sin(θ/2), y*sin(θ/2), z*sin(θ/2)). Elemente des Rotationsvektors sind ohne Einheit. Die x-, y- und z-Achsen sind genauso definiert wie der Beschleunigungssensor. Die Referenz Koordinatensystem als direkte Orthonormalbasis definiert ist (siehe Abbildung 1). Dieses Koordinatensystem weist folgende Merkmale auf:
- X ist definiert als das Vektorprodukt Y x Z. Sie ist tangential zum Boden am aktuellen Standort des Geräts und zeigt ungefähr nach Osten.
- Y ist am aktuellen Standort des Geräts tangential für den Boden und zeigt auf geomagnetisch Nordpol.
- Z zeigt zum Himmel und ist senkrecht zur Bodenebene.
Eine Beispielanwendung, die die Verwendung des Drehvektorsensors zeigt, finden Sie unter RotationVectorDemo.java.
Bewegungssensor mit signifikanter
Der Sensor für relevante Bewegungen löst jedes Mal ein Ereignis aus, wenn eine relevante Bewegung erkannt wird, und deaktiviert sich dann selbst. Eine erhebliche Bewegung ist eine Bewegung, die zu einer Änderung des Standorts des Nutzers führen kann, z. B. wenn er zu Fuß unterwegs ist, Fahrrad fährt oder in einem fahrenden Auto sitzt. Der folgende Code zeigt Ihnen, wie man eine Instanz des Standard-Bewegungssensors für signifikante Bewegungen erhält und wie man ein Ereignis registriert Listener:
Kotlin
val sensorManager = getSystemService(Context.SENSOR_SERVICE) as SensorManager val mSensor: Sensor? = sensorManager.getDefaultSensor(Sensor.TYPE_SIGNIFICANT_MOTION) val triggerEventListener = object : TriggerEventListener() { override fun onTrigger(event: TriggerEvent?) { // Do work } } mSensor?.also { sensor -> sensorManager.requestTriggerSensor(triggerEventListener, sensor) }
Java
private SensorManager sensorManager; private Sensor sensor; private TriggerEventListener triggerEventListener; ... sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE); sensor = sensorManager.getDefaultSensor(Sensor.TYPE_SIGNIFICANT_MOTION); triggerEventListener = new TriggerEventListener() { @Override public void onTrigger(TriggerEvent event) { // Do work } }; sensorManager.requestTriggerSensor(triggerEventListener, mSensor);
Weitere Informationen finden Sie unter TriggerEventListener
.
Schrittzähler verwenden
Der Schrittzähler-Sensor gibt die Anzahl der Schritte an, die der Nutzer seit dem letzten Neustart gemacht hat während der Sensor aktiviert war. Der Schrittzähler hat eine höhere Latenz (bis zu 10 Sekunden), aber mehr genauer als der Schrittdetektorsensor.
Hinweis: Sie müssen die Berechtigung ACTIVITY_RECOGNITION
deklarieren, damit Ihre App diesen Sensor auf Geräten mit Android 10 (API-Level 29) oder höher verwenden kann.
Im folgenden Code wird gezeigt, wie Sie eine Instanz des Standardschrittzählersensors abrufen:
Kotlin
val sensorManager = getSystemService(Context.SENSOR_SERVICE) as SensorManager val sensor: Sensor? = sensorManager.getDefaultSensor(Sensor.TYPE_STEP_COUNTER)
Java
private SensorManager sensorManager; private Sensor sensor; ... sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE); sensor = sensorManager.getDefaultSensor(Sensor.TYPE_STEP_COUNTER);
Um den Akku der Geräte zu schonen, auf denen deine App ausgeführt wird, solltest du die Funktion
Klasse JobScheduler
, aus der der aktuelle Wert abgerufen werden soll
Schrittzähler-Sensors in einem bestimmten Intervall. Für verschiedene Arten von Apps sind unterschiedliche Intervalle für die Sensorabfragen erforderlich. Sie sollten dieses Intervall jedoch so lang wie möglich halten, es sei denn, Ihre App benötigt Echtzeitdaten vom Sensor.
Schritterkennungssensor verwenden
Der Schrittzähler löst jedes Mal ein Ereignis aus, wenn der Nutzer einen Schritt macht. Die Latenz beträgt bei weniger als 2 Sekunden liegen.
Hinweis: Sie müssen das
ACTIVITY_RECOGNITION
Berechtigung, damit deine App diesen Sensor auf Geräten verwenden kann, auf denen
Android 10 (API-Level 29) oder höher
Im folgenden Code wird gezeigt, wie Sie eine Instanz des Standardsensors für den Schrittzähler abrufen:
Kotlin
val sensorManager = getSystemService(Context.SENSOR_SERVICE) as SensorManager val sensor: Sensor? = sensorManager.getDefaultSensor(Sensor.TYPE_STEP_DETECTOR)
Java
private SensorManager sensorManager; private Sensor sensor; ... sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE); sensor = sensorManager.getDefaultSensor(Sensor.TYPE_STEP_DETECTOR);
Mit Rohdaten arbeiten
Die folgenden Sensoren stellen Ihrer App Rohdaten zu den linearen und Rotationskräften zur Verfügung, die auf das Gerät ausgeübt werden. Um die Werte aus müssen Sie Faktoren aus der Umgebung herausfiltern, wie die Schwerkraft. Möglicherweise müssen Sie auch einen Glättungsalgorithmus auf den Trend anwenden. um Rauschen zu reduzieren.
Beschleunigungsmesser verwenden
Ein Beschleunigungssensor misst die Beschleunigung, die auf das Gerät ausgeübt wird, einschließlich der Schwerkraft. Im folgenden Code wird gezeigt, wie Sie eine Instanz des Standardbeschleunigungssensors abrufen:
Kotlin
val sensorManager = getSystemService(Context.SENSOR_SERVICE) as SensorManager val sensor: Sensor? = sensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER)
Java
private SensorManager sensorManager; private Sensor sensor; ... sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE); sensor = sensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
Hinweis: Wenn Ihre App auf Android 12 (API-Level 31) oder höher ausgerichtet ist, ist dieser Sensor taktgesteuert.
Konzeptionell bestimmt ein Beschleunigungssensor die angewendete Beschleunigung auf ein Gerät (Ad) angewendet, indem die Kräfte gemessen werden, die auf den Sensor sich selbst (Fs) mithilfe der folgenden Beziehung zu:

Die Schwerkraft beeinflusst die gemessene Beschleunigung jedoch immer gemäß der folgenden Beziehung:

Wenn das Gerät auf einem Tisch liegt und nicht beschleunigt wird, Der Beschleunigungsmesser zeigt eine Größenordnung von g = 9,81 m/s2 an. Wenn sich das Gerät in und damit mit 9,81 m/s2 schnell auf den Boden zu, wodurch die der Beschleunigungsmesser eine Größenordnung von g = 0 m/s2 anzeigt. Um die tatsächliche Beschleunigung des Geräts zu messen, muss der Beitrag der Schwerkraft aus den Beschleunigungsmesserdaten entfernt werden. Dies kann durch die Anwendung eines Hochpassfilters erreicht werden. Umgekehrt ist ein Lowpass Filter kann verwendet werden, um die Schwerkraft zu isolieren. Das folgende Beispiel zeigt, wie Sie das tun können:
Kotlin
override fun onSensorChanged(event: SensorEvent) { // In this example, alpha is calculated as t / (t + dT), // where t is the low-pass filter's time-constant and // dT is the event delivery rate. val alpha: Float = 0.8f // Isolate the force of gravity with the low-pass filter. gravity[0] = alpha * gravity[0] + (1 - alpha) * event.values[0] gravity[1] = alpha * gravity[1] + (1 - alpha) * event.values[1] gravity[2] = alpha * gravity[2] + (1 - alpha) * event.values[2] // Remove the gravity contribution with the high-pass filter. linear_acceleration[0] = event.values[0] - gravity[0] linear_acceleration[1] = event.values[1] - gravity[1] linear_acceleration[2] = event.values[2] - gravity[2] }
Java
public void onSensorChanged(SensorEvent event){ // In this example, alpha is calculated as t / (t + dT), // where t is the low-pass filter's time-constant and // dT is the event delivery rate. final float alpha = 0.8; // Isolate the force of gravity with the low-pass filter. gravity[0] = alpha * gravity[0] + (1 - alpha) * event.values[0]; gravity[1] = alpha * gravity[1] + (1 - alpha) * event.values[1]; gravity[2] = alpha * gravity[2] + (1 - alpha) * event.values[2]; // Remove the gravity contribution with the high-pass filter. linear_acceleration[0] = event.values[0] - gravity[0]; linear_acceleration[1] = event.values[1] - gravity[1]; linear_acceleration[2] = event.values[2] - gravity[2]; }
Hinweis:Sie können Sensordaten auf viele verschiedene Arten filtern. Im Codebeispiel oben wird eine einfache Filterkonstante (Alpha) verwendet, um einen Tiefpassfilter zu erstellen. Dieser Filter wird von einer Zeitkonstante (t) abgeleitet, die eine grobe Darstellung der Latenz darstellt, fügt der Filter die Sensorereignisse und die Ereignislieferrate des Sensors (dt) hinzu. Im Codebeispiel wird zu Demonstrationszwecken ein Alphawert von 0,8 verwendet. Bei dieser Filtermethode benötigen Sie um einen anderen Alphawert auszuwählen.
Beschleunigungsmesser verwenden das standardmäßige Koordinatensystem des Sensors. In der Praxis bedeutet das, dass die folgenden Bedingungen gelten, wenn ein Gerät in seiner natürlichen Ausrichtung flach auf einem Tisch liegt:
- Wenn Sie das Gerät auf der linken Seite drücken, sodass es nach rechts bewegt wird, ist der Wert für die X‑Beschleunigung positiv.
- Wenn Sie das Gerät auf die Unterseite drücken (sodass es sich von Ihnen wegbewegt), beträgt der y-Beschleunigungswert positiv zu bewerten.
- Wenn Sie das Gerät mit einer Beschleunigung von A m/s2 in Richtung Himmel drücken, z-Beschleunigungswert ist gleich A + 9,81, was der Beschleunigung des Geräts entspricht (+A m/s2) abzüglich der Schwerkraft (-9,81 m/s2).
- Das ruhende Gerät hat einen Beschleunigungswert von +9,81, was der Beschleunigung des Geräts entspricht (0 m/s2 abzüglich der Schwerkraft, also -9,81 m/s2).
Im Allgemeinen eignet sich der Beschleunigungsmesser gut, wenn Sie die Gerätebewegung überwachen möchten. Fast jedes Android-Smartphone und -Tablet hat einen Beschleunigungsmesser, der etwa zehnmal weniger Strom verbraucht als die anderen Bewegungssensoren. Ein Nachteil ist, dass Sie möglicherweise Tiefpass- und Hochpassfilter implementieren müssen, um die Gravitationskräfte zu eliminieren und Geräusche zu reduzieren.
Gyroskop verwenden
Das Gyroskop misst die Umdrehungsgeschwindigkeit in Rad/s um die x-, y- und und die Z-Achse an. Der folgende Code zeigt, wie Sie eine Instanz des Standard-Gyroskops abrufen:
Kotlin
val sensorManager = getSystemService(Context.SENSOR_SERVICE) as SensorManager val sensor: Sensor? = sensorManager.getDefaultSensor(Sensor.TYPE_GYROSCOPE)
Java
private SensorManager sensorManager; private Sensor sensor; ... sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE); sensor = sensorManager.getDefaultSensor(Sensor.TYPE_GYROSCOPE);
Hinweis: Wenn Ihre App auf Android 12 (API-Level 31) oder höher ausgerichtet ist, ist dieser Sensor taktgesteuert.
Das Koordinatensystem des Sensors. ist mit dem für den Beschleunigungssensor verwendeten Sensor identisch. Eine positive Drehung ist eine Drehung gegen den Uhrzeigersinn. Das bedeutet, dass ein Beobachter, der von einem positiven Ort auf der X-, Y- oder Z-Achse auf ein Gerät am Ursprung blickt, eine positive Drehung meldet, wenn sich das Gerät scheinbar gegen den Uhrzeigersinn dreht. Dies ist die die standardmäßige mathematische Definition der positiven Rotation. Sie ist nicht mit der Definition für die vom Ausrichtungssensor verwendet wird.
Normalerweise wird die Ausgabe des Gyroskops über die Zeit integriert, um eine Drehung zu berechnen, die die Änderung der Winkel über den Zeitschritt beschreibt. Beispiel:
Kotlin
// Create a constant to convert nanoseconds to seconds. private val NS2S = 1.0f / 1000000000.0f private val deltaRotationVector = FloatArray(4) { 0f } private var timestamp: Float = 0f override fun onSensorChanged(event: SensorEvent?) { // This timestep's delta rotation to be multiplied by the current rotation // after computing it from the gyro sample data. if (timestamp != 0f && event != null) { val dT = (event.timestamp - timestamp) * NS2S // Axis of the rotation sample, not normalized yet. var axisX: Float = event.values[0] var axisY: Float = event.values[1] var axisZ: Float = event.values[2] // Calculate the angular speed of the sample val omegaMagnitude: Float = sqrt(axisX * axisX + axisY * axisY + axisZ * axisZ) // Normalize the rotation vector if it's big enough to get the axis // (that is, EPSILON should represent your maximum allowable margin of error) if (omegaMagnitude > EPSILON) { axisX /= omegaMagnitude axisY /= omegaMagnitude axisZ /= omegaMagnitude } // Integrate around this axis with the angular speed by the timestep // in order to get a delta rotation from this sample over the timestep // We will convert this axis-angle representation of the delta rotation // into a quaternion before turning it into the rotation matrix. val thetaOverTwo: Float = omegaMagnitude * dT / 2.0f val sinThetaOverTwo: Float = sin(thetaOverTwo) val cosThetaOverTwo: Float = cos(thetaOverTwo) deltaRotationVector[0] = sinThetaOverTwo * axisX deltaRotationVector[1] = sinThetaOverTwo * axisY deltaRotationVector[2] = sinThetaOverTwo * axisZ deltaRotationVector[3] = cosThetaOverTwo } timestamp = event?.timestamp?.toFloat() ?: 0f val deltaRotationMatrix = FloatArray(9) { 0f } SensorManager.getRotationMatrixFromVector(deltaRotationMatrix, deltaRotationVector); // User code should concatenate the delta rotation we computed with the current rotation // in order to get the updated rotation. // rotationCurrent = rotationCurrent * deltaRotationMatrix; }
Java
// Create a constant to convert nanoseconds to seconds. private static final float NS2S = 1.0f / 1000000000.0f; private final float[] deltaRotationVector = new float[4](); private float timestamp; public void onSensorChanged(SensorEvent event) { // This timestep's delta rotation to be multiplied by the current rotation // after computing it from the gyro sample data. if (timestamp != 0) { final float dT = (event.timestamp - timestamp) * NS2S; // Axis of the rotation sample, not normalized yet. float axisX = event.values[0]; float axisY = event.values[1]; float axisZ = event.values[2]; // Calculate the angular speed of the sample float omegaMagnitude = sqrt(axisX*axisX + axisY*axisY + axisZ*axisZ); // Normalize the rotation vector if it's big enough to get the axis // (that is, EPSILON should represent your maximum allowable margin of error) if (omegaMagnitude > EPSILON) { axisX /= omegaMagnitude; axisY /= omegaMagnitude; axisZ /= omegaMagnitude; } // Integrate around this axis with the angular speed by the timestep // in order to get a delta rotation from this sample over the timestep // We will convert this axis-angle representation of the delta rotation // into a quaternion before turning it into the rotation matrix. float thetaOverTwo = omegaMagnitude * dT / 2.0f; float sinThetaOverTwo = sin(thetaOverTwo); float cosThetaOverTwo = cos(thetaOverTwo); deltaRotationVector[0] = sinThetaOverTwo * axisX; deltaRotationVector[1] = sinThetaOverTwo * axisY; deltaRotationVector[2] = sinThetaOverTwo * axisZ; deltaRotationVector[3] = cosThetaOverTwo; } timestamp = event.timestamp; float[] deltaRotationMatrix = new float[9]; SensorManager.getRotationMatrixFromVector(deltaRotationMatrix, deltaRotationVector); // User code should concatenate the delta rotation we computed with the current rotation // in order to get the updated rotation. // rotationCurrent = rotationCurrent * deltaRotationMatrix; }
Standardgyroskope liefern Rohdrehungsdaten ohne Filterung oder Korrektur von Rauschen und Drift (Voreingenommenheit). In der Praxis führen Gyroskoprauschen und -drift zu Fehlern, die behoben werden müssen. kompensiert werden. Normalerweise werden Abweichung (Bias) und Rauschen durch das Überwachen anderer Sensoren wie des Gravitationssensors oder des Beschleunigungsmessers bestimmt.
Nicht kalibriertes Gyroskop verwenden
Das nicht kalibrierte Gyroskop ähnelt dem Gyroskop,
außer dass keine Gyroskopkompensation auf die Rotationsrate angewendet wird. Werkskalibrierung
und die Temperaturkompensation weiterhin
auf die Drehgeschwindigkeit angewendet. Das nicht kalibrierte
Das Gyroskop eignet sich für die Nachbearbeitung und Zusammenführung von Ausrichtungsdaten. Im Allgemeinen
gyroscope_event.values[0]
liegt in der Nähe von
uncalibrated_gyroscope_event.values[0] - uncalibrated_gyroscope_event.values[3]
.
Das bedeutet:
calibrated_x ~= uncalibrated_x - bias_estimate_x
Hinweis: Nicht kalibrierte Sensoren liefern Rohdaten und können eine gewisse Abweichung aufweisen. Ihre Messungen enthalten jedoch weniger Sprünge durch Korrekturen, die durch die Kalibrierung angewendet werden. Für einige Anwendungen sind diese nicht kalibrierten Ergebnisse möglicherweise geeigneter, da sie flüssiger und zuverlässiger sind. Wenn eine Anwendung z. B. versucht, eine eigene Sensorfusion durchzuführen, Kalibrierungen können die Ergebnisse verzerren.
Zusätzlich zu den Drehgeschwindigkeiten liefert das nicht kalibrierte Gyroskop auch die geschätzten Drift um jede Achse. Im folgenden Code wird gezeigt, wie Sie eine Instanz des standardmäßigen nicht kalibrierten Gyroskops abrufen:
Kotlin
val sensorManager = getSystemService(Context.SENSOR_SERVICE) as SensorManager val sensor: Sensor? = sensorManager.getDefaultSensor(Sensor.TYPE_GYROSCOPE_UNCALIBRATED)
Java
private SensorManager sensorManager; private Sensor sensor; ... sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE); sensor = sensorManager.getDefaultSensor(Sensor.TYPE_GYROSCOPE_UNCALIBRATED);
Zusätzliche Codebeispiele
Im Beispiel BatchStepSensor wird die Verwendung der auf dieser Seite beschriebenen APIs veranschaulicht.