自制电动滑板(二)

前言:因为前段时间一直忙找工作的事情,完事了以后到时又催项目的进度,所以等了好久才进行第二篇的更新。这里主要说一些代码的实现,考虑到很多人大家用的单片机不太一样,所以我就没必要把整个工程都贴出来(作者的是KL26),有需要的可以留言发邮箱,所以这里就只贴出来主要部分代码。

1、整体结构

    主要模块:一路PWM,一个PIT定时器(包括设置定时中断),一个串口(包括串口接受中断),若干GPIO。其对应的初始化为:

  DisableInterrupts;

  gpio_init (PTE2, GPO,0);     // FENG MING
    
  gpio_init (PTA17, GPI,1);       // HONG WAI
  
  uart_init (UART1, 9600);      // 设置串口,9600波特率
  
  tpm_pwm_init(TPM0, TPM_CH1,200,16);      // 这个电调需要先给大概一毫秒的低电平,完成初始化,大约20%
  TPM0_C1V=10000;    // 先给PWM一个低占空比
 
  pit_init_ms(PIT0,8);                          //定时bus时钟中断
  set_vector_handler(PIT_VECTORn,pit0_hander);   // 设置PIT中断服务函数到中断向量表里
  
  set_vector_handler(UART1_VECTORn ,uart1_test_handler);  
  EnableInterrupts;       // 使能所有中断

  enable_irq(UART1_IRQn); // 使能串口中断
  enable_irq(PIT_IRQn);   // 使能PIT中断
  uart_rx_irq_en(UART1);  // 使能串口接收中断
  

2、串口模块:主要进行蓝牙串口数据的接受

     除了串口初始化,设置接受中断外还需要在中断函数中进行串口数据的接受,以下是部分代码和注释:

void uart1_test_handler(void)
{
    UARTn_e uratn = UART1;

    if(UART_S1_REG(UARTN[uratn]) & UART_S1_RDRF_MASK)   //接收数据寄存器满
    {
        uart_getchar(UART1,&Re_buff[counter]);  //Re_buff是自己设置的一个数组,接受串口数据
        if(counter==0&&Re_buff[0]!=0xA5) return;  //Re_buff[0]!=0xA5 协议报头为0xA5
        counter++;
        if(counter==3)   //Re_buff数组只接受三个字节,代表了手机发送的指令
        {
        counter=0;
        sign=1;  
        }
    }

3、PIT定时器:主要定时进行串口接收到的数据的解析

      启动定时器中断是因为不能一直进行数据解析,因为串口数据需要不断的接受并更新。

      Re_buff [ ]有三个字节,其中前两个字节也就是协议的报头为启动信号,0xA5和0x5A,设计这样两个报头的目的是为了防止滑板收到其他的蓝牙数据,导致滑板失控等现象的发生,一般0xA5和0x5A相邻出现的概率很小,如果你想更安全一些,可以多加几个字节作为协议的报头。第三个字节就是滑板的状态字节了,其中0x02 0x03 0x04 0x05 0xAA 0x0FF分别对应着手机上几个按键,eg: 当按下停车按钮时,手机会向滑板发送 0xA5 0x5A 0x0FF的信息,滑板通过辨别最后一个字节就会知道是停车。

     接下来就是一个简单的处理,比如我通过第三个字节检测到要加速,我就可以通过设置A=0,A1=0,A2=0,B=0,C=1,D=0;(这几个变量是半夜三四点迷糊的时候瞎定的,后续也没改)这几个变量的值,也可以说是置标志位来进行接下来的处理,接下来的处理也就是控制PWM的占空比实现调速,代码实现在主函数的while循环中。

void pit0_hander()
{
    if(PIT_TFLG(PIT0) == 1 )        //判断是否 PIT0 进入中断
    {  

  if(sign)
         {  
         sign=0;
         if(Re_buff[0]==0xA5)
         if(Re_buff[1]==0x5A)      // 协议报头判断
         {
           if(Re_buff[2]==0x02)    // 加速
           {
             A=0,A1=1,A2=0,B=0,C=0,D=0;
             Re_buff[2]=0x00;
             
           }
           if(Re_buff[2]==0x03)
           {
             A=0,A1=0,A2=1,B=0,C=0,D=0;
             Re_buff[2]=0x00;
           }
           
           if(Re_buff[2]==0x04)
           {
             A=0,A1=0,A2=0,B=1,C=0,D=0;
             Re_buff[2]=0x00;
             
           }
           
           if(Re_buff[2]==0x05)
             
           {
             A=0,A1=0,A2=0,B=0,C=1,D=0;
             Re_buff[2]=0x00;
             
           }
           
           if(Re_buff[2]==0xAA)   // 启动
           {
             A=1,A1=0,A2=0,B=0,C=0,D=0;
             Re_buff[2]=0x00;
             
           }
           if(Re_buff[2]==0xFF)   // 停车
           {
             A=0,A1=0,A2=0,B=0,C=0,D=1;
             Re_buff[2]=0x00;
           }
          }
         }
  
         duiguan=gpio_get(PTA17);    // 以下部分如果不加光电对管可以忽略,主要实现自启停
       
         if(!qidongflag)
           if(!duiguan)
        {
           BmaCnt=25;             // BmaCnt 为蜂鸣器设置,数值大小控制响的时间的长短
           qidongflag=1;
         }
  
         if(pwm>=jishupwm)
         if(qidongflag)
    {
           if(!duiguan)
           {
           zhanli++;
           if(zhanli>600)
           {
           zhanli_flag=1; 
           zhanli=600;
           }
           } 
           
           if(zhanli_flag)
           if(duiguan)
           {
           zhanli_flag=1;
           zhanli--;
           if(zhanli<400)
           {
            pwm=10000; 
            zhanli_flag=0;
           }
         } 
      }    
         
         if(BmaCnt > 0)     
       {
         gpio_set (PTE2, 1);
         BmaCnt--;
        }
      else
      {
       gpio_set (PTE2, 0);
       }  

        PIT_Flag_Clear(PIT0);       //清中断标志位
    }

}

4、PWM控制:将PIT转换后的信息进行相应的PWM占空比的设置

      举个例子就明白了:比如我加速的信号是0X02,这时候我在PIT中断里面判断第三个字节为0X02为预先设计的加速信号,所以设置了使 A=0,A1=1,A2=0,B=0,C=0,D=0;(在3部分代码中实现的),这里我要做的就是判断A1是否为1(只有这里置1了,其余的比如说减速停车信号时,该A1变量均为0),判断为1后进行PWM的设置,设置完之后,滑板就会自动进行加减速。部分实现代码如下:

  while(1)
   {     
     if(A&&!A1&&!A2&&!B&&!C&&!D)
      qidongflag=1;
     
   if(qidongflag)  
{
        if(!key_flag)
        if(!A&&A1&&!A2&&!B&&!C&&!D)     // 判断 只有A1置 1 
        {
          key_flag=1;
          A1=0;                // 进来之后立马清除标志位
          pwm=pwm+100;         // PWM加100,进行加速
          if(pwm>14000)
          pwm=14000;          // 控制最大速度,注意滑行安全
          if(pwm<jishupwm)
          pwm=jishupwm;
           BmaCnt=15;        // 每次手机发送指令,这边进行蜂鸣器哔哔提示,说明加速了
          key_flag=0;
         }

5、GPIO模块

      进行蜂鸣器和光电对管的检测,其实就是一个高低电平的输出及检测判断,实现起来非常简单,这里就不贴代码了。

 

需要整个工程代码的可以留邮箱。。。

评论 28
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值