
输液监护这东西看着不起眼做起来全是细节。我最早做的第一版严格来说只能算个“滴完报警器”红外对管贴在滴斗两侧液体滴完就触发蜂鸣器护士站那边亮个灯。真正决定做这个智能输液监护调控系统升级版是因为有次在医院陪护时发现护士调滴速全靠手腕和经验病人翻身、药液粘稠度变化都会让滴速慢慢飘走而我那版报警器根本察觉不到这些。从那时起我就把目标定成不要只是报警而是让系统自己把滴速稳住出问题还要能主动切断、上报、提醒。这个开源项目包含完整的STM32工程代码、原理图和仿真工程解决的核心问题就是“输液过程实时监护和自动调控”。适合正在做毕业设计、电子设计竞赛项目的同学也适合想看看一个完整STM32项目从硬件到软件、从仿真到真机是怎么一步步落地的开发者。1. 从“滴完报警”到“闭环调控”升级版究竟升级了什么1.1 基础版做到哪一步第一版硬件极其简单一块STM32F103C8T6最小系统板一个红外对管贴在滴斗上一个蜂鸣器加一个继电器。原理是滴斗里每隔一段时间落下一滴液体红外接收管收到的光强会随液滴折射发生变化STM32检测到脉冲就认为“在输液”。一旦超过设定时间没有新脉冲就认为输液结束触发报警。这版的问题很明显第一滴速偏移了不知道只有彻底不滴了才会报警反应太慢。第二完全不能调节只能靠护士手动去推输液器上的滚轮。第三误报率高滴斗壁挂水珠、气泡扰动、药液颜色深都会让检测信号变得乱七八糟一个晚上响错三五次很正常。1.2 升级版在这些维度上做了什么这次的升级版不是简单加几个传感器而是把整个系统从“开环监测”改成“闭环控制”再叠加一套比较完整的异常处理机制。我做了张表方便对比维度基础版升级版滴速检测只判断有没有液体下落实时计算滴速带滤波和去抖滴速调节无蠕动泵PID闭环带前馈控制异常检测仅检测输液完毕输液完毕、堵塞、滴速异常、温度异常异常处置蜂鸣器报警报警断电自动夹管电机停转人机交互一个LEDOLED显示按键设置蜂鸣器分级报警数据上报无HC-05蓝牙串口透传到手机或护士站附加功能无DHT11温度监测加热膜恒温参数保存无Flash模拟EEPROM掉电保存仿真配套无Proteus电路仿真Wokwi代码仿真Simulink控制仿真升级版的整体思路可以概括成“检测-决策-执行-上报”四条链路并行传感器负责感知滴速、压力和温度主控负责滤波、状态判断和PID计算执行器包括蠕动泵、夹管阀和加热膜最后通过蓝牙把运行状态发出去。整个系统围绕着一块STM32F103C8T6展开外设不多但每一路都有讲究。1.3 系统功能清单与总体架构做个功能清单其实就很清楚了实时监测当前滴速OLED显示目标滴速、实时滴速、累计输液量和温度按键设定目标滴速范围10到80滴/分钟蠕动泵根据PID输出自动调整转速把实际滴速稳定在目标值附近压力传感器检测输液管路压力压力异常偏高判定为堵塞红外检测连续无滴判定为输液完毕或者气泡进入任何异常触发蜂鸣器分级报警同时切断夹管阀电源蓝牙每500ms上报一次运行状态手机端可以查看和记录DHT11实时监测环境温度低于设定阈值时启动加热膜给输液管加热2. 硬件选型与原理图设计每一路信号都有讲究2.1 主控选型逻辑为什么还是用STM32F103C8T6有人问我这都“升级版”了怎么还用F103C8T6这颗芯片72MHz主频、64KB Flash、20KB RAM说实话对于这个项目完全够用而且它的外设资源刚好卡在点子上三个USART、两个I2C、两个SPI、三个通用定时器、一个高级定时器、10个12位ADC通道。滴速检测用外部中断电机PWM用定时器输出压力传感器走ADC蓝牙走USART1OLED走I2C刚刚好全覆盖。选型还有一个考虑是生态。F103系列是STM32里资料最全、坑最少、问谁都能聊两句的芯片。对开源项目来说可复现性比极致性能重要得多。如果换成更新的G0系列或者直接上H7性能和功耗确实更好但对初学者和想快速复现的人来说门槛会高不少。真机测试阶段这颗芯片的表现也很稳定72MHz跑状态机加PIDCPU占用率不到30%还有余量。2.2 传感器信号链光电滴速检测的关键设计滴速检测是整个系统的眼睛眼睛看不清后面全是白搭。第一版我直接用红外对管输出接STM32的GPIO结果信号毛刺多到怀疑人生后来才明白问题出在信号没有整形。升级版的做法是红外发射管和接收管分别装在滴斗两侧液滴经过时接收管上的光强会发生明显变化。接收管信号先过一个LM393比较器设置合适的阈值电压把模拟信号整形成干净的TTL方波再进MCU。比较器是开漏输出外部必须加上拉电阻。我还在比较器正反馈端加了一个几十千欧的电阻构成迟滞比较器这样信号在阈值附近抖动时不会反复触发。这个电路看起来不起眼但它解决了一个最关键的问题把“液滴有没有经过”变成一个可靠的边沿信号。没有这样的整形软件端做再多滤波都治标不治本。压力检测用的是FSR402薄膜压力传感器贴在输液管外壁压力变化会改变电阻值配合一个运算放大器放大后进STM32的ADC引脚。温度检测用的DHT11虽然精度一般但用于判断是否要启动加热已经足够。给个引脚分配表照着接线就行功能引脚说明滴速脉冲输入PA0外部中断模式上升沿触发DHT11数据PA1单总线协议加热膜PWM输出PA2定时器2通道3输出压力传感器ADCPA3ADC1通道3步进电机IN1-IN4PB0-PB3接ULN2003驱动夹管阀控制PB4GPIO输出低电平有效蜂鸣器PB5GPIO输出三极管驱动OLED SCL/SDAPB6/PB7硬件I2C1蓝牙TXD/RXDPA9/PA10USART1按键设定/加/减PB8/PB9/PB10输入上拉2.3 执行机构选型蠕动泵、步进电机与安全夹管阀执行机构是这次升级的重头戏。要让滴速自动稳定就必须让液体流动速度可调输液场景下最合适的是蠕动泵通过挤压软管的方式推动液体液体不接触泵体本身干净卫生更换耗材也方便。我用的是带减速箱的步进电机带动蠕动泵泵头通过控制步进电机转速调节流量。电机驱动芯片选了ULN2003因为使用的28BYJ-48是四相五线步进电机和ULN2003是黄金搭档。不过提醒一句如果你选的是42步进电机那就不能再用ULN2003得换成A4988或者DRV8825支持细分驱动大电流电机更稳。28BYJ-48的缺点也很明显低速时扭矩不足长时间运行容易丢步所以升级版实际测试时我把电机供电电压提高到了12V转速响应明显改善。夹管阀是安全机制里最重要的一环。选型的核心原则是断电要能自动夹紧输液管也就是常闭型。我用的方案是12V电磁铁搭配弹簧夹MCU控制一个MOSFET正常运行时给电电磁铁吸合、弹簧夹打开一旦系统检测到异常或者直接断电电磁铁释放弹簧夹立刻夹住输液管。这个设计保证即使MCU死机或者电源断了也不会出现失控输液的情况。加热膜控制相对简单MCU输出PWM通过MOSFET控制加热膜的通断功率。PWM频率选1kHz左右DHT11测温做简单的滞回控制温度低于36℃时加热高于38℃时停止。2.4 电源树与通信接口系统稳定性的基础整套系统的供电比较杂电机要12VMCU和传感器要3.3V蓝牙模块虽然标称3.3V但其实5V供电也能工作不过IO电平最好还是保持一致。我的电源树是12V适配器输入先经过MP2307降压模块转5V给步进电机和加热膜供电5V再经过AMS1117-3.3给MCU、传感器和OLED供电。这里有个实操细节MCU的3.3V和电机的5V/12V一定要分开走线最后在电源输入处单点共地。否则电机启动瞬间的电流冲击会在地线上产生压差轻则ADC读数抖动重则MCU直接复位。我在PCB上把数字地、模拟地、功率地用0欧电阻隔开实测噪声明显减小。蓝牙模块用的是HC-05USART1通信。有个容易踩的坑是HC-05的RXD和STM32的TXD直接相连如果HC-05是5V逻辑而STM32是3.3V逻辑就可能反向灌电流。稳妥的做法是在STM32 TXD到HC-05 RXD之间串一个1k电阻分压。模块供电直接接5VSTROBE状态引脚悬空即可。2.5 原理图绘制与PCB布局经验原理图用立创EDA或者Altium Designer都能画关键是分模块画电源模块、MCU最小系统、传感器接口、电机驱动、通信接口五块分开方便排查。MCU最小系统里特别注意三点BOOT0接10k下拉电阻到地NRST接10k上拉加100nF电容每个电源引脚旁边放一个100nF去耦电容。PCB布局上我把滴速检测探头做成了一个独立小板用排针和主板连接这样调试时方便更换探头位置。主板布局的经验是晶振尽量靠近MCU走线短电源部分放板子一角远离模拟信号输入电机驱动和传感器接口不要挨着避免继电器或电机产生的EMI干扰传感器信号。3. 软件实现与核心算法信号处理和控制策略是灵魂3.1 滴速检测去抖从电平变化到可靠脉冲硬件整形以后PA0上收到的是干净的TTL方波一个下降沿代表一滴液滴。但“干净”是相对的滴斗内水珠飞溅、气泡破裂仍然会产生一些宽度很小的毛刺所以软件层面必须做二次去抖。我的做法是用外部中断记录上升沿时间戳在中断里做最小间隔判断两次有效脉冲间隔小于50ms的直接扔掉因为正常输液滴速就算很快比如80滴/分钟相邻两滴间隔也有750ms50ms以内的脉冲只可能是抖动。有效的滴液间隔存进一个长度为10的环形缓冲区主循环里用滑动平均计算实时滴速。#define MAX_VALID_INTERVAL_MS 60000 // 60秒未见滴判为停滴 #define MIN_VALID_INTERVAL_MS 50 // 小于50ms视为抖动 volatile uint32_t last_drop_tick 0; volatile uint16_t interval_buf[10]; volatile uint8_t interval_idx 0; volatile float display_rate 0; void EXTI0_IRQHandler(void) { if (EXTI_GetITStatus(EXTI_Line0) RESET) return; uint32_t now HAL_GetTick(); uint32_t diff now - last_drop_tick; last_drop_tick now; if (diff MIN_VALID_INTERVAL_MS) { interval_buf[interval_idx] (uint16_t)diff; interval_idx (interval_idx 1) % 10; } EXTI_ClearITPendingBit(EXTI_Line0); } float calc_avg_drop_rate(void) { uint32_t sum 0; uint8_t i; for (i 0; i 10; i) sum interval_buf[i]; if (sum 0) return 0; return 60000.0f * 10 / (float)sum; // 滴/分钟 }有一点必须提醒中断服务函数里不要做浮点运算和复杂处理我只在中断里记录时间戳和存数组真正的滴速计算全部放到主循环里做。中断越短系统越稳。3.2 滴速与流速换算理解滴系数临床记录输液量时习惯用mL/h而传感器检测到的是滴/分钟两者之间的换算关系由输液器的滴系数决定。滴系数指的是多少滴液体等于1mL常见的一次性输液器有15滴/mL和20滴/mL两种规格微量泵用的输液器可能是60滴/mL。换算公式很简单流速(mL/h) 滴速(滴/min) × 60(min/h) ÷ 滴系数(滴/mL)举个例子滴系数20的情况下如果设定滴速是40滴/min那么流速就是40×60÷20120mL/h。这个系数在开机校准界面让用户根据实际输液器包装上的标注选择保存到Flash里。OLED上同时显示滴速和mL/h方便和护士站的记录核对。3.3 自动调节控制策略开关控制为什么不行PID为什么有必要有人可能会问滴速低了我就加大电机转速滴速高了我就减小转速这种开关控制行不行实测下来完全不行。因为蠕动泵和输液管路组成的系统有一定惯性液滴从泵头挤出到进入滴斗被检测到有几百毫秒甚至更长的延迟开关控制会在这个延迟下形成振荡滴速忽高忽低最夸张的时候能在20到80滴/分钟之间来回跳。升级版用的是前馈加增量式PID。前馈的意思是目标滴速确定后先给电机一个基础转速的“开环预置值”这个预置值来自标定时拟合的滴速-转速曲线能大致接近目标滴速但精度不够。PID负责在预置值基础上做精细修正消除稳态误差。增量式PID的计算核心是三个系数(K_p)决定对当前误差的响应力度(K_i)负责消除长期累积偏差(K_d)抑制误差变化趋势。因为我们的反馈量是10秒滑动平均后的滴速本身已经比较平滑D项作用很小甚至可以先设成0。typedef struct { float kp, ki, kd; float err, last_err, prev_err; float out; } PID_t; float pid_incremental(PID_t *pid, float setpoint, float measurement) { float p_out, i_out, d_out, delta; pid-err setpoint - measurement; p_out pid-kp * (pid-err - pid-last_err); i_out pid-ki * pid-err; d_out pid-kd * (pid-err - 2.0f * pid-last_err pid-prev_err); delta p_out i_out d_out; pid-out delta; if (pid-out 2000) pid-out 2000; // 限制电机最大转速对应的占空比/TIM值 if (pid-out 0) pid-out 0; pid-prev_err pid-last_err; pid-last_err pid-err; return pid-out; }这里有个血泪教训不要在主循环里每毫秒都做一次PID计算因为滴速反馈本身就是“一滴一个事件”的离散信号100ms内可能连一滴都没落下来反馈值根本没变化PID输出却一直在动。我的做法是固定每10秒做一次PID计算因为10秒内的平均滴速已经能比较平滑地反映真实趋势了。控制周期太短会放大测量噪声太长又响应不过来10秒是我试下来比较折中的值。3.4 软件状态机与异常处理逻辑整个运行逻辑我整理成了一个状态机比用一堆if-else嵌套清晰得多状态说明进入条件离开条件IDLE待机等待设置和启动上电按下启动键RUNNING正常运行PID控制中启动滴尽、堵塞、按键暂停ALARM异常报警夹管阀断电关闭任意异常触发人工复位PAUSE暂时停止不调节手动暂停继续运行或复位状态机代码用switch实现事件用全局标志位传递typedef enum {STATE_IDLE, STATE_RUNNING, STATE_ALARM, STATE_PAUSE} SysState_t; SysState_t current_state STATE_IDLE; void state_machine_run(void) { switch (current_state) { case STATE_IDLE: if (key_start_pressed) current_state STATE_RUNNING; break; case STATE_RUNNING: if (flag_drop_timeout || flag_pressure_high || flag_rate_abnormal || flag_temp_abnormal) { alarm_trigger(); // 蜂鸣器分级报警 clamp_valve_close(); // 夹管阀断电夹管 motor_stop(); current_state STATE_ALARM; } else if (key_pause_pressed) { motor_stop(); current_state STATE_PAUSE; } break; case STATE_ALARM: if (key_reset_pressed) { alarm_clear(); clamp_valve_open(); current_state STATE_IDLE; } break; case STATE_PAUSE: if (key_start_pressed) current_state STATE_RUNNING; break; default: current_state STATE_IDLE; break; } }异常判断逻辑有几个细节值得展开。滴尽检测不能只看单次无滴时间因为低速输液时两滴间隔本身就能达到6秒我设置了10秒的窗口窗口内没有任何有效脉冲才判定滴尽。压力异常检测也做了防误报压力连续1秒超过阈值才报警滤除掉病人咳嗽、翻身等瞬间动作产生的压力波动。滴速异常偏快的判断是实测滴速持续超过设定值50%并且持续30秒以上因为单独一两滴偏快可能是偶然的挂壁液滴落下。3.5 参数掉电保存Flash模拟EEPROM滴系数、PID参数、目标滴速这些参数如果每次开机都要重新输入体验会很差。STM32F103C8T6没有内置EEPROM但它的Flash可以用来模拟。我在最后一个扇区划出一页做参数存储地址偏移配置好写入前先擦除整页。需要注意一点Flash擦写次数只有一万次左右所以在主循环里绝不能频繁写。我的策略是只有按下设置键确认修改时写一次正常运行时Flash是只读的。如果以后要频繁记录数据建议外挂一颗24C02 I2C EEPROM寿命长得多。4. 仿真验证先说清楚这套仿真能验证什么4.1 Proteus电路级仿真验证信号链和逻辑用Proteus做硬件仿真是有优势的它能验证电路连接、通信协议和程序逻辑。我在Proteus里搭了STM32F103C8T6的主控电路滴速传感器用NE555构成的脉冲发生器替代通过改变电位器频率模拟不同滴速压力传感器用可调电压源模拟OLED和蜂鸣器用Proteus自带的虚拟器件。Proteus支持加载Keil编译生成的hex文件直接运行。这样在画板子之前就能先验证一件事程序逻辑和引脚定义是否一致。比如PB0到PB3驱动电机如果代码里写错成PB4在Proteus里看电机对应的逻辑指示器就能立刻发现。不过Proteus的仿真模型是理想化的尤其STM32的仿真支持近年才比较完善对定时器、ADC这类外设的模拟精度有限。我的建议是把它当“逻辑验证工具”用别指望它验证时序精度。4.2 Wokwi在线仿真没有开发板也能跑代码后来我发现Wokwi这个在线仿真平台对初学者特别友好它支持STM32F103C8T6可以直接在浏览器里搭建虚拟电路连接OLED、按键、LED、串口等外设加载你的固件运行。我放了一份支持Wokwi的工程在开源仓库里diagram.json里预设了滴速脉冲引脚对应的按键和LED方便没有硬件的同学先跑通状态机逻辑。{ version: 1, author: open-source-infusion, editor: wokwi, parts: [ { type: board-stm32f103c8t6, id: mcu, top: 0, left: 0 }, { type: wokwi-pushbutton, id: btn1, top: 80, left: 160, attrs: { label: Drop } }, { type: wokwi-led, id: led1, top: 80, left: 300, attrs: { color: red } } ], connections: [ [ mcu:PA0, btn1:1, white, [v] ], [ mcu:PB5, led1:A, green, [v] ] ] }Wokwi最大的价值在于代码调试方便可以设断点、看变量、单步执行比真机接一堆杜邦线再连调试器要轻量得多。我把PID参数标定后得出的初值写死在工程里Wokwi环境里也能看到OLED上滴速显示的逻辑是否正确。4.3 Simulink控制仿真与PID参数预整定PID参数如果在真机上硬调效率很低一次试错可能要等好几分钟才能看到效果。我在Simulink里搭了一个简化的闭环模型目标滴速作为输入经过PID控制器输出到电机转速电机转速通过一阶惯性环节和延迟环节转换成检测到的滴速。过程模型近似一个带延迟的近似积分环节延迟时间大约0.5到1秒时间常数2秒左右。在这个模型上我先用试凑法得到一组初始PID参数(K_p0.8)(K_i0.15)(K_d0)然后在真机上做微调。实测下来仿真给出的参数方向是对的直接把真机的调参时间从一整天压缩到了两个小时。Simulink里还可以很方便地模拟扰动场景比如在某一刻人为改变管路阻力看看PID的恢复能力。4.4 仿真替代不了真机调试的几个原因必须泼一盆冷水仿真做得再漂亮也替代不了真机。液滴在滴斗中的下落并不是理想的脉冲序列挂壁水珠、药液颜色深浅、药液表面张力变化这些物理世界的细节在仿真里根本不存在。步进电机低速时的振动和共振频率、软管被挤压后的蠕变、电磁铁吸合瞬间对ADC的干扰也都是模型很难预测的。所以整套仿真流程的意义在于降低调试成本但最终精度和可靠性一定是以真机实测为准。5. 实测数据与踩坑笔记真机调试会遇到的坑5.1 红外信号抖动与误报一次完整的排查过程真机调试第一晚就出问题了OLED上显示的滴速在设定值40滴/分钟附近狂跳能跑到七八十甚至一百多。先用示波器抓PA0引脚的电平发现一个正常的液滴脉冲后面还跟着两三个幅度较小的毛刺时间间隔大约在100到200毫秒之间。这些毛刺对应的是液滴落入滴斗后溅起的小水珠水珠经过红外对管时同样会造成光强变化。排查思路很简单先确认电路整形没问题再分析毛刺来源最后对症下药。电路层面我给比较器加了迟滞电阻大概0.3V的迟滞宽度把幅度较小的毛刺直接滤掉。软件层面把最小有效间隔从50ms提高到100ms因为正常滴速最快也就80滴/分钟相邻间隔不会小于750ms100ms以内的脉冲都没必要接受。两层处理之后滴速显示变得非常平稳10秒滑动平均值基本稳定在设定值正负1滴/分钟以内。还有一个环境中容易忽略的因素是药液颜色。偏深色的棕色药液、乳白色的脂肪乳对红外光的吸收和散射和普通盐水完全不一样。我的解决办法是把比较器阈值设计成电位器可调换不同药液时手动微调一次。5.2 电机失步、软管变形与流量漂移第二类问题是执行端的。28BYJ-48步进电机在5V供电下扭矩偏小长时间低速运行容易失步最典型的现象是设定60滴/分钟输了一小时实际只有45滴/分钟了。排查时我一开始怀疑是PID没调好后来单独测电机在固定PWM下的转速发现转速随时间明显下降才确认是电机扭矩和软管蠕变共同导致的。解决分三步第一步把电机供电从5V提到12V扭矩增大失步明显减少。第二步把软管从普通PVC管换成硅胶管软管被泵头挤压后的恢复能力更好流量漂移小很多。第三步在软件里加了一个低速保护如果电机在较高转速下运行但是实测滴速持续偏低先判断是否堵管排除堵管后就触发重新标定流程而不是让PID无限加大输出避免电机长时间堵转烧毁。5.3 “no stm32 target found”这类调试连接问题很多同学在我开源的评论区问烧录时报错怎么办最常见的是error: no stm32 target found! if your product embeds debug authentication。这个报错在ST-Link连不上目标芯片时就会出现我遇到过好几种原因现象原因解决办法ST-Link灯正常但连不上BOOT0引脚悬空或误拉高确认BOOT0接地NRST上拉偶尔能连上一擦除就断目标板供电不足用外部3.3V给板子单独供电新画的板子完全无响应晶振或复位电路问题检查8MHz晶振和22pF负载电容芯片之前写过读保护芯片被锁BOOT0拉高串口ISP全擦除按住复位键可以松开不行程序里马上进入了低功耗按住复位点下载避开运行阶段最实用的技巧是“按住复位烧录法”在Keil里点下载然后立刻按住目标板复位键不放等下载进度出现再松开。这样做可以绕过程序启动阶段的干扰成功率非常高。5.4 实测数据记录这批数据是可以参考的我用生理盐水做了一轮完整测试滴系数按20滴/mL设定环境温度25℃左右记录不同目标滴速下的表现目标滴速(滴/min)实测平均(滴/min)标准差(滴/min)是否触发异常报警2020.41.0否4040.10.8否6059.71.5否8079.62.3否堵塞检测的反应时间测试用手捏住输液管模拟堵塞压力传感器检测到异常后系统在1.8秒内完成报警和夹管阀动作。滴尽检测的反应时间取决于设定的无滴窗口我设10秒实际从最后一滴到报警大概12到14秒包含中断处理和状态机轮询的额外延迟。这个延迟在护理场景下是可以接受的。PID控制的动态响应也测了从40滴/分钟突变设定到60滴/分钟系统大约在40秒内稳定到60±2滴/分钟。为什么不更快因为控制周期10秒一次加上滴速测量本身也有延迟这个收敛速度已经是物理条件能支持的不错水平了。6. 开源资料结构、复现步骤和安全提示6.1 开源仓库结构说明开源内容包括三部分完整Keil工程代码、原理图和PCB源文件、仿真工程。仓库结构如下infusion-monitor-system-upgrade/ ├── MDK-ARM/ │ ├── infusion_monitor.uvprojx │ ├── Core/ │ │ ├── Inc/ # 头文件 │ │ └── Src/ # main.c, stm32f1xx_it.c等 │ ├── Drivers/ # 标准外设库/HAL库 │ └── Hardware/ │ ├── drop_sensor.c # 滴速检测中断与滤波 │ ├── motor.c # 步进电机驱动 │ ├── pid.c # PID控制器 │ ├── oled.c # OLED显示 │ ├── dht11.c # DHT11温度读取 │ ├── bluetooth.c # HC-05串口透传 │ └── flash_save.c # Flash模拟EEPROM ├── Hardware/ │ ├── SCH/ # 原理图源文件与PDF │ ├── PCB/ # PCB工程文件和制造文件 │ └── BOM.xlsx # 物料清单 ├── Simulation/ │ ├── Proteus/ # Proteus电路仿真工程 │ ├── Wokwi/ # Wokwi在线仿真配置 │ └── Simulink/ # PID控制仿真模型 └── Doc/ ├── user_manual.md # 使用和校准说明 └── calibration.md # 滴系数的标定方法6.2 物料清单整理了一份参考物料清单价格按常见电子商城零售价估算不含运输类别型号数量参考价格(元)主控STM32F103C8T6最小系统板110-20滴速检测红外发射管IR333 接收管PT334各21比较器LM393模块22压力检测FSR402薄膜压力传感器115-25温度检测DHT11模块13-5步进电机28BYJ-48 ULN2003驱动板110-15蠕动泵泵头BQ50泵头或国产3D打印泵头130-80夹管阀常闭型电磁夹管阀125-45加热膜聚酰亚胺加热膜 5V/12V110-20显示0.96寸OLED I2C18-12通信HC-05蓝牙模块18-15蜂鸣器有源蜂鸣器 5V11-2电源12V/2A适配器115-25电源芯片MP2307模块 AMS1117-3.3各15-10附件输液器、硅胶管、接线端子等若干20-30总物料成本控制在两百元以内主要成本在泵头和压力传感器上。如果你想省一版的钱压力传感器初期可以先用可变电阻串联分压代替但最终精度会差一些。6.3 从零开始复现的完整步骤复现流程我给个比较稳的路径跟着走能少踩一半坑搭建软件环境安装Keil MDK 5安装STM32F1系列器件支持包安装ST-Link驱动。打开MDK-ARM/infusion_monitor.uvprojx工程。编译烧录基础版先用仓库里的默认配置编译连上ST-Link烧录。OLED能点亮、蜂鸣器能响说明最小系统没问题。接线和硬件测试按照第二章的引脚表接线。先把滴速探头的红外对管和比较器接好用手在探头前面晃动验证PA0能否收到稳定的脉冲。滴系数校准把输液器安装好管内充满生理盐水进入校准菜单。实际记录30秒内滴了多少滴和系统显示值对比误差大的话调整滴系数和比较器阈值。校准完成后参数自动存入Flash。PID参数微调用默认PID参数跑起来观察滴速波动。如果滴速出现周期性振荡减小(K_p)如果存在长期偏差加大(K_i)。每次修改参数后要保存并观察至少3分钟。异常功能测试依次模拟滴尽夹住进气管或直接拿掉输液袋、堵塞捏住输液管、滴速过快人为手动泵入液体确认报警、夹管阀关闭、蓝牙上报都正常。整体可靠性测试用生理盐水连续运行4小时每半小时记录一次滴速数据确认没有漂移和误报。6.4 医疗设备合规与安全提示这个项目是学习和研究用途的电子设计项目它可以演示输液监护和调控的基本原理但不能直接用于临床治疗。医用输液设备的电气安全IEC 60601系列、生物相容性、灭菌要求、报警优先级、软件可靠性验证都远超一个开源项目能覆盖的范围。尤其是夹管阀和蠕动泵涉及直接接触患者的硬件如果走向实际医疗应用需要在专业法规和生产体系下重新设计和验证。即便只是用来做实验我也强烈建议在软件里保留这些东西硬件看门狗IWDG防止死机后系统无反应电机堵转保护持续高转速仍无滴速时自动停机夹管阀的默认值必须是关闭状态保证异常断电时管路被夹住。这些安全设计不会增加多少成本但在关键时刻能避免事故。这个项目整理资料的时候我把源码、原理图、仿真工程重新过了一遍能感觉到从最初那个“滴完报警器”走到现在的闭环系统中间全是一个一个坑堆出来的。红外探头的去抖、PID的调参、电机失步的处理、Flash存储的次数限制每一个都是实测出来的经验。如果你按照这份资料复现预算两三百元时间大概一周基本能跑通。最花时间的一定不是写代码而是调滴速稳定性和异常判断的阈值这部分我只能说慢慢来每台泵、每根软管、每种药液的脾气都不一样调试的过程本身就是嵌入式最有意思的部分。