|
今天来玩一下STM32U0的RTC,后续想用U0做一个电子墨水屏的日历,正好要用到RTC,今天就先来摸一摸RTC是怎么玩的 : ~ p, R. @. E/ L- V' _% z, o
工程还是使用之前的模板工程 ; M% o& ]% m Y7 z: @
一、cube配置 开启RTC,把时钟源和日历都激活
0 o: t4 I5 g; y8 U
下面配置的参数基本上可以保持默认。这里面主要会改的参数是
* L# S& w, o: U7 ` 其他参数保持默认即可 我这边年月日时分秒周几就偷个懒直接用默认的,待会儿我会尝试调用set函数改变其值,因为在实际使用时RTC都要用户自己去设置一下时间才正确 然后把时钟改一下,这个工程之前没有启动外部低速晶振,用的是内部RC产生的LSI,为了RTC更准一点,我要把外部32.768K晶振用起来。然后这边选择RTC Only的这个,因为我没有其他东西要用外部低速晶振,选这个可以在休眠时功耗更低
! r6 i' }" I N' A6 x5 }& d ; R9 W( o7 M& i8 M
+ H9 R# b, r' l6 [3 I% R) j* \, z
最后生成代码(截图略) 二、代码修改 先来写一个获取RTC信息并打印的函数 - void print_rtc_data()$ \( G$ p5 z0 ?$ e+ Y3 H
- {& P7 V2 y3 I9 z( G0 ?3 D( [
- RTC_DateTypeDef sdatestructureget;
, N- [7 Y' c2 n: l - RTC_TimeTypeDef stimestructureget;0 K3 F9 s/ J, o- R" U
- % F3 |, {$ E9 \+ q) ]
- HAL_RTC_GetTime(&hrtc, &stimestructureget, RTC_FORMAT_BIN);0 l- ^8 S4 C( `
- HAL_RTC_GetDate(&hrtc, &sdatestructureget, RTC_FORMAT_BIN);
0 q2 @# {0 T, `$ I" C* J6 F - printf("Date:%02d-%02d-%02d WeekDay:%02d Time:%02d:%02d:%02d \r\n",
f" _7 ^5 N, P3 t0 U: X - 2000 + sdatestructureget.Year,
2 _9 }* r1 [- ? - sdatestructureget.Month,
, [; d2 t" H# n7 K. i3 l - sdatestructureget.Date,7 g) H" t1 f, e
- sdatestructureget.WeekDay,/ O# p/ @. ^( N/ w8 `% A
- stimestructureget.Hours,
% x! K8 \' j2 i; k - stimestructureget.Minutes,/ F2 b+ h" i7 \2 N# l, O
- stimestructureget.Seconds
+ M3 v5 Q- z% [ - );; o! o$ H5 @! _
- }
复制代码
8 E/ y! [1 b" \: N
这边需要注意的是,HAL_RTC_GetTime和HAL_RTC_GetDate都要调用,不能只调用其中一个,如果只调用其中一个,那么后续再次调用get时间也不会更新,会一直获取到和第一次一样的数据 6 ?( U! N3 u; d& |: J2 P" \. e
把这个函数放到while1中,然后再加个delay,避免一直疯狂打印 - print_rtc_data();8 O- z1 Z' U! E1 {
- HAL_Delay(1000);+ q I' H" m' r4 G, g
复制代码
" p/ e. `; N# D! W% B T2 l
然后编译下载,效果如下
/ N0 R/ M l" E& ]
W5 c2 w' K/ o) L! j. d# Q! b
然后我们来试一下重新设置年月日、时分秒、周几参数 写一个设置的函数 - void set_rtc_data(). ^6 c, c+ w7 T' e
- {9 G% C+ g3 a+ O2 H# R) y, d
- RTC_TimeTypeDef sTime = {0};
4 h2 f% O" u$ E( W1 p - RTC_DateTypeDef sDate = {0};
2 \( P1 e w! S% K+ G8 a. T: t! h
, `$ ^. c, f# p
9 b$ P; [/ t' ]+ `) Y- sTime.Hours = 21; /* 21点 */
+ z' r( a; r/ ~' N - sTime.Minutes = 30; /* 30分 */% _. T# B1 f% m& k+ }& u/ U+ q
- sTime.Seconds = 10; /* 10秒 */( i( {0 w2 ~) r0 m
- sTime.DayLightSaving = RTC_DAYLIGHTSAVING_NONE; /* 和初始化时的值保持一致 */
$ N/ R0 d( c% P - sTime.StoreOperation = RTC_STOREOPERATION_RESET; /* 和初始化时的值保持一致 */( i) @( t6 R, W) B# B; t
- if (HAL_RTC_SetTime(&hrtc, &sTime, RTC_FORMAT_BCD) != HAL_OK), T2 b7 B- S* h0 n# G
- {) S4 [6 t& A; n$ a3 J5 G2 R
- Error_Handler();
' X+ d0 r* @1 ^8 `' k F5 F0 h8 ] - }
O3 N$ J2 |0 B/ R7 g4 x) Z - sDate.WeekDay = RTC_WEEKDAY_THURSDAY; /* 周四 */
1 Y Z& P/ B1 h3 E# q, } - sDate.Month = RTC_MONTH_MAY; /* 5月 */4 v% F& ?: o3 H# @7 n3 s0 m0 ]& k
- sDate.Date = 23; /* 23日 */& g7 l: j2 T: ^& ~! I# U
- sDate.Year = 24; /* 24年 */
& U4 }$ F& [8 `1 i) z
+ L( G# [, ?6 \" J% F- if (HAL_RTC_SetDate(&hrtc, &sDate, RTC_FORMAT_BCD) != HAL_OK)
; B E# B: r7 T/ R0 j - {: m3 F& h v1 @$ _( i- q# V s
- Error_Handler();* X3 f) o% c" M9 t
- }9 ]; |: M2 b3 f; \/ }
- }
复制代码
' F9 ?8 K3 h9 F$ N' C# K1 A 然后在while1中把它用一下,我上电后会让默认的RTC值连续打印10次,然后改变RTC的值,之后继续打印RTC的值 - uint8_t cnt = 0;
# M( H# h: Y, r7 e" F& }2 N - uint8_t flag = 0;0 [ j/ Q& e# X y: l4 m; u
复制代码
5 T* ~6 Q1 x% o - if (flag == 0)6 c0 ~/ [+ l4 H$ E
- {0 f# q' B& U% t9 N0 ~
- if (cnt == 10)
2 ]" t% _) @% X0 a* [+ Q; v9 W" t Q - {
; w8 X& v3 ~4 u# [& L* w9 P - set_rtc_data();
1 z7 D$ s) ^( t( M7 T1 D - flag = 1;6 k, l- l( `- H
- }
+ D# y% z$ N* A: E - else
3 v. G6 k2 p+ @$ e* \' ? - {
0 p% a, t9 U4 I6 @) i( m8 C4 p4 r - cnt++;+ j0 p2 n$ U4 f/ G) T X
- }8 O' f) R* I' ?2 E
- }
复制代码
9 h! w1 W9 w+ S/ n 然后下载,运行结果如图
5 Q ~6 n/ b& C+ `
( H9 X* v9 Q/ Y. {8 m |
感谢分享