写一段基于stc32芯片上将mpu6050原始数据转换成角度并在OLED模块上显示的C语言代码
时间: 2024-02-18 12:04:12 浏览: 81
好的,以下是一份基于stc32芯片将mpu6050原始数据转换成角度并在OLED模块上显示的C语言代码,仅供参考:
```
#include <reg52.h>
#include <intrins.h>
#include <stdio.h>
#include "oled.h"
#define MPU6050_ADDR 0xD0
#define MPU6050_SMPLRT_DIV 0x19
#define MPU6050_CONFIG 0x1A
#define MPU6050_GYRO_CONFIG 0x1B
#define MPU6050_ACCEL_CONFIG 0x1C
#define MPU6050_ACCEL_XOUT_H 0x3B
#define MPU6050_ACCEL_XOUT_L 0x3C
#define MPU6050_ACCEL_YOUT_H 0x3D
#define MPU6050_ACCEL_YOUT_L 0x3E
#define MPU6050_ACCEL_ZOUT_H 0x3F
#define MPU6050_ACCEL_ZOUT_L 0x40
#define MPU6050_GYRO_XOUT_H 0x43
#define MPU6050_GYRO_XOUT_L 0x44
#define MPU6050_GYRO_YOUT_H 0x45
#define MPU6050_GYRO_YOUT_L 0x46
#define MPU6050_GYRO_ZOUT_H 0x47
#define MPU6050_GYRO_ZOUT_L 0x48
sbit SCL=P1^6;
sbit SDA=P1^7;
int16_t Accel_X, Accel_Y, Accel_Z, Gyro_X, Gyro_Y, Gyro_Z;
float Accel_Xangle, Accel_Yangle;
float Gyro_Xangle, Gyro_Yangle, Gyro_Zangle;
float CFangle_X, CFangle_Y;
void delay_ms(unsigned int ms)
{
unsigned int i,j;
for(i=0;i<ms;i++)
{
for(j=0;j<114;j++);
}
}
unsigned char IIC_Start()
{
unsigned char i = 0;
SDA = 1;
SCL = 1;
_nop_();
_nop_();
_nop_();
_nop_();
SDA = 0;
_nop_();
_nop_();
_nop_();
_nop_();
SCL = 0;
_nop_();
_nop_();
_nop_();
_nop_();
return 0;
}
unsigned char IIC_Stop()
{
SDA = 0;
SCL = 1;
_nop_();
_nop_();
_nop_();
_nop_();
SDA = 1;
_nop_();
_nop_();
_nop_();
_nop_();
return 0;
}
unsigned char IIC_Wait_Ack()
{
unsigned char i = 0;
SDA = 1;
_nop_();
_nop_();
_nop_();
_nop_();
SCL = 1;
_nop_();
_nop_();
_nop_();
_nop_();
while(SDA)
{
i++;
if(i>250)
{
IIC_Stop();
return 1;
}
}
SCL = 0;
_nop_();
_nop_();
_nop_();
_nop_();
return 0;
}
unsigned char IIC_Send_Byte(unsigned char txd)
{
unsigned char t;
for(t=0;t<8;t++)
{
SDA = ((txd&0x80)>>7);
txd <<= 1;
_nop_();
_nop_();
_nop_();
_nop_();
SCL = 1;
_nop_();
_nop_();
_nop_();
_nop_();
SCL = 0;
_nop_();
_nop_();
_nop_();
_nop_();
}
return 0;
}
unsigned char IIC_Read_Byte(unsigned char ack)
{
unsigned char i, receive = 0;
for(i=0;i<8;i++)
{
SCL = 1;
_nop_();
_nop_();
_nop_();
_nop_();
receive <<= 1;
receive |= SDA;
SCL = 0;
_nop_();
_nop_();
_nop_();
_nop_();
}
if(ack)
{
SDA = 1;
}
else
{
SDA = 0;
}
SCL = 1;
_nop_();
_nop_();
_nop_();
_nop_();
SCL = 0;
_nop_();
_nop_();
_nop_();
_nop_();
return receive;
}
void IIC_Write_OneByte(unsigned char daddr, unsigned char addr, unsigned char data)
{
IIC_Start();
IIC_Send_Byte(daddr);
IIC_Wait_Ack();
IIC_Send_Byte(addr);
IIC_Wait_Ack();
IIC_Send_Byte(data);
IIC_Wait_Ack();
IIC_Stop();
}
unsigned char IIC_Read_OneByte(unsigned char daddr, unsigned char addr)
{
unsigned char res = 0;
IIC_Start();
IIC_Send_Byte(daddr);
IIC_Wait_Ack();
IIC_Send_Byte(addr);
IIC_Wait_Ack();
IIC_Start();
IIC_Send_Byte(daddr+1);
IIC_Wait_Ack();
res = IIC_Read_Byte(0);
IIC_Stop();
return res;
}
void Init_MPU6050()
{
IIC_Write_OneByte(MPU6050_ADDR, MPU6050_SMPLRT_DIV, 0x07);
IIC_Write_OneByte(MPU6050_ADDR, MPU6050_CONFIG, 0x06);
IIC_Write_OneByte(MPU6050_ADDR, MPU6050_GYRO_CONFIG, 0x18);
IIC_Write_OneByte(MPU6050_ADDR, MPU6050_ACCEL_CONFIG, 0x01);
}
void Get_MPU6050_Data()
{
Accel_X = (int16_t)((IIC_Read_OneByte(MPU6050_ADDR, MPU6050_ACCEL_XOUT_H)<<8)|IIC_Read_OneByte(MPU6050_ADDR, MPU6050_ACCEL_XOUT_L));
Accel_Y = (int16_t)((IIC_Read_OneByte(MPU6050_ADDR, MPU6050_ACCEL_YOUT_H)<<8)|IIC_Read_OneByte(MPU6050_ADDR, MPU6050_ACCEL_YOUT_L));
Accel_Z = (int16_t)((IIC_Read_OneByte(MPU6050_ADDR, MPU6050_ACCEL_ZOUT_H)<<8)|IIC_Read_OneByte(MPU6050_ADDR, MPU6050_ACCEL_ZOUT_L));
Gyro_X = (int16_t)((IIC_Read_OneByte(MPU6050_ADDR, MPU6050_GYRO_XOUT_H)<<8)|IIC_Read_OneByte(MPU6050_ADDR, MPU6050_GYRO_XOUT_L));
Gyro_Y = (int16_t)((IIC_Read_OneByte(MPU6050_ADDR, MPU6050_GYRO_YOUT_H)<<8)|IIC_Read_OneByte(MPU6050_ADDR, MPU6050_GYRO_YOUT_L));
Gyro_Z = (int16_t)((IIC_Read_OneByte(MPU6050_ADDR, MPU6050_GYRO_ZOUT_H)<<8)|IIC_Read_OneByte(MPU6050_ADDR, MPU6050_GYRO_ZOUT_L));
}
void Complementary_Filter()
{
Gyro_Xangle += (float)Gyro_X/131.0*0.00035;
Gyro_Yangle += (float)Gyro_Y/131.0*0.00035;
Gyro_Zangle += (float)Gyro_Z/131.0*0.00035;
Accel_Xangle = atan2(Accel_Y,Accel_Z)*57.3;
Accel_Yangle = atan2(Accel_X,Accel_Z)*57.3;
CFangle_X = 0.98*(CFangle_X+Gyro_Xangle)+0.02*Accel_Xangle;
CFangle_Y = 0.98*(CFangle_Y+Gyro_Yangle)+0.02*Accel_Yangle;
}
void main()
{
unsigned char i;
OLED_Init();
Init_MPU6050();
while(1)
{
Get_MPU6050_Data();
Complementary_Filter();
OLED_Clear();
OLED_ShowString(0,0,"MPU6050 Angle:");
OLED_ShowString(0,2,"X:");
OLED_ShowString(30,2,"Y:");
OLED_ShowString(0,4,"CFangle_X:");
OLED_ShowString(0,6,"CFangle_Y:");
sprintf((char*)buf,"%d",(int)Accel_Xangle);
OLED_ShowString(12,2,buf);
sprintf((char*)buf,"%d",(int)Accel_Yangle);
OLED_ShowString(42,2,buf);
sprintf((char*)buf,"%d",(int)CFangle_X);
OLED_ShowString(60,4,buf);
sprintf((char*)buf,"%d",(int)CFangle_Y);
OLED_ShowString(60,6,buf);
delay_ms(100);
}
}
```
需要注意的是,以上代码仅供参考,具体应用中需要针对实际情况进行修改和调试。
阅读全文