倾斜补偿罗盘与外部磁力计和加速度计

时间:2016-08-25 07:59:48

标签: ios swift accelerometer trigonometry

我正在尝试编写一个应用程序,从BLE连接的磁力计和加速度计中获取原始数据,以创建倾斜补偿罗盘。我的代码是:

func tiltCompass(AxR:Float,AyR:Float,AzR:Float,MxR:Float,MyR:Float,MzR:Float) - > (浮动,俯仰:浮动,滚动:浮动,加速:浮动,大小:浮动){

//AxR, AyR, AzR = Raw accelerometer readings in milli G
//MxR, MyR, MzR = Raw magnotometer readings in milli guass

let pitch           = atan2(AxR, sqrtf(powf(AyR, 2)+powf(AzR, 2)))  //p .. asin(-AxR)
let roll            = atan2(AyR, sqrtf(powf(AxR, 2)+powf(AzR, 2)))  //γ .. asin(AyR/acos(pitch))

let acceleration    = sqrt(powf(AxR, 2) + powf(AyR,2) + powf(AzR, 2)) //if not equal to 1 then linear or angular Acceleration detectec
let magnitude       = sqrt(powf(MxR, 2) + powf(MyR,2) + powf(MzR, 2)) //if not equal to 1 then mag interefence or pitch/roll present

//MxC, MyC, MzC =  Tilt compensated magnetic sensor measurements
let MxC             = (MxR * acos(pitch)) + (MzR * asin(pitch))
let MyC             = (MxR * asin(roll) * asin(pitch)) + (MyR * acos(roll)) - (MzR * asin(roll) * acos(pitch))
let MzC             = (-MxR * acos(roll) * asin(pitch)) + (MyR * asin(roll)) + (MzR * acos(roll) * acos(pitch))

//Heading
    var heading : Float = 0
    if MxC > 0 && MyC >= 0 {heading = atan2f(MyC,MxC)}
    else if MxC < 0 {heading = 180 + atan2f(MyC,MxC)}
    else if MxC > 0 && MyC <= 0 {heading = 360 + atan2f(MyC,MxC)}
    else if MxC == 0 && MyC < 0 {heading = 90}
    else if MxC == 0 && MyC > 0 {heading = 270}

return (heading, pitch, roll, acceleration, magnitude)

}

运行并输出到控制台进行测试时,我得到以下结果:

`print ("Tilt Heading :: \(titlheading)"`)

原始输出,通过使用0.5ms采样率的设备缓慢旋转360度:

Tilt Heading :: (359.583313, 0.0420875959, -0.00037289664, 981.505249, 140.133362)
Tilt Heading :: (359.620483, 0.0400086045, 0.000686392013, 977.575562, 141.776596)
Tilt Heading :: (359.604218, 0.0409856997, -0.000686022104, 978.102661, 140.800262)
Tilt Heading :: (359.621552, 0.0415208116, 0.0, 980.199829, 141.251465)
Tilt Heading :: (359.605988, 0.0415050909, -0.000996833201, 979.100708, 143.005798)
Tilt Heading :: (359.617432, 0.0315867998, -0.0142858513, 952.233215, 141.984436)
Tilt Heading :: (359.66037, 0.0344147533, 0.00562020484, 976.83783, 143.398621)
Tilt Heading :: (359.780029, 0.0266412869, 0.00737870578, 975.518738, 142.221939)
Tilt Heading :: (359.845642, 0.0286898259, 0.000808929733, 980.307739, 139.077515)
Tilt Heading :: (359.875763, 0.0289015751, -0.00155698066, 979.460205, 131.390213)
Tilt Heading :: (359.960602, 0.0238598455, 0.0107485456, 981.826172, 127.953026)
Tilt Heading :: (0.0993536413, 0.0159567893, 0.0109700477, 978.684509, 119.979263)
Tilt Heading :: (0.211536095, 0.0434884764, -0.0195928887, 980.775757, 107.317924)
Tilt Heading :: (0.325962782, 0.0267457329, 0.0152643193, 983.115173, 94.8423309)
Tilt Heading :: (0.332540244, 0.0264445059, 0.00895909593, 980.469238, 83.6867523)
Tilt Heading :: (0.344065964, 0.0380582735, -0.00623759581, 977.947266, 72.580513)
Tilt Heading :: (0.430158406, 0.02798892, 0.00858225394, 980.873291, 67.669838)
Tilt Heading :: (0.370779216, 0.0302195679, 0.00629223092, 979.150513, 63.4612465)
Tilt Heading :: (0.289538383, 0.0335264429, -0.00168223935, 979.052612, 55.8212128)
Tilt Heading :: (0.178537324, 0.0272957645, 0.0116259437, 981.189819, 48.8469582)
Tilt Heading :: (359.930176, 0.0456191301, 0.0042596627, 973.78894, 46.9943542)
Tilt Heading :: (0.114507265, 0.0474723466, 0.00697499886, 979.506409, 48.846962)
Tilt Heading :: (359.87915, 0.0223429911, 0.0201583095, 977.479614, 49.1066818)
Tilt Heading :: (359.463013, 0.041566588, 0.006531836, 980.588928, 45.7328796)
Tilt Heading :: (359.108643, 0.0457907319, 0.00280253845, 979.47052, 58.2302399)
Tilt Heading :: (359.009003, 0.0519429594, -0.00353998039, 982.210876, 61.2032242)
Tilt Heading :: (359.018799, 0.0453071184, 0.000811007048, 977.796753, 72.7237701)
Tilt Heading :: (358.989746, 0.0428104326, 0.0182086546, 974.919983, 86.2864609)
Tilt Heading :: (359.111145, 0.0405384526, 0.001929875, 979.856873, 105.036392)
Tilt Heading :: (359.134888, 0.037665993, -0.00355373905, 978.408142, 111.559624)
Tilt Heading :: (359.195068, 0.0360276364, -0.0083027631, 977.155823, 122.110992)
Tilt Heading :: (359.29718, 0.0381992422, -0.0127511648, 975.937317, 133.16391)
Tilt Heading :: (359.361481, 0.0402125083, -0.01025254, 981.725281, 140.315903)
Tilt Heading :: (359.467102, 0.0443913862, -0.00392110227, 980.084106, 141.815857)
Tilt Heading :: (359.544525, 0.0404609852, -0.00336046354, 980.223816, 143.996384)
Tilt Heading :: (359.563568, 0.0364769474, -0.00716915308, 978.506104, 146.075821)
Tilt Heading :: (359.625275, 0.0326416567, -0.00985956006, 977.54425, 143.6297)
Tilt Heading :: (359.677765, 0.0283227563, -0.0191305373, 975.776978, 145.19458)
Tilt Heading :: (359.717773, 0.0356077142, 0.000437195326, 976.680237, 146.306961)
Tilt Heading :: (359.759583, 0.0338454209, -0.00644258223, 975.236816, 144.856705)
Tilt Heading :: (359.798248, 0.0389000885, -0.00695806136, 981.890625, 141.389816)
Tilt Heading :: (359.821259, 0.0386202037, -0.00193677912, 976.363892, 144.480133)
Tilt Heading :: (359.794495, 0.0383632295, 0.000625674089, 974.948547, 143.698517)
Tilt Heading :: (359.801819, 0.0391565114, 0.000623352069, 978.580322, 143.317673)
Tilt Heading :: (359.799316, 0.0375518836, 0.0, 976.505432, 146.329071)

