日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

STM32CubeMX学习——旋转编码器模块

發布時間:2023/12/15 编程问答 34 豆豆
生活随笔 收集整理的這篇文章主要介紹了 STM32CubeMX学习——旋转编码器模块 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

前言

雨打燈難滅,風吹色更明。
若飛天上去,定作月邊星。——李白《詠螢火》


一、旋轉編碼器介紹

旋轉編碼器是一種可以左右旋轉,同時也可以按下,也可以按下旋轉的器件,通過左右旋轉對應著內部不同開關的導通,同時按下也可以旋轉,由此看來旋轉編碼器可以實現很復雜的功能,簡單的通過左右旋轉可以調節音量、亮暗等功能,按鍵可以發揮普通按鍵的作用,按下按鍵的同時左右旋轉又可以區別普通旋轉的按鍵,因此可以用一個旋轉編碼器同時調節音量和亮暗(舉例),同時也可以通過不同的轉速實現不同的功能,綜上所述,它的功能很復雜,用處也很多。

旋轉編碼器是用來測量轉速并配合 PWM 技術可以實現快速調速的裝置,光電式旋轉編碼器通過光電轉換,可將輸出軸的角位移、角速度等機械量轉換成相應的電脈沖以數字量輸出(REP)。

  • 按信號的輸出類型分為: 電壓輸出、集電極開路輸出、推拉互補輸出和長線驅動輸出。
  • 形式分類:
    有軸型:有軸型又可分為夾緊法蘭型、同步法蘭型和伺服安裝型等。
    軸套型:軸套型又可分為半空型、全空型和大口徑型等。
    以編碼器工作原理可分為: 光電式、磁電式和觸點電刷式。
    按碼盤的刻孔方式不同分類編碼器可分為增量式和絕對式兩類。

旋轉編碼器的原理和特點

  • 原理:

    • 旋轉編碼器是集光機電技術于一體的速度位移傳感器。當旋轉編碼器軸帶動光柵盤旋轉時,經發光元件發出的光被光柵盤狹縫切割成斷續光線,并被接收元件接收產生初始信號。該信號經后繼電路處理后,輸出脈沖或代碼信號。
    • 旋轉編碼器是由一個中心有軸的光電碼盤組成,其上有環形通、暗的刻線,有光電發射和接收器件讀取,獲得四組正弦波信號組合成A、B、C、D,每個正弦波相差90度相位差,將C、D信號反向,疊加在A、B兩相上,可以增強穩定信號;另每轉輸出一個Z相脈沖以代表零位參考位。因為A、B兩相相差90度,可以通過比較A相在前還是B相在前,借此來判別編碼器的正轉與反轉,通過零位脈沖,可獲得編碼器的零位參考位。
  • 特點:

    體積小、重量輕、品種多、功能全、頻響高、分辨能力高,力矩小,耗能低,性能穩定,可靠使用壽命長等特點。

1、增量式編碼器

增量式編碼器是將位移轉換成周期性的電信號,再把這個電信號轉變成計數脈沖,用脈沖的個數表示位移的大小。增量式編碼器也稱為正交編碼器,是通過兩個信號線的脈沖輸出來進行數據處理,一個輸出脈沖就對應于一個增量位移,編碼器每轉動一定的位移,就會產生一個脈沖信號。通過讀取單位時間脈沖信號的數量,達到測量速度的效果(v = s / t),通過對脈沖信號的累加,和編碼器的碼盤周長 (轉一圈對應的距離) 便可以達到計算距離的效果(s = n * d)。

  • 工作原理:

    增量式旋轉編碼器通過兩個光敏接收管來轉化角度碼盤的時序和相位關系,得到角度碼盤角度位移量的增加(正方向)或減少(負方向)。
  • 上圖A、B兩點間的距離為S2,A、B表示兩個相同的光敏接收管,下面的角度碼盤的光柵間距分別為S0(凹槽)和S1(凸起)。
  • 當角度碼盤勻速轉動時,可知輸出波形圖中的S0:S1:S2比值與實際圖的S0:S1:S2比值相同,同理,當角度碼盤變速轉動時,輸出波形圖中的S0:S1:S2比值與實際圖的S0:S1:S2比值仍相同。
  • 通過輸出波形圖可知每個運動周期:
