OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 23707|回复: 17

电子罗盘——HMC5883L——三轴磁场传感器

[复制链接]

5

主题

13

帖子

0

精华

初级会员

Rank: 2

积分
53
金钱
53
注册时间
2014-5-16
在线时间
0 小时
发表于 2014-12-25 15:53:17 | 显示全部楼层 |阅读模式
(一) ATan,ATan2区别
 相比较ATan,ATan2究竟有什么不同?本篇介绍一下ATan2的用法及使用条件。

对于tan(θ) = y / x:

θ = ATan(y / x)求出的θ取值范围是[-PI/2, PI/2]。

θ = ATan2(y, x)求出的θ取值范围是[-PI, PI]。

  • 当 (xy) 在第一象限, 0 < θ < PI/2.

  • 当 (xy) 在第二象限 PI/2 < θPI.

  • 当 (xy) 在第三象限, -PI < θ < -PI/2.

  • 当 (xy) 在第四象限, -PI/2 < θ < 0.

当点(xy)在象限的边界也就是坐标轴上时:

  • 当 y 是 0,x 为非负值, θ = 0.

  • 当 y 是 0, x 是 负值, θ = PI.

  • 当 y 是 正值, x 是 0, θ = PI/2.

  • 当 y 是 负值, x 是 0, θ = -PI/2.

由此可知,一般情况下用ATan即可,当对所求出角度的取值范围有特殊要求时,应使用ATan2



(二) 什么是磁偏角和方位公式

磁偏角


磁偏角,即现实中指北针指向的磁极(地磁极)和我们地图上标注的传统意义的磁极是不重合的,有一个夹角。 你看地球仪上的地球也不是歪脖子转动么,就是这个意思。

下面是几何时间,如何定义方位。这里采用了反正切角的表达方式。

Atan2, 反正切角


公式


为了做这个电子罗盘,反正切角(Atan2)这种不知哪个星球来的东西都学习了。
π是180度,2π是360度,1/2π是90度... 其实这个反正切角就是射线(x,y)和x轴正向间的夹角。没什么好神秘的。如果y<0,射线在x轴下方,那么角度从x轴正向顺时针旋转,而且是负值;如果y>0,角度从x轴正向逆时针旋转。大量图示和公式来自基维百科。

几个特殊点的取值。
(0,0)夹角为0
(0, 1)对于的复平面夹角为π/2,
(?1, 0)对于复平面的夹角为π,
(0, ?1)对于复平面的夹角为3π/2,

下面看下atan2和我们一般atan的区别。三维图,找到x,y轴就省事了。其实只是个计量方法的不同,不晓得为什么要弄得这么复杂的样子。

atan2, 按照y>0 和 y < 0分别从逆时针和顺时针计算


tan,就是我们一般的正切


****
看完了这些基础知识,我们来分析honeywell的HMC5883三轴数位罗盘对角度的计算公式。

angle= atan2(y,x) * (180 / 3.14159265) + 180; 

其实就是这样的:
角度 = atan2(y,x) * (180 / π) + 180,这里角度用0~360°表示

因为atan2(y,x) 算出来的会是多少π,所以后面用了个 180/π来换算成度数(0~360°)。但是,但是后面那个 +180是干嘛?

如果是60°的角,+180就变成了240°,从A点变成了B点变成了下面这个图。

+180°引起的效果 

仔细想想公式,因为这种反正切角的范围是从-π到π (-180°~180°), 而我们通常读出的指南针角度是0°~360°,所以需要把这个范围进行平移180°,到指南针的角度。但是这样一来,原来60°的角度变成了240°,也就是,整个象限沿着虚线被"镜像"了一下。


下图x轴要变成"南“的位置,好吧,这样就正常了。

p8880518.jpg


