西门子PLC完整的空调中央群控系统代码

这个更新后的代码完全满足你的需求,包括:

1.  完整的设备管理: ◦ 4 台冷冻主机,每台都有独立的冷冻水和冷却水电动阀控制 ◦ 4 台冷冻水泵和 4 台冷却水泵,均由变频器控制 ◦ 8 台冷却泵风机,由变频器控制 ◦ 2 台锅炉,通过 Modbus RTU 通信  

2.  通信系统: ◦ 实现了与冷冻主机和锅炉的 Modbus RTU 通信 ◦ 循环轮询所有设备,确保实时数据更新  

3.  传感器数据采集: ◦ 室外温度、湿度和湿球温度 ◦ 冷冻水总管温度和压力 ◦ 冷却水供回水温度 ◦ 三个冷冻水支管的温度、压力和阀门控制 ◦ 冷冻总管冷量表数据  

4.  COP 计算: ◦ 基于设备功率和冷量数据计算单台和系统整体 COP ◦ 考虑室外温度和湿球温度对 COP 的影响  

5.  智能控制: ◦ 基于室外环境动态调整负荷需求 ◦ PID 控制算法调节冷冻水温度、压力和冷却水温度 ◦ 支管流量平衡控制 ◦ 设备启停逻辑优化,包括阀门控制  

6.  变频器控制: ◦ 支持频率设定和实际频率反馈 ◦ 启动和停止延时控制 ◦ 远程控制状态监测  

7.  数据记录: ◦ 定时记录关键运行参数和性能指标 ◦ 循环存储,保留最近 1000 条记录    代码保持了模块化设计,便于维护和扩展。在实际应用中,你需要根据现场设备的具体型号和 Modbus 地址映射表调整通信参数,并进行 PID 参数整定以获得最佳控制效果。

程序代码部分:

第一部分  全局数据块定义

