找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 3876|回复: 0
收起左侧

ADXL重力加速度传感器实现计步器程序(利用MSP430F135实现)

[复制链接]
ID:290485 发表于 2018-3-11 19:13 | 显示全部楼层 |阅读模式
ADXL重力加速度传感器实现计步器程序,利用MSP430F135实现,代码功能完整。
可用按键控制。
0.png

单片机源程序如下:

  1. //存储器没有文件系统,一次采集,一次上载

  2. #include "delay.h"
  3. #include "Key.h"
  4. #include  <msp430x13x.h>
  5. #include <string.h>
  6. #include <math.h>
  7. #include <stdio.h>
  8. #include"ADC12.h"
  9. #include "hzlib.h"
  10. #include "LCD.h"
  11. #include "SD2608.h"

  12. #define MEM_IN 0x02                        //P3.1
  13. #define MEM_OUT 0x04                       //P3.2
  14. #define SCLK 0x08                          //P3.3
  15. #define ATRDY 0x40                         //AT45DB161 RDY/BUSY          P2.6
  16. #define ATCS 0x80                          //AT45DB161 AT/CS             P2.7
  17. #define TIME_MS 10000                        //采样频率为100



  18. #define X_CHANNEL 0
  19. #define Y_CHANNEL 1
  20. #define Z_CHANNEL 2
  21. //#define TIMEWINDOW_MIN 8                //时间窗,×0.02s=0.2s
  22. //#define TIMEWINDOW_MAX 30               //时间窗,×0.02s=0.8s
  23. #define REGULATION      8              //认为找到稳定规律所需要的步数


  24. unsigned char       itemp,jtemp,temp;               
  25. unsigned char       TIMEWINDOW_MIN =11;        //时间窗,×0.02s=0.2
  26. unsigned char       TIMEWINDOW_MAX =30        ;       //时间窗,×0.02s=0.8s

  27. unsigned int  Adresult;               
  28. unsigned char _bad_flag[3];                                                                                                                                                       
  29. unsigned char  sampling_counter;                                                               
  30. unsigned int _adresult[3];                                                                       
  31. unsigned int _max[3]={0,0,0};
  32. unsigned int _min[3]={5000,5000,5000};
  33. unsigned int _dc[3]={500,500,500};
  34. unsigned int _vpp[3]={30,30,30};       
  35. unsigned int  _precision[3]={5,5,5};       
  36. unsigned int _old_fixed[3];
  37. unsigned int _new_fixed[3];
  38. unsigned long int STEPS;       
  39. unsigned long int STEPS_Temp;       
  40. unsigned  int _array0[3]={1,1,1};
  41. unsigned  int _array1[3]={1,1,1};
  42. unsigned  int _array2[3]={0,0,0};
  43. unsigned  int _array3[3]={0,0,0};
  44. unsigned  int _array4[3]={0,0,0};
  45. unsigned  int  ADXYZ[3] ;


  46. unsigned long int totalxyz[3];
  47. unsigned int averagexyz[3];
  48. unsigned char avxyz;
  49. unsigned char counter;
  50. unsigned char counterx=0;
  51. unsigned char countery=0;
  52. unsigned char counterz=0;


  53. unsigned char Interval=0;                //记录时间间隔数
  54. unsigned char TempSteps=0;                //记步缓存
  55. unsigned char InvalidSteps=0;        //无效步缓存
  56. unsigned char ReReg=1;                       
  57.                                                                                
  58.                                                                                 //        1-已经开始,但是还没有找到规律
  59.                                                                                 //        0-已经找到规律
  60. unsigned char high_or_low=0,k=0;
  61. unsigned char recieve;
  62. unsigned char date[7];
  63. unsigned char wdata[7]={0,0,128,0,1,1,0};








  64. void fnClkInit(void)
  65. {
  66.   unsigned int a;
  67.   WDTCTL = WDTPW +WDTHOLD;                                //关闭看门狗
  68.    BCSCTL1|=XTS;                                           //XT1口为高频  XTS=1,ACLK = LFXT1
  69.   do
  70.     {
  71.      IFG1&=~OFIFG;                                        //清除振荡器失效标志
  72.      for (a=0xFF;a>0;a--);                                //延时 等待XT1口起振
  73.      }
  74.    while ((IFG1&OFIFG)!=0);                                //判断XT1口是否起振
  75.          BCSCTL2 |= SELM_3;                          //选择LFXT1CLK为MCLK时钟源
  76.          BCSCTL1 |= XT2OFF+DIVA0+DIVA1;                   //禁止XT2口 ACLK 8分频
  77. }  
  78.                     
  79. /*******************定时器初始化定时5MS*******************/
  80. void TimerBInit(void)
  81. {
  82.        TBCTL   = TBSSEL_1 + TBCLR ;               //ACLK为定时器时钟   
  83.        TBCCTL0 = CCIE;                                      //开定时器中断
  84.        TBCCR0  = TIME_MS;                                      //5MS
  85.        //TBCTL  |= MC0;                                       //增计数模式
  86. }



  87. void main(void)
  88. {
  89.    fnClkInit();
  90.    TimerBInit();
  91.    //usart_Init();
  92.    Init_ADC();
  93.    Init_keyPort();
  94.    vdLCD_Init();
  95.    vdDisp_Main();
  96.    clock();
  97.      _EINT();
  98. while(1)
  99.    {
  100.     Iskey ();
  101.      vdDisp_bushu(STEPS);
  102.    }
  103. }


  104. #pragma vector=TIMERB0_VECTOR
  105. __interrupt void Timer_B (void)
  106. {
  107.    ADC12CTL0 &= ~ENC;

  108.   if(recieve==0x04)
  109.    {
  110.      //----------------------------------------------ADC采样----------------------//
  111.        ADXYZ[0] =ADC12MEM0;//AX
  112.        ADXYZ[1]=ADC12MEM1;//AY
  113.        ADXYZ[2]=ADC12MEM2;//AZ
  114.        //----------------------------------------------开机求平均值判断放置位置----------------------//
  115.        if(avxyz==0)
  116.        {  
  117.            counter=counter+1;
  118.            totalxyz[0]=totalxyz[0]+ADXYZ[0];
  119.            totalxyz[1]=totalxyz[1]+ADXYZ[1];
  120.            totalxyz[2]=totalxyz[2]+ADXYZ[2];
  121.            if(counter>=40)
  122.            {
  123.               counter=0;
  124.               counterx=0;
  125.               countery=0;
  126.               counterz=0;
  127.               averagexyz[0]= (int)(totalxyz[0]/40);
  128.               averagexyz[1]= (int)(totalxyz[1]/40);
  129.               averagexyz[2]= (int)(totalxyz[2]/40);
  130.               totalxyz[0]=0;
  131.               totalxyz[1]=0;
  132.               totalxyz[2]=0;
  133.               avxyz=1;
  134.       //----------------------------------------------x方向为垂直位置----------------------//
  135.               if (( averagexyz[0]>= averagexyz[1])&&( averagexyz[0]>= averagexyz[2])&& (averagexyz[0]>3500))
  136.               {
  137.                 counterx=1;
  138.                 countery=0;
  139.                 counterz=0;
  140.               }
  141.               else if (( averagexyz[0]<= averagexyz[1])&&( averagexyz[0]<= averagexyz[2])&& (averagexyz[0]<1800))
  142.               {
  143.                 counterx=1;
  144.                 countery=0;
  145.                 counterz=0;
  146.               }
  147.                //----------------------------------------------y方向为垂直位置----------------------//
  148.              else if (( averagexyz[1]>= averagexyz[0])&&( averagexyz[1]>= averagexyz[2])&& (averagexyz[1]>3500))
  149.               {
  150.                 counterx=0;
  151.                 countery=1;
  152.                 counterz=0;
  153.               }
  154.               else if(( averagexyz[1]<= averagexyz[0])&&( averagexyz[1]<= averagexyz[2])&& (averagexyz[1]<1800))
  155.               {
  156.                 counterx=0;
  157.                 countery=1;
  158.                 counterz=0;
  159.               }
  160.                //----------------------------------------------z方向为垂直位置----------------------//
  161.               else if (( averagexyz[2]>= averagexyz[0])&&( averagexyz[2]>= averagexyz[1])&& (averagexyz[2]>3500))
  162.               {
  163.                 counterx=0;
  164.                 countery=0;
  165.                 counterz=1;
  166.               }
  167.               else if (( averagexyz[2]<= averagexyz[0])&&( averagexyz[2]<= averagexyz[1])&& (averagexyz[2]<1800))
  168.               {
  169.                 counterx=0;
  170.                 countery=0;
  171.                 counterz=1;
  172.               }
  173.               //----------------------------------------------未能确定方向重现找----------------------//
  174.               else
  175.               {
  176.                 avxyz=0;
  177.               }
  178.            }
  179.            
  180.        }
  181.         //----------------------------------------------加速度滤波----------------------//
  182.        if(avxyz==1)
  183.        {
  184.                 for(jtemp=X_CHANNEL;jtemp<=Z_CHANNEL;jtemp++)
  185.                 {
  186.                         _array4[jtemp]=_array3[jtemp];
  187.                         _array3[jtemp]=_array2[jtemp];
  188.                         _array2[jtemp]=_array1[jtemp];
  189.                         _array1[jtemp]=_array0[jtemp];
  190.                        
  191.                        _array0[jtemp]= ADXYZ[jtemp];
  192.                        _adresult[jtemp]=_array0[jtemp]+_array1[jtemp]+_array2[jtemp]+_array3[jtemp]+_array4[jtemp];
  193.                        _adresult[jtemp]=_adresult[jtemp]/5;
  194.                
  195.                         if (_adresult[jtemp]>_max[jtemp])               {_max[jtemp]=_adresult[jtemp];}
  196.                         if (_adresult[jtemp]<_min[jtemp])               {_min[jtemp]=_adresult[jtemp];}
  197.                 }
  198.                
  199.               sampling_counter=sampling_counter+1;
  200.         Interval=Interval+1;
  201.        
  202.                 //----------------------------------计算动态门限和动态精度-----------------------//
  203.         if (sampling_counter==50)
  204.           {               
  205.           sampling_counter=0;
  206.                                
  207.           for(jtemp=X_CHANNEL;jtemp<=Z_CHANNEL;jtemp++)
  208.                 {
  209.                 _vpp[jtemp]=_max[jtemp]-_min[jtemp];
  210.                                    _dc[jtemp]=_min[jtemp]+_vpp[jtemp]/2;
  211.                                _max[jtemp]=0;
  212.                                    _min[jtemp]=5000;
  213.                                 _bad_flag[jtemp]=0;

  214.                                 if (_vpp[jtemp]>=1000)
  215.                                      {
  216.                                         TIMEWINDOW_MIN =20;
  217.                                         TIMEWINDOW_MAX =60;
  218.                                         _precision[jtemp]=40;
  219.                                       }
  220.                                     else if ((_vpp[jtemp]>=400)&& (_vpp[jtemp]<1000))            
  221.                                       {
  222.                                         TIMEWINDOW_MIN =25;
  223.                                         TIMEWINDOW_MAX =70;
  224.                                         _precision[jtemp]=20;
  225.                                        }
  226.                                   else if ((_vpp[jtemp]>=200) && (_vpp[jtemp]<400))  
  227.                                      {
  228.                                        TIMEWINDOW_MIN =35;
  229.                                        TIMEWINDOW_MAX =80;
  230.                                         _precision[jtemp]=10;
  231.                                      }  
  232.                        
  233.                                 else
  234.                                    {
  235.                                        _precision[jtemp]=2;
  236.                                  _bad_flag[jtemp]=1;
  237.                                      }

  238.                         }
  239.               }
  240.                
  241.                 //--------------------------线性移位寄存器--------------------------------------//

  242.                 for(jtemp=X_CHANNEL;jtemp<=Z_CHANNEL;jtemp++)
  243.                 {
  244.                         _old_fixed[jtemp]=_new_fixed[jtemp];

  245.                    if (_adresult[jtemp]>=_new_fixed[jtemp])                        
  246.                       {   
  247.                          if((_adresult[jtemp]-_new_fixed[jtemp])>=_precision[jtemp])                  
  248.                         _new_fixed[jtemp]=_adresult[jtemp];
  249.                       }
  250.                   if (_adresult[jtemp]<_new_fixed[jtemp])
  251.                              {   
  252.                            if((_new_fixed[jtemp]-_adresult[jtemp])>=_precision[jtemp])                  
  253.                         _new_fixed[jtemp]=_adresult[jtemp];
  254.                       }
  255.                 }

  256.                 //------------------------- 动态门限判决 ----------------------------------
  257.       
  258.                 if(counterx==1)
  259.                 {
  260.                   if ((_old_fixed[X_CHANNEL]>=_dc[X_CHANNEL])&&(_new_fixed[X_CHANNEL]<_dc[X_CHANNEL])&&(_bad_flag[X_CHANNEL]==0))        
  261.                    {
  262.                                    if((Interval>=TIMEWINDOW_MIN)&&(Interval<=TIMEWINDOW_MAX))        //如果时间间隔在有效的时间窗内
  263.                                         {
  264.                                           if(ReReg==1)                                        //如果还没有找到规律
  265.                                            {            
  266.                                                 TempSteps++;                                        //记步缓存加1
  267.                                               if(TempSteps>=REGULATION)                               //如果记步缓存达到所要求的规律数
  268.                                              {
  269.                                                   ReReg=0;                                //已经找到规律
  270.                                                   STEPS=STEPS+TempSteps;        //更新显示
  271.                                                   TempSteps=0;
  272.                                                }
  273.                                               Interval=0;
  274.                                             }
  275.                                          else if(ReReg==0)                                //如果已经找到规律,直接更新显示
  276.                                           {
  277.                                               STEPS++;
  278.                                               TempSteps=0;
  279.                                               Interval=0;
  280.                                             }
  281.                                        }  
  282.                
  283.                                    else if(Interval>TIMEWINDOW_MAX)        //如果时间间隔大于时间窗上限,记步已经间断,重新寻找规律
  284.                                    {
  285.                                          
  286.                                             InvalidSteps=0;       
  287.                                             ReReg=1;
  288.                                             TempSteps=1;
  289.                                             Interval=0;
  290.                                             
  291.                                             
  292.                        
  293.                                           }
  294.                                      
  295.                                
  296.                        }
  297.                 }
  298.         
  299.         if(countery==1)
  300.         {
  301.           if ((_old_fixed[Y_CHANNEL]>=_dc[Y_CHANNEL])&&(_new_fixed[Y_CHANNEL]<_dc[Y_CHANNEL])&&(_bad_flag[Y_CHANNEL]==0))        
  302.               {
  303.                
  304.                        if((Interval>=TIMEWINDOW_MIN)&&(Interval<=TIMEWINDOW_MAX))        //如果时间间隔在有效的时间窗内
  305.                                         {
  306.                                           if(ReReg==1)                                        //如果还没有找到规律
  307.                                            {            
  308.                                                 TempSteps++;                                        //记步缓存加1
  309.                                               if(TempSteps>=REGULATION)                               //如果记步缓存达到所要求的规律数
  310.                                              {
  311.                                                   ReReg=0;                                //已经找到规律
  312.                                                   STEPS=STEPS+TempSteps;        //更新显示
  313.                                                   TempSteps=0;
  314.                                                }
  315.                                               Interval=0;
  316.                                             }
  317.                                          else if(ReReg==0)                                //如果已经找到规律,直接更新显示
  318.                                           {
  319.                                               STEPS++;
  320.                                               TempSteps=0;
  321.                                               Interval=0;
  322.                                             }
  323.                                        }  
  324.                
  325.                                    else if(Interval>TIMEWINDOW_MAX)        //如果时间间隔大于时间窗上限,记步已经间断,重新寻找规律
  326.                                    {
  327.                                             InvalidSteps=0;       
  328.                                             ReReg=1;
  329.                                             TempSteps=1;
  330.                                             Interval=0;
  331.                                             
  332.                        
  333.                                       }
  334.                                      
  335.                                
  336.                         }
  337.                 }
  338.         if(counterz==1)
  339.         {
  340.           if ((_old_fixed[Z_CHANNEL]>=_dc[Z_CHANNEL])&&(_new_fixed[Z_CHANNEL]<_dc[Z_CHANNEL])&&(_bad_flag[Z_CHANNEL]==0))        
  341.                {
  342.                        
  343.                                    if((Interval>=TIMEWINDOW_MIN)&&(Interval<=TIMEWINDOW_MAX))        //如果时间间隔在有效的时间窗内
  344.                                         {
  345.                                           if(ReReg==1)                                        //如果还没有找到规律
  346.                                            {            
  347.                                                 TempSteps++;                                        //记步缓存加1
  348. ……………………

  349. …………限于本文篇幅 余下代码请从51黑下载附件…………
复制代码

所有资料51hei提供下载:
ADXL重力加速度传感器实现计步器程序(利用MSP430F135实现).zip (120.55 KB, 下载次数: 35)
回复

使用道具 举报

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

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

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