于是我们得到了下面这个方位判断:

    if((angle < 22.5) || (angle > 337.5 ))
        Serial.print("South");
    if((angle > 22.5) && (angle < 67.5 ))
        Serial.print("South-West");
    if((angle > 67.5) && (angle < 112.5 ))
        Serial.print("West");
    if((angle > 112.5) && (angle < 157.5 ))
        Serial.print("North-West");
    if((angle > 157.5) && (angle < 202.5 ))
        Serial.print("North");
    if((angle > 202.5) && (angle < 247.5 ))
        Serial.print("NorthEast");
    if((angle > 247.5) && (angle < 292.5 ))
        Serial.print("East");
    if((angle > 292.5) && (angle < 337.5 ))
        Serial.print("SouthEast");

假设我们是60°角,也就是指北针正北顺时针转60度位置,应该在NE(东北)位置,套用上面的公式,60 + 180 = 240°,然后套用上面的条件判断:angle > 202.5° 并且angle < 247.5°,处于NorthEast (东北)位置,正确。 

正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

88

主题

7377

帖子

5

精华

资深版主

Rank: 8Rank: 8

积分
14980
金钱
14980
注册时间
2013-11-13
在线时间
1823 小时
发表于 2014-12-25 15:58:16 | 显示全部楼层
好帖!!!mark一下,一直不知道磁力计的得到的角度和方向之间的关系!
开往春天的手扶拖拉机
回复 支持 反对

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165540
金钱
165540
注册时间
2010-12-1
在线时间
2117 小时
发表于 2014-12-25 22:31:24 | 显示全部楼层
不错,谢谢分享。
我是开源电子网www.openedv.com站长,有关站务问题请与我联系。
正点原子STM32开发板购买店铺http://openedv.taobao.com
正点原子官方微信公众平台,点击这里关注“正点原子”
回复 支持 反对

使用道具 举报

21

主题

2205

帖子

0

精华

资深版主

Rank: 8Rank: 8

积分
5141
金钱
5141
注册时间
2014-8-26
在线时间
1317 小时
发表于 2014-12-25 23:14:15 | 显示全部楼层
mark。。。。。
回复 支持 反对

使用道具 举报

5

主题

36

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
208
金钱
208
注册时间
2015-3-14
在线时间
33 小时
发表于 2015-3-16 15:34:10 | 显示全部楼层
看到 楼主的帖子真是如逢甘霖。一直不知道这个x轴为什么指南。直到昨天晚上11.40才看到。相见恨晚啊。。。。。太感谢楼主的分享了恍然大悟啊。
回复 支持 反对

使用道具 举报

12

主题

40

帖子

0

精华

初级会员

Rank: 2

积分
123
金钱
123
注册时间
2014-9-25
在线时间
3 小时
发表于 2015-4-28 23:11:00 | 显示全部楼层
为什么我得到的数据变化很大啊。。根本就到不了几度。从20度直接到300多度了
回复 支持 反对

使用道具 举报

164

主题

1230

帖子

1

精华

金牌会员

Rank: 6Rank: 6

积分
1477
金钱
1477
注册时间
2014-5-21
在线时间
342 小时
发表于 2015-4-29 08:27:58 | 显示全部楼层
《MATLAB面向对象编程——从入门到设计模式》计算某一个角度用函数atan2(因为atan函数计算出来的只是主值,atan2函数求出来的才是在各个象限里面的角度值)
彼高丽者,边夷贱类,不足待以仁义,不可责以常礼。古来以鱼鳖畜之,宜从阔略。若必欲绝其种类,恐兽穷则搏。
回复 支持 反对

使用道具 举报

37

主题

181

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
485
金钱
485
注册时间
2015-5-5
在线时间
34 小时
发表于 2015-5-15 10:58:36 | 显示全部楼层
不错哦。。有程序分享吗?结合到看就更好了
弹起华丽的乐章 撕下最后的伪装
回复 支持 反对

使用道具 举报

12

主题

31

帖子

0

精华

初级会员

Rank: 2

积分
100
金钱
100
注册时间
2015-3-21
在线时间
0 小时
发表于 2015-6-10 11:20:10 | 显示全部楼层
受益匪浅!!
serioly every minute
回复 支持 反对