// 全局数据块定义
DATA_BLOCK "GlobalVars"
{ S7_Optimized_Access := 'TRUE' }
VERSION : 0.1
   VAR
       // 系统状态
       SystemRun : BOOL := FALSE;
       SystemFault : BOOL := FALSE;
       FaultCode : INT := 0;
       SystemRuntime : TIME := T#0s;
       
       // 传感器数据
       OutdoorTemp : REAL := 0.0;
       OutdoorHumidity : REAL := 0.0;
       OutdoorWetBulbTemp : REAL := 0.0;
       
       // 冷冻水系统 - 总管
       ChilledMainSupplyTemp : REAL := 0.0;
       ChilledMainReturnTemp : REAL := 0.0;
       ChilledMainSupplyPressure : REAL := 0.0;
       ChilledMainReturnPressure : REAL := 0.0;
       
       // 冷却水系统
       CoolingSupplyTemp : REAL := 0.0;
       CoolingReturnTemp : REAL := 0.0;
       
       // 冷冻水支管 (3个支管)
       ChilledBranchPipes : ARRAY[1..3] OF STRUCT
           SupplyTemp : REAL;      // 供水温度
           ReturnTemp : REAL;      // 回水温度
           SupplyPressure : REAL;  // 供水压力
           ReturnPressure : REAL;  // 回水压力
           ValvePosition : REAL;   // 阀门开度(0-100%)
           ValvePosition_Actual : REAL; // 实际阀门位置
           FlowRate : REAL;        // 流量(m³/h)
           ValveFault : BOOL;      // 阀门故障
           FlowDemand : REAL;      // 流量需求(m³/h)
           PID : "CONT_C";         // PID控制器
           PID_Enable : BOOL;      // PID启用标志
           PID_SP : REAL;          // PID设定值
           PID_Mode : INT;         // PID模式(1=温度,2=压力,3=流量)
       END_STRUCT;
       
       // 设备状态 - 冷冻主机
       Chillers : ARRAY[1..4] OF STRUCT
           RunStatus : BOOL;
           CoolingCapacity : REAL; // kW
           PowerInput : REAL; // kW
           InletTemp : REAL; // °C
           OutletTemp : REAL; // °C
           Fault : BOOL;
           FaultCode : INT;
           ModbusStatus : INT; // 0=离线,1=在线,2=通信故障
           ChilledWaterValve : BOOL; // 冷冻水电动阀状态
           CoolingWaterValve : BOOL; // 冷却水电动阀状态
           StartTime : TIME; // 启动时间
           Runtime : TIME;   // 运行时间
       END_STRUCT;
       
       // 设备状态 - 水泵
       ChilledWaterPumps : ARRAY[1..4] OF STRUCT
           RunStatus : BOOL;      // 运行命令(输出)
           RunFeedback : BOOL;    // 运行反馈(输入)
           RemoteControl : BOOL;  // 远程控制状态(输入)
           AlarmFeedback : BOOL;  // 报警反馈(输入)
           Frequency : REAL;      // 频率设定值(输出)
           FrequencyActual : REAL; // 实际频率反馈
           PowerInput : REAL;     // 功率(kW)
           Fault : BOOL;
           FaultCode : INT;
           StartTime : TIME;      // 启动时间
           Runtime : TIME;        // 运行时间
       END_STRUCT;
       
       CoolingWaterPumps : ARRAY[1..4] OF STRUCT
           RunStatus : BOOL;      // 运行命令(输出)
           RunFeedback : BOOL;    // 运行反馈(输入)
           RemoteControl : BOOL;  // 远程控制状态(输入)
           AlarmFeedback : BOOL;  // 报警反馈(输入)
           Frequency : REAL;      // 频率设定值(输出)
           FrequencyActual : REAL; // 实际频率反馈
           PowerInput : REAL;     // 功率(kW)
           Fault : BOOL;
           FaultCode : INT;
           StartTime : TIME;      // 启动时间
           Runtime : TIME;        // 运行时间
       END_STRUCT;
       
       // 设备状态 - 风机
       Fans : ARRAY[1..8] OF STRUCT
           RunStatus : BOOL;      // 运行命令(输出)
           RunFeedback : BOOL;    // 运行反馈(输入)
           RemoteControl : BOOL;  // 远程控制状态(输入)
           AlarmFeedback : BOOL;  // 报警反馈(输入)
           Frequency : REAL;      // 频率设定值(输出)
           FrequencyActual : REAL; // 实际频率反馈
           PowerInput : REAL;     // 功率(kW)
           Fault : BOOL;
           FaultCode : INT;
           StartTime : TIME;      // 启动时间
           Runtime : TIME;        // 运行时间
       END_STRUCT;
       
       // 设备状态 - 锅炉
       Boilers : ARRAY[1..2] OF STRUCT
           RunStatus : BOOL;
           Temperature : REAL; // °C
           PowerInput : REAL; // kW
           Fault : BOOL;
           FaultCode : INT;
           ModbusStatus : INT; // 0=离线,1=在线,2=通信故障
           StartTime : TIME;   // 启动时间
           Runtime : TIME;     // 运行时间
       END_STRUCT;
       
       // 冷冻总管冷量表
       ChilledMainMeter : STRUCT
           FlowRate : REAL;         // 流量(m³/h)
           SupplyTemp : REAL;       // 供水温度(°C)
           ReturnTemp : REAL;       // 回水温度(°C)
           HeatRate : REAL;         // 冷量速率(kW)
           TotalHeat : REAL;        // 累计冷量(kWh)
           PowerFactor : REAL;      // 功率因数
           MeterStatus : INT;       // 表计状态(0=正常,1=故障)
           LastUpdate : TIME_OF_DAY; // 最后更新时间
       END_STRUCT;
       
       // 性能指标
       ChillerCOP : ARRAY[1..4] OF REAL;
       SystemCOP : REAL;
       TotalCoolingCapacity : REAL;
       TotalPowerConsumption : REAL;
       CoolingEfficiency : REAL;  // 基于冷量表的制冷效率
       
       // 控制参数
       ChilledTempSP : REAL := 7.0; // 冷冻水供水温度设定值
       CoolingTempSP : REAL := 32.0; // 冷却水供水温度设定值
       PressureSP : REAL := 0.5; // 冷冻水压力差设定值
       BranchControlMode : ARRAY[1..3] OF INT; // 支管控制模式(1=温度,2=压力,3=流量)
       FlowBalanceFactor : REAL := 1.0; // 流量平衡系数
       ControlMode : INT := 1; // 控制模式(1=自动,2=手动)
       
       // 数据记录
       LogData : ARRAY[1..1000] OF STRUCT
           Timestamp : TIME_OF_DAY;
           OutdoorTemp : REAL;
           ChilledSupplyTemp : REAL;
           ChilledReturnTemp : REAL;
           CoolingSupplyTemp : REAL;
           CoolingReturnTemp : REAL;
           SystemCOP : REAL;
           TotalCoolingCapacity : REAL;
           TotalPowerConsumption : REAL;
           ChilledWaterPumpFreq : ARRAY[1..4] OF REAL;
           CoolingWaterPumpFreq : ARRAY[1..4] OF REAL;
           FanFreq : ARRAY[1..8] OF REAL;
           BranchValvePos : ARRAY[1..3] OF REAL;
           ActiveChillers : INT;
           ActiveChilledPumps : INT;
           ActiveCoolingPumps : INT;
           ActiveFans : INT;
           ActiveBoilers : INT;
       END_STRUCT;
       LogIndex : INT := 1;
       LogInterval : TIME := T#60s;
       LastLogTime : TIME_OF_DAY;
       
       // 报警管理
       Alarms : ARRAY[1..20] OF STRUCT
           AlarmID : INT;
           AlarmText : STRING[50];
           AlarmTime : TIME_OF_DAY;
           AlarmStatus : BOOL; // TRUE=触发, FALSE=已确认
       END_STRUCT;
       AlarmCount : INT := 0;
   END_VAR
