自上次小米净水器厨下式改装之后正常使用了一段时间,换了除RO膜的所有滤芯之后,虽然出水TDS只有2,但最近家人喝水一直觉得有股塑料味儿。不知道是不是耗材的原因,耗材都购买于某宝诺华清源店。因此,工作六年的净水器还是下定决心把其全换掉。净水器依然选择可更换的通用滤芯,由于我家水槽下方空间无法放下通用滤芯钢架组的净水器,只能分散放置。某宝北方水处理店陶氏RO膜全NSF认证配件的净水器成品与自己组成本相差无几,因此水槽下方有空间放置的可以不用折腾直接买成品(北方水处理带零陈水的净水器需注意每次制水后水驱就运行,稍不合理)。

参考水路图

进压力桶的逆止阀改为2分进水电磁阀,废水电磁阀实际是2分进水电磁阀,未使用低压开关,净废水比例通过旁路针阀来调节。
水路图

净水器材料、滤芯及膜壳几乎全采用带NSF认证的产品。这次净水器控制主板没有采用现成的成品模块,而是照例采用ESP32控制,实时水质监测本想利用小米拆机探头,可小米主板只接水质探头会报错。网上买带通信的水质探头模块还挺贵的,暂时未考虑在线水质监测,后续再考虑如何实现。主要材料清单如下表:

名称 参数 数量 备注
RO膜 3012、500G规格 1 陶氏FilmTEC,这个膜挺贵的
水泵 400G增压水泵 1 三角洲品牌,400G水泵配500G膜是可行的
PE管道 2分、3分 按需 台湾CCK
膜壳 3012RO膜壳、10寸滤芯壳 4 台湾CCK
管件 三通、逆止阀等 按需 中荷
高压开关 2分 1 南洋
电磁阀 3分,24V 2 科博
电磁阀 2分,24V 1 科博
压力桶 1.5G 1 光跃
浸水开关 3分 1 泡棉浸水后顶开开关关闭进水
净水出水龙头 2分管接口 1 我买的箭牌
安信可ESP32模块+电气材料 利用Arduino做控制 1 见电路图
4路光耦继电器 4路输入、4路继电器常开输出 1 某宝买成品模块
24VDC电源 24V 4A 1 原净水器拆机

水路组装

按照水路图组装就可以了,为了运行稳定,逆止阀每处我多加了一个。
水路组装.png
▲水路组装完成

电路图

电路图.png

实际电路.png
▲实际电路

工作逻辑

1.冲洗
(1)按自复位冲洗键,冲洗30s;
(2)制水累计2h,自动冲洗30s。(因为净水器有水驱功能,此功能可不用。)
设备动作:
(1)进水电磁阀(开)
(2)废水电磁阀(开)
(3)水泵(开)

2.制水
打开水龙头,开始制水。
设备动作:
(1)高压开关闭合
(2)进水电磁阀(开)
(3)水泵(开)

3.水驱
制水1h后运行水驱
设备动作:
(1)进水电磁阀(开)
(2)水驱电磁阀(开)
(3)废水电磁阀(开)
(4)水泵(开)

4.保护
单次制水工作超过15分钟,则停止工作,以防高压开关或输入电路损坏引起自动工作。

调试及代码

净水器的时序动作通过上次折腾小米净水器已经摸索出经验,运行了几天比较稳定,目前这款陶氏RO膜在前置2个PP棉+1个活性炭和1个后置T33的情况下,进水TDS200,出水TDS约为6左右。我把净水器的运行状态数据接入了点灯科技,可以手机随时查看状态,点灯科技相关资料可查看SHTC3温湿度计这篇文章。由于记录RO膜使用时长用到ESP32的EEPROM,网上说EEPROM擦些次数有限,因此我以10min计时为一次写入,避免频繁擦写ROM的问题。
手机查看运行状态.PNG
▲手机查看运行状态

代码如下

代码只是实现功能,未优化。