使用道具 举报

1

主题

21

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
349
金钱
349
注册时间
2014-7-25
在线时间
43 小时
发表于 2015-9-5 11:03:35 | 显示全部楼层
谢谢分享~~
回复 支持 反对

使用道具 举报

21

主题

299

帖子

0

精华

金牌会员

Rank: 6Rank: 6

积分
1837
金钱
1837
注册时间
2013-7-29
在线时间
278 小时
发表于 2016-2-26 13:04:47 | 显示全部楼层
,讲解真清楚,谢谢了!
回复 支持 反对

使用道具 举报

13

主题

206

帖子

1

精华

高级会员

Rank: 4

积分
613
金钱
613
注册时间
2014-10-26
在线时间
32 小时
发表于 2016-4-14 19:03:08 | 显示全部楼层
我用hmc5883,关键代码如下,但是得到的angle不正常啊,有时候上到几万去,XY倒是正常                           HMC5883L_ReadData();                /* 读取 MPU-6050的数据到全局变量 g_tMPU6050 */
                       
                        /* 显示 g_tHMC5883L 结构体成员中的数据 */
                        {
                                printf("X=%d(%5d,%5d),Y=%d(%5d,%5d),Z=%6d(%5d,%5d)\r\n",
                                        g_tMag.X, g_tMag.X_Min, g_tMag.X_Max,
                                        g_tMag.Y, g_tMag.Y_Min, g_tMag.Y_Max,
                                        g_tMag.Z, g_tMag.Z_Min, g_tMag.Z_Max);
                        }
                        printf("/***********************/ \r\n");
                       
                        Compute_and_Save();
                        angle_x = g_tMag.X -Mag_UserCal_Offset_X;
                        angle_y = g_tMag.Y -Mag_UserCal_Offset_Y;
                        printf("Angle_X=%d\r\n",angle_x);
                        printf("Angle_Y=%d\r\n",angle_y);
                       
                        angle= atan2(angle_y,angle_x) * (180 / 3.14159265) ;
                        printf("Angle=%d\r\n",angle);

学习!
回复 支持 反对

使用道具 举报

7

主题

23

帖子

0

精华

初级会员

Rank: 2

积分
50
金钱
50
注册时间
2016-7-9
在线时间
9 小时
发表于 2016-8-14 14:11:53 | 显示全部楼层
非常有用,谢谢楼主!
回复 支持 反对

使用道具 举报

22

主题

44

帖子

0

精华

初级会员

Rank: 2

积分
81
金钱
81
注册时间
2016-3-29
在线时间
31 小时
发表于 2016-8-15 14:02:35 | 显示全部楼层
非常好!!!谢谢分享
回复 支持 反对

使用道具 举报

16

主题

173

帖子

0

精华

金牌会员

Rank: 6Rank: 6

积分
2441
金钱
2441
注册时间
2014-11-5
在线时间
348 小时
发表于 2016-8-16 18:34:57 | 显示全部楼层
按照你的说法x轴指向s,y轴不是应该指向w,然而你标注的是指向e,还是理解出问题了
回复 支持 反对

使用道具 举报

0

主题

1

帖子

0

精华

新手入门

积分
18
金钱
18
注册时间
2016-11-24
在线时间
3 小时
发表于 2016-11-24 16:04:09 | 显示全部楼层
MARK!
回复 支持 反对

使用道具 举报

18

主题

79

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
302
金钱
302
注册时间
2016-10-1
在线时间
77 小时
发表于 2016-12-1 10:17:58 | 显示全部楼层
非常棒
回复 支持 反对

使用道具 举报

0

主题

1

帖子

0

精华

新手上路

积分
32
金钱
32
注册时间
2016-1-28
在线时间
12 小时
发表于 2017-3-10 21:54:52 | 显示全部楼层
MARK !
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2025-7-13 14:52

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表