為什麼我要搞單片機的定時器矩陣,懂的自然懂
///插播一條:我自己在今年年初錄製了一套還比較系統的入門單片機教程,想要的同學找我拿就行了免費的,私信我就可以哦~點我頭像黑色字體加我地球呺也能領取哦。最近比較閒,帶做畢設,帶學生參加省級或以上比賽///
大家好,我是大方老師。
定時功能非常常用,可以說是剛需,也可以說是很多人的痛點。
做LED閃爍效果要用定時、按鍵掃描要定時、數碼管掃描要定時、濾波要定時等等。
曾經,我在產品開發的時候也被各種定時需求搞得焦頭爛額。
還好,後面我自己寫了一個定時器的程序架構,今天一步到位,,徹底解決各種定時的問題。
最近有幾個學員在學習的時候搞不懂這個。
我藉此寫了這篇文章,然後基於這個文章內容來給學員們直播講解。
一、為什麼我要搞定時器矩陣
定時器矩陣這個概念是我自創的,簡單來說就是很多不同定時時間的軟體定時器組合。
因為產品開發這麼多年,總有亂七八糟的精準定時需求,有50us的,有1ms的,有10ms的,有50ms的,有100ms的等等。
如果沒有一個很好的程序架構的話,不同的精準定時需求一多,代碼就會很混亂,而且也不好管理,移植性和可擴展性那些就更不用提了。
二、解決需求的思路
然後我就在想,我能不能設計一個定時器的程序架構,讓它能夠適應所有的精準定時需求。
我的思維雛形大概是這樣的。
圖左邊是定時器時間源,類似於我們的時鐘源,一般我是用單片機定時器中斷做個50us的定時,因為用定時器做時間比較精準。
為什麼要用50us?因為我產品的RFD波形定時採集頻率是50us采一次。
如果你產品沒定時這麼頻繁的功能需求,你完全可以把定時時間源配置成10ms,甚至100ms,這個是根據不同的產品去調整的。
圖右邊的就是定時器矩陣,就是各種亂七八糟的不同定時需求組合,比如LED特效定時功能的定時需求、RFD波形定時採集、RFD重複碼濾波延時等等。
最終這些定時器矩陣都有一個時間單位/基準,這個時間單位/基準是由定時器時間源提供,如果我配置定時器中斷是50us,那定時器矩陣的時間單位就是50us。
有了這種想法以後,剩下的就是考驗你的經驗和代碼水平了。
三、代碼設計思路
一個工程師工作越久,做過的項目越多,就要慢慢形成一個面向對象的思維。
雖然上面雛形出來了,但是我相信很多人依然不知道怎麼動手去寫代碼。
這個是正常的,最好的方法就是先抄後超。
我是用面向對象的思維去做的,對於c語言來說,結構體是實現面向對象最好的方式。
這裡的對象不是你的男女朋友,而是世間萬物皆可以當做一個對象。
比如說人是一個對象,這個對象有很多屬性,比如說性別、年齡、身高、體重等等。
Ok,那在程序里,如何把這個對象的特徵用結構體展現出來呢?
可以通過下面這個代碼:
那回到我們定時器矩陣這裡,我們把定時器矩陣當做一個對象。
那這個定時器矩陣都需要具備哪些共同的特徵?
我總結了下面幾個:
.需要有個變量當做開關標誌控制該定時器啟動/停止
.需要有個變量當做當前的定時值
.需要有個變量當做該定時器的定時周期。
.定時時間到了以後,需要去執行相應動作,為了靈活使用,需要一個函數指針。
那用結構體來表示代碼如下:
這裡很多人可能有點懵逼,我怎麼想不到要這些東西呢?
這個是正常的,不用去糾結,我也不是一開始就把這幾個成員都想到的,而是後面做功能的時候慢慢完善的,你剛開始抄我的思維就行了。
後面很多應用都是用這種套路去做的,比如說我們的任務管理、比如菜單這些,用多了自然就熟了,以後你自己也能設計別的對象了。
Ok,這樣我們就把定時器矩陣這個對象的特徵設計好了。
四、定時器代碼實戰
1.前面我們用結構體自定義了一個定時器的對象來,下面就要用這個定時器對象」生」出定時器矩陣。
我們直接用定義結構體數組的方式,T_SUM就是我們定時器矩陣的個數,也就是我產品有多少個定時器需求。
後面我們所有的操作都是圍繞這個結構體來進行的。
2.配置定時器矩陣時間源,初始化定時器矩陣參數
A).我們首先要給這個定時器矩陣一個時間源,也就是配置我們要去配置單片機定時器中斷。
我們的定時頻率配置的是50us,是因為我們產品有的功能最短需要50us的定時。
然後,我們需要寫一個初始化函數,去調用這個定時器配置,以及初始化定時器矩陣參數。
B).然後在這個50us定時器中斷函數裡,去實現給定時器矩陣定時代碼。
這裡,我單獨寫了一個函數。
然後我們在定時器中斷函數裡調用這個函數,實現給定時器矩陣定時。
3.附加功能
定時器矩陣時間源配置好了,但是我們還需要一些函數來操作定時器矩陣對吧?
A).編寫創建定時器
我希望定時器能像任務一樣,想要的時候創建,所以就有了創建定時器函數。
我們創建定時器的時候這樣調用就可以了。
B).復位定時器
如果說我們需要循環定時的話,在定時時間到了以後就需要復位定時器,讓定時器重新啟動。
除了以上以外,其他功能可以自己去完善,比如說控制定時器狀態、刪除定時器、獲取定時器時間,這裡就不一一舉例了。
有了這個定時器程序架構,以後開發產品再也不怕有各種定時需求啦,使用方便,移植性也強,如果加個動態分配,就更完美了。