順時針運動逆時針運動
A BA B
1 11 1
0 11 0
0 00 0
1 00 1
  • 我們把當前的A、B輸出值保存起來,與下一個到來的A、B輸出值做比較,就可以得出角度碼盤轉動的方向;

  • 如果光柵格S0等于S1時,也就是S0和S1弧度夾角相同,且S2等于S0的1/2,那么可得到此次角度碼盤運動位移角度為S0弧度夾角的1/2,再除以所用的時間,就得到此次角度碼盤運動位移的角速度。

  • S0等于S1時,且S2等于S0的1/2時,1/4個運動周期就可以得到運動方向位和位移角度,如果S0不等于S1,S2不等于S0的1/2,那么要1個運動周期才可以得到運動方向位和位移角度了。

    (我們用的鼠標的滾輪也是這個原理。)

  • 實際使用的增量式編碼器輸出三組方波脈沖A、B和Z(有的叫C相)相。A、B兩組脈沖相位差90o,可以判斷出旋轉方向和旋轉速度。而Z相脈沖又叫做零位脈沖(有時也叫索引脈沖),為每轉一周輸出一個脈沖,Z相脈沖代表零位參考位,通過零位脈沖,可獲得編碼器的零位參考位,專門用于基準點定位,如下圖所示:

  • 增量是編碼器轉軸旋轉時,有相應的脈沖輸出,其計數起點可以任意設定,可實現多圈無限累加和測量。編碼器軸轉動一圈會輸出固定的脈沖數,脈沖數由編碼器碼盤上面的光柵的線數所決定,編碼器以每旋轉360度提供多少通或暗的刻線稱為分辨率,也稱解析分度、或稱作多少線,一般在每轉5~10000線,當需要提高分辯率時,可利用90度相位差的A、B兩路信號進行倍頻或者更換高分辯率編碼器。

  • 增量型編碼器精度取決于機械和電氣的因素,這些因素有:光柵分度誤差、光盤偏心、軸承偏心、電子讀數裝置引入的誤差以及光學部分的不精確性,誤差存在于任何編碼器中。

  • 編碼器的信號輸出有正弦波(電流或電壓)、方波(TTL、HTL)等多種形式。并且都可以用差分驅動方式,含有對稱的A+/A-、B+/B-、Z+/Z-三相信號,由于帶有對稱負信號的連接,電流對于電纜貢獻的電磁場為0,信號穩定衰減最小,抗干擾最佳,可傳輸較遠的距離,例如:對于TTL的帶有對稱負信號輸出的編碼器,信號傳輸距離可達150米。對于HTL的帶有對稱負信號輸出的編碼器,信號傳輸距離可達300米。

  • 增量式編碼器軸旋轉時,有相應的相位輸出。其旋轉方向的判別和脈沖數量的增減,需借助后部的判向電路和計數器來實現。其計數起點可任意設定,并可實現多圈的無限累加和測量。還可以把每轉發出一個脈沖的Z信號,作為參考機械零位。當脈沖已固定,而需要提高分辨率時,可利用帶90度相位差A,B的兩路信號,對原脈沖數進行倍頻。

  • 編碼器時序:

  • 實物圖:

我使用的是下面這種比較簡單的五腳旋轉編碼器:


二、引腳配置

我使用的旋轉編碼器有五個引腳,可能還會有其他不同類型的會有不同的引腳,
這五個引腳分別為GND, VCC(+), SW, DT, CLK,具體的引腳已經在簡介的圖中標明了。

  • VCC:接電源正極 3.3~5V;
  • GND:接地;
  • SW(Switch:開關):PA7(TIM3_CH2)
  • DT(DT:數據):PA6(TIM3_CH1)
  • CLK(CLK:時鐘):PA5(任選一個引腳:配置為上拉輸入模式)

接線表:

旋轉編碼器的接口STM32的IO口設置的工作模式
VCCVCC(3.3V)-
GNDGND-
SW(Switch:開關)PA7定時器編碼模式
DT(DT:數據)PA6定時器編碼模式
CLK(CLK:時鐘)PA5GPIO_Mode_IPU(上拉輸入模式)
-PA9TX(USART1 串口1通信)
-PA10RX(USART1 串口1通信)

三、新建工程

1.打開STM32CubeMX軟件,點擊“新建工程”

2. 選擇 MCU 和封裝

3.配置時鐘



具體學習可以參考:博客網站-RCC學習

4.配置調試模式

5.串口(USART1)配置

6.定時器(TIM)配置

  • 配置為編碼器模式:

7.生成代碼

輸入項目名稱和路徑。(注:路徑中不允許出現中文。)

選擇應用的IDE,開發環境MDK-ARM V5

每個外設生成獨立的 ’.c/.h’ 文件

  • 不勾: 所有初始化代碼都生成在 main.c
  • 勾選: 初始化代碼生成在對應的外設文件。 如 GPIO 初始化代碼生成在 gpio.c 中。

    點擊 GENERATE CODE 生成代碼

8.構建工程

DeBug的模式根據不同的芯片進行選擇:


四、編寫代碼

