[STM32F4] 【Nucleo设计分享】基于stm32f411re的智能手表(调时功能)

[复制链接]
zhanghuichun 发表于 2015-3-2 16:48 | 显示全部楼层 |阅读模式
讲了那么久终于讲到调时功能,我也觉得怪怪的,作为一个手表应该首先介绍其身为手表的功能……   哎,新手,,,,没想太多

stm32f4的固件库对RTC优化了很多,接下来我们就详细讲讲,到底优化多少了!

  1. static void RTC_delay_ms(u16 time)
  2. {
  3.         u16 i=0;
  4.         while(time--)
  5.         {
  6.                 i=16666;
  7.                 while(i--);
  8.         }
  9. }
  10. //RTC时间设置
  11. //hour,min,sec:小时,分钟,秒钟
  12. //ampm:@RTC_AM_PM_Definitions  :RTC_H12_AM/RTC_H12_PM
  13. //返回值:SUCEE(1),成功
  14. //       ERROR(0),进入初始化模式失败
  15. ErrorStatus RTC_Set_Time(u8 hour,u8 min,u8 sec)
  16. {
  17.         RTC_TimeTypeDef         RTC_TimeTypeInitStructure;
  18.         RTC_TimeTypeInitStructure.RTC_Hours=hour;
  19.         RTC_TimeTypeInitStructure.RTC_Minutes=min;
  20.         RTC_TimeTypeInitStructure.RTC_Seconds=sec;
  21.        
  22.         return RTC_SetTime(RTC_Format_BIN,&RTC_TimeTypeInitStructure);
  23. }
  24. //RTC日期设置
  25. //year,month,date:年(0~99),月(1~12),日(0~31)
  26. //week:星期(1~7,0,非法!)
  27. //返回值:SUCEE(1),成功
  28. //       ERROR(0),进入初始化模式失败
  29. ErrorStatus RTC_Set_Date(u8 year,u8 month,u8 date,u8 week)
  30. {
  31.        
  32.         RTC_DateTypeDef RTC_DateTypeInitStructure;
  33.         RTC_DateTypeInitStructure.RTC_Date=date;
  34.         RTC_DateTypeInitStructure.RTC_Month=month;
  35.         RTC_DateTypeInitStructure.RTC_WeekDay=week;
  36.         RTC_DateTypeInitStructure.RTC_Year=year;
  37.         return RTC_SetDate(RTC_Format_BIN,&RTC_DateTypeInitStructure);
  38. }
  39. u8 RTC_init(void)
  40. {
  41.         RTC_InitTypeDef RTC_InitStructure;
  42.         u16 retry=0x1FFF;
  43.         RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR,ENABLE);
  44.         PWR_BackupAccessCmd(ENABLE);
  45.         if(RTC_ReadBackupRegister(RTC_BKP_DR0)!=0x5040)
  46.         {
  47.                 RCC_LSEConfig(RCC_LSE_ON);
  48.                 while(RCC_GetFlagStatus(RCC_FLAG_LSERDY)==RESET)
  49.                 {
  50.                         retry++;
  51.                 RTC_delay_ms(10);
  52.                 }
  53.                 if(retry==0)return 1;
  54.                 RCC_RTCCLKConfig(RCC_RTCCLKSource_LSE);
  55.                 RCC_RTCCLKCmd(ENABLE);
  56.                
  57.                 RTC_InitStructure.RTC_AsynchPrediv=0x7f;
  58.                 RTC_InitStructure.RTC_SynchPrediv=0xff;
  59.                 RTC_InitStructure.RTC_HourFormat=RTC_HourFormat_24;
  60.                 RTC_Init(&RTC_InitStructure);
  61.                
  62.                 RTC_Set_Time(9,46,10);        //设置时间
  63.                 RTC_Set_Date(15,3,2,1);                //设置日期
  64.                 RTC_WriteBackupRegister(RTC_BKP_DR0,0x5040);        //标记已经初始化过了
  65.         }
  66.         return 0;
  67. }
没错,不用70行代码就能对时间日期的修改,打开以前stm32f1系列的代码,粗略计算了一下,要700行,大大减少工程的代码量和我们的工作量。
打开电源管理时钟,使能后备寄存器,判断后备寄存器的值(防止多次配置),如果数据对不上,就对RTC重新初始化,配置LSE时钟并等待时钟稳定,配置RTC的结构体,再设置时间。
在这里利用SysTick定时器对时间进行刷新
  1. void SysTick_Handler(void)
  2. {
  3.         static uint8_t count_time=0;
  4.         static uint32_t rtc_time=0;
  5. //        TimingDelay_Decrement();
  6.         OS_TimeMS ++;
  7.         count_time++;
  8.         rtc_time++;
  9.         if(count_time == 10)
  10.         {
  11.         GUI_TOUCH_Exec();                        //每10ms调用一次,触发调用触摸驱动
  12.         count_time =0;
  13.         }
  14.         if(rtc_time == 2000)
  15.         {
  16.                 if(WM_IsWindow(WinPara.hWinMain))//判断当前激活的窗口
  17.                 WM_SendMessageNoPara(WinPara.hWinMain,MY_MESSAGE_RTC);
  18.                 if(WM_IsWindow(WinPara.hBkWheel))//判断当前激活的窗口
  19.                 WM_SendMessageNoPara(WinPara.hBkWheel,MY_MESSAGE_RTC);
  20.                 rtc_time=0;
  21.                
  22.                 LED_TOGGLE;
  23.         }
  24. }
