利用51单片机读取MPU9150中AK8975C的原始数据
来源:互联网 发布:怎么看10月经济数据 编辑:程序博客网 时间:2024/06/02 04:32
//利用51单片机,晶振11.0592,串口调试助手上波特率设置为9600,数据位8位,停止位1#include <REG51.H> #include <math.h> //Keil library #include <stdio.h> //Keil library #include <INTRINS.H>typedef unsigned char uchar;typedef unsigned short ushort;typedef unsigned int uint;//****************************************// 定义51单片机端口//****************************************#define DataPort P0 //LCD1602数据端口sbit SCL=P2^2; //IIC时钟引脚定义sbit SDA=P2^3; //IIC数据引脚定义//****************************************// 定义MPU6050内部地址//****************************************#define SMPLRT_DIV 0x19 //陀螺仪采样率,典型值:0x07(125Hz)#define CONFIG 0x1A //低通滤波频率,典型值:0x06(5Hz)#define HXL 0X03#define HXH 0X04#define HYL 0X05#define HYH 0X06#define HZL 0X07#define HZH 0X08#define CNTL 0X0A#define INT_PIN_CFG 0X37#define USER_CTRL 0X6A#define MPU9150SLAADD 0XD0#define MAGADD 0X18#define PWR_MGMT_1 0x6B //电源管理,典型值:0x00(正常启用)#define WHO_AM_I 0x75 //IIC地址寄存器(默认数值0x68,只读)//****************************************//定义类型及变量//****************************************uchar dis[6]; //显示数字(-511至512)的字符数组int dis_data; //变量//****************************************//函数声明//****************************************void delay(unsigned int k); //延时 void lcd_printf(uchar *s,int temp_data);//MPU6050操作函数void InitMPU6050(); //初始化MPU6050void Delay5us();void I2C_Start();void I2C_Stop();void I2C_SendACK(bit ack);bit I2C_RecvACK();void I2C_SendByte(uchar dat);uchar I2C_RecvByte();void I2C_ReadPage();void I2C_WritePage();void display_ACCEL_x();void display_ACCEL_y();void display_ACCEL_z();uchar Single_ReadI2C(uchar Slave_Address,uchar REG_Address); //读取I2C数据void Single_WriteI2C(uchar Slave_Address,uchar REG_Address,uchar REG_data); //向I2C写入数据//****************************************//整数转字符串//****************************************void lcd_printf(uchar *s,int temp_data){ if(temp_data<0) { temp_data=-temp_data; *s='-'; } else *s=' '; *++s =temp_data/10000+0x30; temp_data=temp_data%10000; //取余运算 *++s =temp_data/1000+0x30; temp_data=temp_data%1000; //取余运算 *++s =temp_data/100+0x30; temp_data=temp_data%100; //取余运算 *++s =temp_data/10+0x30; temp_data=temp_data%10; //取余运算 *++s =temp_data+0x30; }//****************************************void SeriPushSend(uchar send_data){ SBUF=send_data; while(!TI);TI=0; }//****************************************//延时//****************************************void delay(unsigned int k) { unsigned int i,j; for(i=0;i<k;i++) { for(j=0;j<121;j++); } }//**************************************//延时5微秒(STC90C52RC@12M)//不同的工作环境,需要调整此函数//当改用1T的MCU时,请调整此延时函数//**************************************void Delay5us(){ _nop_();_nop_();_nop_();_nop_(); _nop_();_nop_();_nop_();_nop_(); _nop_();_nop_();_nop_();_nop_(); _nop_();_nop_();_nop_();_nop_(); _nop_();_nop_();_nop_();_nop_(); _nop_();_nop_();_nop_();_nop_();}//**************************************//I2C起始信号//**************************************void I2C_Start(){ SDA = 1; //拉高数据线 SCL = 1; //拉高时钟线 Delay5us(); //延时 SDA = 0; //产生下降沿 Delay5us(); //延时 SCL = 0; //拉低时钟线}//**************************************//I2C停止信号//**************************************void I2C_Stop(){ SDA = 0; //拉低数据线 SCL = 1; //拉高时钟线 Delay5us(); //延时 SDA = 1; //产生上升沿 Delay5us(); //延时}//**************************************//I2C发送应答信号//入口参数:ack (0:ACK 1:NAK)//**************************************void I2C_SendACK(bit ack){ SDA = ack; //写应答信号 SCL = 1; //拉高时钟线 Delay5us(); //延时 SCL = 0; //拉低时钟线 Delay5us(); //延时}//**************************************//I2C接收应答信号//**************************************bit I2C_RecvACK(){ SCL = 1; //拉高时钟线 Delay5us(); //延时 CY = SDA; //读应答信号 SCL = 0; //拉低时钟线 Delay5us(); //延时 return CY;}//**************************************//向I2C总线发送一个字节数据//**************************************void I2C_SendByte(uchar dat){ uchar i; for (i=0; i<8; i++) //8位计数器 { dat <<= 1; //移出数据的最高位 SDA = CY; //送数据口 SCL = 1; //拉高时钟线 Delay5us(); //延时 SCL = 0; //拉低时钟线 Delay5us(); //延时 } I2C_RecvACK();}//**************************************//从I2C总线接收一个字节数据//**************************************uchar I2C_RecvByte(){ uchar i; uchar dat = 0; SDA = 1; //使能内部上拉,准备读取数据, for (i=0; i<8; i++) //8位计数器 { dat <<= 1; SCL = 1; //拉高时钟线 Delay5us(); //延时 dat |= SDA; //读数据 SCL = 0; //拉低时钟线 Delay5us(); //延时 } return dat;}//**************************************//向I2C设备写入一个字节数据//**************************************void Single_WriteI2C(uchar Slave_Address,uchar REG_Address,uchar REG_data){ I2C_Start(); //起始信号 I2C_SendByte(Slave_Address); //发送设备地址+写信号 I2C_SendByte(REG_Address); //内部寄存器地址, I2C_SendByte(REG_data); //内部寄存器数据, I2C_Stop(); //发送停止信号}//**************************************//从I2C设备读取一个字节数据//**************************************uchar Single_ReadI2C(uchar Slave_Address,uchar REG_Address){ uchar REG_data; I2C_Start(); //起始信号 I2C_SendByte(Slave_Address); //发送设备地址+写信号 I2C_SendByte(REG_Address); //发送存储单元地址,从0开始 I2C_Start(); //起始信号 I2C_SendByte(Slave_Address+1); //发送设备地址+读信号 REG_data=I2C_RecvByte(); //读出寄存器数据 I2C_SendACK(1); //接收应答信号 I2C_Stop(); //停止信号 return REG_data;}//**************************************//初始化MPU6050//**************************************void InitMPU6050(){ Single_WriteI2C(MPU9150SLAADD,PWR_MGMT_1,0x00); //解除休眠状态 Single_WriteI2C(MPU9150SLAADD,SMPLRT_DIV,0x07); Single_WriteI2C(MPU9150SLAADD,CONFIG, 0x06); Single_WriteI2C(MPU9150SLAADD,INT_PIN_CFG,0x02); Single_WriteI2C(MPU9150SLAADD,USER_CTRL,0x00); Single_WriteI2C(MAGADD,CNTL, 0x00); delay(100); Single_WriteI2C(MAGADD,CNTL, 0x01);}//**************************************//合成数据//**************************************int GetData(uchar REG_Address){ uchar H,L; H=(Single_ReadI2C(MAGADD,REG_Address)); Single_WriteI2C(MAGADD,CNTL, 0x01);//此处非常关键, //因为日本公司的数据手册上说,在单次测量模式下,每读取一次, //会自动回归power down mode ,所以这里重新设置为单次测量模式 L=Single_ReadI2C(MAGADD,REG_Address-1); Single_WriteI2C(MAGADD,CNTL, 0x01); return (H<<8)+L; //合成数据}//**************************************//在1602上显示10位数据//**************************************void Display10BitData(int value){ uchar i;// value/=64; //转换为10位数据 lcd_printf(dis, value); //转换数据显示 for(i=0;i<6;i++) { SeriPushSend(dis[i]); }}void init_uart(){ TMOD=0x21; TH1=0xfd; TL1=0xfd; SCON=0x50; PS=1; //串口中断设为高优先级别 TR0=1; //启动定时器 TR1=1; ET0=1; //打开定时器0中断 ES=1; EA=1;}//*********************************************************//主程序//*********************************************************void main(){ delay(500); //上电延时 init_uart(); InitMPU6050(); //初始化MPU6050 delay(150); while(1) { Display10BitData(GetData(HXH)); Display10BitData(GetData(HYH)); Display10BitData(GetData(HZH)); SeriPushSend(0x0d); SeriPushSend(0x0a);//换行,回车 delay(100); }}
0 0
- 利用51单片机读取MPU9150中AK8975C的原始数据
- 单片机采集的MPU6050原始数据对应关系
- 51单片机利用IIC总线对LM75A温度进行读取
- CC2540读取MPU6050原始数据
- ubuntu下的EDID原始数据读取和解析
- 利用51单片机制作的电子时钟
- 利用“串口调试助手”等软件调试 PROTEUS 环境中 51单片机 的串行通信
- MPU9250配置及原始数据读取
- 找出与原始数据中没有的数据的算法
- glm 中 数据类型 与 原始数据(c++ 数组)之间的转换
- PHP中支持的原始数据类型和伪类型
- Java的原始数据类型
- 原始数据的分析
- javascript的原始数据类型
- 利用51单片机输出pwm
- 利用51单片机制作一个秒表的详细过程
- 51单片机-利用定时器设计的简单时钟
- 【库函数版本】基于STM32F103的MPU6050的原始数据读取程序详解
- 阿里云CentOS 安装tcpdump
- I帧 P帧 B帧
- LeetCode 31.Next Permutation
- Google Web Toolkit搭建Web扫描应用
- 数据库表的迁移复制的SQL操作
- 利用51单片机读取MPU9150中AK8975C的原始数据
- Cryptography-week1
- 使用jaxp进行dom解析
- MySQL外键约束On Delete、On Update各取值的含义
- linq group by Having 语句的写法.
- Linux free 查看内存
- iOS 在UILabel显示不同的字体和颜色
- android天天理财项目构建思路代码和总结知识点--2
- MFC工程,字符集使用多字节,界面就变成WIN95风格的解决办法