在main.c文件中,添加一下代碼:

  • 重寫fget和fput函數:勾選微庫(這個很重要),添加頭文件<stdio.h>;
/* USER CODE BEGIN Includes */ #include<stdio.h> /* USER CODE END Includes */ /*** 函數功能: 重定向c庫函數printf到DEBUG_USARTx* 輸入參數: 無* 返 回 值: 無* 說 明:無*/ int fputc(int ch, FILE *f) {HAL_UART_Transmit(&huart1, (uint8_t *)&ch, 1, 0xffff);return ch; }/*** 函數功能: 重定向c庫函數getchar,scanf到DEBUG_USARTx* 輸入參數: 無* 返 回 值: 無* 說 明:無*/ int fgetc(FILE *f) {uint8_t ch = 0;HAL_UART_Receive(&huart1, &ch, 1, 0xffff);return ch; }
  • 添加代碼encoder文件對(.c/.h):
    • 首先要新建文件,然后在添加到工程中去;

  • 將新建的文件添加到工程中去;

  • 返回上一級,尋找自己新建的文件:


    - 此時,完成了添加encoder.c文件: 在encoder.c中添加如下代碼,即可將encoder.h添加進工程
#include "encoder.h"
  • 在encoder.c中添加代碼:
#include "encoder.h"uint8_t lock; //旋鈕鎖死標志(1表示鎖死) uint16_t count; //計數標志uint8_t ENCODER_READ(void) {uint8_t key = 0; //存放按鍵的值uint8_t level; //記錄按鈕另一端的電平值if(HAL_GPIO_ReadPin(encoder_port_A, encoder_right) && HAL_GPIO_ReadPin(encoder_port_A, encoder_left)) //讀取此時{lock = 0; //判斷旋鈕是否鎖死}if(!HAL_GPIO_ReadPin(encoder_port_A, encoder_right) && lock == 0) //判斷是否旋轉按鈕,同時判斷是否有按鈕鎖死{HAL_Delay(100);level = HAL_GPIO_ReadPin(encoder_port_A,encoder_left); //把旋鈕另一端電平狀態記錄HAL_Delay(13); //延時if(!HAL_GPIO_ReadPin(encoder_port_A, encoder_right)) //去抖{if(level == 0){key = 1; //右轉}else{key = 2; //左轉}count = 0; //初始鎖死判斷計數器while(!HAL_GPIO_ReadPin(encoder_port_A, encoder_right) && count < 60000) //等待放開旋鈕,同時累加判斷鎖死{count++;lock = 1;HAL_Delay(200);}}}if(!HAL_GPIO_ReadPin(encoder_port_A,encoder_down) && lock == 0){HAL_Delay(20);if(!HAL_GPIO_ReadPin(encoder_port_A,encoder_down)) //消抖{key=3;}}return key; }
  • 在encoder.h中添加代碼:
#ifndef _ENCODER_H_ #define _ENCODER_H_#include "main.h" #include "tim.h"#define encoder_port_A GPIOA#define encoder_left GPIO_PIN_6 //定義IO接口,DT, 旋鈕左轉 #define encoder_right GPIO_PIN_5 //定義IO接口,CLK,旋鈕右轉 #define encoder_down GPIO_PIN_7 //定義IO接口,SW, 旋鈕按下uint8_t ENCODER_READ(void); //接口讀取值#endif
  • 在主函數main.c中添加代碼:
/*** @brief The application entry point.* @retval int*/ int main(void) {/* USER CODE BEGIN 1 */int b;/* USER CODE END 1 *//* MCU Configuration--------------------------------------------------------*//* Reset of all peripherals, Initializes the Flash interface and the Systick. */HAL_Init();/* USER CODE BEGIN Init *//* USER CODE END Init *//* Configure the system clock */SystemClock_Config();/* USER CODE BEGIN SysInit *//* USER CODE END SysInit *//* Initialize all configured peripherals */MX_GPIO_Init();MX_TIM3_Init();MX_USART1_UART_Init();/* USER CODE BEGIN 2 */printf("encoder is ready:\r\n");/* USER CODE END 2 *//* Infinite loop *//* USER CODE BEGIN WHILE */while (1){/* USER CODE END WHILE *//* USER CODE BEGIN 3 */b = ENCODER_READ(); //讀出旋轉器編碼器值HAL_Delay(1000); if(b==1){printf("編碼器右轉\r\n");}if(b==2){printf("編碼器左轉\r\n");}if(b==3){printf("編碼器按下\r\n");}}/* USER CODE END 3 */ }

五、實驗結果

謝謝閱讀!!!

總結

以上是生活随笔為你收集整理的STM32CubeMX学习——旋转编码器模块的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。