分别对两个窗口进行时间刷新,分别为时间调节窗口和主窗口,在这里必须对当前窗口进行判断,否则图形界面可能会卡死。
P50302-135233.jpg

如图为调节时间的主界面,采用的是LISTWHEEL控件进行时间选择,选择好时间后点击ok后即可对时间的调节。

大家可以发现,这里没有对星期的调节,别怕我找了条公式,传说中的蔡勒(Zeller)公式



w=y+[y/4]+[c/4]-2c+[26(m+1)/10]+d-1

  1. if(RTC_DateStruct.RTC_Month==1||RTC_DateStruct.RTC_Month==2)
  2.                                                                                                         {
  3.                                                                                                         m=RTC_DateStruct.RTC_Month+12;
  4.                                                                                                         y=RTC_DateStruct.RTC_Year-1;
  5.                                                                                                         }
  6.                                                                                                         else
  7.                                                                                                         {
  8.                                                                                                         m=RTC_DateStruct.RTC_Month;
  9.                                                                                                         y=RTC_DateStruct.RTC_Year;
  10.                                                                                                         }
  11.                                                                                                        
  12.                                                                                                         RTC_DateStruct.RTC_WeekDay=(y+y/4+26*(m+1)/10+RTC_DateStruct.RTC_Date-36)%7;
  13.                                                                                                        
  14.                                                                                                         if(RTC_DateStruct.RTC_WeekDay==0)RTC_DateStruct.RTC_WeekDay=7;
  15.                                                                                        
  16.                                                                                                 RTC_Set_Date(RTC_DateStruct.RTC_Year,RTC_DateStruct.RTC_Month,RTC_DateStruct.RTC_Date,RTC_DateStruct.RTC_WeekDay);
  17.                                                                                                 RTC_Set_Time(RTC_TimeStruct.RTC_Hours,RTC_TimeStruct.RTC_Minutes,RTC_TimeStruct.RTC_Seconds);
以上就是求星期的源码,有需要的就拿去呗

------------------------------------------------------------------------温柔华丽的分割线--------------------------------------------------------------------



dirtwillfly 发表于 2015-3-2 20:25 | 显示全部楼层
mmuuss586 发表于 2015-3-2 20:26 | 显示全部楼层
不错,支持楼主;
wt.liu 发表于 2015-3-2 22:59 | 显示全部楼层
有硬件原理图吗?学学
xjjspace 发表于 2015-3-3 11:08 | 显示全部楼层
wt.liu 发表于 2015-3-2 22:59
有硬件原理图吗?学学

楼主发的系列贴里有,你进他空间看看
nyszx 发表于 2015-3-3 12:39 | 显示全部楼层
很强大,支持楼主!
 楼主| zhanghuichun 发表于 2015-3-3 13:05 | 显示全部楼层
wt.liu 发表于 2015-3-2 22:59
有硬件原理图吗?学学

硬件设计介绍在这个帖子https://bbs.21ic.com/icview-884047-1-1.html  帖子只有PDF版的原理图   如需PCB和原理图原件,可以联系我,我给你发:handshake
ljl342301 发表于 2015-5-6 11:34 | 显示全部楼层
你好,大神,我看了你的智能手表设计,有几个问题想要问你。
第一个是你在帖子里说你的rtc晶振焊错了,我看原理图没错,是你自己焊接的时候焊错了是吗。
第二个问题我看你PCB可以分成左右两部分,你是不是最后把这个PCB掰断了啊,然后两个叠起来,要不体积不对啊,最后面白色的那个是不是电池呢?
最后不知道你能不能把你的原理图和PCB源文件给我发一份呢,我想在你这个设计的基础上设计一款工控仪表作为我的研究生毕设课题,我的邮箱是525309500@qq.com,以后可能还要和你交流,谢谢了
luy3728000 发表于 2015-5-8 16:03 | 显示全部楼层
不错。!
zh113214 发表于 2015-5-9 08:17 | 显示全部楼层
支持楼主,顶!!!
您需要登录后才可以回帖 登录 | 注册

本版积分规则

20

主题

101

帖子

9

粉丝
快速回复 在线客服 返回列表 返回顶部