基于物联网技术的智慧病房管理系统
目录
- 前言
- 一、功能设计
- 二、基本配置
- 1.选择芯片型号
- 2.RCC配置
- 3.SYS配置
- 4.USART1 与 DMA 配置
- 5.I2C配置
- 6.TIME3配置
- 7.DMA配置
- 8.TIM2 与 PWM 配置
- 9.NVIC配置
- 10.GPIO配置
- 11.时钟配置
- 12.引脚配置
- 三、RTOS 与模块驱动、代码配置
- RTOS 配置
- 四、RTOS、AHT20 与 按钮功能实现
- 1.温湿度获取代码设计
- 2.RTOS 进程设计
- 3.按钮的使用与消抖
- 五、定时开关灯与信息获取
- 1.定时开关灯
- 六、总结
前言
设计一个基于物联网技术的智慧病房管理系统。假设医院住院部的一层病房(走廊两边病房平行分布),病房数量最多60间,每间病房3个床位,编号从1~180号。每间病房可采用的设备如下:STM32F103开发板1块,房间温湿度采集模块1套(I2C接口,AHT20模块),房间自动灯光开关控制器(以PWM方式控制,每天早上7点渐亮,晚上22点渐灭),病人脉搏&血氧检测仪3套(UART接口输出脉搏+血氧的数字值),床头紧急呼叫按键开关3个(按下呼叫)。
每间病房的STM32F103开发板通过UART转485接口,以mobus组网方式,连接到护士监控室的PC电脑上(上位机)。PC电脑上可接收每间病房的温湿度数据(周期为5分钟)、床头紧急呼叫信号、病人脉搏血氧数据(正常状态下30分钟一次采集;当脉搏超过120或血氧值低于90时切换到危重状态下,实时采集),显示在屏幕上并且保存到MySQL数据库里。
一、功能设计
1.使用 I2C 读取 AHT20 模块
2.TIM 定时器与 PWM 呼吸灯
3.按键信息接收与消抖
4.UART 转 485 接口与 modbus 通信
5.MAX30102 模块心率与血氧测量
二、基本配置
1.选择芯片型号
2.RCC配置
3.SYS配置
4.USART1 与 DMA 配置
5.I2C配置
6.TIME3配置
7.DMA配置
8.TIM2 与 PWM 配置
9.NVIC配置
10.GPIO配置
11.时钟配置
12.引脚配置
三、RTOS 与模块驱动、代码配置
RTOS 配置
选择引入 RT-Thread 轻量便捷 :
外部按钮配置
四、RTOS、AHT20 与 按钮功能实现
1.温湿度获取代码设计
首先我们需要引入温湿度驱动头文件:
#include "AHT20.h"
然后我们需要在进程中对温湿度传感器进行初始化,这里在初始化之后,不能立即获取温湿度,需要等待 2 秒或以上,确保数据正确性:
MX_GPIO_Init();
MX_I2C1_Init();
MX_USART1_UART_Init();
uint32_t CT_data[2]={0,0}; // 用于获取温湿度数据
volatile int c1,t1;
rt_thread_delay(50);
AHT20_Init();
rt_thread_delay(2500);
然后我们需要获取经过 CRC 验证的温湿度数据,这里直接调用驱动函数即可:
while(1){AHT20_Read_CTdata_crc(CT_data); //经过CRC校验,读取AHT20的温度和湿度数据 推荐每隔大于1S读一次c1 = CT_data[0]*1000/1024/1024; //计算得到湿度值c1(放大了10倍)t1 = CT_data[1]*2000/1024/1024-500;//计算得到温度值t1(放大了10倍)printf("正在检测");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");printf("\r\n");printf("温度:%d%d.%d",t1/100,(t1/10)%10,t1%10); // 这里需要对温度进行计算后才能得到我们需要的温度值printf("湿度:%d%d.%d",c1/100,(c1/10)%10,c1%10); // 这里同样需要对适度进行计算printf("\r\n");printf("等待");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");printf("\r\n");}
2.RTOS 进程设计
首先新建 app_rt_thread.c 文件,然后引入头文件:
#include "rtthread.h"
#include "main.h"
#include "i2c.h"
#include "usart.h"
#include "gpio.h"
#include "stdio.h"
#include "AHT20.h"
然后我们需要设计进程,这里主进程先设置为串口发送,子进程设置两个,一个是获取温度参数,另一个是控制 PC13 引脚上的板载 LED ,后续会根据系统进程对进行设计:
//初始化线程函数
void MX_RT_Thread_Init(void)
{//初始化LED1线程rt_thread_init(&led1_thread,"led1",led1_task_entry,RT_NULL,&rt_led1_thread_stack[0],sizeof(rt_led1_thread_stack),3,20);//开启线程调度rt_thread_startup(&led1_thread);//初始化USART1线程rt_thread_init(&usart1_thread,"usart1",usart1_task_entry,RT_NULL,&rt_usart1_thread_stack[0],sizeof(rt_usart1_thread_stack),3,20);//开启线程调度rt_thread_startup(&usart1_thread);
}//主任务
void MX_RT_Thread_Process(void)
{printf("Hello RT_Thread!!!\r\n");rt_thread_delay(2000);
}//LED1任务
void led1_task_entry(void *parameter)
{while(1){HAL_GPIO_WritePin(GPIOC,GPIO_PIN_13, GPIO_PIN_RESET);rt_thread_delay(500);HAL_GPIO_WritePin(GPIOC,GPIO_PIN_13, GPIO_PIN_SET);rt_thread_delay(500);}
}
//读取温度任务
void usart1_task_entry(void *parameter)
{MX_GPIO_Init();MX_I2C1_Init();MX_USART1_UART_Init();uint32_t CT_data[2]={0,0}; //volatile int c1,t1;rt_thread_delay(50);AHT20_Init();rt_thread_delay(2500);while(1){AHT20_Read_CTdata_crc(CT_data); //经过CRC校验,读取AHT20的温度和湿度数据 推荐每隔大于1S读一次c1 = CT_data[0]*1000/1024/1024; //计算得到湿度值c1(放大了10倍)t1 = CT_data[1]*2000/1024/1024-500;//计算得到温度值t1(放大了10倍)printf("正在检测");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");printf("\r\n");printf("温度:%d%d.%d",t1/100,(t1/10)%10,t1%10); // 这里需要对温度进行计算后才能得到我们需要的温度值printf("湿度:%d%d.%d",c1/100,(c1/10)%10,c1%10); // 这里同样需要对适度进行计算printf("\r\n");printf("等待");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");rt_thread_delay(100);printf(".");printf("\r\n");}
}
点击查看完整 app_rt_thread.c 代码
然后我们在主函数中引入 RT-Thread 必要的头文件并引用函数:
#include "rtthread.h"extern void MX_RT_Thread_Init(void);
extern void MX_RT_Thread_Process(void);
最后我们直接在主函数中对进程进行初始化,并运行即可,这里直接给出完整主函数:
int main(void)
{/* USER CODE BEGIN 1 *//* USER CODE END 1 *//* MCU Configuration--------------------------------------------------------*//* Reset of all peripherals, Initializes the Flash interface and the Systick. */HAL_Init();/* USER CODE BEGIN Init *//* USER CODE END Init *//* Configure the system clock */SystemClock_Config();/* USER CODE BEGIN SysInit *//* USER CODE END SysInit *//* Initialize all configured peripherals */MX_GPIO_Init();MX_DMA_Init();MX_I2C1_Init();MX_TIM3_Init();MX_USART1_UART_Init();MX_TIM2_Init();/* USER CODE BEGIN 2 */MX_RT_Thread_Init(); // 初始化线程/* USER CODE END 2 *//* Infinite loop *//* USER CODE BEGIN WHILE */while (1){MX_RT_Thread_Process(); // 执行主进程/* USER CODE END WHILE *//* USER CODE BEGIN 3 */}/* USER CODE END 3 */
}
3.按钮的使用与消抖
首先我们设计按钮在 PA3 引脚,然后在设置 PA4 引脚上外接一个 LED ,这里先令按钮按下反转 PA4 引脚电平,即按下小灯泡点亮,再次按下,小灯泡熄灭,这里直接设计为一个新进程:
struct rt_thread btnclick_thread;
rt_uint8_t rt_btnclick_thread_stack[128];
void btnclick_task_entry(void *parameter);void btnclick_task_entry(void *parameter){while(1){switch(KEY_Scan(0)){ case KEY1_PRES: HAL_GPIO_TogglePin(GPIOA,GPIO_PIN_4);break;default:break;}}
}
初始化线程:
//初始化线程
rt_thread_init(&btnclick_thread,"btnclick",btnclick_task_entry,RT_NULL,&rt_btnclick_thread_stack[0],sizeof(rt_btnclick_thread_stack),3,20);
//开启线程调度
rt_thread_startup(&btnclick_thread);
但是我们不进行按键消抖,这里按键非常容易误触,所以这里进行按键消抖:
#define KEY1 HAL_GPIO_ReadPin(GPIOA,GPIO_PIN_3) //读取按键1
#define KEY1_PRES 1 //KEY1按下
uint8_t KEY_Scan(uint8_t mode)
{static uint8_t key_up=1;//按键松开标志位if(key_up&&(KEY1==0)){HAL_Delay(10);//去抖动key_up=0;if(KEY1==0)return KEY1_PRES;}else if(KEY1==1)key_up=1;return 0;//无按键按下
}
五、定时开关灯与信息获取
这里我们主要实现能够定时开关灯,并且能够获取如下信息:
病人按下紧急呼叫信号
定时获取病人脉搏血氧数据
1.定时开关灯
这里要求我们能够实现在早上 7 点开灯,晚上 22 点灭灯,所以我们就要设计 RTC 系统时间与日历读取,确定我们当前的时间与日期,然后判断时间数,最终通过 PWM 实现灯的渐亮与渐灭
这里首先我们需要配置 RTC:
这里先设置两个变量用于获取时间和日期:
RTC_DateTypeDef Date;
RTC_TimeTypeDef Time;
然后我们可以通过时间进行判断从而实现开关灯的效果:
void ledauto_task_entry(void *parameter){HAL_TIM_PWM_Start(&htim2,TIM_CHANNEL_2);while(1){HAL_RTC_GetTime(&hrtc,&Time,RTC_FORMAT_BIN);if(Time.Hours == 7&&Time.Minutes == 0&&Time.Seconds == 0){printf("开灯!");for(uint16_t i=1;i<500;i++){htim2.Instance->CCR2 = i;rt_thread_delay(5);}}else if(Time.Hours == 22&&Time.Minutes == 0&&Time.Seconds == 0){printf("关灯!");for(uint16_t i=499;i>=1;i--){htim2.Instance->CCR2 = i;rt_thread_delay(5);}}}
}
前面在博客中已经介绍了如何通过 RTC 读取日历和时间:
RTC时间读取(可查看我之前博客)
这里我们只需要照做就可以,但是,由于开发板掉电,时间会重置,所以这里设计时间掉电保存,如果使用外接 RTC 并有电池,则会在掉电后继续计时,这里我设计将代码直接写道 RTC 初始化的函数中即可,完整初始化代码如下:
void MX_RTC_Init(void)
{/* USER CODE BEGIN RTC_Init 0 *//* USER CODE END RTC_Init 0 */RTC_TimeTypeDef sTime = {0};RTC_DateTypeDef DateToUpdate = {0};/* USER CODE BEGIN RTC_Init 1 */__HAL_RCC_BKP_CLK_ENABLE();// 开启后背区域时钟__HAL_RCC_PWR_CLK_ENABLE();// 开启电源时钟/* USER CODE END RTC_Init 1 *//** Initialize RTC Only*/hrtc.Instance = RTC;hrtc.Init.AsynchPrediv = RTC_AUTO_1_SECOND;hrtc.Init.OutPut = RTC_OUTPUTSOURCE_NONE;if (HAL_RTC_Init(&hrtc) != HAL_OK){Error_Handler();}/* USER CODE BEGIN Check_RTC_BKUP */if(HAL_RTCEx_BKUPRead(&hrtc,RTC_BKP_DR1)!= 0x5051){/* USER CODE END Check_RTC_BKUP *//** Initialize RTC and set the Time and Date*/sTime.Hours = 0x7;sTime.Minutes = 0x0;sTime.Seconds = 0x0;if (HAL_RTC_SetTime(&hrtc, &sTime, RTC_FORMAT_BCD) != HAL_OK){Error_Handler();}DateToUpdate.WeekDay = RTC_WEEKDAY_THURSDAY;DateToUpdate.Month = RTC_MONTH_JANUARY;DateToUpdate.Date = 0x12;DateToUpdate.Year = 0x23;if (HAL_RTC_SetDate(&hrtc, &DateToUpdate, RTC_FORMAT_BCD) != HAL_OK){Error_Handler();}/* USER CODE BEGIN RTC_Init 2 */__HAL_RTC_SECOND_ENABLE_IT(&hrtc,RTC_IT_SEC); //开启RTC时钟秒中断datebuff = DateToUpdate; //把日期数据拷贝到自己定义的data中HAL_RTCEx_BKUPWrite(&hrtc, RTC_BKP_DR1, 0x5051);//向指定的后备区域寄存器写入数据HAL_RTCEx_BKUPWrite(&hrtc, RTC_BKP_DR2, (uint16_t)datebuff.Year);HAL_RTCEx_BKUPWrite(&hrtc, RTC_BKP_DR3, (uint16_t)datebuff.Month);HAL_RTCEx_BKUPWrite(&hrtc, RTC_BKP_DR4, (uint16_t)datebuff.Date);HAL_RTCEx_BKUPWrite(&hrtc, RTC_BKP_DR5, (uint16_t)datebuff.WeekDay);}else{datebuff.Year = HAL_RTCEx_BKUPRead(&hrtc, RTC_BKP_DR2);datebuff.Month = HAL_RTCEx_BKUPRead(&hrtc, RTC_BKP_DR3);datebuff.Date = HAL_RTCEx_BKUPRead(&hrtc, RTC_BKP_DR4);datebuff.WeekDay = HAL_RTCEx_BKUPRead(&hrtc, RTC_BKP_DR5);DateToUpdate = datebuff;if (HAL_RTC_SetDate(&hrtc, &DateToUpdate, RTC_FORMAT_BIN) != HAL_OK){Error_Handler();}__HAL_RTC_SECOND_ENABLE_IT(&hrtc,RTC_IT_SEC); //开启RTC时钟秒中断 }getRealTime();/* USER CODE END RTC_Init 2 */}
然后我们需要在运行时,实时获取一次时间:
void getRealTime(void)
{HAL_RTC_GetTime(&hrtc, &time, RTC_FORMAT_BIN);HAL_RTC_GetDate(&hrtc, &datebuff, RTC_FORMAT_BIN);HAL_RTCEx_BKUPWrite(&hrtc, RTC_BKP_DR2, (uint16_t)datebuff.Year);HAL_RTCEx_BKUPWrite(&hrtc, RTC_BKP_DR3, (uint16_t)datebuff.Month);HAL_RTCEx_BKUPWrite(&hrtc, RTC_BKP_DR4, (uint16_t)datebuff.Date);HAL_RTCEx_BKUPWrite(&hrtc, RTC_BKP_DR5, (uint16_t)datebuff.WeekDay);
}void HAL_RTCEx_RTCEventCallback(RTC_HandleTypeDef *hrtc)
{if(hrtc->Instance == RTC){getRealTime(); }
}
六、总结
智慧病房是以院内物联网为基础的辅助诊疗及智能护理一体化解决方案。以智能改造医院病房,通过先进的物联网技术,让患者与医务人员、智能医疗设备紧密联接。
通过对临床数据采集、筛选、整合,形成医疗大数据,为临床诊疗、护理提供智能辅助决策。
提高医疗资源的利用率,更好地保障医疗安全,更好地以患者为中心,提供有品质的医疗服务。
基于物联网技术的智慧病房管理系统相关推荐
- 基于物联网技术的智慧病房管理系统(一)—— 系统配置
基于物联网技术的智慧病房管理系统(一)-- 系统分析与配置 系统要求 设计一个基于物联网技术的智慧病房管理系统.假设医院住院部的一层病房(走廊两边病房平行分布),病房数量最多60间,每间病房3个床位, ...
- 基于物联网技术的智慧病房管理系统(三)——定时开关灯与信息获取
基于物联网技术的智慧病房管理系统(三)-- 定时开关灯与信息获取 这里我们主要实现能够定时开关灯,并且能够获取如下信息: 病人按下紧急呼叫信号 定时获取病人脉搏血氧数据 定时开关灯 这里要求我们能够实 ...
- 基于物联网技术的智慧病房管理系统(二)—— RTOS、AHT20 与 按钮功能实现
基于物联网技术的智慧病房管理系统(二)-- RTOS.AHT20 与 按钮功能实现 这里 RTOS 代码修改,AHT20 驱动代码移植可以参考前面博客内容: STM32 -- IIC 读取 ATH20 ...
- 基于嵌入式物联网技术的智慧病房方案设计
文章目录 前言 一.系统设计要求 二.系统硬件设计 单片机控制电路 AHT20模块 心率脉搏采集模块 MOBUS通信模块 三.系统功能分析与STM32F103基本配置 基本配置如下 四 主要代码设计 ...
- 基于物联网技术的智慧教室重点设备监控系统设计与实现
完整文件下载,关注:码视野,回复关键字:2001 一.引言 1.1 研究背景和意义 随着新技术的广泛应用,物联网作为新一代信息技术,在各个领域中的应用也越来越广泛.在教育领域中,物联网已经成为教育发展 ...
- rfid档案管理-基于RFID技术的智能档案管理系统—铨顺宏fuwit
基于RFID技术的智能档案管理系统 1.行业概述 随着企事业单位的发展,各种信息档案资料数量逐日增多,档案的种类日趋多样化,纸质信息存储出现迅速膨胀:而传统的档案管理方式与技术手段所导致的问题也是日益 ...
- 基于物联网技术的智能家居设计
基于物联网技术的智能家居设计 智慧家居的定义与它的功能,设计一个你想象中最满意的智慧家居场景,列举其中传感器的功能和作用,要求远程手机可以监控,列举你所知道的物联网产品以及传感器相关的产品的品牌,回答 ...
- 基于springboot+Vue的智慧酒店管理系统
真正的大师,永远都怀着一颗学徒的心! 一.项目简介 基于springboot+Vue的智慧酒店管理系统 二.实现功能 支持多端 支持用户管理 支持酒店前台管理 支持酒店管理 支持订单管理 支持系统管理 ...
- 基于RFID技术的智能仓储管理系统解决方案—铨顺宏
一.行业背景 简单.静态的传统仓储管理模式普遍存的物资库存量巨大.物资跟踪困难.资金和物资周转效率较低.人力成本偏高.物流管理的信息和手段落后等缺点,已不能适应新的仓储管理需求.破除传统的仓储管理模式 ...
最新文章
- java线程的状态及状态间的切换
- javascript中break和continue
- 【最详细】数据结构(C语言版 第2版)第五章课后习题答案 严蔚敏 等 编著
- python递归算法_python递归算法(上)
- Delphi下实现全屏快速找图找色 二、矩阵遍历
- 力扣两数之和 II - 输入有序数组
- [剑指offer][JAVA]面试题第[10-2]题[青蛙跳台阶问题][动态规划][递归]
- 用t430搭建虚拟服务器教程,T430完美使用VmWare
- java有几大对象_一个 Java 对象到底有多大?
- [状压dp] 玉米田(状压dp)
- python汽车租赁系统django
- App消息推送 实现原理
- 当古典音乐遇上NFT
- javascript 代码技巧 (四) —— javascript获取坐标/滚动/宽高/距离
- Sentinel -- sentinel控制台的简单应用
- FPGA开发工具套餐搭配推荐及软件链接(工程师们转起来)
- 基于php的网络教学平台,基于PHP技术的网络教学平台的设计与实现
- 【sql注入】二次注入
- 算法习题集 - Miscellaneous
- android 精品软件,《分享精彩应用 Android精品软件推荐》