久久久久久久999_99精品久久精品一区二区爱城_成人欧美一区二区三区在线播放_国产精品日本一区二区不卡视频_国产午夜视频_欧美精品在线观看免费

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 4329|回復: 6
打印 上一主題 下一主題
收起左側

三軸加速度模塊GY-271遇到困難,請求幫助

[復制鏈接]
跳轉到指定樓層
樓主
使用商家給的代碼,顯示只有A:45,擺動模塊,沒有任何現象。
商家代碼如下:
//***************************************
// HMC5883 IIC測試程序
// 使用單片機STC89C51
// 晶振:11.0592M
// 顯示:LCD1602
// 編譯環境 Keil uVision2
// 參考宏晶網站24c04通信程序
// 時間:2011年3月1日
//****************************************
#include  <REG51.H>       
#include  <math.h>    //Keil library  
#include  <stdio.h>   //Keil library       
#include  <INTRINS.H>
#define   uchar unsigned char
#define   uint unsigned int       
//使用的端口,請按照以下接線
#define   DataPort P0        //LCD1602數據端口
sbit        SCL=P1^0;      //IIC時鐘引腳定義
sbit        SDA=P1^1;      //IIC數據引腳定義
sbit    LCM_RS=P2^0;   //LCD1602命令端口               
sbit    LCM_RW=P2^1;   //LCD1602命令端口               
sbit    LCM_EN=P2^2;   //LCD1602命令端口

#define        SlaveAddress   0x3C          //定義器件在IIC總線中的從地址
typedef unsigned char BYTE;
typedef unsigned short WORD;

BYTE BUF[8];                         //接收數據緩存區             
uchar ge,shi,bai,qian,wan;           //顯示變量
int  dis_data;                       //變量

void delay(unsigned int k);
void InitLcd();
void Init_HMC5883(void);            //初始化5883

void WriteDataLCM(uchar dataW);
void WriteCommandLCM(uchar CMD,uchar Attribc);
void DisplayOneChar(uchar X,uchar Y,uchar DData);
void conversion(uint temp_data);

void  Single_Write_HMC5883(uchar REG_Address,uchar REG_data);   //單個寫入數據
uchar Single_Read_HMC5883(uchar REG_Address);                   //單個讀取內部寄存器數據
void  Multiple_Read_HMC5883();                                  //連續的讀取內部寄存器數據
//以下是模擬iic使用函數-------------
void Delay5us();
void Delay5ms();
void HMC5883_Start();
void HMC5883_Stop();
void HMC5883_SendACK(bit ack);
bit  HMC5883_RecvACK();
void HMC5883_SendByte(BYTE dat);
BYTE HMC5883_RecvByte();
void HMC5883_ReadPage();
void HMC5883_WritePage();
//-----------------------------------

//*********************************************************
void conversion(uint temp_data)  
{  
    wan=temp_data/10000+0x30 ;
    temp_data=temp_data%10000;   //取余運算
        qian=temp_data/1000+0x30 ;
    temp_data=temp_data%1000;    //取余運算
    bai=temp_data/100+0x30   ;
    temp_data=temp_data%100;     //取余運算
    shi=temp_data/10+0x30    ;
    temp_data=temp_data%10;      //取余運算
    ge=temp_data+0x30;        
}

/*******************************/
void delay(unsigned int k)       
{                                               
unsigned int i,j;                               
for(i=0;i<k;i++)
{                       
for(j=0;j<121;j++)                       
{;}}                                               
}
/*******************************/
void WaitForEnable(void)       
{                                       
DataPort=0xff;               
LCM_RS=0;LCM_RW=1;_nop_();
LCM_EN=1;_nop_();_nop_();
while(DataPort&0x80);       
LCM_EN=0;                               
}                                       
/*******************************/
void WriteCommandLCM(uchar CMD,uchar Attribc)
{                                       
if(Attribc)WaitForEnable();       
LCM_RS=0;LCM_RW=0;_nop_();
DataPort=CMD;_nop_();       
LCM_EN=1;_nop_();_nop_();LCM_EN=0;
}                                       
/*******************************/
void WriteDataLCM(uchar dataW)
{                                       
WaitForEnable();               
LCM_RS=1;LCM_RW=0;_nop_();
DataPort=dataW;_nop_();       
LCM_EN=1;_nop_();_nop_();LCM_EN=0;
}               
/***********************************/
void InitLcd()                               
{                       
WriteCommandLCM(0x38,1);       
WriteCommandLCM(0x08,1);       
WriteCommandLCM(0x01,1);       
WriteCommandLCM(0x06,1);       
WriteCommandLCM(0x0c,1);
}                       
/***********************************/
void DisplayOneChar(uchar X,uchar Y,uchar DData)
{                                               
Y&=1;                                               
X&=15;                                               
if(Y)X|=0x40;                                       
X|=0x80;                       
WriteCommandLCM(X,0);               
WriteDataLCM(DData);               
}                                               