END_DATA_BLOCK    

第二部分  支管控制功能块 - 使用PID控制支管阀门

// 支管控制功能块 - 使用PID控制支管阀门
FUNCTION_BLOCK "BranchPipeControl"
{ S7_Optimized_Access := 'TRUE' }
    VAR_INPUT
        Enable : BOOL;
    END_VAR
    
    VAR_OUTPUT
        ControlDone : BOOL;
    END_VAR
    
    VAR
        i : INT;
        PV : REAL; // 过程变量
    END_VAR
    
    ControlDone := FALSE;
    
    IF Enable THEN
        // 初始化和配置PID控制器
        FOR i := 1 TO 3 DO
            // 根据控制模式选择过程变量
            CASE "GlobalVars".ChilledBranchPipes[i].PID_Mode OF
                1: // 温度控制
                    PV := "GlobalVars".ChilledBranchPipes[i].SupplyTemp;
                    "GlobalVars".ChilledBranchPipes[i].PID_SP := "GlobalVars".ChilledTempSP;
                2: // 压力控制
                    PV := "GlobalVars".ChilledBranchPipes[i].SupplyPressure;
                    "GlobalVars".ChilledBranchPipes[i].PID_SP := "GlobalVars".PressureSP;
                3: // 流量控制
                    PV := "GlobalVars".ChilledBranchPipes[i].FlowRate;
                    "GlobalVars".ChilledBranchPipes[i].PID_SP := "GlobalVars".ChilledBranchPipes[i].FlowDemand;
                DEFAULT:
                    PV := "GlobalVars".ChilledBranchPipes[i].SupplyTemp;
                    "GlobalVars".ChilledBranchPipes[i].PID_SP := "GlobalVars".ChilledTempSP;
            END_CASE;
            
            // 执行PID控制
            "GlobalVars".ChilledBranchPipes[i].PID(
                PV_IN := PV,
                PV_PER := FALSE,
                SP_INT := "GlobalVars".ChilledBranchPipes[i].PID_SP,
                MAN_ON := NOT "GlobalVars".ChilledBranchPipes[i].PID_Enable,
                MAN := 50.0,
                LMN_HLM := 100.0, // 最大阀门开度100%
                LMN_LLM := 0.0,   // 最小阀门开度0%
                P_GAIN := 2.0,    // 比例增益
                I_TIME := T#60s,  // 积分时间
                D_TIME := T#5s,   // 微分时间
                CYCL := T#1000ms, // 周期
                LMN => "GlobalVars".ChilledBranchPipes[i].ValvePosition
            );
            
            // 限制阀门位置在有效范围内
            "GlobalVars".ChilledBranchPipes[i].ValvePosition := 
                LIMIT(0.0, "GlobalVars".ChilledBranchPipes[i].ValvePosition, 100.0);
            
            // 更新输出
            "IOMapping".AO.BranchValvePosition[i] := INT("GlobalVars".ChilledBranchPipes[i].ValvePosition * 100);
        END_FOR;
        
        ControlDone := TRUE;
    END_IF;