原始MxC和MxY输出:

MxC :: 136.499 :: MyC :: 64.3293
MxC :: 141.945 :: MyC :: 72.8294
MxC :: 138.629 :: MyC :: 67.2004
MxC :: 141.684 :: MyC :: 74.0713
MxC :: 142.802 :: MyC :: 87.7088
MxC :: 140.387 :: MyC :: 100.164
MxC :: 132.326 :: MyC :: 112.583
MxC :: 127.345 :: MyC :: 114.873
MxC :: 128.753 :: MyC :: 114.533
MxC :: 121.509 :: MyC :: 119.921
MxC :: 116.456 :: MyC :: 136.453
MxC :: 97.3599 :: MyC :: 146.399
MxC :: 84.349 :: MyC :: 141.576
MxC :: 69.9021 :: MyC :: 146.072
MxC :: 54.5572 :: MyC :: 144.087
MxC :: 40.0276 :: MyC :: 148.076
MxC :: 32.3366 :: MyC :: 136.623
MxC :: 18.0619 :: MyC :: 135.039
MxC :: 7.25728 :: MyC :: 117.712
MxC :: 1.14393 :: MyC :: 101.884
MxC :: -3.98472 :: MyC :: 87.3294
MxC :: -6.75507 :: MyC :: 74.646
MxC :: -10.5574 :: MyC :: 52.1823
MxC :: -2.05467 :: MyC :: 40.4278
MxC :: 6.91559 :: MyC :: 33.662
MxC :: 10.0441 :: MyC :: 33.2202
MxC :: 10.5631 :: MyC :: 39.0956
MxC :: 13.7499 :: MyC :: 17.9752
MxC :: 30.0131 :: MyC :: -1.86769
MxC :: 68.7336 :: MyC :: -26.9304
MxC :: 97.4751 :: MyC :: -18.8135
MxC :: 124.867 :: MyC :: -8.67472
MxC :: 143.179 :: MyC :: 24.6331
MxC :: 151.311 :: MyC :: 55.8918
MxC :: 151.278 :: MyC :: 75.1455
MxC :: 152.033 :: MyC :: 69.4944
MxC :: 149.935 :: MyC :: 75.8773
MxC :: 153.172 :: MyC :: 74.0412
MxC :: 153.288 :: MyC :: 72.4933
MxC :: 149.411 :: MyC :: 77.2322
MxC :: 149.469 :: MyC :: 75.1191
MxC :: 149.95 :: MyC :: 78.3858

不确定我哪里出错了。花了很长时间研究这个并在网上进行研究。有什么帮助吗?

1 个答案:

答案 0 :(得分:0)

您希望359.xx附近的数字显示为小的负数。是吗?

在这种情况下,我会在类中添加一个计算属性,如下所示:

    var normalizedX: Double = {
        let x1 = x % 360.0
        return x1 > 180.0 ? (x1 - 360.0) : x1
    }

编辑:另一个问题可能是,atanf,acos和他们都使用弧度+ -PI而不是0..360。有关详情,请参阅此处:atanf man page