/**************************************
延時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_();
        _nop_();_nop_();_nop_();_nop_();
             _nop_();_nop_();_nop_();_nop_();

}

/**************************************
延時5毫秒(STC90C52RC@12M)
不同的工作環境,需要調整此函數
當改用1T的MCU時,請調整此延時函數
**************************************/
void Delay5ms()
{
    WORD n = 560;

    while (n--);
}

/**************************************
起始信號
**************************************/
void HMC5883_Start()
{
    SDA = 1;                    //拉高數據線
    SCL = 1;                    //拉高時鐘線
    Delay5us();                 //延時
    SDA = 0;                    //產生下降沿
    Delay5us();                 //延時
    SCL = 0;                    //拉低時鐘線
}

/**************************************
停止信號
**************************************/
void HMC5883_Stop()
{
    SDA = 0;                    //拉低數據線
    SCL = 1;                    //拉高時鐘線
    Delay5us();                 //延時
    SDA = 1;                    //產生上升沿
    Delay5us();                 //延時
}

/**************************************
發送應答信號
入口參數:ack (0:ACK 1:NAK)
**************************************/
void HMC5883_SendACK(bit ack)
{
    SDA = ack;                  //寫應答信號
    SCL = 1;                    //拉高時鐘線
    Delay5us();                 //延時
    SCL = 0;                    //拉低時鐘線
    Delay5us();                 //延時
}

/**************************************
接收應答信號
**************************************/
bit HMC5883_RecvACK()
{
    SCL = 1;                    //拉高時鐘線
    Delay5us();                 //延時
    CY = SDA;                   //讀應答信號
    SCL = 0;                    //拉低時鐘線
    Delay5us();                 //延時

    return CY;
}

/**************************************
向IIC總線發送一個字節數據
**************************************/
void HMC5883_SendByte(BYTE dat)
{
    BYTE i;

    for (i=0; i<8; i++)         //8位計數器
    {
        dat <<= 1;              //移出數據的最高位
        SDA = CY;               //送數據口
        SCL = 1;                //拉高時鐘線
        Delay5us();             //延時
        SCL = 0;                //拉低時鐘線
        Delay5us();             //延時
    }
    HMC5883_RecvACK();
}

/**************************************
從IIC總線接收一個字節數據
**************************************/
BYTE HMC5883_RecvByte()
{
    BYTE i;
    BYTE dat = 0;

    SDA = 1;                    //使能內部上拉,準備讀取數據,
    for (i=0; i<8; i++)         //8位計數器
    {
        dat <<= 1;
        SCL = 1;                //拉高時鐘線
        Delay5us();             //延時
        dat |= SDA;             //讀數據               
        SCL = 0;                //拉低時鐘線
        Delay5us();             //延時
    }
    return dat;
}

//***************************************************

void Single_Write_HMC5883(uchar REG_Address,uchar REG_data)
{
    HMC5883_Start();                  //起始信號
    HMC5883_SendByte(SlaveAddress);   //發送設備地址+寫信號
    HMC5883_SendByte(REG_Address);    //內部寄存器地址,請參考中文pdf
    HMC5883_SendByte(REG_data);       //內部寄存器數據,請參考中文pdf
    HMC5883_Stop();                   //發送停止信號
}