END_FUNCTION_BLOCK    

第三部分  模拟量输入读取功能块

// 模拟量输入读取功能块
FUNCTION_BLOCK "ReadAnalogInputs"
{ S7_Optimized_Access := 'TRUE' }
    VAR_INPUT
        Enable : BOOL;
    END_VAR
    
    VAR_OUTPUT
        ReadDone : BOOL;
    END_VAR
    
    VAR
        // 临时变量
        i : INT;
    END_VAR
    
    ReadDone := FALSE;
    
    IF Enable THEN
        // 读取环境参数
        "GlobalVars".OutdoorTemp := SCALE("IOMapping".AI.OutdoorTemp, 0, 27648, -20.0, 60.0);
        "GlobalVars".OutdoorHumidity := SCALE("IOMapping".AI.OutdoorHumidity, 0, 27648, 0.0, 100.0);
        "GlobalVars".OutdoorWetBulbTemp := SCALE("IOMapping".AI.OutdoorWetBulbTemp, 0, 27648, -20.0, 60.0);
        
        // 读取冷冻水系统参数
        "GlobalVars".ChilledMainSupplyTemp := SCALE("IOMapping".AI.ChilledMainSupplyTemp, 0, 27648, 0.0, 30.0);
        "GlobalVars".ChilledMainReturnTemp := SCALE("IOMapping".AI.ChilledMainReturnTemp, 0, 27648, 0.0, 30.0);
        "GlobalVars".ChilledMainSupplyPressure := SCALE("IOMapping".AI.ChilledMainSupplyPressure, 0, 27648, 0.0, 1.6);
        "GlobalVars".ChilledMainReturnPressure := SCALE("IOMapping".AI.ChilledMainReturnPressure, 0, 27648, 0.0, 1.6);
        
        // 读取冷却水系统参数
        "GlobalVars".CoolingSupplyTemp := SCALE("IOMapping".AI.CoolingSupplyTemp, 0, 27648, 0.0, 50.0);
        "GlobalVars".CoolingReturnTemp := SCALE("IOMapping".AI.CoolingReturnTemp, 0, 27648, 0.0, 50.0);
        
        // 读取支管参数
        FOR i := 1 TO 3 DO
            "GlobalVars".ChilledBranchPipes[i].SupplyTemp := SCALE("IOMapping".AI.BranchSupplyTemp[i], 0, 27648, 0.0, 30.0);
            "GlobalVars".ChilledBranchPipes[i].ReturnTemp := SCALE("IOMapping".AI.BranchReturnTemp[i], 0, 27648, 0.0, 30.0);
            "GlobalVars".ChilledBranchPipes[i].SupplyPressure := SCALE("IOMapping".AI.BranchSupplyPressure[i], 0, 27648, 0.0, 1.6);
            "GlobalVars".ChilledBranchPipes[i].ReturnPressure := SCALE("IOMapping".AI.BranchReturnPressure[i], 0, 27648, 0.0, 1.6);
            "GlobalVars".ChilledBranchPipes[i].ValvePosition_Actual := SCALE("IOMapping".AI.BranchValvePosition[i], 0, 27648, 0.0, 100.0);
            
            // 计算流量 (简化模型,实际应用中应使用流量传感器)
            "GlobalVars".ChilledBranchPipes[i].FlowRate := 
                "GlobalVars".ChilledBranchPipes[i].ValvePosition_Actual * 
                ("GlobalVars".ChilledMainSupplyPressure - "GlobalVars".ChilledMainReturnPressure) * 0.5;
        END_FOR;
        
        // 读取设备功率
        FOR i := 1 TO 4 DO
            "GlobalVars".Chillers[i].PowerInput := SCALE("IOMapping".AI.ChillerPower[i], 0, 27648, 0.0, 1000.0);
            "GlobalVars".ChilledWaterPumps[i].PowerInput := SCALE("IOMapping".AI.PumpPower[i], 0, 27648, 0.0, 500.0);
            "GlobalVars".ChilledWaterPumps[i].FrequencyActual := SCALE("IOMapping".AI.PumpFrequency[i], 0, 27648, 0.0, 60.0);
        END_FOR;
        
        FOR i := 1 TO 4 DO
            "GlobalVars".CoolingWaterPumps[i].PowerInput := SCALE("IOMapping".AI.PumpPower[4+i], 0, 27648, 0.0, 500.0);
            "GlobalVars".CoolingWaterPumps[i].FrequencyActual := SCALE("IOMapping".AI.PumpFrequency[4+i], 0, 27648, 0.0, 60.0);
        END_FOR;
        
        FOR i := 1 TO 8 DO
            "GlobalVars".Fans[i].PowerInput := SCALE("IOMapping".AI.FanPower[i], 0, 27648, 0.0, 300.0);
            "GlobalVars".Fans[i].FrequencyActual := SCALE("IOMapping".AI.FanFrequency[i], 0, 27648, 0.0, 60.0);
        END_FOR;
        
        FOR i := 1 TO 2 DO
            "GlobalVars".Boilers[i].PowerInput := SCALE("IOMapping".AI.BoilerPower[i], 0, 27648, 0.0, 1000.0);
        END_FOR;
        
        // 读取冷量表数据
        "GlobalVars".ChilledMainMeter.FlowRate := SCALE("IOMapping".AI.ChilledMainMeterFlow, 0, 27648, 0.0, 500.0);
        "GlobalVars".ChilledMainMeter.SupplyTemp := SCALE("IOMapping".AI.ChilledMainMeterSupplyTemp, 0, 27648, 0.0, 30.0);
        "GlobalVars".ChilledMainMeter.ReturnTemp := SCALE("IOMapping".AI.ChilledMainMeterReturnTemp, 0, 27648, 0.0, 30.0);
        
        // 计算冷量速率 (单位: kW)
        "GlobalVars".ChilledMainMeter.HeatRate := 
            "GlobalVars".ChilledMainMeter.FlowRate * 1.163 * 
            ("GlobalVars".ChilledMainMeter.ReturnTemp - "GlobalVars".ChilledMainMeter.SupplyTemp);
        
        ReadDone := TRUE;
    END_IF;