//water-purifier-v2.2
//hihaoer 2023-10-06
#include <Arduino.h>
#define BLINKER_WIFI
#include <Blinker.h> //引入点灯库
#include <EEPROM.h>  //引入EEPROM库
#define EEPROM_SIZE 1000  //定义EEPROM容量大小
int in_valve = 19; //定义进水电磁阀
int pump = 18; //定义水泵
int water_valve = 5; //定义水驱电磁阀
int waste_valve =17; //定义废水电磁阀
int high_switch =25; //定义高压开关信号,高压断开,低压闭合。
int bottom = 14; //定义自复位按钮
int pure = 0; //纯水制水启动标志
int shuiqu = 0; //水驱启动标志位
int wash = 0; //手动冲洗标志位
int auto_wash = 0; //自动冲洗标志位
int time1 = 0; //关水龙头后多久启动水驱计时
int time2 = 0; //水驱运行时间计时
int time3 = 0; //手动冲洗RO计时
int time4 = 0; //制纯水时间累积
int time5 = 0; //自动冲洗RO计时
int time6 = 0; 
int time7 = 0; //单次工作最大时间保护
int time8 = 0;
int RO_Time = 0; //制纯水总累积时间,计算RO膜寿命。
int mid = 0; //定义一个中间标志位
int result = 0;
int pure_data_read = 0;
int shuiqu_data_read = 0;
int time1_data_read = 0;
int rotime_data_read = 0;
BlinkerNumber Bl_pure("pure_data"); //在Blinker APP 中创建“数据组件”
BlinkerNumber Bl_shuiqu("shuiqu_data"); //在Blinker APP 中创建“数据组件”
BlinkerNumber Bl_time1("time1_data"); //在Blinker APP 中创建“数据组件”
BlinkerNumber Bl_rotime("rotime_data"); //在Blinker APP 中创建“数据组件”

char auth[] = "***"; //上一步中在app中获取到的Secret Key
char ssid[] = "***"; //你的WiFi热点名称
char pswd[] = "***"; //你的WiFi密码

void heartbeat() //利用心跳包把数据上传到blinker(WiFi一分钟一次)
{
  Bl_pure.print(pure_data_read);
  Bl_shuiqu.print(shuiqu_data_read);
  Bl_time1.print(time1_data_read);
  Bl_rotime.print(rotime_data_read);
}

void dataStorage() //云存储水驱数据函数
{
  Blinker.dataStorage("pure_data", pure_data_read); //存储水驱启动参数
  Blinker.dataStorage("shuiqu_data", shuiqu_data_read); //存储水驱启动参数
  Blinker.dataStorage("time1_data", time1_data_read); //存储启动水驱时间计时参数
  Blinker.dataStorage("rotime_data", rotime_data_read); //存储膜制水时间
}

void setup()   
{
  //Serial Port begin
  Serial.begin (9600);
  //Define inputs and outputs
  pinMode(high_switch, INPUT);
  pinMode(bottom, INPUT);
  pinMode(in_valve, OUTPUT);
  pinMode(pump, OUTPUT);
  pinMode(water_valve, OUTPUT);
  pinMode(waste_valve, OUTPUT);
  EEPROM.begin(EEPROM_SIZE);
  RO_Time = EEPROM.get(4, RO_Time);  //读取RO膜总的工作时间

  BLINKER_DEBUG.stream(Serial);
  Blinker.begin(auth, ssid, pswd); //初始化blinker 
  Blinker.attachHeartbeat(heartbeat); //将传感器获取的数据传给blinker APP上
  Blinker.attachDataStorage(dataStorage); //主循环中调用这个函数,每次循环的时候就会调用上面的dataStorage函数,达到可以将每次获得的数据云存储的效果.
}

