stm32驅動超聲波模塊源碼


  下面是關於stm32驅動超聲波模塊的一段代碼,有需要的朋友可以複製參考,希望對大家能夠有所幫助和啓發。


 

 #define HCSR04_PORT GPIOB
  #define HCSR04_CLK RCC_APB2Periph_GPIOB
  #define HCSR04_TRIG GPIO_Pin_8
  #define HCSR04_ECHO GPIO_Pin_9
  #define TRIG_Send(n) do{
  if(n == 0)
  GPIO_ResetBits(HCSR04_PORT,HCSR04_TRIG);
  else if(n == 1)
  GPIO_SetBits(HCSR04_PORT,HCSR04_TRIG);
  }while(0)
  #define ECHO_Reci GPIO_ReadInputDataBit(GPIOB,HCSR04_ECHO)
  void UltrasonicInit(void)
  {
  GPIO_InitTypeDef GPIO_InitStructure;
  RCC_APB2PeriphClockCmd(HCSR04_CLK, ENABLE);
  //IO初始化
  GPIO_InitStructure.GPIO_Pin = HCSR04_TRIG; //發送電平引腳
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;//推輓輸出
  GPIO_Init(HCSR04_PORT, &GPIO_InitStructure);
  GPIO_ResetBits(HCSR04_PORT,HCSR04_TRIG);
  GPIO_InitStructure.GPIO_Pin = HCSR04_ECHO; //返回電平引腳
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;//浮空輸入
  GPIO_Init(HCSR04_PORT, &GPIO_InitStructure);
  GPIO_ResetBits(HCSR04_PORT,HCSR04_ECHO);
  TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure; //生成用於定時器設置的結構體
  RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM6, ENABLE); //使能對應RCC時鐘
  //配置定時器基礎結構體
  TIM_DeInit(TIM6);
  TIM_TimeBaseStructure.TIM_Period = (1000-1); //設置在下一個更新事件裝入活動的自動重裝載寄存器週期的值 計數到1000爲1ms
  TIM_TimeBaseStructure.TIM_Prescaler =(72-1); //設置用來作爲TIMx時鐘頻率除數的預分頻值 1M的計數頻率 1US計數
  TIM_TimeBaseStructure.TIM_ClockDivision=TIM_CKD_DIV1;//不分頻
  TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //TIM向上計數模式
  TIM_TimeBaseInit(TIM6, &TIM_TimeBaseStructure); //根據TIM_TimeBaseInitStruct中指定的參數初始化TIMx的時間基數單位
  TIM_ClearFlag(TIM6, TIM_FLAG_Update); //清除更新中斷,免得一打開中斷立即產生中斷
  TIM_ITConfig(TIM6,TIM_IT_Update,ENABLE); //打開定時器更新中斷
  NVIC_InitTypeDef NVIC_InitStructure;
  NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
  NVIC_InitStructure.NVIC_IRQChannel = TIM6_IRQn; //選擇串口1中斷
  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0; //搶佔式中斷優先級設置爲1
  NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0; //響應式中斷優先級設置爲1
  NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //使能中斷
  NVIC_Init(&NVIC_InitStructure);
  TIM_Cmd(TIM6,DISABLE);
  }
  //定時器6中斷服務程序
  u32 msHcCount = 0;
  void TIM6_IRQHandler(void) //TIM6中斷
  {
  if (TIM_GetITStatus(TIM6, TIM_IT_Update) != RESET) //檢查TIM3更新中斷髮生與否
  {
  TIM_ClearITPendingBit(TIM6, TIM_IT_Update); //清除TIMx更新中斷標誌
  msHcCount++;
  }
  }
  static void OpenTimerForHc() //打開定時器
  {
  TIM_SetCounter(TIM6,0); //清除計數
  msHcCount = 0;
  TIM_Cmd(TIM6, ENABLE); //使能TIMx外設
  }
  static void CloseTimerForHc() //關閉定時器
  {
  TIM_Cmd(TIM6, DISABLE); //使能TIMx外設
  }
  //獲取定時器時間
  u32 GetEchoTimer(void)
  {
  u32 t = 0;
  t = msHcCount*1000; //將MS轉換成US
  t += TIM_GetCounter(TIM6); //得到總的US
  TIM6->CNT = 0; //將TIM6計數寄存器的計數值清零
  return t;
  }
  //一次獲取超聲波測距數據 兩次測距之間需要相隔一段時間,隔斷迴響信號
  //爲了消除餘震的影響,取五次數據的平均值進行加權濾波。
  float Hcsr04GetLength(void )
  {
  u32 t = 0;
  int i = 0;
  float lengthTemp = 0;
  float sum = 0;
  while(i!=5)
  {
  /*發送一個20ms的脈衝*/
  TRIG_Send(1);
  osDelay(20);
  TRIG_Send(0);
  while(ECHO_Reci == 0); //等待接收口高電平輸出(超聲波發出)
  OpenTimerForHc(); //打開定時器
  while(ECHO_Reci == 1); //等待超聲波返回
  CloseTimerForHc(); //關閉定時器
  t = GetEchoTimer(); //獲取時間,分辨率爲1US
  lengthTemp = ((float)t*17/1000.0);//cm
  sum = lengthTemp + sum ;
  i = i + 1;
  }
  lengthTemp = sum/5.0;
  return lengthTemp;
  }
  


  最後在個大家提供一些stm32方面的參考資料

  (stm32直流電機驅動)

  http://www.makeru.com.cn/live/1392_1218.html?s=45051

  (stm32 溫溼度採集)

  http://www.makeru.com.cn/live/detail/1476.html?s=45051

  ( ADC讀取光照傳感器)

  http://www.makeru.com.cn/live/1392_1004.html?s=45051

  (stm32串口應用)

  http://www.makeru.com.cn/live/1392_1164.html?s=45051

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章