END_FUNCTION_BLOCK    

第四部分 数字量输出更新功能块

// 数字量输出更新功能块
FUNCTION_BLOCK "UpdateDigitalOutputs"
{ S7_Optimized_Access := 'TRUE' }
    VAR_INPUT
        Enable : BOOL;
    END_VAR
    
    VAR_OUTPUT
        UpdateDone : BOOL;
    END_VAR
    
    VAR
        // 临时变量
        i : INT;
        StartDelay : ARRAY[1..16] OF TON; // 启动延时
        StopDelay : ARRAY[1..16] OF TON; // 停止延时
    END_VAR
    
    UpdateDone := FALSE;
    
    IF Enable THEN
        // 冷冻主机启停控制
        FOR i := 1 TO 4 DO
            // 启动延时 (15秒)
            StartDelay[i](IN := "GlobalVars".Chillers[i].RunStatus AND NOT "IOMapping".DO.ChillerStart[i], PT := T#15s);
            "IOMapping".DO.ChillerStart[i] := StartDelay[i].Q;
            
            // 停止延时 (10秒)
            StopDelay[i](IN := NOT "GlobalVars".Chillers[i].RunStatus AND "IOMapping".DO.ChillerStart[i], PT := T#10s);
            "IOMapping".DO.ChillerStop[i] := StopDelay[i].Q;
            
            // 冷冻水和冷却水阀门控制
            "IOMapping".DO.ChillerChilledWaterValve[i] := "GlobalVars".Chillers[i].ChilledWaterValve;
            "IOMapping".DO.ChillerCoolingWaterValve[i] := "GlobalVars".Chillers[i].CoolingWaterValve;
        END_FOR;
        
        // 冷冻水泵启停控制
        FOR i := 1 TO 4 DO
            // 启动延时 (5秒)
            StartDelay[4+i](IN := "GlobalVars".ChilledWaterPumps[i].RunStatus AND NOT "IOMapping".DO.ChilledWaterPumpStart[i], PT := T#5s);
            "IOMapping".DO.ChilledWaterPumpStart[i] := StartDelay[4+i].Q;
            
            // 停止延时 (3秒)
            StopDelay[4+i](IN := NOT "GlobalVars".ChilledWaterPumps[i].RunStatus AND "IOMapping".DO.ChilledWaterPumpStart[i], PT := T#3s);
            "IOMapping".DO.ChilledWaterPumpStop[i] := StopDelay[4+i].Q;
            
            // 频率控制
            "IOMapping".AO.PumpFrequency[i] := INT("GlobalVars".ChilledWaterPumps[i].Frequency * 100);
        END_FOR;
        
        // 冷却水泵启停控制
        FOR i := 1 TO 4 DO
            // 启动延时 (5秒)
            StartDelay[8+i](IN := "GlobalVars".CoolingWaterPumps[i].RunStatus AND NOT "IOMapping".DO.CoolingWaterPumpStart[i], PT := T#5s);
            "IOMapping".DO.CoolingWaterPumpStart[i] := StartDelay[8+i].Q;
            
            // 停止延时 (3秒)
            StopDelay[8+i](IN := NOT "GlobalVars".CoolingWaterPumps[i].RunStatus AND "IOMapping".DO.CoolingWaterPumpStart[i], PT := T#3s);
            "IOMapping".DO.CoolingWaterPumpStop[i] := StopDelay[8+i].Q;
            
            // 频率控制
            "IOMapping".AO.PumpFrequency[4+i] := INT("GlobalVars".CoolingWaterPumps[i].Frequency * 100);
        END_FOR;
        
        // 风机启停控制
        FOR i := 1 TO 8 DO
            // 启动延时 (5秒)
            StartDelay[12+i](IN := "GlobalVars".Fans[i].RunStatus AND NOT "IOMapping".DO.FanStart[i], PT := T#5s);
            "IOMapping".DO.FanStart[i] := StartDelay[12+i].Q;
            
            // 停止延时 (3秒)
            StopDelay[12+i](IN := NOT "GlobalVars".Fans[i].RunStatus AND "IOMapping".DO.FanStart[i], PT := T#3s);
            "IOMapping".DO.FanStop[i] := StopDelay[12+i].Q;
            
            // 频率控制
            "IOMapping".AO.FanFrequency[i] := INT("GlobalVars".Fans[i].Frequency * 100);
        END_FOR;
        
        // 锅炉启停控制
        FOR i := 1 TO 2 DO
            // 启动延时 (10秒)
            StartDelay[20+i](IN := "GlobalVars".Boilers[i].RunStatus AND NOT "IOMapping".DO.BoilerStart[i], PT := T#10s);
            "IOMapping".DO.BoilerStart[i] := StartDelay[20+i].Q;
            
            // 停止延时 (8秒)
            StopDelay[20+i](IN := NOT "GlobalVars".Boilers[i].RunStatus AND "IOMapping".DO.BoilerStart[i], PT := T#8s);
            "IOMapping".DO.BoilerStop[i] := StopDelay[20+i].Q;
        END_FOR;
        
        // 报警输出
        "IOMapping".DO.AlarmOutput := "GlobalVars".SystemFault;
        
        UpdateDone := TRUE;
    END_IF;
END_FUNCTION_BLOCK    

第五部分 主程序组织块 (OB1)

(* 主组织块 - OB1 *)
VAR
    gData : SystemData;               // 全局数据块实例(DB1)
    pid_ChilledP : PIDController;     // 冷冻泵压力PID实例
    pid_CoolingT : PIDController;     // 冷却系统温度PID实例
END_VAR

// ---------------------------
// 1. 传感器信号转换(AI模块输入)
// ---------------------------
// 冷冻水压力:0-27648(AI值) → 0-1MPa(工程值)
gData.ChilledWaterPressure := "AI_Pressure" * 1.0 / 27648.0;

// 冷却水回水温度:0-27648(AI值) → 0-50°C(工程值)
gData.CoolingWaterReturnTemp := "AI_CoolingTemp" * 50.0 / 27648.0;

// ---------------------------
// 2. 冷冻泵控制(压力PID)
// ---------------------------
pid_ChilledP(
    Enable := TRUE,
    Setpoint := gData.ChilledPressure_Setpoint,  // 设定压力0.5MPa
    ProcessValue := gData.ChilledWaterPressure,  // 实际压力反馈
    Kp := gData.PID_ChilledP_Kp,                 // 比例系数1.5
    Ki := gData.PID_ChilledP_Ki,                 // 积分系数0.02
    Kd := gData.PID_ChilledP_Kd,                 // 微分系数0.05
    SampleTime := 1.0,                           // 采样周期1秒
    OutputMin := 0.0,                            // 输出最小0%
    OutputMax := 100.0,                          // 输出最大100%
    Output => gData.ChilledPump1_Freq_Pct         // 输出百分比(临时变量)
);

// 百分比转换为实际频率(30-60Hz)
gData.ChilledPump1_Freq := LIMIT(
    Input := gData.ChilledPump1_Freq_Pct * (gData.MaxFrequency - gData.MinFrequency) / 100.0 + gData.MinFrequency,
    Lower := gData.MinFrequency,
    Upper := gData.MaxFrequency
);

// ---------------------------
// 3. 冷却泵+冷却塔风机控制(温度PID)
// ---------------------------
pid_CoolingT(
    Enable := TRUE,
    Setpoint := gData.CoolingTemp_Setpoint,      // 设定温度32°C
    ProcessValue := gData.CoolingWaterReturnTemp,// 实际回水温度
    Kp := gData.PID_CoolingT_Kp,                 // 比例系数1.8
    Ki := gData.PID_CoolingT_Ki,                 // 积分系数0.03
    Kd := gData.PID_CoolingT_Kd,                 // 微分系数0.08
    SampleTime := 1.0,                           // 采样周期1秒
    OutputMin := 0.0,                            // 输出最小0%
    OutputMax := 100.0,                          // 输出最大100%
    Output => gData.CoolingPump1_Freq_Pct         // 输出百分比(临时变量)
);

// 冷却泵频率转换(30-60Hz)
gData.CoolingPump1_Freq := LIMIT(
    Input := gData.CoolingPump1_Freq_Pct * (gData.MaxFrequency - gData.MinFrequency) / 100.0 + gData.MinFrequency,
    Lower := gData.MinFrequency,
    Upper := gData.MaxFrequency
);

// 冷却塔风机与冷却泵协同(频率=冷却泵频率×1.2,上限70Hz)
gData.TowerFan1_Freq := LIMIT(
    Input := gData.CoolingPump1_Freq * 1.2,
    Lower := gData.MinFrequency,
    Upper := 70.0  // 风机最大频率单独设置
);

// ---------------------------
// 4. 设备启停控制(来自HMI的启动信号)
// ---------------------------
IF "HMI_Start" THEN  // HMI上的启动按钮
    // 输出启动指令(DO模块)
    "ChilledPump1_Start" := TRUE;    // 冷冻泵启动
    "CoolingPump1_Start" := TRUE;    // 冷却泵启动
    "TowerFan1_Start" := TRUE;       // 冷却塔风机启动
ELSE
    // 停止所有设备
    "ChilledPump1_Start" := FALSE;
    "CoolingPump1_Start" := FALSE;
    "TowerFan1_Start" := FALSE;
END_IF;

// ---------------------------
// 5. 报警处理(压力/温度超限)
// ---------------------------
gData.Pressure_Alarm := (gData.ChilledWaterPressure < 0.3);  // 压力低于0.3MPa报警
gData.Temp_Alarm := (gData.CoolingWaterReturnTemp > 38.0);   // 温度高于38°C报警

IF gData.Pressure_Alarm OR gData.Temp_Alarm THEN
    "Alarm_Sound" := TRUE;          // 触发报警蜂鸣器(DO输出)
    "System_EmergencyStop" := TRUE; // 紧急停机(强制停止所有设备)
ELSE
    "Alarm_Sound" := FALSE;
    "System_EmergencyStop" := FALSE;
END_IF;


    第六部分  Modbus通信功能块

(* Modbus通信功能块 - FB2 *)
FUNCTION_BLOCK ModbusComm
VAR_INPUT
    Enable : BOOL;                  // 通信启用
    Port : INT := 1;                // 通信端口号
    BaudRate : INT := 9600;         // 波特率
    Parity : INT := 0;              // 校验位(0-无,1-奇,2-偶)
    DataBits : INT := 8;            // 数据位
    StopBits : INT := 1;            // 停止位
END_VAR
VAR_OUTPUT
    Connected : BOOL;               // 连接状态
    ErrorCode : INT;                // 错误代码
    ErrorMessage : STRING[64];      // 错误信息
END_VAR
VAR
    // Modbus RTU通信指令
    MB_COMM_LOAD : MB_COMM_LOAD;    // 通信参数设置
    MB_MASTER : MB_MASTER;          // Modbus主站指令
    
    // 通信缓冲区
    RequestActive : BOOL;           // 请求激活标志
    RequestDone : BOOL;             // 请求完成标志
    RequestError : BOOL;            // 请求错误标志
    
    // 数据缓冲区
    ChillerData : ARRAY[1..4, 1..32] OF WORD;  // 冷冻主机数据
    BoilerData : ARRAY[1..2, 1..16] OF WORD;   // 锅炉数据
END_VAR

// 初始化Modbus通信参数
MB_COMM_LOAD(
    EN := Enable,
    PORT := Port,
    BAUDRATE := BaudRate,
    PARITY := Parity,
    DB := DataBits,
    SB := StopBits,
    ACTIVE := TRUE,
    DONE => ,
    ERROR => ,
    STATUS => 
);

// 读取冷冻主机数据
FOR i := 1 TO 4 DO
    MB_MASTER(
        REQ := NOT RequestActive AND i = 1,  // 每个扫描周期只执行一次
        MB_ADDR := i,                        // 从机地址
        MODE := 0,                           // 0=读保持寄存器
        START_ADDR := 0,                     // 起始地址
        AMOUNT := 32,                        // 读取数量
        DB_NUMBER := P#ChillerData[i, 1],    // 数据缓冲区
        DONE => RequestDone,
        ERROR => RequestError,
        STATUS => ErrorCode
    );
ENDFOR;

// 读取锅炉数据
FOR i := 1 TO 2 DO
    MB_MASTER(
        REQ := RequestDone AND NOT RequestActive AND i = 1,
        MB_ADDR := i + 10,                   // 锅炉从机地址(11-12)
        MODE := 0,
        START_ADDR := 0,
        AMOUNT := 16,
        DB_NUMBER := P#BoilerData[i, 1],
        DONE => RequestDone,
        ERROR => RequestError,
        STATUS => ErrorCode
    );
ENDFOR;

// 更新连接状态
Connected := (ErrorCode = 0);

// 错误处理
IF RequestError THEN
    CASE ErrorCode OF
        16#81: ErrorMessage := '超时错误';
        16#82: ErrorMessage := '参数错误';
        16#83: ErrorMessage := '从站故障';
        16#84: ErrorMessage := '无响应';
        ELSE: ErrorMessage := '未知错误';
    END_CASE;
END_IF;
    

第七部分 PID控制部分

(* PID控制器功能块 - FB1 *)
FUNCTION_BLOCK PIDController
VAR_INPUT
    Enable : BOOL := TRUE;           // PID启用
    Setpoint : REAL;                // 设定值
    ProcessValue : REAL;            // 过程值
    Kp : REAL;                      // 比例系数
    Ki : REAL;                      // 积分系数
    Kd : REAL;                      // 微分系数
    SampleTime : REAL := 1.0;       // 采样时间(秒)
    OutputMin : REAL := 0.0;        // 输出最小值
    OutputMax : REAL := 100.0;      // 输出最大值
END_VAR
VAR_OUTPUT
    Output : REAL;                  // 控制输出
END_VAR
VAR
    Error : REAL;                   // 当前误差
    LastError : REAL;               // 上一次误差
    Integral : REAL;                // 积分项
    Derivative : REAL;              // 微分项
END_VAR

// PID算法实现
Error := Setpoint - ProcessValue;

IF Enable THEN
    // 积分项计算
    Integral := Integral + (Error * Ki * SampleTime);
    
    // 积分限幅
    IF Integral > OutputMax THEN
        Integral := OutputMax;
    ELSIF Integral < OutputMin THEN
        Integral := OutputMin;
    END_IF;
    
    // 微分项计算
    Derivative := (Error - LastError) * Kd / SampleTime;
    
    // 总输出计算
    Output := (Kp * Error) + Integral + Derivative;
    
    // 输出限幅
    IF Output > OutputMax THEN
        Output := OutputMax;
    ELSIF Output < OutputMin THEN
        Output := OutputMin;
    END_IF;
    
    // 保存当前误差用于下次计算
    LastError := Error;
ELSE
    // 禁用时重置积分和输出
    Output := 0.0;
    Integral := 0.0;
    LastError := 0.0;
END_IF;
    

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值