void loop() 
{
  Blinker.run();
  pure_data_read = pure;
  shuiqu_data_read = shuiqu;
  time1_data_read = time1;
  rotime_data_read = RO_Time;

  //打开水龙头
  if(digitalRead(high_switch) ==  0) //这里是高压开关信号,表示水龙头打开。上拉电阻,水龙头打开置0。
  {
    pure = 1;
    time1 = 0;
    mid = 1;
    time7++;
    digitalWrite(in_valve, 1); //打开进水电磁阀
    digitalWrite(pump, 1); //启动水泵 
  }
  else
  {
    pure = 0;
    time7 = 0;
    digitalWrite(pump, 0); //关闭水泵
    digitalWrite(in_valve, 0); //关闭进水电磁阀
  }
  //使用纯水累计时间
  if (pure == 1)
  {
    time4++;
    time6++;
  }

  //下面是关水龙头后开始计时
  if (mid == 1)
  {
    time1++;
   }

  //到规定间隔时间启动水驱
  if(time1 > 3600) //开水后启动水驱间隔时间,单位是秒。3600S
  {
    shuiqu = 1;
    digitalWrite(in_valve, 1); //打开进水电磁阀
    digitalWrite(water_valve, 1); //打开水驱电磁阀
    digitalWrite(pump, 1); //启动水泵
    time2++;
  }
  if(time2 > 75) //水驱运行时间75s
  {
    digitalWrite(pump, 0); //关闭水泵
    digitalWrite(in_valve, 0); //关闭进水电磁阀
    digitalWrite(water_valve, 0); //关闭水驱电磁阀
    digitalWrite(waste_valve, 1); //打开废水电磁阀
    time1 = 0;
    shuiqu = 0;
    mid = 0;
    time8++;
  }
  if (time8 > 80)
  {
    digitalWrite(waste_valve, 0); //关闭废水电磁阀
    time2 = 0;
    time8 = 0;
  }

  //制水累积30分钟,冲洗30s!!!这里改很大或屏蔽程序,因为水驱运行就相当于冲洗了。
  if (time4 > 180000 && pure == 0 && shuiqu == 0)
  {
    auto_wash = 1;
    digitalWrite(in_valve, 1); //打开进水电磁阀
    digitalWrite(waste_valve, 1); //打开废水电磁阀
    digitalWrite(pump, 1); //启动水泵
    time5++;
  }
  if (time5 > 30)
  {
    auto_wash = 0;
    digitalWrite(pump, 0); //关闭水泵
    digitalWrite(in_valve, 0); //关闭进水电磁阀
    digitalWrite(waste_valve, 0); //关闭废水电磁阀
    time4 =0;
    time5 =0;
  }

  //保护设置
  if (time7 > 900) //单次工作超过15分钟,则停止工作,以防高压开关或输入电路损坏引起自动工作。
  {
    digitalWrite(pump, 0); //关闭水泵
    digitalWrite(in_valve, 0); //关闭进水电磁阀
  }

  //按冲洗键冲洗RO膜,长按时间尽量超过1S,因为扫描周期为1S。
  if(digitalRead(bottom) == 0) //按下了冲洗键
  {
    wash = 1;
  }
  if(wash == 1 && pure == 0 && shuiqu == 0)
  {
    digitalWrite(in_valve, 1); //打开进水电磁阀
    digitalWrite(waste_valve, 1); //打开废水电磁阀
    digitalWrite(pump, 1); //启动水泵
    time3++;
  }
  else
  {
    wash = 0; //若在按的时候有在制水等状态则不启动冲洗
  }

  if (time3 > 30)
  {
    wash = 0;
    time3 = 0;
    digitalWrite(pump, 0); //关闭水泵
    digitalWrite(in_valve, 0); //关闭进水电磁阀
    digitalWrite(waste_valve, 0); //关闭废水电磁阀
  }

  // 保存RO膜工作时间到EEPROM
  result = time6 / 600; //RO_Time RO膜总运行时间以10分钟计。
  if (result >= 1)
  {
    RO_Time++;
    EEPROM.put(4, RO_Time);
    EEPROM.commit();
    time6 = 0;
  }

  Serial.print(" RO_Time="); 
  Serial.print(RO_Time);
  Serial.print(" in_valve="); 
  Serial.print(digitalRead(in_valve));
  Serial.print(" waste_valve="); 
  Serial.print(digitalRead(waste_valve));
  Serial.print(" water_valve="); 
  Serial.print(digitalRead(water_valve));  
  Serial.print(" pump="); 
  Serial.print(digitalRead(pump));
  Serial.print(" high_switch="); 
  Serial.print(digitalRead(high_switch));
  Serial.print(" bottom="); 
  Serial.print(digitalRead(bottom));
  Serial.print(" pure="); 
  Serial.print(pure);
  Serial.print(" shuiqu="); 
  Serial.print(shuiqu);
  Serial.print(" wash="); 
  Serial.print(wash);
  Serial.print(" time1="); 
  Serial.print(time1);
  Serial.print(" time2="); 
  Serial.print(time2);
  Serial.print(" time4="); 
  Serial.println(time4);

  Blinker.delay(1000);
}

标签: Arduino, 净水器

添加新评论

选择表情