//********單字節讀取內部寄存器*************************
uchar Single_Read_HMC5883(uchar REG_Address)
{  uchar REG_data;
    HMC5883_Start();                          //起始信號
    HMC5883_SendByte(SlaveAddress);           //發送設備地址+寫信號
    HMC5883_SendByte(REG_Address);                   //發送存儲單元地址,從0開始       
    HMC5883_Start();                          //起始信號
    HMC5883_SendByte(SlaveAddress+1);         //發送設備地址+讀信號
    REG_data=HMC5883_RecvByte();              //讀出寄存器數據
        HMC5883_SendACK(1);   
        HMC5883_Stop();                           //停止信號
    return REG_data;
}
//******************************************************
//
//連續讀出HMC5883內部角度數據,地址范圍0x3~0x5
//
//******************************************************
void Multiple_read_HMC5883(void)
{   uchar i;
    HMC5883_Start();                          //起始信號
    HMC5883_SendByte(SlaveAddress);           //發送設備地址+寫信號
    HMC5883_SendByte(0x03);                   //發送存儲單元地址,從0x3開始       
    HMC5883_Start();                          //起始信號
    HMC5883_SendByte(SlaveAddress+1);         //發送設備地址+讀信號
         for (i=0; i<6; i++)                      //連續讀取6個地址數據,存儲中BUF
    {
        BUF[i] = HMC5883_RecvByte();          //BUF[0]存儲數據
        if (i == 5)
        {
           HMC5883_SendACK(1);                //最后一個數據需要回NOACK
        }
        else
        {
          HMC5883_SendACK(0);                //回應ACK
       }
   }
    HMC5883_Stop();                          //停止信號
    Delay5ms();
}

//初始化HMC5883,根據需要請參考pdf進行修改****
void Init_HMC5883()
{
     Single_Write_HMC5883(0x02,0x00);  //
}
//*********************************************************
//主程序********
//*********************************************************
void main()
{ // bit sign_bit;
   unsigned int i;
   int x,y,z;
   double angle;

   delay(500);                       
   InitLcd();
   Init_HMC5883();
  while(1)            //循環
  {
    Multiple_Read_HMC5883();      //連續讀出數據,存儲在BUF中
//---------顯示X軸
    x=BUF[0] << 8 | BUF[1]; //Combine MSB and LSB of X Data output register
    z=BUF[2] << 8 | BUF[3]; //Combine MSB and LSB of Z Data output register
    y=BUF[4] << 8 | BUF[5]; //Combine MSB and LSB of Y Data output register

    angle= atan2((double)y,(double)x) * (180 / 3.14159265) + 180; // angle in degrees
    angle*=10;
    conversion(angle);       //計算數據和顯示
        DisplayOneChar(2,0,'A');
    DisplayOneChar(3,0,':');
    DisplayOneChar(4,0,qian);
    DisplayOneChar(5,0,bai);
    DisplayOneChar(6,0,shi);
    DisplayOneChar(7,0,'.');
        DisplayOneChar(8,0,ge);

    for (i=0;i<10000;i++);   //延時                  
  }
}


分享到:  QQ好友和群QQ好友和群 QQ空間QQ空間 騰訊微博騰訊微博 騰訊朋友騰訊朋友
收藏收藏 分享淘帖 頂1 踩
回復

使用道具 舉報

沙發
ID:82765 發表于 2017-3-27 22:11 | 只看該作者
提示: 作者被禁止或刪除 內容自動屏蔽
回復

使用道具 舉報

板凳
ID:183949 發表于 2017-3-28 15:32 | 只看該作者
那我要如何修改?
我用串口程序看了,只有FF回來
串口程序如下:
//***************************************
// HMC5883 51串口測試程序
// 使用單片機STC89C51
// 晶振:11.0592M
// 顯示:PC串口
// 編譯環境 Keil uVision2
// 參考宏晶網站24c04通信程序
// 時間:2011年3月1日
//****************************************
#include  <REG51.H>       
#include  <math.h>    //Keil library  
#include  <stdio.h>   //Keil library       
#include  <INTRINS.H>
#define   uchar unsigned char
#define   uint  unsigned int       
//使用的端口,請按照以下接線
#define DataPort P0        //LCD1602數據端口
sbit        SCL=P1^0;      //IIC時鐘引腳定義
sbit        SDA=P1^1;      //IIC數據引腳定義


#define        SlaveAddress   0x3C          //定義器件5883在IIC總線中的從地址
typedef unsigned char BYTE;
typedef unsigned short WORD;

BYTE BUF[8];                         //接收數據緩存區             
uchar ge,shi,bai,qian,wan;           //顯示變量
int  dis_data;                       //變量
//************

//************
void delay(unsigned int k);
void Init_HMC5883(void);            //初始化5883
void conversion(uint temp_data);

void  Single_Write_HMC5883(uchar REG_Address,uchar REG_data);   //單個寫入數據
//uchar Single_Read_HMC5883(uchar REG_Address);                   //單個讀取內部寄存器數據
void  Multiple_Read_HMC5883();                                  //連續的讀取內部寄存器數據
//以下是模擬iic使用函數-------------
void Delay5us();
void Delay5ms();
void HMC5883_Start();
void HMC5883_Stop();
void HMC5883_SendACK(bit ack);
bit  HMC5883_RecvACK();
void HMC5883_SendByte(BYTE dat);
BYTE HMC5883_RecvByte();
void HMC5883_ReadPage();
void HMC5883_WritePage();
//-----------------------------------

