|
STM32 点灯丨V2.1.0 今天把昨天的设想给实现了,目前来看,这个程序可以算是当前的一个完成版本了。 加了IO口的GPIO的宏,方面以后改IO口。 - #define LED_PIN GPIO_Pin_5
|# n( |. o6 ]( W L% c% _ - #define LED_GPIO_PORT GPIOB
1 A7 z; v' x6 Q. ?& R - #define LED_GPIO_CLK RCC_APB2Periph_GPIOB
4 B6 y, G" W4 @1 Q - #define LED_POLAR 0 //LED的电平有效性,0:低电平有效,1:高电平有效8 s" f. N) f; ^( I9 ?! h
- #define LED_TYPE_NUM 3 //LED的类型数
复制代码
4 C& S; h: V) ~: q% A 这样,以后就可以直接在文件顶部直接修改,而不用修改初始化函数里的东西了。 在参数里增加了,IO口的电平有效性设置(也用宏来管理了),如果下次改成高电平有效,我们只要改一个数就可以实现了。 - typedef struct
2 B* p. q) R" |8 J3 ~ |) a - {
% l( C3 m8 K4 c/ Y - u16 Err_num; //故障代码* v, |) m- r% S( X% T7 r) _
- u8 Type; //LED的类型,0:常亮,1:闪烁,2:故障提示7 |; e4 Q9 V. D( J4 V
- u8 Enable; //使能LED) c8 u1 ] F! V+ y
- u8 PolarLED; //LED电平有效极性0 @% x2 T5 q) |4 O4 }$ H
- }LED_t;
复制代码 6 c; h& K- L* G* }+ M9 W; `
增加了极性检测函数,这样可以更好理解和维护程序。 - /** @brief 端口极性检查, P% J& C+ ], s9 k/ z
- * @param[in] polar : 极性
* w. |6 d$ F! F- s: G: Q/ } - data : 数据
+ n$ ^8 d4 X y+ N - * @param[out] 无
! @& B5 f+ I7 |. o - * @retval 0 : 无效
6 ~0 q* g6 o, ?" u) g8 M- g - 1 : 有效% \+ i& o0 ^3 d/ ?: j! [
- * @note 无& q4 p' j8 e& O2 v; F( K1 S
- */
! ], U# ]$ U6 z2 q6 e - u8 sLed_Polar(u8 polar, u8 data): ~4 o3 m& q' n! d; |* J
- {' V* @* X( k$ H: g% t& {4 H' `
- if((polar ^ data) & 0X01) //极性相反1 ^ N" d: O+ k3 ?& K; a
- {
f( V q' E4 g" \- U' D6 U& C - return 0;+ h! x: C8 }3 P; }6 Y% [6 k* T. R0 B
- }
7 b3 b! y2 g. M - else* [% c7 S, m7 q7 M" O& z5 O
- {: b' D9 E4 u' t) ?* l
- return 1;
! u- R7 o4 v8 n* j2 C. H' v - }1 f2 o/ t& e+ p
- }
复制代码 7 \6 e8 V* e+ W5 V/ ]3 B1 c
相应的,循环函数也做了一些修改,主要是在输出到LED端口的时候,用极性检测函数,先检测一下极性,再输出。 - /** @brief LED循环
7 M8 B" [ ^* i" R - * @param[in] 无
4 x4 u; s8 J. }, J0 t6 P - * @param[out] 无0 Q% K' r1 ^$ ]5 [" }' H
- * @retval 类型: x; k" T; J1 N" v
- * @note 10ms9 q. I4 ?% [' y* D) C2 \- ], t* A
- */0 D1 J5 c0 g# Y6 n |. C& k5 n* A
- void sLED_Loop(void)
* M- x8 W- q8 _- _/ ^7 H8 n# D2 J3 ?; k0 j. J - {% u+ N* V( y% m" q5 u& j
- static u32 s_Cnt;6 Q/ Y; [" Q5 M5 a9 E) a) V
- static bool Flash;1 |+ X# X6 M) s0 |# J. q+ A1 x
- static u32 ErrCnt;) c# x/ N0 G% v5 r# q; Y- i9 n
- * L5 J9 J. o1 h6 N
- s_Cnt = (s_Cnt +1)%(FLASH_FREQ * 1000);+ j' \5 S% N4 a. T; E( C# Q, e& f
- switch(s_LED.Type)
' R1 K( K7 M3 s - {6 y$ M* a# P+ l. i
- case 0 :5 c4 I1 X. G1 q6 {# j- S+ J' r
- LED = sLed_Polar(s_LED.PolarLED , s_LED.Enable); //亮LED( A' v/ A1 q0 l, [- f' _. t& L
- break;
2 d0 \+ c3 Z% Y! l% H - case 1:
4 q' E; T4 `9 }; O& a2 L& U% S - if(s_Cnt % FLASH_FREQ == 0) //500ms,闪烁一次
e. g$ q6 m! z9 y1 h' E - {0 x2 k( U% g' Z0 b$ o1 A& L0 G
- Flash = !Flash; //0灭,1:亮
, Z. g: W0 n: W1 O! _1 P - LED = sLed_Polar(s_LED.PolarLED , s_LED.Enable & Flash);//检查极性
8 _$ [( q* B* j& N2 ^ - } # _9 v! }4 v) r7 b4 f
- break;
5 V! }+ R4 ?* U" l' ?. C - case 2:
3 a) x4 C4 s7 y4 \7 j5 a1 i# i - if(s_Cnt % FLASH_FREQ == 0) //间隔500ms1 R3 D& I* a# M( n! b" I
- {
+ A3 X; a" B e; \ - Flash = !Flash; //翻转0 M" ]1 z% \- D& j# d+ Q, P( c
- if(Flash == 1): Q9 Z( z4 C0 J0 K
- ErrCnt++;
2 y- ?# r8 f8 Z L8 A0 D7 {& D - if(ErrCnt > s_LED.Err_num)
* B+ e) S6 [1 }+ \9 ?" a - {/ G! P, L9 i. M1 ^$ u
- ErrCnt++;) Q$ E5 u- y. D' j8 x( L
- Flash = 0;; x) K- }! ?3 d) J) o2 f
- if(ErrCnt > s_LED.Err_num + 2)//灭两个周期1 q5 ~* n+ k. m# B. c
- ErrCnt = 0;$ q- F) V; F; a- K
- }" t% d; {0 z$ X
- LED = sLed_Polar(s_LED.PolarLED , s_LED.Enable & Flash);//检查极性
' Y3 P) w* @# U4 `; E" Q, D - }0 e3 f! w4 t9 V, b9 Z* M
- break;
, K' ]. J; r- Q; X5 [ - default:
& x5 ]7 D" l! m# U* f - break; # u+ x/ |( H: N
- }
2 L! x9 [3 B# p" {- z - }
复制代码 7 I! \" P7 |9 v, p6 V# W% a% o' r
最后,就是昨天说的,设计接口函数,通过接口函数来设置、读取LED的参数。使程序更好理解,更好管理。 获取当前LED的类型 - /** @brief 获取当前LED的类型7 C2 r4 s. ~' P
- * @param[in] 无
* N% y) w! t1 K; h8 _) ]4 n9 ~; @ - * @param[out] 无( i3 d2 s* q/ _
- * @retval 类型
2 u% L3 P3 @* P7 O3 N - * @note 无
# m8 E' j2 z2 m2 F: f G - */
$ b8 L8 ~& ` X' ] - u8 sLED_ReadType(void)
4 \ C& X6 l6 D. U - {# P/ I* M. |8 }5 l$ K' n
- return s_LED.Type;. ]* `8 |+ K8 t
- }
复制代码
! r! i4 v# M4 |% u) w6 L5 q 设置LED的类型 - /** @brief 设置LDE的类型
6 J$ P( C9 i7 G$ T7 ]* j7 c - * @param[in] type : 类型
' K5 P3 i; E0 e# Q7 S c - * @param[out] 无, i! n# u5 U; g8 W4 h
- * @retval 1 : 设置成功
: \" A, ~, l4 M7 T3 F5 j - 0 : 设置失败( F& ?* U1 ~/ |% i) r& _
- * @note 无
$ O& b# ?4 @" U. i. X - */
6 F$ w6 s" Z7 t* l, K - u8 sLED_SetType(u8 type)
, p! Y6 V$ G- Y, N$ ~2 V) V - {
: G" W- Z0 `" x - if(type < LED_TYPE_NUM)
, |9 A+ Z7 l3 N% U - {+ I: o- ~+ j- V2 R( w, a' w; ?. h4 M; c
- s_LED.Type = type;
' k9 {# A H+ S. s% ^ - return 1;
3 m( P. f& `# e - }
. [- N1 V0 Y# g1 q$ G - else+ W8 [1 I0 i7 t( N
- return 0;5 @; o8 ^ F- X0 Z6 x
- }
复制代码 $ i* p$ r1 M1 W+ G
使能LED - /** @brief 使能LED* c" p: s- o! [
- * @param[in] Enable :使能
: f8 N& [& z) @4 t - * @param[out] 无- H9 u, `% p0 J" |# n
- * @retval 无
& D/ H6 h$ t+ O. U* b( Z0 R, J ~1 f - * @note 无
& X+ P N5 o7 \5 K! j5 y- }+ K$ X/ { - */
$ z) H$ I1 H+ I6 T+ F' G! N1 A - void sLED_Enable(u8 Enable)) _+ d& d/ [* e9 X0 G
- { \' a$ f9 j9 x$ x9 V! q4 _
- Enable = (Enable != 0);( E1 C. N5 w' ?4 r/ J
- s_LED.Enable = sLed_Polar(s_LED.PolarLED , Enable);
5 A0 }: X$ \" f! X& e( o; } - }
复制代码 2 T/ J1 S" C- n' T6 i. i
这样,我们只要将LED的头文件包换过去,就可以通过接口操作LED相应的参数了,这样是不是就比之前规范很多了,嘻嘻。 按照惯例,放一个测试视频。效果还是跟原来一样的。 如果大家想要工程文件的话,可以在公众号中找我要。 文章出处: Yue無缺 ( @' u8 J3 f) Y
|