基于“梁山派”开发的智能窗帘可控制系统 - 嘉立创EDA开源硬件平台

编辑器版本 ×
标准版 Standard

1、简单易用,可快速上手

2、流畅支持300个器件或1000个焊盘以下的设计规模

3、支持简单的电路仿真

4、面向学生、老师、创客

专业版 professional

1、全新的交互和界面

2、流畅支持超过3w器件或10w焊盘的设计规模,支持面板和外壳设计

3、更严谨的设计约束,更规范的流程

4、面向企业、更专业的用户

专业版 基于“梁山派”开发的智能窗帘可控制系统

简介:基于梁山派开发板制作的智能窗帘控制

开源协议: LGPL 3.0

(未经作者授权,禁止转载)

已参加:立创·开发板电子设计训练营

创建时间: 2023-08-17 17:29:42
更新时间: 2023-10-08 22:41:30
描述
## 题目要求 技术要求 (1)雨滴传感器模块:用于检测雨滴; (2)光线强度传感器模块:用于检测光线强度; (3)红外接收模块和蓝牙模块,用于遥控控制; (4)步进电机模块:用于窗户窗帘驱动。 技术指标 (1)可以通过红外遥控与语音设置是否打开自动模式; (2)在自动模式下,当光照强度超过设定阈值时,自动展开窗帘;当光照强度低于设定阈值时,自动关闭窗帘; (3)在自动模式下,当检测到大量雨滴值超过设定阈值时,自动展开窗帘,此优先级比光照检测高; (4)可以通过板载的旋转编码器调节各参数阈值的大小,并在板载OLED屏幕上显示,若设定参数时为自动模式,则关闭自动模式 (5)主控芯片接收到数据后,驱动电机运转,现实智能窗帘窗户系统。 (6)可以通过板载的编码器调节自动或手动模式 ## 原理图设计说明 ### 主控电路 ![主控电路.png](//image.lceda.cn/pullimage/dv2bOW3XepSthDOWv97bdi2T3Z4fjGXRSdnIhpKb.png) ### 光线传感器 ![光线传感器.png](//image.lceda.cn/pullimage/UBZAdHvVT2OQNveyRHMmXgsbWiGCBB5LWAnvSKu7.png) ![光线传感器模块实物图.png](//image.lceda.cn/pullimage/AXOgypgnwCBCAIxxGNmByCgAUB4o6uGfPGLIPZCi.png) ![光敏电阻商城图片.png](//image.lceda.cn/pullimage/CjYZ2EGDOaTLFcfOEKBtQ7mRTTz0FFS57xIEiiG1.png) ### 雨滴传感器 ![雨滴传感器.png](//image.lceda.cn/pullimage/zmaujCrf1xCgikOUaU1Q7d1mfuwHtMTzqtFemSUi.png) ![雨滴传感器实物图.png](//image.lceda.cn/pullimage/HTMaOB7KcJK5GQPUm4FIfqHLYQpWDVNcG2W0Khf4.png) ![雨滴传感器商家.png](//image.lceda.cn/pullimage/M46bPM8k10WRZsFR1ydRMn6I1jNIoNMnyM14pTc8.png) ### 红外检测模块 ![红外模块.png](//image.lceda.cn/pullimage/vVY9gN326QfEviddEOmMFlkIpRufueGfQRFiIaPQ.png) ![红外模块实物图.png](//image.lceda.cn/pullimage/lJKJhDPBYVgXRBRNqauH873nS5tc7eomkJx8rWRp.png) ![红外接收头商城.png](//image.lceda.cn/pullimage/jdloYdqWLrIOS1BQmWFND5H8xQfK0rJmnR7KR8FK.png) ### 语音识别模块 ![语音识别模块.png](//image.lceda.cn/pullimage/1zTUEdYBJ91d9pOZaXmLi0ubVd032bS93fV28eyB.png) ![语音识别模块实物.png](//image.lceda.cn/pullimage/myNYTHXXHYaNJGa02Vdm2VvcrtTcPBE3xRmheLeW.png) ![语音识别模块商城.png](//image.lceda.cn/pullimage/hCw6BqWRGvSSHZSOvB2VatQx8LHPm0TDr9kLFDNA.png) ### 板载调试模块 ![编码器电路.png](//image.lceda.cn/pullimage/9jgqHa8QCJPz49KsTPHK45sFbxaupiPf0TdPt72F.png) 旋转编码器 ![OLED屏幕.png](//image.lceda.cn/pullimage/Zv9pQstQPGpMXgr4UFWj1stqxS8m06rLxvH0Pbfu.png) OLED显示屏 ![板载调试模块实物.png](//image.lceda.cn/pullimage/g5FfvtnrW4E6QDs56jxISwSoCTI0aK6bfyS3gEkE.png) ### 板载指示灯模块 ![指示灯电路.png](//image.lceda.cn/pullimage/U20LnED5ZJzB5UjmThI4Fs4Ack1D6ZjfplPRucFk.png) ![指示灯实物.png](//image.lceda.cn/pullimage/UyQumKtHeUtWoSsE0hbLT6pvROn32lHinFa6gYiJ.png) ## PCB设计 ![PCB_LAYOUT.png](//image.lceda.cn/pullimage/rLrhBKDQzCbFFpjXtXgFcc0AaJXaNpQcHjkeFcff.png) ![彩色丝印.png](//image.lceda.cn/pullimage/KUUX5A1zQ8zi9aHWZHJuj1yr9VIYDIFjA9UyL89Q.png) ![PCB正面.jpg](//image.lceda.cn/pullimage/GXtxlZ5nFR7MMCM5UIkQlYqDI8r44Wf9KsF8Ya9Q.jpeg) ![PCB背面.jpg](//image.lceda.cn/pullimage/2IySxqFYbbRn73WyT3YXAeWX9rHAIWjnONGwsUZx.jpeg) ## 软件说明 #### 主程序 ``` #include "gd32f4xx.h" #include "systick.h" #include <stdio.h> #include "ec11.h" #include "oled.h" #include "light_adc.h" #include <djcd.h> #include "step_moter.h" #include "mode_change.h" #include "bsp_voice.h" #include "bsp_ir_receiver.h" int main(void) { int nemu_num = 0; //页面切换参数 systick_config(); //滴答定时器初始话 OLED_Init(); //OLED屏幕初始化 EC11_Config(); //旋转编码器配置 ld_adc_config(); //雨滴传感器、光线传感器配置 led_gpio_config(); //指示灯初配置 stepper_motor_config(); //步进电机配置 OLED_Clear(); //OLED清屏 curtain_reset(); //窗帘初始化 mode_change_config(); //模式转换初始化 infrared_goio_config(); //红外引脚配置 hlk_usart_init(9600); //语音识别串口配置 voice_timer_config(); //语音识别定时器设置 timer_IR_config(); //红外检测定时器设置 while(1) { if (nemu_num == 0) nemu_num = nemu_main(); if (nemu_num == 1) nemu_num = nemu1(); if (nemu_num == 2) nemu_num = nemu2(); if (nemu_num == 3) nemu_num = nemu3(); if (nemu_num == 4) nemu_num = nemu4(); if (nemu_num == 5) nemu_num = nemu6(); } } ``` #### 多级菜单 ``` #include "djcd.h" #include "bsp_voice.h" #include "step_moter.h" int nemu_main(void) { int nemu_num = 1; OLED_Clear(); OLED_ShowString(35,0,"Welcome",16,1);//6*8 “ABC” OLED_ShowString(15,16,"Set numerical",16,1);//12*24 “ABC” OLED_ShowString(15,32,"Show numerical",16,1);//12*24 “ABC” OLED_ShowString(15,48,"Mode Change",16,1);//12*24 “ABC” OLED_Refresh(); while(1) { nemu_num = turn_state; if (nemu_num < 0) { turn_state = 17; } else if (nemu_num >= 1 && nemu_num < 9) { nemu_num = 1; } else if (nemu_num >= 9 && nemu_num <17) { nemu_num = 2; } else if (nemu_num >= 17 && nemu_num < 19) { nemu_num = 3; } else if (nemu_num >= 19) { turn_state = 1; } switch(nemu_num) { case 1: OLED_ShowString(0,16,"*",16,1); OLED_ShowString(0,32," ",16,1); OLED_ShowString(0,48," ",16,1); OLED_Refresh(); break; case 2: OLED_ShowString(0,16," ",16,1); OLED_ShowString(0,32,"*",16,1); OLED_ShowString(0,48," ",16,1); OLED_Refresh(); break; case 3: OLED_ShowString(0,16," ",16,1); OLED_ShowString(0,32," ",16,1); OLED_ShowString(0,48,"*",16,1); OLED_Refresh(); break; } motor_stop(); if (KEY_state != 0) { KEY_state = 0; return nemu_num; } } } int nemu1(void) { unsigned char auto_mode_report[5] = { 0XAA, 0X55, 0X01, 0X55, 0XAA }; //播报【当前为手动模式】语音 unsigned char manual_mode_report[5] = { 0XAA, 0X55, 0X02, 0X55, 0XAA }; int nemu_num = 1; int temp = 1; OLED_Clear(); OLED_ShowString(15,0,"Set numerical",16,1); OLED_ShowString(0,16,"light num",16,1); OLED_ShowString(0,32,"wet num",16,1); OLED_ShowString(0,48,"Turn Back",16,1); OLED_Refresh(); KEY_state = 0; while(1) { OLED_ShowNum(80,16,light_taget,4,16,1); OLED_ShowNum(80,32,wet_taget,4,16,1); nemu_num = turn_state; if (nemu_num < 0) { turn_state = 17; } else if (nemu_num >= 1 && nemu_num < 9) { nemu_num = 1; } else if (nemu_num >= 9 && nemu_num <17) { nemu_num = 2; } else if (nemu_num >= 17 && nemu_num < 19) { nemu_num = 3; } else if (nemu_num >= 19) { turn_state = 1; } switch(nemu_num) { case 1: OLED_ShowString(0,32,"wet num",16,1); OLED_ShowString(0,48,"Turn Back",16,1); if (temp == 0) { temp = 1; OLED_ShowString(0,16,"light num",16,1); OLED_Refresh(); }else { temp = 0; OLED_ShowString(0,16,"light num",16,0); OLED_Refresh(); } delay_1ms(500); if (KEY_state != 0) { OLED_ShowString(0,16,"light num",16,1); if (AUTO_state == 1) { AUTO_state = 0; hlk_usart_send_string(manual_mode_report, 5); } while(KEY_state == 1) { turn_state = 0; OLED_ShowNum(80,16,light_taget,4,16,1); OLED_Refresh(); delay_1ms(500); OLED_ShowNum(80,16,light_taget,4,16,0); OLED_Refresh(); delay_1ms(500); light_taget = light_taget + turn_state; if (KEY_state != 1) { KEY_state = 0; turn_state = nemu_num; break; } } } break; case 2: delay_1ms(50); OLED_ShowString(0,32,"wet num",16,1); OLED_ShowString(0,48,"Turn Back",16,1); if (temp == 0) { temp = 1; OLED_ShowString(0,32,"wet num",16,1); OLED_Refresh(); }else { temp = 0; OLED_ShowString(0,32,"wet num",16,0); OLED_Refresh(); } delay_1ms(500); if (KEY_state != 0) { OLED_ShowString(0,32,"wet num",16,1); if (AUTO_state == 1) { AUTO_state = 0; hlk_usart_send_string(manual_mode_report, 5); } while(KEY_state > 0) { turn_state = 0; OLED_ShowNum(80 ,32,wet_taget,4,16,1); OLED_Refresh(); delay_1ms(500); OLED_ShowNum(80,32,wet_taget,4,16,0); OLED_Refresh(); delay_1ms(500); wet_taget = wet_taget + turn_state; if (KEY_state != 1) { KEY_state = 0; turn_state = nemu_num; break; } } } break; case 3: OLED_ShowString(0,16,"light num",16,1); OLED_ShowString(0,32,"wet num",16,1); if (temp == 0) { temp = 1; OLED_ShowString(0,48,"Turn Back",16,1); OLED_Refresh(); }else { temp = 0; OLED_ShowString(0,48,"Turn Back",16,0); OLED_Refresh(); } delay_1ms(500); if (KEY_state != 0) { KEY_state = 0; return 0; } break; } motor_stop(); } } int nemu2(void) { OLED_Clear(); OLED_ShowString(10,0,"Show numerical",16,1); OLED_ShowString(0,16,"light_num",16,1); OLED_ShowString(0,32,"wet_num",16,1); OLED_ShowString(0,48,"Turn Back",16,1); OLED_Refresh(); while(1) { OLED_ShowNum(80,16,light_num,4,16,1); OLED_ShowNum(80,32,wet_num,4,16,1); OLED_Refresh(); delay_1ms(500); if (KEY_state != 0) { KEY_state = 0; return 0; } motor_stop(); } } int nemu3(void) { int nemu_num = 1; OLED_Clear(); OLED_ShowString(20,0,"Mode change",16,1); OLED_ShowString(0,16,"Now mode",16,1); OLED_ShowString(0,32,"Change mode",16,1); OLED_ShowString(0,48,"Turn Back",16,1); OLED_Refresh(); turn_state = 1; while(1) { nemu_num = turn_state; if (nemu_num < 0) { turn_state = 17; } else if (nemu_num >= 1 && nemu_num < 9) { nemu_num = 1; } else if (nemu_num >= 9 && nemu_num <17) { nemu_num = 2; } else if (nemu_num >= 17 && nemu_num < 19) { nemu_num = 3; } else if (nemu_num >= 19) { turn_state = 1; } switch(nemu_num) { case 1: OLED_ShowString(100,16,"<-",16,1); OLED_ShowString(100,32," ",16,1); OLED_ShowString(100,48," ",16,1); OLED_Refresh(); if (KEY_state != 0) { KEY_state = 0; return 4; } break; case 2: OLED_ShowString(100,16," ",16,1); OLED_ShowString(100,32,"<-",16,1); OLED_ShowString(100,48," ",16,1); OLED_Refresh(); if (KEY_state != 0) { KEY_state = 0; return 5; } break; case 3: OLED_ShowString(100,16," ",16,1); OLED_ShowString(100,32," ",16,1); OLED_ShowString(100,48,"<-",16,1); OLED_Refresh(); if (KEY_state != 0) { KEY_state = 0; return 0; } break; } motor_stop(); } } int nemu4(void) { OLED_Clear(); OLED_ShowString(35,0,"Now mode",16,1); OLED_ShowString(55,48,"Turn back",16,0); OLED_Refresh(); while(1) { if (AUTO_state == 1) { OLED_ShowString(10,16,"AUTO mode",24,1); }else if(AUTO_state == 0) { OLED_ShowString(5,16,"ManualMode",24,1); } OLED_Refresh(); if (KEY_state != 0) { KEY_state = 0; return 3; } motor_stop(); } } int nemu6(void) { unsigned char auto_mode_report[5] = { 0XAA, 0X55, 0X01, 0X55, 0XAA }; //播报【当前为手动模式】语音 unsigned char manual_mode_report[5] = { 0XAA, 0X55, 0X02, 0X55, 0XAA }; int nemu_num = 1; int temp = 1; OLED_Clear(); OLED_ShowString(35,0,"Warning",16,1); OLED_ShowString(0,16,"Do you want chan",16,1); OLED_ShowString(0,32,"ge the mode",16,1); OLED_ShowString(0,48,"YES",16,1); OLED_ShowString(110,48,"NO",16,1); OLED_Refresh(); while(1) { nemu_num = turn_state; if (nemu_num < 0) { turn_state = 17; } else if (nemu_num >= 1 && nemu_num < 9) { nemu_num = 1; } else if (nemu_num >= 9 && nemu_num <17) { nemu_num = 2; } else if (nemu_num >= 17 && nemu_num < 19) { nemu_num = 3; } else if (nemu_num >= 19) { turn_state = 1; } switch(nemu_num) { case 1: OLED_ShowString(110,48,"NO",16,1); if (temp == 1) { OLED_ShowString(0,48,"YES",16,1); temp = 0; delay_1ms(500); }else { OLED_ShowString(0,48,"YES",16,0); temp = 1; delay_1ms(500); } OLED_Refresh(); if (KEY_state != 0) { KEY_state = 0; if (AUTO_state == 1) { AUTO_state = 0; }else if (AUTO_state == 0) { hlk_usart_send_string(auto_mode_report, 5); AUTO_state = 1; } return 4; } break; case 2: OLED_ShowString(0,48,"YES",16,1); if (temp == 1) { OLED_ShowString(110,48,"NO",16,1); temp = 0; delay_1ms(500); }else { OLED_ShowString(110,48,"NO",16,0); temp = 1; delay_1ms(500); } OLED_Refresh(); if (KEY_state != 0) { hlk_usart_send_string(manual_mode_report, 5); KEY_state = 0; return 3; } break; } } } ``` #### 语音识别代码 ``` void timer_voice_IRQHandler (void) { if(timer_interrupt_flag_get(TIMER6,TIMER_INT_FLAG_UP) == SET) { timer_interrupt_flag_clear(TIMER6,TIMER_INT_FLAG_UP); // 清除中断标志位 if( rx_flag == 1 )//接收到语音命令 { rx_flag = 0; switch( rx_data )//根据语音命令确定对应的动作 { case 0x01://开窗帘命令 open_curtain(); //motor_stop(); //设置非自动模式 AUTO_state = 0; break; case 0x02://关窗帘命令 close_curtain(); //motor_stop(); //设置非自动模式 AUTO_state = 0; break; case 0x03://自动模式命令 AUTO_state = 1; break; case 0x04://手动模式命令 AUTO_state = 0; break; } //清除当前数据 clear_hlk_rx_buff(); } //步进电机限位判断 limit_judgment(get_step_count()); } } ``` #### 红外识别代码 ``` void timer_IR_IRQHandler (void) { //播报【当前为自动模式】语音 unsigned char auto_mode_report[5] = {0XAA, 0X55, 0X01, 0X55, 0XAA}; //播报【当前为手动模式】语音 unsigned char manual_mode_report[5] = {0XAA, 0X55, 0X02, 0X55, 0XAA}; //播报【窗帘已打开】语音 unsigned char curtain_open_report[5] = {0XAA, 0X55, 0X03, 0X55, 0XAA}; //播报【窗帘已关闭】语音 unsigned char curtain_clear_report[5] = {0XAA, 0X55, 0X04, 0X55, 0XAA}; if(timer_interrupt_flag_get(TIMER4,TIMER_INT_FLAG_UP) == SET) { timer_interrupt_flag_clear(TIMER4,TIMER_INT_FLAG_UP); if( get_infrared_command() == 0X68 ) { clear_infrared_command(); AUTO_state = 1; //播报【当前为自动模式】语音 hlk_usart_send_string(auto_mode_report, 5); } //如果按下【#】键,进入非自动模式 if( get_infrared_command() == 0Xb0 ) { clear_infrared_command(); AUTO_state = 0; //播报【当前为手动模式】语音 hlk_usart_send_string(manual_mode_report, 5); } //如果按下【<】键,关闭窗帘 if( get_infrared_command() == 0X10 ) { clear_infrared_command(); close_curtain(); delay_1ms(1000); AUTO_state = 0; //播报【窗帘已关闭】语音语音 hlk_usart_send_string(curtain_clear_report, 5); } //如果按下【>】键,展开窗帘 if( get_infrared_command() == 0X5a ) { temp = 10; clear_infrared_command(); open_curtain(); AUTO_state = 0; //播报【窗帘已打开】语音语音 hlk_usart_send_string(curtain_open_report, 5); } } } ``` 完整代码见附件 ## 注意事项 红外控制不是很灵敏,需要多次按键才可以识别成功 红外遥控器的购买链接:

https://detail.tmall.com/item.htmid=548393997684&spm=a1z09.2.0.0.206a2e8dH3nUIB&_u=8201d9rg5ed88c ## 演示视频 演示视频: https://www.bilibili.com/video/BV1a84y117qC/?vd_source=fda5f531b52244dbb434e4a99b5f9018
设计图
原理图
1 /
PCB
1 /
未生成预览图,请在编辑器重新保存一次
工程视频/附件
序号 文件名称 下载次数
1

“电子训练营”软硬件设计.rar

7
工程成员
侵权投诉
相关工程
换一批
加载中...
添加到专辑 ×

加载中...

温馨提示 ×

是否需要添加此工程到专辑?

温馨提示
动态内容涉嫌违规
内容:
  • 153 6159 2675

服务时间

周一至周五 9:00~18:00
  • 技术支持

support
  • 开源平台公众号

MP