在STM32G431内部配置有RTC计时器,将它与OLED屏配合即可实现一个电子时钟。 " I0 j) `7 q' y# _
实现图1所示效果的主程序为: - int main(void)' O0 H2 _; v% ?7 l
- {1 t, R, o% s2 R- }) ?
- /* Reset of all peripherals, Initializes the Flash interface and the Systick. */! F. N& T: C: {. y+ m; C
- HAL_Init();
" U: r& e- e, L% z* m - /* Configure the system clock */
; f' p( R/ X x3 v5 o* g - SystemClock_Config();
* a8 F0 W' c4 s - GPIO_OLED_INIT();3 h. Z& L& V' Z+ D2 O9 I
- OLED_Init();/ ^: \6 n# B" _2 }
- OLED_Clear();
7 v, _9 o1 M( ~6 O3 g: I e4 Q5 u) C6 L - OLED_ShowString(18,0,"STM32G431",16);
9 P+ [4 h4 w: H0 S t! `4 K - OLED_ShowString(10,2,"OLED & RTC",16);
3 ~' t& ^0 q( U V) D+ R - /* Initialize all configured peripherals */
) J+ D' S/ m: z; v: Z+ o# j - MX_RTC_Init();% c* j7 ^& ?; x: U- L% W
- RTCStatus = 1;
; u0 k+ c" ?0 Z, }. v - while (1)$ R/ }# I# }, V; I6 l+ N% M
- {
+ Q6 J5 b9 d6 A: B/ N" h) F - /* Display the updated Time and Date */5 a n4 m% R2 H! j% d
- RTC_CalendarShow(aShowTime, aShowDate);
; Y$ A! q3 `' b# y& u - Delay(200);5 Z( j5 o; w+ V
- }0 b9 k# ?; P3 w! T- N
- }
复制代码 图1 RTC电子时钟 * T; a/ N0 a3 n' Y
实现RTC显示的函数为: - static void RTC_CalendarShow(uint8_t *showtime, uint8_t *showdate)
. N3 d" J. ~0 Q( K/ W - {
A8 s, B$ i, e9 w. i9 m: e+ B - RTC_DateTypeDef sdatestructureget;
6 R4 m, H# u: D, s ]5 ~ - RTC_TimeTypeDef stimestructureget; A% u, t! s! ~. u8 T) x; u
- /* Get the RTC current Time */* A8 d( F: i- [0 Q$ i+ s; ~/ x( Q
- HAL_RTC_GetTime(&hrtc, &stimestructureget, RTC_FORMAT_BIN);
8 n7 O6 G) m i$ \6 k/ G2 y- K1 ^ - /* Get the RTC current Date */
7 Q; R- ?/ e- \ - HAL_RTC_GetDate(&hrtc, &sdatestructureget, RTC_FORMAT_BIN);
; h0 C" E0 u. c0 y& O( L, e - /* Display time Format : hh:mm:ss */. C- d/ _! L/ j# y2 V1 d7 E
- sprintf((char *)showtime, "%2d:%2d:%2d", stimestructureget.Hours, stimestructureget.Minutes, stimestructureget.Seconds);8 \2 ]- ^0 o! J4 G, |
- OLED_ShowString(26,6,showtime,16);. m9 u+ f* N- A5 V
- /* Display date Format : mm-dd-yy */( ?- d3 U+ Z3 @, x8 U% S( `( ^
- sprintf((char *)showdate, "%2d-%2d-%2d", 2000 + sdatestructureget.Year,sdatestructureget.Month, sdatestructureget.Date);
# ]! I+ i8 } l+ f* V - OLED_ShowString(10,4,showdate,16);
: T4 r Y/ D$ P, { - }
复制代码 - P* B2 b G- |, S- J: \* P( u
调用的字符串显示函数为: - void OLED_ShowString(u8 x,u8 y,u8 *chr,u8 Char_Size). W( ~% r( Z8 k2 G
- {
+ Z+ G1 F) j7 n3 u- z - unsigned char j=0;
Q& F* w8 w0 s4 _ - while (chr[j]!='\0'): d$ ], s. M) c- R" i7 H
- { OLED_ShowChar(x,y,chr[j],Char_Size);
2 S Z* u; `6 b/ R, A5 ? - x+=8;
; c2 f6 F* i0 \% r1 P) p - if(x>120){x=0;y+=2;}3 k7 ?8 L; d P' g* d
- j++;
0 I9 F, v/ {8 h7 f - }$ z, L( r3 o3 F: z Z7 H/ q9 v: W
- }
复制代码 2 ~' v2 ~" I( G
由于例程所设置的初始时间是2018年,故需要在函数 MX_RTC_Init()中进行修改,修改后的运行效果如图2所示。 - D) _9 g5 U d* M9 m! e
图2 校时后的显示效果
2 n% H; z i' c4 B# d% g% p& B |
有空我也玩玩。
计时尚可,长时间的误差可能会明显点儿。
就是11月31日会不会自动进入12月1日,还有闰年修正等。& y _5 F$ S+ J( \' W5 L
我给你测了下,两者都没有问题。