gpt4 book ai didi

ios - 罗盘和陀螺仪传感器融合 : between 0 and 360 degrees

转载 作者:塔克拉玛干 更新时间:2023-11-02 21:53:45 26 4
gpt4 key购买 nike

我正在开发一个小型室内导航应用程序,我在其中使用陀螺仪和指南针来确定设备方向。我使用陀螺仪来平滑罗盘数据。我的传感器融合如下所示。这是我的 motionHandler,一切都在这里发生。

// Listen to events from the motionManager
motionHandler = ^ (CMDeviceMotion *motion, NSError *error) {

__block float heading;
heading = mHeading;

CMAttitude *currentAttitude = motion.attitude;

//Initial heading setting
if (lastHeading == 0 && heading != 0) {
updatedHeading = heading;
}
lastHeading = heading;

if (oldQuaternion.w != 0 || oldQuaternion.x != 0 || oldQuaternion.y != 0 || oldQuaternion.z != 0){
diffQuaternion = [self multiplyQuaternions:[self inverseQuaternion:oldQuaternion] :currentAttitude.quaternion];
diffQuaternion = [self normalizeQuaternion:diffQuaternion];
}
oldQuaternion = currentAttitude.quaternion;

diffYaw = RADIANS_TO_DEGREES([self yawFromQuaternion:diffQuaternion]);

quaternion = currentAttitude.quaternion;

//Get Pitch
rpy.pitch = -[self pitchFromQuaternion:quaternion];
rpy.pitch += M_PI/2;

//Use Yaw-Difference for Heading
updatedHeading = updatedHeading - diffYaw;

//Heading has to be between 0 and 360 degrees
if (updatedHeading < 0) {
updatedHeading = 360 + updatedHeading;
}
else if (updatedHeading > 360) {
updatedHeading -= 360;
}

//fusionate gyro estimated heading with new magneticHeading
updatedHeading = (19.0*updatedHeading + 1.0*heading)/20.0;

//generate queternion
rotation = [self createFromAxisAngle:0 :rpy.pitch :DEGREES_TO_RADIANS(updatedHeading)];
};

实际的传感器融合公式是这一行:updatedHeading = (19.0*updatedHeading + 1.0*heading)/20.0;。这是我的 didUpdateHeading 函数,它接收最新的航向信息:

- (void)locationManager:(CLLocationManager *)manager didUpdateHeading:(CLHeading *)newHeading
{
// Get new heading
mHeading = newHeading.magneticHeading;

mHeading += 90;

if (mHeading > 360) {
mHeading -= 360;
}
}

diffYaw 是陀螺仪计算出的航向变化。 rotation 是最后的四元数。这工作完美,除了一个特殊情况:在 0 度和 360 度之间的过渡。

如果 updatedHeading 接近但小于 360 且 mHeading 刚好高于 0,则结​​果会以圆圈形式移动。例如,如果 updatedHeading = 355 和 mHeading = 5,正确的结果应该在 360 和 5 之间。但是我的公式计算出 337,5 度,这显然是完全错误的!

我认为这个问题必须有任何通用的解决方法......

最佳答案

在这些类型的角度计算中,我通常会执行如下操作:

updatedHeading -= angleDiff(updatedHeading, mHeading) * 0.05;

其中 angleDiff() 是:

double angleDiff( double angle1, double angle2 )
{
double angle = angle1 - angle2;
if( angle > 180 ) {
angle -= 360;
} else if( angle <= -180 ) {
angle += 360;
}
return angle;
}

您可能希望通过以下方式更新 0-360 范围内的航向:

updatedHeading = fmod( updatedHeading + 360, 360 );

您的示例通过此计算得出 355.5。

关于ios - 罗盘和陀螺仪传感器融合 : between 0 and 360 degrees,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9050589/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com