//*********************************************
//串口初始化
//9600 bps @ 11.059 MHz
void init_uart()
{
        TMOD=0x21;                               
        TH1=0xfd;                               
        TL1=0xfd;                               
        SCON=0x50;
        PS=1;      //串口中斷設為高優先級別
        TR0=1;           //啟動定時器                       
        TR1=1;
        ET0=1;     //打開定時器0中斷                       
        ES=1;       
}

//*********串口數據發送******************
void  SeriPushSend(uchar send_data)
{
    SBUF=send_data;  
        while(!TI);TI=0;          
}
//*********************************************************
void conversion(uint temp_data)  
{  
    wan=temp_data/10000+0x30 ;
    temp_data=temp_data%10000;   //取余運算
        qian=temp_data/1000+0x30 ;
    temp_data=temp_data%1000;    //取余運算
    bai=temp_data/100+0x30   ;
    temp_data=temp_data%100;     //取余運算
    shi=temp_data/10+0x30    ;
    temp_data=temp_data%10;      //取余運算
    ge=temp_data+0x30;        
}

/*******************************/
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_();
}

/**************************************
延時5毫秒(STC90C52RC@12M)
不同的工作環境,需要調整此函數
當改用1T的MCU時,請調整此延時函數
**************************************/
void Delay5ms()
{
    WORD n = 560;

    while (n--);
}

/**************************************
起始信號
**************************************/
void HMC5883_Start()
{
    SDA = 1;                    //拉高數據線
    SCL = 1;                    //拉高時鐘線
    Delay5us();                 //延時
    SDA = 0;                    //產生下降沿
    Delay5us();                 //延時
    SCL = 0;                    //拉低時鐘線
}

/**************************************
停止信號
**************************************/
void HMC5883_Stop()
{
    SDA = 0;                    //拉低數據線
    SCL = 1;                    //拉高時鐘線
    Delay5us();                 //延時
    SDA = 1;                    //產生上升沿
    Delay5us();                 //延時
}

/**************************************
發送應答信號
入口參數:ack (0:ACK 1:NAK)
**************************************/
void HMC5883_SendACK(bit ack)
{
    SDA = ack;                  //寫應答信號
    SCL = 1;                    //拉高時鐘線
    Delay5us();                 //延時
    SCL = 0;                    //拉低時鐘線
    Delay5us();                 //延時
}

/**************************************
接收應答信號
**************************************/
bit HMC5883_RecvACK()
{
    SCL = 1;                    //拉高時鐘線
    Delay5us();                 //延時
    CY = SDA;                   //讀應答信號
    SCL = 0;                    //拉低時鐘線
    Delay5us();                 //延時

    return CY;
}

/**************************************
向IIC總線發送一個字節數據
**************************************/
void HMC5883_SendByte(BYTE dat)
{
    BYTE i;

    for (i=0; i<8; i++)         //8位計數器
    {
        dat <<= 1;              //移出數據的最高位
        SDA = CY;               //送數據口
        SCL = 1;                //拉高時鐘線
        Delay5us();             //延時
        SCL = 0;                //拉低時鐘線
        Delay5us();             //延時
    }
    HMC5883_RecvACK();
}

/**************************************
從IIC總線接收一個字節數據
**************************************/
BYTE HMC5883_RecvByte()
{
    BYTE i;
    BYTE dat = 0;

    SDA = 1;                    //使能內部上拉,準備讀取數據,
    for (i=0; i<8; i++)         //8位計數器
    {
        dat <<= 1;
        SCL = 1;                //拉高時鐘線
        Delay5us();             //延時
        dat |= SDA;             //讀數據               
        SCL = 0;                //拉低時鐘線
        Delay5us();             //延時
    }
    return dat;
}

//***************************************************

