STM32 Project Sharing: Eternal Calendar

Project Product Image:

STM32 Project Sharing: Eternal Calendar

Bilibili Video Link:

https://www.bilibili.com/video/BV1QD421g7kn/?share_source=copy_web&vd_source=097fdeaf6b6ecfed8a9ff7119c32faf2

(Resource sharing at the end of the article)

01

Project Introduction

1. Function Details

STM32 Eternal Calendar

Functions are as follows:

  1. Real-time clock display

  2. Time setting, power-off memory

  3. Alarm setting, buzzer alarm

  4. Temperature and humidity collection and display, abnormal alarm

2. Material List

  • STM32F103C8T6 Minimum System Board

  • DHT11 Temperature and Humidity Sensor

  • OLED Screen

  • DS1302 Clock Module

  • Active Buzzer

  • LED Light

02

Schematic Design

STM32 Project Sharing: Eternal Calendar

03

PCB Hardware Design

PCB Diagram

STM32 Project Sharing: Eternal CalendarSTM32 Project Sharing: Eternal Calendar

04

Program Design

int main(void) { delay_init(); // Delay function system initialization
 LED_GPIO_Config(); // Initialize GPIO interface
 KEY_Init(); // Key initialization
 BEEP_Init(); // Buzzer initialization
 GENERAL4_TIM_Init(); // 10ms General Timer 3 initialization 10ms
 NVIC_Configuration(); // Interrupt priority setting
 ds1302_gpio_init(); delay_ms(5); // Initialize ds1302 port
 ds1032_read_realTime(); // Read current time
 OLED_Init(); // Initialize OLED OLED_Clear(); // Clear screen delay_ms(100);
 DHT11_Init(); // Sensor initialization
 OLED_DrawBMP(0,0,128,8,BMP19); // Welcome page
 delay_ms(1000);
 OLED_Clear(); // Clear screen
 RealTime_Display_Init(); // Power-on initialization display real-time time
 while(1) { delay_ms(200); // Add delay to ensure detection stability
 ds1032_read_realTime(); // Read current time
 RealTime_Display(); // Real-time time and date refresh display

 if(DHT11_Data_Read_flag) // Read temperature and humidity data every 6 seconds { DHT11_Read_Data(&temperature, &humidity); // Read temperature and humidity values DHT11_Data_Read_flag=0; // Reset DHT11 data read flag }
 //************************ Alarm program segment ***********************************************// if(Alarm_Clock&&!Alarm_Manual_Stop_flag) { if((TimeData.hour==Alarm_Hour)&&(TimeData.minute==Alarm_Minute)) { Alarm_Clock_flag=1; // Alarm flag } else { Alarm_Clock_flag=0; // Alarm flag } } else { Alarm_Clock_flag=0; // Alarm flag }
 if(!KEY_DEC) // Stop key during alarm to reduce key { delay_ms(10);
 if(KEY_DEC==0) { while(!KEY_DEC);
 Alarm_Manual_Stop_flag=1;
 } }
 if(TimeData.minute!=Alarm_Minute) // Once the set value is inconsistent with the current time, manually terminate the alarm reset { Alarm_Manual_Stop_flag=0; }
 //************************** Key modification time and date program segment ***************************************// if(!KEY_ADJ) { delay_ms(10);
 if(KEY_ADJ==0) { while(!KEY_ADJ);
 OLED_Clear(); // Clear screen
 OLED_ShowChinese(0,0,21); // Year OLED_ShowChinese(68,0,22); // Month OLED_ShowChinese(0,3,23); // Day OLED_ShowChinese(68,3,24); // Hour OLED_ShowChinese(0,6,25); // Minute OLED_ShowChinese(68,6,26); // Week
 Show_Modify_Data(num); // Display default time and date setting parameters

 while(1) { OLED_ShowNum(20,0,y,2,16); OLED_ShowNum(88,0,m,2,16); OLED_ShowNum(20,3,d,2,16); OLED_ShowNum(88,3,h,2,16); OLED_ShowNum(20,6,mi,2,16); OLED_ShowNum(88,6,w,2,16);
 if(!KEY_ALM) { delay_ms(10); if(KEY_ALM==0) { while(!KEY_ALM); num++; if(num>5) num= 0; Show_Modify_Data(num); }
 }
 if(!KEY_ADD) { delay_ms(10); if(KEY_ADD ==0) { while(!KEY_ADD);
 switch(num) { case 0 : y++; break; case 1 : m++; break; case 2 : d++; break; case 3 : h++; break; case 4 : mi++; break; case 5 : w++; break; }
 if(y>59) y = 59; if(m>12) m=12; if(d>31) d=31; if(h>23) h=23; if(mi>59) mi=59; if(w>7) w=7; } }
 if(!KEY_DEC) { delay_ms(10); if(KEY_DEC==0) { while(!KEY_DEC); switch(num) { case 0 : y--; break; case 1 : m--; break; case 2 : d--; break; case 3 : h--; break; case 4 : mi--; break; case 5 : w--; break; }
 if(y<=1) y=1; if(m<1) m=1; if(d<1) d=1; if(h<1) h=1; if(mi<1) mi=1; if(w<1) w=1; } }
 if(!KEY_ADJ) { delay_ms(10); if(KEY_ADJ==0) { while(!KEY_ADJ);
 switch(y) // Set year { case 0 : time_buf[1]=0x00;break; case 1 : time_buf[1]=0x01;break; case 2 : time_buf[1]=0x02;break; case 3 : time_buf[1]=0x03;break; case 4 : time_buf[1]=0x04;break; case 5 : time_buf[1]=0x05;break; case 6 : time_buf[1]=0x06;break; case 7 : time_buf[1]=0x07;break; case 8 : time_buf[1]=0x08;break; case 9 : time_buf[1]=0x09;break; case 10 : time_buf[1]=0x10;break; case 11 : time_buf[1]=0x11;break; case 12 : time_buf[1]=0x12;break; case 13 : time_buf[1]=0x13;break; case 14 : time_buf[1]=0x14;break; case 15 : time_buf[1]=0x15;break; case 16 : time_buf[1]=0x16;break; case 17 : time_buf[1]=0x17;break; case 18 : time_buf[1]=0x18;break; case 19 : time_buf[1]=0x19;break; case 20 : time_buf[1]=0x20;break; case 21 : time_buf[1]=0x21;break; case 22 : time_buf[1]=0x22;break; case 23 : time_buf[1]=0x23;break; case 24 : time_buf[1]=0x24;break; case 25 : time_buf[1]=0x25;break; case 26 : time_buf[1]=0x26;break; case 27 : time_buf[1]=0x27;break; case 28 : time_buf[1]=0x28;break; case 29 : time_buf[1]=0x29;break; case 30 : time_buf[1]=0x30;break; case 31 : time_buf[1]=0x31;break; case 32 : time_buf[1]=0x32;break; case 33 : time_buf[1]=0x33;break; case 34 : time_buf[1]=0x34;break; case 35 : time_buf[1]=0x35;break; case 36 : time_buf[1]=0x36;break; case 37 : time_buf[1]=0x37;break; case 38 : time_buf[1]=0x38;break; case 39 : time_buf[1]=0x39;break; case 40 : time_buf[1]=0x40;break; case 41 : time_buf[1]=0x41;break; case 42 : time_buf[1]=0x42;break; case 43 : time_buf[1]=0x43;break; case 44 : time_buf[1]=0x44;break; case 45 : time_buf[1]=0x45;break; case 46 : time_buf[1]=0x46;break; case 47 : time_buf[1]=0x47;break; case 48 : time_buf[1]=0x48;break; case 49 : time_buf[1]=0x49;break; case 50 : time_buf[1]=0x50;break; case 51 : time_buf[1]=0x51;break; case 52 : time_buf[1]=0x52;break; case 53 : time_buf[1]=0x53;break; case 54 : time_buf[1]=0x54;break; case 55 : time_buf[1]=0x55;break; case 56 : time_buf[1]=0x56;break; case 57 : time_buf[1]=0x57;break; case 58 : time_buf[1]=0x58;break; case 59 : time_buf[1]=0x59;break;
 default : time_buf[5]=0x01; }
 switch(m) // Set month { case 1 : time_buf[2]=0x01;break; case 2 : time_buf[2]=0x02;break; case 3 : time_buf[2]=0x03;break; case 4 : time_buf[2]=0x04;break; case 5 : time_buf[2]=0x05;break; case 6 : time_buf[2]=0x06;break; case 7 : time_buf[2]=0x07;break; case 8 : time_buf[2]=0x08;break; case 9 : time_buf[2]=0x09;break; case 10 : time_buf[2]=0x10;break; case 11 : time_buf[2]=0x11;break; case 12 : time_buf[2]=0x12;break; default : time_buf[2]=0x01; }
 switch(d) // Set day { case 1 : time_buf[3]=0x01;break; case 2 : time_buf[3]=0x02;break; case 3 : time_buf[3]=0x03;break; case 4 : time_buf[3]=0x04;break; case 5 : time_buf[3]=0x05;break; case 6 : time_buf[3]=0x06;break; case 7 : time_buf[3]=0x07;break; case 8 : time_buf[3]=0x08;break; case 9 : time_buf[3]=0x09;break; case 10 : time_buf[3]=0x10;break; case 11 : time_buf[3]=0x11;break; case 12 : time_buf[3]=0x12;break; case 13 : time_buf[3]=0x13;break; case 14 : time_buf[3]=0x14;break; case 15 : time_buf[3]=0x15;break; case 16 : time_buf[3]=0x16;break; case 17 : time_buf[3]=0x17;break; case 18 : time_buf[3]=0x18;break; case 19 : time_buf[3]=0x19;break; case 20 : time_buf[3]=0x20;break; case 21 : time_buf[3]=0x21;break; case 22 : time_buf[3]=0x22;break; case 23 : time_buf[3]=0x23;break; case 24 : time_buf[3]=0x24;break; case 25 : time_buf[3]=0x25;break; case 26 : time_buf[3]=0x26;break; case 27 : time_buf[3]=0x27;break; case 28 : time_buf[3]=0x28;break; case 29 : time_buf[3]=0x29;break; case 30 : time_buf[3]=0x30;break; case 31 : time_buf[3]=0x31;break; default : time_buf[3]=0x01; }
 switch(h) // Set hour { case 0 : time_buf[4]=0x00;break; case 1 : time_buf[4]=0x01;break; case 2 : time_buf[4]=0x02;break; case 3 : time_buf[4]=0x03;break; case 4 : time_buf[4]=0x04;break; case 5 : time_buf[4]=0x05;break; case 6 : time_buf[4]=0x06;break; case 7 : time_buf[4]=0x07;break; case 8 : time_buf[4]=0x08;break; case 9 : time_buf[4]=0x09;break; case 10 : time_buf[4]=0x10;break; case 11 : time_buf[4]=0x11;break; case 12 : time_buf[4]=0x12;break; case 13 : time_buf[4]=0x13;break; case 14 : time_buf[4]=0x14;break; case 15 : time_buf[4]=0x15;break; case 16 : time_buf[4]=0x16;break; case 17 : time_buf[4]=0x17;break; case 18 : time_buf[4]=0x18;break; case 19 : time_buf[4]=0x19;break; case 20 : time_buf[4]=0x20;break; case 21 : time_buf[4]=0x21;break; case 22 : time_buf[4]=0x22;break; case 23 : time_buf[4]=0x23;break;
 default : time_buf[4]=0x01; }
 switch(mi) // Set minute { case 0 : time_buf[5]=0x00;break; case 1 : time_buf[5]=0x01;break; case 2 : time_buf[5]=0x02;break; case 3 : time_buf[5]=0x03;break; case 4 : time_buf[5]=0x04;break; case 5 : time_buf[5]=0x05;break; case 6 : time_buf[5]=0x06;break; case 7 : time_buf[5]=0x07;break; case 8 : time_buf[5]=0x08;break; case 9 : time_buf[5]=0x09;break; case 10 : time_buf[5]=0x10;break; case 11 : time_buf[5]=0x11;break; case 12 : time_buf[5]=0x12;break; case 13 : time_buf[5]=0x13;break; case 14 : time_buf[5]=0x14;break; case 15 : time_buf[5]=0x15;break; case 16 : time_buf[5]=0x16;break; case 17 : time_buf[5]=0x17;break; case 18 : time_buf[5]=0x18;break; case 19 : time_buf[5]=0x19;break; case 20 : time_buf[5]=0x20;break; case 21 : time_buf[5]=0x21;break; case 22 : time_buf[5]=0x22;break; case 23 : time_buf[5]=0x23;break; case 24 : time_buf[5]=0x24;break; case 25 : time_buf[5]=0x25;break; case 26 : time_buf[5]=0x26;break; case 27 : time_buf[5]=0x27;break; case 28 : time_buf[5]=0x28;break; case 29 : time_buf[5]=0x29;break; case 30 : time_buf[5]=0x30;break; case 31 : time_buf[5]=0x31;break; case 32 : time_buf[5]=0x32;break; case 33 : time_buf[5]=0x33;break; case 34 : time_buf[5]=0x34;break; case 35 : time_buf[5]=0x35;break; case 36 : time_buf[5]=0x36;break; case 37 : time_buf[5]=0x37;break; case 38 : time_buf[5]=0x38;break; case 39 : time_buf[5]=0x39;break; case 40 : time_buf[5]=0x40;break; case 41 : time_buf[5]=0x41;break; case 42 : time_buf[5]=0x42;break; case 43 : time_buf[5]=0x43;break; case 44 : time_buf[5]=0x44;break; case 45 : time_buf[5]=0x45;break; case 46 : time_buf[5]=0x46;break; case 47 : time_buf[5]=0x47;break; case 48 : time_buf[5]=0x48;break; case 49 : time_buf[5]=0x49;break; case 50 : time_buf[5]=0x50;break; case 51 : time_buf[5]=0x51;break; case 52 : time_buf[5]=0x52;break; case 53 : time_buf[5]=0x53;break; case 54 : time_buf[5]=0x54;break; case 55 : time_buf[5]=0x55;break; case 56 : time_buf[5]=0x56;break; case 57 : time_buf[5]=0x57;break; case 58 : time_buf[5]=0x58;break; case 59 : time_buf[5]=0x59;break;
 default : time_buf[5]=0x01; }
 switch(w) // Set week { case 1 : time_buf[6]=0x01;break; case 2 : time_buf[6]=0x02;break; case 3 : time_buf[6]=0x03;break; case 4 : time_buf[6]=0x04;break; case 5 : time_buf[6]=0x05;break; case 6 : time_buf[6]=0x06;break; case 7 : time_buf[6]=0x07;break;
 default : time_buf[6]=0x01; }
 ds1302_write_time(); // Modify time, write in
 OLED_Clear(); // Clear screen
 ds1032_read_realTime(); // Read current time
 Modify_RealTime_Display(); // Refresh display after modification
 break;
 }
 }
 }
 //****************************** Modify alarm time and alarm setting program segment *******************************// if(!KEY_ALM) { delay_ms(10); if(KEY_ALM==0) { while(!KEY_ALM);
 OLED_Clear(); // Clear screen
 OLED_ShowChinese(32,0,27); // Alarm setting OLED_ShowChinese(48,0,28); OLED_ShowChinese(64,0,29); OLED_ShowChinese(80,0,30);
 OLED_ShowChar(60,3,':',16);
 Show_Modify_Alarm(num2); // Display modify alarm information

 while(1) { OLED_ShowNum(44,3,Alarm_Hour,2,16);
 OLED_ShowNum(68,3,Alarm_Minute,2,16);
 if(Alarm_Clock) // Alarm switch display { OLED_ShowChinese(104,3,31); } else { OLED_ShowChinese(104,3,32); }
 if(Alarm_Minute<10) // Prevent displaying single digit, not neat { OLED_ShowChar(68,3,'0',16); // 0 padding } if(!KEY_ADJ) { delay_ms(10); if(KEY_ADJ==0) { while(!KEY_ADJ); num2++; if(num2>2) num2= 0; Show_Modify_Alarm(num2); }
 }
 if(!KEY_ADD) { delay_ms(10); if(KEY_ADD==0) { while(!KEY_ADD);
 switch(num2) { case 0 : Alarm_Hour++; break; case 1 : Alarm_Minute++; break; case 2 : Alarm_Clock++; break; }
 if(Alarm_Hour>23) Alarm_Hour= 23; if(Alarm_Minute>59) Alarm_Minute=59; if(Alarm_Clock>=1) Alarm_Clock=1; } }
 if(!KEY_DEC) { delay_ms(10); if(KEY_DEC==0) { while(!KEY_DEC); switch(num2) { case 0 : Alarm_Hour--; break; case 1 : Alarm_Minute--; break; case 2 : Alarm_Clock--; break; }
 if(Alarm_Hour<=0) Alarm_Hour=0; if(Alarm_Minute<=0) Alarm_Minute=0; if(Alarm_Clock<=0) Alarm_Clock=0;
 } }
 if(!KEY_ALM) { delay_ms(10); if(KEY_ALM==0) { while(!KEY_ALM);
 OLED_Clear();
 ds1032_read_realTime(); // Read current time
 Modify_RealTime_Display(); // Refresh display after modification
 break; } }
 }
 }
 //**************************** Main program running indicator program segment **************************************// if(Run_Indicate_num>=50) // Flashing indicates that the main program is running { RUN_Indicate_ENABLE; // Indicator light on } else { RUN_Indicate_UNABLE; // Indicator light off }
 }
}

Leave a Comment