void Single_Write_HMC5883(uchar REG_Address,uchar REG_data)
{
    HMC5883_Start();                  //起始信號
    HMC5883_SendByte(SlaveAddress);   //發送設備地址+寫信號
    HMC5883_SendByte(REG_Address);    //內部寄存器地址,請參考中文pdf
    HMC5883_SendByte(REG_data);       //內部寄存器數據,請參考中文pdf
    HMC5883_Stop();                   //發送停止信號
}
/*
//********單字節讀取內部寄存器*************************
uchar Single_Read_HMC5883(uchar REG_Address)
{  uchar REG_data;
    HMC5883_Start();                          //起始信號
    HMC5883_SendByte(SlaveAddress);           //發送設備地址+寫信號
    HMC5883_SendByte(REG_Address);                   //發送存儲單元地址,從0開始       
    HMC5883_Start();                          //起始信號
    HMC5883_SendByte(SlaveAddress+1);         //發送設備地址+讀信號
    REG_data=HMC5883_RecvByte();              //讀出寄存器數據
        HMC5883_SendACK(1);   
        HMC5883_Stop();                           //停止信號
    return REG_data;
}
*/
//******************************************************
//
//連續讀出HMC5883內部角度數據,地址范圍0x3~0x5
//
//******************************************************
void Multiple_read_HMC5883(void)
{   uchar i;
    HMC5883_Start();                          //起始信號
    HMC5883_SendByte(SlaveAddress);           //發送設備地址+寫信號
    HMC5883_SendByte(0x03);                   //發送存儲單元地址,從0x3開始       
    HMC5883_Start();                          //起始信號
    HMC5883_SendByte(SlaveAddress+1);         //發送設備地址+讀信號
         for (i=0; i<7; i++)                      //連續讀取6個地址數據,存儲中BUF
    {
        BUF[i] = HMC5883_RecvByte();          //BUF[0]存儲0x32地址中的數據
        if (i == 6)
        {
           HMC5883_SendACK(1);                //最后一個數據需要回NOACK
        }
        else
        {
          HMC5883_SendACK(0);                //回應ACK
       }
   }
    HMC5883_Stop();                          //停止信號
    Delay5ms();
}

//初始化HMC5883,根據需要請參考pdf進行修改****
void Init_HMC5883()
{
     Single_Write_HMC5883(0x02,0x00);  //
         Single_Write_HMC5883(0x01,0xE0);  //
}
//*********************************************************
//主程序********
//*********************************************************
void main()
{ // bit sign_bit;

   unsigned int i;
   int x,y,z;
   double angle;


   delay(100);                       
   init_uart();
   Init_HMC5883();

  while(1)            //循環
  {

    Multiple_Read_HMC5883();      //連續讀出數據,存儲在BUF中
        x = BUF[0] << 8 | BUF[1];
    y = BUF[4] << 8 | BUF[5];
        z = BUF[2] << 8 | BUF[3];
    angle= atan2((double)y,(double)x) * (180 / 3.14159265) + 180; // angle in degrees
    conversion(angle);       //計算數據和顯示

    SeriPushSend(bai);
    SeriPushSend(shi);
        SeriPushSend(ge);

        SeriPushSend(0x0d);
        SeriPushSend(0x0a);

    for (i=0;i<10000;i++);   //延時                  
  }
}
回復

使用道具 舉報

地板
ID:151348 發表于 2017-3-28 15:34 | 只看該作者
一方面程序只顯示一軸數據,另一方面,擺動模塊這數據沒變化,估計是IIC通信不成功
回復

使用道具 舉報

5#
ID:183949 發表于 2017-3-28 18:20 | 只看該作者
那我下面這個是顯示三軸數據了吧。
//***************************************
// HMC5883 IIC測試程序
// 使用單片機STC89C51
// 晶振:11.0592M
// 顯示:LCD1602
// 編譯環境 Keil uVision2
// 參考宏晶網站24c04通信程序
// 時間:2011年3月1日
//****************************************
#include  <REG51.H>       
#include  <math.h>    //Keil library  
#include  <stdio.h>   //Keil library       
#include  <INTRINS.H>
#define   uchar unsigned char
#define   uint unsigned int       
//使用的端口,請按照以下接線
#define   DataPort P2        //LCD1602數據端口
sbit        SCL=P1^0;      //IIC時鐘引腳定義
sbit        SDA=P1^1;      //IIC數據引腳定義
sbit    LCM_RS=P0^7;   //LCD1602命令端口               
sbit    LCM_RW=P0^6;   //LCD1602命令端口               
sbit    LCM_EN=P0^5;   //LCD1602命令端口

#define        SlaveAddress   0x3C          //定義器件在IIC總線中的從地址
typedef unsigned char BYTE;
typedef unsigned short WORD;

BYTE BUF[8];                         //接收數據緩存區             
uchar ge,shi,bai,qian,wan;           //顯示變量
//int  dis_data;                       //變量

void delay_ms(unsigned int t);
void InitLcd();
void Init_HMC5883(void);            //初始化5883

void WriteDataLCM(uchar dataW);
void WriteCommandLCM(uchar CMD,uchar Attribc);
void DisplayOneChar(uchar X,uchar Y,uchar DData);
void conversion(uint temp_data);

void  Single_Write_HMC5883(uchar REG_Address,uchar REG_data);   //單個寫入數據
//uchar Single_Read_HMC5883(uchar REG_Address);                 /單個讀取內部寄存器數據
void  Multiple_Read_HMC5883();                                  //連續的讀取內部寄存器數據
//以下是模擬iic使用函數-------------
void Delay5us();
void Delay5ms();
void HMC5883_Start();
void HMC5883_Stop();
void HMC5883_SendACK(bit ack);
bit  HMC5883_RecvACK();
void HMC5883_SendByte(BYTE dat);
BYTE HMC5883_RecvByte();
void HMC5883_ReadPage();
void HMC5883_WritePage();
//-----------------------------------

//*************************顯示在LCD的數據********************************
void Conversion(uint temp_data)  
{  
    wan=temp_data/10000+0x30 ;
    temp_data=temp_data%10000;   //取余運算
        qian=temp_data/1000+0x30 ;
    temp_data=temp_data%1000;    //取余運算
    bai=temp_data/100+0x30   ;
    temp_data=temp_data%100;     //取余運算
    shi=temp_data/10+0x30    ;
    temp_data=temp_data%10;      //取余運算
    ge=temp_data+0x30;        
}

/**************延時函數*****************/
void Delay_ms(unsigned int t)       
{                                               
        unsigned int i,j;                               
        for(i=t;i>0;i--)
        for(j=121;j>0;j--);                                               
}
/***************等待LCD使能****************/
void WaitForEnable(void)       
{                                       
        DataPort=0xff;               
        LCM_RS=0;
        LCM_RW=1;
        _nop_();
        LCM_EN=1;
        _nop_();
        _nop_();
        while(DataPort&0x80);       
        LCM_EN=0;                               
}                                       
/**************寫LCD內存命令函數*****************/
void WriteCommandLCM(uchar CMD,uchar Attribc)
{                                       
        if(Attribc)WaitForEnable();       
        LCM_RS=0;
        LCM_RW=0;
        _nop_();
        DataPort=CMD;
        _nop_();       
        LCM_EN=1;
        _nop_();
        _nop_();
        LCM_EN=0;
}                                       
/**************寫LCD數據寄存器*****************/
void WriteDataLCM(uchar dataW)
{                                       
        WaitForEnable();               
        LCM_RS=1;
        LCM_RW=0;
        _nop_();
        DataPort=dataW;
        _nop_();       
        LCM_EN=1;
        _nop_();
        _nop_();
        LCM_EN=0;
}               
/****************初始化LCD*******************/
void InitLcd()                               
{                       
        WriteCommandLCM(0x38,1);       
        WriteCommandLCM(0x08,1);       
        WriteCommandLCM(0x01,1);       
        WriteCommandLCM(0x06,1);       
        WriteCommandLCM(0x0c,1);
}                       
/****************顯示一個字符*******************/
void Display_One_Char(uchar X,uchar Y,uchar DData)
{                                               
        Y&=1;                                               
        X&=15;                                               
        if(Y)X|=0x40;                                       
        X|=0x80;                       
        WriteCommandLCM(X,0);               
        WriteDataLCM(DData);               
}                                               

/**************************************
延時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_();
        _nop_();_nop_();_nop_();_nop_();
        _nop_();_nop_();_nop_();_nop_();
}

/**************************************
延時5毫秒(STC90C52RC@12M)
不同的工作環境,需要調整此函數
當改用1T的MCU時,請調整此延時函數
**************************************/
void Delay5ms()
{
    WORD n = 560;

    while (n--);
}

/**************************************
起始信號
**************************************/
void HMC5883_Start()
{
    SDA = 1;                    //拉高數據線
    SCL = 1;                    //拉高時鐘線
    Delay5us();                 //延時
    SDA = 0;                    //產生下降沿
    Delay5us();                 //延時
    SCL = 0;                    //拉低時鐘線
}

/**************************************
停止信號
**************************************/
void HMC5883_Stop()
{
    SDA = 0;                    //拉低數據線
    SCL = 1;                    //拉高時鐘線
    Delay5us();                 //延時
    SDA = 1;                    //產生上升沿
    Delay5us();                 //延時
}

/**************************************
發送應答信號
入口參數:ack (0:ACK 1:NAK)
**************************************/
void HMC5883_SendACK(bit ack)
{
    SDA = ack;                  //寫應答信號
    SCL = 1;                    //拉高時鐘線
    Delay5us();                 //延時
    SCL = 0;                    //拉低時鐘線
    Delay5us();                 //延時
}

/**************************************
接收應答信號
**************************************/
bit HMC5883_RecvACK()
{
    SCL = 1;                    //拉高時鐘線
    Delay5us();                 //延時
    CY = SDA;                   //讀應答信號
    SCL = 0;                    //拉低時鐘線
    Delay5us();                 //延時

    return CY;
}

/**************************************
向IIC總線發送一個字節數據
**************************************/
void HMC5883_SendByte(BYTE dat)
{
    BYTE i;

    for (i=0; i<8; i++)         //8位計數器
    {
        dat <<= 1;              //移出數據的最高位
        SDA = CY;               //送數據口
        SCL = 1;                //拉高時鐘線
        Delay5us();             //延時
        SCL = 0;                //拉低時鐘線
        Delay5us();             //延時
    }
    HMC5883_RecvACK();
}

/**************************************
從IIC總線接收一個字節數據
**************************************/
BYTE HMC5883_RecvByte()
{
    BYTE i;
    BYTE dat = 0;

    SDA = 1;                    //使能內部上拉,準備讀取數據,
    for (i=0; i<8; i++)         //8位計數器
    {
        dat <<= 1;
        SCL = 1;                //拉高時鐘線
        Delay5us();             //延時
        dat |= SDA;             //讀數據               
        SCL = 0;                //拉低時鐘線
        Delay5us();             //延時
    }
    return dat;
}

//************************寫入單字節數據***************************

void Single_Write_HMC5883(uchar REG_Address,uchar REG_data)
{
    HMC5883_Start();                  //起始信號
    HMC5883_SendByte(SlaveAddress);   //發送設備地址+寫信號
    HMC5883_SendByte(REG_Address);    //內部寄存器地址,請參考中文pdf
    HMC5883_SendByte(REG_data);       //內部寄存器數據,請參考中文pdf
    HMC5883_Stop();                   //發送停止信號
}

//************************讀取內部寄存器*************************
//uchar Single_Read_HMC5883(uchar REG_Address)
//{   
//        uchar REG_data;
//  HMC5883_Start();                          //起始信號
//  HMC5883_SendByte(SlaveAddress);           //發送設備地址+寫信號
//  HMC5883_SendByte(REG_Address);            //發送存儲單元地址,從0開始       
//  HMC5883_Start();                          //起始信號
//  HMC5883_SendByte(SlaveAddress+1);         //發送設備地址+讀信號
//  REG_data=HMC5883_RecvByte();              //讀出寄存器數據
//        HMC5883_SendACK(1);   
//        HMC5883_Stop();                           //停止信號
//  return REG_data;
//}

//******************************************************
//連續讀出HMC5883內部角度數據,地址范圍0x3~0x5
//******************************************************
void Multiple_Read_HMC5883(void)
{   uchar i;
    HMC5883_Start();                          //起始信號
    HMC5883_SendByte(SlaveAddress);           //發送設備地址+寫信號
    HMC5883_SendByte(0x03);                   //發送存儲單元地址,從0x3開始       
    HMC5883_Start();                          //起始信號
    HMC5883_SendByte(SlaveAddress+1);         //發送設備地址+讀信號
         for (i=0; i<6; i++)                      //連續讀取6個地址數據,存儲中BUF
    {
        BUF[i] = HMC5883_RecvByte();          //BUF[0]存儲數據
        if (i == 5)
        {
           HMC5883_SendACK(1);                //最后一個數據需要回NOACK
        }
        else
        {
          HMC5883_SendACK(0);                //回應ACK
       }
   }
    HMC5883_Stop();                          //停止信號
    Delay5ms();
}

//初始化HMC5883,根據需要請參考pdf進行修改****
void Init_HMC5883()
{
     Single_Write_HMC5883(0x02,0x00);  //
}
//*********************************************************
//主程序********
//*********************************************************
void main()
{
        // bit sign_bit;
        unsigned int i;
        int X,Y,Z;
        double Angle_XY=0,Angle_XZ=0,Angle_YZ=0;

        Delay_ms(500);                       
        InitLcd();
        Init_HMC5883();
        while(1)            //循環
        {
                Multiple_Read_HMC5883();      //連續讀出數據,存儲在BUF中
//---------顯示X軸
                X=BUF[0] << 8 | BUF[1]; //Combine MSB and LSB of X Data output register  最高有效位
                Z=BUF[2] << 8 | BUF[3]; //Combine MSB and LSB of Z Data output register
                Y=BUF[4] << 8 | BUF[5]; //Combine MSB and LSB of Y Data output register

                if(X>0x7fff)X-=0xffff;          
                if(Y>0x7fff)Y-=0xffff;
                if(Z>0x7fff)Z-=0xffff;
               
                Display_One_Char(0,0,'H');
                Display_One_Char(1,0,'M');
                Display_One_Char(2,0,'C');
                Display_One_Char(3,0,'5');
                Display_One_Char(4,0,'8');
                Display_One_Char(5,0,'8');
                Display_One_Char(6,0,'3');

                Angle_XY= atan2((double)Y,(double)X) * (180 / 3.14159265) + 180; //計算XY平面角度
                Angle_XY*=10;
                Conversion(Angle_XY);       //計算XY平面角度數據和顯示
                Display_One_Char(8,0,'X');
                Display_One_Char(9,0,'Y');
                Display_One_Char(10,0,':');
                Display_One_Char(11,0,qian);
                Display_One_Char(12,0,bai);
                Display_One_Char(13,0,shi);
                Display_One_Char(14,0,'.');
                Display_One_Char(15,0,ge);
               
                Angle_XZ= atan2((double)Z,(double)X) * (180 / 3.14159265) + 180; //計算XZ平面角度
                Angle_XZ*=10;
                Conversion(Angle_XZ);       //計算XZ平面角度數據和顯示
                Display_One_Char(0,1,'X');
                Display_One_Char(1,1,'Z');
                Display_One_Char(2,1,':');
                Display_One_Char(3,1,qian);
                Display_One_Char(4,1,bai);
                Display_One_Char(5,1,shi);
                Display_One_Char(6,1,'.');
                Display_One_Char(7,1,ge);
               
                Angle_YZ= atan2((double)Z,(double)Y) * (180 / 3.14159265) + 180; //計算YZ平面角度
                Angle_YZ*=10;
                Conversion(Angle_YZ);       //計算YZ平面角度數據和顯示
                Display_One_Char(8,1,'Y');
                Display_One_Char(9,1,'Z');
                Display_One_Char(10,1,':');
                Display_One_Char(11,1,qian);
                Display_One_Char(12,1,bai);
                Display_One_Char(13,1,shi);
                Display_One_Char(14,1,'.');
                Display_One_Char(15,1,ge);

    for (i=0;i<10000;i++);   //延時                  
  }
}

回復

使用道具 舉報

6#
ID:570056 發表于 2019-6-23 14:51 來自手機 | 只看該作者
新人報道 發表于 2017-3-28 18:20
**** 作者被禁止或刪除 內容自動屏蔽 ****

三個軸都是45.0,老兄

1561272646782..jpg (623.76 KB, 下載次數: 74)

1561272646782..jpg
回復

使用道具 舉報

7#
ID:1110204 發表于 2024-1-27 00:34 來自手機 | 只看該作者
請問樓主是怎么解決的呀?我也遇到了相同的問題
回復

使用道具 舉報

您需要登錄后才可以回帖 登錄 | 立即注冊

本版積分規則

手機版|小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術交流QQ群281945664

Powered by 單片機教程網

快速回復 返回頂部 返回列表
主站蜘蛛池模板: 久久国产秒 | 中文在线a在线 | 欧美在线a| 国产一级片久久久 | 久久精品一 | 国产欧美日韩综合精品一区二区 | 国产精品区一区二区三区 | 一区二区三区在线电影 | 日韩免费在线观看视频 | 国产免费国产 | 久久国产精品偷 | 高清国产一区二区 | 青青草原精品99久久精品66 | 亚洲导航深夜福利涩涩屋 | 97久久久 | 亚洲狠狠 | 亚洲国产片| 成人二区三区 | 国产福利在线 | 国产免费一级一级 | 激情国产视频 | 黄色在线免费播放 | 综合色播 | 久久久精品| 成人在线视频网 | 亚州精品天堂中文字幕 | 精品婷婷| 欧美日韩亚洲国产 | www.四虎.com | 欧美视频中文字幕 | 无码一区二区三区视频 | 欧美日韩一 | 一区二区三区国产精品 | 国产精品国产三级国产aⅴ中文 | 日韩有码一区二区三区 | 久久99精品久久久久久国产越南 | 国产精品美女久久久久久免费 | 一区二区三区视频在线 | 伊人精品在线 | 精品国产一区二区在线 | 亚洲精品91 |