LCOV - code coverage report
Current view: top level - EnergyPlus - DXCoils.cc (source / functions) Hit Total Coverage
Test: lcov.output.filtered Lines: 6159 8874 69.4 %
Date: 2024-08-23 23:50:59 Functions: 58 61 95.1 %

          Line data    Source code
       1             : // EnergyPlus, Copyright (c) 1996-2024, The Board of Trustees of the University of Illinois,
       2             : // The Regents of the University of California, through Lawrence Berkeley National Laboratory
       3             : // (subject to receipt of any required approvals from the U.S. Dept. of Energy), Oak Ridge
       4             : // National Laboratory, managed by UT-Battelle, Alliance for Sustainable Energy, LLC, and other
       5             : // contributors. All rights reserved.
       6             : //
       7             : // NOTICE: This Software was developed under funding from the U.S. Department of Energy and the
       8             : // U.S. Government consequently retains certain rights. As such, the U.S. Government has been
       9             : // granted for itself and others acting on its behalf a paid-up, nonexclusive, irrevocable,
      10             : // worldwide license in the Software to reproduce, distribute copies to the public, prepare
      11             : // derivative works, and perform publicly and display publicly, and to permit others to do so.
      12             : //
      13             : // Redistribution and use in source and binary forms, with or without modification, are permitted
      14             : // provided that the following conditions are met:
      15             : //
      16             : // (1) Redistributions of source code must retain the above copyright notice, this list of
      17             : //     conditions and the following disclaimer.
      18             : //
      19             : // (2) Redistributions in binary form must reproduce the above copyright notice, this list of
      20             : //     conditions and the following disclaimer in the documentation and/or other materials
      21             : //     provided with the distribution.
      22             : //
      23             : // (3) Neither the name of the University of California, Lawrence Berkeley National Laboratory,
      24             : //     the University of Illinois, U.S. Dept. of Energy nor the names of its contributors may be
      25             : //     used to endorse or promote products derived from this software without specific prior
      26             : //     written permission.
      27             : //
      28             : // (4) Use of EnergyPlus(TM) Name. If Licensee (i) distributes the software in stand-alone form
      29             : //     without changes from the version obtained under this License, or (ii) Licensee makes a
      30             : //     reference solely to the software portion of its product, Licensee must refer to the
      31             : //     software as "EnergyPlus version X" software, where "X" is the version number Licensee
      32             : //     obtained under this License and may not use a different name for the software. Except as
      33             : //     specifically required in this Section (4), Licensee shall not use in a company name, a
      34             : //     product name, in advertising, publicity, or other promotional activities any name, trade
      35             : //     name, trademark, logo, or other designation of "EnergyPlus", "E+", "e+" or confusingly
      36             : //     similar designation, without the U.S. Department of Energy's prior written consent.
      37             : //
      38             : // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR
      39             : // IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
      40             : // AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
      41             : // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
      42             : // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
      43             : // SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
      44             : // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
      45             : // OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
      46             : // POSSIBILITY OF SUCH DAMAGE.
      47             : 
      48             : // C++ Headers
      49             : #include <cmath>
      50             : #include <string>
      51             : 
      52             : // ObjexxFCL Headers
      53             : #include <ObjexxFCL/Fmath.hh>
      54             : 
      55             : // EnergyPlus Headers
      56             : #include <EnergyPlus/Autosizing/All_Simple_Sizing.hh>
      57             : #include <EnergyPlus/Autosizing/CoolingAirFlowSizing.hh>
      58             : #include <EnergyPlus/Autosizing/CoolingCapacitySizing.hh>
      59             : #include <EnergyPlus/Autosizing/CoolingSHRSizing.hh>
      60             : #include <EnergyPlus/Autosizing/HeatingAirFlowSizing.hh>
      61             : #include <EnergyPlus/Autosizing/HeatingCapacitySizing.hh>
      62             : #include <EnergyPlus/BranchNodeConnections.hh>
      63             : #include <EnergyPlus/CurveManager.hh>
      64             : #include <EnergyPlus/DXCoils.hh>
      65             : #include <EnergyPlus/Data/EnergyPlusData.hh>
      66             : #include <EnergyPlus/DataAirSystems.hh>
      67             : #include <EnergyPlus/DataBranchNodeConnections.hh>
      68             : #include <EnergyPlus/DataContaminantBalance.hh>
      69             : #include <EnergyPlus/DataEnvironment.hh>
      70             : #include <EnergyPlus/DataGlobalConstants.hh>
      71             : #include <EnergyPlus/DataHeatBalance.hh>
      72             : #include <EnergyPlus/DataLoopNode.hh>
      73             : #include <EnergyPlus/DataPrecisionGlobals.hh>
      74             : #include <EnergyPlus/DataSizing.hh>
      75             : #include <EnergyPlus/DataWater.hh>
      76             : #include <EnergyPlus/EMSManager.hh>
      77             : #include <EnergyPlus/Fans.hh>
      78             : #include <EnergyPlus/General.hh>
      79             : #include <EnergyPlus/GeneralRoutines.hh>
      80             : #include <EnergyPlus/GlobalNames.hh>
      81             : #include <EnergyPlus/HVACVariableRefrigerantFlow.hh>
      82             : #include <EnergyPlus/HeatBalanceInternalHeatGains.hh>
      83             : #include <EnergyPlus/InputProcessing/InputProcessor.hh>
      84             : #include <EnergyPlus/NodeInputManager.hh>
      85             : #include <EnergyPlus/OutAirNodeManager.hh>
      86             : #include <EnergyPlus/OutputProcessor.hh>
      87             : #include <EnergyPlus/OutputReportPredefined.hh>
      88             : #include <EnergyPlus/Psychrometrics.hh>
      89             : #include <EnergyPlus/ScheduleManager.hh>
      90             : #include <EnergyPlus/SimAirServingZones.hh>
      91             : #include <EnergyPlus/StandardRatings.hh>
      92             : #include <EnergyPlus/UtilityRoutines.hh>
      93             : #include <EnergyPlus/WaterManager.hh>
      94             : #include <EnergyPlus/ZoneTempPredictorCorrector.hh>
      95             : 
      96             : namespace EnergyPlus::DXCoils {
      97             : 
      98             : // Module containing the DX coil simulation routines
      99             : 
     100             : // MODULE INFORMATION:
     101             : //       AUTHOR         Fred Buhl
     102             : //       DATE WRITTEN   May 2000
     103             : //       MODIFIED       Aug 2000, Don Shirey, Sept 2000, Feb/Oct 2001, Sept 2003, Jan 2004
     104             : //                      Feb 2005, M. J. Witte, GARD Analytics, Inc., Add new coil type COIL:DX:MultiMode:CoolingEmpirical: Work supported by
     105             : //                      ASHRAE research project 1254-RP Aug 2006, B Griffith, NREL, Added water system interactions for new water manager, Feb
     106             : //                      2010, B Nigusse, FSEC, Added Standard Rating for Coil:Cooling:DX:SingleSpeed Apr 2010, Chandan Sharma, FSEC, Added basin
     107             : //                      heater routines for Coil:Cooling:DX:SingleSpeed, Coil:Cooling:DX:TwoSpeed,
     108             : //                                Coil:Cooling:DX:MultiSpeed, and Coil:Cooling:DX:TwoStageWithHumidityControlMode
     109             : //                      Feb 2013, Bereket Nigusse, FSEC, Added DX Coil Model For 100% OA systems
     110             : //                      Jul 2015, RP Zhang, XF Pang, LBNL, Added new coil type for VRF-FluidTemperatureControl Model
     111             : 
     112             : // PURPOSE OF THIS MODULE:
     113             : // To encapsulate the data and algorithms required to simulate DX cooling coils in
     114             : // EnergyPlus. Module currently models air-cooled or evap-cooled direct expansion systems
     115             : // (split or packaged). Air-side performance is modeled to determine coil discharge
     116             : // air conditions. The module also determines the DX unit's electrical energy usage.
     117             : // Neither the air-side performance nor the electrical energy usage includes the effect
     118             : // of supply air fan heat/energy usage. The supply air fan is modeled by other modules.
     119             : 
     120             : // USE STATEMENTS:
     121             : // Use statements for data only modules
     122             : // Using/Aliasing
     123             : using namespace DataLoopNode;
     124             : using namespace Psychrometrics;
     125             : 
     126             : // Use statements for access to subroutines in other modules
     127             : using namespace ScheduleManager;
     128             : 
     129             : // Functions
     130             : 
     131    47491188 : void SimDXCoil(EnergyPlusData &state,
     132             :                std::string_view CompName,             // name of the fan coil unit
     133             :                HVAC::CompressorOp const compressorOp, // compressor operation; 1=on, 0=off
     134             :                bool const FirstHVACIteration,         // True when first HVAC iteration
     135             :                int &CompIndex,
     136             :                HVAC::FanOp const fanOp,                                      // allows parent object to control fan mode
     137             :                ObjexxFCL::Optional<Real64 const> PartLoadRatio,              // part load ratio (for single speed cycling unit)
     138             :                ObjexxFCL::Optional<Real64 const> OnOffAFR,                   // ratio of compressor on airflow to compressor off airflow
     139             :                ObjexxFCL::Optional<Real64 const> CoilCoolingHeatingPLRRatio, // used for cycling fan RH control
     140             :                ObjexxFCL::Optional<Real64 const> MaxCap,                     // maximum cooling capacity of VRF terminal units
     141             :                ObjexxFCL::Optional<Real64 const> CompCyclingRatio            // cycling ratio of VRF condenser connected to this TU
     142             : )
     143             : {
     144             : 
     145             :     // SUBROUTINE INFORMATION:
     146             :     //       AUTHOR         Fred Buhl
     147             :     //       DATE WRITTEN   May 2000
     148             :     //       MODIFIED       Don Shirey, Sept 2000, October 2001, June 2005
     149             : 
     150             :     // PURPOSE OF THIS SUBROUTINE:
     151             :     // Manages the simulation of a single speed on/off DX coil.
     152             : 
     153             :     // Using/Aliasing
     154             : 
     155             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
     156             :     int DXCoilNum;       // index of fan coil unit being simulated
     157             :     Real64 AirFlowRatio; // ratio of compressor on airflow to compressor off airflow
     158             :     Real64 CompCycRatio; // compressor cycling ratio of VRF condenser
     159             : 
     160             :     // First time SimDXCoil is called, get the input for all the DX coils (condensing units)
     161    47491188 :     if (state.dataDXCoils->GetCoilsInputFlag) {
     162           0 :         GetDXCoils(state);
     163           0 :         state.dataDXCoils->GetCoilsInputFlag = false; // Set GetInputFlag false so you don't get coil inputs again
     164             :     }
     165             : 
     166    47491188 :     if (CompIndex == 0) {
     167          22 :         DXCoilNum = Util::FindItemInList(CompName, state.dataDXCoils->DXCoil);
     168          22 :         if (DXCoilNum == 0) {
     169           0 :             ShowFatalError(state, format("DX Coil not found={}", CompName));
     170             :         }
     171          22 :         CompIndex = DXCoilNum;
     172             :     } else {
     173    47491166 :         DXCoilNum = CompIndex;
     174    47491166 :         if (DXCoilNum > state.dataDXCoils->NumDXCoils || DXCoilNum < 1) {
     175           0 :             ShowFatalError(state,
     176           0 :                            format("SimDXCoil: Invalid CompIndex passed={}, Number of DX Coils={}, Coil name={}",
     177             :                                   DXCoilNum,
     178           0 :                                   state.dataDXCoils->NumDXCoils,
     179             :                                   CompName));
     180             :         }
     181    47491166 :         if (state.dataDXCoils->CheckEquipName(DXCoilNum)) {
     182         827 :             if (!CompName.empty() && CompName != state.dataDXCoils->DXCoil(DXCoilNum).Name) {
     183           0 :                 ShowFatalError(state,
     184           0 :                                format("SimDXCoil: Invalid CompIndex passed={}, Coil name={}, stored Coil Name for that index={}",
     185             :                                       DXCoilNum,
     186             :                                       CompName,
     187           0 :                                       state.dataDXCoils->DXCoil(DXCoilNum).Name));
     188             :             }
     189         827 :             state.dataDXCoils->CheckEquipName(DXCoilNum) = false;
     190             :         }
     191             :     }
     192             : 
     193    47491188 :     if (present(OnOffAFR)) {
     194    43615116 :         AirFlowRatio = OnOffAFR;
     195             :     } else {
     196     3876072 :         AirFlowRatio = 1.0;
     197             :     }
     198             : 
     199    47491188 :     if (present(CompCyclingRatio)) {
     200     1516035 :         CompCycRatio = CompCyclingRatio;
     201             :     } else {
     202    45975153 :         CompCycRatio = 1.0;
     203             :     }
     204             : 
     205             :     // Initialize the DX coil unit
     206    47491188 :     InitDXCoil(state, DXCoilNum);
     207             : 
     208             :     // Select the correct unit type
     209    47491188 :     switch (state.dataDXCoils->DXCoil(DXCoilNum).DXCoilType_Num) { // Autodesk:OPTIONAL PartLoadRatio, MaxCap used in this block without PRESENT check
     210    36196184 :     case HVAC::CoilDX_CoolingSingleSpeed: {
     211    36196184 :         if (present(CoilCoolingHeatingPLRRatio)) {
     212    30229503 :             CalcDoe2DXCoil(state, DXCoilNum, compressorOp, FirstHVACIteration, PartLoadRatio, fanOp, _, AirFlowRatio, CoilCoolingHeatingPLRRatio);
     213             :         } else {
     214     5966681 :             CalcDoe2DXCoil(state, DXCoilNum, compressorOp, FirstHVACIteration, PartLoadRatio, fanOp, _, AirFlowRatio);
     215             :         }
     216    36196184 :     } break;
     217     5887090 :     case HVAC::CoilDX_HeatingEmpirical: {
     218     5887090 :         CalcDXHeatingCoil(state, DXCoilNum, PartLoadRatio, fanOp, AirFlowRatio);
     219     5887090 :     } break;
     220      631844 :     case HVAC::CoilDX_HeatPumpWaterHeaterPumped:
     221             :     case HVAC::CoilDX_HeatPumpWaterHeaterWrapped: {
     222             :         //   call the HPWHDXCoil routine to calculate water side performance set up the DX coil info for air-side calcs
     223      631844 :         CalcHPWHDXCoil(state, DXCoilNum, PartLoadRatio);
     224             :         //    CALL CalcDoe2DXCoil(state, DXCoilNum, compressorOp, FirstHVACIteration,PartLoadRatio), perform air-side calculations
     225      631844 :         CalcDoe2DXCoil(state, DXCoilNum, HVAC::CompressorOp::On, FirstHVACIteration, PartLoadRatio, fanOp);
     226      631844 :     } break;
     227     1704059 :     case HVAC::CoilVRF_Cooling: {
     228     1704059 :         CalcVRFCoolingCoil(state, DXCoilNum, HVAC::CompressorOp::On, FirstHVACIteration, PartLoadRatio, fanOp, CompCycRatio, _, AirFlowRatio, MaxCap);
     229     1704059 :     } break;
     230     1704059 :     case HVAC::CoilVRF_Heating: {
     231     1704059 :         CalcDXHeatingCoil(state, DXCoilNum, PartLoadRatio, fanOp, AirFlowRatio, MaxCap);
     232     1704059 :     } break;
     233      683976 :     case HVAC::CoilVRF_FluidTCtrl_Cooling: {
     234      683976 :         CalcVRFCoolingCoil_FluidTCtrl(state, DXCoilNum, HVAC::CompressorOp::On, FirstHVACIteration, PartLoadRatio, fanOp, CompCycRatio, _, _);
     235      683976 :     } break;
     236      683976 :     case HVAC::CoilVRF_FluidTCtrl_Heating: {
     237      683976 :         CalcVRFHeatingCoil_FluidTCtrl(state, compressorOp, DXCoilNum, PartLoadRatio, fanOp, _, MaxCap);
     238      683976 :     } break;
     239           0 :     default: {
     240           0 :         ShowSevereError(state, format("Error detected in DX Coil={}", CompName));
     241           0 :         ShowContinueError(state, format("Invalid DX Coil Type={}", state.dataDXCoils->DXCoil(DXCoilNum).DXCoilType));
     242           0 :         ShowFatalError(state, "Preceding condition causes termination.");
     243           0 :     } break;
     244             :     }
     245             : 
     246             :     // Update the unit outlet nodes
     247    47491188 :     UpdateDXCoil(state, DXCoilNum);
     248             : 
     249             :     // Report the result of the simulation
     250    47491188 :     ReportDXCoil(state, DXCoilNum);
     251    47491188 : }
     252             : 
     253    15913849 : void SimDXCoilMultiSpeed(EnergyPlusData &state,
     254             :                          std::string_view CompName, // name of the fan coil unit
     255             :                          Real64 const SpeedRatio,   // = (CompressorSpeed - CompressorSpeedMin) /
     256             :                          Real64 const CycRatio,     // cycling part load ratio for variable speed
     257             :                          int &CompIndex,
     258             :                          ObjexxFCL::Optional_int_const SpeedNum,       // Speed number for multispeed cooling coil onlyn
     259             :                          ObjexxFCL::Optional<HVAC::FanOp const> fanOp, // Fan operation mode
     260             :                          HVAC::CompressorOp compressorOp,              // Compressor on/off; 1=on, 0=off
     261             :                          ObjexxFCL::Optional_int_const SingleMode      // Single mode operation Yes/No; 1=Yes, 0=No
     262             : )
     263             : {
     264             : 
     265             :     // SUBROUTINE INFORMATION:
     266             :     //       AUTHOR         Fred Buhl
     267             :     //       DATE WRITTEN   September 2002
     268             :     //       MODIFIED       Lixing Gu, Sep. 2007
     269             : 
     270             :     // PURPOSE OF THIS SUBROUTINE:
     271             :     // Manages the simulation of a multi speed DX coil.
     272             : 
     273             :     // Using/Aliasing
     274             : 
     275             :     // Locals
     276             :     // SUBROUTINE ARGUMENT DEFINITIONS:
     277             :     //   (CompressorSpeedMax - CompressorSpeedMin)
     278             :     // for variable speed or 2 speed compressors
     279             :     // or 2 speed compressors
     280             : 
     281             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
     282             :     int DXCoilNum;      // index of fan coil unit being simulated
     283             :     int SingleModeOper; // SingleMode Operation
     284             : 
     285             :     // First time SimDXCoil is called, get the input for all the DX coils (condensing units)
     286    15913849 :     if (state.dataDXCoils->GetCoilsInputFlag) {
     287           0 :         GetDXCoils(state);
     288           0 :         state.dataDXCoils->GetCoilsInputFlag = false; // Set GetInputFlag false so you don't get coil inputs again
     289             :     }
     290             : 
     291             :     //  find correct DX Coil
     292             : 
     293    15913849 :     if (CompIndex == 0) {
     294           0 :         DXCoilNum = Util::FindItemInList(CompName, state.dataDXCoils->DXCoil);
     295           0 :         if (DXCoilNum == 0) {
     296           0 :             ShowFatalError(state, format("DX Coil not found={}", CompName));
     297             :         }
     298           0 :         CompIndex = DXCoilNum;
     299             :     } else {
     300    15913849 :         DXCoilNum = CompIndex;
     301    15913849 :         if (DXCoilNum > state.dataDXCoils->NumDXCoils || DXCoilNum < 1) {
     302           0 :             ShowFatalError(state,
     303           0 :                            format("SimDXCoilMultiSpeed: Invalid CompIndex passed={}, Number of DX Coils={}, Coil name={}",
     304             :                                   DXCoilNum,
     305           0 :                                   state.dataDXCoils->NumDXCoils,
     306             :                                   CompName));
     307             :         }
     308    15913849 :         if (state.dataDXCoils->CheckEquipName(DXCoilNum)) {
     309         138 :             if (!CompName.empty() && CompName != state.dataDXCoils->DXCoil(DXCoilNum).Name) {
     310           0 :                 ShowFatalError(state,
     311           0 :                                format("SimDXCoilMultiSpeed: Invalid CompIndex passed={}, Coil name={}, stored Coil Name for that index={}",
     312             :                                       DXCoilNum,
     313             :                                       CompName,
     314           0 :                                       state.dataDXCoils->DXCoil(DXCoilNum).Name));
     315             :             }
     316         138 :             state.dataDXCoils->CheckEquipName(DXCoilNum) = false;
     317             :         }
     318             :     }
     319             : 
     320    15913849 :     if (present(SingleMode)) {
     321     9026329 :         SingleModeOper = SingleMode;
     322             :     } else {
     323     6887520 :         SingleModeOper = 0;
     324             :     }
     325             : 
     326             :     // Initialize the DX coil unit
     327    15913849 :     InitDXCoil(state, DXCoilNum);
     328             : 
     329             :     // Select the correct unit type
     330    15913849 :     switch (state.dataDXCoils->DXCoil(DXCoilNum).DXCoilType_Num) {
     331     2186570 :     case HVAC::CoilDX_CoolingTwoSpeed: {
     332     2186570 :         CalcMultiSpeedDXCoil(state, DXCoilNum, SpeedRatio, CycRatio);
     333     2186570 :     } break;
     334     6868303 :     case HVAC::CoilDX_MultiSpeedCooling: {
     335     6868303 :         if (present(SpeedNum))
     336     6868303 :             CalcMultiSpeedDXCoilCooling(state,
     337             :                                         DXCoilNum,
     338             :                                         SpeedRatio,
     339             :                                         CycRatio,
     340             :                                         SpeedNum,
     341             :                                         fanOp,
     342             :                                         compressorOp,
     343             :                                         SingleModeOper); // Autodesk:OPTIONAL fanOp, CompressorOp used without PRESENT check
     344             : 
     345     6868303 :     } break;
     346     6858976 :     case HVAC::CoilDX_MultiSpeedHeating: {
     347     6858976 :         if (present(SpeedNum))
     348     6858976 :             CalcMultiSpeedDXCoilHeating(state,
     349             :                                         DXCoilNum,
     350             :                                         SpeedRatio,
     351             :                                         CycRatio,
     352             :                                         SpeedNum,
     353             :                                         fanOp,
     354             :                                         SingleModeOper); // Autodesk:OPTIONAL fanOp used without PRESENT check
     355             : 
     356     6858976 :     } break;
     357           0 :     default: {
     358           0 :         ShowSevereError(state, format("Error detected in DX Coil={}", CompName));
     359           0 :         ShowContinueError(state, format("Invalid DX Coil Type={}", state.dataDXCoils->DXCoil(DXCoilNum).DXCoilType));
     360           0 :         ShowFatalError(state, "Preceding condition causes termination.");
     361           0 :     } break;
     362             :     }
     363             : 
     364             :     // Update the unit outlet nodes
     365    15913849 :     UpdateDXCoil(state, DXCoilNum);
     366             : 
     367             :     // Report the result of the simulation
     368    15913849 :     ReportDXCoil(state, DXCoilNum);
     369    15913849 : }
     370             : 
     371      130449 : void SimDXCoilMultiMode(EnergyPlusData &state,
     372             :                         std::string_view CompName,                              // name of the fan coil unit
     373             :                         [[maybe_unused]] HVAC::CompressorOp const compressorOp, // compressor operation; 1=on, 0=off !unused1208
     374             :                         bool const FirstHVACIteration,                          // true if first hvac iteration
     375             :                         Real64 const PartLoadRatio,                             // part load ratio
     376             :                         HVAC::CoilMode const DehumidMode,                       // dehumidification mode (0=normal, 1=enhanced)
     377             :                         int &CompIndex,
     378             :                         HVAC::FanOp const fanOp // allows parent object to control fan mode
     379             : )
     380             : {
     381             : 
     382             :     // SUBROUTINE INFORMATION:
     383             :     //       AUTHOR         M. J. Witte (based on SimDXCoilMultiSpeed by Fred Buhl)
     384             :     //       DATE WRITTEN   February 2005
     385             :     //       MODIFIED       April 2010, Chandan sharma, added basin heater
     386             : 
     387             :     // PURPOSE OF THIS SUBROUTINE:
     388             :     // Manages the simulation of a DX coil with multiple performance modes, such as
     389             :     // multiple stages, or sub-cool reheat for humidity control.
     390             : 
     391             :     // Using/Aliasing
     392             : 
     393             :     // SUBROUTINE PARAMETER DEFINITIONS:
     394             :     static constexpr std::string_view RoutineName("SimDXCoilMultiMode");
     395             : 
     396             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
     397             :     int DXCoilNum; // index of coil being simulated
     398             :     int PerfMode;  // Performance mode for MultiMode DX coil; Always 1 for other coil types
     399             :     // 1-2=normal mode: 1=stage 1 only, 2=stage 1&2
     400             :     // 3-4=enhanced dehumidification mode: 3=stage 1 only, 4=stage 1&2
     401             :     Real64 AirMassFlow; // Dry air mass flow rate through coil [kg/s]
     402             : 
     403             :     Real64 S1OutletAirTemp;     // Stage 1   Outlet air dry bulb temp [C]
     404             :     Real64 S1OutletAirHumRat;   // Stage 1   Outlet air humidity ratio [kgWater/kgDryAir]
     405             :     Real64 S1OutletAirEnthalpy; // Stage 1   Outlet air enthalpy
     406             :     Real64 S1PLR;               // Stage 1   Ratio of actual sensible cooling load to
     407             :     //           steady-state sensible cooling capacity
     408             :     Real64 S1TotalCoolingEnergyRate; // Stage 1   Total cooling rate [W]
     409             :     Real64 S1SensCoolingEnergyRate;  // Stage 1   Sensible cooling rate [W]
     410             :     Real64 S1LatCoolingEnergyRate;   // Stage 1   Latent cooling rate [W]
     411             :     Real64 S1ElecCoolingPower;       // Stage 1   Electric power input [W]
     412      130449 :     Real64 S1RuntimeFraction(0.0);   // Stage 1   Run time fraction (overlaps with stage1&2 run time)
     413             :     Real64 S1EvapCondPumpElecPower;  // Stage 1   Evaporative condenser pump electric power input [W]
     414             :     Real64 S1EvapWaterConsumpRate;   // Stage 1   Evap condenser water consumption rate [m3/s]
     415             :     Real64 S1CrankcaseHeaterPower;   // Stage 1   Report variable for average crankcase heater power [W]
     416             :     Real64 S1FFullLoadOutAirTemp;    // Stage 1   Full load outlet temperature [C]
     417             :     Real64 S1FullLoadOutAirHumRat;   // Stage 1   Full load outlet humidity ratio [kgWater/kgDryAir]
     418             : 
     419             :     Real64 S12OutletAirTemp;     // Stage 1&2 Outlet air dry bulb temp [C]
     420             :     Real64 S12OutletAirHumRat;   // Stage 1&2 Outlet air humidity ratio [kgWater/kgDryAir]
     421             :     Real64 S12OutletAirEnthalpy; // Stage 1&2 Outlet air enthalpy
     422             :     //                                       !           steady-state sensible cooling capacity
     423             :     Real64 S12TotalCoolingEnergyRate; // Stage 1&2 Total cooling rate [W]
     424             :     Real64 S12SensCoolingEnergyRate;  // Stage 1&2 Sensible cooling rate [W]
     425             :     Real64 S12LatCoolingEnergyRate;   // Stage 1&2 Latent cooling rate [W]
     426             :     Real64 S12ElecCoolingPower;       // Stage 1&2 Electric power input [W]
     427             :     Real64 S12ElecCoolFullLoadPower;  // Stage 1&2 Electric power input at full load (PLR=1) [W]
     428      130449 :     Real64 S12RuntimeFraction(0.0);   // Stage 1&2 Run time fraction (overlaps with stage1 run time)
     429             :     Real64 S12EvapCondPumpElecPower;  // Stage 1&2 Evaporative condenser pump electric power input [W]
     430             :     Real64 S12EvapWaterConsumpRate;   // Stage 1&2 Evap condenser water consumption rate [m3/s]
     431             :     Real64 S12CrankcaseHeaterPower;   // Stage 1&2 Report variable for average crankcase heater power [W]
     432             :     Real64 S2PLR;                     // Stage 2   Ratio of actual sensible cooling load to
     433             :     //           steady-state sensible cooling capacity
     434             :     Real64 TSat;      // calculation to avoid calling psych routines twice
     435             :     Real64 NodePress; // Pressure at condenser inlet node (Pa)
     436             : 
     437             :     // First time SimDXCoil is called, get the input for all the DX coils (condensing units)
     438      130449 :     if (state.dataDXCoils->GetCoilsInputFlag) {
     439           0 :         GetDXCoils(state);
     440           0 :         state.dataDXCoils->GetCoilsInputFlag = false; // Set GetInputFlag false so you don't get coil inputs again
     441             :     }
     442             : 
     443             :     //  find correct DX Coil
     444      130449 :     if (CompIndex == 0) {
     445           2 :         DXCoilNum = Util::FindItemInList(CompName, state.dataDXCoils->DXCoil);
     446           2 :         if (DXCoilNum == 0) {
     447           0 :             ShowFatalError(state, format("DX Coil not found={}", CompName));
     448             :         }
     449           2 :         CompIndex = DXCoilNum;
     450             :     } else {
     451      130447 :         DXCoilNum = CompIndex;
     452      130447 :         if (DXCoilNum > state.dataDXCoils->NumDXCoils || DXCoilNum < 1) {
     453           0 :             ShowFatalError(state,
     454           0 :                            format("SimDXCoilMultiMode: Invalid CompIndex passed={}, Number of DX Coils={}, Coil name={}",
     455             :                                   DXCoilNum,
     456           0 :                                   state.dataDXCoils->NumDXCoils,
     457             :                                   CompName));
     458             :         }
     459      130447 :         if (state.dataDXCoils->CheckEquipName(DXCoilNum)) {
     460          11 :             if ((CompName != "") && (CompName != state.dataDXCoils->DXCoil(DXCoilNum).Name)) {
     461           0 :                 ShowFatalError(state,
     462           0 :                                format("SimDXCoilMultiMode: Invalid CompIndex passed={}, Coil name={}, stored Coil Name for that index={}",
     463             :                                       DXCoilNum,
     464             :                                       CompName,
     465           0 :                                       state.dataDXCoils->DXCoil(DXCoilNum).Name));
     466             :             }
     467          11 :             state.dataDXCoils->CheckEquipName(DXCoilNum) = false;
     468             :         }
     469             :     }
     470             : 
     471             :     // Initialize the DX coil unit
     472      130449 :     InitDXCoil(state, DXCoilNum);
     473             : 
     474      130449 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
     475             :     // Select the correct unit type
     476      130449 :     if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl) {
     477             :         // Initialize local variables
     478      130449 :         S1RuntimeFraction = 0.0;
     479      130449 :         S1OutletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
     480      130449 :         S1OutletAirHumRat = thisDXCoil.InletAirHumRat;
     481      130449 :         S1OutletAirTemp = thisDXCoil.InletAirTemp;
     482      130449 :         S1ElecCoolingPower = 0.0;
     483      130449 :         S1TotalCoolingEnergyRate = 0.0;
     484      130449 :         S1SensCoolingEnergyRate = 0.0;
     485      130449 :         S1LatCoolingEnergyRate = 0.0;
     486      130449 :         S1CrankcaseHeaterPower = 0.0;
     487      130449 :         S1EvapWaterConsumpRate = 0.0;
     488      130449 :         S1EvapCondPumpElecPower = 0.0;
     489             : 
     490      130449 :         S12RuntimeFraction = 0.0;
     491      130449 :         S12OutletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
     492      130449 :         S12OutletAirHumRat = thisDXCoil.InletAirHumRat;
     493      130449 :         S12OutletAirTemp = thisDXCoil.InletAirTemp;
     494      130449 :         S12ElecCoolingPower = 0.0;
     495      130449 :         S12TotalCoolingEnergyRate = 0.0;
     496      130449 :         S12SensCoolingEnergyRate = 0.0;
     497      130449 :         S12LatCoolingEnergyRate = 0.0;
     498      130449 :         S12CrankcaseHeaterPower = 0.0;
     499      130449 :         S12EvapWaterConsumpRate = 0.0;
     500      130449 :         S12EvapCondPumpElecPower = 0.0;
     501             : 
     502      130449 :         thisDXCoil.DehumidificationMode = DehumidMode;
     503      130449 :         if ((int)DehumidMode > thisDXCoil.NumDehumidModes) {
     504           0 :             ShowFatalError(state,
     505           0 :                            format("{} \"{}\" - Requested enhanced dehumidification mode not available.", thisDXCoil.DXCoilType, thisDXCoil.Name));
     506             :         }
     507             : 
     508             :         // If a single-stage coil OR If part load is zero,
     509             :         // run stage 1 at zero part load to set leaving conditions
     510      130449 :         if ((thisDXCoil.NumCapacityStages == 1) || (PartLoadRatio <= 0.0)) {
     511             :             // Run stage 1 at its part load
     512       78555 :             PerfMode = (int)DehumidMode * 2 + 1; // This.  This is not good.  Don't do math on enums.
     513       78555 :             CalcDoe2DXCoil(state, DXCoilNum, HVAC::CompressorOp::On, FirstHVACIteration, PartLoadRatio, fanOp, PerfMode);
     514       78555 :             S1PLR = PartLoadRatio;
     515       78555 :             S2PLR = 0.0;
     516             :         } else {
     517             :             // If a two-stage coil
     518             :             // Run stage 1 at full load
     519       51894 :             PerfMode = (int)DehumidMode * 2 + 1;
     520       51894 :             CalcDoe2DXCoil(state, DXCoilNum, HVAC::CompressorOp::On, FirstHVACIteration, 1.0, fanOp, PerfMode);
     521       51894 :             S1SensCoolingEnergyRate = thisDXCoil.SensCoolingEnergyRate;
     522       51894 :             if (S1SensCoolingEnergyRate > 0.0) {
     523       51894 :                 S1PLR = PartLoadRatio;
     524             :             } else {
     525           0 :                 S1PLR = 0.0;
     526             :             }
     527             :             // Run stage 1+2 at full load
     528       51894 :             if (thisDXCoil.NumCapacityStages >= 2) {
     529       51894 :                 PerfMode = (int)DehumidMode * 2 + 2;
     530       51894 :                 CalcDoe2DXCoil(state, DXCoilNum, HVAC::CompressorOp::On, FirstHVACIteration, 1.0, fanOp, PerfMode);
     531       51894 :                 S12SensCoolingEnergyRate = thisDXCoil.SensCoolingEnergyRate;
     532       51894 :                 S12ElecCoolFullLoadPower = thisDXCoil.ElecCoolingPower;
     533             :             }
     534             : 
     535             :             // Determine run-time fractions for each stage based on sensible capacities
     536             :             //   Relationships:
     537             :             //     Stage 1   PLR1=   Load/Cap1
     538             :             //     Stage1+2  PLR12=  Load/Cap12
     539             :             //     Stage 2   PLR2=   (Load-Cap1)/(Cap2)
     540             :             //     PLR = Load/(Cap1+Cap2)
     541             :             //     Load= PLR*(Cap1+Cap2)
     542             :             //     PLR1= MIN(1,(PLR*(Cap1+Cap2)/Cap1))
     543             :             //     PLR2= MIN(1,((PLR*(Cap1+Cap2)-Cap1)/Cap2))
     544             : 
     545       51894 :             if (S1SensCoolingEnergyRate > 0.0) {
     546       51894 :                 S1PLR = PartLoadRatio * S12SensCoolingEnergyRate / S1SensCoolingEnergyRate;
     547             :             } else {
     548           0 :                 S1PLR = 0.0;
     549             :             }
     550       51894 :             S1PLR = min(1.0, S1PLR);
     551       51894 :             S1PLR = max(0.0, S1PLR);
     552       51894 :             if ((S12SensCoolingEnergyRate - S1SensCoolingEnergyRate) > 0.0) {
     553       51894 :                 S2PLR = (PartLoadRatio * S12SensCoolingEnergyRate - S1SensCoolingEnergyRate) / (S12SensCoolingEnergyRate - S1SensCoolingEnergyRate);
     554             :             } else {
     555           0 :                 S2PLR = 0.0;
     556             :             }
     557       51894 :             S2PLR = min(1.0, S2PLR);
     558       51894 :             S2PLR = max(0.0, S2PLR);
     559             : 
     560             :             // Run stage 1 at its part load
     561       51894 :             PerfMode = (int)DehumidMode * 2 + 1;
     562       51894 :             CalcDoe2DXCoil(state, DXCoilNum, HVAC::CompressorOp::On, FirstHVACIteration, S1PLR, fanOp, PerfMode);
     563             :         }
     564             :         // For stage-1 only operation, all outputs are set by CalcDoe2DXCoil.
     565             :         // No further adjustments are necessary.
     566             : 
     567             :         // Run stage 2 if needed and available
     568      130449 :         if ((S2PLR > 0.0) && (thisDXCoil.NumCapacityStages >= 2)) {
     569             :             // Store stage 1 outputs
     570       46420 :             S1RuntimeFraction = thisDXCoil.CoolingCoilRuntimeFraction;
     571       46420 :             S1OutletAirEnthalpy = thisDXCoil.OutletAirEnthalpy;
     572       46420 :             S1OutletAirHumRat = thisDXCoil.OutletAirHumRat;
     573       46420 :             S1OutletAirTemp = thisDXCoil.OutletAirTemp;
     574       46420 :             S1ElecCoolingPower = thisDXCoil.ElecCoolingPower;
     575       46420 :             S1TotalCoolingEnergyRate = thisDXCoil.TotalCoolingEnergyRate;
     576       46420 :             S1SensCoolingEnergyRate = thisDXCoil.SensCoolingEnergyRate;
     577       46420 :             S1LatCoolingEnergyRate = thisDXCoil.LatCoolingEnergyRate;
     578       46420 :             S1CrankcaseHeaterPower = thisDXCoil.CrankcaseHeaterPower;
     579       46420 :             S1EvapWaterConsumpRate = thisDXCoil.EvapWaterConsumpRate;
     580       46420 :             S1EvapCondPumpElecPower = thisDXCoil.EvapCondPumpElecPower;
     581             : 
     582             :             // Save first stage full load outlet conditions to pass to heat recovery
     583       46420 :             S1FFullLoadOutAirTemp = state.dataDXCoils->DXCoilFullLoadOutAirTemp(DXCoilNum);
     584       46420 :             S1FullLoadOutAirHumRat = state.dataDXCoils->DXCoilFullLoadOutAirHumRat(DXCoilNum);
     585             : 
     586             :             // Run stage 1+2 at its part load
     587       46420 :             PerfMode = (int)DehumidMode * 2 + 2;
     588       46420 :             CalcDoe2DXCoil(state, DXCoilNum, HVAC::CompressorOp::On, FirstHVACIteration, S2PLR, fanOp, PerfMode);
     589       46420 :             S12RuntimeFraction = thisDXCoil.CoolingCoilRuntimeFraction;
     590       46420 :             S12OutletAirEnthalpy = thisDXCoil.OutletAirEnthalpy;
     591       46420 :             S12OutletAirHumRat = thisDXCoil.OutletAirHumRat;
     592       46420 :             S12OutletAirTemp = thisDXCoil.OutletAirTemp;
     593       46420 :             S12ElecCoolingPower = thisDXCoil.ElecCoolingPower;
     594       46420 :             S12TotalCoolingEnergyRate = thisDXCoil.TotalCoolingEnergyRate;
     595       46420 :             S12SensCoolingEnergyRate = thisDXCoil.SensCoolingEnergyRate;
     596       46420 :             S12LatCoolingEnergyRate = thisDXCoil.LatCoolingEnergyRate;
     597       46420 :             S12CrankcaseHeaterPower = thisDXCoil.CrankcaseHeaterPower;
     598       46420 :             S12EvapWaterConsumpRate = thisDXCoil.EvapWaterConsumpRate;
     599       46420 :             S12EvapCondPumpElecPower = thisDXCoil.EvapCondPumpElecPower;
     600             : 
     601             :             // Determine combined performance
     602       46420 :             thisDXCoil.OutletAirEnthalpy = (1.0 - S2PLR) * S1OutletAirEnthalpy + S2PLR * S12OutletAirEnthalpy;
     603       46420 :             thisDXCoil.OutletAirHumRat = (1.0 - S2PLR) * S1OutletAirHumRat + S2PLR * S12OutletAirHumRat;
     604       46420 :             thisDXCoil.OutletAirTemp = PsyTdbFnHW(thisDXCoil.OutletAirEnthalpy, thisDXCoil.OutletAirHumRat);
     605             :             // Check for saturation error and modify temperature at constant enthalpy
     606       46420 :             if (thisDXCoil.CondenserInletNodeNum(PerfMode) != 0) {
     607           0 :                 NodePress = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(PerfMode)).Press;
     608             :                 // If node is not connected to anything, pressure = default, use weather data
     609           0 :                 if (NodePress == state.dataLoopNodes->DefaultNodeValues.Press) NodePress = state.dataEnvrn->OutBaroPress;
     610           0 :                 TSat = PsyTsatFnHPb(state, thisDXCoil.OutletAirEnthalpy, NodePress, RoutineName);
     611           0 :                 if (thisDXCoil.OutletAirTemp < TSat) {
     612           0 :                     thisDXCoil.OutletAirTemp = TSat;
     613             :                 }
     614           0 :                 thisDXCoil.OutletAirHumRat = PsyWFnTdbH(state, thisDXCoil.OutletAirTemp, thisDXCoil.OutletAirEnthalpy, RoutineName);
     615             :             } else {
     616       46420 :                 TSat = PsyTsatFnHPb(state, thisDXCoil.OutletAirEnthalpy, state.dataEnvrn->OutBaroPress, RoutineName);
     617       46420 :                 if (thisDXCoil.OutletAirTemp < TSat) {
     618           0 :                     thisDXCoil.OutletAirTemp = TSat;
     619             :                 }
     620             :                 //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
     621             :                 //      IF(DXCoil(DXCoilNum)%OutletAirTemp .LT. PsyTsatFnHPb(DXCoil(DXCoilNum)%OutletAirEnthalpy, &
     622             :                 //                 Node(DXCoil(DXCoilNum)%AirInNode)%Press)) THEN
     623             :                 //        DXCoil(DXCoilNum)%OutletAirTemp = PsyTsatFnHPb(DXCoil(DXCoilNum)%OutletAirEnthalpy, &
     624             :                 //                 Node(DXCoil(DXCoilNum)%AirInNode)%Press)
     625       46420 :                 thisDXCoil.OutletAirHumRat = PsyWFnTdbH(state, thisDXCoil.OutletAirTemp, thisDXCoil.OutletAirEnthalpy, RoutineName);
     626             :             }
     627             : 
     628             :             //      DXCoil(DXCoilNum)%ElecCoolingPower = (1-S12RuntimeFraction)*S1ElecCoolingPower &
     629             :             //                                             +S12RuntimeFraction*S12ElecCoolingPower
     630             :             //  S12ElecCoolingPower overstates S1 portion of power, because it is also adjust by S12PLR
     631             :             //  So, must make an adjustment for S12ElecCoolingPower/S12ElecCoolFullLoadPower
     632             :             //  when subtracting off S1ElecCoolingPower
     633       46420 :             if (S12ElecCoolFullLoadPower > 0.0) {
     634       46420 :                 thisDXCoil.ElecCoolingPower =
     635       46420 :                     S1RuntimeFraction * S1ElecCoolingPower +
     636       46420 :                     S12RuntimeFraction * (S12ElecCoolingPower - S1ElecCoolingPower * S12ElecCoolingPower / S12ElecCoolFullLoadPower);
     637             :             } else {
     638           0 :                 thisDXCoil.ElecCoolingPower = 0.0;
     639             :             }
     640             : 
     641       46420 :             thisDXCoil.CoolingCoilRuntimeFraction = S1RuntimeFraction;
     642             : 
     643       46420 :             AirMassFlow = thisDXCoil.InletAirMassFlowRate;
     644       46420 :             CalcComponentSensibleLatentOutput(AirMassFlow,
     645             :                                               thisDXCoil.InletAirTemp,
     646             :                                               thisDXCoil.InletAirHumRat,
     647             :                                               thisDXCoil.OutletAirTemp,
     648             :                                               thisDXCoil.OutletAirHumRat,
     649       46420 :                                               thisDXCoil.SensCoolingEnergyRate,
     650       46420 :                                               thisDXCoil.LatCoolingEnergyRate,
     651       46420 :                                               thisDXCoil.TotalCoolingEnergyRate);
     652             : 
     653       46420 :             thisDXCoil.EvapWaterConsumpRate = (1.0 - S12RuntimeFraction) * S1EvapWaterConsumpRate + S12RuntimeFraction * S12EvapWaterConsumpRate;
     654       46420 :             thisDXCoil.EvapCondPumpElecPower = (1.0 - S12RuntimeFraction) * S1EvapCondPumpElecPower + S12RuntimeFraction * S12EvapCondPumpElecPower;
     655             : 
     656             :             // Stage 1 runtime sets the crankcase heater power
     657       46420 :             thisDXCoil.CrankcaseHeaterPower = S1CrankcaseHeaterPower;
     658             : 
     659       46420 :             state.dataDXCoils->DXCoilOutletTemp(DXCoilNum) = thisDXCoil.OutletAirTemp;
     660       46420 :             state.dataDXCoils->DXCoilOutletHumRat(DXCoilNum) = thisDXCoil.OutletAirHumRat;
     661             : 
     662             :             //     calculate average full load outlet conditions for second stage operation
     663       46420 :             state.dataDXCoils->DXCoilFullLoadOutAirTemp(DXCoilNum) =
     664       46420 :                 (1.0 - S2PLR) * S1FFullLoadOutAirTemp + S2PLR * state.dataDXCoils->DXCoilFullLoadOutAirTemp(DXCoilNum);
     665       46420 :             state.dataDXCoils->DXCoilFullLoadOutAirHumRat(DXCoilNum) =
     666       46420 :                 (1.0 - S2PLR) * S1FullLoadOutAirHumRat + S2PLR * state.dataDXCoils->DXCoilFullLoadOutAirHumRat(DXCoilNum);
     667             : 
     668             :         } // End if stage 2 is operating
     669             : 
     670             :         //   set the part load ratio and heat reclaim capacity for use by desuperheater heating coils
     671      130449 :         thisDXCoil.PartLoadRatio = S1PLR;
     672      130449 :         state.dataDXCoils->DXCoilPartLoadRatio(DXCoilNum) = S1PLR;
     673             : 
     674             :         //   Calculation for heat reclaim needs to be corrected to use compressor power (not including condenser fan power)
     675      130449 :         state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).AvailCapacity = thisDXCoil.TotalCoolingEnergyRate + thisDXCoil.ElecCoolingPower;
     676             : 
     677      130449 :         thisDXCoil.CoolingCoilStg2RuntimeFrac = S12RuntimeFraction;
     678             : 
     679             :         //   Calculate basin heater power
     680      130449 :         CalcBasinHeaterPowerForMultiModeDXCoil(state, DXCoilNum, DehumidMode);
     681             :     } else {
     682           0 :         ShowSevereError(state, format("Error detected in DX Coil={}", CompName));
     683           0 :         ShowContinueError(state, format("Invalid DX Coil Type={}", thisDXCoil.DXCoilType));
     684           0 :         ShowFatalError(state, "Preceding condition causes termination.");
     685             :     }
     686             : 
     687             :     // Update the unit outlet nodes
     688      130449 :     UpdateDXCoil(state, DXCoilNum);
     689             : 
     690             :     // Report the result of the simulation
     691      130449 :     ReportDXCoil(state, DXCoilNum);
     692      130449 : }
     693             : 
     694         247 : void GetDXCoils(EnergyPlusData &state)
     695             : {
     696             : 
     697             :     // SUBROUTINE INFORMATION:
     698             :     //       AUTHOR         Fred Buhl
     699             :     //       DATE WRITTEN   May 2000
     700             :     //       MODIFIED       Aug 2000, Don Shirey, Sept 2000, Feb/Oct 2001, Sept 2003, Jan/July 2004
     701             :     //                      Feb 2005, M. J. Witte, GARD Analytics, Inc., Add new coil type COIL:DX:MultiMode:CoolingEmpirical:
     702             :     //                      May 2005, Rich Raustad, FSEC, Added COIL:DX:HeatPumpWaterHeater
     703             :     //                      Jun 2007, L. Gu, FSEC, Added new coil type COIL:DX:MULTISPEED:COOLING and COIL:DX:MULTISPEED:HEATING
     704             :     //                      Apr 2010, Chandan Sharma, FSEC, added basin heater inputs
     705             :     //                      Jul 2015, RP Zhang, XF Pang, LBNL, Added new coil type for VRF-FluidTemperatureControl Model
     706             : 
     707             :     // PURPOSE OF THIS SUBROUTINE:
     708             :     // Obtains input data for DX coils and stores it in DX coil data structure
     709             : 
     710             :     // METHODOLOGY EMPLOYED:
     711             :     // Uses "Get" routines to read in data.
     712             : 
     713             :     // Using/Aliasing
     714             :     using BranchNodeConnections::TestCompSet;
     715             :     using Curve::checkCurveIsNormalizedToOne;
     716             :     using Curve::CurveValue;
     717             :     using Curve::GetCurveIndex;
     718             :     using DataSizing::AutoSize;
     719             :     using EMSManager::ManageEMS;
     720             : 
     721             :     using GlobalNames::VerifyUniqueCoilName;
     722             :     using NodeInputManager::GetOnlySingleNode;
     723             :     using OutAirNodeManager::CheckOutAirNodeNumber;
     724             :     using ScheduleManager::GetScheduleIndex;
     725             :     using WaterManager::SetupTankDemandComponent;
     726             :     using WaterManager::SetupTankSupplyComponent;
     727             : 
     728             :     // SUBROUTINE PARAMETER DEFINITIONS:
     729             :     static constexpr std::string_view RoutineName("GetDXCoils: "); // include trailing blank space
     730         247 :     constexpr Real64 minOATCompDXCooling = -25.0;                  // min OAT for compressor operation for DX cooling coils
     731             : 
     732             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
     733             :     int DXCoilIndex;                 // loop index
     734             :     int DXCoilNum;                   // current DX coil number
     735             :     int NumAlphas;                   // Number of alphas in input
     736             :     int NumNumbers;                  // Number of numeric items in input
     737         247 :     Array1D_string Alphas2;          // Alpha input items for object
     738         247 :     Array1D<Real64> Numbers2;        // Numeric input items for object
     739         247 :     Array1D_string cAlphaFields2;    // Alpha field names
     740         247 :     Array1D_string cNumericFields2;  // Numeric field names
     741         247 :     Array1D_bool lAlphaBlanks2;      // Logical array, alpha field input BLANK = .TRUE.
     742         247 :     Array1D_bool lNumericBlanks2;    // Logical array, numeric field input BLANK = .TRUE.
     743             :     int NumAlphas2;                  // Number of alphas in input for performance object
     744             :     int NumNumbers2;                 // Number of numeric items in input for performance object
     745             :     int IOStatus;                    // Input status returned from GetObjectItem
     746         247 :     bool ErrorsFound(false);         // Set to true if errors in input, fatal at end of routine
     747             :     int DXHPWaterHeaterCoilNum;      // Loop index for 1,NumDXHeatPumpWaterHeaterCoils
     748             :     int CapacityStageNum;            // Loop index for 1,Number of capacity stages
     749             :     int DehumidModeNum;              // Loop index for 1,Number of enhanced dehumidification modes
     750             :     int PerfModeNum;                 // Performance mode index
     751             :     int PerfObjectNum;               // Item number for performance object
     752             :     int AlphaIndex;                  // Index for current alpha field
     753         247 :     std::string CurrentModuleObject; // Object type for getting and error messages
     754         247 :     std::string PerfObjectType;      // Performance object type for getting and error messages
     755         247 :     std::string PerfObjectName;      // Performance object name for getting and error messages
     756             :     Real64 InletAirTemp;             // Used to pass proper inlet air temp to HPWH DX coil performance curves
     757             :     Real64 InletWaterTemp;           // Used to pass proper inlet water temp to HPWH DX coil performance curves
     758             :     int I;                           // Index of speeds
     759             :     Real64 CurveVal;                 // Used to verify modifier curves equal 1 at rated conditions
     760         247 :     Array1D_string Alphas;           // Alpha input items for object
     761         247 :     Array1D_string cAlphaFields;     // Alpha field names
     762         247 :     Array1D_string cNumericFields;   // Numeric field names
     763         247 :     Array1D<Real64> Numbers;         // Numeric input items for object
     764         247 :     Array1D_bool lAlphaBlanks;       // Logical array, alpha field input BLANK = .TRUE.
     765         247 :     Array1D_bool lNumericBlanks;     // Logical array, numeric field input BLANK = .TRUE.
     766         247 :     int MaxNumbers(0);               // Maximum number of numeric input fields
     767         247 :     int MaxAlphas(0);                // Maximum number of alpha input fields
     768         247 :     int TotalArgs(0);                // Total number of alpha and numeric arguments (max) for a
     769             :     //   certain object in the input file
     770             :     Real64 MinCurveVal; // used for testing PLF curve output
     771             :     Real64 MinCurvePLR; // used for testing PLF curve output
     772             :     Real64 MaxCurveVal; // used for testing PLF curve output
     773             :     Real64 MaxCurvePLR; // used for testing PLF curve output
     774             :     Real64 CurveInput;  // index used for testing PLF curve output
     775             : 
     776             :     // find number of each type of DX coil and calculate the total number
     777         247 :     state.dataDXCoils->NumDoe2DXCoils = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Coil:Cooling:DX:SingleSpeed");
     778         247 :     state.dataDXCoils->NumDXHeatingCoils = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Coil:Heating:DX:SingleSpeed");
     779         247 :     state.dataDXCoils->NumDXMulSpeedCoils = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Coil:Cooling:DX:TwoSpeed");
     780         494 :     state.dataDXCoils->NumDXMulModeCoils =
     781         247 :         state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Coil:Cooling:DX:TwoStageWithHumidityControlMode");
     782         494 :     state.dataDXCoils->NumDXHeatPumpWaterHeaterPumpedCoils =
     783         247 :         state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, HVAC::cAllCoilTypes(HVAC::CoilDX_HeatPumpWaterHeaterPumped));
     784         494 :     state.dataDXCoils->NumDXHeatPumpWaterHeaterWrappedCoils =
     785         247 :         state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, HVAC::cAllCoilTypes(HVAC::CoilDX_HeatPumpWaterHeaterWrapped));
     786         247 :     state.dataDXCoils->NumDXMulSpeedCoolCoils = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Coil:Cooling:DX:MultiSpeed");
     787         247 :     state.dataDXCoils->NumDXMulSpeedHeatCoils = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Coil:Heating:DX:MultiSpeed");
     788         494 :     state.dataDXCoils->NumVRFCoolingCoils =
     789         247 :         state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, HVAC::cAllCoilTypes(HVAC::CoilVRF_Cooling));
     790         494 :     state.dataDXCoils->NumVRFHeatingCoils =
     791         247 :         state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, HVAC::cAllCoilTypes(HVAC::CoilVRF_Heating));
     792         494 :     state.dataDXCoils->NumVRFCoolingFluidTCtrlCoils =
     793         247 :         state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, HVAC::cAllCoilTypes(HVAC::CoilVRF_FluidTCtrl_Cooling));
     794         494 :     state.dataDXCoils->NumVRFHeatingFluidTCtrlCoils =
     795         247 :         state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, HVAC::cAllCoilTypes(HVAC::CoilVRF_FluidTCtrl_Heating));
     796             : 
     797         247 :     state.dataDXCoils->NumDXCoils = state.dataDXCoils->NumDoe2DXCoils + state.dataDXCoils->NumDXHeatingCoils + state.dataDXCoils->NumDXMulSpeedCoils +
     798         247 :                                     state.dataDXCoils->NumDXMulModeCoils + state.dataDXCoils->NumDXHeatPumpWaterHeaterPumpedCoils +
     799         247 :                                     state.dataDXCoils->NumDXHeatPumpWaterHeaterWrappedCoils + state.dataDXCoils->NumDXMulSpeedCoolCoils +
     800         247 :                                     state.dataDXCoils->NumDXMulSpeedHeatCoils + state.dataDXCoils->NumVRFCoolingCoils +
     801         247 :                                     state.dataDXCoils->NumVRFHeatingCoils + state.dataDXCoils->NumVRFCoolingFluidTCtrlCoils +
     802         247 :                                     state.dataDXCoils->NumVRFHeatingFluidTCtrlCoils;
     803             : 
     804             :     // Determine max number of alpha and numeric arguments for all objects being read, in order to allocate local arrays
     805         247 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(state, "Coil:Cooling:DX:SingleSpeed", TotalArgs, NumAlphas, NumNumbers);
     806         247 :     MaxNumbers = NumNumbers;
     807         247 :     MaxAlphas = NumAlphas;
     808         247 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(state, "Coil:Heating:DX:SingleSpeed", TotalArgs, NumAlphas, NumNumbers);
     809         247 :     MaxNumbers = max(MaxNumbers, NumNumbers);
     810         247 :     MaxAlphas = max(MaxAlphas, NumAlphas);
     811         247 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(state, "Coil:Cooling:DX:TwoSpeed", TotalArgs, NumAlphas, NumNumbers);
     812         247 :     MaxNumbers = max(MaxNumbers, NumNumbers);
     813         247 :     MaxAlphas = max(MaxAlphas, NumAlphas);
     814         247 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(
     815             :         state, "Coil:Cooling:DX:TwoStageWithHumidityControlMode", TotalArgs, NumAlphas, NumNumbers);
     816         247 :     MaxNumbers = max(MaxNumbers, NumNumbers);
     817         247 :     MaxAlphas = max(MaxAlphas, NumAlphas);
     818         494 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(
     819         247 :         state, HVAC::cAllCoilTypes(HVAC::CoilDX_HeatPumpWaterHeaterPumped), TotalArgs, NumAlphas, NumNumbers);
     820         247 :     MaxNumbers = max(MaxNumbers, NumNumbers);
     821         247 :     MaxAlphas = max(MaxAlphas, NumAlphas);
     822         494 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(
     823         247 :         state, HVAC::cAllCoilTypes(HVAC::CoilDX_HeatPumpWaterHeaterWrapped), TotalArgs, NumAlphas, NumNumbers);
     824         247 :     MaxNumbers = max(MaxNumbers, NumNumbers);
     825         247 :     MaxAlphas = max(MaxAlphas, NumAlphas);
     826         247 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(state, "Coil:Cooling:DX:MultiSpeed", TotalArgs, NumAlphas, NumNumbers);
     827         247 :     MaxNumbers = max(MaxNumbers, NumNumbers);
     828         247 :     MaxAlphas = max(MaxAlphas, NumAlphas);
     829         247 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(state, "Coil:Heating:DX:MultiSpeed", TotalArgs, NumAlphas, NumNumbers);
     830         247 :     MaxNumbers = max(MaxNumbers, NumNumbers);
     831         247 :     MaxAlphas = max(MaxAlphas, NumAlphas);
     832         494 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(
     833         247 :         state, HVAC::cAllCoilTypes(HVAC::CoilVRF_Cooling), TotalArgs, NumAlphas, NumNumbers);
     834         247 :     MaxNumbers = max(MaxNumbers, NumNumbers);
     835         247 :     MaxAlphas = max(MaxAlphas, NumAlphas);
     836         494 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(
     837         247 :         state, HVAC::cAllCoilTypes(HVAC::CoilVRF_Heating), TotalArgs, NumAlphas, NumNumbers);
     838         247 :     MaxNumbers = max(MaxNumbers, NumNumbers);
     839         247 :     MaxAlphas = max(MaxAlphas, NumAlphas);
     840         494 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(
     841         247 :         state, HVAC::cAllCoilTypes(HVAC::CoilVRF_FluidTCtrl_Cooling), TotalArgs, NumAlphas, NumNumbers);
     842         247 :     MaxNumbers = max(MaxNumbers, NumNumbers);
     843         247 :     MaxAlphas = max(MaxAlphas, NumAlphas);
     844         494 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(
     845         247 :         state, HVAC::cAllCoilTypes(HVAC::CoilVRF_FluidTCtrl_Heating), TotalArgs, NumAlphas, NumNumbers);
     846         247 :     MaxNumbers = max(MaxNumbers, NumNumbers);
     847         247 :     MaxAlphas = max(MaxAlphas, NumAlphas);
     848         247 :     state.dataInputProcessing->inputProcessor->getObjectDefMaxArgs(state, "CoilPerformance:DX:Cooling", TotalArgs, NumAlphas, NumNumbers);
     849         247 :     MaxNumbers = max(MaxNumbers, NumNumbers);
     850         247 :     MaxAlphas = max(MaxAlphas, NumAlphas);
     851             : 
     852         247 :     Alphas.allocate(MaxAlphas);
     853         247 :     cAlphaFields.allocate(MaxAlphas);
     854         247 :     cNumericFields.allocate(MaxNumbers);
     855         247 :     Numbers.dimension(MaxNumbers, 0.0);
     856         247 :     lAlphaBlanks.dimension(MaxAlphas, true);
     857         247 :     lNumericBlanks.dimension(MaxNumbers, true);
     858             : 
     859         247 :     Alphas2.allocate(MaxAlphas);
     860         247 :     cAlphaFields2.allocate(MaxAlphas);
     861         247 :     cNumericFields2.allocate(MaxNumbers);
     862         247 :     Numbers2.dimension(MaxNumbers, 0.0);
     863         247 :     lAlphaBlanks2.dimension(MaxAlphas, true);
     864         247 :     lNumericBlanks2.dimension(MaxNumbers, true);
     865             : 
     866             :     // allocate the data structure
     867             : 
     868             :     // Derived types
     869         247 :     state.dataDXCoils->DXCoil.allocate(state.dataDXCoils->NumDXCoils);
     870         247 :     state.dataDXCoils->DXCoilNumericFields.allocate(state.dataDXCoils->NumDXCoils);
     871         247 :     state.dataHeatBal->HeatReclaimDXCoil.allocate(state.dataDXCoils->NumDXCoils);
     872         247 :     state.dataDXCoils->CheckEquipName.dimension(state.dataDXCoils->NumDXCoils, true);
     873             : 
     874             :     // Module level variable arrays
     875         247 :     state.dataDXCoils->DXCoilOutletTemp.allocate(state.dataDXCoils->NumDXCoils);
     876         247 :     state.dataDXCoils->DXCoilOutletHumRat.allocate(state.dataDXCoils->NumDXCoils);
     877         247 :     state.dataDXCoils->DXCoilPartLoadRatio.allocate(state.dataDXCoils->NumDXCoils);
     878         247 :     state.dataDXCoils->DXCoilFanOp.allocate(state.dataDXCoils->NumDXCoils);
     879         247 :     state.dataDXCoils->DXCoilFullLoadOutAirTemp.allocate(state.dataDXCoils->NumDXCoils);
     880         247 :     state.dataDXCoils->DXCoilFullLoadOutAirHumRat.allocate(state.dataDXCoils->NumDXCoils);
     881         247 :     state.dataDXCoils->DXCoilTotalCooling.allocate(state.dataDXCoils->NumDXCoils);
     882         247 :     state.dataDXCoils->DXCoilTotalHeating.allocate(state.dataDXCoils->NumDXCoils);
     883         247 :     state.dataDXCoils->DXCoilCoolInletAirWBTemp.allocate(state.dataDXCoils->NumDXCoils);
     884         247 :     state.dataDXCoils->DXCoilHeatInletAirDBTemp.allocate(state.dataDXCoils->NumDXCoils);
     885         247 :     state.dataDXCoils->DXCoilHeatInletAirWBTemp.allocate(state.dataDXCoils->NumDXCoils);
     886             : 
     887             :     // initialize the module level arrays
     888         247 :     state.dataDXCoils->DXCoilOutletTemp = 0.0;
     889         247 :     state.dataDXCoils->DXCoilOutletHumRat = 0.0;
     890         247 :     state.dataDXCoils->DXCoilPartLoadRatio = 0.0;
     891         247 :     state.dataDXCoils->DXCoilFanOp = HVAC::FanOp::Invalid;
     892         247 :     state.dataDXCoils->DXCoilFullLoadOutAirTemp = 0.0;
     893         247 :     state.dataDXCoils->DXCoilFullLoadOutAirHumRat = 0.0;
     894             : 
     895             :     // initialize the coil counter
     896         247 :     DXCoilNum = 0;
     897             : 
     898             :     // Loop over the Doe2 DX Coils and get & load the data
     899         247 :     CurrentModuleObject = "Coil:Cooling:DX:SingleSpeed";
     900         859 :     for (DXCoilIndex = 1; DXCoilIndex <= state.dataDXCoils->NumDoe2DXCoils; ++DXCoilIndex) {
     901             : 
     902         612 :         state.dataInputProcessing->inputProcessor->getObjectItem(state,
     903             :                                                                  CurrentModuleObject,
     904             :                                                                  DXCoilIndex,
     905             :                                                                  Alphas,
     906             :                                                                  NumAlphas,
     907             :                                                                  Numbers,
     908             :                                                                  NumNumbers,
     909             :                                                                  IOStatus,
     910             :                                                                  lNumericBlanks,
     911             :                                                                  lAlphaBlanks,
     912             :                                                                  cAlphaFields,
     913             :                                                                  cNumericFields);
     914             : 
     915         612 :         ++DXCoilNum;
     916             :         // allocate single performance mode for numeric field strings used for sizing routine
     917         612 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode.allocate(1);
     918         612 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames.allocate(MaxNumbers);
     919         612 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames = cNumericFields;
     920             :         // ErrorsFound will be set to True if problem was found, left untouched otherwise
     921         612 :         VerifyUniqueCoilName(state, CurrentModuleObject, Alphas(1), ErrorsFound, CurrentModuleObject + " Name");
     922             : 
     923         612 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
     924         612 :         thisDXCoil.Name = Alphas(1);
     925             :         // Initialize DataHeatBalance heat reclaim variable name for use by heat reclaim coils
     926         612 :         state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).Name = thisDXCoil.Name;
     927         612 :         state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).SourceType = CurrentModuleObject;
     928         612 :         thisDXCoil.DXCoilType = CurrentModuleObject;
     929         612 :         thisDXCoil.DXCoilType_Num = HVAC::CoilDX_CoolingSingleSpeed;
     930         612 :         thisDXCoil.Schedule = Alphas(2);
     931         612 :         if (lAlphaBlanks(2)) {
     932          81 :             thisDXCoil.SchedPtr = ScheduleManager::ScheduleAlwaysOn;
     933             :         } else {
     934         531 :             thisDXCoil.SchedPtr = GetScheduleIndex(state, Alphas(2)); // convert schedule name to pointer
     935         531 :             if (thisDXCoil.SchedPtr == 0) {
     936           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
     937           0 :                 ShowContinueError(state, format("...{}=\"{}\".", cAlphaFields(2), Alphas(2)));
     938           0 :                 ErrorsFound = true;
     939             :             }
     940             :         }
     941         612 :         thisDXCoil.RatedTotCap(1) = Numbers(1);
     942         612 :         thisDXCoil.RatedSHR(1) = Numbers(2);
     943         612 :         thisDXCoil.RatedCOP(1) = Numbers(3);
     944         612 :         if (thisDXCoil.RatedCOP(1) <= 0.0) {
     945           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
     946           0 :             ShowContinueError(state, format("...{} must be > 0.0, entered value=[{:.2T}].", cNumericFields(3), Numbers(3)));
     947           0 :             ErrorsFound = true;
     948             :         }
     949             : 
     950         612 :         thisDXCoil.RatedAirVolFlowRate(1) = Numbers(4);
     951         612 :         thisDXCoil.FanPowerPerEvapAirFlowRate(1) = Numbers(5);
     952         612 :         thisDXCoil.FanPowerPerEvapAirFlowRate_2023(1) = Numbers(6);
     953             : 
     954         612 :         thisDXCoil.AirInNode = GetOnlySingleNode(state,
     955         612 :                                                  Alphas(3),
     956             :                                                  ErrorsFound,
     957             :                                                  DataLoopNode::ConnectionObjectType::CoilCoolingDXSingleSpeed,
     958         612 :                                                  Alphas(1),
     959             :                                                  DataLoopNode::NodeFluidType::Air,
     960             :                                                  DataLoopNode::ConnectionType::Inlet,
     961             :                                                  NodeInputManager::CompFluidStream::Primary,
     962             :                                                  ObjectIsNotParent);
     963             : 
     964         612 :         thisDXCoil.AirOutNode = GetOnlySingleNode(state,
     965         612 :                                                   Alphas(4),
     966             :                                                   ErrorsFound,
     967             :                                                   DataLoopNode::ConnectionObjectType::CoilCoolingDXSingleSpeed,
     968         612 :                                                   Alphas(1),
     969             :                                                   DataLoopNode::NodeFluidType::Air,
     970             :                                                   DataLoopNode::ConnectionType::Outlet,
     971             :                                                   NodeInputManager::CompFluidStream::Primary,
     972             :                                                   ObjectIsNotParent);
     973             : 
     974         612 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(3), Alphas(4), "Air Nodes");
     975             : 
     976         612 :         thisDXCoil.CCapFTemp(1) = GetCurveIndex(state, Alphas(5)); // convert curve name to number
     977         612 :         if (thisDXCoil.CCapFTemp(1) == 0) {
     978           0 :             if (lAlphaBlanks(5)) {
     979           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
     980           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(5)));
     981             :             } else {
     982           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
     983           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(5), Alphas(5)));
     984             :             }
     985           0 :             ErrorsFound = true;
     986             :         } else {
     987             :             // Verify Curve Object, only legal type is BiQuadratic
     988        1224 :             ErrorsFound |= Curve::CheckCurveDims(state,
     989         612 :                                                  thisDXCoil.CCapFTemp(1), // Curve index
     990             :                                                  {2},                     // Valid dimensions
     991             :                                                  RoutineName,             // Routine name
     992             :                                                  CurrentModuleObject,     // Object Type
     993             :                                                  thisDXCoil.Name,         // Object Name
     994         612 :                                                  cAlphaFields(5));        // Field Name
     995             : 
     996         612 :             if (!ErrorsFound) {
     997         612 :                 checkCurveIsNormalizedToOne(state,
     998        1224 :                                             std::string{RoutineName} + CurrentModuleObject,
     999         612 :                                             thisDXCoil.Name,
    1000         612 :                                             thisDXCoil.CCapFTemp(1),
    1001         612 :                                             cAlphaFields(5),
    1002         612 :                                             Alphas(5),
    1003             :                                             RatedInletWetBulbTemp,
    1004             :                                             RatedOutdoorAirTemp);
    1005             :             }
    1006             :         }
    1007             : 
    1008         612 :         thisDXCoil.CCapFFlow(1) = GetCurveIndex(state, Alphas(6)); // convert curve name to number
    1009         612 :         if (thisDXCoil.CCapFFlow(1) == 0) {
    1010           0 :             if (lAlphaBlanks(6)) {
    1011           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1012           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(6)));
    1013             :             } else {
    1014           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1015           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(6), Alphas(6)));
    1016             :             }
    1017           0 :             ErrorsFound = true;
    1018             :         } else {
    1019             :             // Verify Curve Object, only legal type is Quadratic
    1020        1224 :             ErrorsFound |= Curve::CheckCurveDims(state,
    1021         612 :                                                  thisDXCoil.CCapFFlow(1), // Curve index
    1022             :                                                  {1},                     // Valid dimensions
    1023             :                                                  RoutineName,             // Routine name
    1024             :                                                  CurrentModuleObject,     // Object Type
    1025             :                                                  thisDXCoil.Name,         // Object Name
    1026         612 :                                                  cAlphaFields(6));        // Field Name
    1027             : 
    1028         612 :             if (!ErrorsFound) {
    1029         612 :                 checkCurveIsNormalizedToOne(
    1030        1224 :                     state, std::string{RoutineName} + CurrentModuleObject, thisDXCoil.Name, thisDXCoil.CCapFFlow(1), cAlphaFields(6), Alphas(6), 1.0);
    1031             :             }
    1032             :         }
    1033             : 
    1034         612 :         thisDXCoil.EIRFTemp(1) = GetCurveIndex(state, Alphas(7)); // convert curve name to number
    1035         612 :         if (thisDXCoil.EIRFTemp(1) == 0) {
    1036           0 :             if (lAlphaBlanks(7)) {
    1037           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1038           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(7)));
    1039             :             } else {
    1040           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1041           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(7), Alphas(7)));
    1042             :             }
    1043           0 :             ErrorsFound = true;
    1044             :         } else {
    1045             :             // Verify Curve Object, only legal type is BiQuadratic
    1046        1224 :             ErrorsFound |= Curve::CheckCurveDims(state,
    1047         612 :                                                  thisDXCoil.EIRFTemp(1), // Curve index
    1048             :                                                  {2},                    // Valid dimensions
    1049             :                                                  RoutineName,            // Routine name
    1050             :                                                  CurrentModuleObject,    // Object Type
    1051             :                                                  thisDXCoil.Name,        // Object Name
    1052         612 :                                                  cAlphaFields(7));       // Field Name
    1053             : 
    1054         612 :             if (!ErrorsFound) {
    1055         612 :                 checkCurveIsNormalizedToOne(state,
    1056        1224 :                                             std::string{RoutineName} + CurrentModuleObject,
    1057         612 :                                             thisDXCoil.Name,
    1058         612 :                                             thisDXCoil.EIRFTemp(1),
    1059         612 :                                             cAlphaFields(7),
    1060         612 :                                             Alphas(7),
    1061             :                                             RatedInletWetBulbTemp,
    1062             :                                             RatedOutdoorAirTemp);
    1063             :             }
    1064             :         }
    1065             : 
    1066         612 :         thisDXCoil.EIRFFlow(1) = GetCurveIndex(state, Alphas(8)); // convert curve name to number
    1067         612 :         if (thisDXCoil.EIRFFlow(1) == 0) {
    1068           0 :             if (lAlphaBlanks(8)) {
    1069           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1070           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(8)));
    1071             :             } else {
    1072           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1073           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(8), Alphas(8)));
    1074             :             }
    1075           0 :             ErrorsFound = true;
    1076             :         } else {
    1077             :             // Verify Curve Object, only legal type is Quadratic
    1078        1224 :             ErrorsFound |= Curve::CheckCurveDims(state,
    1079         612 :                                                  thisDXCoil.EIRFFlow(1), // Curve index
    1080             :                                                  {1},                    // Valid dimensions
    1081             :                                                  RoutineName,            // Routine name
    1082             :                                                  CurrentModuleObject,    // Object Type
    1083             :                                                  thisDXCoil.Name,        // Object Name
    1084         612 :                                                  cAlphaFields(8));       // Field Name
    1085             : 
    1086         612 :             if (!ErrorsFound) {
    1087         612 :                 checkCurveIsNormalizedToOne(
    1088        1224 :                     state, std::string{RoutineName} + CurrentModuleObject, thisDXCoil.Name, thisDXCoil.EIRFFlow(1), cAlphaFields(8), Alphas(8), 1.0);
    1089             :             }
    1090             :         }
    1091             : 
    1092         612 :         thisDXCoil.PLFFPLR(1) = GetCurveIndex(state, Alphas(9)); // convert curve name to number
    1093         612 :         if (thisDXCoil.PLFFPLR(1) == 0) {
    1094           0 :             if (lAlphaBlanks(9)) {
    1095           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1096           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(9)));
    1097             :             } else {
    1098           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1099           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(9), Alphas(9)));
    1100             :             }
    1101           0 :             ErrorsFound = true;
    1102             :         } else {
    1103             :             // Verify Curve Object, only legal types are Quadratic or Cubic
    1104        1224 :             ErrorsFound |= Curve::CheckCurveDims(state,
    1105         612 :                                                  thisDXCoil.PLFFPLR(1), // Curve index
    1106             :                                                  {1},                   // Valid dimensions
    1107             :                                                  RoutineName,           // Routine name
    1108             :                                                  CurrentModuleObject,   // Object Type
    1109             :                                                  thisDXCoil.Name,       // Object Name
    1110         612 :                                                  cAlphaFields(9));      // Field Name
    1111             : 
    1112         612 :             if (!ErrorsFound) {
    1113             :                 //     Test PLF curve minimum and maximum. Cap if less than 0.7 or greater than 1.0.
    1114         612 :                 MinCurveVal = 999.0;
    1115         612 :                 MaxCurveVal = -999.0;
    1116         612 :                 CurveInput = 0.0;
    1117       61812 :                 while (CurveInput <= 1.0) {
    1118       61200 :                     CurveVal = CurveValue(state, thisDXCoil.PLFFPLR(1), CurveInput);
    1119       61200 :                     if (CurveVal < MinCurveVal) {
    1120         612 :                         MinCurveVal = CurveVal;
    1121         612 :                         MinCurvePLR = CurveInput;
    1122             :                     }
    1123       61200 :                     if (CurveVal > MaxCurveVal) {
    1124       60408 :                         MaxCurveVal = CurveVal;
    1125       60408 :                         MaxCurvePLR = CurveInput;
    1126             :                     }
    1127       61200 :                     CurveInput += 0.01;
    1128             :                 }
    1129         612 :                 if (MinCurveVal < 0.7) {
    1130           0 :                     ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1131           0 :                     ShowContinueError(state, format("...{}=\"{}\" has out of range values.", cAlphaFields(9), Alphas(9)));
    1132           0 :                     ShowContinueError(state,
    1133           0 :                                       format("...Curve minimum must be >= 0.7, curve min at PLR = {:.2T} is {:.3T}", MinCurvePLR, MinCurveVal));
    1134           0 :                     ShowContinueError(state, "...Setting curve minimum to 0.7 and simulation continues.");
    1135           0 :                     Curve::SetCurveOutputMinValue(state, thisDXCoil.PLFFPLR(1), ErrorsFound, 0.7);
    1136             :                 }
    1137             : 
    1138         612 :                 if (MaxCurveVal > 1.0) {
    1139           0 :                     ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1140           0 :                     ShowContinueError(state, format("...{} = {} has out of range value.", cAlphaFields(9), Alphas(9)));
    1141           0 :                     ShowContinueError(state,
    1142           0 :                                       format("...Curve maximum must be <= 1.0, curve max at PLR = {:.2T} is {:.3T}", MaxCurvePLR, MaxCurveVal));
    1143           0 :                     ShowContinueError(state, "...Setting curve maximum to 1.0 and simulation continues.");
    1144           0 :                     Curve::SetCurveOutputMaxValue(state, thisDXCoil.PLFFPLR(1), ErrorsFound, 1.0);
    1145             :                 }
    1146             :             }
    1147             :         }
    1148             : 
    1149             :         // Set minimum OAT for compressor operation
    1150         612 :         thisDXCoil.MinOATCompressor = Numbers(7);
    1151         612 :         if (NumNumbers < 6)
    1152           0 :             thisDXCoil.MinOATCompressor = minOATCompDXCooling; // input field is after min fields and won't default if field not included
    1153             : 
    1154         612 :         thisDXCoil.Twet_Rated(1) = Numbers(8);
    1155         612 :         thisDXCoil.Gamma_Rated(1) = Numbers(9);
    1156         612 :         thisDXCoil.MaxONOFFCyclesperHour(1) = Numbers(10);
    1157         612 :         thisDXCoil.LatentCapacityTimeConstant(1) = Numbers(11);
    1158             : 
    1159             :         // Numbers (7) through (11) must all be greater than zero to use the latent capacity degradation model
    1160         639 :         if ((Numbers(8) > 0.0 || Numbers(9) > 0.0 || Numbers(10) > 0.0 || Numbers(11) > 0.0) &&
    1161          27 :             (Numbers(8) <= 0.0 || Numbers(9) <= 0.0 || Numbers(10) <= 0.0 || Numbers(11) <= 0.0)) {
    1162           0 :             ShowWarningError(state, format("{}{}=\"{}\":", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1163           0 :             ShowContinueError(state, "...At least one of the four input parameters for the latent capacity degradation model");
    1164           0 :             ShowContinueError(state, "...is set to zero. Therefore, the latent degradation model will not be used for this simulation.");
    1165             :         }
    1166             : 
    1167             :         // outdoor condenser node
    1168         612 :         if (lAlphaBlanks(10)) {
    1169         505 :             thisDXCoil.CondenserInletNodeNum(1) = 0;
    1170             :         } else {
    1171         214 :             thisDXCoil.CondenserInletNodeNum(1) = GetOnlySingleNode(state,
    1172         107 :                                                                     Alphas(10),
    1173             :                                                                     ErrorsFound,
    1174             :                                                                     DataLoopNode::ConnectionObjectType::CoilCoolingDXSingleSpeed,
    1175         107 :                                                                     thisDXCoil.Name,
    1176             :                                                                     DataLoopNode::NodeFluidType::Air,
    1177             :                                                                     DataLoopNode::ConnectionType::OutsideAirReference,
    1178             :                                                                     NodeInputManager::CompFluidStream::Primary,
    1179             :                                                                     ObjectIsNotParent);
    1180             : 
    1181         107 :             if (!CheckOutAirNodeNumber(state, thisDXCoil.CondenserInletNodeNum(1))) {
    1182           0 :                 ShowWarningError(state, format("{}{}=\"{}\", may be invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1183           0 :                 ShowContinueError(
    1184             :                     state,
    1185           0 :                     format("{}=\"{}\", node does not appear in an OutdoorAir:NodeList or as an OutdoorAir:Node.", cAlphaFields(10), Alphas(10)));
    1186           0 :                 ShowContinueError(
    1187             :                     state, "This node needs to be included in an air system or the coil model will not be valid, and the simulation continues");
    1188             :             }
    1189             :         }
    1190             : 
    1191         612 :         if ((Util::SameString(Alphas(11), "AirCooled")) || lAlphaBlanks(11)) {
    1192         610 :             thisDXCoil.CondenserType(1) = DataHeatBalance::RefrigCondenserType::Air;
    1193           2 :         } else if (Util::SameString(Alphas(11), "EvaporativelyCooled")) {
    1194           2 :             thisDXCoil.CondenserType(1) = DataHeatBalance::RefrigCondenserType::Evap;
    1195           2 :             thisDXCoil.ReportEvapCondVars = true;
    1196             :         } else {
    1197           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1198           0 :             ShowContinueError(state, format("...{}=\"{}\":", cAlphaFields(11), Alphas(11)));
    1199           0 :             ShowContinueError(state, "...must be AirCooled or EvaporativelyCooled.");
    1200           0 :             ErrorsFound = true;
    1201             :         }
    1202             : 
    1203         612 :         thisDXCoil.EvapCondEffect(1) = Numbers(12);
    1204         612 :         if (thisDXCoil.EvapCondEffect(1) < 0.0 || thisDXCoil.EvapCondEffect(1) > 1.0) {
    1205           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1206           0 :             ShowContinueError(state, format("...{} cannot be < 0.0 or > 1.0.", cNumericFields(11)));
    1207           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(12)));
    1208           0 :             ErrorsFound = true;
    1209             :         }
    1210             : 
    1211         612 :         thisDXCoil.EvapCondAirFlow(1) = Numbers(13);
    1212         612 :         if (thisDXCoil.EvapCondAirFlow(1) < 0.0 && thisDXCoil.EvapCondAirFlow(1) != AutoSize) {
    1213           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1214           0 :             ShowContinueError(state, format("...{} cannot be < 0.0.", cNumericFields(12)));
    1215           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(13)));
    1216           0 :             ErrorsFound = true;
    1217             :         }
    1218             : 
    1219         612 :         thisDXCoil.EvapCondPumpElecNomPower(1) = Numbers(14);
    1220         612 :         if (thisDXCoil.EvapCondPumpElecNomPower(1) < 0.0 && thisDXCoil.EvapCondPumpElecNomPower(1) != AutoSize) {
    1221           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1222           0 :             ShowContinueError(state, format("...{} cannot be < 0.0.", cNumericFields(13)));
    1223           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(14)));
    1224           0 :             ErrorsFound = true;
    1225             :         }
    1226             : 
    1227             :         // Set crankcase heater capacity
    1228         612 :         thisDXCoil.CrankcaseHeaterCapacity = Numbers(15);
    1229         612 :         if (thisDXCoil.CrankcaseHeaterCapacity < 0.0) {
    1230           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1231           0 :             ShowContinueError(state, format("...{} cannot be < 0.0.", cNumericFields(14)));
    1232           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(15)));
    1233           0 :             ErrorsFound = true;
    1234             :         }
    1235             : 
    1236             :         // Set crankcase heater cutout temperature
    1237         612 :         thisDXCoil.MaxOATCrankcaseHeater = Numbers(16);
    1238             : 
    1239         612 :         if (thisDXCoil.RatedCOP(1) > 0.0) {
    1240         612 :             thisDXCoil.RatedEIR(1) = 1.0 / thisDXCoil.RatedCOP(1);
    1241             :         }
    1242             : 
    1243             :         // A12, \field Crankcase Heater Capacity Function of Outdoor Temperature Curve Name
    1244         612 :         if (!lAlphaBlanks(12)) {
    1245           1 :             thisDXCoil.CrankcaseHeaterCapacityCurveIndex = Curve::GetCurveIndex(state, Alphas(12));
    1246           1 :             ErrorsFound |= Curve::CheckCurveDims(state,
    1247             :                                                  thisDXCoil.CrankcaseHeaterCapacityCurveIndex, // Curve index
    1248             :                                                  {1},                                          // Valid dimensions
    1249             :                                                  RoutineName,                                  // Routine name
    1250             :                                                  CurrentModuleObject,                          // Object Type
    1251             :                                                  thisDXCoil.Name,                              // Object Name
    1252           1 :                                                  cAlphaFields(12));                            // Field Name
    1253             :         }
    1254             : 
    1255             :         // Get Water System tank connections
    1256             :         //  A13, \field Name of Water Storage Tank for Supply
    1257         612 :         thisDXCoil.EvapWaterSupplyName = Alphas(13);
    1258         612 :         if (lAlphaBlanks(13)) {
    1259         612 :             thisDXCoil.EvapWaterSupplyMode = EvapWaterSupply::FromMains;
    1260             :         } else {
    1261           0 :             thisDXCoil.EvapWaterSupplyMode = EvapWaterSupply::FromTank;
    1262           0 :             SetupTankDemandComponent(state,
    1263             :                                      thisDXCoil.Name,
    1264             :                                      CurrentModuleObject,
    1265             :                                      thisDXCoil.EvapWaterSupplyName,
    1266             :                                      ErrorsFound,
    1267           0 :                                      thisDXCoil.EvapWaterSupTankID,
    1268           0 :                                      thisDXCoil.EvapWaterTankDemandARRID);
    1269             :         }
    1270             : 
    1271             :         // A14; \field Name of Water Storage Tank for Condensate Collection
    1272         612 :         thisDXCoil.CondensateCollectName = Alphas(14);
    1273         612 :         if (lAlphaBlanks(14)) {
    1274         612 :             thisDXCoil.CondensateCollectMode = CondensateCollectAction::Discard;
    1275             :         } else {
    1276           0 :             thisDXCoil.CondensateCollectMode = CondensateCollectAction::ToTank;
    1277           0 :             SetupTankSupplyComponent(state,
    1278             :                                      thisDXCoil.Name,
    1279             :                                      CurrentModuleObject,
    1280             :                                      thisDXCoil.CondensateCollectName,
    1281             :                                      ErrorsFound,
    1282           0 :                                      thisDXCoil.CondensateTankID,
    1283           0 :                                      thisDXCoil.CondensateTankSupplyARRID);
    1284             :         }
    1285             : 
    1286             :         //   Basin heater power as a function of temperature must be greater than or equal to 0
    1287         612 :         thisDXCoil.BasinHeaterPowerFTempDiff = Numbers(17);
    1288         612 :         if (Numbers(17) < 0.0) {
    1289           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1290           0 :             ShowContinueError(state, format("...{} must be >= 0.0.", cNumericFields(16)));
    1291           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(17)));
    1292           0 :             ErrorsFound = true;
    1293             :         }
    1294             : 
    1295         612 :         thisDXCoil.BasinHeaterSetPointTemp = Numbers(18);
    1296         612 :         if (thisDXCoil.BasinHeaterPowerFTempDiff > 0.0) {
    1297           3 :             if (NumNumbers < 18) {
    1298           1 :                 thisDXCoil.BasinHeaterSetPointTemp = 2.0;
    1299             :             }
    1300           3 :             if (thisDXCoil.BasinHeaterSetPointTemp < 2.0) {
    1301           0 :                 ShowWarningError(state, format("{}{}=\"{}\", freeze possible", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1302           0 :                 ShowContinueError(state, format("...{} is < 2 {{C}}. Freezing could occur.", cNumericFields(17)));
    1303           0 :                 ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(18)));
    1304             :             }
    1305             :         }
    1306             : 
    1307         612 :         if (!lAlphaBlanks(15)) {
    1308           0 :             thisDXCoil.BasinHeaterSchedulePtr = GetScheduleIndex(state, Alphas(15));
    1309           0 :             if (thisDXCoil.BasinHeaterSchedulePtr == 0) {
    1310           0 :                 ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1311           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(15), Alphas(15)));
    1312           0 :                 ShowContinueError(state, "Basin heater will be available to operate throughout the simulation.");
    1313             :             }
    1314             :         }
    1315             : 
    1316         612 :         if (!lAlphaBlanks(16) && NumAlphas > 15) {
    1317           0 :             thisDXCoil.SHRFTemp(1) = GetCurveIndex(state, Alphas(16)); // convert curve name to number
    1318           0 :             if (thisDXCoil.SHRFTemp(1) == 0) {
    1319           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1320           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(16), Alphas(16)));
    1321             :             } else {
    1322             :                 // Verify Curve Object, only legal type is BiQuadratic
    1323           0 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    1324           0 :                                                      thisDXCoil.SHRFTemp(1), // Curve index
    1325             :                                                      {2},                    // Valid dimensions
    1326             :                                                      RoutineName,            // Routine name
    1327             :                                                      CurrentModuleObject,    // Object Type
    1328             :                                                      thisDXCoil.Name,        // Object Name
    1329           0 :                                                      cAlphaFields(16));      // Field Name
    1330             :             }
    1331             :         }
    1332             : 
    1333         612 :         if (!lAlphaBlanks(17) && NumAlphas > 16) {
    1334           0 :             thisDXCoil.SHRFFlow(1) = GetCurveIndex(state, Alphas(17)); // convert curve name to number
    1335           0 :             if (thisDXCoil.SHRFTemp(1) == 0) {
    1336           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1337           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(17), Alphas(17)));
    1338             :             } else {
    1339             :                 // Verify Curve Object, only legal type is Quadratic and Cubic
    1340           0 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    1341           0 :                                                      thisDXCoil.SHRFFlow(1), // Curve index
    1342             :                                                      {1},                    // Valid dimensions
    1343             :                                                      RoutineName,            // Routine name
    1344             :                                                      CurrentModuleObject,    // Object Type
    1345             :                                                      thisDXCoil.Name,        // Object Name
    1346           0 :                                                      cAlphaFields(17));      // Field Name
    1347             :             }
    1348             :         }
    1349             : 
    1350         612 :         if (thisDXCoil.SHRFTemp(1) > 0 && thisDXCoil.SHRFFlow(1) > 0) {
    1351           0 :             thisDXCoil.UserSHRCurveExists = true;
    1352             :         }
    1353             :         // get User Input flag for ASHRAE Standard 127 Standard Ratings Reporting
    1354         612 :         if (lAlphaBlanks(18)) {
    1355         604 :             thisDXCoil.ASHRAE127StdRprt = false;
    1356             :         } else {
    1357           8 :             if (Alphas(18) == "YES" || Alphas(18) == "Yes") {
    1358           8 :                 thisDXCoil.ASHRAE127StdRprt = true;
    1359             :             } else {
    1360           0 :                 thisDXCoil.ASHRAE127StdRprt = false;
    1361             :             }
    1362             :         }
    1363             :         // A19; \field Zone Name for Condenser Placement
    1364         612 :         if (!lAlphaBlanks(19) && NumAlphas > 18) {
    1365           1 :             thisDXCoil.SecZonePtr = Util::FindItemInList(Alphas(19), state.dataHeatBal->Zone);
    1366             : 
    1367           1 :             if (thisDXCoil.SecZonePtr > 0) {
    1368           1 :                 SetupZoneInternalGain(state,
    1369             :                                       thisDXCoil.SecZonePtr,
    1370             :                                       thisDXCoil.Name,
    1371             :                                       DataHeatBalance::IntGainType::SecCoolingDXCoilSingleSpeed,
    1372             :                                       &thisDXCoil.SecCoilSensibleHeatGainRate);
    1373           1 :                 thisDXCoil.IsSecondaryDXCoilInZone = true;
    1374             :             } else {
    1375           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1376           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(19), Alphas(19)));
    1377             :             }
    1378             :         }
    1379             : 
    1380             :     } // end of the Doe2 DX coil loop
    1381             : 
    1382         247 :     if (ErrorsFound) {
    1383           0 :         ShowFatalError(state,
    1384           0 :                        format("{}Errors found in getting {} input. Preceding condition(s) causes termination.", RoutineName, CurrentModuleObject));
    1385             :     }
    1386             : 
    1387             :     // Loop over the Multimode DX Coils and get & load the data
    1388         247 :     CurrentModuleObject = "Coil:Cooling:DX:TwoStageWithHumidityControlMode";
    1389         258 :     for (DXCoilIndex = 1; DXCoilIndex <= state.dataDXCoils->NumDXMulModeCoils; ++DXCoilIndex) {
    1390             : 
    1391          11 :         state.dataInputProcessing->inputProcessor->getObjectItem(state,
    1392             :                                                                  CurrentModuleObject,
    1393             :                                                                  DXCoilIndex,
    1394             :                                                                  Alphas,
    1395             :                                                                  NumAlphas,
    1396             :                                                                  Numbers,
    1397             :                                                                  NumNumbers,
    1398             :                                                                  IOStatus,
    1399             :                                                                  lNumericBlanks,
    1400             :                                                                  lAlphaBlanks,
    1401             :                                                                  cAlphaFields,
    1402             :                                                                  cNumericFields);
    1403             : 
    1404          11 :         ++DXCoilNum;
    1405             :         // ErrorsFound will be set to True if problem was found, left untouched otherwise
    1406          11 :         VerifyUniqueCoilName(state, CurrentModuleObject, Alphas(1), ErrorsFound, CurrentModuleObject + " Name");
    1407             : 
    1408          11 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    1409          11 :         thisDXCoil.Name = Alphas(1);
    1410             :         // Initialize DataHeatBalance heat reclaim variable name for use by heat reclaim coils
    1411          11 :         state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).Name = thisDXCoil.Name;
    1412          11 :         state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).SourceType = CurrentModuleObject;
    1413          11 :         thisDXCoil.DXCoilType = CurrentModuleObject;
    1414          11 :         thisDXCoil.DXCoilType_Num = HVAC::CoilDX_CoolingTwoStageWHumControl;
    1415          11 :         thisDXCoil.Schedule = Alphas(2);
    1416          11 :         if (lAlphaBlanks(2)) {
    1417           4 :             thisDXCoil.SchedPtr = ScheduleManager::ScheduleAlwaysOn;
    1418             :         } else {
    1419           7 :             thisDXCoil.SchedPtr = GetScheduleIndex(state, Alphas(2)); // convert schedule name to pointer
    1420           7 :             if (thisDXCoil.SchedPtr == 0) {
    1421           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1422           0 :                 ShowContinueError(state, format("...{}=\"{}\".", cAlphaFields(2), Alphas(2)));
    1423           0 :                 ErrorsFound = true;
    1424             :             }
    1425             :         }
    1426             : 
    1427          11 :         thisDXCoil.AirInNode = GetOnlySingleNode(state,
    1428          11 :                                                  Alphas(3),
    1429             :                                                  ErrorsFound,
    1430             :                                                  DataLoopNode::ConnectionObjectType::CoilCoolingDXTwoStageWithHumidityControlMode,
    1431          11 :                                                  Alphas(1),
    1432             :                                                  DataLoopNode::NodeFluidType::Air,
    1433             :                                                  DataLoopNode::ConnectionType::Inlet,
    1434             :                                                  NodeInputManager::CompFluidStream::Primary,
    1435             :                                                  ObjectIsNotParent);
    1436             : 
    1437          11 :         thisDXCoil.AirOutNode = GetOnlySingleNode(state,
    1438          11 :                                                   Alphas(4),
    1439             :                                                   ErrorsFound,
    1440             :                                                   DataLoopNode::ConnectionObjectType::CoilCoolingDXTwoStageWithHumidityControlMode,
    1441          11 :                                                   Alphas(1),
    1442             :                                                   DataLoopNode::NodeFluidType::Air,
    1443             :                                                   DataLoopNode::ConnectionType::Outlet,
    1444             :                                                   NodeInputManager::CompFluidStream::Primary,
    1445             :                                                   ObjectIsNotParent);
    1446             : 
    1447          11 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(3), Alphas(4), "Air Nodes");
    1448             : 
    1449             :         // A5; \field Crankcase Heater Capacity Function of Outdoor Temperature Curve Name
    1450          11 :         if (!lAlphaBlanks(5)) {
    1451           0 :             thisDXCoil.CrankcaseHeaterCapacityCurveIndex = Curve::GetCurveIndex(state, Alphas(5));
    1452           0 :             ErrorsFound |= Curve::CheckCurveDims(state,
    1453             :                                                  thisDXCoil.CrankcaseHeaterCapacityCurveIndex, // Curve index
    1454             :                                                  {1},                                          // Valid dimensions
    1455             :                                                  RoutineName,                                  // Routine name
    1456             :                                                  CurrentModuleObject,                          // Object Type
    1457             :                                                  thisDXCoil.Name,                              // Object Name
    1458           0 :                                                  cAlphaFields(5));                             // Field Name
    1459             :         }
    1460             : 
    1461             :         // Set crankcase heater capacity
    1462          11 :         thisDXCoil.CrankcaseHeaterCapacity = Numbers(1);
    1463          11 :         if (thisDXCoil.CrankcaseHeaterCapacity < 0.0) {
    1464           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1465           0 :             ShowContinueError(state, format("...{} must be >= 0.0, entered value=[{:.2T}].", cNumericFields(1), Numbers(1)));
    1466           0 :             ErrorsFound = true;
    1467             :         }
    1468             : 
    1469             :         // Set crankcase heater cutout temperature
    1470          11 :         thisDXCoil.MaxOATCrankcaseHeater = Numbers(2);
    1471             : 
    1472             :         //  Number of capacity stages
    1473          11 :         thisDXCoil.NumCapacityStages = Numbers(3);
    1474             :         //  Check if requested number of capacity stages exceeds limits
    1475          11 :         if ((thisDXCoil.NumCapacityStages > MaxCapacityStages) || (thisDXCoil.NumCapacityStages < 1)) {
    1476           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1477           0 :             ShowContinueError(state, format("...illegal {} = {}", cNumericFields(3), thisDXCoil.NumCapacityStages));
    1478           0 :             ShowContinueError(state, format("...Valid range is 1 to {}", MaxCapacityStages));
    1479           0 :             ErrorsFound = true;
    1480             :         }
    1481             : 
    1482             :         //  Number of enhanced dehumidification modes
    1483          11 :         thisDXCoil.NumDehumidModes = Numbers(4);
    1484             :         //  Check if requested number of enhanced dehumidification modes exceeds limits
    1485          11 :         if ((thisDXCoil.NumDehumidModes > MaxDehumidModes) || (thisDXCoil.NumDehumidModes < 0)) {
    1486           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1487           0 :             ShowContinueError(state, format("...illegal {} = {}", cNumericFields(4), thisDXCoil.NumDehumidModes));
    1488           0 :             ShowContinueError(state, format("...Valid range is 0 to {}", MaxDehumidModes));
    1489           0 :             ErrorsFound = true;
    1490             :         }
    1491             : 
    1492             :         //  Set starting alpha index for coil performance inputs
    1493          11 :         AlphaIndex = 6;
    1494             :         // allocate performance modes for numeric field strings used for sizing routine
    1495          22 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode.allocate(
    1496          11 :             thisDXCoil.NumDehumidModes * 2 + thisDXCoil.NumCapacityStages * 2); // not sure this math is correct, ask MW
    1497             : 
    1498             :         //  Loop through capacity stages and dehumidification modes
    1499          29 :         for (DehumidModeNum = 0; DehumidModeNum <= thisDXCoil.NumDehumidModes; ++DehumidModeNum) {
    1500          53 :             for (CapacityStageNum = 1; CapacityStageNum <= thisDXCoil.NumCapacityStages; ++CapacityStageNum) {
    1501             :                 //  Check if sufficient number of fields entered
    1502          35 :                 if ((AlphaIndex + 1) > NumAlphas) {
    1503           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1504           0 :                     ShowContinueError(state, "...not enough remaining fields for specified Number of Operating Modes.");
    1505           0 :                     ShowContinueError(state, "...Need additional Coil Performance Object Type and Coil Performance Object Name fields.");
    1506           0 :                     ErrorsFound = true;
    1507             :                 } else {
    1508          35 :                     PerfObjectType = Alphas(AlphaIndex);
    1509          35 :                     PerfObjectName = Alphas(AlphaIndex + 1);
    1510          35 :                     PerfModeNum = DehumidModeNum * 2 + CapacityStageNum;
    1511          35 :                     thisDXCoil.CoilPerformanceType(PerfModeNum) = PerfObjectType;
    1512          35 :                     if (Util::SameString(PerfObjectType, "CoilPerformance:DX:Cooling")) {
    1513          35 :                         thisDXCoil.CoilPerformanceType_Num(PerfModeNum) = HVAC::CoilPerfDX_CoolBypassEmpirical;
    1514             :                     } else {
    1515           0 :                         ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1516           0 :                         ShowContinueError(state, format("...illegal {}=\"{}\".", cAlphaFields(AlphaIndex), PerfObjectType));
    1517           0 :                         ShowContinueError(state, "Must be \"CoilPerformance:DX:Cooling\".");
    1518           0 :                         ErrorsFound = true;
    1519             :                     }
    1520          35 :                     thisDXCoil.CoilPerformanceName(PerfModeNum) = PerfObjectName;
    1521             :                     // Get for CoilPerformance object
    1522          35 :                     PerfObjectNum = state.dataInputProcessing->inputProcessor->getObjectItemNum(state, PerfObjectType, PerfObjectName);
    1523          35 :                     if (PerfObjectNum > 0) {
    1524             : 
    1525          35 :                         state.dataInputProcessing->inputProcessor->getObjectItem(state,
    1526             :                                                                                  PerfObjectType,
    1527             :                                                                                  PerfObjectNum,
    1528             :                                                                                  Alphas2,
    1529             :                                                                                  NumAlphas2,
    1530             :                                                                                  Numbers2,
    1531             :                                                                                  NumNumbers2,
    1532             :                                                                                  IOStatus,
    1533             :                                                                                  lNumericBlanks2,
    1534             :                                                                                  lAlphaBlanks2,
    1535             :                                                                                  cAlphaFields2,
    1536             :                                                                                  cNumericFields2);
    1537             : 
    1538             :                         // allocate performance mode numeric field strings used for sizing routine
    1539          35 :                         state.dataDXCoils->DXCoilNumericFields(DXCoilNum)
    1540          35 :                             .PerfMode(PerfModeNum)
    1541          35 :                             .FieldNames.allocate(NumNumbers2); // use MaxNumbers here??
    1542          35 :                         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(PerfModeNum).FieldNames = cNumericFields2;
    1543             : 
    1544          35 :                         thisDXCoil.RatedTotCap(PerfModeNum) = Numbers2(1);
    1545          35 :                         thisDXCoil.RatedSHR(PerfModeNum) = Numbers2(2);
    1546          35 :                         thisDXCoil.RatedCOP(PerfModeNum) = Numbers2(3);
    1547             :                         // Rated flow is immediately adjusted for bypass fraction if not autosized
    1548          35 :                         thisDXCoil.BypassedFlowFrac(PerfModeNum) = Numbers2(5);
    1549          35 :                         thisDXCoil.RatedAirVolFlowRate(PerfModeNum) = Numbers2(4);
    1550          35 :                         if (thisDXCoil.RatedAirVolFlowRate(PerfModeNum) != AutoSize) {
    1551           7 :                             thisDXCoil.RatedAirVolFlowRate(PerfModeNum) *= (1.0 - thisDXCoil.BypassedFlowFrac(PerfModeNum));
    1552             :                         }
    1553             : 
    1554          35 :                         thisDXCoil.CCapFTemp(PerfModeNum) = GetCurveIndex(state, Alphas2(2)); // convert curve name to number
    1555          35 :                         if (thisDXCoil.CCapFTemp(PerfModeNum) == 0) {
    1556           0 :                             if (lAlphaBlanks2(2)) {
    1557           0 :                                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1558           0 :                                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields2(2)));
    1559             :                             } else {
    1560           0 :                                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1561           0 :                                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields2(2), Alphas2(2)));
    1562             :                             }
    1563           0 :                             ErrorsFound = true;
    1564             :                         } else {
    1565             :                             // Verify Curve Object, only legal type is BiQuadratic
    1566          70 :                             ErrorsFound |= Curve::CheckCurveDims(state,
    1567          35 :                                                                  thisDXCoil.CCapFTemp(PerfModeNum), // Curve index
    1568             :                                                                  {2},                               // Valid dimensions
    1569             :                                                                  RoutineName,                       // Routine name
    1570             :                                                                  CurrentModuleObject,               // Object Type
    1571             :                                                                  thisDXCoil.Name,                   // Object Name
    1572          35 :                                                                  cAlphaFields2(2));                 // Field Name
    1573             : 
    1574          35 :                             if (!ErrorsFound) {
    1575          35 :                                 checkCurveIsNormalizedToOne(state,
    1576          70 :                                                             std::string{RoutineName} + CurrentModuleObject,
    1577          35 :                                                             thisDXCoil.Name,
    1578          35 :                                                             thisDXCoil.CCapFTemp(PerfModeNum),
    1579          35 :                                                             cAlphaFields2(2),
    1580          35 :                                                             Alphas2(2),
    1581             :                                                             RatedInletWetBulbTemp,
    1582             :                                                             RatedOutdoorAirTemp);
    1583             :                             }
    1584             :                         }
    1585             : 
    1586          35 :                         thisDXCoil.CCapFFlow(PerfModeNum) = GetCurveIndex(state, Alphas2(3)); // convert curve name to number
    1587          35 :                         if (thisDXCoil.CCapFFlow(PerfModeNum) == 0) {
    1588           0 :                             if (lAlphaBlanks2(3)) {
    1589           0 :                                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1590           0 :                                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields2(3)));
    1591             :                             } else {
    1592           0 :                                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1593           0 :                                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields2(3), Alphas2(3)));
    1594             :                             }
    1595           0 :                             ErrorsFound = true;
    1596             :                         } else {
    1597             :                             // Verify Curve Object, only legal type is Quadratic
    1598          70 :                             ErrorsFound |= Curve::CheckCurveDims(state,
    1599          35 :                                                                  thisDXCoil.CCapFFlow(PerfModeNum), // Curve index
    1600             :                                                                  {1},                               // Valid dimensions
    1601             :                                                                  RoutineName,                       // Routine name
    1602             :                                                                  CurrentModuleObject,               // Object Type
    1603             :                                                                  thisDXCoil.Name,                   // Object Name
    1604          35 :                                                                  cAlphaFields2(3));                 // Field Name
    1605             : 
    1606          35 :                             if (!ErrorsFound) {
    1607          35 :                                 checkCurveIsNormalizedToOne(state,
    1608          70 :                                                             std::string{RoutineName} + CurrentModuleObject,
    1609          35 :                                                             thisDXCoil.Name,
    1610          35 :                                                             thisDXCoil.CCapFFlow(PerfModeNum),
    1611          35 :                                                             cAlphaFields2(3),
    1612          35 :                                                             Alphas2(3),
    1613             :                                                             1.0);
    1614             :                             }
    1615             :                         }
    1616             : 
    1617          35 :                         thisDXCoil.EIRFTemp(PerfModeNum) = GetCurveIndex(state, Alphas2(4)); // convert curve name to number
    1618          35 :                         if (thisDXCoil.EIRFTemp(PerfModeNum) == 0) {
    1619           0 :                             if (lAlphaBlanks2(4)) {
    1620           0 :                                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1621           0 :                                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields2(4)));
    1622             :                             } else {
    1623           0 :                                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1624           0 :                                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields2(4), Alphas2(4)));
    1625             :                             }
    1626           0 :                             ErrorsFound = true;
    1627             :                         } else {
    1628             :                             // Verify Curve Object, only legal type is BiQuadratic
    1629          70 :                             ErrorsFound |= Curve::CheckCurveDims(state,
    1630          35 :                                                                  thisDXCoil.EIRFTemp(PerfModeNum), // Curve index
    1631             :                                                                  {2},                              // Valid dimensions
    1632             :                                                                  RoutineName,                      // Routine name
    1633             :                                                                  CurrentModuleObject,              // Object Type
    1634             :                                                                  thisDXCoil.Name,                  // Object Name
    1635          35 :                                                                  cAlphaFields2(4));                // Field Name
    1636             : 
    1637          35 :                             if (!ErrorsFound) {
    1638          35 :                                 checkCurveIsNormalizedToOne(state,
    1639          70 :                                                             std::string{RoutineName} + CurrentModuleObject,
    1640          35 :                                                             thisDXCoil.Name,
    1641          35 :                                                             thisDXCoil.EIRFTemp(PerfModeNum),
    1642          35 :                                                             cAlphaFields2(4),
    1643          35 :                                                             Alphas2(4),
    1644             :                                                             RatedInletWetBulbTemp,
    1645             :                                                             RatedOutdoorAirTemp);
    1646             :                             }
    1647             :                         }
    1648             : 
    1649          35 :                         thisDXCoil.EIRFFlow(PerfModeNum) = GetCurveIndex(state, Alphas2(5)); // convert curve name to number
    1650          35 :                         if (thisDXCoil.EIRFFlow(PerfModeNum) == 0) {
    1651           0 :                             if (lAlphaBlanks2(5)) {
    1652           0 :                                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1653           0 :                                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields2(5)));
    1654             :                             } else {
    1655           0 :                                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1656           0 :                                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields2(5), Alphas2(5)));
    1657             :                             }
    1658           0 :                             ErrorsFound = true;
    1659             :                         } else {
    1660             :                             // Verify Curve Object, only legal type is Quadratic
    1661          70 :                             ErrorsFound |= Curve::CheckCurveDims(state,
    1662          35 :                                                                  thisDXCoil.EIRFFlow(PerfModeNum), // Curve index
    1663             :                                                                  {1},                              // Valid dimensions
    1664             :                                                                  RoutineName,                      // Routine name
    1665             :                                                                  CurrentModuleObject,              // Object Type
    1666             :                                                                  thisDXCoil.Name,                  // Object Name
    1667          35 :                                                                  cAlphaFields2(5));                // Field Name
    1668             : 
    1669          35 :                             if (!ErrorsFound) {
    1670          35 :                                 checkCurveIsNormalizedToOne(state,
    1671          70 :                                                             std::string{RoutineName} + CurrentModuleObject,
    1672          35 :                                                             thisDXCoil.Name,
    1673          35 :                                                             thisDXCoil.EIRFFlow(PerfModeNum),
    1674          35 :                                                             cAlphaFields2(5),
    1675          35 :                                                             Alphas2(5),
    1676             :                                                             1.0);
    1677             :                             }
    1678             :                         }
    1679             : 
    1680          35 :                         thisDXCoil.PLFFPLR(PerfModeNum) = GetCurveIndex(state, Alphas2(6)); // convert curve name to number
    1681          35 :                         if (thisDXCoil.PLFFPLR(PerfModeNum) == 0) {
    1682           0 :                             if (lAlphaBlanks2(6)) {
    1683           0 :                                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1684           0 :                                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields2(6)));
    1685             :                             } else {
    1686           0 :                                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1687           0 :                                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields2(6), Alphas2(6)));
    1688             :                             }
    1689           0 :                             ErrorsFound = true;
    1690             :                         } else {
    1691             :                             // Verify Curve Object, only legal types are Quadratic or Cubic
    1692          70 :                             ErrorsFound |= Curve::CheckCurveDims(state,
    1693          35 :                                                                  thisDXCoil.PLFFPLR(PerfModeNum), // Curve index
    1694             :                                                                  {1},                             // Valid dimensions
    1695             :                                                                  RoutineName,                     // Routine name
    1696             :                                                                  CurrentModuleObject,             // Object Type
    1697             :                                                                  thisDXCoil.Name,                 // Object Name
    1698          35 :                                                                  cAlphaFields2(6));               // Field Name
    1699             : 
    1700          35 :                             if (!ErrorsFound) {
    1701             :                                 //             Test PLF curve minimum and maximum. Cap if less than 0.7 or greater than 1.0.
    1702          35 :                                 MinCurveVal = 999.0;
    1703          35 :                                 MaxCurveVal = -999.0;
    1704          35 :                                 CurveInput = 0.0;
    1705        3535 :                                 while (CurveInput <= 1.0) {
    1706        3500 :                                     CurveVal = CurveValue(state, thisDXCoil.PLFFPLR(PerfModeNum), CurveInput);
    1707        3500 :                                     if (CurveVal < MinCurveVal) {
    1708          35 :                                         MinCurveVal = CurveVal;
    1709          35 :                                         MinCurvePLR = CurveInput;
    1710             :                                     }
    1711        3500 :                                     if (CurveVal > MaxCurveVal) {
    1712        3500 :                                         MaxCurveVal = CurveVal;
    1713        3500 :                                         MaxCurvePLR = CurveInput;
    1714             :                                     }
    1715        3500 :                                     CurveInput += 0.01;
    1716             :                                 }
    1717          35 :                                 if (MinCurveVal < 0.7) {
    1718           0 :                                     ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1719           0 :                                     ShowContinueError(state, format("...{} = {} has out of range value.", cAlphaFields2(6), Alphas2(6)));
    1720           0 :                                     ShowContinueError(
    1721             :                                         state,
    1722           0 :                                         format("...Curve minimum must be >= 0.7, curve min at PLR = {:.2T} is {:.3T}", MinCurvePLR, MinCurveVal));
    1723           0 :                                     ShowContinueError(state, "...Setting curve minimum to 0.7 and simulation continues.");
    1724           0 :                                     Curve::SetCurveOutputMinValue(state, thisDXCoil.PLFFPLR(PerfModeNum), ErrorsFound, 0.7);
    1725             :                                 }
    1726             : 
    1727          35 :                                 if (MaxCurveVal > 1.0) {
    1728           0 :                                     ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1729           0 :                                     ShowContinueError(state, format("...{} = {} has out of range value.", cAlphaFields2(6), Alphas2(6)));
    1730           0 :                                     ShowContinueError(
    1731             :                                         state,
    1732           0 :                                         format("...Curve maximum must be <= 1.0, curve max at PLR = {:.2T} is {:.3T}", MaxCurvePLR, MaxCurveVal));
    1733           0 :                                     ShowContinueError(state, "...Setting curve maximum to 1.0 and simulation continues.");
    1734           0 :                                     Curve::SetCurveOutputMaxValue(state, thisDXCoil.PLFFPLR(PerfModeNum), ErrorsFound, 1.0);
    1735             :                                 }
    1736             :                             }
    1737             :                         }
    1738             : 
    1739          35 :                         thisDXCoil.Twet_Rated(PerfModeNum) = Numbers2(6);
    1740          35 :                         thisDXCoil.Gamma_Rated(PerfModeNum) = Numbers2(7);
    1741          35 :                         thisDXCoil.MaxONOFFCyclesperHour(PerfModeNum) = Numbers2(8);
    1742          35 :                         thisDXCoil.LatentCapacityTimeConstant(PerfModeNum) = Numbers2(9);
    1743             :                         // Numbers2 (6) through (9) must all be greater than zero to use the latent capacity degradation model
    1744          35 :                         if ((Numbers2(6) > 0.0 || Numbers2(7) > 0.0 || Numbers2(8) > 0.0 || Numbers2(9) > 0.0) &&
    1745           0 :                             (Numbers2(6) <= 0.0 || Numbers2(7) <= 0.0 || Numbers2(8) <= 0.0 || Numbers2(9) <= 0.0)) {
    1746           0 :                             ShowWarningError(state, format("{}{}=\"{}\":", RoutineName, PerfObjectType, PerfObjectName));
    1747           0 :                             ShowContinueError(state, "...At least one of the four input parameters for the latent capacity degradation model");
    1748           0 :                             ShowContinueError(state,
    1749             :                                               "...is set to zero. Therefore, the latent degradation model will not be used for this simulation.");
    1750             :                         }
    1751             : 
    1752             :                         // outdoor condenser node
    1753          35 :                         if (lAlphaBlanks2(7)) {
    1754          35 :                             thisDXCoil.CondenserInletNodeNum(PerfModeNum) = 0;
    1755             :                         } else {
    1756           0 :                             thisDXCoil.CondenserInletNodeNum(PerfModeNum) =
    1757           0 :                                 GetOnlySingleNode(state,
    1758           0 :                                                   Alphas2(7),
    1759             :                                                   ErrorsFound,
    1760           0 :                                                   (DataLoopNode::ConnectionObjectType)getEnumValue(BranchNodeConnections::ConnectionObjectTypeNamesUC,
    1761           0 :                                                                                                    Util::makeUPPER(PerfObjectType)),
    1762             :                                                   PerfObjectName,
    1763             :                                                   DataLoopNode::NodeFluidType::Air,
    1764             :                                                   DataLoopNode::ConnectionType::OutsideAirReference,
    1765             :                                                   NodeInputManager::CompFluidStream::Primary,
    1766             :                                                   ObjectIsNotParent);
    1767           0 :                             if (!CheckOutAirNodeNumber(state, thisDXCoil.CondenserInletNodeNum(PerfModeNum))) {
    1768           0 :                                 ShowWarningError(state, format("{}{}=\"{}\":", RoutineName, PerfObjectType, PerfObjectName));
    1769           0 :                                 ShowContinueError(state, format("may not be valid {}=\"{}\".", cAlphaFields2(7), Alphas2(7)));
    1770           0 :                                 ShowContinueError(state, "node does not appear in an OutdoorAir:NodeList or as an OutdoorAir:Node.");
    1771           0 :                                 ShowContinueError(state,
    1772             :                                                   "This node needs to be included in an air system or the coil model will not be valid, and the "
    1773             :                                                   "simulation continues");
    1774             :                             }
    1775             :                         }
    1776          35 :                         if ((Util::SameString(Alphas2(8), "AirCooled")) || lAlphaBlanks2(8)) {
    1777          35 :                             thisDXCoil.CondenserType(PerfModeNum) = DataHeatBalance::RefrigCondenserType::Air;
    1778           0 :                         } else if (Util::SameString(Alphas2(8), "EvaporativelyCooled")) {
    1779           0 :                             thisDXCoil.CondenserType(PerfModeNum) = DataHeatBalance::RefrigCondenserType::Evap;
    1780           0 :                             thisDXCoil.ReportEvapCondVars = true;
    1781             :                         } else {
    1782           0 :                             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1783           0 :                             ShowContinueError(state, format("...{}=\"{}\":", cAlphaFields2(8), Alphas2(8)));
    1784           0 :                             ShowContinueError(state, "...must be AirCooled or EvaporativelyCooled.");
    1785           0 :                             ErrorsFound = true;
    1786             :                         }
    1787             : 
    1788          35 :                         thisDXCoil.EvapCondEffect(PerfModeNum) = Numbers2(10);
    1789          35 :                         if (thisDXCoil.EvapCondEffect(PerfModeNum) < 0.0 || thisDXCoil.EvapCondEffect(PerfModeNum) > 1.0) {
    1790           0 :                             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1791           0 :                             ShowContinueError(state, format("...{} cannot be < 0.0 or > 1.0.", cNumericFields2(10)));
    1792           0 :                             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers2(10)));
    1793           0 :                             ErrorsFound = true;
    1794             :                         }
    1795             : 
    1796          35 :                         thisDXCoil.EvapCondAirFlow(PerfModeNum) = Numbers2(11);
    1797          35 :                         if (thisDXCoil.EvapCondAirFlow(PerfModeNum) < 0.0 && thisDXCoil.EvapCondAirFlow(PerfModeNum) != AutoSize) {
    1798           0 :                             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1799           0 :                             ShowContinueError(state, format("...{} cannot be < 0.0.", cNumericFields2(11)));
    1800           0 :                             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers2(11)));
    1801           0 :                             ErrorsFound = true;
    1802             :                         }
    1803             : 
    1804          35 :                         thisDXCoil.EvapCondPumpElecNomPower(PerfModeNum) = Numbers2(12);
    1805          35 :                         if (thisDXCoil.EvapCondPumpElecNomPower(PerfModeNum) < 0.0 && thisDXCoil.EvapCondAirFlow(PerfModeNum) != AutoSize) {
    1806           0 :                             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, PerfObjectType, PerfObjectName));
    1807           0 :                             ShowContinueError(state, format("...{} cannot be less than zero.", cNumericFields2(12)));
    1808           0 :                             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers2(12)));
    1809           0 :                             ErrorsFound = true;
    1810             :                         }
    1811             : 
    1812          35 :                         thisDXCoil.RatedEIR(PerfModeNum) = 1.0 / thisDXCoil.RatedCOP(PerfModeNum);
    1813             : 
    1814             :                         // read in user specified SHR modifer curves
    1815          35 :                         if (!lAlphaBlanks2(9) && NumAlphas2 > 8) {
    1816           0 :                             thisDXCoil.SHRFTemp(PerfModeNum) = GetCurveIndex(state, Alphas2(9)); // convert curve name to number
    1817           0 :                             if (thisDXCoil.SHRFTemp(PerfModeNum) == 0) {
    1818           0 :                                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1819           0 :                                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields2(9), Alphas2(9)));
    1820             :                             } else {
    1821             :                                 // Verify Curve Object, only legal type is BiQuadratic
    1822           0 :                                 ErrorsFound |= Curve::CheckCurveDims(state,
    1823           0 :                                                                      thisDXCoil.SHRFTemp(PerfModeNum), // Curve index
    1824             :                                                                      {2},                              // Valid dimensions
    1825             :                                                                      RoutineName,                      // Routine name
    1826             :                                                                      CurrentModuleObject,              // Object Type
    1827             :                                                                      thisDXCoil.Name,                  // Object Name
    1828           0 :                                                                      cAlphaFields2(9));                // Field Name
    1829             :                             }
    1830             :                         }
    1831             : 
    1832          35 :                         if (!lAlphaBlanks2(10) && NumAlphas2 > 9) {
    1833           0 :                             thisDXCoil.SHRFFlow(PerfModeNum) = GetCurveIndex(state, Alphas2(10)); // convert curve name to number
    1834           0 :                             if (thisDXCoil.SHRFTemp(PerfModeNum) == 0) {
    1835           0 :                                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1836           0 :                                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields2(10), Alphas2(10)));
    1837             :                             } else {
    1838             :                                 // Verify Curve Object, only legal type is BiQuadratic
    1839           0 :                                 ErrorsFound |= Curve::CheckCurveDims(state,
    1840           0 :                                                                      thisDXCoil.SHRFFlow(PerfModeNum), // Curve index
    1841             :                                                                      {1},                              // Valid dimensions
    1842             :                                                                      RoutineName,                      // Routine name
    1843             :                                                                      CurrentModuleObject,              // Object Type
    1844             :                                                                      thisDXCoil.Name,                  // Object Name
    1845           0 :                                                                      cAlphaFields2(10));               // Field Name
    1846             :                             }
    1847             :                         }
    1848          35 :                         if (thisDXCoil.SHRFTemp(PerfModeNum) > 0 && thisDXCoil.SHRFFlow(PerfModeNum) > 0) {
    1849           0 :                             thisDXCoil.UserSHRCurveExists = true;
    1850             :                         } else {
    1851          35 :                             thisDXCoil.UserSHRCurveExists = false;
    1852             :                         }
    1853             : 
    1854             :                     } else { // invalid performance object
    1855           0 :                         ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1856           0 :                         ShowContinueError(state, format("... not found {}=\"{}\".", PerfObjectType, PerfObjectName));
    1857           0 :                         ErrorsFound = true;
    1858             :                     } // end of valid performance object check
    1859          35 :                     AlphaIndex += 2;
    1860             :                 } // end of sufficient number of fields entered check
    1861             :             }     // End of multimode DX capacity stages loop
    1862             :             // Warn if inputs entered for unused capacity stages
    1863          19 :             for (CapacityStageNum = (thisDXCoil.NumCapacityStages + 1); CapacityStageNum <= MaxCapacityStages; ++CapacityStageNum) {
    1864           1 :                 if ((AlphaIndex <= NumAlphas) && ((!Alphas(AlphaIndex).empty()) || (!Alphas(AlphaIndex + 1).empty()))) {
    1865           0 :                     ShowWarningError(state, format("{}{}=\"{}\":", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1866           0 :                     ShowContinueError(state, format("...Capacity Stage {} not active. Therefore,{}", CapacityStageNum, cAlphaFields(AlphaIndex)));
    1867           0 :                     ShowContinueError(state, format("... and {} fields will be ignored.", cAlphaFields(AlphaIndex + 1)));
    1868             :                 }
    1869           1 :                 AlphaIndex += 2;
    1870             :             } // End of unused capacity stages loop
    1871             :         }     // End of multimode DX dehumidification modes loo
    1872             : 
    1873             :         // Get Water System tank connections
    1874             :         //  A14, \field Name of Water Storage Tank for Supply
    1875          11 :         thisDXCoil.EvapWaterSupplyName = Alphas(14);
    1876          11 :         if (lAlphaBlanks(14)) {
    1877          11 :             thisDXCoil.EvapWaterSupplyMode = EvapWaterSupply::FromMains;
    1878             :         } else {
    1879           0 :             thisDXCoil.EvapWaterSupplyMode = EvapWaterSupply::FromTank;
    1880           0 :             SetupTankDemandComponent(state,
    1881             :                                      thisDXCoil.Name,
    1882             :                                      CurrentModuleObject,
    1883             :                                      thisDXCoil.EvapWaterSupplyName,
    1884             :                                      ErrorsFound,
    1885           0 :                                      thisDXCoil.EvapWaterSupTankID,
    1886           0 :                                      thisDXCoil.EvapWaterTankDemandARRID);
    1887             :         }
    1888             : 
    1889             :         // A15; \field Name of Water Storage Tank for Condensate Collection
    1890          11 :         thisDXCoil.CondensateCollectName = Alphas(15);
    1891          11 :         if (lAlphaBlanks(15)) {
    1892          11 :             thisDXCoil.CondensateCollectMode = CondensateCollectAction::Discard;
    1893             :         } else {
    1894           0 :             thisDXCoil.CondensateCollectMode = CondensateCollectAction::ToTank;
    1895           0 :             SetupTankSupplyComponent(state,
    1896             :                                      thisDXCoil.Name,
    1897             :                                      CurrentModuleObject,
    1898             :                                      thisDXCoil.CondensateCollectName,
    1899             :                                      ErrorsFound,
    1900           0 :                                      thisDXCoil.CondensateTankID,
    1901           0 :                                      thisDXCoil.CondensateTankSupplyARRID);
    1902             :         }
    1903             : 
    1904             :         // Set minimum OAT for compressor operation
    1905          11 :         thisDXCoil.MinOATCompressor = Numbers(5);
    1906          11 :         if (NumNumbers < 5)
    1907           8 :             thisDXCoil.MinOATCompressor = minOATCompDXCooling; // input field is after min fields and won't default if field not included
    1908             : 
    1909             :         // Basin heater power as a function of temperature must be greater than or equal to 0
    1910          11 :         thisDXCoil.BasinHeaterPowerFTempDiff = Numbers(6);
    1911          11 :         if (Numbers(6) < 0.0) {
    1912           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1913           0 :             ShowContinueError(state, format("...{} must be >= 0.", cNumericFields(6)));
    1914           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(6)));
    1915           0 :             ErrorsFound = true;
    1916             :         }
    1917             : 
    1918          11 :         thisDXCoil.BasinHeaterSetPointTemp = Numbers(7);
    1919          11 :         if (thisDXCoil.BasinHeaterPowerFTempDiff > 0.0) {
    1920           0 :             if (NumNumbers < 7) {
    1921           0 :                 thisDXCoil.BasinHeaterSetPointTemp = 2.0;
    1922             :             }
    1923           0 :             if (thisDXCoil.BasinHeaterSetPointTemp < 2.0) {
    1924           0 :                 ShowWarningError(state, format("{}{}=\"{}\", freeze possible", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1925           0 :                 ShowContinueError(state, format("...{} is < 2 {{C}}. Freezing could occur.", cNumericFields(7)));
    1926           0 :                 ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(7)));
    1927             :             }
    1928             :         }
    1929             : 
    1930          11 :         if (!lAlphaBlanks(16)) {
    1931           0 :             thisDXCoil.BasinHeaterSchedulePtr = GetScheduleIndex(state, Alphas(16));
    1932           0 :             if (thisDXCoil.BasinHeaterSchedulePtr == 0) {
    1933           0 :                 ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1934           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(16), Alphas(16)));
    1935           0 :                 ShowContinueError(state, "Basin heater will be available to operate throughout the simulation.");
    1936             :             }
    1937             :         }
    1938             : 
    1939             :     } // end of the Multimode DX coil loop
    1940             : 
    1941         247 :     if (ErrorsFound) {
    1942           0 :         ShowFatalError(state,
    1943           0 :                        format("{}Errors found in getting {} input.  Preceding condition(s) causes termination.", RoutineName, CurrentModuleObject));
    1944             :     }
    1945             : 
    1946             :     //************* Read Heat Pump (DX Heating Coil) Input **********
    1947         247 :     CurrentModuleObject = "Coil:Heating:DX:SingleSpeed";
    1948         322 :     for (DXCoilIndex = 1; DXCoilIndex <= state.dataDXCoils->NumDXHeatingCoils; ++DXCoilIndex) {
    1949             : 
    1950          75 :         ++DXCoilNum;
    1951             : 
    1952          75 :         state.dataInputProcessing->inputProcessor->getObjectItem(state,
    1953             :                                                                  CurrentModuleObject,
    1954             :                                                                  DXCoilIndex,
    1955             :                                                                  Alphas,
    1956             :                                                                  NumAlphas,
    1957             :                                                                  Numbers,
    1958             :                                                                  NumNumbers,
    1959             :                                                                  IOStatus,
    1960             :                                                                  lNumericBlanks,
    1961             :                                                                  lAlphaBlanks,
    1962             :                                                                  cAlphaFields,
    1963             :                                                                  cNumericFields);
    1964             : 
    1965             :         // allocate single performance mode for numeric field strings used for sizing routine
    1966          75 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode.allocate(1);
    1967          75 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames.allocate(MaxNumbers);
    1968          75 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames = cNumericFields;
    1969             :         // ErrorsFound will be set to True if problem was found, left untouched otherwise
    1970          75 :         VerifyUniqueCoilName(state, CurrentModuleObject, Alphas(1), ErrorsFound, CurrentModuleObject + " Name");
    1971             : 
    1972          75 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    1973          75 :         thisDXCoil.Name = Alphas(1);
    1974          75 :         thisDXCoil.DXCoilType = CurrentModuleObject;
    1975          75 :         thisDXCoil.DXCoilType_Num = HVAC::CoilDX_HeatingEmpirical;
    1976          75 :         thisDXCoil.Schedule = Alphas(2);
    1977          75 :         if (lAlphaBlanks(2)) {
    1978          22 :             thisDXCoil.SchedPtr = ScheduleManager::ScheduleAlwaysOn;
    1979             :         } else {
    1980          53 :             thisDXCoil.SchedPtr = GetScheduleIndex(state, Alphas(2)); // convert schedule name to pointer
    1981          53 :             if (thisDXCoil.SchedPtr == 0) {
    1982           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    1983           0 :                 ShowContinueError(state, format("...{}=\"{}\".", cAlphaFields(2), Alphas(2)));
    1984           0 :                 ErrorsFound = true;
    1985             :             }
    1986             :         }
    1987             : 
    1988          75 :         thisDXCoil.AirInNode = GetOnlySingleNode(state,
    1989          75 :                                                  Alphas(3),
    1990             :                                                  ErrorsFound,
    1991             :                                                  DataLoopNode::ConnectionObjectType::CoilHeatingDXSingleSpeed,
    1992          75 :                                                  Alphas(1),
    1993             :                                                  DataLoopNode::NodeFluidType::Air,
    1994             :                                                  DataLoopNode::ConnectionType::Inlet,
    1995             :                                                  NodeInputManager::CompFluidStream::Primary,
    1996             :                                                  ObjectIsNotParent);
    1997             : 
    1998          75 :         thisDXCoil.AirOutNode = GetOnlySingleNode(state,
    1999          75 :                                                   Alphas(4),
    2000             :                                                   ErrorsFound,
    2001             :                                                   DataLoopNode::ConnectionObjectType::CoilHeatingDXSingleSpeed,
    2002          75 :                                                   Alphas(1),
    2003             :                                                   DataLoopNode::NodeFluidType::Air,
    2004             :                                                   DataLoopNode::ConnectionType::Outlet,
    2005             :                                                   NodeInputManager::CompFluidStream::Primary,
    2006             :                                                   ObjectIsNotParent);
    2007             : 
    2008          75 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(3), Alphas(4), "Air Nodes");
    2009             : 
    2010          75 :         thisDXCoil.CCapFTemp(1) = GetCurveIndex(state, Alphas(5)); // convert curve name to number
    2011          75 :         if (thisDXCoil.CCapFTemp(1) == 0) {
    2012           0 :             if (lAlphaBlanks(5)) {
    2013           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2014           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(5)));
    2015             :             } else {
    2016           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2017           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(5), Alphas(5)));
    2018             :             }
    2019           0 :             ErrorsFound = true;
    2020             :         } else {
    2021             :             // only legal types are Quadratic, BiQuadratic and Cubic
    2022         150 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2023          75 :                                                  thisDXCoil.CCapFTemp(1), // Curve index
    2024             :                                                  {1, 2},                  // Valid dimensions  // MULTIPLECURVEDIMS
    2025             :                                                  RoutineName,             // Routine name
    2026             :                                                  CurrentModuleObject,     // Object Type
    2027             :                                                  thisDXCoil.Name,         // Object Name
    2028          75 :                                                  cAlphaFields(5));        // Field Name
    2029             : 
    2030          75 :             if (!ErrorsFound) {
    2031          75 :                 if (state.dataCurveManager->PerfCurve(thisDXCoil.CCapFTemp(1))->numDims == 1) {
    2032          74 :                     checkCurveIsNormalizedToOne(state,
    2033         148 :                                                 std::string{RoutineName} + CurrentModuleObject,
    2034          74 :                                                 thisDXCoil.Name,
    2035          74 :                                                 thisDXCoil.CCapFTemp(1),
    2036          74 :                                                 cAlphaFields(5),
    2037          74 :                                                 Alphas(5),
    2038             :                                                 RatedOutdoorAirTempHeat);
    2039             :                 } else {
    2040           1 :                     checkCurveIsNormalizedToOne(state,
    2041           2 :                                                 std::string{RoutineName} + CurrentModuleObject,
    2042           1 :                                                 thisDXCoil.Name,
    2043           1 :                                                 thisDXCoil.CCapFTemp(1),
    2044           1 :                                                 cAlphaFields(5),
    2045           1 :                                                 Alphas(5),
    2046             :                                                 RatedInletAirTempHeat,
    2047             :                                                 RatedOutdoorAirTempHeat);
    2048             :                 }
    2049             :             }
    2050             :         }
    2051             : 
    2052          75 :         thisDXCoil.CCapFFlow(1) = GetCurveIndex(state, Alphas(6)); // convert curve name to number
    2053          75 :         if (thisDXCoil.CCapFFlow(1) == 0) {
    2054           0 :             if (lAlphaBlanks(6)) {
    2055           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2056           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(6)));
    2057             :             } else {
    2058           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2059           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(6), Alphas(6)));
    2060             :             }
    2061           0 :             ErrorsFound = true;
    2062             :         } else {
    2063             :             // Verify Curve Object, only legal type is Quadratic
    2064         150 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2065          75 :                                                  thisDXCoil.CCapFFlow(1), // Curve index
    2066             :                                                  {1},                     // Valid dimensions
    2067             :                                                  RoutineName,             // Routine name
    2068             :                                                  CurrentModuleObject,     // Object Type
    2069             :                                                  thisDXCoil.Name,         // Object Name
    2070          75 :                                                  cAlphaFields(6));        // Field Name
    2071             : 
    2072          75 :             if (!ErrorsFound) {
    2073          75 :                 checkCurveIsNormalizedToOne(
    2074         150 :                     state, std::string{RoutineName} + CurrentModuleObject, thisDXCoil.Name, thisDXCoil.CCapFFlow(1), cAlphaFields(6), Alphas(6), 1.0);
    2075             :             }
    2076             :         }
    2077             : 
    2078          75 :         thisDXCoil.EIRFTemp(1) = GetCurveIndex(state, Alphas(7)); // convert curve name to number
    2079          75 :         if (thisDXCoil.EIRFTemp(1) == 0) {
    2080           0 :             if (lAlphaBlanks(7)) {
    2081           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2082           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(7)));
    2083             :             } else {
    2084           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2085           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(7), Alphas(7)));
    2086             :             }
    2087           0 :             ErrorsFound = true;
    2088             :         } else {
    2089             :             // only legal types are Quadratic, BiQuadratic and Cubic
    2090         150 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2091          75 :                                                  thisDXCoil.EIRFTemp(1), // Curve index
    2092             :                                                  {1, 2},                 // Valid dimensions  // MULTIPLECURVEDIMS
    2093             :                                                  RoutineName,            // Routine name
    2094             :                                                  CurrentModuleObject,    // Object Type
    2095             :                                                  thisDXCoil.Name,        // Object Name
    2096          75 :                                                  cAlphaFields(7));       // Field Name
    2097             : 
    2098          75 :             if (!ErrorsFound) {
    2099          75 :                 if (state.dataCurveManager->PerfCurve(thisDXCoil.EIRFTemp(1))->numDims == 1) {
    2100          74 :                     checkCurveIsNormalizedToOne(state,
    2101         148 :                                                 std::string{RoutineName} + CurrentModuleObject,
    2102          74 :                                                 thisDXCoil.Name,
    2103          74 :                                                 thisDXCoil.EIRFTemp(1),
    2104          74 :                                                 cAlphaFields(7),
    2105          74 :                                                 Alphas(7),
    2106             :                                                 RatedOutdoorAirTempHeat);
    2107             :                 } else {
    2108           1 :                     checkCurveIsNormalizedToOne(state,
    2109           2 :                                                 std::string{RoutineName} + CurrentModuleObject,
    2110           1 :                                                 thisDXCoil.Name,
    2111           1 :                                                 thisDXCoil.EIRFTemp(1),
    2112           1 :                                                 cAlphaFields(7),
    2113           1 :                                                 Alphas(7),
    2114             :                                                 RatedInletAirTempHeat,
    2115             :                                                 RatedOutdoorAirTempHeat);
    2116             :                 }
    2117             :             }
    2118             :         }
    2119             : 
    2120          75 :         thisDXCoil.EIRFFlow(1) = GetCurveIndex(state, Alphas(8)); // convert curve name to number
    2121          75 :         if (thisDXCoil.EIRFFlow(1) == 0) {
    2122           0 :             if (lAlphaBlanks(8)) {
    2123           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2124           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(8)));
    2125             :             } else {
    2126           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2127           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(8), Alphas(8)));
    2128             :             }
    2129           0 :             ErrorsFound = true;
    2130             :         } else {
    2131             :             // Verify Curve Object, only legal type is Quadratic or Cubic
    2132         150 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2133          75 :                                                  thisDXCoil.EIRFFlow(1), // Curve index
    2134             :                                                  {1},                    // Valid dimensions
    2135             :                                                  RoutineName,            // Routine name
    2136             :                                                  CurrentModuleObject,    // Object Type
    2137             :                                                  thisDXCoil.Name,        // Object Name
    2138          75 :                                                  cAlphaFields(8));       // Field Name
    2139             : 
    2140          75 :             if (!ErrorsFound) {
    2141          75 :                 checkCurveIsNormalizedToOne(
    2142         150 :                     state, std::string{RoutineName} + CurrentModuleObject, thisDXCoil.Name, thisDXCoil.EIRFFlow(1), cAlphaFields(8), Alphas(8), 1.0);
    2143             :             }
    2144             :         }
    2145             : 
    2146          75 :         thisDXCoil.PLFFPLR(1) = GetCurveIndex(state, Alphas(9)); // convert curve name to number
    2147          75 :         if (thisDXCoil.PLFFPLR(1) == 0) {
    2148           0 :             if (lAlphaBlanks(9)) {
    2149           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2150           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(9)));
    2151             :             } else {
    2152           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2153           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(9), Alphas(9)));
    2154             :             }
    2155           0 :             ErrorsFound = true;
    2156             :         } else {
    2157             :             // Verify Curve Object, only legal types are Quadratic or Cubic
    2158         150 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2159          75 :                                                  thisDXCoil.PLFFPLR(1), // Curve index
    2160             :                                                  {1},                   // Valid dimensions
    2161             :                                                  RoutineName,           // Routine name
    2162             :                                                  CurrentModuleObject,   // Object Type
    2163             :                                                  thisDXCoil.Name,       // Object Name
    2164          75 :                                                  cAlphaFields(9));      // Field Name
    2165             : 
    2166          75 :             if (!ErrorsFound) {
    2167             :                 //     Test PLF curve minimum and maximum. Cap if less than 0.7 or greater than 1.0.
    2168          75 :                 MinCurveVal = 999.0;
    2169          75 :                 MaxCurveVal = -999.0;
    2170          75 :                 CurveInput = 0.0;
    2171        7575 :                 while (CurveInput <= 1.0) {
    2172        7500 :                     CurveVal = CurveValue(state, thisDXCoil.PLFFPLR(1), CurveInput);
    2173        7500 :                     if (CurveVal < MinCurveVal) {
    2174          75 :                         MinCurveVal = CurveVal;
    2175          75 :                         MinCurvePLR = CurveInput;
    2176             :                     }
    2177        7500 :                     if (CurveVal > MaxCurveVal) {
    2178        7500 :                         MaxCurveVal = CurveVal;
    2179        7500 :                         MaxCurvePLR = CurveInput;
    2180             :                     }
    2181        7500 :                     CurveInput += 0.01;
    2182             :                 }
    2183          75 :                 if (MinCurveVal < 0.7) {
    2184           0 :                     ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2185           0 :                     ShowContinueError(state, format("...{} = {} has out of range value.", cAlphaFields(9), Alphas(9)));
    2186           0 :                     ShowContinueError(state,
    2187           0 :                                       format("...Curve minimum must be >= 0.7, curve min at PLR = {:.2T} is {:.3T}", MinCurvePLR, MinCurveVal));
    2188           0 :                     ShowContinueError(state, "...Setting curve minimum to 0.7 and simulation continues.");
    2189           0 :                     Curve::SetCurveOutputMinValue(state, thisDXCoil.PLFFPLR(1), ErrorsFound, 0.7);
    2190             :                 }
    2191             : 
    2192          75 :                 if (MaxCurveVal > 1.0) {
    2193           0 :                     ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2194           0 :                     ShowContinueError(state, format("...{} = {} has out of range value.", cAlphaFields(9), Alphas(9)));
    2195           0 :                     ShowContinueError(state,
    2196           0 :                                       format("...Curve maximum must be <= 1.0, curve max at PLR = {:.2T} is {:.3T}", MaxCurvePLR, MaxCurveVal));
    2197           0 :                     ShowContinueError(state, "...Setting curve maximum to 1.0 and simulation continues.");
    2198           0 :                     Curve::SetCurveOutputMaxValue(state, thisDXCoil.PLFFPLR(1), ErrorsFound, 1.0);
    2199             :                 }
    2200             :             }
    2201             :         }
    2202             : 
    2203             :         // Only required for reverse cycle heat pumps
    2204          75 :         thisDXCoil.DefrostEIRFT = GetCurveIndex(state, Alphas(10)); // convert curve name to number
    2205             :         // A11; \field Crankcase Heater Capacity Function of Outdoor Temperature Curve Name
    2206          75 :         if (!lAlphaBlanks(11)) {
    2207           1 :             thisDXCoil.CrankcaseHeaterCapacityCurveIndex = Curve::GetCurveIndex(state, Alphas(11));
    2208           1 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2209             :                                                  thisDXCoil.CrankcaseHeaterCapacityCurveIndex, // Curve index
    2210             :                                                  {1},                                          // Valid dimensions
    2211             :                                                  RoutineName,                                  // Routine name
    2212             :                                                  CurrentModuleObject,                          // Object Type
    2213             :                                                  thisDXCoil.Name,                              // Object Name
    2214           1 :                                                  cAlphaFields(11));                            // Field Name
    2215             :         }
    2216             : 
    2217          75 :         if (Util::SameString(Alphas(12), "ReverseCycle")) {
    2218             : 
    2219          27 :             if (thisDXCoil.DefrostEIRFT == 0) {
    2220           0 :                 if (lAlphaBlanks(10)) {
    2221           0 :                     ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2222           0 :                     ShowContinueError(state, format("...required {} is blank.", cAlphaFields(10)));
    2223           0 :                     ShowContinueError(state, format("...field is required because {} is \"ReverseCycle\".", cAlphaFields(12)));
    2224             :                 } else {
    2225           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2226           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(10), Alphas(10)));
    2227             :                 }
    2228           0 :                 ErrorsFound = true;
    2229             :             } else {
    2230             :                 // Verify Curve Object, only legal type is BiQuadratic
    2231          27 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    2232             :                                                      thisDXCoil.DefrostEIRFT, // Curve index
    2233             :                                                      {2},                     // Valid dimensions
    2234             :                                                      RoutineName,             // Routine name
    2235             :                                                      CurrentModuleObject,     // Object Type
    2236             :                                                      thisDXCoil.Name,         // Object Name
    2237          27 :                                                      cAlphaFields(10));       // Field Name
    2238             : 
    2239          27 :                 if (!ErrorsFound) {
    2240          27 :                     checkCurveIsNormalizedToOne(state,
    2241          54 :                                                 std::string{RoutineName} + CurrentModuleObject,
    2242          27 :                                                 thisDXCoil.Name,
    2243             :                                                 thisDXCoil.DefrostEIRFT,
    2244          27 :                                                 cAlphaFields(10),
    2245          27 :                                                 Alphas(10),
    2246             :                                                 RatedInletAirTempHeat,
    2247             :                                                 RatedOutdoorAirTempHeat);
    2248             :                 }
    2249             :             }
    2250             :         }
    2251             : 
    2252          75 :         if (Util::SameString(Alphas(12), "ReverseCycle")) thisDXCoil.DefrostStrategy = StandardRatings::DefrostStrat::ReverseCycle;
    2253          75 :         if (Util::SameString(Alphas(12), "Resistive")) thisDXCoil.DefrostStrategy = StandardRatings::DefrostStrat::Resistive;
    2254             : 
    2255          75 :         if (thisDXCoil.DefrostStrategy == StandardRatings::DefrostStrat::Invalid) {
    2256           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2257           0 :             ShowContinueError(state, format("...illegal {}=\"{}\".", cAlphaFields(12), Alphas(12)));
    2258           0 :             ShowContinueError(state, "...valid values for this field are ReverseCycle or Resistive.");
    2259           0 :             ErrorsFound = true;
    2260             :         }
    2261             : 
    2262          75 :         if (Util::SameString(Alphas(13), "Timed")) thisDXCoil.DefrostControl = StandardRatings::HPdefrostControl::Timed;
    2263          75 :         if (Util::SameString(Alphas(13), "OnDemand")) thisDXCoil.DefrostControl = StandardRatings::HPdefrostControl::OnDemand;
    2264          75 :         if (thisDXCoil.DefrostControl == StandardRatings::HPdefrostControl::Invalid) {
    2265           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2266           0 :             ShowContinueError(state, format("...illegal {}=\"{}\".", cAlphaFields(13), Alphas(13)));
    2267           0 :             ShowContinueError(state, "...valid values for this field are Timed or OnDemand.");
    2268           0 :             ErrorsFound = true;
    2269             :         }
    2270             : 
    2271          75 :         thisDXCoil.RatedSHR(1) = 1.0;
    2272          75 :         thisDXCoil.RatedTotCap(1) = Numbers(1);
    2273          75 :         thisDXCoil.RatedCOP(1) = Numbers(2);
    2274          75 :         thisDXCoil.RatedAirVolFlowRate(1) = Numbers(3);
    2275          75 :         thisDXCoil.FanPowerPerEvapAirFlowRate(1) = Numbers(4);
    2276          75 :         thisDXCoil.FanPowerPerEvapAirFlowRate_2023(1) = Numbers(5);
    2277             : 
    2278             :         // Set minimum OAT for heat pump compressor operation
    2279          75 :         thisDXCoil.MinOATCompressor = Numbers(6);
    2280             : 
    2281          75 :         thisDXCoil.OATempCompressorOn = Numbers(7);
    2282             : 
    2283          75 :         if (lNumericBlanks(7) || lNumericBlanks(6)) { //??TBD:BPS 6 or 5 | 7 or 6
    2284          74 :             thisDXCoil.OATempCompressorOnOffBlank = true;
    2285             :         } else {
    2286           1 :             thisDXCoil.OATempCompressorOnOffBlank = false;
    2287             :         }
    2288             : 
    2289          75 :         if (thisDXCoil.OATempCompressorOn < thisDXCoil.MinOATCompressor) thisDXCoil.OATempCompressorOn = thisDXCoil.MinOATCompressor;
    2290             : 
    2291             :         // Set maximum outdoor temp for defrost to occur
    2292          75 :         thisDXCoil.MaxOATDefrost = Numbers(8);
    2293             : 
    2294             :         // Set crankcase heater capacity
    2295          75 :         thisDXCoil.CrankcaseHeaterCapacity = Numbers(9);
    2296          75 :         if (thisDXCoil.CrankcaseHeaterCapacity < 0.0) {
    2297           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2298           0 :             ShowContinueError(state, format("...{} cannot be < 0.0.", cNumericFields(8)));
    2299           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(9)));
    2300           0 :             ErrorsFound = true;
    2301             :         }
    2302             : 
    2303             :         // Set crankcase heater cutout temperature
    2304          75 :         thisDXCoil.MaxOATCrankcaseHeater = Numbers(10);
    2305             : 
    2306             :         // Set defrost time period
    2307          75 :         thisDXCoil.DefrostTime = Numbers(11);
    2308          75 :         if (thisDXCoil.DefrostTime == 0.0 && thisDXCoil.DefrostControl == StandardRatings::HPdefrostControl::Timed) {
    2309           0 :             ShowWarningError(state, format("{}{}=\"{}\", ", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2310           0 :             ShowContinueError(state, format("...{} = 0.0 for defrost control = TIMED.", cNumericFields(11)));
    2311             :         }
    2312             : 
    2313             :         // Set defrost capacity (for resistive defrost)
    2314          75 :         thisDXCoil.DefrostCapacity = Numbers(12);
    2315          75 :         if (thisDXCoil.DefrostCapacity == 0.0 && thisDXCoil.DefrostStrategy == StandardRatings::DefrostStrat::Resistive) {
    2316           0 :             ShowWarningError(state, format("{}{}=\"{}\", ", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2317           0 :             ShowContinueError(state, format("...{} = 0.0 for defrost strategy = RESISTIVE.", cNumericFields(12)));
    2318             :         }
    2319             : 
    2320             :         // Set Region number for calculating HSPF
    2321          75 :         thisDXCoil.RegionNum = Numbers(13);
    2322             : 
    2323          75 :         if (lNumericBlanks(13)) {
    2324          74 :             thisDXCoil.RegionNum = 4;
    2325             :         }
    2326             : 
    2327          75 :         thisDXCoil.RatedEIR(1) = 1.0 / thisDXCoil.RatedCOP(1);
    2328             : 
    2329             :         // A14 is optional evaporator node name
    2330          75 :         if (lAlphaBlanks(14)) {
    2331          72 :             thisDXCoil.CondenserInletNodeNum(1) = 0;
    2332             :         } else {
    2333           6 :             thisDXCoil.CondenserInletNodeNum(1) = GetOnlySingleNode(state,
    2334           3 :                                                                     Alphas(14),
    2335             :                                                                     ErrorsFound,
    2336             :                                                                     DataLoopNode::ConnectionObjectType::CoilHeatingDXSingleSpeed,
    2337           3 :                                                                     thisDXCoil.Name,
    2338             :                                                                     DataLoopNode::NodeFluidType::Air,
    2339             :                                                                     DataLoopNode::ConnectionType::OutsideAirReference,
    2340             :                                                                     NodeInputManager::CompFluidStream::Primary,
    2341             :                                                                     ObjectIsNotParent);
    2342             :             // warn if not an outdoor node, but allow
    2343           3 :             if (!CheckOutAirNodeNumber(state, thisDXCoil.CondenserInletNodeNum(1))) {
    2344           0 :                 ShowWarningError(state, format("{}{}=\"{}\", may be invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2345           0 :                 ShowContinueError(
    2346             :                     state,
    2347           0 :                     format("{}=\"{}\", node does not appear in an OutdoorAir:NodeList or as an OutdoorAir:Node.", cAlphaFields(14), Alphas(14)));
    2348           0 :                 ShowContinueError(
    2349             :                     state, "This node needs to be included in an air system or the coil model will not be valid, and the simulation continues");
    2350             :             }
    2351             :         }
    2352             : 
    2353             :         // A14, \field Zone Name for Evaporator Placement
    2354          75 :         if (!lAlphaBlanks(15) && NumAlphas > 14) {
    2355           1 :             thisDXCoil.SecZonePtr = Util::FindItemInList(Alphas(15), state.dataHeatBal->Zone);
    2356           1 :             if (thisDXCoil.SecZonePtr > 0) {
    2357           1 :                 SetupZoneInternalGain(state,
    2358             :                                       thisDXCoil.SecZonePtr,
    2359             :                                       thisDXCoil.Name,
    2360             :                                       DataHeatBalance::IntGainType::SecHeatingDXCoilSingleSpeed,
    2361             :                                       &thisDXCoil.SecCoilSensibleHeatRemovalRate,
    2362             :                                       nullptr,
    2363             :                                       nullptr,
    2364             :                                       &thisDXCoil.SecCoilLatentHeatRemovalRate);
    2365           1 :                 thisDXCoil.IsSecondaryDXCoilInZone = true;
    2366             :             } else {
    2367           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2368           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(15), Alphas(15)));
    2369             :             }
    2370             :         }
    2371          75 :         if (thisDXCoil.SecZonePtr > 0) {
    2372             :             // N14, \field Secondary Coil Air Flow Rate
    2373           1 :             if (!lNumericBlanks(13)) {
    2374           1 :                 thisDXCoil.SecCoilAirFlow = Numbers(14);
    2375             :             }
    2376             :             // N15, \field Secondary Coil Fan Flow Scaling Factor
    2377           1 :             if (!lNumericBlanks(15)) {
    2378           1 :                 thisDXCoil.SecCoilAirFlowScalingFactor = Numbers(15);
    2379             :             }
    2380             :             // N16, \field Nominal Sensible Heat Ratio of Secondary Coil
    2381           1 :             if (!lNumericBlanks(16)) {
    2382           1 :                 thisDXCoil.SecCoilRatedSHR = Numbers(16);
    2383             :             } else {
    2384           0 :                 thisDXCoil.SecCoilRatedSHR = 1.0;
    2385             :             }
    2386             :             // A16, \field Sensible Heat Ratio Modifier Function of Temperature Curve Name
    2387           1 :             if (!lAlphaBlanks(16)) {
    2388           1 :                 thisDXCoil.SecCoilSHRFT = GetCurveIndex(state, Alphas(16));
    2389           1 :                 if (thisDXCoil.SecCoilSHRFT == 0) {
    2390           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2391           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(16), Alphas(16)));
    2392             :                 }
    2393             :             }
    2394             :             // A17; \field Sensible Heat Ratio Function of Flow Fraction Curve Name
    2395           1 :             if (!lAlphaBlanks(17)) {
    2396           1 :                 thisDXCoil.SecCoilSHRFF = GetCurveIndex(state, Alphas(17));
    2397           1 :                 if (thisDXCoil.SecCoilSHRFF == 0) {
    2398           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2399           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(17), Alphas(17)));
    2400             :                 }
    2401             :             }
    2402             :         }
    2403             : 
    2404             :     } // end of the DX heating coil loop
    2405             : 
    2406         247 :     if (ErrorsFound) {
    2407           0 :         ShowFatalError(state,
    2408           0 :                        format("{}Errors found in getting {} input. Preceding condition(s) causes termination.", RoutineName, CurrentModuleObject));
    2409             :     }
    2410             : 
    2411         247 :     CurrentModuleObject = "Coil:Cooling:DX:TwoSpeed";
    2412         314 :     for (DXCoilIndex = 1; DXCoilIndex <= state.dataDXCoils->NumDXMulSpeedCoils; ++DXCoilIndex) {
    2413             : 
    2414          67 :         ++DXCoilNum;
    2415             : 
    2416          67 :         state.dataInputProcessing->inputProcessor->getObjectItem(state,
    2417             :                                                                  CurrentModuleObject,
    2418             :                                                                  DXCoilIndex,
    2419             :                                                                  Alphas,
    2420             :                                                                  NumAlphas,
    2421             :                                                                  Numbers,
    2422             :                                                                  NumNumbers,
    2423             :                                                                  IOStatus,
    2424             :                                                                  lNumericBlanks,
    2425             :                                                                  lAlphaBlanks,
    2426             :                                                                  cAlphaFields,
    2427             :                                                                  cNumericFields);
    2428             : 
    2429             :         // allocate single performance mode for numeric field strings used for sizing routine
    2430          67 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode.allocate(1);
    2431          67 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames.allocate(MaxNumbers);
    2432          67 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames = cNumericFields;
    2433             :         // ErrorsFound will be set to True if problem was found, left untouched otherwise
    2434          67 :         VerifyUniqueCoilName(state, CurrentModuleObject, Alphas(1), ErrorsFound, CurrentModuleObject + " Name");
    2435             : 
    2436          67 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    2437          67 :         thisDXCoil.Name = Alphas(1);
    2438             :         // Initialize DataHeatBalance heat reclaim variable name for use by heat reclaim coils
    2439          67 :         state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).Name = thisDXCoil.Name;
    2440          67 :         state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).SourceType = CurrentModuleObject;
    2441          67 :         thisDXCoil.DXCoilType = CurrentModuleObject;
    2442          67 :         thisDXCoil.DXCoilType_Num = HVAC::CoilDX_CoolingTwoSpeed;
    2443          67 :         thisDXCoil.Schedule = Alphas(2);
    2444          67 :         if (lAlphaBlanks(2)) {
    2445           2 :             thisDXCoil.SchedPtr = ScheduleManager::ScheduleAlwaysOn;
    2446             :         } else {
    2447          65 :             thisDXCoil.SchedPtr = GetScheduleIndex(state, Alphas(2)); // convert schedule name to pointer
    2448          65 :             if (thisDXCoil.SchedPtr == 0) {
    2449           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2450           0 :                 ShowContinueError(state, format("...{}=\"{}\".", cAlphaFields(2), Alphas(2)));
    2451           0 :                 ErrorsFound = true;
    2452             :             }
    2453             :         }
    2454          67 :         thisDXCoil.RatedTotCap(1) = Numbers(1);
    2455          67 :         thisDXCoil.RatedSHR(1) = Numbers(2);
    2456          67 :         thisDXCoil.RatedCOP(1) = Numbers(3);
    2457          67 :         thisDXCoil.RatedAirVolFlowRate(1) = Numbers(4);
    2458             : 
    2459          67 :         thisDXCoil.FanPowerPerEvapAirFlowRate(1) = Numbers(5);
    2460          67 :         thisDXCoil.FanPowerPerEvapAirFlowRate_2023(1) = Numbers(6);
    2461             : 
    2462          67 :         if (!lNumericBlanks(7)) {
    2463          32 :             thisDXCoil.InternalStaticPressureDrop = Numbers(7);
    2464          32 :             thisDXCoil.RateWithInternalStaticAndFanObject = true;
    2465             :         } else {
    2466          35 :             thisDXCoil.InternalStaticPressureDrop = -999.0;
    2467          35 :             thisDXCoil.RateWithInternalStaticAndFanObject = false;
    2468             :         }
    2469             : 
    2470          67 :         thisDXCoil.AirInNode = GetOnlySingleNode(state,
    2471          67 :                                                  Alphas(3),
    2472             :                                                  ErrorsFound,
    2473             :                                                  DataLoopNode::ConnectionObjectType::CoilCoolingDXTwoSpeed,
    2474          67 :                                                  Alphas(1),
    2475             :                                                  DataLoopNode::NodeFluidType::Air,
    2476             :                                                  DataLoopNode::ConnectionType::Inlet,
    2477             :                                                  NodeInputManager::CompFluidStream::Primary,
    2478             :                                                  ObjectIsNotParent);
    2479             : 
    2480          67 :         thisDXCoil.AirOutNode = GetOnlySingleNode(state,
    2481          67 :                                                   Alphas(4),
    2482             :                                                   ErrorsFound,
    2483             :                                                   DataLoopNode::ConnectionObjectType::CoilCoolingDXTwoSpeed,
    2484          67 :                                                   Alphas(1),
    2485             :                                                   DataLoopNode::NodeFluidType::Air,
    2486             :                                                   DataLoopNode::ConnectionType::Outlet,
    2487             :                                                   NodeInputManager::CompFluidStream::Primary,
    2488             :                                                   ObjectIsNotParent);
    2489             : 
    2490          67 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(3), Alphas(4), "Air Nodes");
    2491             : 
    2492          67 :         thisDXCoil.CCapFTemp(1) = GetCurveIndex(state, Alphas(5)); // convert curve name to number
    2493          67 :         if (thisDXCoil.CCapFTemp(1) == 0) {
    2494           0 :             if (lAlphaBlanks(5)) {
    2495           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2496           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(5)));
    2497             :             } else {
    2498           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2499           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(5), Alphas(5)));
    2500             :             }
    2501           0 :             ErrorsFound = true;
    2502             :         } else {
    2503             :             // Verify Curve Object, only legal type is BiQuadratic
    2504         134 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2505          67 :                                                  thisDXCoil.CCapFTemp(1), // Curve index
    2506             :                                                  {2},                     // Valid dimensions
    2507             :                                                  RoutineName,             // Routine name
    2508             :                                                  CurrentModuleObject,     // Object Type
    2509             :                                                  thisDXCoil.Name,         // Object Name
    2510          67 :                                                  cAlphaFields(5));        // Field Name
    2511             : 
    2512          67 :             if (!ErrorsFound) {
    2513          67 :                 checkCurveIsNormalizedToOne(state,
    2514         134 :                                             std::string{RoutineName} + CurrentModuleObject,
    2515          67 :                                             thisDXCoil.Name,
    2516          67 :                                             thisDXCoil.CCapFTemp(1),
    2517          67 :                                             cAlphaFields(5),
    2518          67 :                                             Alphas(5),
    2519             :                                             RatedInletWetBulbTemp,
    2520             :                                             RatedOutdoorAirTemp);
    2521             :             }
    2522             :         }
    2523             : 
    2524          67 :         thisDXCoil.CCapFFlow(1) = GetCurveIndex(state, Alphas(6)); // convert curve name to number
    2525          67 :         if (thisDXCoil.CCapFFlow(1) == 0) {
    2526           0 :             if (lAlphaBlanks(6)) {
    2527           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2528           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(6)));
    2529             :             } else {
    2530           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2531           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(6), Alphas(6)));
    2532             :             }
    2533           0 :             ErrorsFound = true;
    2534             :         } else {
    2535             :             // Verify Curve Object, only legal type is Quadratic
    2536         134 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2537          67 :                                                  thisDXCoil.CCapFFlow(1), // Curve index
    2538             :                                                  {1},                     // Valid dimensions
    2539             :                                                  RoutineName,             // Routine name
    2540             :                                                  CurrentModuleObject,     // Object Type
    2541             :                                                  thisDXCoil.Name,         // Object Name
    2542          67 :                                                  cAlphaFields(6));        // Field Name
    2543             : 
    2544          67 :             if (!ErrorsFound) {
    2545          67 :                 checkCurveIsNormalizedToOne(
    2546         134 :                     state, std::string{RoutineName} + CurrentModuleObject, thisDXCoil.Name, thisDXCoil.CCapFFlow(1), cAlphaFields(6), Alphas(6), 1.0);
    2547             :             }
    2548             :         }
    2549             : 
    2550          67 :         thisDXCoil.EIRFTemp(1) = GetCurveIndex(state, Alphas(7)); // convert curve name to number
    2551          67 :         if (thisDXCoil.EIRFTemp(1) == 0) {
    2552           0 :             if (lAlphaBlanks(7)) {
    2553           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2554           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(7)));
    2555             :             } else {
    2556           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2557           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(7), Alphas(7)));
    2558             :             }
    2559           0 :             ErrorsFound = true;
    2560             :         } else {
    2561             :             // Verify Curve Object, only legal type is BiQuadratic
    2562         134 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2563          67 :                                                  thisDXCoil.EIRFTemp(1), // Curve index
    2564             :                                                  {2},                    // Valid dimensions
    2565             :                                                  RoutineName,            // Routine name
    2566             :                                                  CurrentModuleObject,    // Object Type
    2567             :                                                  thisDXCoil.Name,        // Object Name
    2568          67 :                                                  cAlphaFields(7));       // Field Name
    2569             : 
    2570          67 :             if (!ErrorsFound) {
    2571          67 :                 checkCurveIsNormalizedToOne(state,
    2572         134 :                                             std::string{RoutineName} + CurrentModuleObject,
    2573          67 :                                             thisDXCoil.Name,
    2574          67 :                                             thisDXCoil.EIRFTemp(1),
    2575          67 :                                             cAlphaFields(7),
    2576          67 :                                             Alphas(7),
    2577             :                                             RatedInletWetBulbTemp,
    2578             :                                             RatedOutdoorAirTemp);
    2579             :             }
    2580             :         }
    2581             : 
    2582          67 :         thisDXCoil.EIRFFlow(1) = GetCurveIndex(state, Alphas(8)); // convert curve name to number
    2583          67 :         if (thisDXCoil.EIRFFlow(1) == 0) {
    2584           0 :             if (lAlphaBlanks(8)) {
    2585           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2586           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(8)));
    2587             :             } else {
    2588           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2589           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(8), Alphas(8)));
    2590             :             }
    2591           0 :             ErrorsFound = true;
    2592             :         } else {
    2593             :             // Verify Curve Object, only legal type is Quadratic
    2594         134 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2595          67 :                                                  thisDXCoil.EIRFFlow(1), // Curve index
    2596             :                                                  {1},                    // Valid dimensions
    2597             :                                                  RoutineName,            // Routine name
    2598             :                                                  CurrentModuleObject,    // Object Type
    2599             :                                                  thisDXCoil.Name,        // Object Name
    2600          67 :                                                  cAlphaFields(8));       // Field Name
    2601             : 
    2602          67 :             if (!ErrorsFound) {
    2603          67 :                 checkCurveIsNormalizedToOne(
    2604         134 :                     state, std::string{RoutineName} + CurrentModuleObject, thisDXCoil.Name, thisDXCoil.EIRFFlow(1), cAlphaFields(8), Alphas(8), 1.0);
    2605             :             }
    2606             :         }
    2607             : 
    2608          67 :         thisDXCoil.PLFFPLR(1) = GetCurveIndex(state, Alphas(9)); // convert curve name to number
    2609          67 :         if (thisDXCoil.PLFFPLR(1) == 0) {
    2610           0 :             if (lAlphaBlanks(9)) {
    2611           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2612           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(9)));
    2613             :             } else {
    2614           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2615           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(9), Alphas(9)));
    2616             :             }
    2617           0 :             ErrorsFound = true;
    2618             :         } else {
    2619             :             // Verify Curve Object, only legal types are Quadratic or Cubic
    2620         134 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2621          67 :                                                  thisDXCoil.PLFFPLR(1), // Curve index
    2622             :                                                  {1},                   // Valid dimensions
    2623             :                                                  RoutineName,           // Routine name
    2624             :                                                  CurrentModuleObject,   // Object Type
    2625             :                                                  thisDXCoil.Name,       // Object Name
    2626          67 :                                                  cAlphaFields(9));      // Field Name
    2627             : 
    2628          67 :             if (!ErrorsFound) {
    2629             :                 //     Test PLF curve minimum and maximum. Cap if less than 0.7 or greater than 1.0.
    2630          67 :                 MinCurveVal = 999.0;
    2631          67 :                 MaxCurveVal = -999.0;
    2632          67 :                 CurveInput = 0.0;
    2633        6767 :                 while (CurveInput <= 1.0) {
    2634        6700 :                     CurveVal = CurveValue(state, thisDXCoil.PLFFPLR(1), CurveInput);
    2635        6700 :                     if (CurveVal < MinCurveVal) {
    2636          67 :                         MinCurveVal = CurveVal;
    2637          67 :                         MinCurvePLR = CurveInput;
    2638             :                     }
    2639        6700 :                     if (CurveVal > MaxCurveVal) {
    2640        2542 :                         MaxCurveVal = CurveVal;
    2641        2542 :                         MaxCurvePLR = CurveInput;
    2642             :                     }
    2643        6700 :                     CurveInput += 0.01;
    2644             :                 }
    2645          67 :                 if (MinCurveVal < 0.7) {
    2646           0 :                     ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2647           0 :                     ShowContinueError(state, format("...{} = {} has out of range value.", cAlphaFields(9), Alphas(9)));
    2648           0 :                     ShowContinueError(state,
    2649           0 :                                       format("...Curve minimum must be >= 0.7, curve min at PLR = {:.2T} is {:.3T}", MinCurvePLR, MinCurveVal));
    2650           0 :                     ShowContinueError(state, "...Setting curve minimum to 0.7 and simulation continues.");
    2651           0 :                     Curve::SetCurveOutputMinValue(state, thisDXCoil.PLFFPLR(1), ErrorsFound, 0.7);
    2652             :                 }
    2653             : 
    2654          67 :                 if (MaxCurveVal > 1.0) {
    2655           0 :                     ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2656           0 :                     ShowContinueError(state, format("...{} = {} has out of range value.", cAlphaFields(9), Alphas(9)));
    2657           0 :                     ShowContinueError(state,
    2658           0 :                                       format("...Curve maximum must be <= 1.0, curve max at PLR = {:.2T} is {:.3T}", MaxCurvePLR, MaxCurveVal));
    2659           0 :                     ShowContinueError(state, "...Setting curve maximum to 1.0 and simulation continues.");
    2660           0 :                     Curve::SetCurveOutputMaxValue(state, thisDXCoil.PLFFPLR(1), ErrorsFound, 1.0);
    2661             :                 }
    2662             :             }
    2663             :         }
    2664             : 
    2665          67 :         thisDXCoil.RatedEIR(1) = 1.0 / thisDXCoil.RatedCOP(1);
    2666             : 
    2667          67 :         thisDXCoil.RatedTotCap2 = Numbers(8);
    2668          67 :         thisDXCoil.RatedSHR2 = Numbers(9);
    2669          67 :         thisDXCoil.RatedCOP2 = Numbers(10);
    2670          67 :         thisDXCoil.RatedAirVolFlowRate2 = Numbers(11);
    2671             : 
    2672          67 :         thisDXCoil.FanPowerPerEvapAirFlowRate_LowSpeed(1) = Numbers(12);
    2673          67 :         thisDXCoil.FanPowerPerEvapAirFlowRate_2023_LowSpeed(1) = Numbers(13);
    2674             : 
    2675          67 :         if (lNumericBlanks(14)) {
    2676          67 :             thisDXCoil.MinOATCompressor = -25.0;
    2677             :         } else {
    2678           0 :             thisDXCoil.MinOATCompressor = Numbers(14);
    2679             :         }
    2680             : 
    2681          67 :         thisDXCoil.CCapFTemp2 = GetCurveIndex(state, Alphas(10)); // convert curve name to number
    2682          67 :         if (thisDXCoil.CCapFTemp2 == 0) {
    2683           0 :             if (lAlphaBlanks(10)) {
    2684           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2685           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(10)));
    2686             :             } else {
    2687           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2688           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(10), Alphas(10)));
    2689             :             }
    2690           0 :             ErrorsFound = true;
    2691             :         } else {
    2692             :             // Verify Curve Object, only legal type is BiQuadratic
    2693          67 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2694             :                                                  thisDXCoil.CCapFTemp2, // Curve index
    2695             :                                                  {2},                   // Valid dimensions
    2696             :                                                  RoutineName,           // Routine name
    2697             :                                                  CurrentModuleObject,   // Object Type
    2698             :                                                  thisDXCoil.Name,       // Object Name
    2699          67 :                                                  cAlphaFields(10));     // Field Name
    2700             : 
    2701          67 :             if (!ErrorsFound) {
    2702          67 :                 checkCurveIsNormalizedToOne(state,
    2703         134 :                                             std::string{RoutineName} + CurrentModuleObject,
    2704          67 :                                             thisDXCoil.Name,
    2705             :                                             thisDXCoil.CCapFTemp2,
    2706          67 :                                             cAlphaFields(10),
    2707          67 :                                             Alphas(10),
    2708             :                                             RatedInletWetBulbTemp,
    2709             :                                             RatedOutdoorAirTemp);
    2710             :             }
    2711             :         }
    2712             : 
    2713          67 :         thisDXCoil.EIRFTemp2 = GetCurveIndex(state, Alphas(11)); // convert curve name to number
    2714          67 :         if (thisDXCoil.EIRFTemp2 == 0) {
    2715           0 :             if (lAlphaBlanks(11)) {
    2716           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2717           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(11)));
    2718             :             } else {
    2719           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2720           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(11), Alphas(11)));
    2721             :             }
    2722           0 :             ErrorsFound = true;
    2723             :         } else {
    2724             :             // Verify Curve Object, only legal type is BiQuadratic
    2725          67 :             ErrorsFound |= Curve::CheckCurveDims(state,
    2726             :                                                  thisDXCoil.EIRFTemp2, // Curve index
    2727             :                                                  {2},                  // Valid dimensions
    2728             :                                                  RoutineName,          // Routine name
    2729             :                                                  CurrentModuleObject,  // Object Type
    2730             :                                                  thisDXCoil.Name,      // Object Name
    2731          67 :                                                  cAlphaFields(11));    // Field Name
    2732             : 
    2733          67 :             if (!ErrorsFound) {
    2734          67 :                 checkCurveIsNormalizedToOne(state,
    2735         134 :                                             std::string{RoutineName} + CurrentModuleObject,
    2736          67 :                                             thisDXCoil.Name,
    2737             :                                             thisDXCoil.EIRFTemp2,
    2738          67 :                                             cAlphaFields(11),
    2739          67 :                                             Alphas(11),
    2740             :                                             RatedInletWetBulbTemp,
    2741             :                                             RatedOutdoorAirTemp);
    2742             :             }
    2743             :         }
    2744             : 
    2745             :         // outdoor condenser node
    2746          67 :         if (lAlphaBlanks(12)) {
    2747          58 :             thisDXCoil.CondenserInletNodeNum(1) = 0;
    2748             :         } else {
    2749          18 :             thisDXCoil.CondenserInletNodeNum(1) = GetOnlySingleNode(state,
    2750           9 :                                                                     Alphas(12),
    2751             :                                                                     ErrorsFound,
    2752             :                                                                     DataLoopNode::ConnectionObjectType::CoilCoolingDXTwoSpeed,
    2753           9 :                                                                     thisDXCoil.Name,
    2754             :                                                                     DataLoopNode::NodeFluidType::Air,
    2755             :                                                                     DataLoopNode::ConnectionType::OutsideAirReference,
    2756             :                                                                     NodeInputManager::CompFluidStream::Primary,
    2757             :                                                                     ObjectIsNotParent);
    2758           9 :             if (!CheckOutAirNodeNumber(state, thisDXCoil.CondenserInletNodeNum(1))) {
    2759           0 :                 ShowWarningError(state, format("{}{}=\"{}\", may be invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2760           0 :                 ShowContinueError(
    2761             :                     state,
    2762           0 :                     format("{}=\"{}\", node does not appear in an OutdoorAir:NodeList or as an OutdoorAir:Node.", cAlphaFields(12), Alphas(12)));
    2763           0 :                 ShowContinueError(
    2764             :                     state, "This node needs to be included in an air system or the coil model will not be valid, and the simulation continues");
    2765             :             }
    2766             :         }
    2767             : 
    2768          67 :         if ((Util::SameString(Alphas(13), "AirCooled")) || lAlphaBlanks(13)) {
    2769          66 :             thisDXCoil.CondenserType(1) = DataHeatBalance::RefrigCondenserType::Air;
    2770           1 :         } else if (Util::SameString(Alphas(13), "EvaporativelyCooled")) {
    2771           1 :             thisDXCoil.CondenserType(1) = DataHeatBalance::RefrigCondenserType::Evap;
    2772           1 :             thisDXCoil.ReportEvapCondVars = true;
    2773             :         } else {
    2774           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2775           0 :             ShowContinueError(state, format("...{}=\"{}\":", cAlphaFields(13), Alphas(13)));
    2776           0 :             ShowContinueError(state, "...must be AirCooled or EvaporativelyCooled.");
    2777           0 :             ErrorsFound = true;
    2778             :         }
    2779             : 
    2780          67 :         thisDXCoil.EvapCondEffect(1) = Numbers(15);
    2781          67 :         if (thisDXCoil.EvapCondEffect(1) < 0.0 || thisDXCoil.EvapCondEffect(1) > 1.0) {
    2782           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2783           0 :             ShowContinueError(state, format("...{} cannot be < 0.0 or > 1.0.", cNumericFields(15)));
    2784           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(15)));
    2785           0 :             ErrorsFound = true;
    2786             :         }
    2787             : 
    2788          67 :         thisDXCoil.EvapCondAirFlow(1) = Numbers(16);
    2789          67 :         if (thisDXCoil.EvapCondAirFlow(1) < 0.0 && thisDXCoil.EvapCondAirFlow(1) != AutoSize) {
    2790           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2791           0 :             ShowContinueError(state, format("...{} cannot be < 0.0.", cNumericFields(16)));
    2792           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(16)));
    2793           0 :             ErrorsFound = true;
    2794             :         }
    2795             : 
    2796          67 :         thisDXCoil.EvapCondPumpElecNomPower(1) = Numbers(17);
    2797          67 :         if (thisDXCoil.EvapCondPumpElecNomPower(1) < 0.0 && thisDXCoil.EvapCondPumpElecNomPower(1) != AutoSize) {
    2798           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2799           0 :             ShowContinueError(state, format("...{} cannot be < 0.0.", cNumericFields(17)));
    2800           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(17)));
    2801           0 :             ErrorsFound = true;
    2802             :         }
    2803             : 
    2804          67 :         thisDXCoil.EvapCondEffect2 = Numbers(18);
    2805          67 :         if (thisDXCoil.EvapCondEffect2 < 0.0 || thisDXCoil.EvapCondEffect2 > 1.0) {
    2806           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2807           0 :             ShowContinueError(state, format("...{} cannot be cannot be < 0.0 or > 1.0.", cNumericFields(18)));
    2808           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(18)));
    2809           0 :             ErrorsFound = true;
    2810             :         }
    2811             : 
    2812          67 :         thisDXCoil.EvapCondAirFlow2 = Numbers(19);
    2813          67 :         if (thisDXCoil.EvapCondAirFlow2 < 0.0 && thisDXCoil.EvapCondAirFlow2 != AutoSize) {
    2814           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2815           0 :             ShowContinueError(state, format("...{} cannot be < 0.0.", cNumericFields(19)));
    2816           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(19)));
    2817           0 :             ErrorsFound = true;
    2818             :         }
    2819             : 
    2820          67 :         thisDXCoil.EvapCondPumpElecNomPower2 = Numbers(20);
    2821          67 :         if (thisDXCoil.EvapCondPumpElecNomPower2 < 0.0 && thisDXCoil.EvapCondPumpElecNomPower2 != AutoSize) {
    2822           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2823           0 :             ShowContinueError(state, format("...{} cannot be < 0.0.", cNumericFields(20)));
    2824           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(20)));
    2825           0 :             ErrorsFound = true;
    2826             :         }
    2827             : 
    2828          67 :         thisDXCoil.RatedEIR2 = 1.0 / thisDXCoil.RatedCOP2;
    2829             : 
    2830             :         // Get Water System tank connections
    2831             :         //  A14, \field Name of Water Storage Tank for Supply
    2832          67 :         thisDXCoil.EvapWaterSupplyName = Alphas(14);
    2833          67 :         if (lAlphaBlanks(14)) {
    2834          67 :             thisDXCoil.EvapWaterSupplyMode = EvapWaterSupply::FromMains;
    2835             :         } else {
    2836           0 :             thisDXCoil.EvapWaterSupplyMode = EvapWaterSupply::FromTank;
    2837           0 :             SetupTankDemandComponent(state,
    2838             :                                      thisDXCoil.Name,
    2839             :                                      CurrentModuleObject,
    2840             :                                      thisDXCoil.EvapWaterSupplyName,
    2841             :                                      ErrorsFound,
    2842           0 :                                      thisDXCoil.EvapWaterSupTankID,
    2843           0 :                                      thisDXCoil.EvapWaterTankDemandARRID);
    2844             :         }
    2845             : 
    2846             :         // A15; \field Name of Water Storage Tank for Condensate Collection
    2847          67 :         thisDXCoil.CondensateCollectName = Alphas(15);
    2848          67 :         if (lAlphaBlanks(15)) {
    2849          67 :             thisDXCoil.CondensateCollectMode = CondensateCollectAction::Discard;
    2850             :         } else {
    2851           0 :             thisDXCoil.CondensateCollectMode = CondensateCollectAction::ToTank;
    2852           0 :             SetupTankSupplyComponent(state,
    2853             :                                      thisDXCoil.Name,
    2854             :                                      CurrentModuleObject,
    2855             :                                      thisDXCoil.CondensateCollectName,
    2856             :                                      ErrorsFound,
    2857           0 :                                      thisDXCoil.CondensateTankID,
    2858           0 :                                      thisDXCoil.CondensateTankSupplyARRID);
    2859             :         }
    2860             : 
    2861             :         // Basin heater power as a function of temperature must be greater than or equal to 0
    2862          67 :         thisDXCoil.BasinHeaterPowerFTempDiff = Numbers(21);
    2863          67 :         if (Numbers(21) < 0.0) {
    2864           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2865           0 :             ShowContinueError(state, format("...{} must be >= 0.0.", cNumericFields(21)));
    2866           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(21)));
    2867           0 :             ErrorsFound = true;
    2868             :         }
    2869             : 
    2870          67 :         thisDXCoil.BasinHeaterSetPointTemp = Numbers(22);
    2871          67 :         if (thisDXCoil.BasinHeaterPowerFTempDiff > 0.0) {
    2872           1 :             if (NumNumbers < 22) {
    2873           0 :                 thisDXCoil.BasinHeaterSetPointTemp = 2.0;
    2874             :             }
    2875           1 :             if (thisDXCoil.BasinHeaterSetPointTemp < 2.0) {
    2876           0 :                 ShowWarningError(state, format("{}{}=\"{}\", freeze possible", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2877           0 :                 ShowContinueError(state, format("...{} is < 2 {{C}}. Freezing could occur.", cNumericFields(22)));
    2878           0 :                 ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(22)));
    2879             :             }
    2880             :         }
    2881             : 
    2882          67 :         if (!lAlphaBlanks(16)) {
    2883           1 :             thisDXCoil.BasinHeaterSchedulePtr = GetScheduleIndex(state, Alphas(16));
    2884           1 :             if (thisDXCoil.BasinHeaterSchedulePtr == 0) {
    2885           0 :                 ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2886           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(16), Alphas(16)));
    2887           0 :                 ShowContinueError(state, "Basin heater will be available to operate throughout the simulation.");
    2888             :             }
    2889             :         }
    2890             : 
    2891          67 :         if (!lAlphaBlanks(17) && NumAlphas > 16) {
    2892           1 :             thisDXCoil.SHRFTemp(1) = GetCurveIndex(state, Alphas(17)); // convert curve name to number
    2893             :             // DXCoil(DXCoilNum)%SHRFTemp2 = DXCoil(DXCoilNum)%SHRFTemp(1)
    2894           1 :             if (thisDXCoil.SHRFTemp(1) == 0) {
    2895           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2896           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(17), Alphas(17)));
    2897             :             } else {
    2898             :                 // Verify Curve Object, only legal type is BiQuadratic
    2899           2 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    2900           1 :                                                      thisDXCoil.SHRFTemp(1), // Curve index
    2901             :                                                      {2},                    // Valid dimensions
    2902             :                                                      RoutineName,            // Routine name
    2903             :                                                      CurrentModuleObject,    // Object Type
    2904             :                                                      thisDXCoil.Name,        // Object Name
    2905           1 :                                                      cAlphaFields(17));      // Field Name
    2906             :             }
    2907             :         }
    2908             : 
    2909          67 :         if (!lAlphaBlanks(18) && NumAlphas > 17) {
    2910           1 :             thisDXCoil.SHRFFlow(1) = GetCurveIndex(state, Alphas(18)); // convert curve name to number
    2911             :             // DXCoil(DXCoilNum)%SHRFFlow2 = DXCoil(DXCoilNum)%SHRFFlow(1)
    2912           1 :             if (thisDXCoil.SHRFFlow(1) == 0) {
    2913           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2914           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(18), Alphas(18)));
    2915             :             } else {
    2916             :                 // Verify Curve Object, only legal type is BiQuadratic
    2917           2 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    2918           1 :                                                      thisDXCoil.SHRFFlow(1), // Curve index
    2919             :                                                      {1},                    // Valid dimensions
    2920             :                                                      RoutineName,            // Routine name
    2921             :                                                      CurrentModuleObject,    // Object Type
    2922             :                                                      thisDXCoil.Name,        // Object Name
    2923           1 :                                                      cAlphaFields(18));      // Field Name
    2924             :             }
    2925             :         }
    2926             : 
    2927          67 :         if (!lAlphaBlanks(19) && NumAlphas > 18) {
    2928           1 :             thisDXCoil.SHRFTemp2 = GetCurveIndex(state, Alphas(19)); // convert curve name to number
    2929           1 :             if (thisDXCoil.SHRFTemp2 == 0) {
    2930           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2931           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(19), Alphas(19)));
    2932             :             } else {
    2933             :                 // Verify Curve Object, only legal type is BiQuadratic
    2934           1 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    2935             :                                                      thisDXCoil.SHRFTemp2, // Curve index
    2936             :                                                      {2},                  // Valid dimensions
    2937             :                                                      RoutineName,          // Routine name
    2938             :                                                      CurrentModuleObject,  // Object Type
    2939             :                                                      thisDXCoil.Name,      // Object Name
    2940           1 :                                                      cAlphaFields(19));    // Field Name
    2941             :             }
    2942             :         }
    2943             : 
    2944          67 :         if (!lAlphaBlanks(20) && NumAlphas > 19) {
    2945           1 :             thisDXCoil.SHRFFlow2 = GetCurveIndex(state, Alphas(20)); // convert curve name to number
    2946           1 :             if (thisDXCoil.SHRFTemp2 == 0) {
    2947           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2948           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(20), Alphas(20)));
    2949             :             } else {
    2950             :                 // Verify Curve Object, only legal type is BiQuadratic
    2951           1 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    2952             :                                                      thisDXCoil.SHRFFlow2, // Curve index
    2953             :                                                      {1},                  // Valid dimensions
    2954             :                                                      RoutineName,          // Routine name
    2955             :                                                      CurrentModuleObject,  // Object Type
    2956             :                                                      thisDXCoil.Name,      // Object Name
    2957           1 :                                                      cAlphaFields(20));    // Field Name
    2958             :             }
    2959             :         }
    2960          67 :         if (thisDXCoil.SHRFTemp(1) > 0 && thisDXCoil.SHRFFlow(1) > 0 && thisDXCoil.SHRFTemp2 > 0 && thisDXCoil.SHRFFlow2 > 0) {
    2961           1 :             thisDXCoil.UserSHRCurveExists = true;
    2962             :         } else {
    2963          66 :             thisDXCoil.UserSHRCurveExists = false;
    2964             :         }
    2965             :         // A21; \field Zone Name for Condenser Placement
    2966          67 :         if (!lAlphaBlanks(21) && NumAlphas > 20) {
    2967           0 :             thisDXCoil.SecZonePtr = Util::FindItemInList(Alphas(21), state.dataHeatBal->Zone);
    2968           0 :             if (thisDXCoil.SecZonePtr > 0) {
    2969           0 :                 SetupZoneInternalGain(state,
    2970             :                                       thisDXCoil.SecZonePtr,
    2971             :                                       thisDXCoil.Name,
    2972             :                                       DataHeatBalance::IntGainType::SecCoolingDXCoilTwoSpeed,
    2973             :                                       &thisDXCoil.SecCoilSensibleHeatGainRate);
    2974           0 :                 thisDXCoil.IsSecondaryDXCoilInZone = true;
    2975             :             } else {
    2976           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    2977           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(21), Alphas(21)));
    2978             :             }
    2979             :         }
    2980             :     }
    2981             : 
    2982         247 :     if (ErrorsFound) {
    2983           0 :         ShowFatalError(state,
    2984           0 :                        format("{}Errors found in getting {} input.  Preceding condition(s) causes termination.", RoutineName, CurrentModuleObject));
    2985             :     }
    2986             : 
    2987             :     // Loop over the Pumped DX Water Heater Coils and get & load the data
    2988         247 :     CurrentModuleObject = HVAC::cAllCoilTypes(HVAC::CoilDX_HeatPumpWaterHeaterPumped);
    2989         260 :     for (DXHPWaterHeaterCoilNum = 1; DXHPWaterHeaterCoilNum <= state.dataDXCoils->NumDXHeatPumpWaterHeaterPumpedCoils; ++DXHPWaterHeaterCoilNum) {
    2990             : 
    2991          13 :         state.dataInputProcessing->inputProcessor->getObjectItem(state,
    2992             :                                                                  CurrentModuleObject,
    2993             :                                                                  DXHPWaterHeaterCoilNum,
    2994             :                                                                  Alphas,
    2995             :                                                                  NumAlphas,
    2996             :                                                                  Numbers,
    2997             :                                                                  NumNumbers,
    2998             :                                                                  IOStatus,
    2999             :                                                                  lNumericBlanks,
    3000             :                                                                  lAlphaBlanks,
    3001             :                                                                  cAlphaFields,
    3002             :                                                                  cNumericFields);
    3003             : 
    3004          13 :         ++DXCoilNum;
    3005             : 
    3006             :         // allocate single performance mode for numeric field strings used for sizing routine
    3007          13 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode.allocate(1);
    3008          13 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames.allocate(MaxNumbers);
    3009          13 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames = cNumericFields;
    3010             :         // ErrorsFound will be set to True if problem was found, left untouched otherwise
    3011          13 :         VerifyUniqueCoilName(state, CurrentModuleObject, Alphas(1), ErrorsFound, CurrentModuleObject + " Name");
    3012             : 
    3013          13 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    3014          13 :         thisDXCoil.Name = Alphas(1);
    3015          13 :         thisDXCoil.DXCoilType = CurrentModuleObject;
    3016          13 :         thisDXCoil.DXCoilType_Num = HVAC::CoilDX_HeatPumpWaterHeaterPumped;
    3017          13 :         thisDXCoil.SchedPtr = 0; // heat pump water heater DX coil has no schedule
    3018             : 
    3019             :         // Store the HPWH DX coil heating capacity in RatedTotCap2. After backing off pump and fan heat,
    3020             :         // move to RatedTotCap() for use by DX coil
    3021          13 :         thisDXCoil.RatedTotCap2 = Numbers(1);
    3022          13 :         if (thisDXCoil.RatedTotCap2 <= 0.0) {
    3023           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3024           0 :             ShowContinueError(state, format("...{} must be > 0.0, entered value=[{:.2T}].", cNumericFields(1), Numbers(1)));
    3025           0 :             ErrorsFound = true;
    3026             :         }
    3027             : 
    3028          13 :         thisDXCoil.RatedCOP(1) = Numbers(2);
    3029          13 :         if (thisDXCoil.RatedCOP(1) <= 0.0) {
    3030           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3031           0 :             ShowContinueError(state, format("...{} must be > 0.0, entered value=[{:.2T}].", cNumericFields(2), Numbers(2)));
    3032           0 :             ErrorsFound = true;
    3033             :         }
    3034             : 
    3035          13 :         thisDXCoil.RatedSHR(1) = Numbers(3);
    3036          13 :         if (thisDXCoil.RatedSHR(1) <= 0.0 || thisDXCoil.RatedSHR(1) > 1.0) {
    3037           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3038           0 :             ShowContinueError(state, format("...{} must be > 0 and <= 1.  entered value=[{:.3T}].", cNumericFields(3), Numbers(3)));
    3039             : 
    3040           0 :             ErrorsFound = true;
    3041             :         }
    3042             : 
    3043          13 :         thisDXCoil.RatedInletDBTemp = Numbers(4);
    3044          13 :         if (thisDXCoil.RatedInletDBTemp <= 5.0) {
    3045           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3046           0 :             ShowContinueError(state, format("...{} must be > 5 {{C}}.  entered value=[{:.1T}].", cNumericFields(4), Numbers(4)));
    3047           0 :             ErrorsFound = true;
    3048             :         }
    3049             : 
    3050          13 :         thisDXCoil.RatedInletWBTemp = Numbers(5);
    3051          13 :         if (thisDXCoil.RatedInletWBTemp <= 5.0) {
    3052           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3053           0 :             ShowContinueError(state, format("...{} must be > 5 {{C}}.  entered value=[{:.1T}].", cNumericFields(5), Numbers(5)));
    3054           0 :             ErrorsFound = true;
    3055             :         }
    3056             : 
    3057          13 :         thisDXCoil.RatedInletWaterTemp = Numbers(6);
    3058          13 :         if (thisDXCoil.RatedInletWaterTemp <= 25.0) {
    3059           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3060           0 :             ShowContinueError(state, format("...{} must be > 25 {{C}}.  entered value=[{:.1T}].", cNumericFields(6), Numbers(6)));
    3061           0 :             ErrorsFound = true;
    3062             :         }
    3063             : 
    3064          13 :         thisDXCoil.RatedAirVolFlowRate(1) = Numbers(7);
    3065          13 :         if (thisDXCoil.RatedAirVolFlowRate(1) != Constant::AutoCalculate) {
    3066           7 :             if (thisDXCoil.RatedAirVolFlowRate(1) <= 0.0) {
    3067           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3068           0 :                 ShowContinueError(state, format("...{} must be > 0.0.  entered value=[{:.3T}].", cNumericFields(7), Numbers(7)));
    3069           0 :                 ErrorsFound = true;
    3070             :             }
    3071             :         }
    3072             : 
    3073          13 :         thisDXCoil.RatedHPWHCondWaterFlow = Numbers(8);
    3074             :         // move to init
    3075          13 :         if (thisDXCoil.RatedHPWHCondWaterFlow != Constant::AutoCalculate) {
    3076           7 :             if (thisDXCoil.RatedHPWHCondWaterFlow <= 0.0) {
    3077           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3078           0 :                 ShowContinueError(state, format("...{} must be > 0.0  entered value=[{:.3T}].", cNumericFields(8), Numbers(8)));
    3079           0 :                 ErrorsFound = true;
    3080             :             }
    3081             :             //   check the range of flow rate to be >= 1 gpm/ton and <= 5 gpm/ton
    3082           7 :             if (thisDXCoil.RatedHPWHCondWaterFlow / thisDXCoil.RatedTotCap2 < 1.79405e-8 ||
    3083           7 :                 thisDXCoil.RatedHPWHCondWaterFlow / thisDXCoil.RatedTotCap2 > 8.97024e-8) {
    3084           0 :                 ShowWarningError(state, format("{}{}=\"{}\", outside range", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3085           0 :                 ShowContinueError(state,
    3086           0 :                                   format("...{} per watt of {} is outside the recommended range of >= 1.79405E-8 m3/s/W (0.083 gpm/MBH) and <= "
    3087             :                                          "8.97024E-8 m3/s/W (0.417 gpm/MBH).",
    3088             :                                          cNumericFields(8),
    3089             :                                          cNumericFields(1)));
    3090           0 :                 ShowContinueError(
    3091           0 :                     state, format("...Entered Flow rate per watt = [{:.10T}].", (thisDXCoil.RatedHPWHCondWaterFlow / thisDXCoil.RatedTotCap2)));
    3092             :             }
    3093             :         }
    3094             : 
    3095          13 :         if (Util::SameString(Alphas(2), "Yes") || Util::SameString(Alphas(2), "No")) {
    3096             :             //  initialized to TRUE on allocate
    3097          13 :             if (Util::SameString(Alphas(2), "No")) thisDXCoil.FanPowerIncludedInCOP = false;
    3098             :         } else {
    3099           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3100           0 :             ShowContinueError(state, format(",,,invalid choice for {}.  Entered choice = {}", cAlphaFields(2), Alphas(2)));
    3101           0 :             ShowContinueError(state, "Valid choices are Yes or No.");
    3102           0 :             ErrorsFound = true;
    3103             :         }
    3104             : 
    3105          13 :         if (Util::SameString(Alphas(3), "Yes") || Util::SameString(Alphas(3), "No")) {
    3106             :             //  initialized to FALSE on allocate
    3107          13 :             if (Util::SameString(Alphas(3), "Yes")) thisDXCoil.CondPumpPowerInCOP = true;
    3108             :         } else {
    3109           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3110           0 :             ShowContinueError(state, format(",,,invalid choice for {}.  Entered choice = {}", cAlphaFields(3), Alphas(3)));
    3111           0 :             ShowContinueError(state, "Valid choices are Yes or No.");
    3112           0 :             ErrorsFound = true;
    3113             :         }
    3114             : 
    3115          13 :         if (Util::SameString(Alphas(4), "Yes") || Util::SameString(Alphas(4), "No")) {
    3116             :             //  initialized to FALSE on allocate
    3117          13 :             if (Util::SameString(Alphas(4), "Yes")) thisDXCoil.CondPumpHeatInCapacity = true;
    3118             :         } else {
    3119           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3120           0 :             ShowContinueError(state, format(",,,invalid choice for {}.  Entered choice = {}", cAlphaFields(4), Alphas(4)));
    3121           0 :             ShowContinueError(state, "Valid choices are Yes or No.");
    3122           0 :             ErrorsFound = true;
    3123             :         }
    3124             : 
    3125          13 :         thisDXCoil.HPWHCondPumpElecNomPower = Numbers(9);
    3126          13 :         if (thisDXCoil.HPWHCondPumpElecNomPower < 0.0) {
    3127           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3128           0 :             ShowContinueError(state, format("...{} must be >= 0.0  entered value=[{:.3T}].", cNumericFields(9), Numbers(9)));
    3129           0 :             ErrorsFound = true;
    3130             :         }
    3131             : 
    3132          13 :         thisDXCoil.HPWHCondPumpFracToWater = Numbers(10);
    3133          13 :         if (thisDXCoil.HPWHCondPumpFracToWater <= 0.0 || thisDXCoil.HPWHCondPumpFracToWater > 1.0) {
    3134           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3135           0 :             ShowContinueError(state, format("...{} must be >= 0 and <= 1.  entered value=[{:.3T}].", cNumericFields(10), Numbers(10)));
    3136           0 :             ErrorsFound = true;
    3137             :         }
    3138             : 
    3139             :         // Air nodes
    3140          13 :         thisDXCoil.AirInNode = GetOnlySingleNode(state,
    3141          13 :                                                  Alphas(5),
    3142             :                                                  ErrorsFound,
    3143             :                                                  DataLoopNode::ConnectionObjectType::CoilWaterHeatingAirToWaterHeatPumpPumped,
    3144          13 :                                                  Alphas(1),
    3145             :                                                  DataLoopNode::NodeFluidType::Air,
    3146             :                                                  DataLoopNode::ConnectionType::Inlet,
    3147             :                                                  NodeInputManager::CompFluidStream::Primary,
    3148             :                                                  ObjectIsNotParent);
    3149             : 
    3150          13 :         thisDXCoil.AirOutNode = GetOnlySingleNode(state,
    3151          13 :                                                   Alphas(6),
    3152             :                                                   ErrorsFound,
    3153             :                                                   DataLoopNode::ConnectionObjectType::CoilWaterHeatingAirToWaterHeatPumpPumped,
    3154          13 :                                                   Alphas(1),
    3155             :                                                   DataLoopNode::NodeFluidType::Air,
    3156             :                                                   DataLoopNode::ConnectionType::Outlet,
    3157             :                                                   NodeInputManager::CompFluidStream::Primary,
    3158             :                                                   ObjectIsNotParent);
    3159             : 
    3160          13 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(5), Alphas(6), "Air Nodes");
    3161             : 
    3162             :         // Check if the air inlet node is OA node, to justify whether the coil is placed in zone or not
    3163          13 :         thisDXCoil.IsDXCoilInZone = !CheckOutAirNodeNumber(state, thisDXCoil.AirInNode);
    3164             : 
    3165             :         // Water nodes
    3166          13 :         thisDXCoil.WaterInNode = GetOnlySingleNode(state,
    3167          13 :                                                    Alphas(7),
    3168             :                                                    ErrorsFound,
    3169             :                                                    DataLoopNode::ConnectionObjectType::CoilWaterHeatingAirToWaterHeatPumpPumped,
    3170          13 :                                                    Alphas(1),
    3171             :                                                    DataLoopNode::NodeFluidType::Water,
    3172             :                                                    DataLoopNode::ConnectionType::Inlet,
    3173             :                                                    NodeInputManager::CompFluidStream::Secondary,
    3174             :                                                    ObjectIsNotParent);
    3175             : 
    3176          13 :         thisDXCoil.WaterOutNode = GetOnlySingleNode(state,
    3177          13 :                                                     Alphas(8),
    3178             :                                                     ErrorsFound,
    3179             :                                                     DataLoopNode::ConnectionObjectType::CoilWaterHeatingAirToWaterHeatPumpPumped,
    3180          13 :                                                     Alphas(1),
    3181             :                                                     DataLoopNode::NodeFluidType::Water,
    3182             :                                                     DataLoopNode::ConnectionType::Outlet,
    3183             :                                                     NodeInputManager::CompFluidStream::Secondary,
    3184             :                                                     ObjectIsNotParent);
    3185             : 
    3186          13 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(7), Alphas(8), "Water Nodes");
    3187             : 
    3188          13 :         thisDXCoil.CrankcaseHeaterCapacity = Numbers(11);
    3189          13 :         if (thisDXCoil.CrankcaseHeaterCapacity < 0.0) {
    3190           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3191           0 :             ShowContinueError(state, format("...{} must be >= 0.0  entered value=[{:.1T}].", cNumericFields(11), Numbers(11)));
    3192           0 :             ErrorsFound = true;
    3193             :         }
    3194             : 
    3195          13 :         thisDXCoil.MaxOATCrankcaseHeater = Numbers(12);
    3196          13 :         if (thisDXCoil.MaxOATCrankcaseHeater < 0.0) {
    3197           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3198           0 :             ShowContinueError(state, format("...{} must be >= 0 {{C}}.  entered value=[{:.1T}].", cNumericFields(12), Numbers(12)));
    3199           0 :             ErrorsFound = true;
    3200             :         }
    3201             : 
    3202          13 :         if (!lAlphaBlanks(9)) {
    3203           0 :             thisDXCoil.CrankcaseHeaterCapacityCurveIndex = Curve::GetCurveIndex(state, Alphas(9));
    3204           0 :             ErrorsFound |= Curve::CheckCurveDims(state,
    3205             :                                                  thisDXCoil.CrankcaseHeaterCapacityCurveIndex, // Curve index
    3206             :                                                  {1},                                          // Valid dimensions
    3207             :                                                  RoutineName,                                  // Routine name
    3208             :                                                  CurrentModuleObject,                          // Object Type
    3209             :                                                  thisDXCoil.Name,                              // Object Name
    3210           0 :                                                  cAlphaFields(9));                             // Field Name
    3211             :         }
    3212             : 
    3213          13 :         thisDXCoil.InletAirTemperatureType = static_cast<HVAC::OATType>(getEnumValue(HVAC::oatTypeNamesUC, Alphas(10)));
    3214             : 
    3215             :         // set rated inlet air temperature for curve object verification
    3216          13 :         if (thisDXCoil.InletAirTemperatureType == HVAC::OATType::WetBulb) {
    3217          13 :             InletAirTemp = thisDXCoil.RatedInletWBTemp;
    3218             :         } else {
    3219           0 :             InletAirTemp = thisDXCoil.RatedInletDBTemp;
    3220             :         }
    3221             :         // set rated water temperature for curve object verification
    3222          13 :         InletWaterTemp = thisDXCoil.RatedInletWaterTemp;
    3223             : 
    3224          13 :         if (!lAlphaBlanks(11)) {
    3225          13 :             thisDXCoil.HCapFTemp = GetCurveIndex(state, Alphas(11));
    3226          13 :             if (thisDXCoil.HCapFTemp == 0) {
    3227           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3228           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(11), Alphas(11)));
    3229           0 :                 ErrorsFound = true;
    3230             :             } else {
    3231             :                 // Verify Curve Object, only legal types are BiQuadratic or Cubic
    3232          13 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    3233             :                                                      thisDXCoil.HCapFTemp, // Curve index
    3234             :                                                      {1, 2},               // Valid dimensions  // MULTIPLECURVEDIMS
    3235             :                                                      RoutineName,          // Routine name
    3236             :                                                      CurrentModuleObject,  // Object Type
    3237             :                                                      thisDXCoil.Name,      // Object Name
    3238          13 :                                                      cAlphaFields(11));    // Field Name
    3239             : 
    3240          13 :                 if (!ErrorsFound) {
    3241          13 :                     if (state.dataCurveManager->PerfCurve(thisDXCoil.HCapFTemp)->numDims == 1) {
    3242           0 :                         checkCurveIsNormalizedToOne(state,
    3243           0 :                                                     std::string{RoutineName} + CurrentModuleObject,
    3244           0 :                                                     thisDXCoil.Name,
    3245             :                                                     thisDXCoil.HCapFTemp,
    3246           0 :                                                     cAlphaFields(11),
    3247           0 :                                                     Alphas(11),
    3248             :                                                     InletAirTemp);
    3249             :                     } else {
    3250          13 :                         checkCurveIsNormalizedToOne(state,
    3251          26 :                                                     std::string{RoutineName} + CurrentModuleObject,
    3252          13 :                                                     thisDXCoil.Name,
    3253             :                                                     thisDXCoil.HCapFTemp,
    3254          13 :                                                     cAlphaFields(11),
    3255          13 :                                                     Alphas(11),
    3256             :                                                     InletAirTemp,
    3257             :                                                     InletWaterTemp);
    3258             :                     }
    3259             :                 }
    3260             :             }
    3261             :         }
    3262             : 
    3263          13 :         if (!lAlphaBlanks(12)) {
    3264           0 :             thisDXCoil.HCapFAirFlow = GetCurveIndex(state, Alphas(12));
    3265           0 :             if (thisDXCoil.HCapFAirFlow == 0) {
    3266           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3267           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(12), Alphas(12)));
    3268           0 :                 ErrorsFound = true;
    3269             :             } else {
    3270             :                 // Verify Curve Object, only legal types are Cubic or Quadratic
    3271           0 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    3272             :                                                      thisDXCoil.HCapFAirFlow, // Curve index
    3273             :                                                      {1},                     // Valid dimensions
    3274             :                                                      RoutineName,             // Routine name
    3275             :                                                      CurrentModuleObject,     // Object Type
    3276             :                                                      thisDXCoil.Name,         // Object Name
    3277           0 :                                                      cAlphaFields(12));       // Field Name
    3278             : 
    3279           0 :                 if (!ErrorsFound) {
    3280           0 :                     checkCurveIsNormalizedToOne(state,
    3281           0 :                                                 std::string{RoutineName} + CurrentModuleObject,
    3282           0 :                                                 thisDXCoil.Name,
    3283             :                                                 thisDXCoil.HCapFAirFlow,
    3284           0 :                                                 cAlphaFields(12),
    3285           0 :                                                 Alphas(12),
    3286             :                                                 1.0);
    3287             :                 }
    3288             :             }
    3289             :         }
    3290             : 
    3291          13 :         if (!lAlphaBlanks(13)) {
    3292           0 :             thisDXCoil.HCapFWaterFlow = GetCurveIndex(state, Alphas(13));
    3293           0 :             if (thisDXCoil.HCapFWaterFlow == 0) {
    3294           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3295           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(13), Alphas(13)));
    3296           0 :                 ErrorsFound = true;
    3297             :             } else {
    3298             :                 // Verify Curve Object, only legal types are Cubic or Quadratic
    3299           0 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    3300             :                                                      thisDXCoil.HCapFWaterFlow, // Curve index
    3301             :                                                      {1},                       // Valid dimensions
    3302             :                                                      RoutineName,               // Routine name
    3303             :                                                      CurrentModuleObject,       // Object Type
    3304             :                                                      thisDXCoil.Name,           // Object Name
    3305           0 :                                                      cAlphaFields(13));         // Field Name
    3306             : 
    3307           0 :                 if (!ErrorsFound) {
    3308           0 :                     checkCurveIsNormalizedToOne(state,
    3309           0 :                                                 std::string{RoutineName} + CurrentModuleObject,
    3310           0 :                                                 thisDXCoil.Name,
    3311             :                                                 thisDXCoil.HCapFWaterFlow,
    3312           0 :                                                 cAlphaFields(13),
    3313           0 :                                                 Alphas(13),
    3314             :                                                 1.0);
    3315             :                 }
    3316             :             }
    3317             :         }
    3318             : 
    3319          13 :         if (!lAlphaBlanks(14)) {
    3320          13 :             thisDXCoil.HCOPFTemp = GetCurveIndex(state, Alphas(14));
    3321          13 :             if (thisDXCoil.HCOPFTemp == 0) {
    3322           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3323           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(14), Alphas(14)));
    3324           0 :                 ErrorsFound = true;
    3325             :             } else {
    3326             :                 // Verify Curve Object, only legal types are BiQuadratic or Cubic
    3327          13 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    3328             :                                                      thisDXCoil.HCOPFTemp, // Curve index
    3329             :                                                      {1, 2},               // Valid dimensions  // MULTIPLECURVEDIMS
    3330             :                                                      RoutineName,          // Routine name
    3331             :                                                      CurrentModuleObject,  // Object Type
    3332             :                                                      thisDXCoil.Name,      // Object Name
    3333          13 :                                                      cAlphaFields(14));    // Field Name
    3334             : 
    3335          13 :                 if (!ErrorsFound) {
    3336          13 :                     if (state.dataCurveManager->PerfCurve(thisDXCoil.HCOPFTemp)->numDims == 1) {
    3337           0 :                         checkCurveIsNormalizedToOne(state,
    3338           0 :                                                     std::string{RoutineName} + CurrentModuleObject,
    3339           0 :                                                     thisDXCoil.Name,
    3340             :                                                     thisDXCoil.HCOPFTemp,
    3341           0 :                                                     cAlphaFields(14),
    3342           0 :                                                     Alphas(14),
    3343             :                                                     InletAirTemp);
    3344             :                     } else {
    3345          13 :                         checkCurveIsNormalizedToOne(state,
    3346          26 :                                                     std::string{RoutineName} + CurrentModuleObject,
    3347          13 :                                                     thisDXCoil.Name,
    3348             :                                                     thisDXCoil.HCOPFTemp,
    3349          13 :                                                     cAlphaFields(14),
    3350          13 :                                                     Alphas(14),
    3351             :                                                     InletAirTemp,
    3352             :                                                     InletWaterTemp);
    3353             :                     }
    3354             :                 }
    3355             :             }
    3356             :         }
    3357             : 
    3358          13 :         if (!lAlphaBlanks(15)) {
    3359           0 :             thisDXCoil.HCOPFAirFlow = GetCurveIndex(state, Alphas(15));
    3360           0 :             if (thisDXCoil.HCOPFAirFlow == 0) {
    3361           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3362           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(15), Alphas(15)));
    3363           0 :                 ErrorsFound = true;
    3364             :             } else {
    3365             :                 // Verify Curve Object, only legal types are Cubic or Quadratic
    3366           0 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    3367             :                                                      thisDXCoil.HCOPFAirFlow, // Curve index
    3368             :                                                      {1},                     // Valid dimensions
    3369             :                                                      RoutineName,             // Routine name
    3370             :                                                      CurrentModuleObject,     // Object Type
    3371             :                                                      thisDXCoil.Name,         // Object Name
    3372           0 :                                                      cAlphaFields(15));       // Field Name
    3373             : 
    3374           0 :                 if (!ErrorsFound) {
    3375           0 :                     checkCurveIsNormalizedToOne(state,
    3376           0 :                                                 std::string{RoutineName} + CurrentModuleObject,
    3377           0 :                                                 thisDXCoil.Name,
    3378             :                                                 thisDXCoil.HCOPFAirFlow,
    3379           0 :                                                 cAlphaFields(15),
    3380           0 :                                                 Alphas(15),
    3381             :                                                 1.0);
    3382             :                 }
    3383             :             }
    3384             :         }
    3385             : 
    3386          13 :         if (!lAlphaBlanks(16)) {
    3387           0 :             thisDXCoil.HCOPFWaterFlow = GetCurveIndex(state, Alphas(16));
    3388           0 :             if (thisDXCoil.HCOPFWaterFlow == 0) {
    3389           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3390           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(16), Alphas(16)));
    3391           0 :                 ErrorsFound = true;
    3392             :             } else {
    3393             :                 // Verify Curve Object, only legal types are Cubic or Quadratic
    3394           0 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    3395             :                                                      thisDXCoil.HCOPFWaterFlow, // Curve index
    3396             :                                                      {1},                       // Valid dimensions
    3397             :                                                      RoutineName,               // Routine name
    3398             :                                                      CurrentModuleObject,       // Object Type
    3399             :                                                      thisDXCoil.Name,           // Object Name
    3400           0 :                                                      cAlphaFields(16));         // Field Name
    3401             : 
    3402           0 :                 if (!ErrorsFound) {
    3403           0 :                     checkCurveIsNormalizedToOne(state,
    3404           0 :                                                 std::string{RoutineName} + CurrentModuleObject,
    3405           0 :                                                 thisDXCoil.Name,
    3406             :                                                 thisDXCoil.HCOPFWaterFlow,
    3407           0 :                                                 cAlphaFields(16),
    3408           0 :                                                 Alphas(16),
    3409             :                                                 1.0);
    3410             :                 }
    3411             :             }
    3412             :         }
    3413             : 
    3414          13 :         if (!lAlphaBlanks(17)) {
    3415          13 :             thisDXCoil.PLFFPLR(1) = GetCurveIndex(state, Alphas(17));
    3416          13 :             if (thisDXCoil.PLFFPLR(1) == 0) {
    3417           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3418           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(17), Alphas(17)));
    3419           0 :                 ErrorsFound = true;
    3420             :             } else {
    3421             :                 // Verify Curve Object, only legal types are Cubic or Quadratic
    3422          26 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    3423          13 :                                                      thisDXCoil.PLFFPLR(1), // Curve index
    3424             :                                                      {1},                   // Valid dimensions
    3425             :                                                      RoutineName,           // Routine name
    3426             :                                                      CurrentModuleObject,   // Object Type
    3427             :                                                      thisDXCoil.Name,       // Object Name
    3428          13 :                                                      cAlphaFields(17));     // Field Name
    3429             : 
    3430          13 :                 if (!ErrorsFound) {
    3431             :                     //       Test PLF curve minimum and maximum. Cap if less than 0.7 or greater than 1.0.
    3432          13 :                     MinCurveVal = 999.0;
    3433          13 :                     MaxCurveVal = -999.0;
    3434          13 :                     CurveInput = 0.0;
    3435        1313 :                     while (CurveInput <= 1.0) {
    3436        1300 :                         CurveVal = CurveValue(state, thisDXCoil.PLFFPLR(1), CurveInput);
    3437        1300 :                         if (CurveVal < MinCurveVal) {
    3438          13 :                             MinCurveVal = CurveVal;
    3439          13 :                             MinCurvePLR = CurveInput;
    3440             :                         }
    3441        1300 :                         if (CurveVal > MaxCurveVal) {
    3442        1300 :                             MaxCurveVal = CurveVal;
    3443        1300 :                             MaxCurvePLR = CurveInput;
    3444             :                         }
    3445        1300 :                         CurveInput += 0.01;
    3446             :                     }
    3447          13 :                     if (MinCurveVal < 0.7) {
    3448           0 :                         ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3449           0 :                         ShowContinueError(state, format("...{} = {} has out of range value.", cAlphaFields(17), Alphas(17)));
    3450           0 :                         ShowContinueError(state,
    3451           0 :                                           format("...Curve minimum must be >= 0.7, curve min at PLR = {:.2T} is {:.3T}", MinCurvePLR, MinCurveVal));
    3452           0 :                         ShowContinueError(state, "...Setting curve minimum to 0.7 and simulation continues.");
    3453           0 :                         Curve::SetCurveOutputMinValue(state, thisDXCoil.PLFFPLR(1), ErrorsFound, 0.7);
    3454             :                     }
    3455             : 
    3456          13 :                     if (MaxCurveVal > 1.0) {
    3457           0 :                         ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3458           0 :                         ShowContinueError(state, format("...{} = {} has out of range value.", cAlphaFields(17), Alphas(17)));
    3459           0 :                         ShowContinueError(state,
    3460           0 :                                           format("...Curve maximum must be <= 1.0, curve max at PLR = {:.2T} is {:.3T}", MaxCurvePLR, MaxCurveVal));
    3461           0 :                         ShowContinueError(state, "...Setting curve maximum to 1.0 and simulation continues.");
    3462           0 :                         Curve::SetCurveOutputMaxValue(state, thisDXCoil.PLFFPLR(1), ErrorsFound, 1.0);
    3463             :                     }
    3464             :                 }
    3465             :             }
    3466             :         }
    3467             : 
    3468             :         // assume compressor resides at the inlet to the DX Coil
    3469          13 :         thisDXCoil.CondenserInletNodeNum(1) = thisDXCoil.AirInNode;
    3470             : 
    3471             :         // set condenser type as HPWH
    3472          13 :         thisDXCoil.CondenserType(1) = DataHeatBalance::RefrigCondenserType::WaterHeater;
    3473             : 
    3474             :     } // end of the DX water heater coil loop
    3475             : 
    3476         247 :     if (ErrorsFound) {
    3477           0 :         ShowFatalError(state,
    3478           0 :                        format("{}Errors found in getting {} input. Preceding condition(s) causes termination.", RoutineName, CurrentModuleObject));
    3479             :     }
    3480             :     // Loop over the Wrapped DX Water Heater Coils and get & load the data
    3481         247 :     CurrentModuleObject = HVAC::cAllCoilTypes(HVAC::CoilDX_HeatPumpWaterHeaterWrapped);
    3482         250 :     for (DXHPWaterHeaterCoilNum = 1; DXHPWaterHeaterCoilNum <= state.dataDXCoils->NumDXHeatPumpWaterHeaterWrappedCoils; ++DXHPWaterHeaterCoilNum) {
    3483             : 
    3484           3 :         state.dataInputProcessing->inputProcessor->getObjectItem(state,
    3485             :                                                                  CurrentModuleObject,
    3486             :                                                                  DXHPWaterHeaterCoilNum,
    3487             :                                                                  Alphas,
    3488             :                                                                  NumAlphas,
    3489             :                                                                  Numbers,
    3490             :                                                                  NumNumbers,
    3491             :                                                                  IOStatus,
    3492             :                                                                  lNumericBlanks,
    3493             :                                                                  lAlphaBlanks,
    3494             :                                                                  cAlphaFields,
    3495             :                                                                  cNumericFields);
    3496             : 
    3497           3 :         ++DXCoilNum;
    3498             : 
    3499             :         // allocate single performance mode for numeric field strings used for sizing routine
    3500           3 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode.allocate(1);
    3501           3 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames.allocate(MaxNumbers);
    3502           3 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames = cNumericFields;
    3503             :         // ErrorsFound will be set to True if problem was found, left untouched otherwise
    3504           3 :         VerifyUniqueCoilName(state, CurrentModuleObject, Alphas(1), ErrorsFound, CurrentModuleObject + " Name");
    3505             : 
    3506           3 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    3507           3 :         thisDXCoil.Name = Alphas(1);
    3508           3 :         thisDXCoil.DXCoilType = CurrentModuleObject;
    3509           3 :         thisDXCoil.DXCoilType_Num = HVAC::CoilDX_HeatPumpWaterHeaterWrapped;
    3510           3 :         thisDXCoil.SchedPtr = 0; // heat pump water heater DX coil has no schedule
    3511             : 
    3512             :         // Store the HPWH DX coil heating capacity in RatedTotCap2. After backing off pump and fan heat,
    3513             :         // move to RatedTotCap() for use by DX coil
    3514           3 :         thisDXCoil.RatedTotCap2 = Numbers(1);
    3515           3 :         if (thisDXCoil.RatedTotCap2 <= 0.0) {
    3516           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3517           0 :             ShowContinueError(state, format("...{} must be > 0.0, entered value=[{:.2T}].", cNumericFields(1), Numbers(1)));
    3518           0 :             ErrorsFound = true;
    3519             :         }
    3520             : 
    3521           3 :         thisDXCoil.RatedCOP(1) = Numbers(2);
    3522           3 :         if (thisDXCoil.RatedCOP(1) <= 0.0) {
    3523           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3524           0 :             ShowContinueError(state, format("...{} must be > 0.0, entered value=[{:.2T}].", cNumericFields(2), Numbers(2)));
    3525           0 :             ErrorsFound = true;
    3526             :         }
    3527             : 
    3528           3 :         thisDXCoil.RatedSHR(1) = Numbers(3);
    3529           3 :         if (thisDXCoil.RatedSHR(1) <= 0.0 || thisDXCoil.RatedSHR(1) > 1.0) {
    3530           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3531           0 :             ShowContinueError(state, format("...{} must be > 0 and <= 1.  entered value=[{:.3T}].", cNumericFields(3), Numbers(3)));
    3532             : 
    3533           0 :             ErrorsFound = true;
    3534             :         }
    3535             : 
    3536           3 :         thisDXCoil.RatedInletDBTemp = Numbers(4);
    3537           3 :         if (thisDXCoil.RatedInletDBTemp <= 5.0) {
    3538           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3539           0 :             ShowContinueError(state, format("...{} must be > 5 {{C}}.  entered value=[{:.1T}].", cNumericFields(4), Numbers(4)));
    3540           0 :             ErrorsFound = true;
    3541             :         }
    3542             : 
    3543           3 :         thisDXCoil.RatedInletWBTemp = Numbers(5);
    3544           3 :         if (thisDXCoil.RatedInletWBTemp <= 5.0) {
    3545           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3546           0 :             ShowContinueError(state, format("...{} must be > 5 {{C}}.  entered value=[{:.1T}].", cNumericFields(5), Numbers(5)));
    3547           0 :             ErrorsFound = true;
    3548             :         }
    3549             : 
    3550           3 :         thisDXCoil.RatedInletWaterTemp = Numbers(6);
    3551           3 :         if (thisDXCoil.RatedInletWaterTemp <= 25.0) {
    3552           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3553           0 :             ShowContinueError(state, format("...{} must be > 25 {{C}}.  entered value=[{:.1T}].", cNumericFields(6), Numbers(6)));
    3554           0 :             ErrorsFound = true;
    3555             :         }
    3556             : 
    3557           3 :         thisDXCoil.RatedAirVolFlowRate(1) = Numbers(7);
    3558           3 :         if (thisDXCoil.RatedAirVolFlowRate(1) != Constant::AutoCalculate) {
    3559           3 :             if (thisDXCoil.RatedAirVolFlowRate(1) <= 0.0) {
    3560           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3561           0 :                 ShowContinueError(state, format("...{} must be > 0.0.  entered value=[{:.3T}].", cNumericFields(7), Numbers(7)));
    3562           0 :                 ErrorsFound = true;
    3563             :             }
    3564             :         }
    3565             : 
    3566           3 :         if (Util::SameString(Alphas(2), "Yes") || Util::SameString(Alphas(2), "No")) {
    3567             :             //  initialized to TRUE on allocate
    3568           3 :             if (Util::SameString(Alphas(2), "No")) thisDXCoil.FanPowerIncludedInCOP = false;
    3569             :         } else {
    3570           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3571           0 :             ShowContinueError(state, format(",,,invalid choice for {}.  Entered choice = {}", cAlphaFields(2), Alphas(2)));
    3572           0 :             ShowContinueError(state, "Valid choices are Yes or No.");
    3573           0 :             ErrorsFound = true;
    3574             :         }
    3575             : 
    3576             :         // Air nodes
    3577           3 :         thisDXCoil.AirInNode = GetOnlySingleNode(state,
    3578           3 :                                                  Alphas(3),
    3579             :                                                  ErrorsFound,
    3580             :                                                  DataLoopNode::ConnectionObjectType::CoilWaterHeatingAirToWaterHeatPumpWrapped,
    3581           3 :                                                  Alphas(1),
    3582             :                                                  DataLoopNode::NodeFluidType::Air,
    3583             :                                                  DataLoopNode::ConnectionType::Inlet,
    3584             :                                                  NodeInputManager::CompFluidStream::Primary,
    3585             :                                                  ObjectIsNotParent);
    3586             : 
    3587           3 :         thisDXCoil.AirOutNode = GetOnlySingleNode(state,
    3588           3 :                                                   Alphas(4),
    3589             :                                                   ErrorsFound,
    3590             :                                                   DataLoopNode::ConnectionObjectType::CoilWaterHeatingAirToWaterHeatPumpWrapped,
    3591           3 :                                                   Alphas(1),
    3592             :                                                   DataLoopNode::NodeFluidType::Air,
    3593             :                                                   DataLoopNode::ConnectionType::Outlet,
    3594             :                                                   NodeInputManager::CompFluidStream::Primary,
    3595             :                                                   ObjectIsNotParent);
    3596             : 
    3597           3 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(3), Alphas(4), "Air Nodes");
    3598             : 
    3599             :         // Check if the air inlet node is OA node, to justify whether the coil is placed in zone or not
    3600           3 :         thisDXCoil.IsDXCoilInZone = !CheckOutAirNodeNumber(state, thisDXCoil.AirInNode);
    3601             : 
    3602           3 :         std::string const DummyCondenserInletName("DUMMY CONDENSER INLET " + thisDXCoil.Name);
    3603           3 :         std::string const DummyCondenserOutletName("DUMMY CONDENSER OUTLET " + thisDXCoil.Name);
    3604           3 :         thisDXCoil.WaterInNode = GetOnlySingleNode(state,
    3605             :                                                    DummyCondenserInletName,
    3606             :                                                    ErrorsFound,
    3607             :                                                    DataLoopNode::ConnectionObjectType::CoilWaterHeatingAirToWaterHeatPumpWrapped,
    3608           3 :                                                    Alphas(1),
    3609             :                                                    DataLoopNode::NodeFluidType::Water,
    3610             :                                                    DataLoopNode::ConnectionType::Inlet,
    3611             :                                                    NodeInputManager::CompFluidStream::Secondary,
    3612             :                                                    ObjectIsNotParent);
    3613             : 
    3614           3 :         thisDXCoil.WaterOutNode = GetOnlySingleNode(state,
    3615             :                                                     DummyCondenserOutletName,
    3616             :                                                     ErrorsFound,
    3617             :                                                     DataLoopNode::ConnectionObjectType::CoilWaterHeatingAirToWaterHeatPumpWrapped,
    3618           3 :                                                     Alphas(1),
    3619             :                                                     DataLoopNode::NodeFluidType::Water,
    3620             :                                                     DataLoopNode::ConnectionType::Outlet,
    3621             :                                                     NodeInputManager::CompFluidStream::Secondary,
    3622             :                                                     ObjectIsNotParent);
    3623             : 
    3624           3 :         TestCompSet(state, CurrentModuleObject, Alphas(1), DummyCondenserInletName, DummyCondenserOutletName, "Water Nodes");
    3625             : 
    3626           3 :         thisDXCoil.CrankcaseHeaterCapacity = Numbers(8);
    3627           3 :         if (thisDXCoil.CrankcaseHeaterCapacity < 0.0) {
    3628           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3629           0 :             ShowContinueError(state, format("...{} must be >= 0.0  entered value=[{:.1T}].", cNumericFields(8), Numbers(8)));
    3630           0 :             ErrorsFound = true;
    3631             :         }
    3632             : 
    3633           3 :         thisDXCoil.MaxOATCrankcaseHeater = Numbers(9);
    3634           3 :         if (thisDXCoil.MaxOATCrankcaseHeater < 0.0) {
    3635           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3636           0 :             ShowContinueError(state, format("...{} must be >= 0 {{C}}.  entered value=[{:.1T}].", cNumericFields(9), Numbers(9)));
    3637           0 :             ErrorsFound = true;
    3638             :         }
    3639             : 
    3640             :         // Coil:WaterHeating:AirToWaterHeatPump:Wrapped
    3641           3 :         if (!lAlphaBlanks(5)) {
    3642           0 :             thisDXCoil.CrankcaseHeaterCapacityCurveIndex = Curve::GetCurveIndex(state, Alphas(5));
    3643           0 :             ErrorsFound |= Curve::CheckCurveDims(state,
    3644             :                                                  thisDXCoil.CrankcaseHeaterCapacityCurveIndex, // Curve index
    3645             :                                                  {1},                                          // Valid dimensions
    3646             :                                                  RoutineName,                                  // Routine name
    3647             :                                                  CurrentModuleObject,                          // Object Type
    3648             :                                                  thisDXCoil.Name,                              // Object Name
    3649           0 :                                                  cAlphaFields(5));                             // Field Name
    3650             :         }
    3651             : 
    3652           3 :         if (Util::SameString(Alphas(6), "DryBulbTemperature")) {
    3653           0 :             thisDXCoil.InletAirTemperatureType = HVAC::OATType::DryBulb;
    3654           3 :         } else if (Util::SameString(Alphas(6), "WetBulbTemperature")) {
    3655           3 :             thisDXCoil.InletAirTemperatureType = HVAC::OATType::WetBulb;
    3656             :         } else {
    3657             :             //   wrong temperature type selection
    3658           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3659           0 :             ShowContinueError(state, format("...{} must be DryBulbTemperature or WetBulbTemperature.", cAlphaFields(6)));
    3660           0 :             ShowContinueError(state, format("...entered value=\"{}\".", Alphas(6)));
    3661           0 :             ErrorsFound = true;
    3662             :         }
    3663             : 
    3664             :         // set rated inlet air temperature for curve object verification
    3665           3 :         if (thisDXCoil.InletAirTemperatureType == HVAC::OATType::WetBulb) {
    3666           3 :             InletAirTemp = thisDXCoil.RatedInletWBTemp;
    3667             :         } else {
    3668           0 :             InletAirTemp = thisDXCoil.RatedInletDBTemp;
    3669             :         }
    3670             :         // set rated water temperature for curve object verification
    3671           3 :         InletWaterTemp = thisDXCoil.RatedInletWaterTemp;
    3672             : 
    3673           3 :         if (!lAlphaBlanks(7)) {
    3674           3 :             thisDXCoil.HCapFTemp = GetCurveIndex(state, Alphas(7));
    3675           3 :             if (thisDXCoil.HCapFTemp == 0) {
    3676           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3677           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(7), Alphas(7)));
    3678           0 :                 ErrorsFound = true;
    3679             :             } else {
    3680             :                 // Verify Curve Object, only legal types are BiQuadratic or Cubic
    3681           3 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    3682             :                                                      thisDXCoil.HCapFTemp, // Curve index
    3683             :                                                      {1, 2},               // Valid dimensions  // MULTIPLECURVEDIMS
    3684             :                                                      RoutineName,          // Routine name
    3685             :                                                      CurrentModuleObject,  // Object Type
    3686             :                                                      thisDXCoil.Name,      // Object Name
    3687           3 :                                                      cAlphaFields(7));     // Field Name
    3688             : 
    3689           3 :                 if (!ErrorsFound) {
    3690           3 :                     if (state.dataCurveManager->PerfCurve(thisDXCoil.HCapFTemp)->numDims == 1) {
    3691           0 :                         checkCurveIsNormalizedToOne(state,
    3692           0 :                                                     std::string{RoutineName} + CurrentModuleObject,
    3693           0 :                                                     thisDXCoil.Name,
    3694             :                                                     thisDXCoil.HCapFTemp,
    3695           0 :                                                     cAlphaFields(7),
    3696           0 :                                                     Alphas(7),
    3697             :                                                     InletAirTemp);
    3698             :                     } else {
    3699           3 :                         checkCurveIsNormalizedToOne(state,
    3700           6 :                                                     std::string{RoutineName} + CurrentModuleObject,
    3701           3 :                                                     thisDXCoil.Name,
    3702             :                                                     thisDXCoil.HCapFTemp,
    3703           3 :                                                     cAlphaFields(7),
    3704           3 :                                                     Alphas(7),
    3705             :                                                     InletAirTemp,
    3706             :                                                     InletWaterTemp);
    3707             :                     }
    3708             :                 }
    3709             :             }
    3710             :         }
    3711             : 
    3712           3 :         if (!lAlphaBlanks(8)) {
    3713           0 :             thisDXCoil.HCapFAirFlow = GetCurveIndex(state, Alphas(8));
    3714           0 :             if (thisDXCoil.HCapFAirFlow == 0) {
    3715           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3716           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(8), Alphas(8)));
    3717           0 :                 ErrorsFound = true;
    3718             :             } else {
    3719             :                 // Verify Curve Object, only legal types are Cubic or Quadratic
    3720           0 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    3721             :                                                      thisDXCoil.HCapFAirFlow, // Curve index
    3722             :                                                      {1},                     // Valid dimensions
    3723             :                                                      RoutineName,             // Routine name
    3724             :                                                      CurrentModuleObject,     // Object Type
    3725             :                                                      thisDXCoil.Name,         // Object Name
    3726           0 :                                                      cAlphaFields(8));        // Field Name
    3727             : 
    3728           0 :                 if (!ErrorsFound) {
    3729           0 :                     checkCurveIsNormalizedToOne(state,
    3730           0 :                                                 std::string{RoutineName} + CurrentModuleObject,
    3731           0 :                                                 thisDXCoil.Name,
    3732             :                                                 thisDXCoil.HCapFAirFlow,
    3733           0 :                                                 cAlphaFields(8),
    3734           0 :                                                 Alphas(8),
    3735             :                                                 1.0);
    3736             :                 }
    3737             :             }
    3738             :         }
    3739             : 
    3740           3 :         if (!lAlphaBlanks(9)) {
    3741           3 :             thisDXCoil.HCOPFTemp = GetCurveIndex(state, Alphas(9));
    3742           3 :             if (thisDXCoil.HCOPFTemp == 0) {
    3743           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3744           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(9), Alphas(9)));
    3745           0 :                 ErrorsFound = true;
    3746             :             } else {
    3747             :                 // Verify Curve Object, only legal types are BiQuadratic or Cubic
    3748           3 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    3749             :                                                      thisDXCoil.HCOPFTemp, // Curve index
    3750             :                                                      {1, 2},               // Valid dimensions  // MULTIPLECURVEDIMS
    3751             :                                                      RoutineName,          // Routine name
    3752             :                                                      CurrentModuleObject,  // Object Type
    3753             :                                                      thisDXCoil.Name,      // Object Name
    3754           3 :                                                      cAlphaFields(9));     // Field Name
    3755             : 
    3756           3 :                 if (!ErrorsFound) {
    3757           3 :                     if (state.dataCurveManager->PerfCurve(thisDXCoil.HCOPFTemp)->numDims == 1) {
    3758           0 :                         checkCurveIsNormalizedToOne(state,
    3759           0 :                                                     std::string{RoutineName} + CurrentModuleObject,
    3760           0 :                                                     thisDXCoil.Name,
    3761             :                                                     thisDXCoil.HCOPFTemp,
    3762           0 :                                                     cAlphaFields(9),
    3763           0 :                                                     Alphas(9),
    3764             :                                                     InletAirTemp);
    3765             :                     } else {
    3766           3 :                         checkCurveIsNormalizedToOne(state,
    3767           6 :                                                     std::string{RoutineName} + CurrentModuleObject,
    3768           3 :                                                     thisDXCoil.Name,
    3769             :                                                     thisDXCoil.HCOPFTemp,
    3770           3 :                                                     cAlphaFields(9),
    3771           3 :                                                     Alphas(9),
    3772             :                                                     InletAirTemp,
    3773             :                                                     InletWaterTemp);
    3774             :                     }
    3775             :                 }
    3776             :             }
    3777             :         }
    3778             : 
    3779           3 :         if (!lAlphaBlanks(10)) {
    3780           0 :             thisDXCoil.HCOPFAirFlow = GetCurveIndex(state, Alphas(10));
    3781           0 :             if (thisDXCoil.HCOPFAirFlow == 0) {
    3782           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3783           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(10), Alphas(10)));
    3784           0 :                 ErrorsFound = true;
    3785             :             } else {
    3786             :                 // Verify Curve Object, only legal types are Cubic or Quadratic
    3787           0 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    3788             :                                                      thisDXCoil.HCOPFAirFlow, // Curve index
    3789             :                                                      {1},                     // Valid dimensions
    3790             :                                                      RoutineName,             // Routine name
    3791             :                                                      CurrentModuleObject,     // Object Type
    3792             :                                                      thisDXCoil.Name,         // Object Name
    3793           0 :                                                      cAlphaFields(10));       // Field Name
    3794             : 
    3795           0 :                 if (!ErrorsFound) {
    3796           0 :                     checkCurveIsNormalizedToOne(state,
    3797           0 :                                                 std::string{RoutineName} + CurrentModuleObject,
    3798           0 :                                                 thisDXCoil.Name,
    3799             :                                                 thisDXCoil.HCOPFAirFlow,
    3800           0 :                                                 cAlphaFields(10),
    3801           0 :                                                 Alphas(10),
    3802             :                                                 1.0);
    3803             :                 }
    3804             :             }
    3805             :         }
    3806             : 
    3807           3 :         if (!lAlphaBlanks(11)) {
    3808           3 :             thisDXCoil.PLFFPLR(1) = GetCurveIndex(state, Alphas(11));
    3809           3 :             if (thisDXCoil.PLFFPLR(1) == 0) {
    3810           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3811           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(11), Alphas(11)));
    3812           0 :                 ErrorsFound = true;
    3813             :             } else {
    3814             :                 // Verify Curve Object, only legal types are Cubic or Quadratic
    3815           6 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    3816           3 :                                                      thisDXCoil.PLFFPLR(1), // Curve index
    3817             :                                                      {1},                   // Valid dimensions
    3818             :                                                      RoutineName,           // Routine name
    3819             :                                                      CurrentModuleObject,   // Object Type
    3820             :                                                      thisDXCoil.Name,       // Object Name
    3821           3 :                                                      cAlphaFields(11));     // Field Name
    3822             : 
    3823           3 :                 if (!ErrorsFound) {
    3824             :                     //       Test PLF curve minimum and maximum. Cap if less than 0.7 or greater than 1.0.
    3825           3 :                     MinCurveVal = 999.0;
    3826           3 :                     MaxCurveVal = -999.0;
    3827           3 :                     CurveInput = 0.0;
    3828         303 :                     while (CurveInput <= 1.0) {
    3829         300 :                         CurveVal = CurveValue(state, thisDXCoil.PLFFPLR(1), CurveInput);
    3830         300 :                         if (CurveVal < MinCurveVal) {
    3831           3 :                             MinCurveVal = CurveVal;
    3832           3 :                             MinCurvePLR = CurveInput;
    3833             :                         }
    3834         300 :                         if (CurveVal > MaxCurveVal) {
    3835           3 :                             MaxCurveVal = CurveVal;
    3836           3 :                             MaxCurvePLR = CurveInput;
    3837             :                         }
    3838         300 :                         CurveInput += 0.01;
    3839             :                     }
    3840           3 :                     if (MinCurveVal < 0.7) {
    3841           0 :                         ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3842           0 :                         ShowContinueError(state, format("...{} = {} has out of range value.", cAlphaFields(11), Alphas(11)));
    3843           0 :                         ShowContinueError(state,
    3844           0 :                                           format("...Curve minimum must be >= 0.7, curve min at PLR = {:.2T} is {:.3T}", MinCurvePLR, MinCurveVal));
    3845           0 :                         ShowContinueError(state, "...Setting curve minimum to 0.7 and simulation continues.");
    3846           0 :                         Curve::SetCurveOutputMinValue(state, thisDXCoil.PLFFPLR(1), ErrorsFound, 0.7);
    3847             :                     }
    3848             : 
    3849           3 :                     if (MaxCurveVal > 1.0) {
    3850           0 :                         ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3851           0 :                         ShowContinueError(state, format("...{} = {} has out of range value.", cAlphaFields(11), Alphas(11)));
    3852           0 :                         ShowContinueError(state,
    3853           0 :                                           format("...Curve maximum must be <= 1.0, curve max at PLR = {:.2T} is {:.3T}", MaxCurvePLR, MaxCurveVal));
    3854           0 :                         ShowContinueError(state, "...Setting curve maximum to 1.0 and simulation continues.");
    3855           0 :                         Curve::SetCurveOutputMaxValue(state, thisDXCoil.PLFFPLR(1), ErrorsFound, 1.0);
    3856             :                     }
    3857             :                 }
    3858             :             }
    3859             :         }
    3860             : 
    3861             :         // assume compressor resides at the inlet to the DX Coil
    3862           3 :         thisDXCoil.CondenserInletNodeNum(1) = thisDXCoil.AirInNode;
    3863             : 
    3864             :         // set condenser type as HPWH
    3865           3 :         thisDXCoil.CondenserType(1) = DataHeatBalance::RefrigCondenserType::WaterHeater;
    3866             : 
    3867           3 :     } // end of the DX water heater wrapped coil loop
    3868             : 
    3869         247 :     if (ErrorsFound) {
    3870           0 :         ShowFatalError(state,
    3871           0 :                        format("{}Errors found in getting {} input. Preceding condition(s) causes termination.", RoutineName, CurrentModuleObject));
    3872             :     }
    3873             : 
    3874             :     // DX Multispeed cooling coil
    3875         247 :     CurrentModuleObject = "Coil:Cooling:DX:MultiSpeed";
    3876         296 :     for (DXCoilIndex = 1; DXCoilIndex <= state.dataDXCoils->NumDXMulSpeedCoolCoils; ++DXCoilIndex) {
    3877             : 
    3878          49 :         ++DXCoilNum;
    3879             : 
    3880          49 :         state.dataInputProcessing->inputProcessor->getObjectItem(state,
    3881             :                                                                  CurrentModuleObject,
    3882             :                                                                  DXCoilIndex,
    3883             :                                                                  Alphas,
    3884             :                                                                  NumAlphas,
    3885             :                                                                  Numbers,
    3886             :                                                                  NumNumbers,
    3887             :                                                                  IOStatus,
    3888             :                                                                  lNumericBlanks,
    3889             :                                                                  lAlphaBlanks,
    3890             :                                                                  cAlphaFields,
    3891             :                                                                  cNumericFields);
    3892             : 
    3893             :         // allocate single performance mode for numeric field strings used for sizing routine (all fields are in this object)
    3894          49 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode.allocate(1);
    3895          49 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames.allocate(MaxNumbers);
    3896          49 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames = cNumericFields;
    3897             :         // ErrorsFound will be set to True if problem was found, left untouched otherwise
    3898          49 :         VerifyUniqueCoilName(state, CurrentModuleObject, Alphas(1), ErrorsFound, CurrentModuleObject + " Name");
    3899             : 
    3900          49 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    3901          49 :         thisDXCoil.Name = Alphas(1);
    3902             :         // Initialize DataHeatBalance heat reclaim variable name for use by heat reclaim coils
    3903          49 :         state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).Name = thisDXCoil.Name;
    3904          49 :         state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).SourceType = CurrentModuleObject;
    3905          49 :         thisDXCoil.DXCoilType = CurrentModuleObject;
    3906          49 :         thisDXCoil.DXCoilType_Num = HVAC::CoilDX_MultiSpeedCooling;
    3907          49 :         thisDXCoil.Schedule = Alphas(2);
    3908          49 :         if (lAlphaBlanks(2)) {
    3909           2 :             thisDXCoil.SchedPtr = ScheduleManager::ScheduleAlwaysOn;
    3910             :         } else {
    3911          47 :             thisDXCoil.SchedPtr = GetScheduleIndex(state, Alphas(2)); // convert schedule name to pointer
    3912          47 :             if (thisDXCoil.SchedPtr == 0) {
    3913           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3914           0 :                 ShowContinueError(state, format("...{}=\"{}\".", cAlphaFields(2), Alphas(2)));
    3915           0 :                 ErrorsFound = true;
    3916             :             }
    3917             :         }
    3918             : 
    3919          49 :         thisDXCoil.AirInNode = GetOnlySingleNode(state,
    3920          49 :                                                  Alphas(3),
    3921             :                                                  ErrorsFound,
    3922             :                                                  DataLoopNode::ConnectionObjectType::CoilCoolingDXMultiSpeed,
    3923          49 :                                                  Alphas(1),
    3924             :                                                  DataLoopNode::NodeFluidType::Air,
    3925             :                                                  DataLoopNode::ConnectionType::Inlet,
    3926             :                                                  NodeInputManager::CompFluidStream::Primary,
    3927             :                                                  ObjectIsNotParent);
    3928             : 
    3929          49 :         thisDXCoil.AirOutNode = GetOnlySingleNode(state,
    3930          49 :                                                   Alphas(4),
    3931             :                                                   ErrorsFound,
    3932             :                                                   DataLoopNode::ConnectionObjectType::CoilCoolingDXMultiSpeed,
    3933          49 :                                                   Alphas(1),
    3934             :                                                   DataLoopNode::NodeFluidType::Air,
    3935             :                                                   DataLoopNode::ConnectionType::Outlet,
    3936             :                                                   NodeInputManager::CompFluidStream::Primary,
    3937             :                                                   ObjectIsNotParent);
    3938             : 
    3939          49 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(3), Alphas(4), "Air Nodes");
    3940             : 
    3941             :         // outdoor condenser node
    3942          49 :         if (lAlphaBlanks(5)) {
    3943          33 :             thisDXCoil.CondenserInletNodeNum(1) = 0;
    3944             :         } else {
    3945          32 :             thisDXCoil.CondenserInletNodeNum(1) = GetOnlySingleNode(state,
    3946          16 :                                                                     Alphas(5),
    3947             :                                                                     ErrorsFound,
    3948             :                                                                     DataLoopNode::ConnectionObjectType::CoilCoolingDXMultiSpeed,
    3949          16 :                                                                     thisDXCoil.Name,
    3950             :                                                                     DataLoopNode::NodeFluidType::Air,
    3951             :                                                                     DataLoopNode::ConnectionType::OutsideAirReference,
    3952             :                                                                     NodeInputManager::CompFluidStream::Primary,
    3953             :                                                                     ObjectIsNotParent);
    3954          16 :             if (!CheckOutAirNodeNumber(state, thisDXCoil.CondenserInletNodeNum(1))) {
    3955           0 :                 ShowWarningError(state, format("{}{}=\"{}\", may be invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3956           0 :                 ShowContinueError(
    3957           0 :                     state, format("{}=\"{}\", node does not appear in an OutdoorAir:NodeList or as an OutdoorAir:Node.", cAlphaFields(5), Alphas(5)));
    3958           0 :                 ShowContinueError(
    3959             :                     state, "This node needs to be included in an air system or the coil model will not be valid, and the simulation continues");
    3960             :             }
    3961             :         }
    3962             : 
    3963          49 :         if ((Util::SameString(Alphas(6), "AirCooled")) || lAlphaBlanks(6)) {
    3964          49 :             thisDXCoil.CondenserType(1) = DataHeatBalance::RefrigCondenserType::Air;
    3965           0 :         } else if (Util::SameString(Alphas(6), "EvaporativelyCooled")) {
    3966           0 :             thisDXCoil.CondenserType(1) = DataHeatBalance::RefrigCondenserType::Evap;
    3967           0 :             thisDXCoil.ReportEvapCondVars = true;
    3968             :         } else {
    3969           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    3970           0 :             ShowContinueError(state, format("...{}=\"{}\":", cAlphaFields(6), Alphas(6)));
    3971           0 :             ShowContinueError(state, "...must be AirCooled or EvaporativelyCooled.");
    3972           0 :             ErrorsFound = true;
    3973             :         }
    3974             : 
    3975             :         // Get Water System tank connections
    3976             :         //  A8, \field Name of Water Storage Tank for Supply
    3977          49 :         thisDXCoil.EvapWaterSupplyName = Alphas(7);
    3978          49 :         if (lAlphaBlanks(7)) {
    3979          49 :             thisDXCoil.EvapWaterSupplyMode = EvapWaterSupply::FromMains;
    3980             :         } else {
    3981           0 :             thisDXCoil.EvapWaterSupplyMode = EvapWaterSupply::FromTank;
    3982           0 :             SetupTankDemandComponent(state,
    3983             :                                      thisDXCoil.Name,
    3984             :                                      CurrentModuleObject,
    3985             :                                      thisDXCoil.EvapWaterSupplyName,
    3986             :                                      ErrorsFound,
    3987           0 :                                      thisDXCoil.EvapWaterSupTankID,
    3988           0 :                                      thisDXCoil.EvapWaterTankDemandARRID);
    3989             :         }
    3990             : 
    3991             :         // A9; \field Name of Water Storage Tank for Condensate Collection
    3992          49 :         thisDXCoil.CondensateCollectName = Alphas(8);
    3993          49 :         if (lAlphaBlanks(8)) {
    3994          49 :             thisDXCoil.CondensateCollectMode = CondensateCollectAction::Discard;
    3995             :         } else {
    3996           0 :             thisDXCoil.CondensateCollectMode = CondensateCollectAction::ToTank;
    3997           0 :             SetupTankSupplyComponent(state,
    3998             :                                      thisDXCoil.Name,
    3999             :                                      CurrentModuleObject,
    4000             :                                      thisDXCoil.CondensateCollectName,
    4001             :                                      ErrorsFound,
    4002           0 :                                      thisDXCoil.CondensateTankID,
    4003           0 :                                      thisDXCoil.CondensateTankSupplyARRID);
    4004             :         }
    4005             : 
    4006             :         // Set minimum OAT for compressor operation
    4007          49 :         thisDXCoil.MinOATCompressor = Numbers(1);
    4008             : 
    4009             :         // Set crankcase heater capacity
    4010          49 :         thisDXCoil.CrankcaseHeaterCapacity = Numbers(2);
    4011          49 :         if (thisDXCoil.CrankcaseHeaterCapacity < 0.0) {
    4012           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4013           0 :             ShowContinueError(state, format("...{} cannot be < 0.0.", cNumericFields(2)));
    4014           0 :             ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(2)));
    4015           0 :             ErrorsFound = true;
    4016             :         }
    4017             : 
    4018             :         // Set crankcase heater cutout temperature
    4019          49 :         thisDXCoil.MaxOATCrankcaseHeater = Numbers(3);
    4020             : 
    4021          49 :         if (Util::SameString(Alphas(9), "Yes")) {
    4022           0 :             thisDXCoil.PLRImpact = true;
    4023          49 :         } else if (Util::SameString(Alphas(9), "No")) {
    4024          49 :             thisDXCoil.PLRImpact = false;
    4025             :         } else {
    4026           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4027           0 :             ShowContinueError(state, format(",,,invalid choice for {}.  Entered choice = {}", cAlphaFields(9), Alphas(9)));
    4028           0 :             ShowContinueError(state, "The allowed choices are Yes or No.");
    4029           0 :             ErrorsFound = true;
    4030             :         }
    4031             : 
    4032          49 :         if (Util::SameString(Alphas(10), "Yes")) {
    4033           0 :             thisDXCoil.LatentImpact = true;
    4034          49 :         } else if (Util::SameString(Alphas(10), "No")) {
    4035          49 :             thisDXCoil.LatentImpact = false;
    4036             :         } else {
    4037           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4038           0 :             ShowContinueError(state, format(",,,invalid choice for {}.  Entered choice = {}", cAlphaFields(10), Alphas(10)));
    4039           0 :             ShowContinueError(state, "The allowed choices are Yes or No.");
    4040           0 :             ErrorsFound = true;
    4041             :         }
    4042             : 
    4043             :         //   Basin heater power as a function of temperature must be greater than or equal to 0
    4044          49 :         thisDXCoil.BasinHeaterPowerFTempDiff = Numbers(4);
    4045          49 :         if (Numbers(4) < 0.0) {
    4046           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4047           0 :             ShowContinueError(state, format("...{} must be >= 0.0, entered value=[{:.3T}].", cNumericFields(4), Numbers(4)));
    4048           0 :             ErrorsFound = true;
    4049             :         }
    4050             : 
    4051          49 :         thisDXCoil.BasinHeaterSetPointTemp = Numbers(5);
    4052          49 :         if (thisDXCoil.BasinHeaterPowerFTempDiff > 0.0) {
    4053           0 :             if (NumNumbers < 5) {
    4054           0 :                 thisDXCoil.BasinHeaterSetPointTemp = 2.0;
    4055             :             }
    4056           0 :             if (thisDXCoil.BasinHeaterSetPointTemp < 2.0) {
    4057           0 :                 ShowWarningError(state, format("{}{}=\"{}\", freeze possible", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4058           0 :                 ShowContinueError(state, format("...{} is less than 2 {{C}}. Freezing could occur.", cNumericFields(5)));
    4059           0 :                 ShowContinueError(state, format("...entered value=[{:.2T}].", Numbers(5)));
    4060             :             }
    4061             :         }
    4062             : 
    4063          49 :         if (!lAlphaBlanks(11)) {
    4064           0 :             thisDXCoil.CrankcaseHeaterCapacityCurveIndex = Curve::GetCurveIndex(state, Alphas(11));
    4065           0 :             ErrorsFound |= Curve::CheckCurveDims(state,
    4066             :                                                  thisDXCoil.CrankcaseHeaterCapacityCurveIndex, // Curve index
    4067             :                                                  {1},                                          // Valid dimensions
    4068             :                                                  RoutineName,                                  // Routine name
    4069             :                                                  CurrentModuleObject,                          // Object Type
    4070             :                                                  thisDXCoil.Name,                              // Object Name
    4071           0 :                                                  cAlphaFields(11));                            // Field Name
    4072             :         }
    4073             : 
    4074          49 :         if (!lAlphaBlanks(12)) {
    4075           0 :             thisDXCoil.BasinHeaterSchedulePtr = GetScheduleIndex(state, Alphas(12));
    4076           0 :             if (thisDXCoil.BasinHeaterSchedulePtr == 0) {
    4077           0 :                 ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4078           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(12), Alphas(12)));
    4079           0 :                 ShowContinueError(state, "Basin heater will be available to operate throughout the simulation.");
    4080             :             }
    4081             :         }
    4082             : 
    4083             :         // A13; \field Fuel type, Validate fuel type input
    4084          49 :         thisDXCoil.FuelType = static_cast<Constant::eFuel>(getEnumValue(Constant::eFuelNamesUC, Alphas(13)));
    4085             : 
    4086          49 :         thisDXCoil.NumOfSpeeds = Numbers(6); // Number of speeds
    4087          49 :         if (thisDXCoil.NumOfSpeeds < 2) {
    4088           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4089           0 :             ShowContinueError(state, format("...{} must be >= 2. entered number is {:.0T}", cNumericFields(6), Numbers(6)));
    4090           0 :             ErrorsFound = true;
    4091             :         }
    4092             : 
    4093             :         // Allocate arrays based on the number of speeds
    4094          49 :         thisDXCoil.MSErrIndex.allocate(thisDXCoil.NumOfSpeeds);
    4095          49 :         thisDXCoil.MSErrIndex = 0;
    4096          49 :         thisDXCoil.MSRatedTotCap.allocate(thisDXCoil.NumOfSpeeds);
    4097          49 :         thisDXCoil.MSRatedTotCapDes.allocate(thisDXCoil.NumOfSpeeds);
    4098          49 :         thisDXCoil.MSRatedSHR.allocate(thisDXCoil.NumOfSpeeds);
    4099          49 :         thisDXCoil.MSRatedCOP.allocate(thisDXCoil.NumOfSpeeds);
    4100          49 :         thisDXCoil.MSRatedAirVolFlowRate.allocate(thisDXCoil.NumOfSpeeds);
    4101          49 :         thisDXCoil.MSRatedAirMassFlowRate.allocate(thisDXCoil.NumOfSpeeds);
    4102          49 :         thisDXCoil.MSRatedAirMassFlowRate = 1.0; // avoid divide by 0, will get overwritten in InitDXCoil
    4103          49 :         thisDXCoil.MSCCapFTemp.allocate(thisDXCoil.NumOfSpeeds);
    4104          49 :         thisDXCoil.MSCCapFFlow.allocate(thisDXCoil.NumOfSpeeds);
    4105          49 :         thisDXCoil.MSEIRFTemp.allocate(thisDXCoil.NumOfSpeeds);
    4106          49 :         thisDXCoil.MSEIRFFlow.allocate(thisDXCoil.NumOfSpeeds);
    4107          49 :         thisDXCoil.MSWasteHeat.allocate(thisDXCoil.NumOfSpeeds);
    4108          49 :         thisDXCoil.MSEvapCondEffect.allocate(thisDXCoil.NumOfSpeeds);
    4109          49 :         thisDXCoil.MSEvapCondAirFlow.allocate(thisDXCoil.NumOfSpeeds);
    4110          49 :         thisDXCoil.MSEvapCondPumpElecNomPower.allocate(thisDXCoil.NumOfSpeeds);
    4111          49 :         thisDXCoil.MSRatedCBF.allocate(thisDXCoil.NumOfSpeeds);
    4112          49 :         thisDXCoil.MSWasteHeatFrac.allocate(thisDXCoil.NumOfSpeeds);
    4113          49 :         thisDXCoil.MSPLFFPLR.allocate(thisDXCoil.NumOfSpeeds);
    4114          49 :         thisDXCoil.MSTwet_Rated.allocate(thisDXCoil.NumOfSpeeds);
    4115          49 :         thisDXCoil.MSGamma_Rated.allocate(thisDXCoil.NumOfSpeeds);
    4116          49 :         thisDXCoil.MSMaxONOFFCyclesperHour.allocate(thisDXCoil.NumOfSpeeds);
    4117          49 :         thisDXCoil.MSLatentCapacityTimeConstant.allocate(thisDXCoil.NumOfSpeeds);
    4118          49 :         thisDXCoil.MSFanPowerPerEvapAirFlowRate.allocate(thisDXCoil.NumOfSpeeds);
    4119          49 :         thisDXCoil.MSFanPowerPerEvapAirFlowRate_2023.allocate(thisDXCoil.NumOfSpeeds);
    4120             : 
    4121         162 :         for (I = 1; I <= thisDXCoil.NumOfSpeeds; ++I) {
    4122         113 :             thisDXCoil.MSRatedTotCap(I) = Numbers(7 + (I - 1) * 14);
    4123         113 :             thisDXCoil.MSRatedSHR(I) = Numbers(8 + (I - 1) * 14);
    4124         113 :             thisDXCoil.MSRatedCOP(I) = Numbers(9 + (I - 1) * 14);
    4125         113 :             thisDXCoil.MSRatedAirVolFlowRate(I) = Numbers(10 + (I - 1) * 14);
    4126         113 :             thisDXCoil.MSFanPowerPerEvapAirFlowRate(I) = Numbers(11 + (I - 1) * 14);
    4127         113 :             thisDXCoil.MSFanPowerPerEvapAirFlowRate_2023(I) = Numbers(12 + (I - 1) * 14);
    4128             : 
    4129         113 :             thisDXCoil.MSCCapFTemp(I) = GetCurveIndex(state, Alphas(14 + (I - 1) * 6)); // convert curve name to number
    4130         113 :             if (thisDXCoil.MSCCapFTemp(I) == 0) {
    4131           0 :                 if (lAlphaBlanks(14 + (I - 1) * 6)) {
    4132           0 :                     ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4133           0 :                     ShowContinueError(state, format("...required {} is blank.", cAlphaFields(14 + (I - 1) * 6)));
    4134             :                 } else {
    4135           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4136           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(14 + (I - 1) * 6), Alphas(14 + (I - 1) * 6)));
    4137             :                 }
    4138           0 :                 ErrorsFound = true;
    4139             :             } else {
    4140             :                 // Verify Curve Object, only legal type is BiQuadratic
    4141         226 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    4142         113 :                                                      thisDXCoil.MSCCapFTemp(I),       // Curve index
    4143             :                                                      {2},                             // Valid dimensions
    4144             :                                                      RoutineName,                     // Routine name
    4145             :                                                      CurrentModuleObject,             // Object Type
    4146             :                                                      thisDXCoil.Name,                 // Object Name
    4147         113 :                                                      cAlphaFields(14 + (I - 1) * 6)); // Field Name
    4148             : 
    4149         113 :                 if (!ErrorsFound) {
    4150         113 :                     checkCurveIsNormalizedToOne(state,
    4151         226 :                                                 std::string{RoutineName} + CurrentModuleObject,
    4152         113 :                                                 thisDXCoil.Name,
    4153         113 :                                                 thisDXCoil.MSCCapFTemp(I),
    4154         113 :                                                 cAlphaFields(14 + (I - 1) * 6),
    4155         113 :                                                 Alphas(14 + (I - 1) * 6),
    4156             :                                                 RatedInletWetBulbTemp,
    4157             :                                                 RatedOutdoorAirTemp);
    4158             :                 }
    4159             :             }
    4160             : 
    4161         113 :             thisDXCoil.MSCCapFFlow(I) = GetCurveIndex(state, Alphas(15 + (I - 1) * 6)); // convert curve name to number
    4162         113 :             if (thisDXCoil.MSCCapFFlow(I) == 0) {
    4163           0 :                 if (lAlphaBlanks(15 + (I - 1) * 6)) {
    4164           0 :                     ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4165           0 :                     ShowContinueError(state, format("...required {} is blank.", cAlphaFields(15 + (I - 1) * 6)));
    4166             :                 } else {
    4167           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4168           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(15 + (I - 1) * 6), Alphas(15 + (I - 1) * 6)));
    4169             :                 }
    4170           0 :                 ErrorsFound = true;
    4171             :             } else {
    4172             :                 // Verify Curve Object, only legal type is Quadratic
    4173         226 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    4174         113 :                                                      thisDXCoil.MSCCapFFlow(I),       // Curve index
    4175             :                                                      {1},                             // Valid dimensions
    4176             :                                                      RoutineName,                     // Routine name
    4177             :                                                      CurrentModuleObject,             // Object Type
    4178             :                                                      thisDXCoil.Name,                 // Object Name
    4179         113 :                                                      cAlphaFields(15 + (I - 1) * 6)); // Field Name
    4180             : 
    4181         113 :                 if (!ErrorsFound) {
    4182         113 :                     checkCurveIsNormalizedToOne(state,
    4183         226 :                                                 std::string{RoutineName} + CurrentModuleObject,
    4184         113 :                                                 thisDXCoil.Name,
    4185         113 :                                                 thisDXCoil.MSCCapFFlow(I),
    4186         113 :                                                 cAlphaFields(15 + (I - 1) * 6),
    4187         113 :                                                 Alphas(15 + (I - 1) * 6),
    4188             :                                                 1.0);
    4189             :                 }
    4190             :             }
    4191             : 
    4192         113 :             thisDXCoil.MSEIRFTemp(I) = GetCurveIndex(state, Alphas(16 + (I - 1) * 6)); // convert curve name to number
    4193         113 :             if (thisDXCoil.MSEIRFTemp(I) == 0) {
    4194           0 :                 if (lAlphaBlanks(16 + (I - 1) * 6)) {
    4195           0 :                     ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4196           0 :                     ShowContinueError(state, format("...required {} is blank.", cAlphaFields(16 + (I - 1) * 6)));
    4197             :                 } else {
    4198           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4199           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(16 + (I - 1) * 6), Alphas(16 + (I - 1) * 6)));
    4200             :                 }
    4201           0 :                 ErrorsFound = true;
    4202             :             } else {
    4203             :                 // Verify Curve Object, only legal type is BiQuadratic
    4204         226 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    4205         113 :                                                      thisDXCoil.MSEIRFTemp(I),        // Curve index
    4206             :                                                      {2},                             // Valid dimensions
    4207             :                                                      RoutineName,                     // Routine name
    4208             :                                                      CurrentModuleObject,             // Object Type
    4209             :                                                      thisDXCoil.Name,                 // Object Name
    4210         113 :                                                      cAlphaFields(16 + (I - 1) * 6)); // Field Name
    4211             : 
    4212         113 :                 if (!ErrorsFound) {
    4213         113 :                     checkCurveIsNormalizedToOne(state,
    4214         226 :                                                 std::string{RoutineName} + CurrentModuleObject,
    4215         113 :                                                 thisDXCoil.Name,
    4216         113 :                                                 thisDXCoil.MSEIRFTemp(I),
    4217         113 :                                                 cAlphaFields(16 + (I - 1) * 6),
    4218         113 :                                                 Alphas(16 + (I - 1) * 6),
    4219             :                                                 RatedInletWetBulbTemp,
    4220             :                                                 RatedOutdoorAirTemp);
    4221             :                 }
    4222             :             }
    4223             : 
    4224         113 :             thisDXCoil.MSEIRFFlow(I) = GetCurveIndex(state, Alphas(17 + (I - 1) * 6)); // convert curve name to number
    4225         113 :             if (thisDXCoil.MSEIRFFlow(I) == 0) {
    4226           0 :                 if (lAlphaBlanks(17 + (I - 1) * 6)) {
    4227           0 :                     ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4228           0 :                     ShowContinueError(state, format("...required {} is blank.", cAlphaFields(17 + (I - 1) * 6)));
    4229             :                 } else {
    4230           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4231           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(17 + (I - 1) * 6), Alphas(17 + (I - 1) * 6)));
    4232             :                 }
    4233           0 :                 ErrorsFound = true;
    4234             :             } else {
    4235             :                 // Verify Curve Object, only legal type is Quadratic
    4236         226 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    4237         113 :                                                      thisDXCoil.MSEIRFFlow(I),        // Curve index
    4238             :                                                      {1},                             // Valid dimensions
    4239             :                                                      RoutineName,                     // Routine name
    4240             :                                                      CurrentModuleObject,             // Object Type
    4241             :                                                      thisDXCoil.Name,                 // Object Name
    4242         113 :                                                      cAlphaFields(17 + (I - 1) * 6)); // Field Name
    4243             : 
    4244         113 :                 if (!ErrorsFound) {
    4245         113 :                     checkCurveIsNormalizedToOne(state,
    4246         226 :                                                 std::string{RoutineName} + CurrentModuleObject,
    4247         113 :                                                 thisDXCoil.Name,
    4248         113 :                                                 thisDXCoil.MSEIRFFlow(I),
    4249         113 :                                                 cAlphaFields(17 + (I - 1) * 6),
    4250         113 :                                                 Alphas(17 + (I - 1) * 6),
    4251             :                                                 1.0);
    4252             :                 }
    4253             :             }
    4254             : 
    4255         113 :             thisDXCoil.MSPLFFPLR(I) = GetCurveIndex(state, Alphas(18 + (I - 1) * 6)); // convert curve name to number
    4256         113 :             if (thisDXCoil.MSPLFFPLR(I) == 0) {
    4257           0 :                 if (lAlphaBlanks(18 + (I - 1) * 6)) {
    4258           0 :                     ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4259           0 :                     ShowContinueError(state, format("...required {} is blank.", cAlphaFields(18 + (I - 1) * 6)));
    4260             :                 } else {
    4261           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4262           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(18 + (I - 1) * 6), Alphas(18 + (I - 1) * 6)));
    4263             :                 }
    4264           0 :                 ErrorsFound = true;
    4265             :             } else {
    4266             :                 // Verify Curve Object, only legal types are Quadratic or Cubic
    4267         226 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    4268         113 :                                                      thisDXCoil.MSPLFFPLR(I),         // Curve index
    4269             :                                                      {1},                             // Valid dimensions
    4270             :                                                      RoutineName,                     // Routine name
    4271             :                                                      CurrentModuleObject,             // Object Type
    4272             :                                                      thisDXCoil.Name,                 // Object Name
    4273         113 :                                                      cAlphaFields(18 + (I - 1) * 6)); // Field Name
    4274             : 
    4275         113 :                 if (!ErrorsFound) {
    4276             :                     //       Test PLF curve minimum and maximum. Cap if less than 0.7 or greater than 1.0.
    4277         113 :                     MinCurveVal = 999.0;
    4278         113 :                     MaxCurveVal = -999.0;
    4279         113 :                     CurveInput = 0.0;
    4280       11413 :                     while (CurveInput <= 1.0) {
    4281       11300 :                         CurveVal = CurveValue(state, thisDXCoil.MSPLFFPLR(I), CurveInput);
    4282       11300 :                         if (CurveVal < MinCurveVal) {
    4283         113 :                             MinCurveVal = CurveVal;
    4284         113 :                             MinCurvePLR = CurveInput;
    4285             :                         }
    4286       11300 :                         if (CurveVal > MaxCurveVal) {
    4287       11300 :                             MaxCurveVal = CurveVal;
    4288       11300 :                             MaxCurvePLR = CurveInput;
    4289             :                         }
    4290       11300 :                         CurveInput += 0.01;
    4291             :                     }
    4292         113 :                     if (MinCurveVal < 0.7) {
    4293           0 :                         ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4294           0 :                         ShowContinueError(state,
    4295           0 :                                           format("...{} = {} has out of range value.", cAlphaFields2(18 + (I - 1) * 6), Alphas2(18 + (I - 1) * 6)));
    4296           0 :                         ShowContinueError(state,
    4297           0 :                                           format("...Curve minimum must be >= 0.7, curve min at PLR = {:.2T} is {:.3T}", MinCurvePLR, MinCurveVal));
    4298           0 :                         ShowContinueError(state, "...Setting curve minimum to 0.7 and simulation continues.");
    4299           0 :                         Curve::SetCurveOutputMinValue(state, thisDXCoil.PLFFPLR(PerfModeNum), ErrorsFound, 0.7);
    4300             :                     }
    4301             : 
    4302         113 :                     if (MaxCurveVal > 1.0) {
    4303           0 :                         ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4304           0 :                         ShowContinueError(state,
    4305           0 :                                           format("...{} = {} has out of range value.", cAlphaFields2(18 + (I - 1) * 6), Alphas2(18 + (I - 1) * 6)));
    4306           0 :                         ShowContinueError(state,
    4307           0 :                                           format("...Curve maximum must be <= 1.0, curve max at PLR = {:.2T} is {:.3T}", MaxCurvePLR, MaxCurveVal));
    4308           0 :                         ShowContinueError(state, "...Setting curve maximum to 1.0 and simulation continues.");
    4309           0 :                         Curve::SetCurveOutputMaxValue(state, thisDXCoil.MSPLFFPLR(I), ErrorsFound, 1.0);
    4310             :                     }
    4311             :                 }
    4312             :             }
    4313             : 
    4314             :             // read data for latent degradation
    4315         113 :             thisDXCoil.MSTwet_Rated(I) = Numbers(13 + (I - 1) * 14);
    4316         113 :             if (thisDXCoil.MSTwet_Rated(I) < 0.0) {
    4317           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4318           0 :                 ShowContinueError(
    4319           0 :                     state, format("...{} cannot be < 0.0, entered value=[{:.4T}].", cNumericFields(13 + (I - 1) * 14), thisDXCoil.MSTwet_Rated(I)));
    4320           0 :                 ErrorsFound = true;
    4321             :             }
    4322         113 :             thisDXCoil.MSGamma_Rated(I) = Numbers(14 + (I - 1) * 14);
    4323         113 :             if (thisDXCoil.MSGamma_Rated(I) < 0.0) {
    4324           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4325           0 :                 ShowContinueError(
    4326           0 :                     state, format("...{} cannot be < 0.0, entered value=[{:.4T}].", cNumericFields(14 + (I - 1) * 14), thisDXCoil.MSGamma_Rated(I)));
    4327           0 :                 ErrorsFound = true;
    4328             :             }
    4329         113 :             thisDXCoil.MSMaxONOFFCyclesperHour(I) = Numbers(15 + (I - 1) * 14);
    4330         113 :             if (thisDXCoil.Gamma_Rated(I) < 0.0) {
    4331           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4332           0 :                 ShowContinueError(state,
    4333           0 :                                   format("...{} cannot be < 0.0, entered value=[{:.2T}].",
    4334           0 :                                          cNumericFields(15 + (I - 1) * 14),
    4335             :                                          thisDXCoil.MSMaxONOFFCyclesperHour(I)));
    4336           0 :                 ErrorsFound = true;
    4337             :             }
    4338         113 :             thisDXCoil.MSLatentCapacityTimeConstant(I) = Numbers(16 + (I - 1) * 14);
    4339         113 :             if (thisDXCoil.Gamma_Rated(I) < 0.0) {
    4340           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4341           0 :                 ShowContinueError(state,
    4342           0 :                                   format("...{} cannot be < 0.0, entered value=[{:.2T}].",
    4343           0 :                                          cNumericFields(16 + (I - 1) * 14),
    4344             :                                          thisDXCoil.MSLatentCapacityTimeConstant(I)));
    4345           0 :                 ErrorsFound = true;
    4346             :             }
    4347             : 
    4348         113 :             thisDXCoil.MSWasteHeatFrac(I) = Numbers(17 + (I - 1) * 14);
    4349             : 
    4350             :             // Read waste heat modifier curve name
    4351         113 :             thisDXCoil.MSWasteHeat(I) = GetCurveIndex(state, Alphas(19 + (I - 1) * 6)); // convert curve name to number
    4352         113 :             if (thisDXCoil.FuelType != Constant::eFuel::Electricity) {
    4353          24 :                 if (thisDXCoil.MSWasteHeat(I) > 0) {
    4354             :                     // Verify Curve Object, only legal types are BiQuadratic
    4355          48 :                     ErrorsFound |= Curve::CheckCurveDims(state,
    4356          24 :                                                          thisDXCoil.MSWasteHeat(I),       // Curve index
    4357             :                                                          {2},                             // Valid dimensions
    4358             :                                                          RoutineName,                     // Routine name
    4359             :                                                          CurrentModuleObject,             // Object Type
    4360             :                                                          thisDXCoil.Name,                 // Object Name
    4361          24 :                                                          cAlphaFields(19 + (I - 1) * 6)); // Field Name
    4362             : 
    4363          24 :                     if (!ErrorsFound) {
    4364          24 :                         CurveVal = CurveValue(state, thisDXCoil.MSWasteHeat(I), RatedOutdoorAirTemp, RatedInletAirTemp);
    4365          24 :                         if (CurveVal > 1.10 || CurveVal < 0.90) {
    4366           0 :                             ShowWarningError(state, format("{}{}=\"{}\", curve values", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4367           0 :                             ShowContinueError(state, format("{} = {}", cAlphaFields(19 + (I - 1) * 6), Alphas(19 + (I - 1) * 6)));
    4368           0 :                             ShowContinueError(
    4369           0 :                                 state, format("...{} output is not equal to 1.0 (+ or - 10%) at rated conditions.", cAlphaFields(19 + (I - 1) * 6)));
    4370           0 :                             ShowContinueError(state, format("...Curve output at rated conditions = {:.3T}", CurveVal));
    4371             :                         }
    4372             :                     }
    4373             :                 }
    4374             :             }
    4375             : 
    4376         113 :             thisDXCoil.MSEvapCondEffect(I) = Numbers(18 + (I - 1) * 14);
    4377         113 :             if (thisDXCoil.MSEvapCondEffect(I) < 0.0 || thisDXCoil.MSEvapCondEffect(I) > 1.0) {
    4378           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4379           0 :                 ShowContinueError(
    4380             :                     state,
    4381           0 :                     format("...{} cannot be < 0.0 or > 1.0, entered value=[{:.3T}].", cNumericFields(18 + (I - 1) * 14), Numbers(18 + (I - 1) * 14)));
    4382           0 :                 ErrorsFound = true;
    4383             :             }
    4384             : 
    4385         113 :             thisDXCoil.MSEvapCondAirFlow(I) = Numbers(19 + (I - 1) * 14);
    4386         113 :             if (thisDXCoil.MSEvapCondAirFlow(I) < 0.0 && thisDXCoil.MSEvapCondAirFlow(I) != AutoSize) {
    4387           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4388           0 :                 ShowContinueError(
    4389           0 :                     state, format("...{} cannot be < 0.0, entered value=[{:.3T}].", cNumericFields(19 + (I - 1) * 14), Numbers(19 + (I - 1) * 14)));
    4390           0 :                 ErrorsFound = true;
    4391             :             }
    4392             : 
    4393         113 :             thisDXCoil.MSEvapCondPumpElecNomPower(I) = Numbers(20 + (I - 1) * 14);
    4394         113 :             if (thisDXCoil.MSEvapCondPumpElecNomPower(I) < 0.0 && thisDXCoil.MSEvapCondPumpElecNomPower(I) != AutoSize) {
    4395           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4396           0 :                 ShowContinueError(
    4397           0 :                     state, format("...{} cannot be < 0.0, entered value=[{:.3T}].", cNumericFields(20 + (I - 1) * 14), Numbers(20 + (I - 1) * 14)));
    4398           0 :                 ErrorsFound = true;
    4399             :             }
    4400             :         }
    4401             :         // A38; \field Zone Name for Condenser Placement
    4402          49 :         if (!lAlphaBlanks(38) && NumAlphas > 37) {
    4403           0 :             thisDXCoil.SecZonePtr = Util::FindItemInList(Alphas(38), state.dataHeatBal->Zone);
    4404           0 :             if (thisDXCoil.SecZonePtr > 0) {
    4405           0 :                 SetupZoneInternalGain(state,
    4406             :                                       thisDXCoil.SecZonePtr,
    4407             :                                       thisDXCoil.Name,
    4408             :                                       DataHeatBalance::IntGainType::SecCoolingDXCoilMultiSpeed,
    4409             :                                       &thisDXCoil.SecCoilSensibleHeatGainRate);
    4410           0 :                 thisDXCoil.IsSecondaryDXCoilInZone = true;
    4411             :             } else {
    4412           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4413           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(38), Alphas(38)));
    4414             :             }
    4415             :         }
    4416             :     }
    4417             : 
    4418         247 :     if (ErrorsFound) {
    4419           0 :         ShowFatalError(state,
    4420           0 :                        format("{}Errors found in getting {} input. Preceding condition(s) causes termination.", RoutineName, CurrentModuleObject));
    4421             :     }
    4422             : 
    4423             :     // DX multispeed heating coil
    4424         247 :     CurrentModuleObject = "Coil:Heating:DX:MultiSpeed";
    4425         269 :     for (DXCoilIndex = 1; DXCoilIndex <= state.dataDXCoils->NumDXMulSpeedHeatCoils; ++DXCoilIndex) {
    4426             : 
    4427          22 :         ++DXCoilNum;
    4428             : 
    4429          22 :         state.dataInputProcessing->inputProcessor->getObjectItem(state,
    4430             :                                                                  CurrentModuleObject,
    4431             :                                                                  DXCoilIndex,
    4432             :                                                                  Alphas,
    4433             :                                                                  NumAlphas,
    4434             :                                                                  Numbers,
    4435             :                                                                  NumNumbers,
    4436             :                                                                  IOStatus,
    4437             :                                                                  lNumericBlanks,
    4438             :                                                                  lAlphaBlanks,
    4439             :                                                                  cAlphaFields,
    4440             :                                                                  cNumericFields);
    4441             : 
    4442             :         // *** will have to circle back to this one to fix since the multispeed coil has all fields in this coil object ***
    4443             :         // allocate single performance mode for numeric field strings used for sizing routine
    4444          22 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode.allocate(1);
    4445          22 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames.allocate(MaxNumbers);
    4446          22 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames = cNumericFields;
    4447             :         // ErrorsFound will be set to True if problem was found, left untouched otherwise
    4448          22 :         VerifyUniqueCoilName(state, CurrentModuleObject, Alphas(1), ErrorsFound, CurrentModuleObject + " Name");
    4449             : 
    4450          22 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    4451          22 :         thisDXCoil.Name = Alphas(1);
    4452             :         // Initialize DataHeatBalance heat reclaim variable name for use by heat reclaim coils
    4453          22 :         state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).Name = thisDXCoil.Name;
    4454          22 :         state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).SourceType = CurrentModuleObject;
    4455          22 :         thisDXCoil.DXCoilType = CurrentModuleObject;
    4456          22 :         thisDXCoil.DXCoilType_Num = HVAC::CoilDX_MultiSpeedHeating;
    4457          22 :         thisDXCoil.Schedule = Alphas(2);
    4458          22 :         if (lAlphaBlanks(2)) {
    4459           8 :             thisDXCoil.SchedPtr = ScheduleManager::ScheduleAlwaysOn;
    4460             :         } else {
    4461          14 :             thisDXCoil.SchedPtr = GetScheduleIndex(state, Alphas(2)); // convert schedule name to pointer
    4462          14 :             if (thisDXCoil.SchedPtr == 0) {
    4463           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4464           0 :                 ShowContinueError(state, format("...{}=\"{}\".", cAlphaFields(2), Alphas(2)));
    4465           0 :                 ErrorsFound = true;
    4466             :             }
    4467             :         }
    4468             : 
    4469          22 :         thisDXCoil.AirInNode = GetOnlySingleNode(state,
    4470          22 :                                                  Alphas(3),
    4471             :                                                  ErrorsFound,
    4472             :                                                  DataLoopNode::ConnectionObjectType::CoilHeatingDXMultiSpeed,
    4473          22 :                                                  Alphas(1),
    4474             :                                                  DataLoopNode::NodeFluidType::Air,
    4475             :                                                  DataLoopNode::ConnectionType::Inlet,
    4476             :                                                  NodeInputManager::CompFluidStream::Primary,
    4477             :                                                  ObjectIsNotParent);
    4478             : 
    4479          22 :         thisDXCoil.AirOutNode = GetOnlySingleNode(state,
    4480          22 :                                                   Alphas(4),
    4481             :                                                   ErrorsFound,
    4482             :                                                   DataLoopNode::ConnectionObjectType::CoilHeatingDXMultiSpeed,
    4483          22 :                                                   Alphas(1),
    4484             :                                                   DataLoopNode::NodeFluidType::Air,
    4485             :                                                   DataLoopNode::ConnectionType::Outlet,
    4486             :                                                   NodeInputManager::CompFluidStream::Primary,
    4487             :                                                   ObjectIsNotParent);
    4488             : 
    4489          22 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(3), Alphas(4), "Air Nodes");
    4490             : 
    4491             :         // Set minimum OAT for heat pump compressor operation
    4492          22 :         thisDXCoil.MinOATCompressor = Numbers(1);
    4493             : 
    4494             :         // set Minimum Outdoor Dry-Bulb Temperature for Compressor Operation
    4495          22 :         thisDXCoil.OATempCompressorOn = Numbers(2);
    4496             :         // Set crankcase heater capacity
    4497          22 :         thisDXCoil.CrankcaseHeaterCapacity = Numbers(3);
    4498          22 :         if (thisDXCoil.CrankcaseHeaterCapacity < 0.0) {
    4499           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4500           0 :             ShowContinueError(state, format("...{} cannot be < 0.0, entered value=[{:.2T}].", cNumericFields(3), Numbers(3)));
    4501           0 :             ErrorsFound = true;
    4502             :         }
    4503             : 
    4504             :         // Set crankcase heater cutout temperature
    4505          22 :         thisDXCoil.MaxOATCrankcaseHeater = Numbers(4);
    4506             : 
    4507          22 :         if (!lAlphaBlanks(5)) {
    4508           0 :             thisDXCoil.CrankcaseHeaterCapacityCurveIndex = Curve::GetCurveIndex(state, Alphas(5));
    4509           0 :             ErrorsFound |= Curve::CheckCurveDims(state,
    4510             :                                                  thisDXCoil.CrankcaseHeaterCapacityCurveIndex, // Curve index
    4511             :                                                  {1},                                          // Valid dimensions
    4512             :                                                  RoutineName,                                  // Routine name
    4513             :                                                  CurrentModuleObject,                          // Object Type
    4514             :                                                  thisDXCoil.Name,                              // Object Name
    4515           0 :                                                  cAlphaFields(5));                             // Field Name
    4516             :         }
    4517             : 
    4518             :         // Only required for reverse cycle heat pumps
    4519          22 :         thisDXCoil.DefrostEIRFT = GetCurveIndex(state, Alphas(6)); // convert curve name to number
    4520          22 :         if (Util::SameString(Alphas(7), "ReverseCycle")) {
    4521          22 :             if (thisDXCoil.DefrostEIRFT == 0) {
    4522           0 :                 if (lAlphaBlanks(6)) {
    4523           0 :                     ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4524           0 :                     ShowContinueError(state, format("...required {} is blank.", cAlphaFields(6)));
    4525             :                 } else {
    4526           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4527           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(6), Alphas(6)));
    4528             :                 }
    4529           0 :                 ErrorsFound = true;
    4530             :             } else {
    4531             :                 // Verify Curve Object, only legal type is BiQuadratic
    4532          22 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    4533             :                                                      thisDXCoil.DefrostEIRFT, // Curve index
    4534             :                                                      {2},                     // Valid dimensions
    4535             :                                                      RoutineName,             // Routine name
    4536             :                                                      CurrentModuleObject,     // Object Type
    4537             :                                                      thisDXCoil.Name,         // Object Name
    4538          22 :                                                      cAlphaFields(6));        // Field Name
    4539             : 
    4540          22 :                 if (!ErrorsFound) {
    4541          22 :                     checkCurveIsNormalizedToOne(state,
    4542          44 :                                                 std::string{RoutineName} + CurrentModuleObject,
    4543          22 :                                                 thisDXCoil.Name,
    4544             :                                                 thisDXCoil.DefrostEIRFT,
    4545          22 :                                                 cAlphaFields(6),
    4546          22 :                                                 Alphas(6),
    4547             :                                                 RatedInletWetBulbTempHeat,
    4548             :                                                 RatedOutdoorAirTempHeat);
    4549             :                 }
    4550             :             }
    4551             :         }
    4552             : 
    4553          22 :         if (Util::SameString(Alphas(7), "ReverseCycle")) thisDXCoil.DefrostStrategy = StandardRatings::DefrostStrat::ReverseCycle;
    4554          22 :         if (Util::SameString(Alphas(7), "Resistive")) thisDXCoil.DefrostStrategy = StandardRatings::DefrostStrat::Resistive;
    4555          22 :         if (thisDXCoil.DefrostStrategy == StandardRatings::DefrostStrat::Invalid) {
    4556           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4557           0 :             ShowContinueError(state, format("...illegal {}=\"{}\".", cAlphaFields(7), Alphas(7)));
    4558           0 :             ShowContinueError(state, "...valid values for this field are ReverseCycle or Resistive.");
    4559           0 :             ErrorsFound = true;
    4560             :         }
    4561             : 
    4562          22 :         if (Util::SameString(Alphas(8), "Timed")) thisDXCoil.DefrostControl = StandardRatings::HPdefrostControl::Timed;
    4563          22 :         if (Util::SameString(Alphas(8), "OnDemand")) thisDXCoil.DefrostControl = StandardRatings::HPdefrostControl::OnDemand;
    4564          22 :         if (thisDXCoil.DefrostControl == StandardRatings::HPdefrostControl::Invalid) {
    4565           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4566           0 :             ShowContinueError(state, format("...illegal {}=\"{}\".", cAlphaFields(8), Alphas(8)));
    4567           0 :             ShowContinueError(state, "...valid values for this field are Timed or OnDemand.");
    4568           0 :             ErrorsFound = true;
    4569             :         }
    4570             : 
    4571             :         // Set maximum outdoor temp for defrost to occur
    4572          22 :         thisDXCoil.MaxOATDefrost = Numbers(5);
    4573             : 
    4574             :         // Set defrost time period
    4575          22 :         thisDXCoil.DefrostTime = Numbers(6);
    4576          22 :         if (thisDXCoil.DefrostTime == 0.0 && thisDXCoil.DefrostControl == StandardRatings::HPdefrostControl::Timed) {
    4577           0 :             ShowWarningError(state, format("{}{}=\"{}\", ", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4578           0 :             ShowContinueError(state, format("...{} = 0.0 for defrost control = TIMED.", cNumericFields(5)));
    4579             :         }
    4580             : 
    4581             :         // Set defrost capacity (for resistive defrost)
    4582          22 :         thisDXCoil.DefrostCapacity = Numbers(7);
    4583          22 :         if (thisDXCoil.DefrostCapacity == 0.0 && thisDXCoil.DefrostStrategy == StandardRatings::DefrostStrat::Resistive) {
    4584           0 :             ShowWarningError(state, format("{}{}=\"{}\", ", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4585           0 :             ShowContinueError(state, format("...{} = 0.0 for defrost strategy = RESISTIVE.", cNumericFields(7)));
    4586             :         }
    4587             : 
    4588          22 :         if (Util::SameString(Alphas(9), "Yes")) {
    4589           0 :             thisDXCoil.PLRImpact = true;
    4590          22 :         } else if (Util::SameString(Alphas(9), "No")) {
    4591          22 :             thisDXCoil.PLRImpact = false;
    4592             :         } else {
    4593           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4594           0 :             ShowContinueError(state, format(",,,invalid choice for {}.  Entered choice = {}", cAlphaFields(9), Alphas(9)));
    4595           0 :             ShowContinueError(state, "The allowed choices are Yes or No.");
    4596           0 :             ErrorsFound = true;
    4597             :         }
    4598             : 
    4599             :         // A10; \field Fuel type, Validate fuel type input
    4600          22 :         thisDXCoil.FuelType = static_cast<Constant::eFuel>(getEnumValue(Constant::eFuelNamesUC, Alphas(10)));
    4601             : 
    4602          22 :         thisDXCoil.RegionNum = Numbers(8);   // Region Number for HSPF Calc
    4603          22 :         thisDXCoil.NumOfSpeeds = Numbers(9); // Number of speeds
    4604          22 :         if (thisDXCoil.NumOfSpeeds < 2) {
    4605           0 :             ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4606           0 :             ShowContinueError(state, format("...{} must be >= 2. entered number is {:.0T}", cNumericFields(9), Numbers(9)));
    4607           0 :             ErrorsFound = true;
    4608             :         }
    4609             : 
    4610             :         // Allocate arrays based on the number of speeds
    4611          22 :         thisDXCoil.MSErrIndex.allocate(thisDXCoil.NumOfSpeeds);
    4612          22 :         thisDXCoil.MSErrIndex = 0;
    4613          22 :         thisDXCoil.MSRatedTotCap.allocate(thisDXCoil.NumOfSpeeds);
    4614          22 :         thisDXCoil.MSRatedCOP.allocate(thisDXCoil.NumOfSpeeds);
    4615          22 :         thisDXCoil.MSRatedAirVolFlowRate.allocate(thisDXCoil.NumOfSpeeds);
    4616          22 :         thisDXCoil.MSRatedAirMassFlowRate.allocate(thisDXCoil.NumOfSpeeds);
    4617          22 :         thisDXCoil.MSRatedAirMassFlowRate = 1.0; // avoid divide by 0, will get overwritten in InitDXCoil
    4618          22 :         thisDXCoil.MSCCapFTemp.allocate(thisDXCoil.NumOfSpeeds);
    4619          22 :         thisDXCoil.MSCCapFFlow.allocate(thisDXCoil.NumOfSpeeds);
    4620          22 :         thisDXCoil.MSEIRFTemp.allocate(thisDXCoil.NumOfSpeeds);
    4621          22 :         thisDXCoil.MSEIRFFlow.allocate(thisDXCoil.NumOfSpeeds);
    4622          22 :         thisDXCoil.MSWasteHeat.allocate(thisDXCoil.NumOfSpeeds);
    4623          22 :         thisDXCoil.MSPLFFPLR.allocate(thisDXCoil.NumOfSpeeds);
    4624          22 :         thisDXCoil.MSRatedCBF.allocate(thisDXCoil.NumOfSpeeds);
    4625          22 :         thisDXCoil.MSWasteHeatFrac.allocate(thisDXCoil.NumOfSpeeds);
    4626          22 :         thisDXCoil.MSFanPowerPerEvapAirFlowRate.allocate(thisDXCoil.NumOfSpeeds);
    4627          22 :         thisDXCoil.MSFanPowerPerEvapAirFlowRate_2023.allocate(thisDXCoil.NumOfSpeeds);
    4628          22 :         thisDXCoil.MSSecCoilSHRFT.allocate(thisDXCoil.NumOfSpeeds);
    4629          22 :         thisDXCoil.MSSecCoilSHRFF.allocate(thisDXCoil.NumOfSpeeds);
    4630          22 :         thisDXCoil.MSSecCoilAirFlow.allocate(thisDXCoil.NumOfSpeeds);
    4631          22 :         thisDXCoil.MSSecCoilAirFlowScalingFactor.allocate(thisDXCoil.NumOfSpeeds);
    4632          22 :         thisDXCoil.MSSecCoilRatedSHR.allocate(thisDXCoil.NumOfSpeeds);
    4633             : 
    4634          22 :         thisDXCoil.RatedSHR(1) = 1.0;
    4635             : 
    4636          92 :         for (I = 1; I <= thisDXCoil.NumOfSpeeds; ++I) {
    4637          70 :             thisDXCoil.MSRatedTotCap(I) = Numbers(10 + (I - 1) * 6);
    4638          70 :             thisDXCoil.MSRatedCOP(I) = Numbers(11 + (I - 1) * 6);
    4639          70 :             thisDXCoil.MSRatedAirVolFlowRate(I) = Numbers(12 + (I - 1) * 6);
    4640          70 :             thisDXCoil.MSFanPowerPerEvapAirFlowRate(I) = Numbers(13 + (I - 1) * 6);
    4641          70 :             thisDXCoil.MSFanPowerPerEvapAirFlowRate_2023(I) = Numbers(14 + (I - 1) * 6);
    4642          70 :             thisDXCoil.MSWasteHeatFrac(I) = Numbers(15 + (I - 1) * 6);
    4643             : 
    4644          70 :             thisDXCoil.MSCCapFTemp(I) = GetCurveIndex(state, Alphas(11 + (I - 1) * 6)); // convert curve name to number
    4645          70 :             if (thisDXCoil.MSCCapFTemp(I) == 0) {
    4646           0 :                 ShowSevereError(state,
    4647           0 :                                 format("{}, \"{}\" {} not found:{}",
    4648             :                                        CurrentModuleObject,
    4649           0 :                                        thisDXCoil.Name,
    4650           0 :                                        cAlphaFields(11 + (I - 1) * 6),
    4651           0 :                                        Alphas(11 + (I - 1) * 6)));
    4652           0 :                 ErrorsFound = true;
    4653             :             } else {
    4654             :                 // only legal types are Quadratic, BiQuadratic and Cubic
    4655         140 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    4656          70 :                                                      thisDXCoil.MSCCapFTemp(I),       // Curve index
    4657             :                                                      {1, 2},                          // Valid dimensions  // MULTIPLECURVEDIMS
    4658             :                                                      RoutineName,                     // Routine name
    4659             :                                                      CurrentModuleObject,             // Object Type
    4660             :                                                      thisDXCoil.Name,                 // Object Name
    4661          70 :                                                      cAlphaFields(11 + (I - 1) * 6)); // Field Name
    4662             : 
    4663          70 :                 if (!ErrorsFound) {
    4664          70 :                     if (state.dataCurveManager->PerfCurve(thisDXCoil.MSCCapFTemp(I))->numDims == 1) {
    4665          52 :                         checkCurveIsNormalizedToOne(state,
    4666         104 :                                                     std::string{RoutineName} + CurrentModuleObject,
    4667          52 :                                                     thisDXCoil.Name,
    4668          52 :                                                     thisDXCoil.MSCCapFTemp(I),
    4669          52 :                                                     cAlphaFields(11 + (I - 1) * 6),
    4670          52 :                                                     Alphas(11 + (I - 1) * 6),
    4671             :                                                     RatedOutdoorAirTempHeat);
    4672             :                     } else {
    4673          18 :                         checkCurveIsNormalizedToOne(state,
    4674          36 :                                                     std::string{RoutineName} + CurrentModuleObject,
    4675          18 :                                                     thisDXCoil.Name,
    4676          18 :                                                     thisDXCoil.MSCCapFTemp(I),
    4677          18 :                                                     cAlphaFields(11 + (I - 1) * 6),
    4678          18 :                                                     Alphas(11 + (I - 1) * 6),
    4679             :                                                     RatedInletAirTempHeat,
    4680             :                                                     RatedOutdoorAirTempHeat);
    4681             :                     }
    4682             :                 }
    4683             :             }
    4684             : 
    4685          70 :             thisDXCoil.MSCCapFFlow(I) = GetCurveIndex(state, Alphas(12 + (I - 1) * 6)); // convert curve name to number
    4686          70 :             if (thisDXCoil.MSCCapFFlow(I) == 0) {
    4687           0 :                 if (lAlphaBlanks(12 + (I - 1) * 6)) {
    4688           0 :                     ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4689           0 :                     ShowContinueError(state, format("...required {} is blank.", cAlphaFields(12 + (I - 1) * 6)));
    4690             :                 } else {
    4691           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4692           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(12 + (I - 1) * 6), Alphas(12 + (I - 1) * 6)));
    4693             :                 }
    4694           0 :                 ErrorsFound = true;
    4695             :             } else {
    4696             :                 // Verify Curve Object, only legal type is Quadratic
    4697         140 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    4698          70 :                                                      thisDXCoil.MSCCapFFlow(I),       // Curve index
    4699             :                                                      {1},                             // Valid dimensions
    4700             :                                                      RoutineName,                     // Routine name
    4701             :                                                      CurrentModuleObject,             // Object Type
    4702             :                                                      thisDXCoil.Name,                 // Object Name
    4703          70 :                                                      cAlphaFields(12 + (I - 1) * 6)); // Field Name
    4704             : 
    4705          70 :                 if (!ErrorsFound) {
    4706          70 :                     checkCurveIsNormalizedToOne(state,
    4707         140 :                                                 std::string{RoutineName} + CurrentModuleObject,
    4708          70 :                                                 thisDXCoil.Name,
    4709          70 :                                                 thisDXCoil.MSCCapFFlow(I),
    4710          70 :                                                 cAlphaFields(12 + (I - 1) * 6),
    4711          70 :                                                 Alphas(12 + (I - 1) * 6),
    4712             :                                                 1.0);
    4713             :                 }
    4714             :             }
    4715             : 
    4716          70 :             thisDXCoil.MSEIRFTemp(I) = GetCurveIndex(state, Alphas(13 + (I - 1) * 6)); // convert curve name to number
    4717          70 :             if (thisDXCoil.MSEIRFTemp(I) == 0) {
    4718           0 :                 if (lAlphaBlanks(13 + (I - 1) * 6)) {
    4719           0 :                     ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4720           0 :                     ShowContinueError(state, format("...required {} is blank.", cAlphaFields(13 + (I - 1) * 6)));
    4721             :                 } else {
    4722           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4723           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(13 + (I - 1) * 6), Alphas(13 + (I - 1) * 6)));
    4724             :                 }
    4725           0 :                 ErrorsFound = true;
    4726             :             } else {
    4727             :                 // only legal types are Quadratic, BiQuadratic and Cubic
    4728         140 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    4729          70 :                                                      thisDXCoil.MSEIRFTemp(I),        // Curve index
    4730             :                                                      {1, 2},                          // Valid dimensions  // MULTIPLECURVEDIMS
    4731             :                                                      RoutineName,                     // Routine name
    4732             :                                                      CurrentModuleObject,             // Object Type
    4733             :                                                      thisDXCoil.Name,                 // Object Name
    4734          70 :                                                      cAlphaFields(13 + (I - 1) * 6)); // Field Name
    4735             : 
    4736          70 :                 if (!ErrorsFound) {
    4737          70 :                     if (state.dataCurveManager->PerfCurve(thisDXCoil.MSEIRFTemp(I))->numDims == 1) {
    4738          52 :                         checkCurveIsNormalizedToOne(state,
    4739         104 :                                                     std::string{RoutineName} + CurrentModuleObject,
    4740          52 :                                                     thisDXCoil.Name,
    4741          52 :                                                     thisDXCoil.MSEIRFTemp(I),
    4742          52 :                                                     cAlphaFields(13 + (I - 1) * 6),
    4743          52 :                                                     Alphas(13 + (I - 1) * 6),
    4744             :                                                     RatedOutdoorAirTempHeat);
    4745             :                     } else {
    4746          18 :                         checkCurveIsNormalizedToOne(state,
    4747          36 :                                                     std::string{RoutineName} + CurrentModuleObject,
    4748          18 :                                                     thisDXCoil.Name,
    4749          18 :                                                     thisDXCoil.MSEIRFTemp(I),
    4750          18 :                                                     cAlphaFields(13 + (I - 1) * 6),
    4751          18 :                                                     Alphas(13 + (I - 1) * 6),
    4752             :                                                     RatedInletAirTempHeat,
    4753             :                                                     RatedOutdoorAirTempHeat);
    4754             :                     }
    4755             :                 }
    4756             :             }
    4757             : 
    4758          70 :             thisDXCoil.MSEIRFFlow(I) = GetCurveIndex(state, Alphas(14 + (I - 1) * 6)); // convert curve name to number
    4759          70 :             if (thisDXCoil.MSEIRFFlow(I) == 0) {
    4760           0 :                 if (lAlphaBlanks(14 + (I - 1) * 6)) {
    4761           0 :                     ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4762           0 :                     ShowContinueError(state, format("...required {} is blank.", cAlphaFields(14 + (I - 1) * 6)));
    4763             :                 } else {
    4764           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4765           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(14 + (I - 1) * 6), Alphas(14 + (I - 1) * 6)));
    4766             :                 }
    4767           0 :                 ErrorsFound = true;
    4768             :             } else {
    4769             :                 // Verify Curve Object, only legal type is Quadratic
    4770         140 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    4771          70 :                                                      thisDXCoil.MSEIRFFlow(I),        // Curve index
    4772             :                                                      {1},                             // Valid dimensions
    4773             :                                                      RoutineName,                     // Routine name
    4774             :                                                      CurrentModuleObject,             // Object Type
    4775             :                                                      thisDXCoil.Name,                 // Object Name
    4776          70 :                                                      cAlphaFields(14 + (I - 1) * 6)); // Field Name
    4777             : 
    4778          70 :                 if (!ErrorsFound) {
    4779          70 :                     checkCurveIsNormalizedToOne(state,
    4780         140 :                                                 std::string{RoutineName} + CurrentModuleObject,
    4781          70 :                                                 thisDXCoil.Name,
    4782          70 :                                                 thisDXCoil.MSEIRFFlow(I),
    4783          70 :                                                 cAlphaFields(14 + (I - 1) * 6),
    4784          70 :                                                 Alphas(14 + (I - 1) * 6),
    4785             :                                                 1.0);
    4786             :                 }
    4787             :             }
    4788             : 
    4789          70 :             thisDXCoil.MSPLFFPLR(I) = GetCurveIndex(state, Alphas(15 + (I - 1) * 6)); // convert curve name to number
    4790          70 :             if (thisDXCoil.MSPLFFPLR(I) == 0) {
    4791           0 :                 if (lAlphaBlanks(15 + (I - 1) * 6)) {
    4792           0 :                     ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4793           0 :                     ShowContinueError(state, format("...required {} is blank.", cAlphaFields(15 + (I - 1) * 6)));
    4794             :                 } else {
    4795           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4796           0 :                     ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(15 + (I - 1) * 6), Alphas(15 + (I - 1) * 6)));
    4797             :                 }
    4798           0 :                 ErrorsFound = true;
    4799             :             } else {
    4800             :                 // Verify Curve Object, only legal types are Quadratic or Cubic
    4801         140 :                 ErrorsFound |= Curve::CheckCurveDims(state,
    4802          70 :                                                      thisDXCoil.MSPLFFPLR(I),         // Curve index
    4803             :                                                      {1},                             // Valid dimensions
    4804             :                                                      RoutineName,                     // Routine name
    4805             :                                                      CurrentModuleObject,             // Object Type
    4806             :                                                      thisDXCoil.Name,                 // Object Name
    4807          70 :                                                      cAlphaFields(15 + (I - 1) * 6)); // Field Name
    4808             : 
    4809          70 :                 if (!ErrorsFound) {
    4810             :                     //       Test PLF curve minimum and maximum. Cap if less than 0.7 or greater than 1.0.
    4811          70 :                     MinCurveVal = 999.0;
    4812          70 :                     MaxCurveVal = -999.0;
    4813          70 :                     CurveInput = 0.0;
    4814        7070 :                     while (CurveInput <= 1.0) {
    4815        7000 :                         CurveVal = CurveValue(state, thisDXCoil.MSPLFFPLR(I), CurveInput);
    4816        7000 :                         if (CurveVal < MinCurveVal) {
    4817          70 :                             MinCurveVal = CurveVal;
    4818          70 :                             MinCurvePLR = CurveInput;
    4819             :                         }
    4820        7000 :                         if (CurveVal > MaxCurveVal) {
    4821        7000 :                             MaxCurveVal = CurveVal;
    4822        7000 :                             MaxCurvePLR = CurveInput;
    4823             :                         }
    4824        7000 :                         CurveInput += 0.01;
    4825             :                     }
    4826          70 :                     if (MinCurveVal < 0.7) {
    4827           0 :                         ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4828           0 :                         ShowContinueError(state,
    4829           0 :                                           format("...{} = {} has out of range value.", cAlphaFields(15 + (I - 1) * 6), Alphas(15 + (I - 1) * 6)));
    4830           0 :                         ShowContinueError(state,
    4831           0 :                                           format("...Curve minimum must be >= 0.7, curve min at PLR = {:.2T} is {:.3T}", MinCurvePLR, MinCurveVal));
    4832           0 :                         ShowContinueError(state, "...Setting curve minimum to 0.7 and simulation continues.");
    4833           0 :                         Curve::SetCurveOutputMinValue(state, thisDXCoil.MSPLFFPLR(I), ErrorsFound, 0.7);
    4834             :                     }
    4835             : 
    4836          70 :                     if (MaxCurveVal > 1.0) {
    4837           0 :                         ShowWarningError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4838           0 :                         ShowContinueError(state,
    4839           0 :                                           format("...{} = {} has out of range value.", cAlphaFields(15 + (I - 1) * 6), Alphas(15 + (I - 1) * 6)));
    4840           0 :                         ShowContinueError(state,
    4841           0 :                                           format("...Curve maximum must be <= 1.0, curve max at PLR = {:.2T} is {:.3T}", MaxCurvePLR, MaxCurveVal));
    4842           0 :                         ShowContinueError(state, "...Setting curve maximum to 1.0 and simulation continues.");
    4843           0 :                         Curve::SetCurveOutputMaxValue(state, thisDXCoil.MSPLFFPLR(I), ErrorsFound, 1.0);
    4844             :                     }
    4845             :                 }
    4846             :             }
    4847             : 
    4848             :             // Read waste heat modifier curve name
    4849          70 :             thisDXCoil.MSWasteHeat(I) = GetCurveIndex(state, Alphas(16 + (I - 1) * 6)); // convert curve name to number
    4850          70 :             if (thisDXCoil.FuelType != Constant::eFuel::Electricity) {
    4851          16 :                 if (thisDXCoil.MSWasteHeat(I) > 0) {
    4852             :                     // Verify Curve Object, only legal types are BiQuadratic
    4853          32 :                     ErrorsFound |= Curve::CheckCurveDims(state,
    4854          16 :                                                          thisDXCoil.MSWasteHeat(I),       // Curve index
    4855             :                                                          {2},                             // Valid dimensions
    4856             :                                                          RoutineName,                     // Routine name
    4857             :                                                          CurrentModuleObject,             // Object Type
    4858             :                                                          thisDXCoil.Name,                 // Object Name
    4859          16 :                                                          cAlphaFields(16 + (I - 1) * 6)); // Field Name
    4860             : 
    4861          16 :                     if (!ErrorsFound) {
    4862          16 :                         checkCurveIsNormalizedToOne(state,
    4863          32 :                                                     std::string{RoutineName} + CurrentModuleObject,
    4864          16 :                                                     thisDXCoil.Name,
    4865          16 :                                                     thisDXCoil.MSWasteHeat(I),
    4866          16 :                                                     cAlphaFields(16 + (I - 1) * 6),
    4867          16 :                                                     Alphas(16 + (I - 1) * 6),
    4868             :                                                     RatedOutdoorAirTempHeat,
    4869             :                                                     RatedInletAirTempHeat);
    4870             :                     }
    4871             :                 }
    4872             :             }
    4873             :         }
    4874             :         // A35; \field Zone Name for Condenser Placement
    4875          22 :         if (!lAlphaBlanks(35) && NumAlphas > 34) {
    4876           0 :             thisDXCoil.SecZonePtr = Util::FindItemInList(Alphas(35), state.dataHeatBal->Zone);
    4877           0 :             if (thisDXCoil.SecZonePtr > 0) {
    4878           0 :                 SetupZoneInternalGain(state,
    4879             :                                       thisDXCoil.SecZonePtr,
    4880             :                                       thisDXCoil.Name,
    4881             :                                       DataHeatBalance::IntGainType::SecHeatingDXCoilMultiSpeed,
    4882             :                                       &thisDXCoil.SecCoilSensibleHeatRemovalRate,
    4883             :                                       nullptr,
    4884             :                                       nullptr,
    4885             :                                       &thisDXCoil.SecCoilLatentHeatRemovalRate);
    4886           0 :                 thisDXCoil.IsSecondaryDXCoilInZone = true;
    4887             :             } else {
    4888           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4889           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(35), Alphas(35)));
    4890             :             }
    4891             :         }
    4892          22 :         if (thisDXCoil.SecZonePtr > 0) {
    4893           0 :             for (I = 1; I <= thisDXCoil.NumOfSpeeds; ++I) {
    4894           0 :                 thisDXCoil.MSSecCoilAirFlow(I) = Numbers(34 + (I - 1) * 3);
    4895           0 :                 thisDXCoil.MSSecCoilAirFlowScalingFactor(I) = Numbers(35 + (I - 1) * 3);
    4896           0 :                 thisDXCoil.MSSecCoilRatedSHR(I) = Numbers(36 + (I - 1) * 3);
    4897             :                 // Read SHR modifier curve function of temperature
    4898           0 :                 if (!lAlphaBlanks(36 + (I - 1) * 2)) {
    4899           0 :                     thisDXCoil.MSSecCoilSHRFT(I) = GetCurveIndex(state, Alphas(36 + (I - 1) * 2)); // convert curve name to number
    4900           0 :                     if (thisDXCoil.MSSecCoilSHRFT(I) == 0) {
    4901           0 :                         ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4902           0 :                         ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(36 + (I - 1) * 2), Alphas(36 + (I - 1) * 2)));
    4903             :                     }
    4904             :                 }
    4905             :                 // Read SHR modifier curve function of flow fraction
    4906           0 :                 if (!lAlphaBlanks(36 + (I - 1) * 2)) {
    4907           0 :                     thisDXCoil.MSSecCoilSHRFF(I) = GetCurveIndex(state, Alphas(36 + (I - 1) * 2)); // convert curve name to number
    4908           0 :                     if (thisDXCoil.MSSecCoilSHRFF(I) == 0) {
    4909           0 :                         ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4910           0 :                         ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(36 + (I - 1) * 2), Alphas(36 + (I - 1) * 2)));
    4911             :                     }
    4912             :                 }
    4913             :             }
    4914             :         }
    4915             :     }
    4916             : 
    4917             :     // Loop over the VRF Cooling Coils and get & load the data
    4918         247 :     CurrentModuleObject = HVAC::cAllCoilTypes(HVAC::CoilVRF_Cooling);
    4919         293 :     for (DXCoilIndex = 1; DXCoilIndex <= state.dataDXCoils->NumVRFCoolingCoils; ++DXCoilIndex) {
    4920             : 
    4921          46 :         state.dataInputProcessing->inputProcessor->getObjectItem(state,
    4922             :                                                                  CurrentModuleObject,
    4923             :                                                                  DXCoilIndex,
    4924             :                                                                  Alphas,
    4925             :                                                                  NumAlphas,
    4926             :                                                                  Numbers,
    4927             :                                                                  NumNumbers,
    4928             :                                                                  IOStatus,
    4929             :                                                                  lNumericBlanks,
    4930             :                                                                  lAlphaBlanks,
    4931             :                                                                  cAlphaFields,
    4932             :                                                                  cNumericFields);
    4933             : 
    4934          46 :         ++DXCoilNum;
    4935             : 
    4936             :         // allocate single performance mode for numeric field strings used for sizing routine
    4937          46 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode.allocate(1);
    4938          46 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames.allocate(MaxNumbers);
    4939          46 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames = cNumericFields;
    4940             :         // ErrorsFound will be set to True if problem was found, left untouched otherwise
    4941          46 :         VerifyUniqueCoilName(state, CurrentModuleObject, Alphas(1), ErrorsFound, CurrentModuleObject + " Name");
    4942             : 
    4943          46 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    4944          46 :         thisDXCoil.Name = Alphas(1);
    4945          46 :         thisDXCoil.DXCoilType = CurrentModuleObject;
    4946          46 :         thisDXCoil.DXCoilType_Num = HVAC::CoilVRF_Cooling;
    4947          46 :         thisDXCoil.Schedule = Alphas(2);
    4948          46 :         if (lAlphaBlanks(2)) {
    4949           5 :             thisDXCoil.SchedPtr = ScheduleManager::ScheduleAlwaysOn;
    4950             :         } else {
    4951          41 :             thisDXCoil.SchedPtr = GetScheduleIndex(state, Alphas(2)); // convert schedule name to pointer
    4952          41 :             if (thisDXCoil.SchedPtr == 0) {
    4953           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4954           0 :                 ShowContinueError(state, format("...{}=\"{}\".", cAlphaFields(2), Alphas(2)));
    4955           0 :                 ErrorsFound = true;
    4956             :             }
    4957             :         }
    4958          46 :         thisDXCoil.RatedTotCap(1) = Numbers(1);
    4959          46 :         thisDXCoil.RatedSHR(1) = Numbers(2);
    4960          46 :         thisDXCoil.RatedAirVolFlowRate(1) = Numbers(3);
    4961             : 
    4962          46 :         thisDXCoil.CCapFTemp(1) = GetCurveIndex(state, Alphas(3));
    4963             :         // Verify Curve Object, only legal type is Linear, Quadratic, Cubic, or BiQuadratic
    4964          92 :         ErrorsFound |= Curve::CheckCurveDims(state,
    4965          46 :                                              thisDXCoil.CCapFTemp(1), // Curve index
    4966             :                                              {1, 2},                  // Valid dimensions  // MULTIPLECURVEDIMS
    4967             :                                              RoutineName,             // Routine name
    4968             :                                              CurrentModuleObject,     // Object Type
    4969             :                                              thisDXCoil.Name,         // Object Name
    4970          46 :                                              cAlphaFields(3));        // Field Name
    4971             : 
    4972          46 :         if (!ErrorsFound) {
    4973          46 :             if (state.dataCurveManager->PerfCurve(thisDXCoil.CCapFTemp(1))->numDims == 1) {
    4974          31 :                 checkCurveIsNormalizedToOne(state,
    4975          62 :                                             std::string{RoutineName} + CurrentModuleObject,
    4976          31 :                                             thisDXCoil.Name,
    4977          31 :                                             thisDXCoil.CCapFTemp(1),
    4978          31 :                                             cAlphaFields(3),
    4979          31 :                                             Alphas(3),
    4980             :                                             RatedInletWetBulbTemp);
    4981             :             } else {
    4982          15 :                 checkCurveIsNormalizedToOne(state,
    4983          30 :                                             std::string{RoutineName} + CurrentModuleObject,
    4984          15 :                                             thisDXCoil.Name,
    4985          15 :                                             thisDXCoil.CCapFTemp(1),
    4986          15 :                                             cAlphaFields(3),
    4987          15 :                                             Alphas(3),
    4988             :                                             RatedInletWetBulbTemp,
    4989             :                                             RatedOutdoorAirTemp);
    4990             :             }
    4991             :         }
    4992             : 
    4993          46 :         thisDXCoil.CCapFFlow(1) = GetCurveIndex(state, Alphas(4)); // convert curve name to number
    4994          46 :         if (thisDXCoil.CCapFFlow(1) == 0) {
    4995           0 :             if (lAlphaBlanks(4)) {
    4996           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    4997           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(4)));
    4998             :             } else {
    4999           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5000           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(4), Alphas(4)));
    5001             :             }
    5002           0 :             ErrorsFound = true;
    5003             :         } else {
    5004             :             // Verify Curve Object, only legal type is Linear, Quadratic or Cubic
    5005          92 :             ErrorsFound |= Curve::CheckCurveDims(state,
    5006          46 :                                                  thisDXCoil.CCapFFlow(1), // Curve index
    5007             :                                                  {1},                     // Valid dimensions
    5008             :                                                  RoutineName,             // Routine name
    5009             :                                                  CurrentModuleObject,     // Object Type
    5010             :                                                  thisDXCoil.Name,         // Object Name
    5011          46 :                                                  cAlphaFields(4));        // Field Name
    5012             : 
    5013          46 :             if (!ErrorsFound) {
    5014          46 :                 checkCurveIsNormalizedToOne(
    5015          92 :                     state, std::string{RoutineName} + CurrentModuleObject, thisDXCoil.Name, thisDXCoil.CCapFFlow(1), cAlphaFields(4), Alphas(4), 1.0);
    5016             :             }
    5017             :         }
    5018             : 
    5019          46 :         thisDXCoil.AirInNode = GetOnlySingleNode(state,
    5020          46 :                                                  Alphas(5),
    5021             :                                                  ErrorsFound,
    5022             :                                                  DataLoopNode::ConnectionObjectType::CoilCoolingDXVariableRefrigerantFlow,
    5023          46 :                                                  Alphas(1),
    5024             :                                                  DataLoopNode::NodeFluidType::Air,
    5025             :                                                  DataLoopNode::ConnectionType::Inlet,
    5026             :                                                  NodeInputManager::CompFluidStream::Primary,
    5027             :                                                  ObjectIsNotParent);
    5028             : 
    5029          46 :         thisDXCoil.AirOutNode = GetOnlySingleNode(state,
    5030          46 :                                                   Alphas(6),
    5031             :                                                   ErrorsFound,
    5032             :                                                   DataLoopNode::ConnectionObjectType::CoilCoolingDXVariableRefrigerantFlow,
    5033          46 :                                                   Alphas(1),
    5034             :                                                   DataLoopNode::NodeFluidType::Air,
    5035             :                                                   DataLoopNode::ConnectionType::Outlet,
    5036             :                                                   NodeInputManager::CompFluidStream::Primary,
    5037             :                                                   ObjectIsNotParent);
    5038             : 
    5039          46 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(5), Alphas(6), "Air Nodes");
    5040             : 
    5041          46 :         thisDXCoil.CondensateCollectName = Alphas(7);
    5042          46 :         if (lAlphaBlanks(7)) {
    5043          46 :             thisDXCoil.CondensateCollectMode = CondensateCollectAction::Discard;
    5044             :         } else {
    5045           0 :             thisDXCoil.CondensateCollectMode = CondensateCollectAction::ToTank;
    5046           0 :             SetupTankSupplyComponent(state,
    5047             :                                      thisDXCoil.Name,
    5048             :                                      CurrentModuleObject,
    5049             :                                      thisDXCoil.CondensateCollectName,
    5050             :                                      ErrorsFound,
    5051           0 :                                      thisDXCoil.CondensateTankID,
    5052           0 :                                      thisDXCoil.CondensateTankSupplyARRID);
    5053             :         }
    5054             :     }
    5055             : 
    5056         247 :     if (ErrorsFound) {
    5057           0 :         ShowFatalError(state,
    5058           0 :                        format("{}Errors found in getting {} input. Preceding condition(s) causes termination.", RoutineName, CurrentModuleObject));
    5059             :     }
    5060             : 
    5061             :     // Loop over the VRF Heating Coils and get & load the data
    5062         247 :     CurrentModuleObject = HVAC::cAllCoilTypes(HVAC::CoilVRF_Heating);
    5063         293 :     for (DXCoilIndex = 1; DXCoilIndex <= state.dataDXCoils->NumVRFHeatingCoils; ++DXCoilIndex) {
    5064             : 
    5065          46 :         state.dataInputProcessing->inputProcessor->getObjectItem(state,
    5066             :                                                                  CurrentModuleObject,
    5067             :                                                                  DXCoilIndex,
    5068             :                                                                  Alphas,
    5069             :                                                                  NumAlphas,
    5070             :                                                                  Numbers,
    5071             :                                                                  NumNumbers,
    5072             :                                                                  IOStatus,
    5073             :                                                                  lNumericBlanks,
    5074             :                                                                  lAlphaBlanks,
    5075             :                                                                  cAlphaFields,
    5076             :                                                                  cNumericFields);
    5077             : 
    5078          46 :         ++DXCoilNum;
    5079             : 
    5080             :         // allocate single performance mode for numeric field strings used for sizing routine
    5081          46 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode.allocate(1);
    5082          46 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames.allocate(MaxNumbers);
    5083          46 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames = cNumericFields;
    5084             :         // ErrorsFound will be set to True if problem was found, left untouched otherwise
    5085          46 :         VerifyUniqueCoilName(state, CurrentModuleObject, Alphas(1), ErrorsFound, CurrentModuleObject + " Name");
    5086             : 
    5087          46 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    5088          46 :         thisDXCoil.Name = Alphas(1);
    5089          46 :         thisDXCoil.DXCoilType = CurrentModuleObject;
    5090          46 :         thisDXCoil.DXCoilType_Num = HVAC::CoilVRF_Heating;
    5091          46 :         thisDXCoil.Schedule = Alphas(2);
    5092          46 :         if (lAlphaBlanks(2)) {
    5093           5 :             thisDXCoil.SchedPtr = ScheduleManager::ScheduleAlwaysOn;
    5094             :         } else {
    5095          41 :             thisDXCoil.SchedPtr = GetScheduleIndex(state, Alphas(2)); // convert schedule name to pointer
    5096          41 :             if (thisDXCoil.SchedPtr == 0) {
    5097           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5098           0 :                 ShowContinueError(state, format("...{}=\"{}\".", cAlphaFields(2), Alphas(2)));
    5099           0 :                 ErrorsFound = true;
    5100             :             }
    5101             :         }
    5102          46 :         thisDXCoil.RatedTotCap(1) = Numbers(1);
    5103          46 :         thisDXCoil.RatedAirVolFlowRate(1) = Numbers(2);
    5104             : 
    5105          46 :         thisDXCoil.AirInNode = GetOnlySingleNode(state,
    5106          46 :                                                  Alphas(3),
    5107             :                                                  ErrorsFound,
    5108             :                                                  DataLoopNode::ConnectionObjectType::CoilHeatingDXVariableRefrigerantFlow,
    5109          46 :                                                  Alphas(1),
    5110             :                                                  DataLoopNode::NodeFluidType::Air,
    5111             :                                                  DataLoopNode::ConnectionType::Inlet,
    5112             :                                                  NodeInputManager::CompFluidStream::Primary,
    5113             :                                                  ObjectIsNotParent);
    5114             : 
    5115          46 :         thisDXCoil.AirOutNode = GetOnlySingleNode(state,
    5116          46 :                                                   Alphas(4),
    5117             :                                                   ErrorsFound,
    5118             :                                                   DataLoopNode::ConnectionObjectType::CoilHeatingDXVariableRefrigerantFlow,
    5119          46 :                                                   Alphas(1),
    5120             :                                                   DataLoopNode::NodeFluidType::Air,
    5121             :                                                   DataLoopNode::ConnectionType::Outlet,
    5122             :                                                   NodeInputManager::CompFluidStream::Primary,
    5123             :                                                   ObjectIsNotParent);
    5124             : 
    5125          46 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(3), Alphas(4), "Air Nodes");
    5126             : 
    5127          46 :         thisDXCoil.CCapFTemp = GetCurveIndex(state, Alphas(5));
    5128          46 :         if (thisDXCoil.CCapFTemp(1) == 0) {
    5129           0 :             if (lAlphaBlanks(5)) {
    5130           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5131           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(5)));
    5132             :             } else {
    5133           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5134           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(5), Alphas(5)));
    5135             :             }
    5136           0 :             ErrorsFound = true;
    5137             :         } else {
    5138          92 :             ErrorsFound |= Curve::CheckCurveDims(state,
    5139          46 :                                                  thisDXCoil.CCapFTemp(1), // Curve index
    5140             :                                                  {1, 2},                  // Valid dimensions  // MULTIPLECURVEDIMS
    5141             :                                                  RoutineName,             // Routine name
    5142             :                                                  CurrentModuleObject,     // Object Type
    5143             :                                                  thisDXCoil.Name,         // Object Name
    5144          46 :                                                  cAlphaFields(5));        // Field Name
    5145             : 
    5146          46 :             if (!ErrorsFound) {
    5147          46 :                 if (state.dataCurveManager->PerfCurve(thisDXCoil.CCapFTemp(1))->numDims == 1) {
    5148          31 :                     checkCurveIsNormalizedToOne(state,
    5149          62 :                                                 std::string{RoutineName} + CurrentModuleObject,
    5150          31 :                                                 thisDXCoil.Name,
    5151          31 :                                                 thisDXCoil.CCapFTemp(1),
    5152          31 :                                                 cAlphaFields(5),
    5153          31 :                                                 Alphas(5),
    5154             :                                                 RatedInletAirTempHeat);
    5155             :                 } else {
    5156             :                     // Can't check this here, don't know if using outdoor dry-bulb or outdoor wet-bulb temp as input. Make this check in VRF TU
    5157             :                     // GetInput.
    5158             :                 }
    5159             :             }
    5160             :         }
    5161             : 
    5162          46 :         thisDXCoil.CCapFFlow(1) = GetCurveIndex(state, Alphas(6)); // convert curve name to number
    5163          46 :         if (thisDXCoil.CCapFFlow(1) == 0) {
    5164           0 :             if (lAlphaBlanks(6)) {
    5165           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5166           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(6)));
    5167             :             } else {
    5168           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5169           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(6), Alphas(6)));
    5170             :             }
    5171           0 :             ErrorsFound = true;
    5172             :         } else {
    5173             :             // Verify Curve Object, only legal type is Quadratic
    5174          92 :             ErrorsFound |= Curve::CheckCurveDims(state,
    5175          46 :                                                  thisDXCoil.CCapFFlow(1), // Curve index
    5176             :                                                  {1},                     // Valid dimensions
    5177             :                                                  RoutineName,             // Routine name
    5178             :                                                  CurrentModuleObject,     // Object Type
    5179             :                                                  thisDXCoil.Name,         // Object Name
    5180          46 :                                                  cAlphaFields(6));        // Field Name
    5181             : 
    5182          46 :             if (!ErrorsFound) {
    5183          46 :                 checkCurveIsNormalizedToOne(
    5184          92 :                     state, std::string{RoutineName} + CurrentModuleObject, thisDXCoil.Name, thisDXCoil.CCapFFlow(1), cAlphaFields(6), Alphas(6), 1.0);
    5185             :             }
    5186             :         }
    5187             :     }
    5188             : 
    5189         247 :     if (ErrorsFound) {
    5190           0 :         ShowFatalError(state,
    5191           0 :                        format("{}Errors found in getting {} input. Preceding condition(s) causes termination.", RoutineName, CurrentModuleObject));
    5192             :     }
    5193             : 
    5194             :     // Loop over the VRF Cooling Coils for VRF FluidTCtrl Model_zrp 2015
    5195         247 :     CurrentModuleObject = HVAC::cAllCoilTypes(HVAC::CoilVRF_FluidTCtrl_Cooling);
    5196         263 :     for (DXCoilIndex = 1; DXCoilIndex <= state.dataDXCoils->NumVRFCoolingFluidTCtrlCoils; ++DXCoilIndex) {
    5197             : 
    5198          16 :         state.dataInputProcessing->inputProcessor->getObjectItem(state,
    5199             :                                                                  CurrentModuleObject,
    5200             :                                                                  DXCoilIndex,
    5201             :                                                                  Alphas,
    5202             :                                                                  NumAlphas,
    5203             :                                                                  Numbers,
    5204             :                                                                  NumNumbers,
    5205             :                                                                  IOStatus,
    5206             :                                                                  lNumericBlanks,
    5207             :                                                                  lAlphaBlanks,
    5208             :                                                                  cAlphaFields,
    5209             :                                                                  cNumericFields);
    5210             : 
    5211          16 :         ++DXCoilNum;
    5212             : 
    5213             :         // allocate single performance mode for numeric field strings used for sizing routine
    5214          16 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode.allocate(1);
    5215          16 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames.allocate(MaxNumbers);
    5216          16 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames = cNumericFields;
    5217             :         // ErrorsFound will be set to True if problem was found, left untouched otherwise
    5218          16 :         VerifyUniqueCoilName(state, CurrentModuleObject, Alphas(1), ErrorsFound, CurrentModuleObject + " Name");
    5219             : 
    5220          16 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    5221          16 :         thisDXCoil.Name = Alphas(1);
    5222          16 :         thisDXCoil.DXCoilType = CurrentModuleObject;
    5223          16 :         thisDXCoil.DXCoilType_Num = HVAC::CoilVRF_FluidTCtrl_Cooling;
    5224          16 :         thisDXCoil.Schedule = Alphas(2);
    5225          16 :         if (lAlphaBlanks(2)) {
    5226           0 :             thisDXCoil.SchedPtr = ScheduleManager::ScheduleAlwaysOn;
    5227             :         } else {
    5228          16 :             thisDXCoil.SchedPtr = GetScheduleIndex(state, Alphas(2)); // convert schedule name to pointer
    5229          16 :             if (thisDXCoil.SchedPtr == 0) {
    5230           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5231           0 :                 ShowContinueError(state, format("...{}=\"{}\".", cAlphaFields(2), Alphas(2)));
    5232           0 :                 ErrorsFound = true;
    5233             :             }
    5234             :         }
    5235             : 
    5236          16 :         thisDXCoil.AirInNode = GetOnlySingleNode(state,
    5237          16 :                                                  Alphas(3),
    5238             :                                                  ErrorsFound,
    5239             :                                                  DataLoopNode::ConnectionObjectType::CoilCoolingDXVariableRefrigerantFlowFluidTemperatureControl,
    5240          16 :                                                  Alphas(1),
    5241             :                                                  DataLoopNode::NodeFluidType::Air,
    5242             :                                                  DataLoopNode::ConnectionType::Inlet,
    5243             :                                                  NodeInputManager::CompFluidStream::Primary,
    5244             :                                                  ObjectIsNotParent);
    5245          16 :         thisDXCoil.AirOutNode = GetOnlySingleNode(state,
    5246          16 :                                                   Alphas(4),
    5247             :                                                   ErrorsFound,
    5248             :                                                   DataLoopNode::ConnectionObjectType::CoilCoolingDXVariableRefrigerantFlowFluidTemperatureControl,
    5249          16 :                                                   Alphas(1),
    5250             :                                                   DataLoopNode::NodeFluidType::Air,
    5251             :                                                   DataLoopNode::ConnectionType::Outlet,
    5252             :                                                   NodeInputManager::CompFluidStream::Primary,
    5253             :                                                   ObjectIsNotParent);
    5254          16 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(3), Alphas(4), "Air Nodes");
    5255             : 
    5256          16 :         thisDXCoil.RatedTotCap(1) = Numbers(1);
    5257          16 :         thisDXCoil.RatedSHR(1) = Numbers(2);
    5258          16 :         thisDXCoil.SH = Numbers(3);
    5259             :         // @@ DXCoil( DXCoilNum ).RateBFVRFIUEvap = 0.0592; there will be a new field for this, which will be handled in a separate issue to
    5260             :         // update VRF-HP idd. It is not hanlded here to avoide tranistion issues for VRF-HP.
    5261             : 
    5262          16 :         int indexSHCurve = GetCurveIndex(state, Alphas(5)); // convert curve name to index number
    5263             :         // Verify curve name and type
    5264          16 :         if (indexSHCurve == 0) {
    5265           0 :             if (lAlphaBlanks(5)) {
    5266           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5267           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(5)));
    5268             :             } else {
    5269           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5270           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(5), Alphas(5)));
    5271             :             }
    5272           0 :             ErrorsFound = true;
    5273             :         } else {
    5274             :             {
    5275          16 :                 if (state.dataCurveManager->PerfCurve(indexSHCurve)->curveType == Curve::CurveType::Quadratic) {
    5276          16 :                     thisDXCoil.C1Te = state.dataCurveManager->PerfCurve(indexSHCurve)->coeff[0];
    5277          16 :                     thisDXCoil.C2Te = state.dataCurveManager->PerfCurve(indexSHCurve)->coeff[1];
    5278          16 :                     thisDXCoil.C3Te = state.dataCurveManager->PerfCurve(indexSHCurve)->coeff[2];
    5279             : 
    5280             :                 } else {
    5281           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5282           0 :                     ShowContinueError(state,
    5283           0 :                                       format("...illegal {} type for this object = {}",
    5284             :                                              cAlphaFields(5),
    5285           0 :                                              Curve::objectNames[static_cast<int>(state.dataCurveManager->PerfCurve(indexSHCurve)->curveType)]));
    5286           0 :                     ShowContinueError(state, "... Curve type must be Quadratic.");
    5287           0 :                     ErrorsFound = true;
    5288             :                 }
    5289             :             }
    5290             :         }
    5291             : 
    5292          16 :         thisDXCoil.CondensateCollectName = Alphas(6);
    5293          16 :         if (lAlphaBlanks(6)) {
    5294          16 :             thisDXCoil.CondensateCollectMode = CondensateCollectAction::Discard;
    5295             :         } else {
    5296           0 :             thisDXCoil.CondensateCollectMode = CondensateCollectAction::ToTank;
    5297           0 :             SetupTankSupplyComponent(state,
    5298             :                                      thisDXCoil.Name,
    5299             :                                      CurrentModuleObject,
    5300             :                                      thisDXCoil.CondensateCollectName,
    5301             :                                      ErrorsFound,
    5302           0 :                                      thisDXCoil.CondensateTankID,
    5303           0 :                                      thisDXCoil.CondensateTankSupplyARRID);
    5304             :         }
    5305             :     }
    5306             : 
    5307         247 :     if (ErrorsFound) {
    5308           0 :         ShowFatalError(state,
    5309           0 :                        format("{}Errors found in getting {} input. Preceding condition(s) causes termination.", RoutineName, CurrentModuleObject));
    5310             :     }
    5311             : 
    5312             :     // Loop over the VRF Heating Coils for VRF FluidTCtrl Model_zrp 2015
    5313         247 :     CurrentModuleObject = HVAC::cAllCoilTypes(HVAC::CoilVRF_FluidTCtrl_Heating);
    5314         263 :     for (DXCoilIndex = 1; DXCoilIndex <= state.dataDXCoils->NumVRFHeatingFluidTCtrlCoils; ++DXCoilIndex) {
    5315             : 
    5316          16 :         state.dataInputProcessing->inputProcessor->getObjectItem(state,
    5317             :                                                                  CurrentModuleObject,
    5318             :                                                                  DXCoilIndex,
    5319             :                                                                  Alphas,
    5320             :                                                                  NumAlphas,
    5321             :                                                                  Numbers,
    5322             :                                                                  NumNumbers,
    5323             :                                                                  IOStatus,
    5324             :                                                                  lNumericBlanks,
    5325             :                                                                  lAlphaBlanks,
    5326             :                                                                  cAlphaFields,
    5327             :                                                                  cNumericFields);
    5328             : 
    5329          16 :         ++DXCoilNum;
    5330             : 
    5331             :         // allocate single performance mode for numeric field strings used for sizing routine
    5332          16 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode.allocate(1);
    5333          16 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames.allocate(MaxNumbers);
    5334          16 :         state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames = cNumericFields;
    5335             :         // ErrorsFound will be set to True if problem was found, left untouched otherwise
    5336          16 :         VerifyUniqueCoilName(state, CurrentModuleObject, Alphas(1), ErrorsFound, CurrentModuleObject + " Name");
    5337             : 
    5338          16 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    5339          16 :         thisDXCoil.Name = Alphas(1);
    5340          16 :         thisDXCoil.DXCoilType = CurrentModuleObject;
    5341          16 :         thisDXCoil.DXCoilType_Num = HVAC::CoilVRF_FluidTCtrl_Heating;
    5342          16 :         thisDXCoil.Schedule = Alphas(2);
    5343          16 :         if (lAlphaBlanks(2)) {
    5344           0 :             thisDXCoil.SchedPtr = ScheduleManager::ScheduleAlwaysOn;
    5345             :         } else {
    5346          16 :             thisDXCoil.SchedPtr = GetScheduleIndex(state, Alphas(2)); // convert schedule name to pointer
    5347          16 :             if (thisDXCoil.SchedPtr == 0) {
    5348           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5349           0 :                 ShowContinueError(state, format("...{}=\"{}\".", cAlphaFields(2), Alphas(2)));
    5350           0 :                 ErrorsFound = true;
    5351             :             }
    5352             :         }
    5353             : 
    5354          16 :         thisDXCoil.AirInNode = GetOnlySingleNode(state,
    5355          16 :                                                  Alphas(3),
    5356             :                                                  ErrorsFound,
    5357             :                                                  DataLoopNode::ConnectionObjectType::CoilHeatingDXVariableRefrigerantFlowFluidTemperatureControl,
    5358          16 :                                                  Alphas(1),
    5359             :                                                  DataLoopNode::NodeFluidType::Air,
    5360             :                                                  DataLoopNode::ConnectionType::Inlet,
    5361             :                                                  NodeInputManager::CompFluidStream::Primary,
    5362             :                                                  ObjectIsNotParent);
    5363          16 :         thisDXCoil.AirOutNode = GetOnlySingleNode(state,
    5364          16 :                                                   Alphas(4),
    5365             :                                                   ErrorsFound,
    5366             :                                                   DataLoopNode::ConnectionObjectType::CoilHeatingDXVariableRefrigerantFlowFluidTemperatureControl,
    5367          16 :                                                   Alphas(1),
    5368             :                                                   DataLoopNode::NodeFluidType::Air,
    5369             :                                                   DataLoopNode::ConnectionType::Outlet,
    5370             :                                                   NodeInputManager::CompFluidStream::Primary,
    5371             :                                                   ObjectIsNotParent);
    5372          16 :         TestCompSet(state, CurrentModuleObject, Alphas(1), Alphas(3), Alphas(4), "Air Nodes");
    5373             : 
    5374          16 :         thisDXCoil.RatedTotCap(1) = Numbers(1);
    5375          16 :         thisDXCoil.SC = Numbers(2);
    5376             :         //@@ DXCoil( DXCoilNum ).RateBFVRFIUCond = 0.136;
    5377             : 
    5378          16 :         int indexSCCurve = GetCurveIndex(state, Alphas(5)); // convert curve name to index number
    5379             :         // Verify curve name and type
    5380          16 :         if (indexSCCurve == 0) {
    5381           0 :             if (lAlphaBlanks(5)) {
    5382           0 :                 ShowSevereError(state, format("{}{}=\"{}\", missing", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5383           0 :                 ShowContinueError(state, format("...required {} is blank.", cAlphaFields(5)));
    5384             :             } else {
    5385           0 :                 ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5386           0 :                 ShowContinueError(state, format("...not found {}=\"{}\".", cAlphaFields(5), Alphas(5)));
    5387             :             }
    5388           0 :             ErrorsFound = true;
    5389             :         } else {
    5390             :             {
    5391          16 :                 if (state.dataCurveManager->PerfCurve(indexSCCurve)->curveType == Curve::CurveType::Quadratic) {
    5392          16 :                     thisDXCoil.C1Tc = state.dataCurveManager->PerfCurve(indexSCCurve)->coeff[0];
    5393          16 :                     thisDXCoil.C2Tc = state.dataCurveManager->PerfCurve(indexSCCurve)->coeff[1];
    5394          16 :                     thisDXCoil.C3Tc = state.dataCurveManager->PerfCurve(indexSCCurve)->coeff[2];
    5395             : 
    5396             :                 } else {
    5397           0 :                     ShowSevereError(state, format("{}{}=\"{}\", invalid", RoutineName, CurrentModuleObject, thisDXCoil.Name));
    5398           0 :                     ShowContinueError(state,
    5399           0 :                                       format("...illegal {} type for this object = {}",
    5400             :                                              cAlphaFields(5),
    5401           0 :                                              Curve::objectNames[static_cast<int>(state.dataCurveManager->PerfCurve(indexSCCurve)->curveType)]));
    5402           0 :                     ShowContinueError(state, "... Curve type must be Quadratic.");
    5403           0 :                     ErrorsFound = true;
    5404             :                 }
    5405             :             }
    5406             :         }
    5407             :     }
    5408             : 
    5409         247 :     if (ErrorsFound) {
    5410           0 :         ShowFatalError(state,
    5411           0 :                        format("{}Errors found in getting {} input. Preceding condition(s) causes termination.", RoutineName, CurrentModuleObject));
    5412             :     }
    5413             : 
    5414        1223 :     for (DXCoilNum = 1; DXCoilNum <= state.dataDXCoils->NumDXCoils; ++DXCoilNum) {
    5415             : 
    5416         976 :         auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    5417             : 
    5418         976 :         if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingSingleSpeed || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl) {
    5419             :             // Setup Report Variables for Cooling Equipment
    5420             :             // CurrentModuleObject='Coil:Cooling:DX:SingleSpeed/Coil:Cooling:DX:TwoStageWithHumidityControlMode'
    5421        1246 :             SetupOutputVariable(state,
    5422             :                                 "Cooling Coil Total Cooling Rate",
    5423             :                                 Constant::Units::W,
    5424         623 :                                 thisDXCoil.TotalCoolingEnergyRate,
    5425             :                                 OutputProcessor::TimeStepType::System,
    5426             :                                 OutputProcessor::StoreType::Average,
    5427         623 :                                 thisDXCoil.Name);
    5428        1246 :             SetupOutputVariable(state,
    5429             :                                 "Cooling Coil Total Cooling Energy",
    5430             :                                 Constant::Units::J,
    5431         623 :                                 thisDXCoil.TotalCoolingEnergy,
    5432             :                                 OutputProcessor::TimeStepType::System,
    5433             :                                 OutputProcessor::StoreType::Sum,
    5434         623 :                                 thisDXCoil.Name,
    5435             :                                 Constant::eResource::EnergyTransfer,
    5436             :                                 OutputProcessor::Group::HVAC,
    5437             :                                 OutputProcessor::EndUseCat::CoolingCoils);
    5438        1246 :             SetupOutputVariable(state,
    5439             :                                 "Cooling Coil Sensible Cooling Rate",
    5440             :                                 Constant::Units::W,
    5441         623 :                                 thisDXCoil.SensCoolingEnergyRate,
    5442             :                                 OutputProcessor::TimeStepType::System,
    5443             :                                 OutputProcessor::StoreType::Average,
    5444         623 :                                 thisDXCoil.Name);
    5445        1246 :             SetupOutputVariable(state,
    5446             :                                 "Cooling Coil Sensible Cooling Energy",
    5447             :                                 Constant::Units::J,
    5448         623 :                                 thisDXCoil.SensCoolingEnergy,
    5449             :                                 OutputProcessor::TimeStepType::System,
    5450             :                                 OutputProcessor::StoreType::Sum,
    5451         623 :                                 thisDXCoil.Name);
    5452        1246 :             SetupOutputVariable(state,
    5453             :                                 "Cooling Coil Latent Cooling Rate",
    5454             :                                 Constant::Units::W,
    5455         623 :                                 thisDXCoil.LatCoolingEnergyRate,
    5456             :                                 OutputProcessor::TimeStepType::System,
    5457             :                                 OutputProcessor::StoreType::Average,
    5458         623 :                                 thisDXCoil.Name);
    5459        1246 :             SetupOutputVariable(state,
    5460             :                                 "Cooling Coil Latent Cooling Energy",
    5461             :                                 Constant::Units::J,
    5462         623 :                                 thisDXCoil.LatCoolingEnergy,
    5463             :                                 OutputProcessor::TimeStepType::System,
    5464             :                                 OutputProcessor::StoreType::Sum,
    5465         623 :                                 thisDXCoil.Name);
    5466        1246 :             SetupOutputVariable(state,
    5467             :                                 "Cooling Coil Electricity Rate",
    5468             :                                 Constant::Units::W,
    5469         623 :                                 thisDXCoil.ElecCoolingPower,
    5470             :                                 OutputProcessor::TimeStepType::System,
    5471             :                                 OutputProcessor::StoreType::Average,
    5472         623 :                                 thisDXCoil.Name);
    5473        1246 :             SetupOutputVariable(state,
    5474             :                                 "Cooling Coil Electricity Energy",
    5475             :                                 Constant::Units::J,
    5476         623 :                                 thisDXCoil.ElecCoolingConsumption,
    5477             :                                 OutputProcessor::TimeStepType::System,
    5478             :                                 OutputProcessor::StoreType::Sum,
    5479         623 :                                 thisDXCoil.Name,
    5480             :                                 Constant::eResource::Electricity,
    5481             :                                 OutputProcessor::Group::HVAC,
    5482             :                                 OutputProcessor::EndUseCat::Cooling);
    5483        1246 :             SetupOutputVariable(state,
    5484             :                                 "Cooling Coil Runtime Fraction",
    5485             :                                 Constant::Units::None,
    5486         623 :                                 thisDXCoil.CoolingCoilRuntimeFraction,
    5487             :                                 OutputProcessor::TimeStepType::System,
    5488             :                                 OutputProcessor::StoreType::Average,
    5489         623 :                                 thisDXCoil.Name);
    5490         623 :             if (thisDXCoil.IsSecondaryDXCoilInZone) {
    5491           2 :                 SetupOutputVariable(state,
    5492             :                                     "Secondary Coil Heat Rejection Rate",
    5493             :                                     Constant::Units::W,
    5494           1 :                                     thisDXCoil.SecCoilSensibleHeatGainRate,
    5495             :                                     OutputProcessor::TimeStepType::System,
    5496             :                                     OutputProcessor::StoreType::Average,
    5497           1 :                                     thisDXCoil.Name);
    5498             :             }
    5499             : 
    5500             :             // do we report these even if no storage tank?
    5501         623 :             if (thisDXCoil.CondensateCollectMode == CondensateCollectAction::ToTank) {
    5502           0 :                 SetupOutputVariable(state,
    5503             :                                     "Cooling Coil Condensate Volume Flow Rate",
    5504             :                                     Constant::Units::m3_s,
    5505           0 :                                     thisDXCoil.CondensateVdot,
    5506             :                                     OutputProcessor::TimeStepType::System,
    5507             :                                     OutputProcessor::StoreType::Average,
    5508           0 :                                     thisDXCoil.Name);
    5509           0 :                 SetupOutputVariable(state,
    5510             :                                     "Cooling Coil Condensate Volume",
    5511             :                                     Constant::Units::m3,
    5512           0 :                                     thisDXCoil.CondensateVol,
    5513             :                                     OutputProcessor::TimeStepType::System,
    5514             :                                     OutputProcessor::StoreType::Sum,
    5515           0 :                                     thisDXCoil.Name,
    5516             :                                     Constant::eResource::OnSiteWater,
    5517             :                                     OutputProcessor::Group::HVAC,
    5518             :                                     OutputProcessor::EndUseCat::Condensate);
    5519             :             }
    5520             : 
    5521         623 :             if (thisDXCoil.ReportEvapCondVars) {
    5522           4 :                 SetupOutputVariable(state,
    5523             :                                     "Cooling Coil Condenser Inlet Temperature",
    5524             :                                     Constant::Units::C,
    5525           2 :                                     thisDXCoil.CondInletTemp,
    5526             :                                     OutputProcessor::TimeStepType::System,
    5527             :                                     OutputProcessor::StoreType::Average,
    5528           2 :                                     thisDXCoil.Name);
    5529           4 :                 SetupOutputVariable(state,
    5530             :                                     "Cooling Coil Evaporative Condenser Water Volume",
    5531             :                                     Constant::Units::m3,
    5532           2 :                                     thisDXCoil.EvapWaterConsump,
    5533             :                                     OutputProcessor::TimeStepType::System,
    5534             :                                     OutputProcessor::StoreType::Sum,
    5535           2 :                                     thisDXCoil.Name,
    5536             :                                     Constant::eResource::Water,
    5537             :                                     OutputProcessor::Group::HVAC,
    5538             :                                     OutputProcessor::EndUseCat::Cooling);
    5539           4 :                 SetupOutputVariable(state,
    5540             :                                     "Cooling Coil Evaporative Condenser Mains Supply Water Volume",
    5541             :                                     Constant::Units::m3,
    5542           2 :                                     thisDXCoil.EvapWaterConsump,
    5543             :                                     OutputProcessor::TimeStepType::System,
    5544             :                                     OutputProcessor::StoreType::Sum,
    5545           2 :                                     thisDXCoil.Name,
    5546             :                                     Constant::eResource::MainsWater,
    5547             :                                     OutputProcessor::Group::HVAC,
    5548             :                                     OutputProcessor::EndUseCat::Cooling);
    5549           4 :                 SetupOutputVariable(state,
    5550             :                                     "Cooling Coil Evaporative Condenser Pump Electricity Rate",
    5551             :                                     Constant::Units::W,
    5552           2 :                                     thisDXCoil.EvapCondPumpElecPower,
    5553             :                                     OutputProcessor::TimeStepType::System,
    5554             :                                     OutputProcessor::StoreType::Average,
    5555           2 :                                     thisDXCoil.Name);
    5556           4 :                 SetupOutputVariable(state,
    5557             :                                     "Cooling Coil Evaporative Condenser Pump Electricity Energy",
    5558             :                                     Constant::Units::J,
    5559           2 :                                     thisDXCoil.EvapCondPumpElecConsumption,
    5560             :                                     OutputProcessor::TimeStepType::System,
    5561             :                                     OutputProcessor::StoreType::Sum,
    5562           2 :                                     thisDXCoil.Name,
    5563             :                                     Constant::eResource::Electricity,
    5564             :                                     OutputProcessor::Group::HVAC,
    5565             :                                     OutputProcessor::EndUseCat::Cooling);
    5566           2 :                 if (thisDXCoil.BasinHeaterPowerFTempDiff > 0.0) {
    5567           4 :                     SetupOutputVariable(state,
    5568             :                                         "Cooling Coil Basin Heater Electricity Rate",
    5569             :                                         Constant::Units::W,
    5570           2 :                                         thisDXCoil.BasinHeaterPower,
    5571             :                                         OutputProcessor::TimeStepType::System,
    5572             :                                         OutputProcessor::StoreType::Average,
    5573           2 :                                         thisDXCoil.Name);
    5574           4 :                     SetupOutputVariable(state,
    5575             :                                         "Cooling Coil Basin Heater Electricity Energy",
    5576             :                                         Constant::Units::J,
    5577           2 :                                         thisDXCoil.BasinHeaterConsumption,
    5578             :                                         OutputProcessor::TimeStepType::System,
    5579             :                                         OutputProcessor::StoreType::Sum,
    5580           2 :                                         thisDXCoil.Name,
    5581             :                                         Constant::eResource::Electricity,
    5582             :                                         OutputProcessor::Group::HVAC,
    5583             :                                         OutputProcessor::EndUseCat::Cooling);
    5584             :                 }
    5585             :             }
    5586             : 
    5587         623 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl) {
    5588             :                 // Setup Report Variables for Cooling Equipment
    5589             :                 // CurrentModuleObject='Cooling:DX:TwoStageWithHumidityControlMode'
    5590          22 :                 SetupOutputVariable(state,
    5591             :                                     "Cooling Coil Stage 2 Runtime Fraction",
    5592             :                                     Constant::Units::None,
    5593          11 :                                     thisDXCoil.CoolingCoilStg2RuntimeFrac,
    5594             :                                     OutputProcessor::TimeStepType::System,
    5595             :                                     OutputProcessor::StoreType::Average,
    5596          11 :                                     thisDXCoil.Name);
    5597          11 :                 SetupOutputVariable(state,
    5598             :                                     "Cooling Coil Dehumidification Mode",
    5599             :                                     Constant::Units::None,
    5600          11 :                                     (int &)thisDXCoil.DehumidificationMode,
    5601             :                                     OutputProcessor::TimeStepType::System,
    5602             :                                     OutputProcessor::StoreType::Average,
    5603          11 :                                     thisDXCoil.Name);
    5604             :             }
    5605             : 
    5606             :         }
    5607             : 
    5608         353 :         else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatingEmpirical) {
    5609             :             // Setup Report Variables for Heating Equipment
    5610             :             // CurrentModuleObject='Coil:Heating:DX:SingleSpeed'
    5611         150 :             SetupOutputVariable(state,
    5612             :                                 "Heating Coil Heating Rate",
    5613             :                                 Constant::Units::W,
    5614          75 :                                 thisDXCoil.TotalHeatingEnergyRate,
    5615             :                                 OutputProcessor::TimeStepType::System,
    5616             :                                 OutputProcessor::StoreType::Average,
    5617          75 :                                 thisDXCoil.Name);
    5618         150 :             SetupOutputVariable(state,
    5619             :                                 "Heating Coil Heating Energy",
    5620             :                                 Constant::Units::J,
    5621          75 :                                 thisDXCoil.TotalHeatingEnergy,
    5622             :                                 OutputProcessor::TimeStepType::System,
    5623             :                                 OutputProcessor::StoreType::Sum,
    5624          75 :                                 thisDXCoil.Name,
    5625             :                                 Constant::eResource::EnergyTransfer,
    5626             :                                 OutputProcessor::Group::HVAC,
    5627             :                                 OutputProcessor::EndUseCat::HeatingCoils);
    5628         150 :             SetupOutputVariable(state,
    5629             :                                 "Heating Coil Electricity Rate",
    5630             :                                 Constant::Units::W,
    5631          75 :                                 thisDXCoil.ElecHeatingPower,
    5632             :                                 OutputProcessor::TimeStepType::System,
    5633             :                                 OutputProcessor::StoreType::Average,
    5634          75 :                                 thisDXCoil.Name);
    5635         150 :             SetupOutputVariable(state,
    5636             :                                 "Heating Coil Electricity Energy",
    5637             :                                 Constant::Units::J,
    5638          75 :                                 thisDXCoil.ElecHeatingConsumption,
    5639             :                                 OutputProcessor::TimeStepType::System,
    5640             :                                 OutputProcessor::StoreType::Sum,
    5641          75 :                                 thisDXCoil.Name,
    5642             :                                 Constant::eResource::Electricity,
    5643             :                                 OutputProcessor::Group::HVAC,
    5644             :                                 OutputProcessor::EndUseCat::Heating);
    5645         150 :             SetupOutputVariable(state,
    5646             :                                 "Heating Coil Defrost Electricity Rate",
    5647             :                                 Constant::Units::W,
    5648          75 :                                 thisDXCoil.DefrostPower,
    5649             :                                 OutputProcessor::TimeStepType::System,
    5650             :                                 OutputProcessor::StoreType::Average,
    5651          75 :                                 thisDXCoil.Name);
    5652         150 :             SetupOutputVariable(state,
    5653             :                                 "Heating Coil Defrost Electricity Energy",
    5654             :                                 Constant::Units::J,
    5655          75 :                                 thisDXCoil.DefrostConsumption,
    5656             :                                 OutputProcessor::TimeStepType::System,
    5657             :                                 OutputProcessor::StoreType::Sum,
    5658          75 :                                 thisDXCoil.Name,
    5659             :                                 Constant::eResource::Electricity,
    5660             :                                 OutputProcessor::Group::HVAC,
    5661             :                                 OutputProcessor::EndUseCat::Heating);
    5662         150 :             SetupOutputVariable(state,
    5663             :                                 "Heating Coil Crankcase Heater Electricity Rate",
    5664             :                                 Constant::Units::W,
    5665          75 :                                 thisDXCoil.CrankcaseHeaterPower,
    5666             :                                 OutputProcessor::TimeStepType::System,
    5667             :                                 OutputProcessor::StoreType::Average,
    5668          75 :                                 thisDXCoil.Name);
    5669         150 :             SetupOutputVariable(state,
    5670             :                                 "Heating Coil Crankcase Heater Electricity Energy",
    5671             :                                 Constant::Units::J,
    5672          75 :                                 thisDXCoil.CrankcaseHeaterConsumption,
    5673             :                                 OutputProcessor::TimeStepType::System,
    5674             :                                 OutputProcessor::StoreType::Sum,
    5675          75 :                                 thisDXCoil.Name,
    5676             :                                 Constant::eResource::Electricity,
    5677             :                                 OutputProcessor::Group::HVAC,
    5678             :                                 OutputProcessor::EndUseCat::Heating);
    5679         150 :             SetupOutputVariable(state,
    5680             :                                 "Heating Coil Runtime Fraction",
    5681             :                                 Constant::Units::None,
    5682          75 :                                 thisDXCoil.HeatingCoilRuntimeFraction,
    5683             :                                 OutputProcessor::TimeStepType::System,
    5684             :                                 OutputProcessor::StoreType::Average,
    5685          75 :                                 thisDXCoil.Name);
    5686          75 :             if (thisDXCoil.IsSecondaryDXCoilInZone) {
    5687           2 :                 SetupOutputVariable(state,
    5688             :                                     "Secondary Coil Total Heat Removal Rate",
    5689             :                                     Constant::Units::W,
    5690           1 :                                     thisDXCoil.SecCoilTotalHeatRemovalRate,
    5691             :                                     OutputProcessor::TimeStepType::System,
    5692             :                                     OutputProcessor::StoreType::Average,
    5693           1 :                                     thisDXCoil.Name);
    5694           2 :                 SetupOutputVariable(state,
    5695             :                                     "Secondary Coil Sensible Heat Removal Rate",
    5696             :                                     Constant::Units::W,
    5697           1 :                                     thisDXCoil.SecCoilSensibleHeatRemovalRate,
    5698             :                                     OutputProcessor::TimeStepType::System,
    5699             :                                     OutputProcessor::StoreType::Average,
    5700           1 :                                     thisDXCoil.Name);
    5701           2 :                 SetupOutputVariable(state,
    5702             :                                     "Secondary Coil Latent Heat Removal Rate",
    5703             :                                     Constant::Units::W,
    5704           1 :                                     thisDXCoil.SecCoilLatentHeatRemovalRate,
    5705             :                                     OutputProcessor::TimeStepType::System,
    5706             :                                     OutputProcessor::StoreType::Average,
    5707           1 :                                     thisDXCoil.Name);
    5708           2 :                 SetupOutputVariable(state,
    5709             :                                     "Secondary Coil Sensible Heat Ratio",
    5710             :                                     Constant::Units::None,
    5711           1 :                                     thisDXCoil.SecCoilSHR,
    5712             :                                     OutputProcessor::TimeStepType::System,
    5713             :                                     OutputProcessor::StoreType::Average,
    5714           1 :                                     thisDXCoil.Name);
    5715           2 :                 SetupOutputVariable(state,
    5716             :                                     "Secondary Coil Compressor Part Load Ratio",
    5717             :                                     Constant::Units::None,
    5718           1 :                                     thisDXCoil.CompressorPartLoadRatio,
    5719             :                                     OutputProcessor::TimeStepType::System,
    5720             :                                     OutputProcessor::StoreType::Average,
    5721           1 :                                     thisDXCoil.Name);
    5722             :             }
    5723             :         }
    5724             : 
    5725         278 :         else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed) {
    5726             :             // Setup Report Variables for Cooling Equipment
    5727             :             // CurrentModuleObject='Coil:Cooling:DX:TwoSpeed'
    5728         134 :             SetupOutputVariable(state,
    5729             :                                 "Cooling Coil Total Cooling Rate",
    5730             :                                 Constant::Units::W,
    5731          67 :                                 thisDXCoil.TotalCoolingEnergyRate,
    5732             :                                 OutputProcessor::TimeStepType::System,
    5733             :                                 OutputProcessor::StoreType::Average,
    5734          67 :                                 thisDXCoil.Name);
    5735         134 :             SetupOutputVariable(state,
    5736             :                                 "Cooling Coil Total Cooling Energy",
    5737             :                                 Constant::Units::J,
    5738          67 :                                 thisDXCoil.TotalCoolingEnergy,
    5739             :                                 OutputProcessor::TimeStepType::System,
    5740             :                                 OutputProcessor::StoreType::Sum,
    5741          67 :                                 thisDXCoil.Name,
    5742             :                                 Constant::eResource::EnergyTransfer,
    5743             :                                 OutputProcessor::Group::HVAC,
    5744             :                                 OutputProcessor::EndUseCat::CoolingCoils);
    5745         134 :             SetupOutputVariable(state,
    5746             :                                 "Cooling Coil Sensible Cooling Rate",
    5747             :                                 Constant::Units::W,
    5748          67 :                                 thisDXCoil.SensCoolingEnergyRate,
    5749             :                                 OutputProcessor::TimeStepType::System,
    5750             :                                 OutputProcessor::StoreType::Average,
    5751          67 :                                 thisDXCoil.Name);
    5752         134 :             SetupOutputVariable(state,
    5753             :                                 "Cooling Coil Sensible Cooling Energy",
    5754             :                                 Constant::Units::J,
    5755          67 :                                 thisDXCoil.SensCoolingEnergy,
    5756             :                                 OutputProcessor::TimeStepType::System,
    5757             :                                 OutputProcessor::StoreType::Sum,
    5758          67 :                                 thisDXCoil.Name);
    5759         134 :             SetupOutputVariable(state,
    5760             :                                 "Cooling Coil Latent Cooling Rate",
    5761             :                                 Constant::Units::W,
    5762          67 :                                 thisDXCoil.LatCoolingEnergyRate,
    5763             :                                 OutputProcessor::TimeStepType::System,
    5764             :                                 OutputProcessor::StoreType::Average,
    5765          67 :                                 thisDXCoil.Name);
    5766         134 :             SetupOutputVariable(state,
    5767             :                                 "Cooling Coil Latent Cooling Energy",
    5768             :                                 Constant::Units::J,
    5769          67 :                                 thisDXCoil.LatCoolingEnergy,
    5770             :                                 OutputProcessor::TimeStepType::System,
    5771             :                                 OutputProcessor::StoreType::Sum,
    5772          67 :                                 thisDXCoil.Name);
    5773         134 :             SetupOutputVariable(state,
    5774             :                                 "Cooling Coil Electricity Rate",
    5775             :                                 Constant::Units::W,
    5776          67 :                                 thisDXCoil.ElecCoolingPower,
    5777             :                                 OutputProcessor::TimeStepType::System,
    5778             :                                 OutputProcessor::StoreType::Average,
    5779          67 :                                 thisDXCoil.Name);
    5780         134 :             SetupOutputVariable(state,
    5781             :                                 "Cooling Coil Electricity Energy",
    5782             :                                 Constant::Units::J,
    5783          67 :                                 thisDXCoil.ElecCoolingConsumption,
    5784             :                                 OutputProcessor::TimeStepType::System,
    5785             :                                 OutputProcessor::StoreType::Sum,
    5786          67 :                                 thisDXCoil.Name,
    5787             :                                 Constant::eResource::Electricity,
    5788             :                                 OutputProcessor::Group::HVAC,
    5789             :                                 OutputProcessor::EndUseCat::Cooling);
    5790         134 :             SetupOutputVariable(state,
    5791             :                                 "Cooling Coil Runtime Fraction",
    5792             :                                 Constant::Units::None,
    5793          67 :                                 thisDXCoil.CoolingCoilRuntimeFraction,
    5794             :                                 OutputProcessor::TimeStepType::System,
    5795             :                                 OutputProcessor::StoreType::Average,
    5796          67 :                                 thisDXCoil.Name);
    5797          67 :             if (thisDXCoil.IsSecondaryDXCoilInZone) {
    5798           0 :                 SetupOutputVariable(state,
    5799             :                                     "Secondary Coil Heat Rejection Rate",
    5800             :                                     Constant::Units::W,
    5801           0 :                                     thisDXCoil.SecCoilSensibleHeatGainRate,
    5802             :                                     OutputProcessor::TimeStepType::System,
    5803             :                                     OutputProcessor::StoreType::Average,
    5804           0 :                                     thisDXCoil.Name);
    5805             :             }
    5806             : 
    5807          67 :             if (thisDXCoil.ReportEvapCondVars) {
    5808           2 :                 SetupOutputVariable(state,
    5809             :                                     "Cooling Coil Condenser Inlet Temperature",
    5810             :                                     Constant::Units::C,
    5811           1 :                                     thisDXCoil.CondInletTemp,
    5812             :                                     OutputProcessor::TimeStepType::System,
    5813             :                                     OutputProcessor::StoreType::Average,
    5814           1 :                                     thisDXCoil.Name);
    5815           2 :                 SetupOutputVariable(state,
    5816             :                                     "Cooling Coil Evaporative Condenser Water Volume",
    5817             :                                     Constant::Units::m3,
    5818           1 :                                     thisDXCoil.EvapWaterConsump,
    5819             :                                     OutputProcessor::TimeStepType::System,
    5820             :                                     OutputProcessor::StoreType::Sum,
    5821           1 :                                     thisDXCoil.Name,
    5822             :                                     Constant::eResource::Water,
    5823             :                                     OutputProcessor::Group::HVAC,
    5824             :                                     OutputProcessor::EndUseCat::Cooling);
    5825           2 :                 SetupOutputVariable(state,
    5826             :                                     "Cooling Coil Evaporative Condenser Mains Supply Water Volume",
    5827             :                                     Constant::Units::m3,
    5828           1 :                                     thisDXCoil.EvapWaterConsump,
    5829             :                                     OutputProcessor::TimeStepType::System,
    5830             :                                     OutputProcessor::StoreType::Sum,
    5831           1 :                                     thisDXCoil.Name,
    5832             :                                     Constant::eResource::MainsWater,
    5833             :                                     OutputProcessor::Group::HVAC,
    5834             :                                     OutputProcessor::EndUseCat::Cooling);
    5835           2 :                 SetupOutputVariable(state,
    5836             :                                     "Cooling Coil Evaporative Condenser Pump Electricity Rate",
    5837             :                                     Constant::Units::W,
    5838           1 :                                     thisDXCoil.EvapCondPumpElecPower,
    5839             :                                     OutputProcessor::TimeStepType::System,
    5840             :                                     OutputProcessor::StoreType::Average,
    5841           1 :                                     thisDXCoil.Name);
    5842           2 :                 SetupOutputVariable(state,
    5843             :                                     "Cooling Coil Evaporative Condenser Pump Electricity Energy",
    5844             :                                     Constant::Units::J,
    5845           1 :                                     thisDXCoil.EvapCondPumpElecConsumption,
    5846             :                                     OutputProcessor::TimeStepType::System,
    5847             :                                     OutputProcessor::StoreType::Sum,
    5848           1 :                                     thisDXCoil.Name,
    5849             :                                     Constant::eResource::Electricity,
    5850             :                                     OutputProcessor::Group::HVAC,
    5851             :                                     OutputProcessor::EndUseCat::Cooling);
    5852           1 :                 if (thisDXCoil.BasinHeaterPowerFTempDiff > 0.0) {
    5853           2 :                     SetupOutputVariable(state,
    5854             :                                         "Cooling Coil Basin Heater Electricity Rate",
    5855             :                                         Constant::Units::W,
    5856           1 :                                         thisDXCoil.BasinHeaterPower,
    5857             :                                         OutputProcessor::TimeStepType::System,
    5858             :                                         OutputProcessor::StoreType::Average,
    5859           1 :                                         thisDXCoil.Name);
    5860           2 :                     SetupOutputVariable(state,
    5861             :                                         "Cooling Coil Basin Heater Electricity Energy",
    5862             :                                         Constant::Units::J,
    5863           1 :                                         thisDXCoil.BasinHeaterConsumption,
    5864             :                                         OutputProcessor::TimeStepType::System,
    5865             :                                         OutputProcessor::StoreType::Sum,
    5866           1 :                                         thisDXCoil.Name,
    5867             :                                         Constant::eResource::Electricity,
    5868             :                                         OutputProcessor::Group::HVAC,
    5869             :                                         OutputProcessor::EndUseCat::Cooling);
    5870             :                 }
    5871             :             }
    5872             : 
    5873             :         }
    5874             : 
    5875         211 :         else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    5876         198 :                  thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) {
    5877             :             // Setup Report Variables for Cooling Equipment
    5878             :             // CurrentModuleObject='Coil:WaterHeating:AirToWaterHeatPump:Pumped'
    5879             :             // or 'Coil:WaterHeating:AirToWaterHeatPump:Wrapped'
    5880          32 :             SetupOutputVariable(state,
    5881             :                                 "Cooling Coil Total Cooling Rate",
    5882             :                                 Constant::Units::W,
    5883          16 :                                 thisDXCoil.TotalCoolingEnergyRate,
    5884             :                                 OutputProcessor::TimeStepType::System,
    5885             :                                 OutputProcessor::StoreType::Average,
    5886          16 :                                 thisDXCoil.Name);
    5887             : 
    5888          16 :             if (thisDXCoil.IsDXCoilInZone) {
    5889          30 :                 SetupOutputVariable(state,
    5890             :                                     "Cooling Coil Total Cooling Energy",
    5891             :                                     Constant::Units::J,
    5892          15 :                                     thisDXCoil.TotalCoolingEnergy,
    5893             :                                     OutputProcessor::TimeStepType::System,
    5894             :                                     OutputProcessor::StoreType::Sum,
    5895          15 :                                     thisDXCoil.Name,
    5896             :                                     Constant::eResource::EnergyTransfer,
    5897             :                                     OutputProcessor::Group::HVAC,
    5898             :                                     OutputProcessor::EndUseCat::CoolingCoils);
    5899             :             } else {
    5900           2 :                 SetupOutputVariable(state,
    5901             :                                     "Cooling Coil Total Cooling Energy",
    5902             :                                     Constant::Units::J,
    5903           1 :                                     thisDXCoil.TotalCoolingEnergy,
    5904             :                                     OutputProcessor::TimeStepType::System,
    5905             :                                     OutputProcessor::StoreType::Sum,
    5906           1 :                                     thisDXCoil.Name);
    5907             :             }
    5908             : 
    5909          32 :             SetupOutputVariable(state,
    5910             :                                 "Cooling Coil Sensible Cooling Rate",
    5911             :                                 Constant::Units::W,
    5912          16 :                                 thisDXCoil.SensCoolingEnergyRate,
    5913             :                                 OutputProcessor::TimeStepType::System,
    5914             :                                 OutputProcessor::StoreType::Average,
    5915          16 :                                 thisDXCoil.Name);
    5916          32 :             SetupOutputVariable(state,
    5917             :                                 "Cooling Coil Sensible Cooling Energy",
    5918             :                                 Constant::Units::J,
    5919          16 :                                 thisDXCoil.SensCoolingEnergy,
    5920             :                                 OutputProcessor::TimeStepType::System,
    5921             :                                 OutputProcessor::StoreType::Sum,
    5922          16 :                                 thisDXCoil.Name);
    5923          32 :             SetupOutputVariable(state,
    5924             :                                 "Cooling Coil Latent Cooling Rate",
    5925             :                                 Constant::Units::W,
    5926          16 :                                 thisDXCoil.LatCoolingEnergyRate,
    5927             :                                 OutputProcessor::TimeStepType::System,
    5928             :                                 OutputProcessor::StoreType::Average,
    5929          16 :                                 thisDXCoil.Name);
    5930          32 :             SetupOutputVariable(state,
    5931             :                                 "Cooling Coil Latent Cooling Energy",
    5932             :                                 Constant::Units::J,
    5933          16 :                                 thisDXCoil.LatCoolingEnergy,
    5934             :                                 OutputProcessor::TimeStepType::System,
    5935             :                                 OutputProcessor::StoreType::Sum,
    5936          16 :                                 thisDXCoil.Name);
    5937          32 :             SetupOutputVariable(state,
    5938             :                                 "Cooling Coil Runtime Fraction",
    5939             :                                 Constant::Units::None,
    5940          16 :                                 thisDXCoil.CoolingCoilRuntimeFraction,
    5941             :                                 OutputProcessor::TimeStepType::System,
    5942             :                                 OutputProcessor::StoreType::Average,
    5943          16 :                                 thisDXCoil.Name);
    5944             : 
    5945          16 :             if (thisDXCoil.ReportCoolingCoilCrankcasePower) {
    5946          32 :                 SetupOutputVariable(state,
    5947             :                                     "Cooling Coil Crankcase Heater Electricity Rate",
    5948             :                                     Constant::Units::W,
    5949          16 :                                     thisDXCoil.CrankcaseHeaterPower,
    5950             :                                     OutputProcessor::TimeStepType::System,
    5951             :                                     OutputProcessor::StoreType::Average,
    5952          16 :                                     thisDXCoil.Name);
    5953          32 :                 SetupOutputVariable(state,
    5954             :                                     "Cooling Coil Crankcase Heater Electricity Energy",
    5955             :                                     Constant::Units::J,
    5956          16 :                                     thisDXCoil.CrankcaseHeaterConsumption,
    5957             :                                     OutputProcessor::TimeStepType::System,
    5958             :                                     OutputProcessor::StoreType::Sum,
    5959          16 :                                     thisDXCoil.Name,
    5960             :                                     Constant::eResource::Electricity,
    5961             :                                     OutputProcessor::Group::Plant,
    5962             :                                     OutputProcessor::EndUseCat::WaterSystem); // DHW
    5963             :             }
    5964             : 
    5965             :             // new report variables for a HP water heater DX coil
    5966          32 :             SetupOutputVariable(state,
    5967             :                                 "Cooling Coil Total Water Heating Rate",
    5968             :                                 Constant::Units::W,
    5969          16 :                                 thisDXCoil.TotalHeatingEnergyRate,
    5970             :                                 OutputProcessor::TimeStepType::System,
    5971             :                                 OutputProcessor::StoreType::Average,
    5972          16 :                                 thisDXCoil.Name);
    5973          32 :             SetupOutputVariable(state,
    5974             :                                 "Cooling Coil Total Water Heating Energy",
    5975             :                                 Constant::Units::J,
    5976          16 :                                 thisDXCoil.TotalHeatingEnergy,
    5977             :                                 OutputProcessor::TimeStepType::System,
    5978             :                                 OutputProcessor::StoreType::Sum,
    5979          16 :                                 thisDXCoil.Name); //, &
    5980             :             //                           ResourceTypeKey='ENERGYTRANSFER',EndUseKey='HEATING',GroupKey='Plant')
    5981          32 :             SetupOutputVariable(state,
    5982             :                                 "Cooling Coil Water Heating Electricity Rate",
    5983             :                                 Constant::Units::W,
    5984          16 :                                 thisDXCoil.ElecWaterHeatingPower,
    5985             :                                 OutputProcessor::TimeStepType::System,
    5986             :                                 OutputProcessor::StoreType::Average,
    5987          16 :                                 thisDXCoil.Name);
    5988          32 :             SetupOutputVariable(state,
    5989             :                                 "Cooling Coil Water Heating Electricity Energy",
    5990             :                                 Constant::Units::J,
    5991          16 :                                 thisDXCoil.ElecWaterHeatingConsumption,
    5992             :                                 OutputProcessor::TimeStepType::System,
    5993             :                                 OutputProcessor::StoreType::Sum,
    5994          16 :                                 thisDXCoil.Name,
    5995             :                                 Constant::eResource::Electricity,
    5996             :                                 OutputProcessor::Group::Plant,
    5997             :                                 OutputProcessor::EndUseCat::WaterSystem); // DHW
    5998             :         }
    5999             : 
    6000         195 :         else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedCooling) {
    6001             :             // Setup Report Variables for Cooling Equipment:
    6002             :             // CurrentModuleObject='Coil:Cooling:DX:MultiSpeed'
    6003          98 :             SetupOutputVariable(state,
    6004             :                                 "Cooling Coil Total Cooling Rate",
    6005             :                                 Constant::Units::W,
    6006          49 :                                 thisDXCoil.TotalCoolingEnergyRate,
    6007             :                                 OutputProcessor::TimeStepType::System,
    6008             :                                 OutputProcessor::StoreType::Average,
    6009          49 :                                 thisDXCoil.Name);
    6010          98 :             SetupOutputVariable(state,
    6011             :                                 "Cooling Coil Total Cooling Energy",
    6012             :                                 Constant::Units::J,
    6013          49 :                                 thisDXCoil.TotalCoolingEnergy,
    6014             :                                 OutputProcessor::TimeStepType::System,
    6015             :                                 OutputProcessor::StoreType::Sum,
    6016          49 :                                 thisDXCoil.Name,
    6017             :                                 Constant::eResource::EnergyTransfer,
    6018             :                                 OutputProcessor::Group::HVAC,
    6019             :                                 OutputProcessor::EndUseCat::CoolingCoils);
    6020          98 :             SetupOutputVariable(state,
    6021             :                                 "Cooling Coil Sensible Cooling Rate",
    6022             :                                 Constant::Units::W,
    6023          49 :                                 thisDXCoil.SensCoolingEnergyRate,
    6024             :                                 OutputProcessor::TimeStepType::System,
    6025             :                                 OutputProcessor::StoreType::Average,
    6026          49 :                                 thisDXCoil.Name);
    6027          98 :             SetupOutputVariable(state,
    6028             :                                 "Cooling Coil Sensible Cooling Energy",
    6029             :                                 Constant::Units::J,
    6030          49 :                                 thisDXCoil.SensCoolingEnergy,
    6031             :                                 OutputProcessor::TimeStepType::System,
    6032             :                                 OutputProcessor::StoreType::Sum,
    6033          49 :                                 thisDXCoil.Name);
    6034          98 :             SetupOutputVariable(state,
    6035             :                                 "Cooling Coil Latent Cooling Rate",
    6036             :                                 Constant::Units::W,
    6037          49 :                                 thisDXCoil.LatCoolingEnergyRate,
    6038             :                                 OutputProcessor::TimeStepType::System,
    6039             :                                 OutputProcessor::StoreType::Average,
    6040          49 :                                 thisDXCoil.Name);
    6041          98 :             SetupOutputVariable(state,
    6042             :                                 "Cooling Coil Latent Cooling Energy",
    6043             :                                 Constant::Units::J,
    6044          49 :                                 thisDXCoil.LatCoolingEnergy,
    6045             :                                 OutputProcessor::TimeStepType::System,
    6046             :                                 OutputProcessor::StoreType::Sum,
    6047          49 :                                 thisDXCoil.Name);
    6048          98 :             SetupOutputVariable(state,
    6049             :                                 "Cooling Coil Electricity Rate",
    6050             :                                 Constant::Units::W,
    6051          49 :                                 thisDXCoil.ElecCoolingPower,
    6052             :                                 OutputProcessor::TimeStepType::System,
    6053             :                                 OutputProcessor::StoreType::Average,
    6054          49 :                                 thisDXCoil.Name);
    6055          98 :             SetupOutputVariable(state,
    6056             :                                 "Cooling Coil Electricity Energy",
    6057             :                                 Constant::Units::J,
    6058          49 :                                 thisDXCoil.ElecCoolingConsumption,
    6059             :                                 OutputProcessor::TimeStepType::System,
    6060             :                                 OutputProcessor::StoreType::Sum,
    6061          49 :                                 thisDXCoil.Name,
    6062             :                                 Constant::eResource::Electricity,
    6063             :                                 OutputProcessor::Group::HVAC,
    6064             :                                 OutputProcessor::EndUseCat::Cooling);
    6065             : 
    6066          49 :             if (thisDXCoil.FuelType != Constant::eFuel::Electricity) {
    6067           6 :                 std::string_view sFuelType = Constant::eFuelNames[static_cast<int>(thisDXCoil.FuelType)];
    6068          18 :                 SetupOutputVariable(state,
    6069          12 :                                     format("Cooling Coil {} Rate", sFuelType),
    6070             :                                     Constant::Units::W,
    6071           6 :                                     thisDXCoil.FuelUsed,
    6072             :                                     OutputProcessor::TimeStepType::System,
    6073             :                                     OutputProcessor::StoreType::Average,
    6074           6 :                                     thisDXCoil.Name);
    6075          18 :                 SetupOutputVariable(state,
    6076          12 :                                     format("Cooling Coil {} Energy", sFuelType),
    6077             :                                     Constant::Units::J,
    6078           6 :                                     thisDXCoil.FuelConsumed,
    6079             :                                     OutputProcessor::TimeStepType::System,
    6080             :                                     OutputProcessor::StoreType::Sum,
    6081           6 :                                     thisDXCoil.Name,
    6082           6 :                                     Constant::eFuel2eResource[(int)thisDXCoil.FuelType],
    6083             :                                     OutputProcessor::Group::HVAC,
    6084             :                                     OutputProcessor::EndUseCat::Cooling);
    6085             :             }
    6086             : 
    6087          98 :             SetupOutputVariable(state,
    6088             :                                 "Cooling Coil Runtime Fraction",
    6089             :                                 Constant::Units::None,
    6090          49 :                                 thisDXCoil.CoolingCoilRuntimeFraction,
    6091             :                                 OutputProcessor::TimeStepType::System,
    6092             :                                 OutputProcessor::StoreType::Average,
    6093          49 :                                 thisDXCoil.Name);
    6094             : 
    6095          49 :             if (thisDXCoil.ReportEvapCondVars) {
    6096           0 :                 SetupOutputVariable(state,
    6097             :                                     "Cooling Coil Condenser Inlet Temperature",
    6098             :                                     Constant::Units::C,
    6099           0 :                                     thisDXCoil.CondInletTemp,
    6100             :                                     OutputProcessor::TimeStepType::System,
    6101             :                                     OutputProcessor::StoreType::Average,
    6102           0 :                                     thisDXCoil.Name);
    6103           0 :                 SetupOutputVariable(state,
    6104             :                                     "Cooling Coil Evaporative Condenser Water Volume",
    6105             :                                     Constant::Units::m3,
    6106           0 :                                     thisDXCoil.EvapWaterConsump,
    6107             :                                     OutputProcessor::TimeStepType::System,
    6108             :                                     OutputProcessor::StoreType::Sum,
    6109           0 :                                     thisDXCoil.Name,
    6110             :                                     Constant::eResource::Water,
    6111             :                                     OutputProcessor::Group::HVAC,
    6112             :                                     OutputProcessor::EndUseCat::Cooling);
    6113           0 :                 SetupOutputVariable(state,
    6114             :                                     "Cooling Coil Evaporative Condenser Mains Supply Water Volume",
    6115             :                                     Constant::Units::m3,
    6116           0 :                                     thisDXCoil.EvapWaterConsump,
    6117             :                                     OutputProcessor::TimeStepType::System,
    6118             :                                     OutputProcessor::StoreType::Sum,
    6119           0 :                                     thisDXCoil.Name,
    6120             :                                     Constant::eResource::MainsWater,
    6121             :                                     OutputProcessor::Group::HVAC,
    6122             :                                     OutputProcessor::EndUseCat::Cooling);
    6123           0 :                 SetupOutputVariable(state,
    6124             :                                     "Cooling Coil Evaporative Condenser Pump Electricity Rate",
    6125             :                                     Constant::Units::W,
    6126           0 :                                     thisDXCoil.EvapCondPumpElecPower,
    6127             :                                     OutputProcessor::TimeStepType::System,
    6128             :                                     OutputProcessor::StoreType::Average,
    6129           0 :                                     thisDXCoil.Name);
    6130           0 :                 SetupOutputVariable(state,
    6131             :                                     "Cooling Coil Evaporative Condenser Pump Electricity Energy",
    6132             :                                     Constant::Units::J,
    6133           0 :                                     thisDXCoil.EvapCondPumpElecConsumption,
    6134             :                                     OutputProcessor::TimeStepType::System,
    6135             :                                     OutputProcessor::StoreType::Sum,
    6136           0 :                                     thisDXCoil.Name,
    6137             :                                     Constant::eResource::Electricity,
    6138             :                                     OutputProcessor::Group::HVAC,
    6139             :                                     OutputProcessor::EndUseCat::Cooling);
    6140           0 :                 if (thisDXCoil.BasinHeaterPowerFTempDiff > 0.0) {
    6141           0 :                     SetupOutputVariable(state,
    6142             :                                         "Cooling Coil Basin Heater Electricity Rate",
    6143             :                                         Constant::Units::W,
    6144           0 :                                         thisDXCoil.BasinHeaterPower,
    6145             :                                         OutputProcessor::TimeStepType::System,
    6146             :                                         OutputProcessor::StoreType::Average,
    6147           0 :                                         thisDXCoil.Name);
    6148           0 :                     SetupOutputVariable(state,
    6149             :                                         "Cooling Coil Basin Heater Electricity Energy",
    6150             :                                         Constant::Units::J,
    6151           0 :                                         thisDXCoil.BasinHeaterConsumption,
    6152             :                                         OutputProcessor::TimeStepType::System,
    6153             :                                         OutputProcessor::StoreType::Sum,
    6154           0 :                                         thisDXCoil.Name,
    6155             :                                         Constant::eResource::Electricity,
    6156             :                                         OutputProcessor::Group::HVAC,
    6157             :                                         OutputProcessor::EndUseCat::Cooling);
    6158             :                 }
    6159             :             }
    6160          49 :             if (thisDXCoil.IsSecondaryDXCoilInZone) {
    6161           0 :                 SetupOutputVariable(state,
    6162             :                                     "Secondary Coil Heat Rejection Rate",
    6163             :                                     Constant::Units::W,
    6164           0 :                                     thisDXCoil.SecCoilSensibleHeatGainRate,
    6165             :                                     OutputProcessor::TimeStepType::System,
    6166             :                                     OutputProcessor::StoreType::Average,
    6167           0 :                                     thisDXCoil.Name);
    6168             :             }
    6169             : 
    6170             :         }
    6171             : 
    6172         146 :         else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedHeating) {
    6173             :             // Setup Report Variables for Heating Equipment:
    6174             :             // CurrentModuleObject='Coil:Heating:DX:MultiSpeed'
    6175          44 :             SetupOutputVariable(state,
    6176             :                                 "Heating Coil Heating Rate",
    6177             :                                 Constant::Units::W,
    6178          22 :                                 thisDXCoil.TotalHeatingEnergyRate,
    6179             :                                 OutputProcessor::TimeStepType::System,
    6180             :                                 OutputProcessor::StoreType::Average,
    6181          22 :                                 thisDXCoil.Name);
    6182          44 :             SetupOutputVariable(state,
    6183             :                                 "Heating Coil Heating Energy",
    6184             :                                 Constant::Units::J,
    6185          22 :                                 thisDXCoil.TotalHeatingEnergy,
    6186             :                                 OutputProcessor::TimeStepType::System,
    6187             :                                 OutputProcessor::StoreType::Sum,
    6188          22 :                                 thisDXCoil.Name,
    6189             :                                 Constant::eResource::EnergyTransfer,
    6190             :                                 OutputProcessor::Group::HVAC,
    6191             :                                 OutputProcessor::EndUseCat::HeatingCoils);
    6192          44 :             SetupOutputVariable(state,
    6193             :                                 "Heating Coil Electricity Rate",
    6194             :                                 Constant::Units::W,
    6195          22 :                                 thisDXCoil.ElecHeatingPower,
    6196             :                                 OutputProcessor::TimeStepType::System,
    6197             :                                 OutputProcessor::StoreType::Average,
    6198          22 :                                 thisDXCoil.Name);
    6199          44 :             SetupOutputVariable(state,
    6200             :                                 "Heating Coil Electricity Energy",
    6201             :                                 Constant::Units::J,
    6202          22 :                                 thisDXCoil.ElecHeatingConsumption,
    6203             :                                 OutputProcessor::TimeStepType::System,
    6204             :                                 OutputProcessor::StoreType::Sum,
    6205          22 :                                 thisDXCoil.Name,
    6206             :                                 Constant::eResource::Electricity,
    6207             :                                 OutputProcessor::Group::HVAC,
    6208             :                                 OutputProcessor::EndUseCat::Heating);
    6209             : 
    6210          22 :             if (thisDXCoil.FuelType != Constant::eFuel::Electricity) {
    6211           4 :                 std::string_view sFuelType = Constant::eFuelNames[static_cast<int>(thisDXCoil.FuelType)];
    6212          12 :                 SetupOutputVariable(state,
    6213           8 :                                     format("Heating Coil {} Rate", sFuelType),
    6214             :                                     Constant::Units::W,
    6215           4 :                                     thisDXCoil.FuelUsed,
    6216             :                                     OutputProcessor::TimeStepType::System,
    6217             :                                     OutputProcessor::StoreType::Average,
    6218           4 :                                     thisDXCoil.Name);
    6219          12 :                 SetupOutputVariable(state,
    6220           8 :                                     format("Heating Coil {} Energy", sFuelType),
    6221             :                                     Constant::Units::J,
    6222           4 :                                     thisDXCoil.FuelConsumed,
    6223             :                                     OutputProcessor::TimeStepType::System,
    6224             :                                     OutputProcessor::StoreType::Sum,
    6225           4 :                                     thisDXCoil.Name,
    6226           4 :                                     Constant::eFuel2eResource[(int)thisDXCoil.FuelType],
    6227             :                                     OutputProcessor::Group::HVAC,
    6228             :                                     OutputProcessor::EndUseCat::HeatingCoils);
    6229             :             }
    6230             : 
    6231          22 :             if (thisDXCoil.FuelType != Constant::eFuel::Electricity && thisDXCoil.DefrostStrategy == StandardRatings::DefrostStrat::ReverseCycle) {
    6232           4 :                 std::string_view sFuelType = Constant::eFuelNames[static_cast<int>(thisDXCoil.FuelType)];
    6233          12 :                 SetupOutputVariable(state,
    6234           8 :                                     format("Heating Coil Defrost {} Rate", sFuelType),
    6235             :                                     Constant::Units::W,
    6236           4 :                                     thisDXCoil.DefrostPower,
    6237             :                                     OutputProcessor::TimeStepType::System,
    6238             :                                     OutputProcessor::StoreType::Average,
    6239           4 :                                     thisDXCoil.Name);
    6240          12 :                 SetupOutputVariable(state,
    6241           8 :                                     format("Heating Coil Defrost {} Energy", sFuelType),
    6242             :                                     Constant::Units::J,
    6243           4 :                                     thisDXCoil.DefrostConsumption,
    6244             :                                     OutputProcessor::TimeStepType::System,
    6245             :                                     OutputProcessor::StoreType::Sum,
    6246           4 :                                     thisDXCoil.Name,
    6247           4 :                                     Constant::eFuel2eResource[(int)thisDXCoil.FuelType],
    6248             :                                     OutputProcessor::Group::HVAC,
    6249             :                                     OutputProcessor::EndUseCat::Heating);
    6250           4 :             } else {
    6251          36 :                 SetupOutputVariable(state,
    6252             :                                     "Heating Coil Defrost Electricity Rate",
    6253             :                                     Constant::Units::W,
    6254          18 :                                     thisDXCoil.DefrostPower,
    6255             :                                     OutputProcessor::TimeStepType::System,
    6256             :                                     OutputProcessor::StoreType::Average,
    6257          18 :                                     thisDXCoil.Name);
    6258          36 :                 SetupOutputVariable(state,
    6259             :                                     "Heating Coil Defrost Electricity Energy",
    6260             :                                     Constant::Units::J,
    6261          18 :                                     thisDXCoil.DefrostConsumption,
    6262             :                                     OutputProcessor::TimeStepType::System,
    6263             :                                     OutputProcessor::StoreType::Sum,
    6264          18 :                                     thisDXCoil.Name,
    6265             :                                     Constant::eResource::Electricity,
    6266             :                                     OutputProcessor::Group::HVAC,
    6267             :                                     OutputProcessor::EndUseCat::Heating);
    6268             :             }
    6269             : 
    6270          44 :             SetupOutputVariable(state,
    6271             :                                 "Heating Coil Crankcase Heater Electricity Rate",
    6272             :                                 Constant::Units::W,
    6273          22 :                                 thisDXCoil.CrankcaseHeaterPower,
    6274             :                                 OutputProcessor::TimeStepType::System,
    6275             :                                 OutputProcessor::StoreType::Average,
    6276          22 :                                 thisDXCoil.Name);
    6277          44 :             SetupOutputVariable(state,
    6278             :                                 "Heating Coil Crankcase Heater Electricity Energy",
    6279             :                                 Constant::Units::J,
    6280          22 :                                 thisDXCoil.CrankcaseHeaterConsumption,
    6281             :                                 OutputProcessor::TimeStepType::System,
    6282             :                                 OutputProcessor::StoreType::Sum,
    6283          22 :                                 thisDXCoil.Name,
    6284             :                                 Constant::eResource::Electricity,
    6285             :                                 OutputProcessor::Group::HVAC,
    6286             :                                 OutputProcessor::EndUseCat::Heating);
    6287          44 :             SetupOutputVariable(state,
    6288             :                                 "Heating Coil Runtime Fraction",
    6289             :                                 Constant::Units::None,
    6290          22 :                                 thisDXCoil.HeatingCoilRuntimeFraction,
    6291             :                                 OutputProcessor::TimeStepType::System,
    6292             :                                 OutputProcessor::StoreType::Average,
    6293          22 :                                 thisDXCoil.Name);
    6294             : 
    6295          22 :             if (thisDXCoil.IsSecondaryDXCoilInZone) {
    6296           0 :                 SetupOutputVariable(state,
    6297             :                                     "Secondary Coil Total Heat Removal Rate",
    6298             :                                     Constant::Units::W,
    6299           0 :                                     thisDXCoil.SecCoilTotalHeatRemovalRate,
    6300             :                                     OutputProcessor::TimeStepType::System,
    6301             :                                     OutputProcessor::StoreType::Average,
    6302           0 :                                     thisDXCoil.Name);
    6303           0 :                 SetupOutputVariable(state,
    6304             :                                     "Secondary Coil Sensible Heat Removal Rate",
    6305             :                                     Constant::Units::W,
    6306           0 :                                     thisDXCoil.SecCoilSensibleHeatRemovalRate,
    6307             :                                     OutputProcessor::TimeStepType::System,
    6308             :                                     OutputProcessor::StoreType::Average,
    6309           0 :                                     thisDXCoil.Name);
    6310           0 :                 SetupOutputVariable(state,
    6311             :                                     "Secondary Coil Latent Heat Removal Rate",
    6312             :                                     Constant::Units::W,
    6313           0 :                                     thisDXCoil.SecCoilLatentHeatRemovalRate,
    6314             :                                     OutputProcessor::TimeStepType::System,
    6315             :                                     OutputProcessor::StoreType::Average,
    6316           0 :                                     thisDXCoil.Name);
    6317           0 :                 SetupOutputVariable(state,
    6318             :                                     "Secondary Coil Sensible Heat Ratio",
    6319             :                                     Constant::Units::None,
    6320           0 :                                     thisDXCoil.SecCoilSHR,
    6321             :                                     OutputProcessor::TimeStepType::System,
    6322             :                                     OutputProcessor::StoreType::Average,
    6323           0 :                                     thisDXCoil.Name);
    6324             :             }
    6325             :         }
    6326             : 
    6327             :         // VRF cooling coil report variables
    6328         124 :         else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Cooling) {
    6329             :             // Setup Report Variables for Cooling Equipment:
    6330             :             // CurrentModuleObject='Coil:Cooling:DX:VariableRefrigerantFlow
    6331          92 :             SetupOutputVariable(state,
    6332             :                                 "Cooling Coil Total Cooling Rate",
    6333             :                                 Constant::Units::W,
    6334          46 :                                 thisDXCoil.TotalCoolingEnergyRate,
    6335             :                                 OutputProcessor::TimeStepType::System,
    6336             :                                 OutputProcessor::StoreType::Average,
    6337          46 :                                 thisDXCoil.Name);
    6338          92 :             SetupOutputVariable(state,
    6339             :                                 "Cooling Coil Total Cooling Energy",
    6340             :                                 Constant::Units::J,
    6341          46 :                                 thisDXCoil.TotalCoolingEnergy,
    6342             :                                 OutputProcessor::TimeStepType::System,
    6343             :                                 OutputProcessor::StoreType::Sum,
    6344          46 :                                 thisDXCoil.Name,
    6345             :                                 Constant::eResource::EnergyTransfer,
    6346             :                                 OutputProcessor::Group::HVAC,
    6347             :                                 OutputProcessor::EndUseCat::CoolingCoils);
    6348          92 :             SetupOutputVariable(state,
    6349             :                                 "Cooling Coil Sensible Cooling Rate",
    6350             :                                 Constant::Units::W,
    6351          46 :                                 thisDXCoil.SensCoolingEnergyRate,
    6352             :                                 OutputProcessor::TimeStepType::System,
    6353             :                                 OutputProcessor::StoreType::Average,
    6354          46 :                                 thisDXCoil.Name);
    6355          92 :             SetupOutputVariable(state,
    6356             :                                 "Cooling Coil Sensible Cooling Energy",
    6357             :                                 Constant::Units::J,
    6358          46 :                                 thisDXCoil.SensCoolingEnergy,
    6359             :                                 OutputProcessor::TimeStepType::System,
    6360             :                                 OutputProcessor::StoreType::Sum,
    6361          46 :                                 thisDXCoil.Name);
    6362          92 :             SetupOutputVariable(state,
    6363             :                                 "Cooling Coil Latent Cooling Rate",
    6364             :                                 Constant::Units::W,
    6365          46 :                                 thisDXCoil.LatCoolingEnergyRate,
    6366             :                                 OutputProcessor::TimeStepType::System,
    6367             :                                 OutputProcessor::StoreType::Average,
    6368          46 :                                 thisDXCoil.Name);
    6369          92 :             SetupOutputVariable(state,
    6370             :                                 "Cooling Coil Latent Cooling Energy",
    6371             :                                 Constant::Units::J,
    6372          46 :                                 thisDXCoil.LatCoolingEnergy,
    6373             :                                 OutputProcessor::TimeStepType::System,
    6374             :                                 OutputProcessor::StoreType::Sum,
    6375          46 :                                 thisDXCoil.Name);
    6376          92 :             SetupOutputVariable(state,
    6377             :                                 "Cooling Coil Runtime Fraction",
    6378             :                                 Constant::Units::None,
    6379          46 :                                 thisDXCoil.CoolingCoilRuntimeFraction,
    6380             :                                 OutputProcessor::TimeStepType::System,
    6381             :                                 OutputProcessor::StoreType::Average,
    6382          46 :                                 thisDXCoil.Name);
    6383          46 :             if (thisDXCoil.CondensateCollectMode == CondensateCollectAction::ToTank) {
    6384           0 :                 SetupOutputVariable(state,
    6385             :                                     "Cooling Coil Condensate Volume Flow Rate",
    6386             :                                     Constant::Units::m3_s,
    6387           0 :                                     thisDXCoil.CondensateVdot,
    6388             :                                     OutputProcessor::TimeStepType::System,
    6389             :                                     OutputProcessor::StoreType::Average,
    6390           0 :                                     thisDXCoil.Name);
    6391           0 :                 SetupOutputVariable(state,
    6392             :                                     "Cooling Coil Condensate Volume",
    6393             :                                     Constant::Units::m3,
    6394           0 :                                     thisDXCoil.CondensateVol,
    6395             :                                     OutputProcessor::TimeStepType::System,
    6396             :                                     OutputProcessor::StoreType::Sum,
    6397           0 :                                     thisDXCoil.Name,
    6398             :                                     Constant::eResource::OnSiteWater,
    6399             :                                     OutputProcessor::Group::HVAC,
    6400             :                                     OutputProcessor::EndUseCat::Condensate);
    6401             :             }
    6402             :         }
    6403             : 
    6404             :         // VRF heating coil report variables
    6405          78 :         else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Heating) {
    6406             :             // Setup Report Variables for Heating Equipment:
    6407             :             // CurrentModuleObject='Coil:Heating:DX:VariableRefrigerantFlow
    6408          92 :             SetupOutputVariable(state,
    6409             :                                 "Heating Coil Heating Rate",
    6410             :                                 Constant::Units::W,
    6411          46 :                                 thisDXCoil.TotalHeatingEnergyRate,
    6412             :                                 OutputProcessor::TimeStepType::System,
    6413             :                                 OutputProcessor::StoreType::Average,
    6414          46 :                                 thisDXCoil.Name);
    6415          92 :             SetupOutputVariable(state,
    6416             :                                 "Heating Coil Heating Energy",
    6417             :                                 Constant::Units::J,
    6418          46 :                                 thisDXCoil.TotalHeatingEnergy,
    6419             :                                 OutputProcessor::TimeStepType::System,
    6420             :                                 OutputProcessor::StoreType::Sum,
    6421          46 :                                 thisDXCoil.Name,
    6422             :                                 Constant::eResource::EnergyTransfer,
    6423             :                                 OutputProcessor::Group::HVAC,
    6424             :                                 OutputProcessor::EndUseCat::HeatingCoils);
    6425          92 :             SetupOutputVariable(state,
    6426             :                                 "Heating Coil Runtime Fraction",
    6427             :                                 Constant::Units::None,
    6428          46 :                                 thisDXCoil.HeatingCoilRuntimeFraction,
    6429             :                                 OutputProcessor::TimeStepType::System,
    6430             :                                 OutputProcessor::StoreType::Average,
    6431          46 :                                 thisDXCoil.Name);
    6432             :         }
    6433             : 
    6434             :         // VRF cooling coil for FluidTCtrl, report variables
    6435          32 :         else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Cooling) {
    6436             :             // Setup Report Variables for Cooling Equipment:
    6437             :             // CurrentModuleObject='Coil:Cooling:DX:VariableRefrigerantFlow:FluidTemperatureControl
    6438          32 :             SetupOutputVariable(state,
    6439             :                                 "Cooling Coil Total Cooling Rate",
    6440             :                                 Constant::Units::W,
    6441          16 :                                 thisDXCoil.TotalCoolingEnergyRate,
    6442             :                                 OutputProcessor::TimeStepType::System,
    6443             :                                 OutputProcessor::StoreType::Average,
    6444          16 :                                 thisDXCoil.Name);
    6445          32 :             SetupOutputVariable(state,
    6446             :                                 "Cooling Coil Total Cooling Energy",
    6447             :                                 Constant::Units::J,
    6448          16 :                                 thisDXCoil.TotalCoolingEnergy,
    6449             :                                 OutputProcessor::TimeStepType::System,
    6450             :                                 OutputProcessor::StoreType::Sum,
    6451          16 :                                 thisDXCoil.Name,
    6452             :                                 Constant::eResource::EnergyTransfer,
    6453             :                                 OutputProcessor::Group::HVAC,
    6454             :                                 OutputProcessor::EndUseCat::CoolingCoils);
    6455          32 :             SetupOutputVariable(state,
    6456             :                                 "Cooling Coil Sensible Cooling Rate",
    6457             :                                 Constant::Units::W,
    6458          16 :                                 thisDXCoil.SensCoolingEnergyRate,
    6459             :                                 OutputProcessor::TimeStepType::System,
    6460             :                                 OutputProcessor::StoreType::Average,
    6461          16 :                                 thisDXCoil.Name);
    6462          32 :             SetupOutputVariable(state,
    6463             :                                 "Cooling Coil Sensible Cooling Energy",
    6464             :                                 Constant::Units::J,
    6465          16 :                                 thisDXCoil.SensCoolingEnergy,
    6466             :                                 OutputProcessor::TimeStepType::System,
    6467             :                                 OutputProcessor::StoreType::Sum,
    6468          16 :                                 thisDXCoil.Name);
    6469          32 :             SetupOutputVariable(state,
    6470             :                                 "Cooling Coil Latent Cooling Rate",
    6471             :                                 Constant::Units::W,
    6472          16 :                                 thisDXCoil.LatCoolingEnergyRate,
    6473             :                                 OutputProcessor::TimeStepType::System,
    6474             :                                 OutputProcessor::StoreType::Average,
    6475          16 :                                 thisDXCoil.Name);
    6476          32 :             SetupOutputVariable(state,
    6477             :                                 "Cooling Coil Latent Cooling Energy",
    6478             :                                 Constant::Units::J,
    6479          16 :                                 thisDXCoil.LatCoolingEnergy,
    6480             :                                 OutputProcessor::TimeStepType::System,
    6481             :                                 OutputProcessor::StoreType::Sum,
    6482          16 :                                 thisDXCoil.Name);
    6483          32 :             SetupOutputVariable(state,
    6484             :                                 "Cooling Coil Runtime Fraction",
    6485             :                                 Constant::Units::None,
    6486          16 :                                 thisDXCoil.CoolingCoilRuntimeFraction,
    6487             :                                 OutputProcessor::TimeStepType::System,
    6488             :                                 OutputProcessor::StoreType::Average,
    6489          16 :                                 thisDXCoil.Name);
    6490             :             // Followings for VRF_FluidTCtrl Only
    6491          32 :             SetupOutputVariable(state,
    6492             :                                 "Cooling Coil VRF Evaporating Temperature",
    6493             :                                 Constant::Units::C,
    6494          16 :                                 thisDXCoil.EvaporatingTemp,
    6495             :                                 OutputProcessor::TimeStepType::System,
    6496             :                                 OutputProcessor::StoreType::Average,
    6497          16 :                                 thisDXCoil.Name);
    6498          32 :             SetupOutputVariable(state,
    6499             :                                 "Cooling Coil VRF Super Heating Degrees",
    6500             :                                 Constant::Units::C,
    6501          16 :                                 thisDXCoil.ActualSH,
    6502             :                                 OutputProcessor::TimeStepType::System,
    6503             :                                 OutputProcessor::StoreType::Average,
    6504          16 :                                 thisDXCoil.Name);
    6505             : 
    6506          16 :             if (thisDXCoil.CondensateCollectMode == CondensateCollectAction::ToTank) {
    6507           0 :                 SetupOutputVariable(state,
    6508             :                                     "Cooling Coil Condensate Volume Flow Rate",
    6509             :                                     Constant::Units::m3_s,
    6510           0 :                                     thisDXCoil.CondensateVdot,
    6511             :                                     OutputProcessor::TimeStepType::System,
    6512             :                                     OutputProcessor::StoreType::Average,
    6513           0 :                                     thisDXCoil.Name);
    6514           0 :                 SetupOutputVariable(state,
    6515             :                                     "Cooling Coil Condensate Volume",
    6516             :                                     Constant::Units::m3,
    6517           0 :                                     thisDXCoil.CondensateVol,
    6518             :                                     OutputProcessor::TimeStepType::System,
    6519             :                                     OutputProcessor::StoreType::Sum,
    6520           0 :                                     thisDXCoil.Name,
    6521             :                                     Constant::eResource::OnSiteWater,
    6522             :                                     OutputProcessor::Group::HVAC,
    6523             :                                     OutputProcessor::EndUseCat::Condensate);
    6524             :             }
    6525             :         }
    6526             : 
    6527             :         // VRF heating coil for FluidTCtrl, report variables
    6528          16 :         else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Heating) {
    6529             :             // Setup Report Variables for Heating Equipment:
    6530             :             // CurrentModuleObject='Coil:Heating:DX:VariableRefrigerantFlow:FluidTemperatureControl
    6531          32 :             SetupOutputVariable(state,
    6532             :                                 "Heating Coil Heating Rate",
    6533             :                                 Constant::Units::W,
    6534          16 :                                 thisDXCoil.TotalHeatingEnergyRate,
    6535             :                                 OutputProcessor::TimeStepType::System,
    6536             :                                 OutputProcessor::StoreType::Average,
    6537          16 :                                 thisDXCoil.Name);
    6538          32 :             SetupOutputVariable(state,
    6539             :                                 "Heating Coil Heating Energy",
    6540             :                                 Constant::Units::J,
    6541          16 :                                 thisDXCoil.TotalHeatingEnergy,
    6542             :                                 OutputProcessor::TimeStepType::System,
    6543             :                                 OutputProcessor::StoreType::Sum,
    6544          16 :                                 thisDXCoil.Name,
    6545             :                                 Constant::eResource::EnergyTransfer,
    6546             :                                 OutputProcessor::Group::HVAC,
    6547             :                                 OutputProcessor::EndUseCat::HeatingCoils);
    6548          32 :             SetupOutputVariable(state,
    6549             :                                 "Heating Coil Runtime Fraction",
    6550             :                                 Constant::Units::None,
    6551          16 :                                 thisDXCoil.HeatingCoilRuntimeFraction,
    6552             :                                 OutputProcessor::TimeStepType::System,
    6553             :                                 OutputProcessor::StoreType::Average,
    6554          16 :                                 thisDXCoil.Name);
    6555             :             // Followings for VRF_FluidTCtrl Only
    6556          32 :             SetupOutputVariable(state,
    6557             :                                 "Heating Coil VRF Condensing Temperature",
    6558             :                                 Constant::Units::C,
    6559          16 :                                 thisDXCoil.CondensingTemp,
    6560             :                                 OutputProcessor::TimeStepType::System,
    6561             :                                 OutputProcessor::StoreType::Average,
    6562          16 :                                 thisDXCoil.Name);
    6563          32 :             SetupOutputVariable(state,
    6564             :                                 "Heating Coil VRF Subcooling Degrees",
    6565             :                                 Constant::Units::C,
    6566          16 :                                 thisDXCoil.ActualSC,
    6567             :                                 OutputProcessor::TimeStepType::System,
    6568             :                                 OutputProcessor::StoreType::Average,
    6569          16 :                                 thisDXCoil.Name);
    6570             :         }
    6571             :     }
    6572             : 
    6573         247 :     if (state.dataGlobal->AnyEnergyManagementSystemInModel) {
    6574             :         // setup EMS sizing actuators for single speed DX
    6575         183 :         for (DXCoilNum = 1; DXCoilNum <= state.dataDXCoils->NumDoe2DXCoils; ++DXCoilNum) {
    6576             : 
    6577         144 :             auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    6578             : 
    6579         144 :             SetupEMSActuator(state,
    6580             :                              "Coil:Cooling:DX:SingleSpeed",
    6581             :                              thisDXCoil.Name,
    6582             :                              "Autosized Rated Air Flow Rate",
    6583             :                              "[m3/s]",
    6584             :                              thisDXCoil.RatedAirVolFlowRateEMSOverrideON(1),
    6585         144 :                              thisDXCoil.RatedAirVolFlowRateEMSOverrideValue(1));
    6586             : 
    6587         144 :             SetupEMSActuator(state,
    6588             :                              "Coil:Cooling:DX:SingleSpeed",
    6589             :                              thisDXCoil.Name,
    6590             :                              "Autosized Rated Sensible Heat Ratio",
    6591             :                              "[W/W]",
    6592             :                              thisDXCoil.RatedSHREMSOverrideOn(1),
    6593         144 :                              thisDXCoil.RatedSHREMSOverrideValue(1));
    6594             : 
    6595         144 :             SetupEMSActuator(state,
    6596             :                              "Coil:Cooling:DX:SingleSpeed",
    6597             :                              thisDXCoil.Name,
    6598             :                              "Autosized Rated Total Cooling Capacity",
    6599             :                              "[W]",
    6600             :                              thisDXCoil.RatedTotCapEMSOverrideOn(1),
    6601         144 :                              thisDXCoil.RatedTotCapEMSOverrideValue(1));
    6602             :         }
    6603             :     }
    6604         247 :     Alphas.deallocate();
    6605         247 :     cAlphaFields.deallocate();
    6606         247 :     cNumericFields.deallocate();
    6607         247 :     Numbers.deallocate();
    6608         247 :     lAlphaBlanks.deallocate();
    6609         247 :     lNumericBlanks.deallocate();
    6610             : 
    6611         247 :     Alphas2.deallocate();
    6612         247 :     cAlphaFields2.deallocate();
    6613         247 :     cNumericFields2.deallocate();
    6614         247 :     Numbers2.deallocate();
    6615         247 :     lAlphaBlanks2.deallocate();
    6616         247 :     lNumericBlanks2.deallocate();
    6617             :     bool anyEMSRan;
    6618         247 :     ManageEMS(state, EMSManager::EMSCallFrom::ComponentGetInput, anyEMSRan, ObjexxFCL::Optional_int_const());
    6619         247 : }
    6620             : 
    6621    63535486 : void InitDXCoil(EnergyPlusData &state, int const DXCoilNum) // number of the current DX coil unit being simulated
    6622             : {
    6623             : 
    6624             :     // SUBROUTINE INFORMATION:
    6625             :     //       AUTHOR         Fred Buhl
    6626             :     //       DATE WRITTEN   May 2000
    6627             :     //                      Feb 2005, M. J. Witte, GARD Analytics, Inc. Add new coil type COIL:DX:MultiMode:CoolingEmpirical:
    6628             :     //                      Jul 2005, R. Raustad, FSEC. Add new coil type COIL:DX:HEATPUMPWATERHEATER
    6629             :     //                      Jun 2007, L. Gu, FSEC. Add new coil type COIL:DX:MULTISPEED:COOLING and HEATING
    6630             :     //                      Aug 2015, R. Zhang, LBNL. Add new coil types for VRF_FluidTCtrl
    6631             : 
    6632             :     // PURPOSE OF THIS SUBROUTINE:
    6633             :     // This subroutine is for initializations of DX Coil Components.
    6634             : 
    6635             :     // METHODOLOGY EMPLOYED:
    6636             :     // Uses the status flags to trigger initializations.
    6637             : 
    6638             :     // SUBROUTINE PARAMETER DEFINITIONS:
    6639    63535486 :     constexpr Real64 SmallDifferenceTest(0.00000001);
    6640             :     static constexpr std::string_view RoutineName("InitDXCoil");
    6641             : 
    6642             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
    6643             :     Real64 RatedHeatPumpIndoorAirTemp; // Indoor dry-bulb temperature to heat pump evaporator at rated conditions [C]
    6644             :     Real64 RatedHeatPumpIndoorHumRat;  // Inlet humidity ratio to heat pump evaporator at rated conditions [kgWater/kgDryAir]
    6645             :     Real64 RatedVolFlowPerRatedTotCap; // Rated Air Volume Flow Rate divided by Rated Total Capacity [m3/s-W)
    6646             :     Real64 HPInletAirHumRat;           // Rated inlet air humidity ratio for heat pump water heater [kgWater/kgDryAir]
    6647    63535486 :     bool ErrorsFound(false);           // TRUE when errors found
    6648             :     int CapacityStageNum;              // Loop index for 1,Number of capacity stages
    6649             :     int DehumidModeNum;                // Loop index for 1,Number of enhanced dehumidification modes
    6650             :     int Mode;                          // Performance mode for MultiMode DX coil; Always 1 for other coil types
    6651             :     int DXCoilNumTemp;                 // Counter for crankcase heater report variable DO loop
    6652             :     int AirInletNode;                  // Air inlet node number
    6653             :     int SpeedNum;                      // Speed number for multispeed coils
    6654             : 
    6655    63535486 :     if (state.dataDXCoils->MyOneTimeFlag) {
    6656             :         // initialize the environment and sizing flags
    6657         243 :         state.dataDXCoils->MyEnvrnFlag.dimension(state.dataDXCoils->NumDXCoils, true);
    6658         243 :         state.dataDXCoils->MySizeFlag.dimension(state.dataDXCoils->NumDXCoils, true);
    6659         243 :         state.dataDXCoils->MyOneTimeFlag = false;
    6660             :     }
    6661             : 
    6662    63535486 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    6663             : 
    6664             :     // if "ISHundredPercentDOASDXCoil" =.TRUE., then set coil as 100% DOAS dx coil
    6665    63535486 :     state.dataHVACGlobal->DXCT = (thisDXCoil.ISHundredPercentDOASDXCoil) ? HVAC::DXCoilType::DOAS : HVAC::DXCoilType::Regular;
    6666             : 
    6667   190183833 :     if ((thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    6668    64167330 :          thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) &&
    6669      631844 :         state.dataDXCoils->MyEnvrnFlag(DXCoilNum)) {
    6670             : 
    6671          16 :         SizeDXCoil(state, DXCoilNum);
    6672             : 
    6673          16 :         RatedVolFlowPerRatedTotCap = thisDXCoil.RatedAirVolFlowRate(1) / thisDXCoil.RatedTotCap2;
    6674          32 :         if (((HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT] - RatedVolFlowPerRatedTotCap) > SmallDifferenceTest) ||
    6675          16 :             ((RatedVolFlowPerRatedTotCap - HVAC::MaxHeatVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) > SmallDifferenceTest)) {
    6676           4 :             ShowWarningError(state,
    6677           4 :                              format("{} \"{}\": Rated air volume flow rate per watt of rated total water heating capacity is out of range",
    6678           2 :                                     thisDXCoil.DXCoilType,
    6679           2 :                                     thisDXCoil.Name));
    6680           4 :             ShowContinueError(state,
    6681           4 :                               format("Min Rated Vol Flow Per Watt=[{:.3T}], Rated Vol Flow Per Watt=[{:.3T}], Max Rated Vol Flow Per "
    6682             :                                      "Watt=[{:.3T}]. See Input-Output Reference Manual for valid range.",
    6683           2 :                                      HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
    6684             :                                      RatedVolFlowPerRatedTotCap,
    6685           2 :                                      HVAC::MaxHeatVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]));
    6686             :         }
    6687             :         HPInletAirHumRat =
    6688          16 :             PsyWFnTdbTwbPb(state, thisDXCoil.RatedInletDBTemp, thisDXCoil.RatedInletWBTemp, DataEnvironment::StdPressureSeaLevel, RoutineName);
    6689          16 :         state.dataHVACGlobal->HPWHInletDBTemp = thisDXCoil.RatedInletDBTemp;
    6690          16 :         state.dataHVACGlobal->HPWHInletWBTemp = thisDXCoil.RatedInletWBTemp;
    6691          32 :         thisDXCoil.RatedAirMassFlowRate(1) =
    6692          16 :             thisDXCoil.RatedAirVolFlowRate(1) *
    6693          16 :             PsyRhoAirFnPbTdbW(state, state.dataEnvrn->StdBaroPress, thisDXCoil.RatedInletDBTemp, HPInletAirHumRat, RoutineName);
    6694             :         //   get rated coil bypass factor excluding fan heat
    6695             : 
    6696             :         //   call CalcHPWHDXCoil to determine DXCoil%RatedTotCap(1) for rated CBF calculation below
    6697          16 :         CalcHPWHDXCoil(state, DXCoilNum, 1.0);
    6698          16 :         if (state.dataDXCoils->MySizeFlag(DXCoilNum)) {
    6699          16 :             SizeDXCoil(state, DXCoilNum);
    6700          16 :             state.dataDXCoils->MySizeFlag(DXCoilNum) = false;
    6701             :         }
    6702             : 
    6703          16 :         thisDXCoil.RatedCBF(1) = CalcCBF(state,
    6704          16 :                                          thisDXCoil.DXCoilType,
    6705          16 :                                          thisDXCoil.Name,
    6706             :                                          thisDXCoil.RatedInletDBTemp,
    6707             :                                          HPInletAirHumRat,
    6708          16 :                                          thisDXCoil.RatedTotCap(1),
    6709          16 :                                          thisDXCoil.RatedAirVolFlowRate(1),
    6710          16 :                                          thisDXCoil.RatedSHR(1),
    6711             :                                          true);
    6712          16 :         state.dataDXCoils->MyEnvrnFlag(DXCoilNum) = false;
    6713             :     }
    6714             : 
    6715    77262765 :     if ((thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedCooling || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedHeating) &&
    6716    13727279 :         state.dataDXCoils->MyEnvrnFlag(DXCoilNum)) {
    6717          71 :         if (thisDXCoil.FuelType != Constant::eFuel::Electricity) {
    6718          10 :             if (thisDXCoil.MSHPHeatRecActive) {
    6719           0 :                 for (SpeedNum = 1; SpeedNum <= thisDXCoil.NumOfSpeeds; ++SpeedNum) {
    6720           0 :                     if (thisDXCoil.MSWasteHeat(SpeedNum) == 0) {
    6721           0 :                         ShowWarningError(
    6722             :                             state,
    6723           0 :                             format("GetDXCoils:{}. The value of Waste Heat Function of Temperature Curve is assumed to be 1. Simulation continues. ",
    6724           0 :                                    thisDXCoil.Name));
    6725           0 :                         break;
    6726             :                     }
    6727             :                 }
    6728             :             }
    6729             :         }
    6730          71 :         state.dataDXCoils->MyEnvrnFlag(DXCoilNum) = false;
    6731             :     }
    6732             : 
    6733             :     // Find the companion upstream coil (DX cooling coil) that is used with DX heating coils (HP AC units only)
    6734    63535486 :     if (thisDXCoil.FindCompanionUpStreamCoil) {
    6735     3924847 :         if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatingEmpirical || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedHeating) {
    6736     3923968 :             thisDXCoil.CompanionUpstreamDXCoil = GetHPCoolingCoilIndex(state, thisDXCoil.DXCoilType, thisDXCoil.Name, DXCoilNum);
    6737     3923968 :             if (thisDXCoil.CompanionUpstreamDXCoil > 0) {
    6738          74 :                 state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).ReportCoolingCoilCrankcasePower = false;
    6739          74 :                 thisDXCoil.FindCompanionUpStreamCoil = false;
    6740             :                 //       Copy condenser node number from DX cooling coil when used with a companion DX heating coil
    6741         370 :                 for (Mode = 1; Mode <= MaxModes; ++Mode) {
    6742         296 :                     thisDXCoil.CondenserInletNodeNum(Mode) =
    6743         296 :                         state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).CondenserInletNodeNum(Mode);
    6744             :                 }
    6745             :             }
    6746             :         } else {
    6747         879 :             thisDXCoil.FindCompanionUpStreamCoil = false;
    6748             :         }
    6749             :     } // IF(DXCoil(DXCoilNum)%FindCompanionUpStreamCoil)THEN
    6750             : 
    6751             :     // CR7308 - Wait for zone and air loop equipment to be simulated, then print out report variables
    6752    63535486 :     if (state.dataDXCoils->CrankcaseHeaterReportVarFlag) {
    6753        7915 :         if (state.dataAirLoop->AirLoopInputsFilled) {
    6754             :             //     Set report variables for DX cooling coils that will have a crankcase heater (all DX coils not used in a HP AC unit)
    6755        1219 :             for (DXCoilNumTemp = 1; DXCoilNumTemp <= state.dataDXCoils->NumDXCoils; ++DXCoilNumTemp) {
    6756         976 :                 if ((state.dataDXCoils->DXCoil(DXCoilNumTemp).DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl) ||
    6757        1329 :                     (state.dataDXCoils->DXCoil(DXCoilNumTemp).DXCoilType_Num == HVAC::CoilDX_CoolingSingleSpeed) ||
    6758         353 :                     (state.dataDXCoils->DXCoil(DXCoilNumTemp).DXCoilType_Num == HVAC::CoilDX_MultiSpeedCooling)) {
    6759         672 :                     if (state.dataDXCoils->DXCoil(DXCoilNumTemp).ReportCoolingCoilCrankcasePower) {
    6760        1196 :                         SetupOutputVariable(state,
    6761             :                                             "Cooling Coil Crankcase Heater Electricity Rate",
    6762             :                                             Constant::Units::W,
    6763         598 :                                             state.dataDXCoils->DXCoil(DXCoilNumTemp).CrankcaseHeaterPower,
    6764             :                                             OutputProcessor::TimeStepType::System,
    6765             :                                             OutputProcessor::StoreType::Average,
    6766         598 :                                             state.dataDXCoils->DXCoil(DXCoilNumTemp).Name);
    6767        1196 :                         SetupOutputVariable(state,
    6768             :                                             "Cooling Coil Crankcase Heater Electricity Energy",
    6769             :                                             Constant::Units::J,
    6770         598 :                                             state.dataDXCoils->DXCoil(DXCoilNumTemp).CrankcaseHeaterConsumption,
    6771             :                                             OutputProcessor::TimeStepType::System,
    6772             :                                             OutputProcessor::StoreType::Sum,
    6773         598 :                                             state.dataDXCoils->DXCoil(DXCoilNumTemp).Name,
    6774             :                                             Constant::eResource::Electricity,
    6775             :                                             OutputProcessor::Group::HVAC,
    6776             :                                             OutputProcessor::EndUseCat::Cooling);
    6777         598 :                         state.dataDXCoils->DXCoil(DXCoilNumTemp).ReportCoolingCoilCrankcasePower = false;
    6778             :                     }
    6779             :                 }
    6780             :             }
    6781         243 :             state.dataDXCoils->CrankcaseHeaterReportVarFlag = false;
    6782             :         } //(AirLoopInputsFilled)THEN
    6783             :     }     //(CrankcaseHeaterReportVarFlag)THEN
    6784             : 
    6785    63535486 :     if (!state.dataGlobal->SysSizingCalc && state.dataDXCoils->MySizeFlag(DXCoilNum)) {
    6786             :         // for each coil, do the sizing once.
    6787         960 :         SizeDXCoil(state, DXCoilNum);
    6788         960 :         state.dataDXCoils->MySizeFlag(DXCoilNum) = false;
    6789             : 
    6790         960 :         if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingSingleSpeed || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed ||
    6791         281 :             thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Cooling || thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Cooling) {
    6792             : 
    6793         741 :             Mode = 1;
    6794             :             // Check for zero capacity or zero max flow rate
    6795         741 :             if (thisDXCoil.RatedTotCap(Mode) <= 0.0) {
    6796           0 :                 ShowSevereError(state, format("Sizing: {} {} has zero rated total capacity", thisDXCoil.DXCoilType, thisDXCoil.Name));
    6797           0 :                 ErrorsFound = true;
    6798             :             }
    6799         741 :             if (thisDXCoil.RatedAirVolFlowRate(Mode) <= 0.0) {
    6800           0 :                 ShowSevereError(state, format("Sizing: {} {} has zero rated air flow rate", thisDXCoil.DXCoilType, thisDXCoil.Name));
    6801           0 :                 ErrorsFound = true;
    6802             :             }
    6803         741 :             if (ErrorsFound) {
    6804           0 :                 ShowFatalError(state, "Preceding condition causes termination.");
    6805             :             }
    6806             : 
    6807             :             // Check for valid range of (Rated Air Volume Flow Rate / Rated Total Capacity)
    6808         741 :             if (thisDXCoil.DXCoilType_Num !=
    6809             :                 HVAC::CoilVRF_FluidTCtrl_Cooling) { // the VolFlowPerRatedTotCap check is not applicable for VRF-FluidTCtrl coil
    6810         725 :                 RatedVolFlowPerRatedTotCap = thisDXCoil.RatedAirVolFlowRate(Mode) / thisDXCoil.RatedTotCap(Mode);
    6811        1450 :                 if (((HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT] - RatedVolFlowPerRatedTotCap) > SmallDifferenceTest) ||
    6812         725 :                     ((RatedVolFlowPerRatedTotCap - HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) > SmallDifferenceTest)) {
    6813           0 :                     ShowWarningError(state,
    6814           0 :                                      format("Sizing: {} \"{}\": Rated air volume flow rate per watt of rated total cooling capacity is out of range.",
    6815           0 :                                             thisDXCoil.DXCoilType,
    6816           0 :                                             thisDXCoil.Name));
    6817           0 :                     ShowContinueError(state,
    6818           0 :                                       format("Min Rated Vol Flow Per Watt=[{:.3T}], Rated Vol Flow Per Watt=[{:.3T}], Max Rated Vol Flow Per "
    6819             :                                              "Watt=[{:.3T}]. See Input Output Reference Manual for valid range.",
    6820           0 :                                              HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
    6821             :                                              RatedVolFlowPerRatedTotCap,
    6822           0 :                                              HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]));
    6823             :                 }
    6824             :             }
    6825             : 
    6826        1482 :             thisDXCoil.RatedAirMassFlowRate(Mode) =
    6827         741 :                 thisDXCoil.RatedAirVolFlowRate(Mode) *
    6828         741 :                 PsyRhoAirFnPbTdbW(state, state.dataEnvrn->StdBaroPress, RatedInletAirTemp, RatedInletAirHumRat, RoutineName);
    6829             :             // get high speed rated coil bypass factor
    6830         741 :             thisDXCoil.RatedCBF(Mode) = CalcCBF(state,
    6831         741 :                                                 thisDXCoil.DXCoilType,
    6832         741 :                                                 thisDXCoil.Name,
    6833             :                                                 RatedInletAirTemp,
    6834             :                                                 RatedInletAirHumRat,
    6835         741 :                                                 thisDXCoil.RatedTotCap(Mode),
    6836         741 :                                                 thisDXCoil.RatedAirVolFlowRate(Mode),
    6837         741 :                                                 thisDXCoil.RatedSHR(Mode));
    6838             : 
    6839             :             // call coil model with everthing set at rating point
    6840         741 :             thisDXCoil.InletAirMassFlowRate = thisDXCoil.RatedAirMassFlowRate(Mode);
    6841         741 :             thisDXCoil.InletAirMassFlowRateMax = thisDXCoil.RatedAirMassFlowRate(Mode);
    6842         741 :             thisDXCoil.InletAirTemp = RatedInletAirTemp;
    6843             :             Real64 tempInletAirHumRat =
    6844         741 :                 Psychrometrics::PsyWFnTdbTwbPb(state, RatedInletAirTemp, RatedInletWetBulbTemp, DataEnvironment::StdPressureSeaLevel, RoutineName);
    6845             :             // DXCoil( DXCoilNum ).InletAirHumRat = RatedInletAirHumRat; // this seems inconsistent with dry bulb and wetbulb, filed NREL issue
    6846             :             // #5934  Real64 tempInletAirWetBulb = Psychrometrics::PsyTwbFnTdbWPb( RatedInletAirTemp, RatedInletAirHumRat,
    6847             :             // DataEnvironment::StdPressureSeaLevel );
    6848         741 :             thisDXCoil.InletAirHumRat = tempInletAirHumRat;
    6849         741 :             thisDXCoil.InletAirEnthalpy = Psychrometrics::PsyHFnTdbW(RatedInletAirTemp, tempInletAirHumRat);
    6850             : 
    6851             :             // store environment data fill back in after rating point calc is over
    6852         741 :             Real64 holdOutDryBulbTemp = state.dataEnvrn->OutDryBulbTemp;
    6853         741 :             Real64 holdOutHumRat = state.dataEnvrn->OutHumRat;
    6854         741 :             Real64 holdOutWetBulb = state.dataEnvrn->OutWetBulbTemp;
    6855         741 :             Real64 holdOutBaroPress = state.dataEnvrn->OutBaroPress;
    6856         741 :             Real64 ratedOutdoorAirWetBulb = 23.9; // from I/O ref. more precise value?
    6857         741 :             state.dataEnvrn->OutDryBulbTemp = RatedOutdoorAirTemp;
    6858         741 :             state.dataEnvrn->OutWetBulbTemp = ratedOutdoorAirWetBulb;
    6859         741 :             state.dataEnvrn->OutBaroPress = DataEnvironment::StdPressureSeaLevel; // assume rating is for sea level.
    6860        1482 :             state.dataEnvrn->OutHumRat =
    6861         741 :                 Psychrometrics::PsyWFnTdbTwbPb(state, RatedOutdoorAirTemp, ratedOutdoorAirWetBulb, DataEnvironment::StdPressureSeaLevel, RoutineName);
    6862         741 :             if (thisDXCoil.CondenserInletNodeNum(1) > 0) { // set condenser inlet node values
    6863         162 :                 state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).Temp = RatedOutdoorAirTemp;
    6864         162 :                 state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).HumRat = state.dataEnvrn->OutHumRat;
    6865         162 :                 state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).OutAirWetBulb = ratedOutdoorAirWetBulb;
    6866             :             }
    6867             : 
    6868             :             // calculate coil model at rating point
    6869         741 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingSingleSpeed) {
    6870         612 :                 CalcDoe2DXCoil(state, DXCoilNum, HVAC::CompressorOp::On, false, 1.0, HVAC::FanOp::Cycling, _, 1.0);
    6871         129 :             } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed) {
    6872          67 :                 CalcMultiSpeedDXCoil(state, DXCoilNum, 1.0, 1.0);
    6873          62 :             } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Cooling) {
    6874          46 :                 CalcVRFCoolingCoil(state, DXCoilNum, HVAC::CompressorOp::On, false, 1.0, HVAC::FanOp::Cycling, 1.0, _, _, _);
    6875          16 :             } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Cooling) {
    6876          16 :                 CalcVRFCoolingCoil_FluidTCtrl(state, DXCoilNum, HVAC::CompressorOp::On, false, 1.0, HVAC::FanOp::Cycling, 1.0, _, _);
    6877             :             }
    6878             : 
    6879             :             // coil outlets
    6880         741 :             Real64 RatedOutletWetBulb(0.0);
    6881         741 :             RatedOutletWetBulb = Psychrometrics::PsyTwbFnTdbWPb(
    6882             :                 state, thisDXCoil.OutletAirTemp, thisDXCoil.OutletAirHumRat, DataEnvironment::StdPressureSeaLevel, RoutineName);
    6883             : 
    6884         741 :             state.dataRptCoilSelection->coilSelectionReportObj->setRatedCoilConditions(
    6885             :                 state,
    6886         741 :                 thisDXCoil.Name,
    6887         741 :                 thisDXCoil.DXCoilType,
    6888             :                 thisDXCoil.TotalCoolingEnergyRate, // this is the report variable
    6889             :                 thisDXCoil.SensCoolingEnergyRate,  // this is the report variable
    6890             :                 thisDXCoil.InletAirMassFlowRate,
    6891             :                 thisDXCoil.InletAirTemp,
    6892             :                 thisDXCoil.InletAirHumRat,
    6893             :                 RatedInletWetBulbTemp,
    6894             :                 thisDXCoil.OutletAirTemp,
    6895             :                 thisDXCoil.OutletAirHumRat,
    6896             :                 RatedOutletWetBulb,
    6897             :                 RatedOutdoorAirTemp,
    6898             :                 ratedOutdoorAirWetBulb,
    6899         741 :                 thisDXCoil.RatedCBF(Mode),
    6900             :                 -999.0); // coil effectiveness not define for DX
    6901             : 
    6902             :             // now replace the outdoor air conditions set above for one time rating point calc
    6903         741 :             state.dataEnvrn->OutDryBulbTemp = holdOutDryBulbTemp;
    6904         741 :             state.dataEnvrn->OutHumRat = holdOutHumRat;
    6905         741 :             state.dataEnvrn->OutWetBulbTemp = holdOutWetBulb;
    6906         741 :             state.dataEnvrn->OutBaroPress = holdOutBaroPress;
    6907             :         }
    6908             : 
    6909         960 :         if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl) {
    6910          29 :             for (DehumidModeNum = 0; DehumidModeNum <= thisDXCoil.NumDehumidModes; ++DehumidModeNum) {
    6911          53 :                 for (CapacityStageNum = 1; CapacityStageNum <= thisDXCoil.NumCapacityStages; ++CapacityStageNum) {
    6912          35 :                     Mode = DehumidModeNum * 2 + CapacityStageNum;
    6913             :                     // Check for zero capacity or zero max flow rate
    6914          35 :                     if (thisDXCoil.RatedTotCap(Mode) <= 0.0) {
    6915           0 :                         ShowSevereError(state, format("Sizing: {} {} has zero rated total capacity", thisDXCoil.DXCoilType, thisDXCoil.Name));
    6916           0 :                         ShowContinueError(state, format("for CoilPerformance:DX:Cooling mode: {}", thisDXCoil.CoilPerformanceName(Mode)));
    6917           0 :                         ErrorsFound = true;
    6918             :                     }
    6919          35 :                     if (thisDXCoil.RatedAirVolFlowRate(Mode) <= 0.0) {
    6920           0 :                         ShowSevereError(state, format("Sizing: {} {} has zero rated air flow rate", thisDXCoil.DXCoilType, thisDXCoil.Name));
    6921           0 :                         ShowContinueError(state, format("for CoilPerformance:DX:Cooling mode: {}", thisDXCoil.CoilPerformanceName(Mode)));
    6922           0 :                         ErrorsFound = true;
    6923             :                     }
    6924          35 :                     if (ErrorsFound) {
    6925           0 :                         ShowFatalError(state, "Preceding condition causes termination.");
    6926             :                     }
    6927             :                     // Check for valid range of (Rated Air Volume Flow Rate / Rated Total Capacity)
    6928          35 :                     RatedVolFlowPerRatedTotCap = thisDXCoil.RatedAirVolFlowRate(Mode) / thisDXCoil.RatedTotCap(Mode);
    6929          70 :                     if (((HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT] - RatedVolFlowPerRatedTotCap) > SmallDifferenceTest) ||
    6930          35 :                         ((RatedVolFlowPerRatedTotCap - HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) > SmallDifferenceTest)) {
    6931           0 :                         ShowWarningError(
    6932             :                             state,
    6933           0 :                             format("Sizing: {} \"{}\": Rated air volume flow rate per watt of rated total cooling capacity is out of range.",
    6934           0 :                                    thisDXCoil.DXCoilType,
    6935           0 :                                    thisDXCoil.Name));
    6936           0 :                         ShowContinueError(state,
    6937           0 :                                           format("Min Rated Vol Flow Per Watt=[{:.3T}], Rated Vol Flow Per Watt=[{:.3T}], Max Rated Vol Flow Per "
    6938             :                                                  "Watt=[{:.3T}]. See Input Output Reference Manual for valid range.",
    6939           0 :                                                  HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
    6940             :                                                  RatedVolFlowPerRatedTotCap,
    6941           0 :                                                  HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]));
    6942           0 :                         ShowContinueError(state, format("for CoilPerformance:DX:Cooling mode: {}", thisDXCoil.CoilPerformanceName(Mode)));
    6943             :                     }
    6944          70 :                     thisDXCoil.RatedAirMassFlowRate(Mode) =
    6945          35 :                         thisDXCoil.RatedAirVolFlowRate(Mode) *
    6946          35 :                         PsyRhoAirFnPbTdbW(state, state.dataEnvrn->StdBaroPress, RatedInletAirTemp, RatedInletAirHumRat, RoutineName);
    6947             :                     // get rated coil bypass factor
    6948          35 :                     thisDXCoil.RatedCBF(Mode) = CalcCBF(state,
    6949          35 :                                                         thisDXCoil.CoilPerformanceType(Mode),
    6950          35 :                                                         thisDXCoil.CoilPerformanceName(Mode),
    6951             :                                                         RatedInletAirTemp,
    6952             :                                                         RatedInletAirHumRat,
    6953          35 :                                                         thisDXCoil.RatedTotCap(Mode),
    6954          35 :                                                         thisDXCoil.RatedAirVolFlowRate(Mode),
    6955          35 :                                                         thisDXCoil.RatedSHR(Mode));
    6956             :                 } // End capacity stages loop
    6957             :             }     // End dehumidification modes loop
    6958             :         }
    6959             : 
    6960         960 :         if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatingEmpirical || thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Heating ||
    6961         839 :             thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Heating) {
    6962             : 
    6963         137 :             Mode = 1;
    6964         137 :             if (thisDXCoil.RatedTotCap(Mode) <= 0.0) {
    6965           0 :                 ShowSevereError(state, format("Sizing: {} {} has zero rated total capacity", thisDXCoil.DXCoilType, thisDXCoil.Name));
    6966           0 :                 ErrorsFound = true;
    6967             :             }
    6968         137 :             if (thisDXCoil.RatedAirVolFlowRate(Mode) <= 0.0) {
    6969           0 :                 ShowSevereError(state, format("Sizing: {} {} has zero rated air flow rate", thisDXCoil.DXCoilType, thisDXCoil.Name));
    6970           0 :                 ErrorsFound = true;
    6971             :             }
    6972         137 :             if (ErrorsFound) {
    6973           0 :                 ShowFatalError(state, "Preceding condition causes termination.");
    6974             :             }
    6975         137 :             RatedHeatPumpIndoorAirTemp = 21.11;  // 21.11C or 70F
    6976         137 :             RatedHeatPumpIndoorHumRat = 0.00881; // Humidity ratio corresponding to 70F dry bulb/60F wet bulb
    6977         274 :             thisDXCoil.RatedAirMassFlowRate(Mode) =
    6978         137 :                 thisDXCoil.RatedAirVolFlowRate(Mode) *
    6979         137 :                 PsyRhoAirFnPbTdbW(state, state.dataEnvrn->StdBaroPress, RatedHeatPumpIndoorAirTemp, RatedHeatPumpIndoorHumRat, RoutineName);
    6980             : 
    6981             :             // Check for valid range of (Rated Air Volume Flow Rate / Rated Total Capacity)
    6982         137 :             if (thisDXCoil.DXCoilType_Num !=
    6983             :                 HVAC::CoilVRF_FluidTCtrl_Heating) { // the VolFlowPerRatedTotCap check is not applicable for VRF-FluidTCtrl coil
    6984         121 :                 RatedVolFlowPerRatedTotCap = thisDXCoil.RatedAirVolFlowRate(Mode) / thisDXCoil.RatedTotCap(Mode);
    6985         242 :                 if (((HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT] - RatedVolFlowPerRatedTotCap) > SmallDifferenceTest) ||
    6986         121 :                     ((RatedVolFlowPerRatedTotCap - HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) > SmallDifferenceTest)) {
    6987           0 :                     ShowWarningError(state,
    6988           0 :                                      format("Sizing: {} {}: Rated air volume flow rate per watt of rated total heating capacity is out of range.",
    6989           0 :                                             thisDXCoil.DXCoilType,
    6990           0 :                                             thisDXCoil.Name));
    6991           0 :                     ShowContinueError(state,
    6992           0 :                                       format("Min Rated Vol Flow Per Watt=[{:.3T}], Rated Vol Flow Per Watt=[{:.3T}], Max Rated Vol Flow Per "
    6993             :                                              "Watt=[{:.3T}]. See Input-Output Reference Manual for valid range.",
    6994           0 :                                              HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
    6995             :                                              RatedVolFlowPerRatedTotCap,
    6996           0 :                                              HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]));
    6997             :                 }
    6998             :             }
    6999             : 
    7000             :             // call coil model with everthing set at rating point
    7001         137 :             thisDXCoil.InletAirMassFlowRate = thisDXCoil.RatedAirMassFlowRate(Mode);
    7002         137 :             thisDXCoil.InletAirMassFlowRateMax = thisDXCoil.RatedAirMassFlowRate(Mode);
    7003             : 
    7004         137 :             thisDXCoil.InletAirTemp = RatedInletAirTempHeat;
    7005         137 :             Real64 tempInletAirHumRat = Psychrometrics::PsyWFnTdbTwbPb(
    7006             :                 state, RatedInletAirTempHeat, RatedInletWetBulbTempHeat, DataEnvironment::StdPressureSeaLevel, RoutineName);
    7007         137 :             thisDXCoil.InletAirHumRat = tempInletAirHumRat;
    7008         137 :             thisDXCoil.InletAirEnthalpy = Psychrometrics::PsyHFnTdbW(RatedInletAirTempHeat, tempInletAirHumRat);
    7009             : 
    7010             :             // store environment data fill back in after rating point calc is over
    7011         137 :             Real64 holdOutDryBulbTemp = state.dataEnvrn->OutDryBulbTemp;
    7012         137 :             Real64 holdOutHumRat = state.dataEnvrn->OutHumRat;
    7013         137 :             Real64 holdOutWetBulb = state.dataEnvrn->OutWetBulbTemp;
    7014         137 :             Real64 holdOutBaroPress = state.dataEnvrn->OutBaroPress;
    7015             : 
    7016         137 :             state.dataEnvrn->OutDryBulbTemp = RatedOutdoorAirTempHeat;
    7017             : 
    7018         137 :             Real64 ratedOutdoorAirWetBulb = 6.11; // from I/O ref. more precise value?
    7019         137 :             state.dataEnvrn->OutWetBulbTemp = ratedOutdoorAirWetBulb;
    7020         137 :             state.dataEnvrn->OutBaroPress = DataEnvironment::StdPressureSeaLevel; // assume rating is for sea level.
    7021         137 :             state.dataEnvrn->OutHumRat = Psychrometrics::PsyWFnTdbTwbPb(
    7022             :                 state, RatedOutdoorAirTempHeat, ratedOutdoorAirWetBulb, DataEnvironment::StdPressureSeaLevel, RoutineName);
    7023             : 
    7024         137 :             if (thisDXCoil.CondenserInletNodeNum(1) > 0) { // set condenser inlet node values
    7025          61 :                 state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).Temp = RatedOutdoorAirTempHeat;
    7026          61 :                 state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).HumRat = state.dataEnvrn->OutHumRat;
    7027          61 :                 state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).OutAirWetBulb = ratedOutdoorAirWetBulb;
    7028             :             }
    7029             : 
    7030             :             // calculate coil model at rating point
    7031         137 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatingEmpirical) {
    7032          75 :                 CalcDXHeatingCoil(state, DXCoilNum, 1.0, HVAC::FanOp::Cycling, 1.0);
    7033          62 :             } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Heating) {
    7034          46 :                 CalcDXHeatingCoil(state, DXCoilNum, 1.0, HVAC::FanOp::Cycling, _, _);
    7035          16 :             } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Heating) {
    7036          16 :                 CalcVRFHeatingCoil_FluidTCtrl(state, HVAC::CompressorOp::On, DXCoilNum, 1.0, HVAC::FanOp::Cycling, _, _);
    7037             :             }
    7038             :             // coil outlets
    7039         137 :             Real64 RatedOutletWetBulb(0.0);
    7040         137 :             RatedOutletWetBulb = Psychrometrics::PsyTwbFnTdbWPb(
    7041             :                 state, thisDXCoil.OutletAirTemp, thisDXCoil.OutletAirHumRat, DataEnvironment::StdPressureSeaLevel, RoutineName);
    7042             : 
    7043         137 :             state.dataRptCoilSelection->coilSelectionReportObj->setRatedCoilConditions(
    7044             :                 state,
    7045         137 :                 thisDXCoil.Name,
    7046         137 :                 thisDXCoil.DXCoilType,
    7047             :                 thisDXCoil.TotalHeatingEnergyRate, // this is the report variable
    7048             :                 thisDXCoil.TotalHeatingEnergyRate, // this is the report variable
    7049             :                 thisDXCoil.InletAirMassFlowRate,
    7050             :                 thisDXCoil.InletAirTemp,
    7051             :                 thisDXCoil.InletAirHumRat,
    7052             :                 RatedInletWetBulbTempHeat,
    7053             :                 thisDXCoil.OutletAirTemp,
    7054             :                 thisDXCoil.OutletAirHumRat,
    7055             :                 RatedOutletWetBulb,
    7056             :                 RatedOutdoorAirTempHeat,
    7057             :                 ratedOutdoorAirWetBulb,
    7058         137 :                 thisDXCoil.RatedCBF(Mode),
    7059             :                 -999.0); // coil effectiveness not define for DX
    7060             : 
    7061             :             // now replace the outdoor air conditions set above for one time rating point calc
    7062         137 :             state.dataEnvrn->OutDryBulbTemp = holdOutDryBulbTemp;
    7063         137 :             state.dataEnvrn->OutHumRat = holdOutHumRat;
    7064         137 :             state.dataEnvrn->OutWetBulbTemp = holdOutWetBulb;
    7065         137 :             state.dataEnvrn->OutBaroPress = holdOutBaroPress;
    7066             :         }
    7067             : 
    7068         960 :         if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed) {
    7069             :             // Check for valid range of (Rated Air Volume Flow Rate / Rated Total Capacity)
    7070          67 :             RatedVolFlowPerRatedTotCap = thisDXCoil.RatedAirVolFlowRate2 / thisDXCoil.RatedTotCap2;
    7071         134 :             if (((HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT] - RatedVolFlowPerRatedTotCap) > SmallDifferenceTest) ||
    7072          67 :                 ((RatedVolFlowPerRatedTotCap - HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) > SmallDifferenceTest)) {
    7073          10 :                 ShowWarningError(state,
    7074          10 :                                  format("Coil:Cooling:DX:TwoSpeed \"{}\": At low speed rated air volume flow rate per watt of rated total cooling "
    7075             :                                         "capacity is out of range.",
    7076           5 :                                         thisDXCoil.Name));
    7077          10 :                 ShowContinueError(state,
    7078          10 :                                   format("Min Rated Vol Flow Per Watt=[{:.3T}], Rated Vol Flow Per Watt=[{:.3T}], Max Rated Vol Flow Per "
    7079             :                                          "Watt=[{:.3T}]. See Input-Output Reference Manual for valid range.",
    7080           5 :                                          HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
    7081             :                                          RatedVolFlowPerRatedTotCap,
    7082           5 :                                          HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]));
    7083             :             }
    7084             : 
    7085          67 :             thisDXCoil.RatedAirMassFlowRate2 =
    7086         134 :                 thisDXCoil.RatedAirVolFlowRate2 *
    7087          67 :                 PsyRhoAirFnPbTdbW(state, state.dataEnvrn->StdBaroPress, RatedInletAirTemp, RatedInletAirHumRat, RoutineName);
    7088             :             // get low speed rated coil bypass factor
    7089         134 :             thisDXCoil.RatedCBF2 = CalcCBF(state,
    7090          67 :                                            thisDXCoil.DXCoilType,
    7091          67 :                                            thisDXCoil.Name,
    7092             :                                            RatedInletAirTemp,
    7093             :                                            RatedInletAirHumRat,
    7094             :                                            thisDXCoil.RatedTotCap2,
    7095             :                                            thisDXCoil.RatedAirVolFlowRate2,
    7096             :                                            thisDXCoil.RatedSHR2);
    7097             : 
    7098             :             // call for standard ratings for two-speeed DX coil
    7099          67 :             if (thisDXCoil.CondenserType(1) == DataHeatBalance::RefrigCondenserType::Air) {
    7100          66 :                 CalcTwoSpeedDXCoilStandardRating(state, DXCoilNum);
    7101             :             }
    7102             :         }
    7103             : 
    7104             :         // Multispeed Cooling
    7105         960 :         if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedCooling) {
    7106         162 :             for (Mode = 1; Mode <= thisDXCoil.NumOfSpeeds; ++Mode) {
    7107             :                 // Check for zero capacity or zero max flow rate
    7108         113 :                 if (thisDXCoil.MSRatedTotCap(Mode) <= 0.0) {
    7109           0 :                     ShowSevereError(state,
    7110           0 :                                     format("Sizing: {} {} has zero rated total capacity at speed {}", thisDXCoil.DXCoilType, thisDXCoil.Name, Mode));
    7111           0 :                     ErrorsFound = true;
    7112             :                 }
    7113         113 :                 if (thisDXCoil.MSRatedAirVolFlowRate(Mode) <= 0.0) {
    7114           0 :                     ShowSevereError(state,
    7115           0 :                                     format("Sizing: {} {} has zero rated air flow rate at speed {}", thisDXCoil.DXCoilType, thisDXCoil.Name, Mode));
    7116           0 :                     ErrorsFound = true;
    7117             :                 }
    7118         113 :                 if (ErrorsFound) {
    7119           0 :                     ShowFatalError(state, "Preceding condition causes termination.");
    7120             :                 }
    7121             :                 // Check for valid range of (Rated Air Volume Flow Rate / Rated Total Capacity)
    7122         113 :                 RatedVolFlowPerRatedTotCap = thisDXCoil.MSRatedAirVolFlowRate(Mode) / thisDXCoil.MSRatedTotCap(Mode);
    7123         226 :                 if (((HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT] - RatedVolFlowPerRatedTotCap) > SmallDifferenceTest) ||
    7124         113 :                     ((RatedVolFlowPerRatedTotCap - HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) > SmallDifferenceTest)) {
    7125          58 :                     ShowWarningError(
    7126             :                         state,
    7127          58 :                         format("Sizing: {} \"{}\": Rated air volume flow rate per watt of rated total cooling capacity is out of range at speed {}",
    7128          29 :                                thisDXCoil.DXCoilType,
    7129          29 :                                thisDXCoil.Name,
    7130             :                                Mode));
    7131          58 :                     ShowContinueError(state,
    7132          58 :                                       format("Min Rated Vol Flow Per Watt=[{:.3T}], Rated Vol Flow Per Watt=[{:.3T}], Max Rated Vol Flow Per "
    7133             :                                              "Watt=[{:.3T}]. See Input Output Reference Manual for valid range.",
    7134          29 :                                              HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
    7135             :                                              RatedVolFlowPerRatedTotCap,
    7136          29 :                                              HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]));
    7137             :                 }
    7138         226 :                 thisDXCoil.MSRatedAirMassFlowRate(Mode) =
    7139         113 :                     thisDXCoil.MSRatedAirVolFlowRate(Mode) *
    7140         113 :                     PsyRhoAirFnPbTdbW(state, state.dataEnvrn->StdBaroPress, RatedInletAirTemp, RatedInletAirHumRat, RoutineName);
    7141             :                 // get high speed rated coil bypass factor
    7142         113 :                 thisDXCoil.MSRatedCBF(Mode) = CalcCBF(state,
    7143         113 :                                                       thisDXCoil.DXCoilType,
    7144         113 :                                                       thisDXCoil.Name,
    7145             :                                                       RatedInletAirTemp,
    7146             :                                                       RatedInletAirHumRat,
    7147         113 :                                                       thisDXCoil.MSRatedTotCap(Mode),
    7148         113 :                                                       thisDXCoil.MSRatedAirVolFlowRate(Mode),
    7149         113 :                                                       thisDXCoil.MSRatedSHR(Mode));
    7150             :             }
    7151             :         }
    7152             : 
    7153             :         // Multispeed Heating
    7154         960 :         if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedHeating) {
    7155          22 :             RatedHeatPumpIndoorAirTemp = 21.11;  // 21.11C or 70F
    7156          22 :             RatedHeatPumpIndoorHumRat = 0.00881; // Humidity ratio corresponding to 70F dry bulb/60F wet bulb
    7157          92 :             for (Mode = 1; Mode <= thisDXCoil.NumOfSpeeds; ++Mode) {
    7158             : 
    7159         140 :                 thisDXCoil.MSRatedAirMassFlowRate(Mode) =
    7160          70 :                     thisDXCoil.MSRatedAirVolFlowRate(Mode) *
    7161          70 :                     PsyRhoAirFnPbTdbW(state, state.dataEnvrn->StdBaroPress, RatedHeatPumpIndoorAirTemp, RatedHeatPumpIndoorHumRat, RoutineName);
    7162             :                 // Check for valid range of (Rated Air Volume Flow Rate / Rated Total Capacity)
    7163          70 :                 RatedVolFlowPerRatedTotCap = thisDXCoil.MSRatedAirVolFlowRate(Mode) / thisDXCoil.MSRatedTotCap(Mode);
    7164         140 :                 if (((HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT] - RatedVolFlowPerRatedTotCap) > SmallDifferenceTest) ||
    7165          70 :                     ((RatedVolFlowPerRatedTotCap - HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) > SmallDifferenceTest)) {
    7166          12 :                     ShowWarningError(state,
    7167          12 :                                      format("Coil:Heating:DX:MultiSpeed {}: Rated air volume flow rate per watt of rated total heating capacity "
    7168             :                                             "is out of range at speed {}",
    7169           6 :                                             thisDXCoil.Name,
    7170             :                                             Mode));
    7171          12 :                     ShowContinueError(state,
    7172          12 :                                       format("Min Rated Vol Flow Per Watt=[{:.3T}], Rated Vol Flow Per Watt=[{:.3T}], Max Rated Vol Flow Per "
    7173             :                                              "Watt=[{:.3T}]. See Input Output Reference Manual for valid range.",
    7174           6 :                                              HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
    7175             :                                              RatedVolFlowPerRatedTotCap,
    7176           6 :                                              HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]));
    7177             :                 }
    7178             :             }
    7179             :         }
    7180             : 
    7181             :         // store fan info for coil
    7182         960 :         state.dataRptCoilSelection->coilSelectionReportObj->setCoilSupplyFanInfo(
    7183         960 :             state, thisDXCoil.Name, thisDXCoil.DXCoilType, thisDXCoil.SupplyFanName, thisDXCoil.supplyFanType, thisDXCoil.SupplyFanIndex);
    7184             :     }
    7185             : 
    7186    63535486 :     AirInletNode = thisDXCoil.AirInNode;
    7187             : 
    7188             :     // Each iteration, load the coil data structure with the inlet conditions
    7189             : 
    7190    63535486 :     thisDXCoil.InletAirMassFlowRate = state.dataLoopNodes->Node(AirInletNode).MassFlowRate;
    7191    63535486 :     thisDXCoil.InletAirMassFlowRateMax =
    7192    63535486 :         max(state.dataLoopNodes->Node(AirInletNode).MassFlowRateMax, state.dataLoopNodes->Node(AirInletNode).MassFlowRate);
    7193    63535486 :     thisDXCoil.InletAirTemp = state.dataLoopNodes->Node(AirInletNode).Temp;
    7194    63535486 :     thisDXCoil.InletAirHumRat = state.dataLoopNodes->Node(AirInletNode).HumRat;
    7195    63535486 :     thisDXCoil.InletAirEnthalpy = state.dataLoopNodes->Node(AirInletNode).Enthalpy;
    7196             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
    7197             :     //  DXCoil(DXCoilNum)%InletAirPressure        = Node(AirInletNode)%Press
    7198             : 
    7199    63535486 :     if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatingEmpirical || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedHeating) {
    7200    12746066 :         if (thisDXCoil.IsSecondaryDXCoilInZone) {
    7201       81924 :             thisDXCoil.EvapInletWetBulb = PsyTwbFnTdbWPb(state,
    7202       81924 :                                                          state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr).ZT,
    7203       81924 :                                                          state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr).airHumRat,
    7204       81924 :                                                          state.dataEnvrn->OutBaroPress,
    7205             :                                                          RoutineName);
    7206             :         }
    7207             :     }
    7208             : 
    7209    63535486 :     if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) {
    7210      631844 :         thisDXCoil.TotalHeatingEnergyRate = 0.0;
    7211      631844 :         thisDXCoil.ElecWaterHeatingPower = 0.0;
    7212             :         //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
    7213             :         //  DXCoil(DXCoilNum)%InletAirPressure         = StdBaroPress
    7214             : 
    7215             :         //   HPWH's that use an inlet air temperature schedule also need to have a valid barometric pressure
    7216             :         //   The DX Coil used in HPWH's does not know if it is using a scheduled inlet temperature so check the node pressure
    7217      631844 :         if (thisDXCoil.CondenserInletNodeNum(1) > 0) {
    7218      631844 :             if (state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).Press == 0.0) {
    7219           0 :                 state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).Press = state.dataEnvrn->StdBaroPress;
    7220             :             }
    7221             :         }
    7222             :     }
    7223    63535486 :     thisDXCoil.BasinHeaterPower = 0.0;
    7224             : 
    7225    63535486 :     if (thisDXCoil.IsSecondaryDXCoilInZone) {
    7226      163849 :         thisDXCoil.CompressorPartLoadRatio = 0.0;
    7227      163849 :         thisDXCoil.SecCoilSensibleHeatGainRate = 0.0;
    7228      163849 :         thisDXCoil.SecCoilTotalHeatRemovalRate = 0.0;
    7229      163849 :         thisDXCoil.SecCoilSensibleHeatRemovalRate = 0.0;
    7230      163849 :         thisDXCoil.SecCoilLatentHeatRemovalRate = 0.0;
    7231             :     }
    7232    63535486 : }
    7233             : 
    7234         992 : void SizeDXCoil(EnergyPlusData &state, int const DXCoilNum)
    7235             : {
    7236             : 
    7237             :     // SUBROUTINE INFORMATION:
    7238             :     //       AUTHOR         Fred Buhl
    7239             :     //       DATE WRITTEN   January 2002
    7240             :     //                      Feb 2005, M. J. Witte, GARD Analytics, Inc. Add new coil type COIL:DX:MultiMode:CoolingEmpirical.
    7241             :     //                      Jul 2005, R. Raustad, FSEC. Add new coil type COIL:DX:HEATPUMPWATERHEATER
    7242             :     //                      Jun 2007, L. Gu, FSEC. Add new coil type COIL:DX:MULTISPEED:COOLING and HEATING
    7243             :     //                      Jan 2011, B. Griffithn, NREL. add EMS overrides for autosized fields
    7244             :     //                      Aug 2013, D. Kang. add component sizing table entries
    7245             :     //                      May 2014, R. Raustad, FSEC. moved sizing calculations to common routine
    7246             :     //                      Aug 2015, R. Zhang, LBNL. Add new coil types for VRF_FluidTCtrl
    7247             :     //       RE-ENGINEERED  na
    7248             : 
    7249             :     // PURPOSE OF THIS SUBROUTINE:
    7250             :     // This subroutine is for sizing DX Coil components for which nominal capacity and air flow rate
    7251             :     // have not been specified in the input.
    7252             : 
    7253             :     // METHODOLOGY EMPLOYED:
    7254             :     // Obtains cooling capacities and air flow rates from the zone or system sizing arrays.
    7255             : 
    7256             :     // Using/Aliasing
    7257             :     using namespace DataSizing;
    7258             :     using Curve::CurveValue;
    7259             : 
    7260             :     using namespace OutputReportPredefined;
    7261             :     using StandardRatings::CalcDXCoilStandardRating;
    7262             : 
    7263             :     // SUBROUTINE PARAMETER DEFINITIONS:
    7264             :     static constexpr std::string_view RoutineName("SizeDXCoil");
    7265             : 
    7266             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
    7267             :     Real64 CoilInTemp;       // DX coil inlet temperature
    7268             :     int CapacityStageNum;    // Loop index for 1,Number of capacity stages
    7269             :     int DehumidModeNum;      // Loop index for 1,Number of enhanced dehumidification modes
    7270             :     int Mode;                // Operating mode for MultiMode DX coil; Always 1 for other coil types
    7271             :     int NumOfSpeedCompanion; // Number of speed for a companion cooling coil (Multispeed HO heating coil only
    7272         992 :     std::string equipName;
    7273             :     Real64 RatedAirVolFlowRateDes;          // Design rated air volume flow for reporting
    7274             :     Real64 RatedAirVolFlowRateUser;         // Hard-sized rated air volume flow for reporting
    7275             :     Real64 RatedAirVolFlowRate2Des;         // Design rated low speed air volume flow for reporting
    7276             :     Real64 RatedAirVolFlowRate2User;        // Hard-sized rated low speed air volume flow for reporting
    7277             :     Real64 RatedTotCapDes;                  // Design rated total capacity for reproting
    7278             :     Real64 RatedTotCapUser;                 // Hard-sized rated total capacity for reproting
    7279             :     Real64 RatedTotCap2Des;                 // Design rated low speed total capacity for reproting
    7280             :     Real64 RatedTotCap2User;                // Hard-sized rated low speed total capacity for reproting
    7281             :     Real64 RatedSHRDes;                     // Design ratd SHR for reporting
    7282             :     Real64 RatedSHRUser;                    // Hard-sized ratd SHR for reporting
    7283             :     Real64 RatedSHR2Des;                    // Design ratd low speed SHR for reporting
    7284             :     Real64 RatedSHR2User;                   // Hard-sized ratd low speed SHR for reporting
    7285             :     Real64 EvapCondAirFlowDes;              // Design evaporative condenser air flow for reporting
    7286             :     Real64 EvapCondAirFlowUser;             // Hard-sized evaporative condenser air flow for reporting
    7287             :     Real64 EvapCondAirFlow2Des;             // Design low speed evaporative condenser air flow for reporting
    7288             :     Real64 EvapCondAirFlow2User;            // Hard-sized low speed evaporative condenser air flow for reporting
    7289             :     Real64 EvapCondPumpElecNomPowerDes;     // Design evaporative condenser pump rated power consumption for reporting
    7290             :     Real64 EvapCondPumpElecNomPowerUser;    // Hard-sized evaporative condenser pump rated power consumption for reporting
    7291             :     Real64 EvapCondPumpElecNomPower2Des;    // Design low speed condenser pump rated power consumption for reporting
    7292             :     Real64 EvapCondPumpElecNomPower2User;   // Hard-sized low speed condenser pump rated power consumption for reporting
    7293             :     Real64 DefrostCapacityDes;              // Design defrost heater capacity for reporting
    7294             :     Real64 DefrostCapacityUser;             // Hard-sized defrost heater capacity for reporting
    7295             :     Real64 MSRatedAirVolFlowRateDes;        // Design multispeed rated air volume flow rate for reporting
    7296             :     Real64 MSRatedAirVolFlowRateUser;       // Hard-sized multispeed rated air volume flow rate for reporting
    7297             :     Real64 MSRatedTotCapDesAtMaxSpeed;      // Design multispeed rated total capacity for reporting (at maximum speed)
    7298             :     Real64 MSRatedTotCapUser;               // Hard-sized multispeed rated total capacity for reporting
    7299             :     Real64 MSRatedSHRDes;                   // Design multispeed rated SHR for reporting
    7300             :     Real64 MSRatedSHRUser;                  // Hard-sized multispeed rated SHR for reporting
    7301             :     Real64 MSEvapCondAirFlowDes;            // Design evaporative condenser air flow for reporting
    7302             :     Real64 MSEvapCondAirFlowUser;           // Hard-sized evaporative condenser air flow for reporting
    7303             :     Real64 MSEvapCondAirFlow2Des;           // Design low speed evaporative condenser air flow for reporting
    7304             :     Real64 MSEvapCondAirFlow2User;          // Hard-sized low speed evaporative condenser air flow for reporting
    7305             :     Real64 MSEvapCondPumpElecNomPowerDes;   // Design evaporative condenser pump rated power consumption for reporting
    7306             :     Real64 MSEvapCondPumpElecNomPowerUser;  // Hard-sized evaporative condenser pump rated power consumption for reporting
    7307             :     Real64 MSEvapCondPumpElecNomPower2Des;  // Design low speed condenser pump rated power consumption for reporting
    7308             :     Real64 MSEvapCondPumpElecNomPower2User; // Hard-sized low speed condenser pump rated power consumption for reporting
    7309             :     Real64 MSDefrostCapacityDes;            // Design defrost heater capacity for reporting
    7310             :     Real64 MSDefrostCapacityUser;           // Hard-sized defrost heater capacity for reporting
    7311             :     bool HardSizeNoDesRun;                  // Indicator to a hard-sized field with no design sizing data
    7312             :     bool IsAutoSize;                        // Indicator to autosize for reporting
    7313             :     bool IsCoolCoilCapAutoSize;             // Indicator to cooling capacity autosize for reporting
    7314             :     bool SizingDesRunThisAirSys;            // true if a particular air system had a Sizing:System object and system sizing done
    7315             :     bool SizingDesRunThisZone;              // true if a particular zone had a Sizing:Zone object and zone sizing was done
    7316         992 :     std::string CompName;                   // component name
    7317         992 :     std::string CompType;                   // component type
    7318         992 :     std::string SizingString;               // input field sizing description (e.g., Nominal Capacity)
    7319         992 :     bool bPRINT = true;                     // TRUE if sizing is reported to output (eio)
    7320             :     Real64 TempSize;                        // autosized value of coil input field
    7321         992 :     int FieldNum = 2;                       // IDD numeric field number where input field description is found
    7322             :     int SizingMethod;                       // Integer representation of sizing method (e.g., CoolingAirflowSizing, HeatingCapacitySizing, etc.)
    7323             :     bool PrintFlag;                         // TRUE when sizing information is reported in the eio file
    7324             :     bool SizeSecDXCoil;                     // if true do sizing calculation for secondary coil
    7325             :     Real64 SecCoilAirFlowDes;               // Design secondary DX coil air flow for reporting
    7326             :     Real64 SecCoilAirFlowUser;              // Hard-sized secondary DX coil air flow for reporting
    7327             : 
    7328             :     // Initiate all reporting variables
    7329         992 :     if (state.dataSize->SysSizingRunDone || state.dataSize->ZoneSizingRunDone) {
    7330         858 :         HardSizeNoDesRun = false;
    7331             :     } else {
    7332         134 :         HardSizeNoDesRun = true;
    7333             :     }
    7334             : 
    7335         992 :     if (state.dataSize->CurSysNum > 0) {
    7336         617 :         CheckThisAirSystemForSizing(state, state.dataSize->CurSysNum, SizingDesRunThisAirSys);
    7337             :     } else {
    7338         375 :         SizingDesRunThisAirSys = false;
    7339             :     }
    7340         992 :     if (state.dataSize->CurZoneEqNum > 0) {
    7341         351 :         CheckThisZoneForSizing(state, state.dataSize->CurZoneEqNum, SizingDesRunThisZone);
    7342             :     } else {
    7343         641 :         SizingDesRunThisZone = false;
    7344             :     }
    7345             : 
    7346         992 :     IsAutoSize = false;
    7347         992 :     IsCoolCoilCapAutoSize = false;
    7348         992 :     SizeSecDXCoil = false;
    7349         992 :     RatedAirVolFlowRateDes = 0.0;
    7350         992 :     RatedAirVolFlowRateUser = 0.0;
    7351         992 :     RatedAirVolFlowRate2Des = 0.0;
    7352         992 :     RatedAirVolFlowRate2User = 0.0;
    7353         992 :     RatedTotCapDes = 0.0;
    7354         992 :     RatedTotCapUser = 0.0;
    7355         992 :     RatedTotCap2Des = 0.0;
    7356         992 :     RatedTotCap2User = 0.0;
    7357         992 :     MSRatedTotCapDesAtMaxSpeed = 0.0;
    7358         992 :     RatedSHRDes = 0.0;
    7359         992 :     RatedSHRUser = 0.0;
    7360         992 :     RatedSHR2Des = 0.0;
    7361         992 :     RatedSHR2User = 0.0;
    7362         992 :     EvapCondAirFlowDes = 0.0;
    7363         992 :     EvapCondAirFlowUser = 0.0;
    7364         992 :     EvapCondAirFlow2Des = 0.0;
    7365         992 :     EvapCondAirFlow2User = 0.0;
    7366         992 :     EvapCondPumpElecNomPowerDes = 0.0;
    7367         992 :     EvapCondPumpElecNomPowerUser = 0.0;
    7368         992 :     EvapCondPumpElecNomPower2Des = 0.0;
    7369         992 :     EvapCondPumpElecNomPower2User = 0.0;
    7370         992 :     DefrostCapacityDes = 0.0;
    7371         992 :     DefrostCapacityUser = 0.0;
    7372         992 :     MSRatedAirVolFlowRateDes = 0.0;
    7373         992 :     MSRatedAirVolFlowRateUser = 0.0;
    7374             :     // MSRatedTotCapDes = 0.0;
    7375         992 :     MSRatedTotCapUser = 0.0;
    7376         992 :     MSRatedSHRDes = 0.0;
    7377         992 :     MSRatedSHRUser = 0.0;
    7378         992 :     MSEvapCondAirFlowDes = 0.0;
    7379         992 :     MSEvapCondAirFlowUser = 0.0;
    7380         992 :     MSEvapCondAirFlow2Des = 0.0;
    7381         992 :     MSEvapCondAirFlow2User = 0.0;
    7382         992 :     MSEvapCondPumpElecNomPowerDes = 0.0;
    7383         992 :     MSEvapCondPumpElecNomPowerUser = 0.0;
    7384         992 :     MSEvapCondPumpElecNomPower2Des = 0.0;
    7385         992 :     MSEvapCondPumpElecNomPower2User = 0.0;
    7386         992 :     MSDefrostCapacityDes = 0.0;
    7387         992 :     MSDefrostCapacityUser = 0.0;
    7388         992 :     SecCoilAirFlowDes = 0.0;
    7389         992 :     SecCoilAirFlowUser = 0.0;
    7390             : 
    7391             :     // Sizer classes
    7392         992 :     CoolingSHRSizer sizerCoolingSHR;
    7393         992 :     bool ErrorsFound = false;
    7394             : 
    7395         992 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    7396             : 
    7397             :     // NOTE: we are sizing COIL:DX:HeatingEmpirical on the COOLING load. Thus the cooling and
    7398             :     // and heating capacities of a DX heat pump system will be identical. In real life the AHRI
    7399             :     // heating and cooling capacities are close but not identical.
    7400        1991 :     for (DehumidModeNum = 0; DehumidModeNum <= thisDXCoil.NumDehumidModes; ++DehumidModeNum) {
    7401        2015 :         for (CapacityStageNum = 1; CapacityStageNum <= thisDXCoil.NumCapacityStages; ++CapacityStageNum) {
    7402        1016 :             Mode = DehumidModeNum * 2 + CapacityStageNum;
    7403        1016 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    7404         990 :                 thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) {
    7405          32 :                 if (thisDXCoil.RatedAirVolFlowRate(1) == Constant::AutoCalculate) {
    7406             :                     // report autocalculated sizing
    7407           6 :                     PrintFlag = true;
    7408           6 :                     CompName = thisDXCoil.Name;
    7409           6 :                     CompType = thisDXCoil.DXCoilType;
    7410             :                     // DXCoil( DXCoilNum ).RatedAirVolFlowRate( 1 ) = DXCoil( DXCoilNum ).RatedTotCap2 * 0.00005035
    7411           6 :                     state.dataSize->DataConstantUsedForSizing = thisDXCoil.RatedTotCap2;
    7412           6 :                     state.dataSize->DataFractionUsedForSizing = 0.00005035;
    7413           6 :                     TempSize = AutoSize;
    7414           6 :                     AutoCalculateSizer sizerHPRatedAirVolFlow;
    7415           6 :                     std::string stringOverride = "Rated Evaporator Air Flow Rate [m3/s]";
    7416           6 :                     if (state.dataGlobal->isEpJSON) stringOverride = "rated_evaporator_air_flow_rate [m3/s]";
    7417           6 :                     sizerHPRatedAirVolFlow.overrideSizingString(stringOverride);
    7418           6 :                     sizerHPRatedAirVolFlow.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7419           6 :                     thisDXCoil.RatedAirVolFlowRate(1) = sizerHPRatedAirVolFlow.size(state, TempSize, ErrorsFound);
    7420           6 :                     PrintFlag = false;
    7421           6 :                 }
    7422             : 
    7423          32 :                 if (thisDXCoil.RatedHPWHCondWaterFlow == Constant::AutoCalculate) {
    7424             :                     // report autocalculated sizing
    7425           6 :                     PrintFlag = true;
    7426           6 :                     CompName = thisDXCoil.Name;
    7427           6 :                     CompType = thisDXCoil.DXCoilType;
    7428             :                     // DXCoil( DXCoilNum ).RatedAirVolFlowRate( 1 ) = DXCoil( DXCoilNum ).RatedTotCap2 * 0.00000004487
    7429           6 :                     state.dataSize->DataConstantUsedForSizing = thisDXCoil.RatedTotCap2;
    7430           6 :                     state.dataSize->DataFractionUsedForSizing = 0.00000004487;
    7431           6 :                     TempSize = AutoSize;
    7432           6 :                     AutoCalculateSizer sizerHPWHCondWaterFlow;
    7433           6 :                     std::string stringOverride = "Rated Condenser Water Flow Rate [m3/s]";
    7434           6 :                     if (state.dataGlobal->isEpJSON) stringOverride = "rated_condenser_water_flow_rate [m3/s]";
    7435           6 :                     sizerHPWHCondWaterFlow.overrideSizingString(stringOverride);
    7436           6 :                     sizerHPWHCondWaterFlow.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7437           6 :                     thisDXCoil.RatedHPWHCondWaterFlow = sizerHPWHCondWaterFlow.size(state, TempSize, ErrorsFound);
    7438           6 :                     PrintFlag = false;
    7439           6 :                 }
    7440          32 :             } else {
    7441         984 :                 PrintFlag = true;
    7442         984 :                 FieldNum = 0;
    7443         984 :                 if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl) {
    7444          35 :                     CompName = thisDXCoil.Name + ":" + thisDXCoil.CoilPerformanceName(Mode);
    7445          35 :                     FieldNum = 4;
    7446          35 :                     state.dataSize->DataBypassFrac = thisDXCoil.BypassedFlowFrac(Mode);
    7447         949 :                 } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatingEmpirical) {
    7448          75 :                     CompName = thisDXCoil.Name;
    7449          75 :                     FieldNum = 3;
    7450             :                     // doesn't look like this is needed for air flow sizing, only for heating capacity sizing
    7451         150 :                     state.dataSize->DataCoolCoilCap =
    7452          75 :                         state.dataSize->DXCoolCap; // pass global variable used only for heat pumps (i.e., DX cooling and heating coils)
    7453          76 :                     if ((thisDXCoil.IsSecondaryDXCoilInZone) &&
    7454           1 :                         (thisDXCoil.CondenserType(1) ==
    7455             :                          DataHeatBalance::RefrigCondenserType::Air)) { // seconday DX coil in secondary zone is specified
    7456           1 :                         SizeSecDXCoil = true;
    7457             :                     }
    7458         874 :                 } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Heating) {
    7459          46 :                     CompName = thisDXCoil.Name;
    7460          46 :                     FieldNum = 2;
    7461         828 :                 } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Cooling) {
    7462          46 :                     CompName = thisDXCoil.Name;
    7463          46 :                     FieldNum = 3;
    7464         782 :                 } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Heating) {
    7465          16 :                     CompName = thisDXCoil.Name;
    7466         766 :                 } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Cooling) {
    7467          16 :                     CompName = thisDXCoil.Name;
    7468         750 :                 } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedCooling) {
    7469          49 :                     thisDXCoil.RatedAirVolFlowRate(Mode) = thisDXCoil.MSRatedAirVolFlowRate(thisDXCoil.NumOfSpeeds);
    7470          49 :                     CompName = thisDXCoil.Name;
    7471          49 :                     PrintFlag = false;
    7472         701 :                 } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedHeating) {
    7473          22 :                     thisDXCoil.RatedAirVolFlowRate(Mode) = thisDXCoil.MSRatedAirVolFlowRate(thisDXCoil.NumOfSpeeds);
    7474          22 :                     CompName = thisDXCoil.Name;
    7475          22 :                     PrintFlag = false;
    7476             :                 } else {
    7477         679 :                     CompName = thisDXCoil.Name;
    7478         679 :                     FieldNum = 4;
    7479             :                 }
    7480             : 
    7481         984 :                 TempSize = thisDXCoil.RatedAirVolFlowRate(Mode);
    7482         984 :                 if (FieldNum > 0) {
    7483         881 :                     SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(Mode).FieldNames(FieldNum) + " [m3/s]";
    7484             :                 } else {
    7485         103 :                     SizingString = "Rated Air Flow Rate [m3/s]";
    7486             :                 }
    7487         984 :                 CompType = thisDXCoil.DXCoilType;
    7488         984 :                 state.dataSize->DataIsDXCoil = true;
    7489         984 :                 state.dataSize->DataEMSOverrideON = thisDXCoil.RatedAirVolFlowRateEMSOverrideON(Mode);
    7490         984 :                 state.dataSize->DataEMSOverride = thisDXCoil.RatedAirVolFlowRateEMSOverrideValue(Mode);
    7491         984 :                 if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedHeating || thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Heating ||
    7492         946 :                     thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Heating || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatingEmpirical) {
    7493         159 :                     bool errorsFound = false;
    7494         159 :                     HeatingAirFlowSizer sizingHeatingAirFlow;
    7495         159 :                     sizingHeatingAirFlow.overrideSizingString(SizingString);
    7496             :                     // sizingHeatingAirFlow.setHVACSizingIndexData(FanCoil(FanCoilNum).HVACSizingIndex);
    7497         159 :                     sizingHeatingAirFlow.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7498         159 :                     thisDXCoil.RatedAirVolFlowRate(Mode) = sizingHeatingAirFlow.size(state, TempSize, errorsFound);
    7499         159 :                 } else {
    7500         825 :                     bool errorsFound = false;
    7501         825 :                     CoolingAirFlowSizer sizingCoolingAirFlow;
    7502         825 :                     sizingCoolingAirFlow.overrideSizingString(SizingString);
    7503             :                     // sizingCoolingAirFlow.setHVACSizingIndexData(FanCoil(FanCoilNum).HVACSizingIndex);
    7504         825 :                     sizingCoolingAirFlow.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7505         825 :                     thisDXCoil.RatedAirVolFlowRate(Mode) = sizingCoolingAirFlow.size(state, TempSize, errorsFound);
    7506         825 :                 }
    7507         984 :                 state.dataSize->DataIsDXCoil = false;
    7508         984 :                 state.dataSize->DataEMSOverrideON = false;
    7509         984 :                 state.dataSize->DataEMSOverride = 0.0;
    7510         984 :                 state.dataSize->DataBypassFrac = 0.0;
    7511             :             }
    7512             : 
    7513        1016 :             state.dataSize->DataFlowUsedForSizing = thisDXCoil.RatedAirVolFlowRate(Mode);
    7514             :             // get autosized air flow for capacity calc's if capacity is not autosized
    7515             :             // *** RAR this if block is a last minute addition to correct capacity reporting when not autosized and a sizing run is done. Test
    7516             :             // suite was not run with this code included. *** The question here is if the autosized air flow rate or the user specified air flow
    7517             :             // rate should be used to calculate capacity removing this for now until more is known
    7518             :             //                if ( DXCoil( DXCoilNum ).RatedTotCap( Mode ) != AutoSize && ( ( SysSizingRunDone && CurSysNum > 0 ) ||
    7519             :             //(  ZoneSizingRunDone && CurZoneEqNum > 0 ) ) ) {                     if ( DXCoil( DXCoilNum ).DXCoilType_Num ==
    7520             :             // HVAC::CoilDX_CoolingTwoStageWHumControl ) {                         SizingMethod = CoolingAirflowSizing;
    7521             :             //                        DataBypassFrac = DXCoil ( DXCoilNum ).BypassedFlowFrac ( Mode );
    7522             :             //                    } else if ( DXCoil( DXCoilNum ).DXCoilType_Num == HVAC::CoilDX_HeatingEmpirical ) {
    7523             :             //                        SizingMethod = HeatingAirflowSizing;
    7524             :             ////                        DataCoolCoilCap = DXCoolCap; // pass global variable used only for heat pumps (i.e.,
    7525             :             /// DX  cooling  and  heating coils)
    7526             :             //                    } else if ( DXCoil( DXCoilNum ).DXCoilType_Num == HVAC::CoilVRF_Heating ) {
    7527             :             //                        SizingMethod = HeatingAirflowSizing;
    7528             :             //                    } else if ( DXCoil( DXCoilNum ).DXCoilType_Num == HVAC::CoilVRF_Cooling ) {
    7529             :             //                        SizingMethod = CoolingAirflowSizing;
    7530             :             //                    } else {
    7531             :             //                        SizingMethod = CoolingAirflowSizing;
    7532             :             //                    }
    7533             :             //                    CompName = DXCoil( DXCoilNum ).Name;
    7534             :             //                    TempSize = AutoSize;
    7535             :             //                    SizingString.clear(); // don't care
    7536             :             //                    CompType = DXCoil( DXCoilNum ).DXCoilType;
    7537             :             //                    DataIsDXCoil = true;
    7538             :             //                    DataEMSOverrideON = DXCoil ( DXCoilNum ).RatedAirVolFlowRateEMSOverrideON ( Mode );
    7539             :             //                    DataEMSOverride = DXCoil( DXCoilNum ).RatedAirVolFlowRateEMSOverrideValue( Mode );
    7540             :             //                  CoolingAirFlowSizer sizingCoolingAirFlow;
    7541             :             //                  sizingCoolingAirFlow.setHVACSizingIndexData(FanCoil(FanCoilNum).HVACSizingIndex);
    7542             :             //                  sizingCoolingAirFlow.initializeWithinEP(state, CompType, CompName, bPRINT, RoutineName);
    7543             :             //                  DataAirFlowUsedForSizing = sizingCoolingAirFlow.size(state, TempSize, errorsFound);
    7544             :             //                    DataIsDXCoil = false; // don't need this and next 2, they are just overwritten below. Delete
    7545             :             // on  next  pass so testing will show problems if any.                     DataEMSOverrideON = false;
    7546             :             //                    DataEMSOverride = 0.0;
    7547             :             //                    DataBypassFrac = 0.0;
    7548             :             //                }
    7549        1016 :             PrintFlag = true;
    7550        1016 :             state.dataSize->DataTotCapCurveIndex = thisDXCoil.CCapFTemp(Mode);
    7551        1016 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl) {
    7552          35 :                 SizingMethod = HVAC::CoolingCapacitySizing;
    7553          35 :                 CompName = thisDXCoil.Name + ":" + thisDXCoil.CoilPerformanceName(Mode);
    7554          35 :                 FieldNum = 1;
    7555          35 :                 TempSize = thisDXCoil.RatedTotCap(Mode);
    7556          35 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(Mode).FieldNames(FieldNum) + " [W]";
    7557         981 :             } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatingEmpirical || thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Heating ||
    7558         860 :                        thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Heating) {
    7559         137 :                 SizingMethod = HVAC::HeatingCapacitySizing;
    7560         137 :                 CompName = thisDXCoil.Name;
    7561         137 :                 FieldNum = 1;
    7562         137 :                 TempSize = thisDXCoil.RatedTotCap(Mode);
    7563         137 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(Mode).FieldNames(FieldNum) + " [W]";
    7564         137 :                 state.dataSize->DataCoolCoilCap = state.dataSize->DXCoolCap;
    7565         844 :             } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    7566         818 :                        thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) {
    7567          32 :                 SizingMethod = HVAC::CoolingCapacitySizing;
    7568          32 :                 CompName = thisDXCoil.Name;
    7569          32 :                 FieldNum = 1;
    7570          32 :                 TempSize = thisDXCoil.RatedTotCap(Mode);
    7571          32 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(Mode).FieldNames(FieldNum) + " [W]";
    7572          32 :                 PrintFlag = false;
    7573          32 :                 state.dataLoopNodes->Node(thisDXCoil.WaterInNode).Temp =
    7574          32 :                     thisDXCoil.RatedInletWaterTemp; // set the rated water inlet node for HPWHs for use in CalcHPWHDXCoil
    7575         812 :             } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Cooling) {
    7576          16 :                 SizingMethod = HVAC::CoolingCapacitySizing;
    7577          16 :                 CompName = thisDXCoil.Name;
    7578          16 :                 FieldNum = 1;
    7579          16 :                 TempSize = thisDXCoil.RatedTotCap(Mode);
    7580          16 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(Mode).FieldNames(FieldNum) + " [W]";
    7581          16 :                 if (state.dataSize->CurZoneEqNum > 0) {
    7582          16 :                     CoilInTemp =
    7583          16 :                         state.dataSize->ZoneSizingRunDone ? state.dataSize->FinalZoneSizing(state.dataSize->CurZoneEqNum).DesCoolCoilInTemp : 26;
    7584             :                 } else {
    7585           0 :                     if (state.dataSize->CurOASysNum > 0) {
    7586           0 :                         CoilInTemp =
    7587           0 :                             state.dataSize->SysSizingRunDone ? state.dataSize->FinalSysSizing(state.dataSize->CurSysNum).OutTempAtCoolPeak : 32;
    7588             :                     } else {
    7589           0 :                         CoilInTemp =
    7590           0 :                             state.dataSize->SysSizingRunDone ? state.dataSize->FinalSysSizing(state.dataSize->CurSysNum).MixTempAtCoolPeak : 26;
    7591             :                     }
    7592             :                 }
    7593          16 :                 CalcVRFCoilCapModFac(state, 0, _, CompName, CoilInTemp, _, _, _, state.dataSize->DataTotCapCurveValue);
    7594         796 :             } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedCooling) {
    7595          49 :                 SizingMethod = HVAC::CoolingCapacitySizing;
    7596          49 :                 CompName = thisDXCoil.Name;
    7597          49 :                 FieldNum = 7 + (thisDXCoil.NumOfSpeeds - 1) * 13;
    7598          49 :                 state.dataSize->DataTotCapCurveIndex = thisDXCoil.MSCCapFTemp(thisDXCoil.NumOfSpeeds);
    7599          49 :                 TempSize = thisDXCoil.MSRatedTotCap(thisDXCoil.NumOfSpeeds);
    7600          49 :                 PrintFlag = false;
    7601          49 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(Mode).FieldNames(FieldNum) + " [W]";
    7602         747 :             } else if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedHeating) {
    7603          22 :                 SizingMethod = HVAC::HeatingCapacitySizing;
    7604          22 :                 CompName = thisDXCoil.Name;
    7605          22 :                 FieldNum = 10 + (thisDXCoil.NumOfSpeeds - 1) * 5;
    7606          22 :                 state.dataSize->DataTotCapCurveIndex = thisDXCoil.MSCCapFTemp(thisDXCoil.NumOfSpeeds);
    7607          22 :                 TempSize = thisDXCoil.MSRatedTotCap(thisDXCoil.NumOfSpeeds);
    7608          22 :                 PrintFlag = false;
    7609          22 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(Mode).FieldNames(FieldNum) + " [W]";
    7610             :             } else {
    7611         725 :                 SizingMethod = HVAC::CoolingCapacitySizing;
    7612         725 :                 CompName = thisDXCoil.Name;
    7613         725 :                 FieldNum = 1;
    7614         725 :                 TempSize = thisDXCoil.RatedTotCap(Mode);
    7615         725 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(Mode).FieldNames(FieldNum) + " [W]";
    7616             :             }
    7617        1016 :             CompType = thisDXCoil.DXCoilType;
    7618        1016 :             state.dataSize->DataIsDXCoil = true;
    7619        1016 :             state.dataSize->DataEMSOverrideON = thisDXCoil.RatedTotCapEMSOverrideOn(Mode);
    7620        1016 :             state.dataSize->DataEMSOverride = thisDXCoil.RatedTotCapEMSOverrideValue(Mode);
    7621        1016 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedHeating || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatingEmpirical ||
    7622         919 :                 thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Heating || thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Heating) {
    7623         159 :                 HeatingCapacitySizer sizerHeatingCapacity;
    7624         159 :                 sizerHeatingCapacity.overrideSizingString(SizingString);
    7625         159 :                 sizerHeatingCapacity.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7626         159 :                 thisDXCoil.RatedTotCap(Mode) = sizerHeatingCapacity.size(state, TempSize, ErrorsFound);
    7627         159 :             } else {
    7628         857 :                 CoolingCapacitySizer sizerCoolingCapacity;
    7629         857 :                 sizerCoolingCapacity.overrideSizingString(SizingString);
    7630         857 :                 sizerCoolingCapacity.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7631         857 :                 thisDXCoil.RatedTotCap(Mode) = sizerCoolingCapacity.size(state, TempSize, ErrorsFound);
    7632         857 :             }
    7633        1016 :             state.dataSize->DataIsDXCoil = false;
    7634        1016 :             state.dataSize->DataFlowUsedForSizing = 0.0;
    7635        1016 :             state.dataSize->DataCoolCoilCap = 0.0;
    7636        1016 :             state.dataSize->DataTotCapCurveIndex = 0;
    7637        1016 :             state.dataSize->DataEMSOverrideON = false;
    7638        1016 :             state.dataSize->DataEMSOverride = 0.0;
    7639        1016 :             state.dataSize->DataConstantUsedForSizing = 0.0;
    7640        1016 :             state.dataSize->DataFractionUsedForSizing = 0.0;
    7641        1016 :             state.dataSize->DataTotCapCurveValue = 0.0;
    7642             : 
    7643             :             // Cooling coil capacity
    7644        1016 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingSingleSpeed || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed ||
    7645         337 :                 thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl || thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Cooling ||
    7646         256 :                 thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Cooling) {
    7647         776 :                 state.dataSize->DXCoolCap = thisDXCoil.RatedTotCap(Mode);
    7648             :             }
    7649             : 
    7650             :             // Sizing DX cooling coil SHR
    7651        1016 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingSingleSpeed || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed ||
    7652         337 :                 thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl || thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_Cooling ||
    7653         256 :                 thisDXCoil.DXCoilType_Num == HVAC::CoilVRF_FluidTCtrl_Cooling) {
    7654             : 
    7655         776 :                 if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl) {
    7656          35 :                     CompName = thisDXCoil.Name + ":" + thisDXCoil.CoilPerformanceName(Mode);
    7657             :                 } else {
    7658         741 :                     CompName = thisDXCoil.Name;
    7659             :                 }
    7660         776 :                 CompType = thisDXCoil.DXCoilType;
    7661         776 :                 TempSize = thisDXCoil.RatedSHR(Mode);
    7662         776 :                 state.dataSize->DataDXSpeedNum = Mode;
    7663         776 :                 state.dataSize->DataFlowUsedForSizing = thisDXCoil.RatedAirVolFlowRate(Mode);
    7664         776 :                 state.dataSize->DataCapacityUsedForSizing = thisDXCoil.RatedTotCap(Mode);
    7665         776 :                 state.dataSize->DataEMSOverrideON = thisDXCoil.RatedSHREMSOverrideOn(Mode);
    7666         776 :                 state.dataSize->DataEMSOverride = thisDXCoil.RatedSHREMSOverrideValue(Mode);
    7667         776 :                 bool ErrorsFound = false;
    7668         776 :                 sizerCoolingSHR.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7669         776 :                 thisDXCoil.RatedSHR(Mode) = sizerCoolingSHR.size(state, TempSize, ErrorsFound);
    7670         776 :                 state.dataSize->DataDXSpeedNum = 0;
    7671         776 :                 state.dataSize->DataFlowUsedForSizing = 0.0;
    7672         776 :                 state.dataSize->DataCapacityUsedForSizing = 0.0;
    7673         776 :                 state.dataSize->DataEMSOverrideON = false;
    7674         776 :                 state.dataSize->DataEMSOverride = 0.0;
    7675             : 
    7676             :             } // End of Rated SHR
    7677             : 
    7678             :             // Sizing evaporator condenser air flow
    7679        1016 :             if (thisDXCoil.CondenserType(1) == DataHeatBalance::RefrigCondenserType::Evap && thisDXCoil.EvapCondAirFlow(Mode) != 0.0 &&
    7680           0 :                 (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingSingleSpeed || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed ||
    7681           0 :                  thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl)) {
    7682             : 
    7683           0 :                 AutoCalculateSizer sizerEvapCondAirFlow;
    7684           0 :                 std::string stringOverride = "Evaporative Condenser Air Flow Rate [m3/s]";
    7685           0 :                 if (state.dataGlobal->isEpJSON) stringOverride = "evaporative_condenser_air_flow_rate [m3/s]";
    7686           0 :                 if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl) {
    7687           0 :                     CompName = thisDXCoil.Name + ":" + thisDXCoil.CoilPerformanceName(Mode);
    7688             :                 } else {
    7689           0 :                     CompName = thisDXCoil.Name;
    7690           0 :                     if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed) {
    7691           0 :                         stringOverride = "High Speed Evaporative Condenser Air Flow Rate [m3/s]";
    7692           0 :                         if (state.dataGlobal->isEpJSON) stringOverride = "high_speed_evaporative_condenser_air_flow_rate [m3/s]";
    7693             :                     } else {
    7694           0 :                         stringOverride = "Evaporative Condenser Air Flow Rate [m3/s]";
    7695           0 :                         if (state.dataGlobal->isEpJSON) stringOverride = "evaporative_condenser_air_flow_rate [m3/s]";
    7696             :                     }
    7697             :                 }
    7698           0 :                 CompType = thisDXCoil.DXCoilType;
    7699             :                 // Auto-size condenser air flow to Total Capacity * 0.000114 m3/s/w (850 cfm/ton)
    7700           0 :                 state.dataSize->DataConstantUsedForSizing = thisDXCoil.RatedTotCap(Mode);
    7701           0 :                 state.dataSize->DataFractionUsedForSizing = 0.000114;
    7702           0 :                 TempSize = thisDXCoil.EvapCondAirFlow(Mode);
    7703           0 :                 sizerEvapCondAirFlow.overrideSizingString(stringOverride);
    7704           0 :                 sizerEvapCondAirFlow.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7705           0 :                 thisDXCoil.EvapCondAirFlow(Mode) = sizerEvapCondAirFlow.size(state, TempSize, ErrorsFound);
    7706           0 :             }
    7707             : 
    7708        1016 :             if (SizeSecDXCoil) { // autosize secondary coil air flow rate for AirCooled condenser type
    7709           1 :                 IsAutoSize = false;
    7710           1 :                 if (thisDXCoil.SecCoilAirFlow == AutoSize) {
    7711           1 :                     IsAutoSize = true;
    7712             :                 }
    7713             :                 // Autosize Primary Coil Air Flow * Secondary Coil Scaling Factor
    7714           1 :                 SecCoilAirFlowDes = thisDXCoil.RatedAirVolFlowRate(1) * thisDXCoil.SecCoilAirFlowScalingFactor;
    7715           1 :                 if (IsAutoSize) {
    7716           1 :                     thisDXCoil.SecCoilAirFlow = SecCoilAirFlowDes;
    7717           1 :                     BaseSizer::reportSizerOutput(
    7718             :                         state, thisDXCoil.DXCoilType, thisDXCoil.Name, "Design Size Secondary Coil Air Flow Rate [m3/s]", SecCoilAirFlowDes);
    7719             :                 } else {
    7720           0 :                     if (thisDXCoil.SecCoilAirFlow > 0.0 && SecCoilAirFlowDes > 0.0 && !HardSizeNoDesRun) {
    7721           0 :                         SecCoilAirFlowUser = thisDXCoil.SecCoilAirFlow;
    7722           0 :                         BaseSizer::reportSizerOutput(state,
    7723             :                                                      thisDXCoil.DXCoilType,
    7724             :                                                      thisDXCoil.Name,
    7725             :                                                      "Design Size Secondary Coil Air Flow Rate [m3/s]",
    7726             :                                                      SecCoilAirFlowDes,
    7727             :                                                      "User-Specified Secondary Coil Air Flow Rate [m3/s]",
    7728             :                                                      SecCoilAirFlowUser);
    7729           0 :                         if (state.dataGlobal->DisplayExtraWarnings) {
    7730           0 :                             if ((std::abs(SecCoilAirFlowDes - SecCoilAirFlowUser) / SecCoilAirFlowUser) > state.dataSize->AutoVsHardSizingThreshold) {
    7731           0 :                                 ShowMessage(
    7732             :                                     state,
    7733           0 :                                     format("SizeDxCoil: Potential issue with equipment sizing for {} {}", thisDXCoil.DXCoilType, thisDXCoil.Name));
    7734           0 :                                 ShowContinueError(state, format("User-Specified Secondary Coil Air Flow Rate of {:.5R} [m3/s]", SecCoilAirFlowUser));
    7735           0 :                                 ShowContinueError(
    7736           0 :                                     state, format("differs from Design Size Secondary Coil Air Flow Rate of {:.5R} [m3/s]", SecCoilAirFlowDes));
    7737           0 :                                 ShowContinueError(state, "This may, or may not, indicate mismatched component sizes.");
    7738           0 :                                 ShowContinueError(state, "Verify that the value entered is intended and is consistent with other components.");
    7739             :                             }
    7740             :                         }
    7741             :                     }
    7742             :                 }
    7743             :             }
    7744             : 
    7745             :             // Sizing evaporative condenser air flow 2
    7746        1016 :             PrintFlag = true;
    7747        1016 :             if (thisDXCoil.CondenserType(1) == DataHeatBalance::RefrigCondenserType::Evap && thisDXCoil.EvapCondAirFlow2 != 0.0 &&
    7748           0 :                 thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed) {
    7749           0 :                 CompName = thisDXCoil.Name;
    7750           0 :                 FieldNum = 15; // Low Speed Evaporative Condenser Air Flow Rate
    7751           0 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(Mode).FieldNames(FieldNum) + " [m3/s]";
    7752           0 :                 SizingMethod = HVAC::AutoCalculateSizing;
    7753           0 :                 CompType = thisDXCoil.DXCoilType;
    7754             :                 // Autosize low speed condenser air flow to 1/3 Total Capacity * 0.000114 m3/s/w (850 cfm/ton)
    7755           0 :                 state.dataSize->DataConstantUsedForSizing = thisDXCoil.RatedTotCap(Mode);
    7756           0 :                 state.dataSize->DataFractionUsedForSizing = 0.000114 * 0.3333;
    7757           0 :                 TempSize = thisDXCoil.EvapCondAirFlow2;
    7758           0 :                 AutoCalculateSizer sizerEvapCondAirFlow2;
    7759           0 :                 std::string stringOverride = "Low Speed Evaporative Condenser Air Flow Rate [m3/s]";
    7760           0 :                 if (state.dataGlobal->isEpJSON) stringOverride = "low_speed_evaporative_condenser_air_flow_rate [m3/s]";
    7761           0 :                 sizerEvapCondAirFlow2.overrideSizingString(stringOverride);
    7762           0 :                 sizerEvapCondAirFlow2.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7763           0 :                 thisDXCoil.EvapCondAirFlow2 = sizerEvapCondAirFlow2.size(state, TempSize, ErrorsFound);
    7764           0 :             }
    7765             : 
    7766             :             // Sizing evaporative condenser pump electric nominal power
    7767        1016 :             if (thisDXCoil.CondenserType(1) == DataHeatBalance::RefrigCondenserType::Evap && thisDXCoil.EvapCondPumpElecNomPower(Mode) != 0.0 &&
    7768           0 :                 (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingSingleSpeed || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed ||
    7769           0 :                  thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl)) {
    7770             : 
    7771           0 :                 AutoCalculateSizer sizerEvapCondPumpPower;
    7772           0 :                 std::string stringOverride = "Evaporative Condenser Pump Rated Power Consumption [W]";
    7773           0 :                 if (state.dataGlobal->isEpJSON) stringOverride = "evaporative_condenser_pump_rated_power_consumption [W]";
    7774           0 :                 if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl) {
    7775           0 :                     CompName = thisDXCoil.Name + ":" + thisDXCoil.CoilPerformanceName(Mode);
    7776             :                 } else {
    7777           0 :                     CompName = thisDXCoil.Name;
    7778           0 :                     if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed) {
    7779           0 :                         stringOverride = "High Speed Evaporative Condenser Pump Rated Power Consumption [W]";
    7780           0 :                         if (state.dataGlobal->isEpJSON) stringOverride = "high_speed_evaporative_condenser_pump_rated_power_consumption [W]";
    7781             :                     } else {
    7782           0 :                         stringOverride = "Evaporative Condenser Pump Rated Power Consumption [W]";
    7783           0 :                         if (state.dataGlobal->isEpJSON) stringOverride = "evaporative_condenser_pump_rated_power_consumption [W]";
    7784             :                     }
    7785             :                 }
    7786           0 :                 SizingMethod = HVAC::AutoCalculateSizing;
    7787           0 :                 CompType = thisDXCoil.DXCoilType;
    7788             :                 // Autosize high speed evap condenser pump power to Total Capacity * 0.004266 w/w (15 w/ton)
    7789           0 :                 state.dataSize->DataConstantUsedForSizing = thisDXCoil.RatedTotCap(Mode);
    7790           0 :                 state.dataSize->DataFractionUsedForSizing = 0.004266;
    7791           0 :                 TempSize = thisDXCoil.EvapCondPumpElecNomPower(Mode);
    7792           0 :                 sizerEvapCondPumpPower.overrideSizingString(stringOverride);
    7793           0 :                 sizerEvapCondPumpPower.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7794           0 :                 thisDXCoil.EvapCondPumpElecNomPower(Mode) = sizerEvapCondPumpPower.size(state, TempSize, ErrorsFound);
    7795           0 :             }
    7796             : 
    7797             :             // Sizing low speed evaporative condenser pump electric nominal power
    7798        1016 :             if (thisDXCoil.CondenserType(1) == DataHeatBalance::RefrigCondenserType::Evap && thisDXCoil.EvapCondPumpElecNomPower2 != 0.0 &&
    7799           0 :                 thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed) {
    7800           0 :                 CompName = thisDXCoil.Name;
    7801           0 :                 CompType = thisDXCoil.DXCoilType;
    7802             :                 // Autosize low speed evap condenser pump power to 1/3 Total Capacity * 0.004266 w/w (15 w/ton)
    7803           0 :                 state.dataSize->DataConstantUsedForSizing = thisDXCoil.RatedTotCap(Mode);
    7804           0 :                 state.dataSize->DataFractionUsedForSizing = 0.004266 * 0.3333;
    7805           0 :                 TempSize = thisDXCoil.EvapCondPumpElecNomPower2;
    7806           0 :                 AutoCalculateSizer sizerEvapCondPumpPower2;
    7807           0 :                 std::string stringOverride = "Low Speed Evaporative Condenser Pump Rated Power Consumption [W]";
    7808           0 :                 if (state.dataGlobal->isEpJSON) stringOverride = "low_speed_evaporative_condenser_pump_rated_power_consumption [W]";
    7809           0 :                 sizerEvapCondPumpPower2.overrideSizingString(stringOverride);
    7810           0 :                 sizerEvapCondPumpPower2.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7811           0 :                 thisDXCoil.EvapCondPumpElecNomPower2 = sizerEvapCondPumpPower2.size(state, TempSize, ErrorsFound);
    7812           0 :             }
    7813             : 
    7814             :             //                // Sizing rated low speed air flow rate
    7815        1016 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed) {
    7816          67 :                 CompName = thisDXCoil.Name;
    7817          67 :                 CompType = thisDXCoil.DXCoilType;
    7818             :                 // Autosize low speed air flow rate to 1/3 high speed air flow rate
    7819          67 :                 state.dataSize->DataConstantUsedForSizing = thisDXCoil.RatedAirVolFlowRate(Mode);
    7820          67 :                 state.dataSize->DataFractionUsedForSizing = 0.3333;
    7821          67 :                 TempSize = thisDXCoil.RatedAirVolFlowRate2;
    7822          67 :                 AutoCalculateSizer sizerLowSpdAirFlow;
    7823          67 :                 std::string stringOverride = "Low Speed Rated Air Flow Rate [m3/s]";
    7824          67 :                 if (state.dataGlobal->isEpJSON) stringOverride = "low_speed_rated_air_flow_rate [m3/s]";
    7825          67 :                 sizerLowSpdAirFlow.overrideSizingString(stringOverride);
    7826          67 :                 sizerLowSpdAirFlow.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7827          67 :                 thisDXCoil.RatedAirVolFlowRate2 = sizerLowSpdAirFlow.size(state, TempSize, ErrorsFound);
    7828          67 :             }
    7829             : 
    7830             :             //                // Sizing rated low speed total cooling capacity
    7831        1016 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed) {
    7832          67 :                 CompName = thisDXCoil.Name;
    7833          67 :                 CompType = thisDXCoil.DXCoilType;
    7834             :                 // Autosize low speed capacity to 1/3 high speed capacity
    7835          67 :                 state.dataSize->DataConstantUsedForSizing = thisDXCoil.RatedTotCap(Mode);
    7836          67 :                 state.dataSize->DataFractionUsedForSizing = 0.3333;
    7837          67 :                 TempSize = thisDXCoil.RatedTotCap2;
    7838          67 :                 AutoCalculateSizer sizerLowSpdCap;
    7839          67 :                 std::string stringOverride = "Low Speed Gross Rated Total Cooling Capacity [W]";
    7840          67 :                 if (state.dataGlobal->isEpJSON) stringOverride = "low_speed_gross_rated_total_cooling_capacity [W]";
    7841          67 :                 sizerLowSpdCap.overrideSizingString(stringOverride);
    7842          67 :                 sizerLowSpdCap.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7843          67 :                 thisDXCoil.RatedTotCap2 = sizerLowSpdCap.size(state, TempSize, ErrorsFound);
    7844          67 :             }
    7845             : 
    7846        1016 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed) {
    7847          67 :                 if (thisDXCoil.EvapCondAirFlow2 > thisDXCoil.EvapCondAirFlow(Mode)) {
    7848           0 :                     ShowSevereError(
    7849             :                         state,
    7850           0 :                         format("SizeDXCoil: {} {}, Evaporative Condenser low speed air flow must be less than or equal to high speed air flow.",
    7851           0 :                                thisDXCoil.DXCoilType,
    7852           0 :                                thisDXCoil.Name));
    7853           0 :                     ShowContinueError(state, format("Instead, {:.2R} > {:.2R}", thisDXCoil.EvapCondAirFlow2, thisDXCoil.EvapCondAirFlow(Mode)));
    7854           0 :                     ShowFatalError(state, "Preceding conditions cause termination.");
    7855             :                 }
    7856             : 
    7857          67 :                 if (thisDXCoil.EvapCondPumpElecNomPower2 > thisDXCoil.EvapCondPumpElecNomPower(Mode)) {
    7858           0 :                     ShowSevereError(
    7859             :                         state,
    7860           0 :                         format("SizeDXCoil: {} {}, Evaporative Condenser low speed pump power must be less than or equal to high speed pump power.",
    7861           0 :                                thisDXCoil.DXCoilType,
    7862           0 :                                thisDXCoil.Name));
    7863           0 :                     ShowContinueError(
    7864           0 :                         state, format("Instead, {:.2R} > {:.2R}", thisDXCoil.EvapCondPumpElecNomPower2, thisDXCoil.EvapCondPumpElecNomPower(Mode)));
    7865           0 :                     ShowFatalError(state, "Preceding conditions cause termination.");
    7866             :                 }
    7867             : 
    7868          67 :                 if (thisDXCoil.RatedTotCap2 > thisDXCoil.RatedTotCap(Mode)) {
    7869           0 :                     ShowSevereError(state,
    7870           0 :                                     format("SizeDXCoil: {} {}, Rated Total Cooling Capacity, Low Speed must be less than or equal to Rated Total "
    7871             :                                            "Cooling Capacity, High Speed.",
    7872           0 :                                            thisDXCoil.DXCoilType,
    7873           0 :                                            thisDXCoil.Name));
    7874           0 :                     ShowContinueError(state, format("Instead, {:.2R} > {:.2R}", thisDXCoil.RatedTotCap2, thisDXCoil.RatedTotCap(Mode)));
    7875           0 :                     ShowFatalError(state, "Preceding conditions cause termination.");
    7876             :                 }
    7877             : 
    7878          67 :                 if (thisDXCoil.RatedAirVolFlowRate2 > thisDXCoil.RatedAirVolFlowRate(Mode)) {
    7879           0 :                     ShowFatalError(state,
    7880           0 :                                    format("SizeDXCoil: {} {}, Rated Air Volume Flow Rate, low speed must be less than or equal to Rated Air Volume "
    7881             :                                           "Flow Rate, high speed.",
    7882           0 :                                           thisDXCoil.DXCoilType,
    7883           0 :                                           thisDXCoil.Name));
    7884           0 :                     ShowContinueError(state,
    7885           0 :                                       format("Instead, {:.2R} > {:.2R}", thisDXCoil.RatedAirVolFlowRate2, thisDXCoil.RatedAirVolFlowRate(Mode)));
    7886           0 :                     ShowFatalError(state, "Preceding conditions cause termination.");
    7887             :                 }
    7888             :             }
    7889             : 
    7890             :             //                // Sizing rated low speed SHR2
    7891        1016 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed) {
    7892          67 :                 CompName = thisDXCoil.Name;
    7893          67 :                 FieldNum = 7;
    7894          67 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(Mode).FieldNames(FieldNum);
    7895          67 :                 SizingMethod = HVAC::AutoCalculateSizing;
    7896          67 :                 CompType = thisDXCoil.DXCoilType;
    7897             :                 // Autosize low speed SHR to be the same as high speed SHR
    7898          67 :                 state.dataSize->DataConstantUsedForSizing = thisDXCoil.RatedSHR(Mode);
    7899          67 :                 state.dataSize->DataFractionUsedForSizing = 1.0;
    7900          67 :                 state.dataSize->DataDXSpeedNum = 2; // refers to low speed in sizer
    7901          67 :                 bool ErrorsFound = false;
    7902          67 :                 TempSize = thisDXCoil.RatedSHR2;
    7903          67 :                 sizerCoolingSHR.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7904          67 :                 thisDXCoil.RatedSHR2 = sizerCoolingSHR.size(state, TempSize, ErrorsFound);
    7905          67 :                 state.dataSize->DataConstantUsedForSizing = 0.0;
    7906          67 :                 state.dataSize->DataFractionUsedForSizing = 0.0;
    7907          67 :                 state.dataSize->DataDXSpeedNum = 0;
    7908             :             }
    7909             : 
    7910             :             //                // Sizing resistive defrost heater capacity
    7911        1016 :             if (thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_Heating && thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_FluidTCtrl_Heating &&
    7912         954 :                 thisDXCoil.DXCoilType_Num != HVAC::CoilDX_MultiSpeedHeating) {
    7913             :                 // IF (DXCoil(DXCoilNum)%DXCoilType_Num == HVAC::CoilDX_MultiSpeedHeating .OR. &
    7914             :                 //    DXCoil(DXCoilNum)%DXCoilType_Num == Coil_HeatingAirToAirVariableSpeed) THEN
    7915         932 :                 if (thisDXCoil.DefrostStrategy == StandardRatings::DefrostStrat::Resistive) {
    7916          48 :                     CompName = thisDXCoil.Name;
    7917          48 :                     CompType = thisDXCoil.DXCoilType;
    7918             :                     // Autosize low speed capacity to 1/3 high speed capacity
    7919          48 :                     state.dataSize->DataConstantUsedForSizing = state.dataSize->DXCoolCap;
    7920          48 :                     state.dataSize->DataFractionUsedForSizing = 1.0;
    7921          48 :                     TempSize = thisDXCoil.DefrostCapacity;
    7922          48 :                     AutoCalculateSizer sizerResDefCap;
    7923          48 :                     std::string stringOverride = "Resistive Defrost Heater Capacity [W]";
    7924          48 :                     if (state.dataGlobal->isEpJSON) stringOverride = "resistive_defrost_heater_capacity [W]";
    7925          48 :                     sizerResDefCap.overrideSizingString(stringOverride);
    7926          48 :                     sizerResDefCap.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7927          48 :                     thisDXCoil.DefrostCapacity = sizerResDefCap.size(state, TempSize, ErrorsFound);
    7928          48 :                 } else {
    7929         884 :                     thisDXCoil.DefrostCapacity = 0.0;
    7930             :                 }
    7931             :             }
    7932             : 
    7933             :         } // End capacity stages loop
    7934             :     }     // End dehumidification modes loop
    7935             : 
    7936             :     // Autosizing for multispeed cooling coil
    7937         992 :     if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedCooling) {
    7938             :         // flow rate autosize
    7939         162 :         for (Mode = thisDXCoil.NumOfSpeeds; Mode >= 1; --Mode) {
    7940             :             // Sizing multispeed air volume flow rate
    7941         113 :             IsAutoSize = false;
    7942         113 :             if (thisDXCoil.MSRatedAirVolFlowRate(Mode) == AutoSize) {
    7943           7 :                 IsAutoSize = true;
    7944             :             }
    7945         113 :             state.dataSize->DataIsDXCoil = true;
    7946         113 :             CompName = thisDXCoil.Name;
    7947         113 :             CompType = thisDXCoil.DXCoilType;
    7948         113 :             if (Mode == thisDXCoil.NumOfSpeeds) {
    7949          49 :                 FieldNum = 10 + (Mode - 1) * 14;
    7950          49 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames(FieldNum) + " [m3/s]";
    7951          49 :                 TempSize = thisDXCoil.MSRatedAirVolFlowRate(Mode);
    7952          49 :                 state.dataSize->DataEMSOverrideON = thisDXCoil.RatedAirVolFlowRateEMSOverrideON(Mode);
    7953          49 :                 state.dataSize->DataEMSOverride = thisDXCoil.RatedAirVolFlowRateEMSOverrideValue(Mode);
    7954          49 :                 bool errorsFound = false;
    7955          49 :                 CoolingAirFlowSizer sizingCoolingAirFlow;
    7956          49 :                 sizingCoolingAirFlow.overrideSizingString(SizingString);
    7957             :                 // sizingCoolingAirFlow.setHVACSizingIndexData(FanCoil(FanCoilNum).HVACSizingIndex);
    7958          49 :                 sizingCoolingAirFlow.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    7959          49 :                 TempSize = sizingCoolingAirFlow.size(state, TempSize, errorsFound);
    7960          49 :                 thisDXCoil.MSRatedAirVolFlowRate(Mode) = TempSize;
    7961          49 :                 state.dataSize->DataEMSOverrideON = false;
    7962          49 :                 state.dataSize->DataEMSOverride = 0.0;
    7963          49 :                 if (!IsAutoSize && !HardSizeNoDesRun) {
    7964          36 :                     TempSize = AutoSize;
    7965          36 :                     bPRINT = false;
    7966          36 :                     sizingCoolingAirFlow.initializeWithinEP(state, CompType, CompName, bPRINT, RoutineName);
    7967          36 :                     MSRatedAirVolFlowRateDes = sizingCoolingAirFlow.size(state, TempSize, errorsFound);
    7968          36 :                     bPRINT = true;
    7969             :                 }
    7970          49 :                 if (IsAutoSize) {
    7971           2 :                     MSRatedAirVolFlowRateDes = TempSize;
    7972             :                 }
    7973          49 :             } else {
    7974          64 :                 FieldNum = 10 + (Mode - 1) * 14;
    7975          64 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames(FieldNum) + " [m3/s]";
    7976          64 :                 if (IsAutoSize || !HardSizeNoDesRun) {
    7977          41 :                     SizingMethod = HVAC::AutoCalculateSizing;
    7978             :                     // Autosize low speed flow to fraction of the highest speed flow
    7979          41 :                     state.dataSize->DataConstantUsedForSizing = thisDXCoil.MSRatedAirVolFlowRate(thisDXCoil.NumOfSpeeds);
    7980          41 :                     if (!IsAutoSize && !HardSizeNoDesRun) state.dataSize->DataConstantUsedForSizing = MSRatedAirVolFlowRateDes;
    7981          41 :                     state.dataSize->DataFractionUsedForSizing = (float)Mode / thisDXCoil.NumOfSpeeds;
    7982             :                 }
    7983          64 :                 TempSize = thisDXCoil.MSRatedAirVolFlowRate(Mode);
    7984          64 :                 state.dataSize->DataEMSOverrideON = thisDXCoil.RatedAirVolFlowRateEMSOverrideON(Mode);
    7985          64 :                 state.dataSize->DataEMSOverride = thisDXCoil.RatedAirVolFlowRateEMSOverrideValue(Mode);
    7986          64 :                 bool errorsFound = false;
    7987          64 :                 CoolingAirFlowSizer sizingCoolingAirFlow;
    7988          64 :                 sizingCoolingAirFlow.overrideSizingString(SizingString);
    7989          64 :                 sizingCoolingAirFlow.initializeWithinEP(state, CompType, CompName, bPRINT, RoutineName);
    7990          64 :                 thisDXCoil.MSRatedAirVolFlowRate(Mode) = sizingCoolingAirFlow.size(state, TempSize, errorsFound);
    7991          64 :             }
    7992         113 :             state.dataSize->DataEMSOverride = 0.0;
    7993         113 :             state.dataSize->DataEMSOverrideON = false;
    7994         113 :             state.dataSize->DataIsDXCoil = false;
    7995         113 :             state.dataSize->DataTotCapCurveIndex = 0;
    7996         113 :             state.dataSize->DataConstantUsedForSizing = 0.0;
    7997         113 :             state.dataSize->DataFractionUsedForSizing = 0.0;
    7998             :         }
    7999             : 
    8000             :         // Ensure flow rate at lower speed must be lower or equal to the flow rate at higher speed. Otherwise, a severe error is isssued.
    8001         113 :         for (Mode = 1; Mode <= thisDXCoil.NumOfSpeeds - 1; ++Mode) {
    8002          64 :             if (thisDXCoil.MSRatedAirVolFlowRate(Mode) > thisDXCoil.MSRatedAirVolFlowRate(Mode + 1)) {
    8003           0 :                 ShowWarningError(state,
    8004           0 :                                  format("SizeDXCoil: {} {}, Speed {} Rated Air Flow Rate must be less than or equal to Speed {} Rated Air Flow Rate.",
    8005           0 :                                         thisDXCoil.DXCoilType,
    8006           0 :                                         thisDXCoil.Name,
    8007             :                                         Mode,
    8008           0 :                                         Mode + 1));
    8009           0 :                 ShowContinueError(
    8010           0 :                     state, format("Instead, {:.2R} > {:.2R}", thisDXCoil.MSRatedAirVolFlowRate(Mode), thisDXCoil.MSRatedAirVolFlowRate(Mode + 1)));
    8011           0 :                 ShowFatalError(state, "Preceding conditions cause termination.");
    8012             :             }
    8013             :         }
    8014             : 
    8015             :         // Sizing multispeed rated total cooling capacity
    8016         162 :         for (Mode = thisDXCoil.NumOfSpeeds; Mode >= 1; --Mode) {
    8017         113 :             IsAutoSize = false;
    8018         113 :             if (thisDXCoil.MSRatedTotCap(Mode) == AutoSize) {
    8019           7 :                 IsAutoSize = true;
    8020             :             }
    8021         113 :             CompName = thisDXCoil.Name;
    8022         113 :             CompType = thisDXCoil.DXCoilType;
    8023         113 :             state.dataSize->DataIsDXCoil = true;
    8024         113 :             state.dataSize->DataTotCapCurveIndex = thisDXCoil.MSCCapFTemp(Mode);
    8025         113 :             if (Mode == thisDXCoil.NumOfSpeeds) {
    8026          49 :                 PrintFlag = true;
    8027          49 :                 state.dataSize->DataFlowUsedForSizing = thisDXCoil.MSRatedAirVolFlowRate(Mode);
    8028          49 :                 SizingMethod = HVAC::CoolingCapacitySizing;
    8029          49 :                 FieldNum = 7 + (Mode - 1) * 14;
    8030          49 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames(FieldNum) + " [W]";
    8031          49 :                 state.dataSize->DataEMSOverrideON = thisDXCoil.RatedTotCapEMSOverrideOn(Mode);
    8032          49 :                 state.dataSize->DataEMSOverride = thisDXCoil.RatedTotCapEMSOverrideValue(Mode);
    8033          49 :                 MSRatedTotCapDesAtMaxSpeed = thisDXCoil.MSRatedTotCap(Mode);
    8034          49 :                 if (!HardSizeNoDesRun) {
    8035          38 :                     PrintFlag = false;
    8036          38 :                     TempSize = DataSizing::AutoSize;
    8037             :                     // Auto-size capacity at the highest speed
    8038          38 :                     CoolingCapacitySizer sizerCoolingCapacity;
    8039          38 :                     sizerCoolingCapacity.overrideSizingString(SizingString);
    8040          38 :                     sizerCoolingCapacity.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    8041          38 :                     TempSize = sizerCoolingCapacity.size(state, TempSize, ErrorsFound);
    8042          38 :                     SizingMethod = HVAC::AutoCalculateSizing;
    8043          38 :                     state.dataSize->DataConstantUsedForSizing = TempSize;
    8044          38 :                     state.dataSize->DataFractionUsedForSizing = 1.0;
    8045          38 :                     MSRatedTotCapDesAtMaxSpeed = TempSize;
    8046          38 :                     thisDXCoil.MSRatedTotCapDes(Mode) = TempSize;
    8047          38 :                     PrintFlag = true;
    8048          38 :                 }
    8049          49 :                 TempSize = thisDXCoil.MSRatedTotCap(Mode);
    8050          49 :                 CoolingCapacitySizer sizerCoolingCapacity2;
    8051          49 :                 sizerCoolingCapacity2.overrideSizingString(SizingString);
    8052          49 :                 sizerCoolingCapacity2.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    8053          49 :                 TempSize = sizerCoolingCapacity2.size(state, TempSize, ErrorsFound);
    8054          49 :                 thisDXCoil.MSRatedTotCap(Mode) = TempSize;
    8055          49 :                 if (IsAutoSize) {
    8056           2 :                     MSRatedTotCapDesAtMaxSpeed = TempSize;
    8057           2 :                     thisDXCoil.MSRatedTotCapDes(Mode) = TempSize;
    8058             :                 }
    8059          49 :             } else {
    8060             :                 // cooling capacity at lower speeds
    8061          64 :                 PrintFlag = true;
    8062          64 :                 SizingMethod = HVAC::CoolingCapacitySizing;
    8063          64 :                 FieldNum = 7 + (Mode - 1) * 14;
    8064          64 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames(FieldNum) + " [W]";
    8065          64 :                 if (IsAutoSize || !HardSizeNoDesRun) {
    8066          41 :                     SizingMethod = HVAC::AutoCalculateSizing;
    8067             :                     // autosize low speed capacity to fraction of the highest speed capacity
    8068          41 :                     if (!HardSizeNoDesRun) {
    8069          41 :                         state.dataSize->DataConstantUsedForSizing = MSRatedTotCapDesAtMaxSpeed;
    8070             :                     } else {
    8071           0 :                         state.dataSize->DataConstantUsedForSizing = thisDXCoil.MSRatedTotCap(thisDXCoil.NumOfSpeeds);
    8072             :                     }
    8073          41 :                     state.dataSize->DataFractionUsedForSizing = (float)Mode / thisDXCoil.NumOfSpeeds;
    8074          41 :                     thisDXCoil.MSRatedTotCapDes(Mode) = state.dataSize->DataConstantUsedForSizing * state.dataSize->DataFractionUsedForSizing;
    8075             :                 }
    8076          64 :                 TempSize = thisDXCoil.MSRatedTotCap(Mode);
    8077          64 :                 state.dataSize->DataEMSOverrideON = thisDXCoil.RatedTotCapEMSOverrideOn(Mode);
    8078          64 :                 state.dataSize->DataEMSOverride = thisDXCoil.RatedTotCapEMSOverrideValue(Mode);
    8079          64 :                 CoolingCapacitySizer sizerCoolingCapacity;
    8080          64 :                 sizerCoolingCapacity.overrideSizingString(SizingString);
    8081          64 :                 sizerCoolingCapacity.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    8082          64 :                 thisDXCoil.MSRatedTotCap(Mode) = sizerCoolingCapacity.size(state, TempSize, ErrorsFound);
    8083          64 :             }
    8084         113 :             state.dataSize->DataEMSOverride = 0.0;
    8085         113 :             state.dataSize->DataEMSOverrideON = false;
    8086         113 :             state.dataSize->DataIsDXCoil = false;
    8087         113 :             state.dataSize->DataCoolCoilCap = 0.0;
    8088         113 :             state.dataSize->DataTotCapCurveIndex = 0;
    8089         113 :             state.dataSize->DataConstantUsedForSizing = 0.0;
    8090         113 :             state.dataSize->DataFractionUsedForSizing = 0.0;
    8091             :         }
    8092             : 
    8093             :         // Ensure capacity at lower speed must be lower or equal to the capacity at higher speed.
    8094         113 :         for (Mode = 1; Mode <= thisDXCoil.NumOfSpeeds - 1; ++Mode) {
    8095          64 :             if (thisDXCoil.MSRatedTotCap(Mode) > thisDXCoil.MSRatedTotCap(Mode + 1)) {
    8096           0 :                 ShowWarningError(state,
    8097           0 :                                  format("SizeDXCoil: {} {}, Speed {} Rated Total Cooling Capacity must be less than or equal to Speed {} Rated "
    8098             :                                         "Total Cooling Capacity.",
    8099           0 :                                         thisDXCoil.DXCoilType,
    8100           0 :                                         thisDXCoil.Name,
    8101             :                                         Mode,
    8102           0 :                                         Mode + 1));
    8103           0 :                 ShowContinueError(state, format("Instead, {:.2R} > {:.2R}", thisDXCoil.MSRatedTotCap(Mode), thisDXCoil.MSRatedTotCap(Mode + 1)));
    8104           0 :                 ShowFatalError(state, "Preceding conditions cause termination.");
    8105             :             }
    8106             :         }
    8107             : 
    8108             :         // Rated SHR
    8109         162 :         for (Mode = thisDXCoil.NumOfSpeeds; Mode >= 1; --Mode) {
    8110         113 :             IsAutoSize = false;
    8111         113 :             if (thisDXCoil.MSRatedSHR(Mode) == AutoSize) {
    8112           7 :                 IsAutoSize = true;
    8113             :             }
    8114         113 :             if (Mode == thisDXCoil.NumOfSpeeds) {
    8115          49 :                 CompType = thisDXCoil.DXCoilType;
    8116          49 :                 CompName = thisDXCoil.Name;
    8117          49 :                 TempSize = thisDXCoil.MSRatedSHR(Mode);
    8118          49 :                 state.dataSize->DataFlowUsedForSizing = MSRatedAirVolFlowRateDes;
    8119          49 :                 state.dataSize->DataCapacityUsedForSizing = MSRatedTotCapDesAtMaxSpeed;
    8120          49 :                 state.dataSize->DataEMSOverrideON = thisDXCoil.RatedSHREMSOverrideOn(Mode);
    8121          49 :                 state.dataSize->DataEMSOverride = thisDXCoil.RatedSHREMSOverrideValue(Mode);
    8122          49 :                 bool ErrorsFound = false;
    8123          49 :                 state.dataSize->DataDXSpeedNum = Mode;
    8124          49 :                 sizerCoolingSHR.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    8125          49 :                 thisDXCoil.MSRatedSHR(Mode) = sizerCoolingSHR.size(state, TempSize, ErrorsFound);
    8126             :                 // added for rated sensible cooling capacity estimate for html reporting, issue #7381
    8127          49 :                 thisDXCoil.RatedSHR(1) = thisDXCoil.MSRatedSHR(Mode);
    8128             :                 // design SHR value at the maxiumum speed calculated above was supposed to be used for all speeds
    8129             :                 // Now user specified SHR value is used when the SHR field is not autosized and design day run is
    8130             :                 // set to yes unless the code below is commented out
    8131          49 :                 MSRatedSHRDes = thisDXCoil.MSRatedSHR(Mode);
    8132             :             } else {
    8133          64 :                 TempSize = thisDXCoil.MSRatedSHR(Mode);
    8134          64 :                 bool ErrorsFound = false;
    8135          64 :                 state.dataSize->DataDXSpeedNum = Mode;
    8136          64 :                 state.dataSize->DataFractionUsedForSizing = MSRatedSHRDes;
    8137          64 :                 state.dataSize->DataConstantUsedForSizing = 1.0;
    8138          64 :                 sizerCoolingSHR.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    8139          64 :                 thisDXCoil.MSRatedSHR(Mode) = sizerCoolingSHR.size(state, TempSize, ErrorsFound);
    8140             :             }
    8141             :         }
    8142          49 :         state.dataSize->DataFlowUsedForSizing = 0.0;
    8143          49 :         state.dataSize->DataCapacityUsedForSizing = 0.0;
    8144          49 :         state.dataSize->DataEMSOverrideON = false;
    8145          49 :         state.dataSize->DataEMSOverride = 0.0;
    8146          49 :         state.dataSize->DataDXSpeedNum = 0;
    8147          49 :         state.dataSize->DataFractionUsedForSizing = 0.0;
    8148          49 :         state.dataSize->DataConstantUsedForSizing = 0.0;
    8149             : 
    8150             :         // Rated Evapovative condenser airflow rates
    8151         162 :         for (Mode = 1; Mode <= thisDXCoil.NumOfSpeeds; ++Mode) {
    8152         113 :             IsAutoSize = false;
    8153         113 :             if (thisDXCoil.MSEvapCondAirFlow(Mode) == AutoSize) {
    8154           0 :                 IsAutoSize = true;
    8155             :             }
    8156         113 :             if (IsAutoSize || !HardSizeNoDesRun) {
    8157             :                 // Autosize condenser air flow to Total Capacity * 0.000114 m3/s/w (850 cfm/ton)
    8158          79 :                 MSEvapCondAirFlowDes = ((float)Mode / thisDXCoil.NumOfSpeeds) * MSRatedTotCapDesAtMaxSpeed * 0.000114;
    8159             :             } else {
    8160             :                 // this is done to duplicate any existing calc method
    8161          34 :                 MSEvapCondAirFlowDes = thisDXCoil.MSRatedTotCap(Mode) * 0.000114;
    8162             :             }
    8163         113 :             if (IsAutoSize) {
    8164           0 :                 thisDXCoil.MSEvapCondAirFlow(Mode) = MSEvapCondAirFlowDes;
    8165           0 :                 BaseSizer::reportSizerOutput(state,
    8166             :                                              thisDXCoil.DXCoilType,
    8167             :                                              thisDXCoil.Name,
    8168           0 :                                              format("Design Size Speed {} Evaporative Condenser Air Flow Rate [m3/s]", Mode),
    8169             :                                              MSEvapCondAirFlowDes);
    8170             :             } else {
    8171         113 :                 if (thisDXCoil.MSEvapCondAirFlow(Mode) > 0.0 && MSEvapCondAirFlowDes > 0.0 && !HardSizeNoDesRun) {
    8172           8 :                     MSEvapCondAirFlowUser = thisDXCoil.MSEvapCondAirFlow(Mode);
    8173          24 :                     BaseSizer::reportSizerOutput(state,
    8174             :                                                  thisDXCoil.DXCoilType,
    8175             :                                                  thisDXCoil.Name,
    8176          16 :                                                  format("Design Size Speed {} Evaporative Condenser Air Flow Rate [m3/s]", Mode),
    8177             :                                                  MSEvapCondAirFlowDes,
    8178          16 :                                                  format("User-Specified Speed {} Evaporative Condenser Air Flow Rate [m3/s]", Mode),
    8179             :                                                  MSEvapCondAirFlowUser);
    8180           8 :                     if (state.dataGlobal->DisplayExtraWarnings) {
    8181           0 :                         if ((std::abs(MSEvapCondAirFlowDes - MSEvapCondAirFlowUser) / MSEvapCondAirFlowUser) >
    8182           0 :                             state.dataSize->AutoVsHardSizingThreshold) {
    8183           0 :                             ShowMessage(
    8184           0 :                                 state, format("SizeDxCoil: Potential issue with equipment sizing for {} {}", thisDXCoil.DXCoilType, thisDXCoil.Name));
    8185           0 :                             ShowContinueError(state,
    8186           0 :                                               format("User-Specified Evaporative Condenser Air Flow Rate of {:.5R} [m3/s]", MSEvapCondAirFlowUser));
    8187           0 :                             ShowContinueError(
    8188           0 :                                 state, format("differs from Design Size Evaporative Condenser Air Flow Rate of {:.5R} [m3/s]", MSEvapCondAirFlowDes));
    8189           0 :                             ShowContinueError(state, "This may, or may not, indicate mismatched component sizes.");
    8190           0 :                             ShowContinueError(state, "Verify that the value entered is intended and is consistent with other components.");
    8191             :                         }
    8192             :                     }
    8193             :                 }
    8194             :             }
    8195             :         }
    8196             : 
    8197             :         // Ensure evaporative condenser airflow rate at lower speed must be lower or equal to one at higher speed.
    8198         113 :         for (Mode = 1; Mode <= thisDXCoil.NumOfSpeeds - 1; ++Mode) {
    8199          64 :             if (thisDXCoil.MSEvapCondAirFlow(Mode) > thisDXCoil.MSEvapCondAirFlow(Mode + 1)) {
    8200           0 :                 ShowWarningError(state,
    8201           0 :                                  format("SizeDXCoil: {} {}, Speed {} Evaporative Condenser Air Flow Rate must be less than or equal to Speed {} "
    8202             :                                         "Evaporative Condenser Air Flow Rate.",
    8203           0 :                                         thisDXCoil.DXCoilType,
    8204           0 :                                         thisDXCoil.Name,
    8205             :                                         Mode,
    8206           0 :                                         Mode + 1));
    8207           0 :                 ShowContinueError(state,
    8208           0 :                                   format("Instead, {:.2R} > {:.2R}", thisDXCoil.MSEvapCondAirFlow(Mode), thisDXCoil.MSEvapCondAirFlow(Mode + 1)));
    8209           0 :                 ShowFatalError(state, "Preceding conditions cause termination.");
    8210             :             }
    8211             :         }
    8212             : 
    8213             :         // Sizing multispeed rated evapovative condenser pump power
    8214         162 :         for (Mode = 1; Mode <= thisDXCoil.NumOfSpeeds; ++Mode) {
    8215         113 :             IsAutoSize = false;
    8216         113 :             if (thisDXCoil.MSEvapCondPumpElecNomPower(Mode) == AutoSize) {
    8217           0 :                 IsAutoSize = true;
    8218             :             }
    8219             : 
    8220         113 :             if (IsAutoSize || !HardSizeNoDesRun) {
    8221             :                 // Autosize low speed evap condenser pump power to 1/3 Total Capacity * 0.004266 w/w (15 w/ton)
    8222          79 :                 MSEvapCondPumpElecNomPowerDes = ((float)Mode / thisDXCoil.NumOfSpeeds) * MSRatedTotCapDesAtMaxSpeed * 0.004266;
    8223             :             } else {
    8224             :                 // this is done to duplicate any existing calc method
    8225          34 :                 MSEvapCondPumpElecNomPowerDes = thisDXCoil.MSRatedTotCap(Mode) * 0.004266;
    8226             :             }
    8227             :             // Design Size data is always available
    8228         113 :             if (IsAutoSize) {
    8229           0 :                 thisDXCoil.MSEvapCondPumpElecNomPower(Mode) = MSEvapCondPumpElecNomPowerDes;
    8230           0 :                 BaseSizer::reportSizerOutput(state,
    8231             :                                              thisDXCoil.DXCoilType,
    8232             :                                              thisDXCoil.Name,
    8233           0 :                                              format("Design Size Speed {} Rated Evaporative Condenser Pump Power Consumption [W]", Mode),
    8234             :                                              MSEvapCondPumpElecNomPowerDes);
    8235             :             } else {
    8236         113 :                 if (thisDXCoil.MSEvapCondPumpElecNomPower(Mode) > 0.0 && MSEvapCondPumpElecNomPowerDes > 0.0 && !HardSizeNoDesRun) {
    8237           8 :                     MSEvapCondPumpElecNomPowerUser = thisDXCoil.MSEvapCondPumpElecNomPower(Mode);
    8238          24 :                     BaseSizer::reportSizerOutput(state,
    8239             :                                                  thisDXCoil.DXCoilType,
    8240             :                                                  thisDXCoil.Name,
    8241          16 :                                                  format("Design Size Speed {} Rated Evaporative Condenser Pump Power Consumption [W]", Mode),
    8242             :                                                  MSEvapCondPumpElecNomPowerDes,
    8243          16 :                                                  format("User-Specified Speed {} Rated Evaporative Condenser Pump Power Consumption [W]", Mode),
    8244             :                                                  MSEvapCondPumpElecNomPowerUser);
    8245           8 :                     if (state.dataGlobal->DisplayExtraWarnings) {
    8246           0 :                         if ((std::abs(MSEvapCondPumpElecNomPowerDes - MSEvapCondPumpElecNomPowerUser) / MSEvapCondPumpElecNomPowerUser) >
    8247           0 :                             state.dataSize->AutoVsHardSizingThreshold) {
    8248           0 :                             ShowMessage(
    8249           0 :                                 state, format("SizeDxCoil: Potential issue with equipment sizing for {} {}", thisDXCoil.DXCoilType, thisDXCoil.Name));
    8250           0 :                             ShowContinueError(state,
    8251           0 :                                               format("User-Specified Evaporative Condenser Pump Rated Power Consumption of {:.2R} [W]",
    8252             :                                                      MSEvapCondPumpElecNomPowerUser));
    8253           0 :                             ShowContinueError(state,
    8254           0 :                                               format("differs from Design Size Evaporative Condenser Pump Rated Power Consumption of {:.2R} [W]",
    8255             :                                                      MSEvapCondPumpElecNomPowerDes));
    8256           0 :                             ShowContinueError(state, "This may, or may not, indicate mismatched component sizes.");
    8257           0 :                             ShowContinueError(state, "Verify that the value entered is intended and is consistent with other components.");
    8258             :                         }
    8259             :                     }
    8260             :                 }
    8261             :             }
    8262             :         }
    8263             : 
    8264             :         // Ensure evaporative condesner pump power at lower speed must be lower or equal to one at higher speed.
    8265         113 :         for (Mode = 1; Mode <= thisDXCoil.NumOfSpeeds - 1; ++Mode) {
    8266          64 :             if (thisDXCoil.MSEvapCondPumpElecNomPower(Mode) > thisDXCoil.MSEvapCondPumpElecNomPower(Mode + 1)) {
    8267           0 :                 ShowWarningError(state,
    8268           0 :                                  format("SizeDXCoil: {} {}, Speed {} Rated Evaporative Condenser Pump Power Consumption must be less than or "
    8269             :                                         "equal to Speed {} Rated Evaporative Condenser Pump Power Consumption.",
    8270           0 :                                         thisDXCoil.DXCoilType,
    8271           0 :                                         thisDXCoil.Name,
    8272             :                                         Mode,
    8273           0 :                                         Mode + 1));
    8274           0 :                 ShowContinueError(
    8275             :                     state,
    8276           0 :                     format("Instead, {:.2R} > {:.2R}", thisDXCoil.MSEvapCondPumpElecNomPower(Mode), thisDXCoil.MSEvapCondPumpElecNomPower(Mode + 1)));
    8277           0 :                 ShowFatalError(state, "Preceding conditions cause termination.");
    8278             :             }
    8279             :         }
    8280             :     }
    8281             : 
    8282             :     // Autosizing for multispeed heating coil
    8283         992 :     if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedHeating) {
    8284             :         // flow rate autosize
    8285          92 :         for (Mode = thisDXCoil.NumOfSpeeds; Mode >= 1; --Mode) {
    8286          70 :             IsAutoSize = false;
    8287          70 :             if (thisDXCoil.MSRatedAirVolFlowRate(Mode) == AutoSize) {
    8288          32 :                 IsAutoSize = true;
    8289             :             }
    8290          70 :             state.dataSize->DataIsDXCoil = true;
    8291          70 :             CompName = thisDXCoil.Name;
    8292          70 :             CompType = thisDXCoil.DXCoilType;
    8293             :             // Sizing rated air flow rate
    8294          70 :             if (Mode == thisDXCoil.NumOfSpeeds) {
    8295          22 :                 FieldNum = 12 + (Mode - 1) * 6;
    8296          22 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames(FieldNum) + " [m3/s]";
    8297          22 :                 TempSize = thisDXCoil.MSRatedAirVolFlowRate(Mode);
    8298          22 :                 state.dataSize->DataEMSOverrideON = thisDXCoil.RatedAirVolFlowRateEMSOverrideON(Mode);
    8299          22 :                 state.dataSize->DataEMSOverride = thisDXCoil.RatedAirVolFlowRateEMSOverrideValue(Mode);
    8300          22 :                 bool errorsFound = false;
    8301          22 :                 HeatingAirFlowSizer sizingHeatingAirFlow;
    8302          22 :                 sizingHeatingAirFlow.overrideSizingString(SizingString);
    8303             :                 // sizingHeatingAirFlow.setHVACSizingIndexData(FanCoil(FanCoilNum).HVACSizingIndex);
    8304          22 :                 sizingHeatingAirFlow.initializeWithinEP(state, CompType, CompName, bPRINT, RoutineName);
    8305          22 :                 thisDXCoil.MSRatedAirVolFlowRate(Mode) = sizingHeatingAirFlow.size(state, TempSize, errorsFound);
    8306          22 :                 if (!IsAutoSize && !HardSizeNoDesRun) {
    8307           5 :                     TempSize = AutoSize;
    8308           5 :                     bPRINT = false;
    8309           5 :                     errorsFound = false;
    8310           5 :                     HeatingAirFlowSizer sizingHeatingAirFlow2;
    8311           5 :                     sizingHeatingAirFlow2.overrideSizingString(SizingString);
    8312             :                     // sizingHeatingAirFlow.setHVACSizingIndexData(FanCoil(FanCoilNum).HVACSizingIndex);
    8313           5 :                     sizingHeatingAirFlow2.initializeWithinEP(state, CompType, CompName, bPRINT, RoutineName);
    8314           5 :                     MSRatedAirVolFlowRateDes = sizingHeatingAirFlow2.size(state, TempSize, errorsFound);
    8315           5 :                     bPRINT = true;
    8316           5 :                 }
    8317          22 :             } else {
    8318          48 :                 FieldNum = 12 + (Mode - 1) * 6;
    8319          48 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames(FieldNum) + " [m3/s]";
    8320          48 :                 if (IsAutoSize || !HardSizeNoDesRun) {
    8321          31 :                     SizingMethod = HVAC::AutoCalculateSizing;
    8322             :                     // Auto-size low speed flow to fraction of the highest speed capacity
    8323          31 :                     state.dataSize->DataConstantUsedForSizing = thisDXCoil.MSRatedAirVolFlowRate(thisDXCoil.NumOfSpeeds);
    8324          31 :                     if (!IsAutoSize && !HardSizeNoDesRun) state.dataSize->DataConstantUsedForSizing = MSRatedAirVolFlowRateDes;
    8325          31 :                     state.dataSize->DataFractionUsedForSizing = (float)Mode / thisDXCoil.NumOfSpeeds;
    8326             :                 }
    8327          48 :                 TempSize = thisDXCoil.MSRatedAirVolFlowRate(Mode);
    8328          48 :                 bool errorsFound = false;
    8329          48 :                 HeatingAirFlowSizer sizingHeatingAirFlow;
    8330          48 :                 sizingHeatingAirFlow.overrideSizingString(SizingString);
    8331             :                 // sizingHeatingAirFlow.setHVACSizingIndexData(FanCoil(FanCoilNum).HVACSizingIndex);
    8332          48 :                 sizingHeatingAirFlow.initializeWithinEP(state, CompType, CompName, bPRINT, RoutineName);
    8333          48 :                 thisDXCoil.MSRatedAirVolFlowRate(Mode) = sizingHeatingAirFlow.size(state, TempSize, errorsFound);
    8334          48 :             }
    8335          70 :             state.dataSize->DataEMSOverride = 0.0;
    8336          70 :             state.dataSize->DataEMSOverrideON = false;
    8337          70 :             state.dataSize->DataIsDXCoil = false;
    8338          70 :             state.dataSize->DataTotCapCurveIndex = 0;
    8339          70 :             state.dataSize->DataConstantUsedForSizing = 0.0;
    8340          70 :             state.dataSize->DataFractionUsedForSizing = 0.0;
    8341             :         }
    8342             : 
    8343             :         // Ensure flow rate at lower speed must be lower or equal to the flow rate at higher speed. Otherwise, a severe error is isssued.
    8344          70 :         for (Mode = 1; Mode <= thisDXCoil.NumOfSpeeds - 1; ++Mode) {
    8345          48 :             if (thisDXCoil.MSRatedAirVolFlowRate(Mode) > thisDXCoil.MSRatedAirVolFlowRate(Mode + 1)) {
    8346           0 :                 ShowWarningError(state,
    8347           0 :                                  format("SizeDXCoil: {} {}, Speed {} Rated Air Flow Rate must be less than or equal to Speed {} Rated Air Flow Rate.",
    8348           0 :                                         thisDXCoil.DXCoilType,
    8349           0 :                                         thisDXCoil.Name,
    8350             :                                         Mode,
    8351           0 :                                         Mode + 1));
    8352           0 :                 ShowContinueError(
    8353           0 :                     state, format("Instead, {:.2R} > {:.2R}", thisDXCoil.MSRatedAirVolFlowRate(Mode), thisDXCoil.MSRatedAirVolFlowRate(Mode + 1)));
    8354           0 :                 ShowFatalError(state, "Preceding conditions cause termination.");
    8355             :             }
    8356             :         }
    8357             :         // Rated Secondary Coil Airflow Rates for AirCooled condenser type
    8358          22 :         if (thisDXCoil.IsSecondaryDXCoilInZone) {
    8359           0 :             for (Mode = thisDXCoil.NumOfSpeeds; Mode >= 1; --Mode) {
    8360           0 :                 IsAutoSize = false;
    8361           0 :                 if (thisDXCoil.MSSecCoilAirFlow(Mode) == AutoSize) {
    8362           0 :                     IsAutoSize = true;
    8363             :                 }
    8364             :                 // Autosize Primary Coil air flow * Secondary Coil Scaling Factor
    8365           0 :                 SecCoilAirFlowDes = thisDXCoil.MSRatedAirVolFlowRate(Mode) * thisDXCoil.MSSecCoilAirFlowScalingFactor(Mode);
    8366           0 :                 if (IsAutoSize) {
    8367           0 :                     thisDXCoil.MSSecCoilAirFlow(Mode) = SecCoilAirFlowDes;
    8368           0 :                     BaseSizer::reportSizerOutput(state,
    8369             :                                                  thisDXCoil.DXCoilType,
    8370             :                                                  thisDXCoil.Name,
    8371           0 :                                                  format("Design Size Speed {} Secondary Coil Air Flow Rate [m3/s]", Mode),
    8372             :                                                  SecCoilAirFlowDes);
    8373             :                 } else {
    8374           0 :                     if (thisDXCoil.MSSecCoilAirFlow(Mode) > 0.0 && SecCoilAirFlowDes > 0.0 && !HardSizeNoDesRun) {
    8375           0 :                         SecCoilAirFlowUser = thisDXCoil.MSSecCoilAirFlow(Mode);
    8376           0 :                         BaseSizer::reportSizerOutput(state,
    8377             :                                                      thisDXCoil.DXCoilType,
    8378             :                                                      thisDXCoil.Name,
    8379           0 :                                                      format("Design Size Speed {} Secondary Coil Air Flow Rate [m3/s]", Mode),
    8380             :                                                      SecCoilAirFlowDes,
    8381           0 :                                                      format("User-Specified Speed {} Secondary Coil Air Flow Rate [m3/s]", Mode),
    8382             :                                                      SecCoilAirFlowUser);
    8383           0 :                         if (state.dataGlobal->DisplayExtraWarnings) {
    8384           0 :                             if ((std::abs(SecCoilAirFlowDes - SecCoilAirFlowUser) / SecCoilAirFlowUser) > state.dataSize->AutoVsHardSizingThreshold) {
    8385           0 :                                 ShowMessage(
    8386             :                                     state,
    8387           0 :                                     format("SizeDxCoil: Potential issue with equipment sizing for {} {}", thisDXCoil.DXCoilType, thisDXCoil.Name));
    8388           0 :                                 ShowContinueError(state, format("User-Specified Secondary Coil Air Flow Rate of {:.5R} [m3/s]", SecCoilAirFlowUser));
    8389           0 :                                 ShowContinueError(
    8390           0 :                                     state, format("differs from Design Size Secondary Coil Air Flow Rate of {:.5R} [m3/s]", SecCoilAirFlowDes));
    8391           0 :                                 ShowContinueError(state, "This may, or may not, indicate mismatched component sizes.");
    8392           0 :                                 ShowContinueError(state, "Verify that the value entered is intended and is consistent with other components.");
    8393             :                             }
    8394             :                         }
    8395             :                     }
    8396             :                 }
    8397             :             }
    8398             :         }
    8399             : 
    8400             :         // Sizing rated total heating capacity
    8401          92 :         for (Mode = thisDXCoil.NumOfSpeeds; Mode >= 1; --Mode) {
    8402          70 :             IsAutoSize = false;
    8403          70 :             if (thisDXCoil.MSRatedTotCap(Mode) == AutoSize) {
    8404          36 :                 IsAutoSize = true;
    8405             :             }
    8406          70 :             state.dataSize->DataIsDXCoil = true;
    8407          70 :             CompName = thisDXCoil.Name;
    8408          70 :             CompType = thisDXCoil.DXCoilType;
    8409          70 :             if (Mode == thisDXCoil.NumOfSpeeds) {
    8410          22 :                 SizingMethod = HVAC::HeatingCapacitySizing;
    8411          22 :                 state.dataSize->DataFlowUsedForSizing = thisDXCoil.MSRatedAirVolFlowRate(Mode);
    8412          22 :                 FieldNum = 10 + (Mode - 1) * 6;
    8413          22 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames(FieldNum) + " [W]";
    8414          22 :                 state.dataSize->DataTotCapCurveIndex = thisDXCoil.MSCCapFTemp(Mode);
    8415          22 :                 if (IsAutoSize || !HardSizeNoDesRun) {
    8416             :                     // Heating capacity is assumed to be equal to the cooling capacity
    8417          13 :                     PrintFlag = false;
    8418          13 :                     SizingMethod = HVAC::AutoCalculateSizing;
    8419          13 :                     state.dataSize->DataFractionUsedForSizing = 1.0;
    8420          13 :                     if (thisDXCoil.CompanionUpstreamDXCoil > 0) {
    8421           5 :                         NumOfSpeedCompanion = state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).NumOfSpeeds;
    8422           5 :                         state.dataSize->DataConstantUsedForSizing =
    8423           5 :                             state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).MSRatedTotCapDes(NumOfSpeedCompanion);
    8424             :                     } else {
    8425           8 :                         state.dataSize->DataConstantUsedForSizing = thisDXCoil.RatedTotCap(1); // sized above
    8426             :                     }
    8427          13 :                     TempSize = DataSizing::AutoSize;
    8428          13 :                     state.dataSize->DataEMSOverrideON = thisDXCoil.RatedTotCapEMSOverrideOn(Mode);
    8429          13 :                     state.dataSize->DataEMSOverride = thisDXCoil.RatedTotCapEMSOverrideValue(Mode);
    8430          13 :                     HeatingCapacitySizer sizerHeatingCapacity;
    8431          13 :                     sizerHeatingCapacity.overrideSizingString(SizingString);
    8432          13 :                     sizerHeatingCapacity.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    8433          13 :                     MSRatedTotCapDesAtMaxSpeed = sizerHeatingCapacity.size(state, TempSize, ErrorsFound);
    8434          13 :                     SizingMethod = HVAC::AutoCalculateSizing;
    8435          13 :                     state.dataSize->DataConstantUsedForSizing = MSRatedTotCapDesAtMaxSpeed;
    8436          13 :                     state.dataSize->DataFractionUsedForSizing = 1.0;
    8437          13 :                 }
    8438          22 :                 PrintFlag = true;
    8439          22 :                 TempSize = thisDXCoil.MSRatedTotCap(Mode);
    8440          22 :                 state.dataSize->DataEMSOverrideON = thisDXCoil.RatedTotCapEMSOverrideOn(Mode);
    8441          22 :                 state.dataSize->DataEMSOverride = thisDXCoil.RatedTotCapEMSOverrideValue(Mode);
    8442          22 :                 HeatingCapacitySizer sizerHeatingCapacity;
    8443          22 :                 sizerHeatingCapacity.overrideSizingString(SizingString);
    8444          22 :                 sizerHeatingCapacity.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    8445          22 :                 TempSize = sizerHeatingCapacity.size(state, TempSize, ErrorsFound);
    8446          22 :                 thisDXCoil.MSRatedTotCap(Mode) = TempSize;
    8447          22 :                 if (IsAutoSize) {
    8448          10 :                     MSRatedTotCapDesAtMaxSpeed = TempSize;
    8449             :                 }
    8450          22 :             } else {
    8451          48 :                 PrintFlag = true;
    8452          48 :                 SizingMethod = HVAC::HeatingCapacitySizing;
    8453          48 :                 FieldNum = 10 + (Mode - 1) * 6;
    8454          48 :                 SizingString = state.dataDXCoils->DXCoilNumericFields(DXCoilNum).PerfMode(1).FieldNames(FieldNum) + " [W]";
    8455          48 :                 if (IsAutoSize || !HardSizeNoDesRun) {
    8456          31 :                     SizingMethod = HVAC::AutoCalculateSizing;
    8457             :                     // autosize low speed capacity to fraction of the highest speed capacity
    8458          31 :                     if (!HardSizeNoDesRun) {
    8459          31 :                         state.dataSize->DataConstantUsedForSizing = MSRatedTotCapDesAtMaxSpeed;
    8460             :                     } else {
    8461           0 :                         state.dataSize->DataConstantUsedForSizing = thisDXCoil.MSRatedTotCap(thisDXCoil.NumOfSpeeds);
    8462             :                     }
    8463          31 :                     state.dataSize->DataFractionUsedForSizing = (float)Mode / thisDXCoil.NumOfSpeeds;
    8464             :                 }
    8465          48 :                 TempSize = thisDXCoil.MSRatedTotCap(Mode);
    8466          48 :                 state.dataSize->DataEMSOverrideON = thisDXCoil.RatedTotCapEMSOverrideOn(Mode);
    8467          48 :                 state.dataSize->DataEMSOverride = thisDXCoil.RatedTotCapEMSOverrideValue(Mode);
    8468          48 :                 HeatingCapacitySizer sizerHeatingCapacity;
    8469          48 :                 sizerHeatingCapacity.overrideSizingString(SizingString);
    8470          48 :                 sizerHeatingCapacity.initializeWithinEP(state, CompType, CompName, PrintFlag, RoutineName);
    8471          48 :                 TempSize = sizerHeatingCapacity.size(state, TempSize, ErrorsFound);
    8472          48 :                 thisDXCoil.MSRatedTotCap(Mode) = TempSize;
    8473          48 :             }
    8474          70 :             PrintFlag = false;
    8475          70 :             state.dataSize->DataEMSOverrideON = false;
    8476          70 :             state.dataSize->DataEMSOverride = 0.0;
    8477          70 :             state.dataSize->DataIsDXCoil = false;
    8478          70 :             state.dataSize->DataFlowUsedForSizing = 0.0;
    8479          70 :             state.dataSize->DataCoolCoilCap = 0.0;
    8480          70 :             state.dataSize->DataTotCapCurveIndex = 0;
    8481          70 :             state.dataSize->DataConstantUsedForSizing = 0.0;
    8482          70 :             state.dataSize->DataFractionUsedForSizing = 0.0;
    8483             :         }
    8484             :         // Ensure capacity at lower speed must be lower or equal to the capacity at higher speed.
    8485          70 :         for (Mode = 1; Mode <= thisDXCoil.NumOfSpeeds - 1; ++Mode) {
    8486          48 :             if (thisDXCoil.MSRatedTotCap(Mode) > thisDXCoil.MSRatedTotCap(Mode + 1)) {
    8487           0 :                 ShowWarningError(state,
    8488           0 :                                  format("SizeDXCoil: {} {}, Speed {} Rated Total Heating Capacity must be less than or equal to Speed {} Rated "
    8489             :                                         "Total Heating Capacity.",
    8490           0 :                                         thisDXCoil.DXCoilType,
    8491           0 :                                         thisDXCoil.Name,
    8492             :                                         Mode,
    8493           0 :                                         Mode + 1));
    8494           0 :                 ShowContinueError(state, format("Instead, {:.2R} > {:.2R}", thisDXCoil.MSRatedTotCap(Mode), thisDXCoil.MSRatedTotCap(Mode + 1)));
    8495           0 :                 ShowFatalError(state, "Preceding conditions cause termination.");
    8496             :             }
    8497             :         }
    8498             : 
    8499             :         // Resistive Defrost Heater Capacity = capacity at the first stage
    8500             :         // Sizing defrost heater capacity
    8501          22 :         IsAutoSize = false;
    8502          22 :         if (thisDXCoil.DefrostCapacity == AutoSize) {
    8503           8 :             IsAutoSize = true;
    8504             :         }
    8505          22 :         if (thisDXCoil.DefrostStrategy == StandardRatings::DefrostStrat::Resistive) {
    8506           0 :             DefrostCapacityDes = thisDXCoil.MSRatedTotCap(1);
    8507             :         } else {
    8508          22 :             DefrostCapacityDes = 0.0;
    8509             :         }
    8510          22 :         if (IsAutoSize) {
    8511           8 :             thisDXCoil.DefrostCapacity = DefrostCapacityDes;
    8512           8 :             BaseSizer::reportSizerOutput(
    8513             :                 state, thisDXCoil.DXCoilType, thisDXCoil.Name, "Design Size Resistive Defrost Heater Capacity", DefrostCapacityDes);
    8514             :         } else {
    8515          14 :             if (thisDXCoil.DefrostCapacity > 0.0 && DefrostCapacityDes > 0.0 && !HardSizeNoDesRun) {
    8516           0 :                 DefrostCapacityUser = thisDXCoil.DefrostCapacity;
    8517           0 :                 BaseSizer::reportSizerOutput(state,
    8518             :                                              thisDXCoil.DXCoilType,
    8519             :                                              thisDXCoil.Name,
    8520             :                                              "Design Size Resistive Defrost Heater Capacity",
    8521             :                                              DefrostCapacityDes,
    8522             :                                              "User-Specified Resistive Defrost Heater Capacity",
    8523             :                                              DefrostCapacityUser);
    8524           0 :                 if (state.dataGlobal->DisplayExtraWarnings) {
    8525           0 :                     if ((std::abs(DefrostCapacityDes - DefrostCapacityUser) / DefrostCapacityUser) > state.dataSize->AutoVsHardSizingThreshold) {
    8526           0 :                         ShowWarningMessage(
    8527           0 :                             state, format("SizeDxCoil: Potential issue with equipment sizing for {} {}", thisDXCoil.DXCoilType, thisDXCoil.Name));
    8528           0 :                         ShowContinueError(state, format("User-Specified Resistive Defrost Heater Capacity of {:.2R}[W]", DefrostCapacityUser));
    8529           0 :                         ShowContinueError(state,
    8530           0 :                                           format("differs from Design Size Resistive Defrost Heater Capacity of {:.2R}[W]", DefrostCapacityDes));
    8531           0 :                         ShowContinueError(state, "This may, or may not, indicate mismatched component sizes.");
    8532           0 :                         ShowContinueError(state, "Verify that the value entered is intended and is consistent with other components.");
    8533             :                     }
    8534             :                 }
    8535             :             }
    8536             :         }
    8537             :     }
    8538             : 
    8539             :     // Call routine that computes AHRI certified rating for single-speed DX Coils
    8540        2596 :     if ((thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingSingleSpeed &&
    8541         612 :          (thisDXCoil.CondenserType(1) == DataHeatBalance::RefrigCondenserType::Air ||
    8542        1984 :           thisDXCoil.CondenserType(1) == DataHeatBalance::RefrigCondenserType::Evap)) ||
    8543         380 :         thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatingEmpirical) {
    8544        1374 :         CalcDXCoilStandardRating(state,
    8545         687 :                                  thisDXCoil.Name,
    8546         687 :                                  thisDXCoil.DXCoilType,
    8547             :                                  thisDXCoil.DXCoilType_Num,
    8548             :                                  1,
    8549         687 :                                  thisDXCoil.RatedTotCap(1),
    8550         687 :                                  thisDXCoil.RatedCOP(1),
    8551         687 :                                  thisDXCoil.CCapFFlow(1),
    8552         687 :                                  thisDXCoil.CCapFTemp(1),
    8553         687 :                                  thisDXCoil.EIRFFlow(1),
    8554         687 :                                  thisDXCoil.EIRFTemp(1),
    8555         687 :                                  thisDXCoil.PLFFPLR(1),
    8556         687 :                                  thisDXCoil.RatedAirVolFlowRate(1),
    8557         687 :                                  thisDXCoil.FanPowerPerEvapAirFlowRate(1),
    8558         687 :                                  thisDXCoil.FanPowerPerEvapAirFlowRate_2023(1),
    8559         687 :                                  thisDXCoil.CondenserType,
    8560         687 :                                  thisDXCoil.RegionNum,
    8561         687 :                                  thisDXCoil.MinOATCompressor,
    8562         687 :                                  thisDXCoil.OATempCompressorOn,
    8563         687 :                                  thisDXCoil.OATempCompressorOnOffBlank,
    8564         687 :                                  thisDXCoil.DefrostControl,
    8565         687 :                                  thisDXCoil.ASHRAE127StdRprt);
    8566             :     }
    8567             :     // Call routine that computes AHRI certified rating for multi-speed DX cooling Coils
    8568         992 :     if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedCooling || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_MultiSpeedHeating) {
    8569         284 :         CalcDXCoilStandardRating(state,
    8570          71 :                                  thisDXCoil.Name,
    8571          71 :                                  thisDXCoil.DXCoilType,
    8572             :                                  thisDXCoil.DXCoilType_Num,
    8573             :                                  thisDXCoil.NumOfSpeeds,
    8574             :                                  thisDXCoil.MSRatedTotCap,
    8575             :                                  thisDXCoil.MSRatedCOP,
    8576             :                                  thisDXCoil.MSCCapFFlow,
    8577             :                                  thisDXCoil.MSCCapFTemp,
    8578             :                                  thisDXCoil.MSEIRFFlow,
    8579             :                                  thisDXCoil.MSEIRFTemp,
    8580             :                                  thisDXCoil.MSPLFFPLR,
    8581             :                                  thisDXCoil.MSRatedAirVolFlowRate,
    8582             :                                  thisDXCoil.MSFanPowerPerEvapAirFlowRate,
    8583             :                                  thisDXCoil.MSFanPowerPerEvapAirFlowRate_2023,
    8584          71 :                                  thisDXCoil.CondenserType,
    8585          71 :                                  thisDXCoil.RegionNum,
    8586          71 :                                  thisDXCoil.MinOATCompressor,
    8587          71 :                                  thisDXCoil.OATempCompressorOn,
    8588          71 :                                  thisDXCoil.OATempCompressorOnOffBlank,
    8589          71 :                                  thisDXCoil.DefrostControl,
    8590         142 :                                  ObjexxFCL::Optional_bool_const());
    8591             :     }
    8592             : 
    8593         993 :     if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed && (thisDXCoil.CondenserType(1) == DataHeatBalance::RefrigCondenserType::Air ||
    8594           1 :                                                                       thisDXCoil.CondenserType(1) == DataHeatBalance::RefrigCondenserType::Evap)) {
    8595         134 :         StandardRatings::CalcTwoSpeedDXCoilRating(state,
    8596          67 :                                                   thisDXCoil.Name,
    8597          67 :                                                   thisDXCoil.DXCoilType,
    8598             :                                                   thisDXCoil.DXCoilType_Num,
    8599             :                                                   thisDXCoil.RatedTotCap,
    8600             :                                                   thisDXCoil.RatedTotCap2,
    8601             :                                                   thisDXCoil.RatedCOP,
    8602             :                                                   thisDXCoil.RatedCOP2,
    8603             :                                                   thisDXCoil.CCapFFlow, // High Speed
    8604             :                                                   thisDXCoil.CCapFTemp,
    8605             :                                                   thisDXCoil.CCapFTemp2,
    8606             :                                                   thisDXCoil.EIRFFlow, // High Speed
    8607             :                                                   thisDXCoil.EIRFTemp,
    8608             :                                                   thisDXCoil.EIRFTemp2,
    8609             :                                                   thisDXCoil.RatedAirVolFlowRate,
    8610             :                                                   thisDXCoil.RatedAirVolFlowRate2,
    8611             :                                                   thisDXCoil.FanPowerPerEvapAirFlowRate_2023,
    8612             :                                                   thisDXCoil.FanPowerPerEvapAirFlowRate_2023_LowSpeed,
    8613          67 :                                                   thisDXCoil.CondenserType,
    8614          67 :                                                   thisDXCoil.PLFFPLR(1));
    8615             :     }
    8616             : 
    8617             :     // create predefined report entries
    8618         992 :     equipName = thisDXCoil.Name;
    8619             :     // put tables for cooling and heating separate
    8620         992 :     switch (thisDXCoil.DXCoilType_Num) {
    8621         739 :     case HVAC::CoilDX_CoolingSingleSpeed:
    8622             :     case HVAC::CoilDX_CoolingTwoSpeed:
    8623             :     case HVAC::CoilDX_CoolingTwoStageWHumControl:
    8624             :     case HVAC::CoilDX_MultiSpeedCooling: {
    8625         739 :         PreDefTableEntry(state, state.dataOutRptPredefined->pdchCoolCoilType, equipName, thisDXCoil.DXCoilType);
    8626         739 :         if (thisDXCoil.NumOfSpeeds == 0) {
    8627         690 :             if (thisDXCoil.NumCapacityStages == 1) {
    8628         680 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchCoolCoilTotCap, equipName, thisDXCoil.RatedTotCap(1));
    8629        1360 :                 PreDefTableEntry(
    8630         680 :                     state, state.dataOutRptPredefined->pdchCoolCoilSensCap, equipName, thisDXCoil.RatedTotCap(1) * thisDXCoil.RatedSHR(1));
    8631        1360 :                 PreDefTableEntry(state,
    8632         680 :                                  state.dataOutRptPredefined->pdchCoolCoilLatCap,
    8633             :                                  equipName,
    8634         680 :                                  thisDXCoil.RatedTotCap(1) - thisDXCoil.RatedTotCap(1) * thisDXCoil.RatedSHR(1));
    8635         680 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchCoolCoilSHR, equipName, thisDXCoil.RatedSHR(1));
    8636         680 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchCoolCoilNomEff, equipName, thisDXCoil.RatedCOP(1));
    8637             :             } else {
    8638          10 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchCoolCoilTotCap, equipName, thisDXCoil.RatedTotCap(2));
    8639          20 :                 PreDefTableEntry(
    8640          10 :                     state, state.dataOutRptPredefined->pdchCoolCoilSensCap, equipName, thisDXCoil.RatedTotCap(2) * thisDXCoil.RatedSHR(2));
    8641          20 :                 PreDefTableEntry(state,
    8642          10 :                                  state.dataOutRptPredefined->pdchCoolCoilLatCap,
    8643             :                                  equipName,
    8644          10 :                                  thisDXCoil.RatedTotCap(2) - thisDXCoil.RatedTotCap(2) * thisDXCoil.RatedSHR(2));
    8645          10 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchCoolCoilSHR, equipName, thisDXCoil.RatedSHR(2));
    8646          10 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchCoolCoilNomEff, equipName, thisDXCoil.RatedCOP(2));
    8647             :             }
    8648             :         } else {
    8649         162 :             for (Mode = 1; Mode <= thisDXCoil.NumOfSpeeds; ++Mode) {
    8650         113 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchCoolCoilTotCap, equipName, thisDXCoil.MSRatedTotCap(Mode));
    8651         226 :                 PreDefTableEntry(
    8652         113 :                     state, state.dataOutRptPredefined->pdchCoolCoilSensCap, equipName, thisDXCoil.MSRatedTotCap(Mode) * thisDXCoil.MSRatedSHR(Mode));
    8653         226 :                 PreDefTableEntry(state,
    8654         113 :                                  state.dataOutRptPredefined->pdchCoolCoilLatCap,
    8655             :                                  equipName,
    8656         113 :                                  thisDXCoil.MSRatedTotCap(Mode) - thisDXCoil.MSRatedTotCap(Mode) * thisDXCoil.MSRatedSHR(Mode));
    8657         113 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchCoolCoilSHR, equipName, thisDXCoil.MSRatedSHR(Mode));
    8658         113 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchCoolCoilNomEff, equipName, thisDXCoil.MSRatedCOP(Mode));
    8659             :             }
    8660             :         }
    8661        1478 :         addFootNoteSubTable(state,
    8662         739 :                             state.dataOutRptPredefined->pdstCoolCoil,
    8663             :                             "Nominal values are gross at rated conditions, i.e., the supply air fan heat and electric power NOT accounted for.");
    8664         739 :     } break;
    8665         129 :     case HVAC::CoilDX_HeatingEmpirical:
    8666             :     case HVAC::CoilDX_MultiSpeedHeating:
    8667             :     case HVAC::CoilDX_HeatPumpWaterHeaterPumped:
    8668             :     case HVAC::CoilDX_HeatPumpWaterHeaterWrapped: {
    8669         129 :         PreDefTableEntry(state, state.dataOutRptPredefined->pdchHeatCoilType, equipName, thisDXCoil.DXCoilType);
    8670         129 :         if (thisDXCoil.NumOfSpeeds == 0) {
    8671         107 :             if (thisDXCoil.NumCapacityStages == 1) {
    8672         107 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchHeatCoilNomCap, equipName, thisDXCoil.RatedTotCap(1));
    8673         107 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchHeatCoilNomEff, equipName, thisDXCoil.RatedCOP(1));
    8674             :             } else {
    8675           0 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchHeatCoilNomCap, equipName, thisDXCoil.RatedTotCap(2));
    8676           0 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchHeatCoilNomEff, equipName, thisDXCoil.RatedCOP(2));
    8677             :             }
    8678             :         } else {
    8679          92 :             for (Mode = 1; Mode <= thisDXCoil.NumOfSpeeds; ++Mode) {
    8680          70 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchHeatCoilNomCap, equipName, thisDXCoil.MSRatedTotCap(Mode));
    8681          70 :                 PreDefTableEntry(state, state.dataOutRptPredefined->pdchHeatCoilNomEff, equipName, thisDXCoil.MSRatedCOP(Mode));
    8682             :             }
    8683             :         }
    8684         258 :         addFootNoteSubTable(state,
    8685         129 :                             state.dataOutRptPredefined->pdstHeatCoil,
    8686             :                             "Nominal values are gross at rated conditions, i.e., the supply air fan heat and electric power NOT accounted for.");
    8687             : 
    8688             :         // std 229 existing table DX Heating coil new reporting variables
    8689         258 :         OutputReportPredefined::PreDefTableEntry(
    8690         129 :             state, state.dataOutRptPredefined->pdchDXHeatCoilMinOADBTforCompOp, equipName, thisDXCoil.MinOATCompressor);
    8691         258 :         OutputReportPredefined::PreDefTableEntry(state,
    8692         129 :                                                  state.dataOutRptPredefined->pdchDXHeatCoilAirloopName,
    8693             :                                                  equipName,
    8694         258 :                                                  thisDXCoil.AirLoopNum > 0 ? state.dataAirSystemsData->PrimaryAirSystems(thisDXCoil.AirLoopNum).Name
    8695             :                                                                            : "N/A");
    8696             :         // std 229 existing table DX Heating coil 2023 AHRI new reporting variables
    8697         258 :         OutputReportPredefined::PreDefTableEntry(
    8698         129 :             state, state.dataOutRptPredefined->pdchDXHeatCoilMinOADBTforCompOp_2023, equipName, thisDXCoil.MinOATCompressor);
    8699         258 :         OutputReportPredefined::PreDefTableEntry(state,
    8700         129 :                                                  state.dataOutRptPredefined->pdchDXHeatCoilAirloopName_2023,
    8701             :                                                  equipName,
    8702         258 :                                                  thisDXCoil.AirLoopNum > 0 ? state.dataAirSystemsData->PrimaryAirSystems(thisDXCoil.AirLoopNum).Name
    8703             :                                                                            : "N/A");
    8704         129 :     } break;
    8705         124 :     default:
    8706         124 :         break;
    8707             :     }
    8708         992 : }
    8709             : 
    8710     1098657 : void CalcHPWHDXCoil(EnergyPlusData &state,
    8711             :                     int const DXCoilNum,       // the number of the DX coil to be simulated
    8712             :                     Real64 const PartLoadRatio // sensible water heating load / full load sensible water heating capacity
    8713             : )
    8714             : {
    8715             : 
    8716             :     // SUBROUTINE INFORMATION:
    8717             :     //       AUTHOR         Richard Raustad
    8718             :     //       DATE WRITTEN   May 2005
    8719             : 
    8720             :     // PURPOSE OF THIS SUBROUTINE:
    8721             :     // Calculates the gross cooling capacity of a heat pump water heater evaporator and
    8722             :     // heating capacity of the condenser coil given the rated heating capacity and COP.
    8723             : 
    8724             :     // METHODOLOGY EMPLOYED:
    8725             :     // The routine requires the user to enter the total heating capacity and COP for the
    8726             :     // heat pump water heater along with logicals defining if fan and condenser pump are included.
    8727             :     // Since manufacturer's can rate their HPWH equipment with or without including condenser
    8728             :     // pump heat, this information is required to accurately determine the condenser's leaving
    8729             :     // water temperature. In addition, knowledge of the fan heat is required to back into
    8730             :     // a compressor COP.
    8731             : 
    8732             :     // Using/Aliasing
    8733             :     using Curve::CurveValue;
    8734             : 
    8735             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
    8736             :     Real64 RatedHeatingCapacity;     // Water heating rated capacity with or without condenser water pump heat (W)
    8737             :     Real64 RatedHeatingCOP;          // Water heating rated COP with or without evap fan and cond water pump heat (W/W)
    8738             :     Real64 OperatingHeatingCapacity; // Water heating operating capacity including the impact of capacity and COP curves (W)
    8739             :     Real64 OperatingHeatingCOP;      // Water heating operating COP including the impact of capacity and COP curves (W/W)
    8740             :     Real64 OperatingHeatingPower;    // Water heating operating Power (W)
    8741             :     Real64 CompressorPower;          // Power consumed by compressor only (W)
    8742             : 
    8743             :     Real64 TotalTankHeatingCapacity; // Water heating capacity corrected for condenser water pump heat (W)
    8744             :     Real64 TankHeatingCOP;           // Water heating COP corrected for fan and condenser water pump power (W/W)
    8745             :     // (these previous 2 variables also include the impact of capacity and COP curves)
    8746             :     Real64 EvapCoolingCapacity;   // Air cooling capacity corrected for evap fan and cond water pump heat (W)
    8747             :     Real64 InletWaterTemp;        // Condenser water inlet temperature (C)
    8748             :     Real64 OutletWaterTemp;       // Condenser water outlet temperature (C)
    8749             :     Real64 EvapInletMassFlowRate; // Evaporator air inlet mass flow rate (m3/s)
    8750             :     Real64 CondInletMassFlowRate; // Condenser water inlet mass flow rate (m3/s)
    8751             :     Real64 CpWater;               // Specific heat of condenser inlet water (J/Kg/k)
    8752             :     Real64 InletAirTemp;          // HPWH inlet air temperature (dry-bulb or wet-bulb) (C)
    8753             :     Real64 HeatCapFTemp;          // Output of HPWH Heating Capacity as a Function of Temperature curve
    8754             :     Real64 HeatCapFAirFlow;       // Output of HPWH Heating Capacity as a Function of Air Flow Rate Ratio curve
    8755             :     Real64 HeatCapFWaterFlow;     // Output of HPWH Heating Capacity as a Function of Water Flow Rate Ratio curve
    8756             :     Real64 HeatCOPFTemp;          // Output of HPWH COP as a Function of Temperature curve
    8757             :     Real64 HeatCOPFAirFlow;       // Output of HPWH COP as a Function of Air Flow Rate Ratio curve
    8758             :     Real64 HeatCOPFWaterFlow;     // Output of HPWH COP as a Function of Water Flow Rate Ratio curve
    8759             :     Real64 AirFlowRateRatio;      // Ratio of evaporator inlet air mass flow rate to rated mass flow rate
    8760             :     Real64 WaterFlowRateRatio;    // Ratio of evaporator inlet water mass flow rate to rated mass flow rate
    8761             :     Real64 PartLoadFraction;      // Output of Part Load Fraction as a Function of Part Load Ratio curve
    8762             :     Real64 PumpHeatToWater;       // Amount of pump heat attributed to heating water
    8763             :     Real64 HPRTF;                 // Heat pump run time fraction
    8764             : 
    8765             :     // References to Coil and Node struct
    8766     1098657 :     DXCoilData &Coil = state.dataDXCoils->DXCoil(DXCoilNum);
    8767     1098657 :     NodeData &AirInletNode = state.dataLoopNodes->Node(Coil.AirInNode);
    8768     1098657 :     NodeData &WaterInletNode = state.dataLoopNodes->Node(Coil.WaterInNode);
    8769     1098657 :     NodeData &WaterOutletNode = state.dataLoopNodes->Node(Coil.WaterOutNode);
    8770             : 
    8771             :     // If heat pump water heater is OFF, set outlet to inlet and RETURN
    8772             :     // Also set the heating energy rate to zero
    8773     1098657 :     if (PartLoadRatio == 0.0) {
    8774      358458 :         WaterOutletNode = WaterInletNode;
    8775      358458 :         Coil.TotalHeatingEnergyRate = 0.0;
    8776      358458 :         return;
    8777             :     } else {
    8778      740199 :         RatedHeatingCapacity = Coil.RatedTotCap2;
    8779      740199 :         RatedHeatingCOP = Coil.RatedCOP(1);
    8780      740199 :         InletWaterTemp = WaterInletNode.Temp;
    8781      740199 :         CondInletMassFlowRate = WaterInletNode.MassFlowRate / PartLoadRatio;
    8782      740199 :         EvapInletMassFlowRate = AirInletNode.MassFlowRate / PartLoadRatio;
    8783      740199 :         CpWater = CPHW(InletWaterTemp);
    8784      740199 :         CompressorPower = 0.0;
    8785      740199 :         OperatingHeatingPower = 0.0;
    8786      740199 :         TankHeatingCOP = 0.0;
    8787             :     }
    8788             : 
    8789             :     // determine inlet air temperature type for curve objects
    8790      740199 :     if (Coil.InletAirTemperatureType == HVAC::OATType::WetBulb) {
    8791      740199 :         InletAirTemp = state.dataHVACGlobal->HPWHInletWBTemp;
    8792             :     } else {
    8793           0 :         InletAirTemp = state.dataHVACGlobal->HPWHInletDBTemp;
    8794             :     }
    8795             : 
    8796             :     // get output of Heating Capacity and Heating COP curves (curves default to 1 if user has not specified curve name)
    8797      740199 :     if (Coil.HCapFTemp > 0) {
    8798      740199 :         if (state.dataCurveManager->PerfCurve(Coil.HCapFTemp)->numDims == 1) {
    8799           0 :             HeatCapFTemp = CurveValue(state, Coil.HCapFTemp, InletAirTemp);
    8800             :         } else {
    8801      740199 :             HeatCapFTemp = CurveValue(state, Coil.HCapFTemp, InletAirTemp, InletWaterTemp);
    8802             :         }
    8803             :         //   Warn user if curve output goes negative
    8804      740199 :         if (HeatCapFTemp < 0.0) {
    8805           0 :             if (Coil.HCapFTempErrorIndex == 0) {
    8806           0 :                 ShowWarningMessage(state, format("{} \"{}\":", Coil.DXCoilType, Coil.Name));
    8807           0 :                 ShowContinueError(
    8808           0 :                     state, format(" HPWH Heating Capacity Modifier curve (function of temperature) output is negative ({:.3T}).", HeatCapFTemp));
    8809           0 :                 if (state.dataCurveManager->PerfCurve(Coil.HCapFTemp)->numDims == 2) {
    8810           0 :                     ShowContinueError(
    8811             :                         state,
    8812           0 :                         format(" Negative value occurs using an inlet air temperature of {:.1T} and an inlet water temperature of {:.1T}.",
    8813             :                                InletAirTemp,
    8814             :                                InletWaterTemp));
    8815             :                 } else {
    8816           0 :                     ShowContinueError(state, format(" Negative value occurs using an inlet air temperature of {:.1T}.", InletAirTemp));
    8817             :                 }
    8818           0 :                 ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
    8819             :             }
    8820           0 :             ShowRecurringWarningErrorAtEnd(
    8821             :                 state,
    8822           0 :                 Coil.DXCoilType + " \"" + Coil.Name +
    8823             :                     "\": HPWH Heating Capacity Modifier curve (function of temperature) output is negative warning continues...",
    8824           0 :                 Coil.HCapFTempErrorIndex,
    8825             :                 HeatCapFTemp,
    8826             :                 HeatCapFTemp,
    8827             :                 _,
    8828             :                 "[C]",
    8829             :                 "[C]");
    8830           0 :             HeatCapFTemp = 0.0;
    8831             :         }
    8832             :     } else {
    8833           0 :         HeatCapFTemp = 1.0;
    8834             :     }
    8835             : 
    8836      740199 :     if (Coil.HCOPFTemp > 0) {
    8837      740199 :         if (state.dataCurveManager->PerfCurve(Coil.HCOPFTemp)->numDims == 1) {
    8838           0 :             HeatCOPFTemp = CurveValue(state, Coil.HCOPFTemp, InletAirTemp);
    8839             :         } else {
    8840      740199 :             HeatCOPFTemp = CurveValue(state, Coil.HCOPFTemp, InletAirTemp, InletWaterTemp);
    8841             :         }
    8842             :         //   Warn user if curve output goes negative
    8843      740199 :         if (HeatCOPFTemp < 0.0) {
    8844           0 :             if (Coil.HCOPFTempErrorIndex == 0) {
    8845           0 :                 ShowWarningMessage(state, format("{} \"{}\":", Coil.DXCoilType, Coil.Name));
    8846           0 :                 ShowContinueError(state,
    8847           0 :                                   format(" HPWH Heating COP Modifier curve (function of temperature) output is negative ({:.3T}).", HeatCOPFTemp));
    8848           0 :                 if (state.dataCurveManager->PerfCurve(Coil.HCOPFTemp)->numDims == 2) {
    8849           0 :                     ShowContinueError(
    8850             :                         state,
    8851           0 :                         format(" Negative value occurs using an inlet air temperature of {:.1T} and an inlet water temperature of {:.1T}.",
    8852             :                                InletAirTemp,
    8853             :                                InletWaterTemp));
    8854             :                 } else {
    8855           0 :                     ShowContinueError(state, format(" Negative value occurs using an inlet air temperature of {:.1T}.", InletAirTemp));
    8856             :                 }
    8857           0 :                 ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
    8858             :             }
    8859           0 :             ShowRecurringWarningErrorAtEnd(
    8860             :                 state,
    8861           0 :                 Coil.DXCoilType + " \"" + Coil.Name +
    8862             :                     "\": HPWH Heating COP Modifier curve (function of temperature) output is negative warning continues...",
    8863           0 :                 Coil.HCOPFTempErrorIndex,
    8864             :                 HeatCOPFTemp,
    8865             :                 HeatCOPFTemp,
    8866             :                 _,
    8867             :                 "[C]",
    8868             :                 "[C]");
    8869           0 :             HeatCOPFTemp = 0.0;
    8870             :         }
    8871             :     } else {
    8872           0 :         HeatCOPFTemp = 1.0;
    8873             :     }
    8874             : 
    8875      740199 :     if (Coil.HCapFAirFlow > 0) {
    8876           0 :         AirFlowRateRatio = EvapInletMassFlowRate / (Coil.RatedAirMassFlowRate(1));
    8877           0 :         HeatCapFAirFlow = CurveValue(state, Coil.HCapFAirFlow, AirFlowRateRatio);
    8878             :         //   Warn user if curve output goes negative
    8879           0 :         if (HeatCapFAirFlow < 0.0) {
    8880           0 :             if (Coil.HCapFAirFlowErrorIndex == 0) {
    8881           0 :                 ShowWarningMessage(state, format("{} \"{}\":", Coil.DXCoilType, Coil.Name));
    8882           0 :                 ShowContinueError(
    8883             :                     state,
    8884           0 :                     format(" HPWH Heating Capacity Modifier curve (function of air flow fraction) output is negative ({:.3T}).", HeatCapFAirFlow));
    8885           0 :                 ShowContinueError(state, format(" Negative value occurs using an air flow fraction of {:.3T}.", AirFlowRateRatio));
    8886           0 :                 ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
    8887             :             }
    8888           0 :             ShowRecurringWarningErrorAtEnd(
    8889             :                 state,
    8890           0 :                 Coil.DXCoilType + " \"" + Coil.Name +
    8891             :                     "\": HPWH Heating Capacity Modifier curve (function of air flow fraction) output is negative warning continues...",
    8892           0 :                 Coil.HCapFAirFlowErrorIndex,
    8893             :                 HeatCapFAirFlow,
    8894             :                 HeatCapFAirFlow);
    8895           0 :             HeatCapFAirFlow = 0.0;
    8896             :         }
    8897             :     } else {
    8898      740199 :         HeatCapFAirFlow = 1.0;
    8899             :     }
    8900             : 
    8901      740199 :     if (Coil.HCOPFAirFlow > 0) {
    8902           0 :         AirFlowRateRatio = EvapInletMassFlowRate / (Coil.RatedAirMassFlowRate(1));
    8903           0 :         HeatCOPFAirFlow = CurveValue(state, Coil.HCOPFAirFlow, AirFlowRateRatio);
    8904             :         //   Warn user if curve output goes negative
    8905           0 :         if (HeatCOPFAirFlow < 0.0) {
    8906           0 :             if (Coil.HCOPFAirFlowErrorIndex == 0) {
    8907           0 :                 ShowWarningMessage(state, format("{} \"{}\":", Coil.DXCoilType, Coil.Name));
    8908           0 :                 ShowContinueError(
    8909           0 :                     state, format(" HPWH Heating COP Modifier curve (function of air flow fraction) output is negative ({:.3T}).", HeatCOPFAirFlow));
    8910           0 :                 ShowContinueError(state, format(" Negative value occurs using an air flow fraction of {:.3T}.", AirFlowRateRatio));
    8911           0 :                 ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
    8912             :             }
    8913           0 :             ShowRecurringWarningErrorAtEnd(
    8914             :                 state,
    8915           0 :                 Coil.DXCoilType + " \"" + Coil.Name +
    8916             :                     "\": HPWH Heating COP Modifier curve (function of air flow fraction) output is negative warning continues...",
    8917           0 :                 Coil.HCOPFAirFlowErrorIndex,
    8918             :                 HeatCOPFAirFlow,
    8919             :                 HeatCOPFAirFlow);
    8920           0 :             HeatCOPFAirFlow = 0.0;
    8921             :         }
    8922             :     } else {
    8923      740199 :         HeatCOPFAirFlow = 1.0;
    8924             :     }
    8925             : 
    8926      740199 :     if (Coil.HCapFWaterFlow > 0) {
    8927           0 :         WaterFlowRateRatio = CondInletMassFlowRate / (Coil.RatedHPWHCondWaterFlow * RhoH2O(InletWaterTemp));
    8928           0 :         HeatCapFWaterFlow = CurveValue(state, Coil.HCapFWaterFlow, WaterFlowRateRatio);
    8929             :         //   Warn user if curve output goes negative
    8930           0 :         if (HeatCapFWaterFlow < 0.0) {
    8931           0 :             if (Coil.HCapFWaterFlowErrorIndex == 0) {
    8932           0 :                 ShowWarningMessage(state, format("{} \"{}\":", Coil.DXCoilType, Coil.Name));
    8933           0 :                 ShowContinueError(state,
    8934           0 :                                   format(" HPWH Heating Capacity Modifier curve (function of water flow fraction) output is negative ({:.3T}).",
    8935             :                                          HeatCapFWaterFlow));
    8936           0 :                 ShowContinueError(state, format(" Negative value occurs using a water flow fraction of {:.3T}.", WaterFlowRateRatio));
    8937           0 :                 ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
    8938             :             }
    8939           0 :             ShowRecurringWarningErrorAtEnd(
    8940             :                 state,
    8941           0 :                 Coil.DXCoilType + " \"" + Coil.Name +
    8942             :                     "\": HPWH Heating Capacity Modifier curve (function of water flow fraction) output is negative warning continues...",
    8943           0 :                 Coil.HCapFWaterFlowErrorIndex,
    8944             :                 HeatCapFWaterFlow,
    8945             :                 HeatCapFWaterFlow);
    8946           0 :             HeatCapFWaterFlow = 0.0;
    8947             :         }
    8948             :     } else {
    8949      740199 :         HeatCapFWaterFlow = 1.0;
    8950             :     }
    8951             : 
    8952      740199 :     if (Coil.HCOPFWaterFlow > 0) {
    8953           0 :         WaterFlowRateRatio = CondInletMassFlowRate / (Coil.RatedHPWHCondWaterFlow * RhoH2O(InletWaterTemp));
    8954           0 :         HeatCOPFWaterFlow = CurveValue(state, Coil.HCOPFWaterFlow, WaterFlowRateRatio);
    8955             :         //   Warn user if curve output goes negative
    8956           0 :         if (HeatCOPFWaterFlow < 0.0) {
    8957           0 :             if (Coil.HCOPFWaterFlowErrorIndex == 0) {
    8958           0 :                 ShowWarningMessage(state, format("{} \"{}\":", Coil.DXCoilType, Coil.Name));
    8959           0 :                 ShowContinueError(
    8960             :                     state,
    8961           0 :                     format(" HPWH Heating COP Modifier curve (function of water flow fraction) output is negative ({:.3T}).", HeatCOPFWaterFlow));
    8962           0 :                 ShowContinueError(state, format(" Negative value occurs using a water flow fraction of {:.3T}.", WaterFlowRateRatio));
    8963           0 :                 ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
    8964             :             }
    8965           0 :             ShowRecurringWarningErrorAtEnd(
    8966             :                 state,
    8967           0 :                 Coil.DXCoilType + " \"" + Coil.Name +
    8968             :                     "\": HPWH Heating COP Modifier curve (function of water flow fraction) output is negative warning continues...",
    8969           0 :                 Coil.HCOPFWaterFlowErrorIndex,
    8970             :                 HeatCOPFWaterFlow,
    8971             :                 HeatCOPFWaterFlow);
    8972           0 :             HeatCOPFWaterFlow = 0.0;
    8973             :         }
    8974             :     } else {
    8975      740199 :         HeatCOPFWaterFlow = 1.0;
    8976             :     }
    8977             : 
    8978             :     // adjust Heating Capacity and COP for off-design conditions
    8979      740199 :     OperatingHeatingCapacity = RatedHeatingCapacity * HeatCapFTemp * HeatCapFAirFlow * HeatCapFWaterFlow;
    8980      740199 :     OperatingHeatingCOP = RatedHeatingCOP * HeatCOPFTemp * HeatCOPFAirFlow * HeatCOPFWaterFlow;
    8981             : 
    8982      740199 :     if (OperatingHeatingCOP > 0.0) OperatingHeatingPower = OperatingHeatingCapacity / OperatingHeatingCOP;
    8983             : 
    8984      740199 :     PumpHeatToWater = Coil.HPWHCondPumpElecNomPower * Coil.HPWHCondPumpFracToWater;
    8985      740199 :     TankHeatingCOP = OperatingHeatingCOP;
    8986             : 
    8987             :     // account for pump heat if not included in total water heating capacity
    8988      740199 :     if (Coil.CondPumpHeatInCapacity) {
    8989           0 :         TotalTankHeatingCapacity = OperatingHeatingCapacity;
    8990             :     } else {
    8991      740199 :         TotalTankHeatingCapacity = OperatingHeatingCapacity + PumpHeatToWater;
    8992             :     }
    8993             : 
    8994             :     // find part load fraction to calculate RTF
    8995      740199 :     if (Coil.PLFFPLR(1) > 0) {
    8996      740199 :         PartLoadFraction = max(0.7, CurveValue(state, Coil.PLFFPLR(1), PartLoadRatio));
    8997             :     } else {
    8998           0 :         PartLoadFraction = 1.0;
    8999             :     }
    9000             : 
    9001      740199 :     HPRTF = min(1.0, (PartLoadRatio / PartLoadFraction));
    9002             : 
    9003      740199 :     Real64 locFanElecPower = state.dataFans->fans(Coil.SupplyFanIndex)->totalPower;
    9004             : 
    9005             :     // calculate evaporator total cooling capacity
    9006      740199 :     if (HPRTF > 0.0) {
    9007      740199 :         if (Coil.FanPowerIncludedInCOP) {
    9008      420988 :             if (Coil.CondPumpPowerInCOP) {
    9009             :                 //       make sure fan power is full load fan power
    9010           0 :                 CompressorPower = OperatingHeatingPower - locFanElecPower / HPRTF - Coil.HPWHCondPumpElecNomPower;
    9011           0 :                 if (OperatingHeatingPower > 0.0) TankHeatingCOP = TotalTankHeatingCapacity / OperatingHeatingPower;
    9012             :             } else {
    9013      420988 :                 CompressorPower = OperatingHeatingPower - locFanElecPower / HPRTF;
    9014      420988 :                 if ((OperatingHeatingPower + Coil.HPWHCondPumpElecNomPower) > 0.0)
    9015      420988 :                     TankHeatingCOP = TotalTankHeatingCapacity / (OperatingHeatingPower + Coil.HPWHCondPumpElecNomPower);
    9016             :             }
    9017             :         } else {
    9018      319211 :             if (Coil.CondPumpPowerInCOP) {
    9019             :                 //       make sure fan power is full load fan power
    9020           0 :                 CompressorPower = OperatingHeatingPower - Coil.HPWHCondPumpElecNomPower;
    9021           0 :                 if ((OperatingHeatingPower + locFanElecPower / HPRTF) > 0.0)
    9022           0 :                     TankHeatingCOP = TotalTankHeatingCapacity / (OperatingHeatingPower + locFanElecPower / HPRTF);
    9023             :             } else {
    9024      319211 :                 CompressorPower = OperatingHeatingPower;
    9025      319211 :                 if ((OperatingHeatingPower + locFanElecPower / HPRTF + Coil.HPWHCondPumpElecNomPower) > 0.0)
    9026      319211 :                     TankHeatingCOP = TotalTankHeatingCapacity / (OperatingHeatingPower + locFanElecPower / HPRTF + Coil.HPWHCondPumpElecNomPower);
    9027             :             }
    9028             :         }
    9029             :     }
    9030             : 
    9031      740199 :     if (Coil.CondPumpHeatInCapacity) {
    9032           0 :         EvapCoolingCapacity = TotalTankHeatingCapacity - PumpHeatToWater - CompressorPower;
    9033             :     } else {
    9034      740199 :         EvapCoolingCapacity = TotalTankHeatingCapacity - CompressorPower;
    9035             :     }
    9036             : 
    9037             :     // set evaporator total cooling capacity prior to CalcDOE2DXCoil subroutine
    9038      740199 :     Coil.RatedTotCap(1) = EvapCoolingCapacity;
    9039             : 
    9040             :     // determine condenser water inlet/outlet condition at full capacity
    9041      740199 :     if (CondInletMassFlowRate == 0.0) {
    9042      418529 :         OutletWaterTemp = InletWaterTemp;
    9043             :     } else {
    9044      321670 :         OutletWaterTemp = InletWaterTemp + TotalTankHeatingCapacity / (CpWater * CondInletMassFlowRate);
    9045             :     }
    9046             : 
    9047      740199 :     WaterOutletNode.Temp = OutletWaterTemp;
    9048             : 
    9049      740199 :     WaterOutletNode.MassFlowRate = WaterInletNode.MassFlowRate;
    9050             : 
    9051             :     // send heating capacity and COP to water heater module for standards rating calculation
    9052             :     // total heating capacity including condenser pump
    9053      740199 :     state.dataDXCoils->HPWHHeatingCapacity = TotalTankHeatingCapacity;
    9054             :     // total heating COP including compressor, fan, and condenser pump
    9055      740199 :     state.dataDXCoils->HPWHHeatingCOP = TankHeatingCOP;
    9056             : 
    9057             :     // send DX coil total cooling capacity to HPWH for reporting
    9058      740199 :     state.dataHVACGlobal->DXCoilTotalCapacity = EvapCoolingCapacity;
    9059             : 
    9060      740199 :     Coil.TotalHeatingEnergyRate = TotalTankHeatingCapacity * PartLoadRatio;
    9061             : 
    9062             :     // calculate total compressor plus condenser pump power, fan power reported in fan module
    9063      740199 :     Coil.ElecWaterHeatingPower = (CompressorPower + Coil.HPWHCondPumpElecNomPower) * HPRTF;
    9064             : }
    9065             : 
    9066    39594393 : void CalcDoe2DXCoil(EnergyPlusData &state,
    9067             :                     int const DXCoilNum,                                 // the number of the DX coil to be simulated
    9068             :                     HVAC::CompressorOp const compressorOp,               // compressor operation; 1=on, 0=off
    9069             :                     bool const FirstHVACIteration,                       // true if this is the first iteration of HVAC
    9070             :                     Real64 const PartLoadRatio,                          // sensible cooling load / full load sensible cooling capacity
    9071             :                     HVAC::FanOp const fanOp,                             // Allows parent object to control fan operation
    9072             :                     ObjexxFCL::Optional_int_const PerfMode,              // Performance mode for MultiMode DX coil; Always 1 for other coil types
    9073             :                     ObjexxFCL::Optional<Real64 const> OnOffAirFlowRatio, // ratio of compressor on airflow to compressor off airflow
    9074             :                     ObjexxFCL::Optional<Real64 const> CoolingHeatingPLR  // used for cycling fan RH control
    9075             : )
    9076             : {
    9077             : 
    9078             :     // SUBROUTINE INFORMATION:
    9079             :     //       AUTHOR         Fred Buhl
    9080             :     //       DATE WRITTEN   May 2000
    9081             :     //       MODIFIED       Shirey, Feb/October 2001, Feb/Mar 2004
    9082             :     //                      Feb 2005 M. J. Witte, GARD Analytics, Inc.
    9083             :     //                        Add new coil type COIL:DX:MultiMode:CoolingEmpirical:
    9084             :     //                      April 2010 Chandan Sharma, FSEC, Added basin heater
    9085             :     //       RE-ENGINEERED  Don Shirey, Aug/Sept 2000
    9086             : 
    9087             :     // PURPOSE OF THIS SUBROUTINE:
    9088             :     // Calculates the air-side performance and electrical energy use of a direct-
    9089             :     // expansion, air-cooled cooling unit.
    9090             : 
    9091             :     // METHODOLOGY EMPLOYED:
    9092             :     // This routine simulates the performance of air-cooled DX cooling equipment.
    9093             :     // The routine requires the user to enter the total cooling capacity, sensible heat ratio,
    9094             :     // and COP for the unit at ARI 210/240 rating conditions (26.67C [80F] dry-bulb, 19.44C [67F]
    9095             :     // wet-bulb air entering the cooling coil, 35C [95F] dry-bulb air entering the outdoor
    9096             :     // condenser. Since different manufacturer's rate their equipment at different air flow rates,
    9097             :     // the supply air flow rate corresponding to the rated capacities and rated COP must also be
    9098             :     // entered (should be between 300 cfm/ton and 450 cfm/ton). The rated information entered by
    9099             :     // the user should NOT include the thermal or electrical impacts of the supply air fan, as
    9100             :     // this is addressed by another module.
    9101             : 
    9102             :     // With the rated performance data entered by the user, the model employs some of the
    9103             :     // DOE-2.1E curve fits to adjust the capacity and efficiency of the unit as a function
    9104             :     // of entering air temperatures and supply air flow rate (actual vs rated flow). The model
    9105             :     // does NOT employ the exact same methodology to calculate performance as DOE-2, although
    9106             :     // some of the DOE-2 curve fits are employed by this model.
    9107             : 
    9108             :     // The model checks for coil dryout conditions, and adjusts the calculated performance
    9109             :     // appropriately.
    9110             : 
    9111             :     // REFERENCES:
    9112             :     // ASHRAE HVAC 2 Toolkit page 4-81.
    9113             :     // Henderson, H.I. Jr., K. Rengarajan and D.B. Shirey, III. 1992.The impact of comfort
    9114             :     // control on air conditioner energy use in humid climates. ASHRAE Transactions 98(2):
    9115             :     // 104-113.
    9116             :     // Henderson, H.I. Jr., Danny Parker and Y.J. Huang. 2000.Improving DOE-2's RESYS routine:
    9117             :     // User Defined Functions to Provide More Accurate Part Load Energy Use and Humidity
    9118             :     // Predictions. Proceedings of ACEEE Conference.
    9119             : 
    9120             :     // Using/Aliasing
    9121             :     using Curve::CurveValue;
    9122    39594393 :     Real64 SysTimeElapsed = state.dataHVACGlobal->SysTimeElapsed;
    9123    39594393 :     Real64 TimeStepSys = state.dataHVACGlobal->TimeStepSys;
    9124             :     using General::CreateSysTimeIntervalString;
    9125             : 
    9126             :     // SUBROUTINE PARAMETER DEFINITIONS:
    9127             :     static constexpr std::string_view RoutineName("CalcDoe2DXCoil: ");
    9128             :     static constexpr std::string_view calcDoe2DXCoil("CalcDoe2DXCoil");
    9129             : 
    9130             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
    9131             :     Real64 AirMassFlow;       // dry air mass flow rate through coil [kg/s] (adjusted for bypass if any)
    9132             :     Real64 AirMassFlowRatio;  // Ratio of actual air mass flow to rated air mass flow (adjusted for bypass if any)
    9133             :     Real64 AirVolumeFlowRate; // Air volume flow rate across the cooling coil [m3/s] (adjusted for bypass if any)
    9134             :     // (average flow if cycling fan, full flow if constant fan)
    9135             :     Real64 VolFlowperRatedTotCap; // Air volume flow rate divided by rated total cooling capacity [m3/s-W] (adjusted for bypass)
    9136             :     Real64 BypassFlowFraction;    // Fraction of total flow which is bypassed around the cooling coil
    9137             :     Real64 TotCap;                // gross total cooling capacity at off-rated conditions [W]
    9138             :     Real64 TotCapTempModFac;      // Total capacity modifier (function of entering wetbulb, outside drybulb)
    9139             :     Real64 TotCapFlowModFac;      // Total capacity modifier (function of actual supply air flow vs rated flow)
    9140             :     Real64 InletAirWetBulbC;      // wetbulb temperature of inlet air [C]
    9141             :     Real64 InletAirDryBulbTemp;   // inlet air dry bulb temperature [C]
    9142             :     Real64 InletAirEnthalpy;      // inlet air enthalpy [J/kg]
    9143             :     Real64 InletAirHumRat;        // inlet air humidity ratio [kg/kg]
    9144             :     Real64 InletAirHumRatTemp;    // inlet air humidity ratio used in ADP/BF loop [kg/kg]
    9145             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
    9146             :     // REAL(r64) :: InletAirPressure      ! inlet air pressure [Pa]
    9147             :     Real64 RatedCBF;             // coil bypass factor at rated conditions
    9148             :     Real64 SHR;                  // Sensible Heat Ratio (sensible/total) of the cooling coil
    9149             :     Real64 CBF;                  // coil bypass factor at off rated conditions
    9150             :     Real64 A0;                   // NTU * air mass flow rate, used in CBF calculation
    9151             :     Real64 hDelta;               // Change in air enthalpy across the cooling coil [J/kg]
    9152             :     Real64 hADP;                 // Apparatus dew point enthalpy [J/kg]
    9153             :     Real64 hTinwADP;             // Enthalpy at inlet dry-bulb and wADP [J/kg]
    9154             :     Real64 hTinwout;             // Enthalpy at inlet dry-bulb and outlet humidity ratio [J/kg]
    9155             :     Real64 tADP;                 // Apparatus dew point temperature [C]
    9156             :     Real64 wADP;                 // Apparatus dew point humidity ratio [kg/kg]
    9157             :     Real64 FullLoadOutAirEnth;   // outlet full load enthalpy [J/kg]
    9158             :     Real64 FullLoadOutAirHumRat; // outlet humidity ratio at full load
    9159             :     Real64 FullLoadOutAirTemp;   // outlet air temperature at full load [C]
    9160             :     Real64 EIRTempModFac;        // EIR modifier (function of entering wetbulb, outside drybulb)
    9161             :     Real64 EIRFlowModFac;        // EIR modifier (function of actual supply air flow vs rated flow)
    9162             :     Real64 EIR;                  // EIR at part load and off rated conditions
    9163             :     Real64 PLF;                  // Part load factor, accounts for thermal lag at compressor startup, used in power calculation
    9164             :     Real64 QLatActual;           // operating latent capacity of DX coil
    9165             :     Real64 QLatRated;            // Rated latent capacity of DX coil
    9166             :     Real64 SHRUnadjusted;        // SHR prior to latent degradation effective SHR calculation
    9167             :     int Counter;                 // Counter for dry evaporator iterations
    9168             :     int MaxIter;                 // Maximum number of iterations for dry evaporator calculations
    9169             :     Real64 RF;                   // Relaxation factor for dry evaporator iterations
    9170             :     Real64 Tolerance;            // Error tolerance for dry evaporator iterations
    9171             :     Real64 werror;               // Deviation of humidity ratio in dry evaporator iteration loop
    9172             :     Real64 CondInletTemp;        // Condenser inlet temperature (C). Outdoor dry-bulb temp for air-cooled condenser.
    9173             :     // Outdoor Wetbulb +(1 - effectiveness)*(outdoor drybulb - outdoor wetbulb) for evap condenser.
    9174             :     Real64 CondInletHumRat; // Condenser inlet humidity ratio (kg/kg). Zero for air-cooled condenser.
    9175             :     // For evap condenser, its the humidity ratio of the air leaving the evap cooling pads.
    9176             :     Real64 CondAirMassFlow;       // Condenser air mass flow rate [kg/s]
    9177             :     Real64 RhoAir;                // Density of air [kg/m3]
    9178             :     Real64 RhoWater;              // Density of water [kg/m3]
    9179             :     Real64 CrankcaseHeatingPower; // power due to crankcase heater
    9180    39594393 :     Real64 CompAmbTemp(0.0);      // Ambient temperature at compressor
    9181             :     Real64 AirFlowRatio;          // ratio of compressor on airflow to average timestep airflow
    9182             :     // used when constant fan mode yields different air flow rates when compressor is ON and OFF
    9183             :     // (e.g. Packaged Terminal Heat Pump)
    9184             :     Real64 OutdoorDryBulb;  // Outdoor dry-bulb temperature at condenser (C)
    9185             :     Real64 OutdoorWetBulb;  // Outdoor wet-bulb temperature at condenser (C)
    9186             :     Real64 OutdoorHumRat;   // Outdoor humidity ratio at condenser (kg/kg)
    9187             :     Real64 OutdoorPressure; // Outdoor barometric pressure at condenser (Pa)
    9188             : 
    9189             :     int Mode;                    // Performance mode for Multimode DX coil; Always 1 for other coil types
    9190             :     Real64 OutletAirTemp;        // Supply air temperature (average value if constant fan, full output if cycling fan)
    9191             :     Real64 OutletAirHumRat;      // Supply air humidity ratio (average value if constant fan, full output if cycling fan)
    9192             :     Real64 OutletAirEnthalpy;    // Supply air enthalpy (average value if constant fan, full output if cycling fan)
    9193             :     Real64 ADiff;                // Used for exponential
    9194             :     Real64 DXcoolToHeatPLRRatio; // ratio of cooling PLR to heating PLR, used for cycling fan RH control
    9195             :     Real64 HeatRTF;              // heating coil part-load ratio, used for cycling fan RH control
    9196             :     Real64 HeatingCoilPLF;       // heating coil PLF (function of PLR), used for cycling fan RH control
    9197             : 
    9198    39594393 :     auto &DXCT = state.dataHVACGlobal->DXCT;
    9199             : 
    9200             :     // If Performance mode not present, then set to 1.  Used only by Multimode/Multispeed DX coil (otherwise mode = 1)
    9201    39594393 :     if (present(PerfMode)) {
    9202      280657 :         Mode = PerfMode;
    9203             :     } else {
    9204    39313736 :         Mode = 1;
    9205             :     }
    9206             : 
    9207             :     // If AirFlowRatio not present, then set to 1. Used only by DX coils with different air flow
    9208             :     // during cooling and when no cooling is required (constant fan, fan speed changes)
    9209    39594393 :     if (present(OnOffAirFlowRatio)) {
    9210    36196796 :         AirFlowRatio = OnOffAirFlowRatio;
    9211             :     } else {
    9212     3397597 :         AirFlowRatio = 1.0;
    9213             :     }
    9214             : 
    9215             :     // If CoolingHeatingPLR not present, then set to 1. Used for cycling fan systems where
    9216             :     // heating PLR is greater than cooling PLR, otherwise CoolingHeatingPLR = 1.
    9217    39594393 :     if (present(CoolingHeatingPLR)) {
    9218    30229503 :         DXcoolToHeatPLRRatio = CoolingHeatingPLR;
    9219             :     } else {
    9220     9364890 :         DXcoolToHeatPLRRatio = 1.0;
    9221             :     }
    9222             : 
    9223    39594393 :     MaxIter = 30;
    9224    39594393 :     RF = 0.4;
    9225    39594393 :     Counter = 0;
    9226    39594393 :     Tolerance = 0.01;
    9227    39594393 :     CondInletTemp = 0.0;
    9228    39594393 :     CondInletHumRat = 0.0;
    9229             : 
    9230    39594393 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
    9231             : 
    9232    39594393 :     BypassFlowFraction = thisDXCoil.BypassedFlowFrac(Mode);
    9233    39594393 :     AirMassFlow = thisDXCoil.InletAirMassFlowRate * (1.0 - BypassFlowFraction);
    9234    39594393 :     InletAirDryBulbTemp = thisDXCoil.InletAirTemp;
    9235    39594393 :     InletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
    9236    39594393 :     InletAirHumRat = thisDXCoil.InletAirHumRat;
    9237             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
    9238             :     // InletAirPressure    = DXCoil(DXCoilNum)%InletAirPressure
    9239    39594393 :     state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).AvailCapacity = 0.0;
    9240    39594393 :     thisDXCoil.CoolingCoilRuntimeFraction = 0.0;
    9241    39594393 :     thisDXCoil.PartLoadRatio = 0.0;
    9242    39594393 :     thisDXCoil.BasinHeaterPower = 0.0;
    9243             : 
    9244    39594393 :     if (thisDXCoil.CondenserType(Mode) != DataHeatBalance::RefrigCondenserType::WaterHeater) {
    9245    38962549 :         if (thisDXCoil.CondenserInletNodeNum(Mode) != 0) {
    9246     8600936 :             OutdoorPressure = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).Press;
    9247             :             // If node is not connected to anything, pressure = default, use weather data
    9248     8600936 :             if (OutdoorPressure == state.dataLoopNodes->DefaultNodeValues.Press) {
    9249           0 :                 OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
    9250           0 :                 OutdoorHumRat = state.dataEnvrn->OutHumRat;
    9251           0 :                 OutdoorPressure = state.dataEnvrn->OutBaroPress;
    9252           0 :                 OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
    9253             :             } else {
    9254     8600936 :                 OutdoorDryBulb = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).Temp;
    9255     8600936 :                 OutdoorHumRat = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).HumRat;
    9256             :                 // this should use Node%WetBulbTemp or a PSYC function, not OAWB
    9257     8600936 :                 OutdoorWetBulb = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).OutAirWetBulb;
    9258             :             }
    9259             :         } else {
    9260    30361613 :             OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
    9261    30361613 :             OutdoorHumRat = state.dataEnvrn->OutHumRat;
    9262    30361613 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
    9263    30361613 :             OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
    9264             :         }
    9265    38962549 :         if (thisDXCoil.IsSecondaryDXCoilInZone) {
    9266       81926 :             auto &secZoneHB = state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr);
    9267       81926 :             OutdoorDryBulb = secZoneHB.ZT;
    9268       81926 :             OutdoorHumRat = secZoneHB.airHumRat;
    9269       81926 :             OutdoorWetBulb = thisDXCoil.EvapInletWetBulb;
    9270       81926 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
    9271             :         }
    9272             :     } else {
    9273      631844 :         if (thisDXCoil.CondenserInletNodeNum(Mode) != 0) {
    9274      631844 :             OutdoorPressure = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).Press;
    9275             :             // If node is not connected to anything, pressure = default, use weather data
    9276      631844 :             if (OutdoorPressure == state.dataLoopNodes->DefaultNodeValues.Press)
    9277         390 :                 OutdoorPressure = state.dataEnvrn->OutBaroPress; // node not connected
    9278             :         } else {
    9279           0 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
    9280             :         }
    9281             :     }
    9282             : 
    9283    39594393 :     if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Air) {
    9284    38850193 :         CondInletTemp = OutdoorDryBulb; // Outdoor dry-bulb temp
    9285    38850193 :         CompAmbTemp = OutdoorDryBulb;
    9286    38850193 :         if (thisDXCoil.IsSecondaryDXCoilInZone) {
    9287       81926 :             auto &secZoneHB = state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr);
    9288       81926 :             CondInletTemp = secZoneHB.ZT;
    9289       81926 :             CompAmbTemp = CondInletTemp; // assumes compressor is in same location as secondary coil
    9290       81926 :             OutdoorDryBulb = CondInletTemp;
    9291       81926 :             OutdoorHumRat = secZoneHB.airHumRat;
    9292       81926 :             OutdoorWetBulb = thisDXCoil.EvapInletWetBulb;
    9293       81926 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
    9294             :         }
    9295      744200 :     } else if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Evap) {
    9296      112356 :         RhoAir = PsyRhoAirFnPbTdbW(state, OutdoorPressure, OutdoorDryBulb, OutdoorHumRat);
    9297      112356 :         CondAirMassFlow = RhoAir * thisDXCoil.EvapCondAirFlow(Mode);
    9298             :         // (Outdoor wet-bulb temp from DataEnvironment) + (1.0-EvapCondEffectiveness) * (drybulb - wetbulb)
    9299      112356 :         CondInletTemp = OutdoorWetBulb + (OutdoorDryBulb - OutdoorWetBulb) * (1.0 - thisDXCoil.EvapCondEffect(Mode));
    9300      112356 :         CondInletHumRat = PsyWFnTdbTwbPb(state, CondInletTemp, OutdoorWetBulb, OutdoorPressure);
    9301      112356 :         CompAmbTemp = OutdoorDryBulb;
    9302      631844 :     } else if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::WaterHeater) {
    9303      631844 :         CompAmbTemp = state.dataHVACGlobal->HPWHCrankcaseDBTemp;   // Temperature at HP water heater compressor
    9304      631844 :         CondInletTemp = state.dataHVACGlobal->HPWHCrankcaseDBTemp; // Temperature at HP water heater compressor
    9305             :     }
    9306             : 
    9307             :     // Initialize crankcase heater, operates below OAT defined in input deck for HP DX cooling coil
    9308             :     // If used in a heat pump, the value of MaxOAT in the heating coil overrides that in the cooling coil (in GetInput)
    9309    39594393 :     if (CompAmbTemp < thisDXCoil.MaxOATCrankcaseHeater) {
    9310    15293395 :         CrankcaseHeatingPower = thisDXCoil.CrankcaseHeaterCapacity;
    9311    15293395 :         if (thisDXCoil.CrankcaseHeaterCapacityCurveIndex > 0) {
    9312       56165 :             CrankcaseHeatingPower *= Curve::CurveValue(state, thisDXCoil.CrankcaseHeaterCapacityCurveIndex, CompAmbTemp);
    9313             :         }
    9314             :     } else {
    9315    24300998 :         CrankcaseHeatingPower = 0.0;
    9316             :     }
    9317             : 
    9318             :     // calculate end time of current time step to determine if error messages should be printed
    9319    39594393 :     state.dataDXCoils->CurrentEndTime = state.dataGlobal->CurrentTime + SysTimeElapsed;
    9320             : 
    9321             :     //   Print warning messages only when valid and only for the first ocurrance. Let summary provide statistics.
    9322             :     //   Wait for next time step to print warnings. If simulation iterates, print out
    9323             :     //   the warning for the last iteration only. Must wait for next time step to accomplish this.
    9324             :     //   If a warning occurs and the simulation down shifts, the warning is not valid.
    9325             : 
    9326    39594393 :     if (thisDXCoil.PrintLowAmbMessage) { // .AND. &
    9327        5852 :         if (state.dataDXCoils->CurrentEndTime > thisDXCoil.CurrentEndTimeLast && TimeStepSys >= thisDXCoil.TimeStepSysLast) {
    9328         650 :             if (thisDXCoil.LowAmbErrIndex == 0) {
    9329          10 :                 ShowWarningMessage(state, format("{}{}", RoutineName, thisDXCoil.LowAmbBuffer1));
    9330          10 :                 ShowContinueError(state, thisDXCoil.LowAmbBuffer2);
    9331          10 :                 ShowContinueError(state, "... Operation at low ambient temperatures may require special performance curves.");
    9332             :             }
    9333         650 :             if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Air) {
    9334        1950 :                 ShowRecurringWarningErrorAtEnd(state,
    9335        1300 :                                                std::string{RoutineName} + thisDXCoil.DXCoilType + "=\"" + thisDXCoil.Name +
    9336             :                                                    "\" - Low condenser dry-bulb temperature error continues...",
    9337         650 :                                                thisDXCoil.LowAmbErrIndex,
    9338         650 :                                                thisDXCoil.LowTempLast,
    9339         650 :                                                thisDXCoil.LowTempLast,
    9340             :                                                _,
    9341             :                                                "[C]",
    9342             :                                                "[C]");
    9343             :             } else {
    9344           0 :                 ShowRecurringWarningErrorAtEnd(state,
    9345           0 :                                                std::string{RoutineName} + thisDXCoil.DXCoilType + "=\"" + thisDXCoil.Name +
    9346             :                                                    "\" - Low condenser wet-bulb temperature error continues...",
    9347           0 :                                                thisDXCoil.LowAmbErrIndex,
    9348           0 :                                                thisDXCoil.LowTempLast,
    9349           0 :                                                thisDXCoil.LowTempLast,
    9350             :                                                _,
    9351             :                                                "[C]",
    9352             :                                                "[C]");
    9353             :             }
    9354             :         }
    9355             :     }
    9356             : 
    9357    39594393 :     if (thisDXCoil.PrintLowOutTempMessage) {
    9358        4402 :         if (state.dataDXCoils->CurrentEndTime > thisDXCoil.CurrentEndTimeLast && TimeStepSys >= thisDXCoil.TimeStepSysLast) {
    9359         727 :             if (thisDXCoil.LowOutletTempIndex == 0) {
    9360          10 :                 ShowWarningMessage(state, format("{}{}", RoutineName, thisDXCoil.LowOutTempBuffer1));
    9361          10 :                 ShowContinueError(state, thisDXCoil.LowOutTempBuffer2);
    9362          10 :                 ShowContinueError(state, "... Possible reasons for low outlet air dry-bulb temperatures are: This DX coil");
    9363          20 :                 ShowContinueError(state,
    9364          20 :                                   format("   1) may have a low inlet air dry-bulb temperature. Inlet air temperature = {:.3T} C.",
    9365          10 :                                          thisDXCoil.FullLoadInletAirTempLast));
    9366          10 :                 ShowContinueError(state, "   2) may have a low air flow rate per watt of cooling capacity. Check inputs.");
    9367          10 :                 ShowContinueError(state,
    9368             :                                   "   3) is used as part of a HX assisted cooling coil which uses a high sensible effectiveness. Check inputs.");
    9369             :             }
    9370        2181 :             ShowRecurringWarningErrorAtEnd(state,
    9371        1454 :                                            std::string{RoutineName} + thisDXCoil.DXCoilType + "=\"" + thisDXCoil.Name +
    9372             :                                                "\" - Full load outlet temperature indicates a possibility of frost/freeze error continues. "
    9373             :                                                "Outlet air temperature statistics follow:",
    9374         727 :                                            thisDXCoil.LowOutletTempIndex,
    9375         727 :                                            thisDXCoil.FullLoadOutAirTempLast,
    9376         727 :                                            thisDXCoil.FullLoadOutAirTempLast);
    9377             :         }
    9378             :     }
    9379             : 
    9380             :     // save last system time step and last end time of current time step (used to determine if warning is valid)
    9381    39594393 :     thisDXCoil.TimeStepSysLast = TimeStepSys;
    9382    39594393 :     thisDXCoil.CurrentEndTimeLast = state.dataDXCoils->CurrentEndTime;
    9383    39594393 :     thisDXCoil.PrintLowAmbMessage = false;
    9384    39594393 :     thisDXCoil.PrintLowOutTempMessage = false;
    9385             : 
    9386    71191939 :     if ((AirMassFlow > 0.0) &&
    9387    31597546 :         (GetCurrentScheduleValue(state, thisDXCoil.SchedPtr) > 0.0 || thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    9388      309974 :          thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) &&
    9389    86177814 :         (PartLoadRatio > 0.0) && (compressorOp == HVAC::CompressorOp::On) &&
    9390    14985875 :         CompAmbTemp > thisDXCoil.MinOATCompressor) { // criteria for coil operation
    9391    14985875 :         if (fanOp == HVAC::FanOp::Cycling) {
    9392     7430004 :             AirMassFlow /= (PartLoadRatio / DXcoolToHeatPLRRatio);
    9393     7555871 :         } else if (fanOp == HVAC::FanOp::Continuous && thisDXCoil.DXCoilType_Num != HVAC::CoilDX_CoolingTwoSpeed) {
    9394     7555871 :             AirMassFlow *= AirFlowRatio;
    9395             :         } else {
    9396           0 :             AirMassFlow = thisDXCoil.RatedAirMassFlowRate(Mode);
    9397             :         }
    9398             : 
    9399             :         // Check for valid air volume flow per rated total cooling capacity (200 - 500 cfm/ton)
    9400             : 
    9401             :         // for some reason there are diff's when using coil inlet air pressure
    9402             :         // these lines (more to follow) are commented out for the time being
    9403             : 
    9404    14985875 :         InletAirWetBulbC = PsyTwbFnTdbWPb(state, InletAirDryBulbTemp, InletAirHumRat, OutdoorPressure);
    9405    14985875 :         AirVolumeFlowRate = AirMassFlow / PsyRhoAirFnPbTdbW(state, OutdoorPressure, InletAirDryBulbTemp, InletAirHumRat);
    9406             :         //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
    9407             :         //  InletAirWetBulbC = PsyTwbFnTdbWPb(InletAirDryBulbTemp,InletAirHumRat,InletAirPressure)
    9408             :         //  AirVolumeFlowRate = AirMassFlow/ PsyRhoAirFnPbTdbW(InletAirPressure,InletAirDryBulbTemp, InletAirHumRat)
    9409    14985875 :         if (thisDXCoil.RatedTotCap(Mode) <= 0.0) {
    9410           0 :             ShowFatalError(
    9411           0 :                 state, format("{}{}=\"{}\" - Rated total cooling capacity is zero or less.", RoutineName, thisDXCoil.DXCoilType, thisDXCoil.Name));
    9412             :         }
    9413    14985875 :         if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    9414    14863772 :             thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) {
    9415      273402 :             VolFlowperRatedTotCap = AirVolumeFlowRate / thisDXCoil.RatedTotCap2;
    9416             :         } else {
    9417    14712473 :             VolFlowperRatedTotCap = AirVolumeFlowRate / thisDXCoil.RatedTotCap(Mode);
    9418             :         }
    9419     9789732 :         if (!FirstHVACIteration && !state.dataGlobal->WarmupFlag && thisDXCoil.DXCoilType_Num != HVAC::CoilDX_HeatPumpWaterHeaterPumped &&
    9420    26111713 :             thisDXCoil.DXCoilType_Num != HVAC::CoilDX_HeatPumpWaterHeaterWrapped &&
    9421     1336106 :             ((VolFlowperRatedTotCap < HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) ||
    9422     1333620 :              (VolFlowperRatedTotCap > HVAC::MaxCoolVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]))) {
    9423        2486 :             if (thisDXCoil.ErrIndex1 == 0) {
    9424           6 :                 ShowWarningMessage(
    9425             :                     state,
    9426           6 :                     format("{}{}=\"{}\" - Air volume flow rate per watt of rated total cooling capacity is out of range at {:.3R} m3/s/W.",
    9427             :                            RoutineName,
    9428           3 :                            thisDXCoil.DXCoilType,
    9429           3 :                            thisDXCoil.Name,
    9430             :                            VolFlowperRatedTotCap));
    9431           3 :                 ShowContinueErrorTimeStamp(state, "");
    9432           6 :                 ShowContinueError(state,
    9433           6 :                                   format("Expected range for VolumeFlowPerRatedTotalCapacity=[{:.3R}--{:.3R}]",
    9434           3 :                                          HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
    9435           3 :                                          HVAC::MaxCoolVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]));
    9436           3 :                 ShowContinueError(state, "Possible causes include inconsistent air flow rates in system components,");
    9437           3 :                 ShowContinueError(state, "or variable air volume [VAV] system using incorrect coil type.");
    9438             :             }
    9439        7458 :             ShowRecurringWarningErrorAtEnd(
    9440             :                 state,
    9441        4972 :                 std::string{RoutineName} + thisDXCoil.DXCoilType + "=\"" + thisDXCoil.Name +
    9442             :                     "\" - Air volume flow rate per watt of rated total cooling capacity is out of range error continues...",
    9443        2486 :                 thisDXCoil.ErrIndex1,
    9444             :                 VolFlowperRatedTotCap,
    9445             :                 VolFlowperRatedTotCap);
    9446    14983389 :         } else if (!state.dataGlobal->WarmupFlag &&
    9447     2140886 :                    (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    9448    17164443 :                     thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) &&
    9449       58882 :                    ((VolFlowperRatedTotCap < HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) ||
    9450       58882 :                     (VolFlowperRatedTotCap > HVAC::MaxHeatVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]))) {
    9451       29016 :             if (thisDXCoil.ErrIndex1 == 0) {
    9452           2 :                 ShowWarningMessage(
    9453             :                     state,
    9454           2 :                     format("{}{}=\"{}\" - Air volume flow rate per watt of rated total water heating capacity is out of range at {:.2R} m3/s/W.",
    9455             :                            RoutineName,
    9456           1 :                            thisDXCoil.DXCoilType,
    9457           1 :                            thisDXCoil.Name,
    9458             :                            VolFlowperRatedTotCap));
    9459           1 :                 ShowContinueErrorTimeStamp(state, "");
    9460           2 :                 ShowContinueError(state,
    9461           2 :                                   format("Expected range for VolumeFlowPerRatedTotalCapacity=[{:.3R}--{:.3R}]",
    9462           1 :                                          HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
    9463           1 :                                          HVAC::MaxHeatVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]));
    9464           1 :                 ShowContinueError(state,
    9465             :                                   "Possible causes may be that the parent object is calling for an actual supply air flow rate that is much "
    9466             :                                   "higher or lower than the DX coil rated supply air flow rate.");
    9467             :             }
    9468       87048 :             ShowRecurringWarningErrorAtEnd(
    9469             :                 state,
    9470       58032 :                 std::string{RoutineName} + thisDXCoil.DXCoilType + "=\"" + thisDXCoil.Name +
    9471             :                     "\" - Air volume flow rate per watt of rated total water heating capacity is out of range error continues...",
    9472       29016 :                 thisDXCoil.ErrIndex1,
    9473             :                 VolFlowperRatedTotCap,
    9474             :                 VolFlowperRatedTotCap);
    9475             :         }
    9476             :         //    Adjust coil bypass factor for actual air flow rate. Use relation CBF = exp(-NTU) where
    9477             :         //    NTU = A0/(m*cp). Relationship models the cooling coil as a heat exchanger with Cmin/Cmax = 0.
    9478             : 
    9479    14985875 :         RatedCBF = thisDXCoil.RatedCBF(Mode);
    9480    14985875 :         if (RatedCBF > 0.0) {
    9481    14985875 :             A0 = -std::log(RatedCBF) * thisDXCoil.RatedAirMassFlowRate(Mode);
    9482             :         } else {
    9483           0 :             A0 = 0.0;
    9484             :         }
    9485    14985875 :         ADiff = -A0 / AirMassFlow;
    9486    14985875 :         if (ADiff >= DataPrecisionGlobals::EXP_LowerLimit) {
    9487    14963247 :             CBF = std::exp(ADiff);
    9488             :         } else {
    9489       22628 :             CBF = 0.0;
    9490             :         }
    9491             : 
    9492             :         //   check boundary for low ambient temperature and post warnings to individual DX coil buffers to print at end of time step
    9493    14985875 :         if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Air) {
    9494    14667487 :             if (OutdoorDryBulb < 0.0 && !state.dataGlobal->WarmupFlag) { // Same threshold as for air-cooled electric chiller
    9495        5852 :                 thisDXCoil.PrintLowAmbMessage = true;
    9496        5852 :                 thisDXCoil.LowTempLast = OutdoorDryBulb;
    9497        5852 :                 if (thisDXCoil.LowAmbErrIndex == 0) {
    9498             :                     thisDXCoil.LowAmbBuffer1 =
    9499         244 :                         format("{} \"{}\" - Air-cooled condenser inlet dry-bulb temperature below 0 C. Outdoor dry-bulb temperature = {:.2R}",
    9500         122 :                                thisDXCoil.DXCoilType,
    9501         122 :                                thisDXCoil.Name,
    9502         122 :                                OutdoorDryBulb);
    9503         244 :                     thisDXCoil.LowAmbBuffer2 = " ... Occurrence info = " + state.dataEnvrn->EnvironmentName + ", " + state.dataEnvrn->CurMnDy + ' ' +
    9504         366 :                                                CreateSysTimeIntervalString(state);
    9505             :                 }
    9506             :             }
    9507      318388 :         } else if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Evap) {
    9508       44986 :             if (OutdoorWetBulb < 10.0 && !state.dataGlobal->WarmupFlag) { // Same threshold as for evap-cooled electric chiller
    9509           0 :                 thisDXCoil.PrintLowAmbMessage = true;
    9510           0 :                 thisDXCoil.LowTempLast = OutdoorWetBulb;
    9511           0 :                 if (thisDXCoil.LowAmbErrIndex == 0) {
    9512             :                     thisDXCoil.LowAmbBuffer1 =
    9513           0 :                         format("{} \"{}\" - Evap-cooled condenser inlet wet-bulb temperature below 10 C. Outdoor wet-bulb temperature = {:.2R}",
    9514           0 :                                thisDXCoil.DXCoilType,
    9515           0 :                                thisDXCoil.Name,
    9516           0 :                                OutdoorWetBulb);
    9517           0 :                     thisDXCoil.LowAmbBuffer2 = " ... Occurrence info = " + state.dataEnvrn->EnvironmentName + ", " + state.dataEnvrn->CurMnDy + ' ' +
    9518           0 :                                                CreateSysTimeIntervalString(state);
    9519             :                 }
    9520             :             }
    9521             :         }
    9522             : 
    9523             :         //  Get total capacity modifying factor (function of temperature) for off-rated conditions
    9524             :         //  InletAirHumRat may be modified in this ADP/BF loop, use temporary varible for calculations
    9525    14985875 :         InletAirHumRatTemp = InletAirHumRat;
    9526    14985875 :         AirMassFlowRatio = AirMassFlow / thisDXCoil.RatedAirMassFlowRate(Mode);
    9527             :         while (true) {
    9528    23920519 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    9529    23798416 :                 thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) {
    9530             :                 // Coil:DX:HeatPumpWaterHeater does not have total cooling capacity as a function of temp or flow curve
    9531      547615 :                 TotCapTempModFac = 1.0;
    9532      547615 :                 TotCapFlowModFac = 1.0;
    9533             :             } else {
    9534    23372904 :                 if (state.dataCurveManager->PerfCurve(thisDXCoil.CCapFTemp(Mode))->numDims == 2) {
    9535    23372904 :                     TotCapTempModFac = CurveValue(state, thisDXCoil.CCapFTemp(Mode), InletAirWetBulbC, CondInletTemp);
    9536             :                 } else {
    9537           0 :                     TotCapTempModFac = CurveValue(state, thisDXCoil.CCapFTemp(Mode), CondInletTemp);
    9538             :                 }
    9539             : 
    9540             :                 //    Warn user if curve output goes negative
    9541    23372904 :                 if (TotCapTempModFac < 0.0) {
    9542           0 :                     if (thisDXCoil.CCapFTempErrorIndex == 0) {
    9543           0 :                         ShowWarningMessage(state, format("{}{} \"{}\":", RoutineName, thisDXCoil.DXCoilType, thisDXCoil.Name));
    9544           0 :                         ShowContinueError(state,
    9545           0 :                                           format(" Total Cooling Capacity Modifier curve (function of temperature) output is negative ({:.3T}).",
    9546             :                                                  TotCapTempModFac));
    9547           0 :                         if (state.dataCurveManager->PerfCurve(thisDXCoil.CCapFTemp(Mode))->numDims == 2) {
    9548           0 :                             ShowContinueError(state,
    9549           0 :                                               format(" Negative value occurs using a condenser inlet air temperature of {:.1T} and an inlet air "
    9550             :                                                      "wet-bulb temperature of {:.1T}.",
    9551             :                                                      CondInletTemp,
    9552             :                                                      InletAirWetBulbC));
    9553             :                         } else {
    9554           0 :                             ShowContinueError(state,
    9555           0 :                                               format(" Negative value occurs using a condenser inlet air temperature of {:.1T}.", CondInletTemp));
    9556             :                         }
    9557           0 :                         if (Mode > 1) {
    9558           0 :                             ShowContinueError(state, format(" Negative output results from stage {} compressor operation.", Mode));
    9559             :                         }
    9560           0 :                         ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
    9561             :                     }
    9562           0 :                     ShowRecurringWarningErrorAtEnd(
    9563             :                         state,
    9564           0 :                         std::string{RoutineName} + thisDXCoil.DXCoilType + " \"" + thisDXCoil.Name +
    9565             :                             "\": Total Cooling Capacity Modifier curve (function of temperature) output is negative warning continues...",
    9566           0 :                         thisDXCoil.CCapFTempErrorIndex,
    9567             :                         TotCapTempModFac,
    9568             :                         TotCapTempModFac);
    9569           0 :                     TotCapTempModFac = 0.0;
    9570             :                 }
    9571             : 
    9572             :                 //    Get total capacity modifying factor (function of mass flow) for off-rated conditions
    9573    23372904 :                 TotCapFlowModFac = CurveValue(state, thisDXCoil.CCapFFlow(Mode), AirMassFlowRatio);
    9574             :                 //    Warn user if curve output goes negative
    9575    23372904 :                 if (TotCapFlowModFac < 0.0) {
    9576           0 :                     if (thisDXCoil.CCapFFlowErrorIndex == 0) {
    9577           0 :                         ShowWarningMessage(state, format("{}{} \"{}\":", RoutineName, thisDXCoil.DXCoilType, thisDXCoil.Name));
    9578           0 :                         ShowContinueError(state,
    9579           0 :                                           format(" Total Cooling Capacity Modifier curve (function of flow fraction) output is negative ({:.3T}).",
    9580             :                                                  TotCapFlowModFac));
    9581           0 :                         ShowContinueError(state, format(" Negative value occurs using an air flow fraction of {:.3T}.", AirMassFlowRatio));
    9582           0 :                         ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
    9583           0 :                         if (Mode > 1) {
    9584           0 :                             ShowContinueError(state, format(" Negative output results from stage {} compressor operation.", Mode));
    9585             :                         }
    9586             :                     }
    9587           0 :                     ShowRecurringWarningErrorAtEnd(
    9588             :                         state,
    9589           0 :                         std::string{RoutineName} + thisDXCoil.DXCoilType + " \"" + thisDXCoil.Name +
    9590             :                             "\": Total Cooling Capacity Modifier curve (function of flow fraction) output is negative warning continues...",
    9591           0 :                         thisDXCoil.CCapFFlowErrorIndex,
    9592             :                         TotCapFlowModFac,
    9593             :                         TotCapFlowModFac);
    9594           0 :                     TotCapFlowModFac = 0.0;
    9595             :                 }
    9596             :             }
    9597    23920519 :             TotCap = thisDXCoil.RatedTotCap(Mode) * TotCapFlowModFac * TotCapTempModFac;
    9598             :             // if user specified SHR modifier curves are available calculate the SHR as follows:
    9599    23920519 :             if (thisDXCoil.UserSHRCurveExists) {
    9600           0 :                 SHR = CalcSHRUserDefinedCurves(state,
    9601             :                                                InletAirDryBulbTemp,
    9602             :                                                InletAirWetBulbC,
    9603             :                                                AirMassFlowRatio,
    9604           0 :                                                thisDXCoil.SHRFTemp(Mode),
    9605           0 :                                                thisDXCoil.SHRFFlow(Mode),
    9606           0 :                                                thisDXCoil.RatedSHR(Mode));
    9607           0 :                 hDelta = TotCap / AirMassFlow;
    9608           0 :                 break;
    9609             :             } else {
    9610             :                 // Calculate apparatus dew point conditions using TotCap and CBF
    9611    23920519 :                 hDelta = TotCap / AirMassFlow;
    9612    23920519 :                 hADP = InletAirEnthalpy - hDelta / (1.0 - CBF);
    9613    23920519 :                 tADP = PsyTsatFnHPb(state, hADP, OutdoorPressure, calcDoe2DXCoil);
    9614             :                 //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
    9615             :                 //  tADP = PsyTsatFnHPb(hADP,InletAirPressure)
    9616    23920519 :                 wADP = PsyWFnTdbH(state, tADP, hADP, calcDoe2DXCoil);
    9617    23920519 :                 hTinwADP = PsyHFnTdbW(InletAirDryBulbTemp, wADP);
    9618    23920519 :                 if ((InletAirEnthalpy - hADP) > 1.e-10) {
    9619    23920519 :                     SHR = min((hTinwADP - hADP) / (InletAirEnthalpy - hADP), 1.0);
    9620             :                 } else {
    9621           0 :                     SHR = 1.0;
    9622             :                 }
    9623             :                 // Check for dry evaporator conditions (win < wadp)
    9624    23920519 :                 if (wADP > InletAirHumRatTemp || (Counter >= 1 && Counter < MaxIter)) {
    9625    11211526 :                     if (InletAirHumRatTemp == 0.0) InletAirHumRatTemp = 0.00001;
    9626    11211526 :                     werror = (InletAirHumRatTemp - wADP) / InletAirHumRatTemp;
    9627             :                     // Increase InletAirHumRatTemp at constant InletAirTemp to find coil dry-out point. Then use the
    9628             :                     // capacity at the dry-out point to determine exiting conditions from coil. This is required
    9629             :                     // since the TotCapTempModFac doesn't work properly with dry-coil conditions.
    9630    11211526 :                     InletAirHumRatTemp = RF * wADP + (1.0 - RF) * InletAirHumRatTemp;
    9631    11211526 :                     InletAirWetBulbC = PsyTwbFnTdbWPb(state, InletAirDryBulbTemp, InletAirHumRatTemp, OutdoorPressure);
    9632             :                     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment
    9633             :                     //  line InletAirWetBulbC = PsyTwbFnTdbWPb(InletAirDryBulbTemp,InletAirHumRatTemp,InletAirPressure)
    9634    11211526 :                     ++Counter;
    9635    11211526 :                     if (std::abs(werror) > Tolerance) continue; // Recalculate with modified inlet conditions
    9636     2276882 :                     break;
    9637             :                 } else {
    9638             :                     break;
    9639             :                 }
    9640             :             }
    9641             :         } // end of DO iteration loop
    9642             : 
    9643    14985875 :         if (thisDXCoil.PLFFPLR(Mode) > 0) {
    9644    14985875 :             PLF = CurveValue(state, thisDXCoil.PLFFPLR(Mode), PartLoadRatio); // Calculate part-load factor
    9645             :         } else {
    9646           0 :             PLF = 1.0;
    9647             :         }
    9648             : 
    9649    14985875 :         if (PLF < 0.7) {
    9650           0 :             if (thisDXCoil.ErrIndex2 == 0) {
    9651           0 :                 if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    9652           0 :                     thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) {
    9653           0 :                     ShowWarningMessage(state, format("{}{}=\"{}\", PLF curve value", RoutineName, thisDXCoil.DXCoilType, thisDXCoil.Name));
    9654           0 :                     ShowContinueError(state, format("The PLF curve value = {:.3T} for part-load ratio = {:.3T}", PLF, PartLoadRatio));
    9655           0 :                     ShowContinueErrorTimeStamp(state, "PLF curve values must be >= 0.7. PLF has been reset to 0.7 and simulation is continuing.");
    9656           0 :                     ShowContinueError(state, format("Check the IO reference manual for PLF curve guidance [{}].", thisDXCoil.DXCoilType));
    9657             :                 } else {
    9658           0 :                     ShowWarningMessage(state, format("{}{}=\"{}\", PLF curve value", RoutineName, thisDXCoil.DXCoilType, thisDXCoil.Name));
    9659           0 :                     ShowContinueError(state, format("The PLF curve value = {:.3T} for part-load ratio = {:.3T}", PLF, PartLoadRatio));
    9660           0 :                     ShowContinueErrorTimeStamp(state, "PLF curve values must be >= 0.7. PLF has been reset to 0.7 and simulation is continuing.");
    9661           0 :                     ShowContinueError(state, format("Check the IO reference manual for PLF curve guidance [{}].", thisDXCoil.DXCoilType));
    9662             :                 }
    9663             :             }
    9664           0 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    9665           0 :                 thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) {
    9666           0 :                 ShowRecurringWarningErrorAtEnd(
    9667           0 :                     state, thisDXCoil.Name + ", " + thisDXCoil.DXCoilType + " PLF curve < 0.7 warning continues...", thisDXCoil.ErrIndex2, PLF, PLF);
    9668             :             } else {
    9669           0 :                 ShowRecurringWarningErrorAtEnd(
    9670           0 :                     state, thisDXCoil.Name + ", " + thisDXCoil.DXCoilType + " PLF curve < 0.7 warning continues...", thisDXCoil.ErrIndex2, PLF, PLF);
    9671             :             }
    9672           0 :             PLF = 0.7;
    9673             :         }
    9674             : 
    9675    14985875 :         thisDXCoil.PartLoadRatio = PartLoadRatio;
    9676    14985875 :         thisDXCoil.CoolingCoilRuntimeFraction = PartLoadRatio / PLF;
    9677    14985875 :         if (thisDXCoil.CoolingCoilRuntimeFraction > 1.0 && std::abs(thisDXCoil.CoolingCoilRuntimeFraction - 1.0) > 0.001) {
    9678           0 :             if (thisDXCoil.ErrIndex3 == 0) {
    9679           0 :                 if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    9680           0 :                     thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) {
    9681           0 :                     ShowWarningMessage(state, format("{}{}=\"{}\", runtime fraction", RoutineName, thisDXCoil.DXCoilType, thisDXCoil.Name));
    9682           0 :                     ShowWarningMessage(state, format("The runtime fraction exceeded 1.0. [{:.4R}].", thisDXCoil.CoolingCoilRuntimeFraction));
    9683           0 :                     ShowContinueError(state, "Runtime fraction reset to 1 and the simulation will continue.");
    9684           0 :                     ShowContinueError(state, format("Check the IO reference manual for PLF curve guidance [{}].", thisDXCoil.DXCoilType));
    9685           0 :                     ShowContinueErrorTimeStamp(state, "");
    9686             :                 } else {
    9687           0 :                     ShowWarningMessage(state, format("{}{}=\"{}\", runtime fraction", RoutineName, thisDXCoil.DXCoilType, thisDXCoil.Name));
    9688           0 :                     ShowWarningMessage(state, format("The runtime fraction exceeded 1.0. [{:.4R}].", thisDXCoil.CoolingCoilRuntimeFraction));
    9689           0 :                     ShowContinueError(state, "Runtime fraction reset to 1 and the simulation will continue.");
    9690           0 :                     ShowContinueError(state, format("Check the IO reference manual for PLF curve guidance [{}].", thisDXCoil.DXCoilType));
    9691           0 :                     ShowContinueErrorTimeStamp(state, "");
    9692             :                 }
    9693             :             }
    9694           0 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    9695           0 :                 thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) {
    9696           0 :                 ShowRecurringWarningErrorAtEnd(state,
    9697           0 :                                                thisDXCoil.Name + ", " + thisDXCoil.DXCoilType + " runtime fraction > 1.0 warning continues...",
    9698           0 :                                                thisDXCoil.ErrIndex3,
    9699           0 :                                                thisDXCoil.CoolingCoilRuntimeFraction,
    9700           0 :                                                thisDXCoil.CoolingCoilRuntimeFraction);
    9701             :             } else {
    9702           0 :                 ShowRecurringWarningErrorAtEnd(state,
    9703           0 :                                                thisDXCoil.Name + ", " + thisDXCoil.DXCoilType + " runtime fraction > 1.0 warning continues...",
    9704           0 :                                                thisDXCoil.ErrIndex3,
    9705           0 :                                                thisDXCoil.CoolingCoilRuntimeFraction,
    9706           0 :                                                thisDXCoil.CoolingCoilRuntimeFraction);
    9707             :             }
    9708           0 :             thisDXCoil.CoolingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
    9709    14985875 :         } else if (thisDXCoil.CoolingCoilRuntimeFraction > 1.0) {
    9710      747051 :             thisDXCoil.CoolingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
    9711             :         }
    9712             : 
    9713             :         // If cycling fan, send coil part-load fraction to on/off fan via HVACDataGlobals
    9714    14985875 :         if (fanOp == HVAC::FanOp::Cycling) state.dataHVACGlobal->OnOffFanPartLoadFraction = PLF;
    9715             : 
    9716             :         //  Calculate full load output conditions
    9717    14985875 :         if (thisDXCoil.UserSHRCurveExists) {
    9718           0 :             FullLoadOutAirEnth = InletAirEnthalpy - hDelta;
    9719           0 :             if (SHR < 1.0) {
    9720           0 :                 hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
    9721           0 :                 FullLoadOutAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout);
    9722           0 :                 if (FullLoadOutAirHumRat <= 0.0) {
    9723           0 :                     FullLoadOutAirHumRat = min(DryCoilOutletHumRatioMin, InletAirHumRat);
    9724             :                 }
    9725             :             } else {
    9726           0 :                 SHR = 1.0;
    9727           0 :                 FullLoadOutAirHumRat = InletAirHumRat;
    9728             :             }
    9729             :         } else {
    9730    14985875 :             if (SHR > 1.0 || Counter > 0) SHR = 1.0;
    9731    14985875 :             FullLoadOutAirEnth = InletAirEnthalpy - TotCap / AirMassFlow;
    9732    14985875 :             hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
    9733    14985875 :             if (SHR < 1.0) {
    9734    12708993 :                 FullLoadOutAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout);
    9735             :             } else {
    9736     2276882 :                 FullLoadOutAirHumRat = InletAirHumRat;
    9737             :             }
    9738             :         }
    9739    14985875 :         FullLoadOutAirTemp = PsyTdbFnHW(FullLoadOutAirEnth, FullLoadOutAirHumRat);
    9740             : 
    9741             :         // Check for saturation error and modify temperature at constant enthalpy
    9742    14985875 :         if (FullLoadOutAirTemp < PsyTsatFnHPb(state, FullLoadOutAirEnth, OutdoorPressure)) {
    9743      225993 :             FullLoadOutAirTemp = PsyTsatFnHPb(state, FullLoadOutAirEnth, OutdoorPressure);
    9744             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
    9745             :             //   IF(FullLoadOutAirTemp .LT. PsyTsatFnHPb(FullLoadOutAirEnth,InletAirPressure)) THEN
    9746             :             //    FullLoadOutAirTemp = PsyTsatFnHPb(FullLoadOutAirEnth,InletAirPressure)
    9747      225993 :             FullLoadOutAirHumRat = PsyWFnTdbH(state, FullLoadOutAirTemp, FullLoadOutAirEnth);
    9748             :         }
    9749             : 
    9750             :         // Store actual outlet conditions when DX coil is ON for use in heat recovery module
    9751    14985875 :         state.dataDXCoils->DXCoilFullLoadOutAirTemp(DXCoilNum) = FullLoadOutAirTemp;
    9752    14985875 :         state.dataDXCoils->DXCoilFullLoadOutAirHumRat(DXCoilNum) = FullLoadOutAirHumRat;
    9753             : 
    9754             :         // Add warning message for cold cooling coil (FullLoadOutAirTemp < 2 C)
    9755    14985875 :         if (FullLoadOutAirTemp < 2.0 && !FirstHVACIteration && !state.dataGlobal->WarmupFlag) {
    9756        4406 :             thisDXCoil.PrintLowOutTempMessage = true;
    9757        4406 :             thisDXCoil.FullLoadOutAirTempLast = FullLoadOutAirTemp;
    9758        4406 :             if (thisDXCoil.LowOutletTempIndex == 0) {
    9759          75 :                 thisDXCoil.FullLoadInletAirTempLast = InletAirDryBulbTemp;
    9760         150 :                 thisDXCoil.LowOutTempBuffer1 = format("{} \"{}\" - Full load outlet air dry-bulb temperature < 2C. This indicates the "
    9761             :                                                       "possibility of coil frost/freeze. Outlet temperature = {:.2R} C.",
    9762          75 :                                                       thisDXCoil.DXCoilType,
    9763          75 :                                                       thisDXCoil.Name,
    9764          75 :                                                       FullLoadOutAirTemp);
    9765         150 :                 thisDXCoil.LowOutTempBuffer2 = " ...Occurrence info = " + state.dataEnvrn->EnvironmentName + ", " + state.dataEnvrn->CurMnDy + ' ' +
    9766         225 :                                                CreateSysTimeIntervalString(state);
    9767             :             }
    9768             :         }
    9769             : 
    9770             :         //  If constant fan with cycling compressor, call function to determine "effective SHR"
    9771             :         //  which includes the part-load degradation on latent capacity
    9772    14985875 :         if (fanOp == HVAC::FanOp::Continuous) {
    9773     7555871 :             QLatRated = thisDXCoil.RatedTotCap(Mode) * (1.0 - thisDXCoil.RatedSHR(Mode));
    9774     7555871 :             QLatActual = TotCap * (1.0 - SHR);
    9775     7555871 :             SHRUnadjusted = SHR;
    9776     7555871 :             SHR = CalcEffectiveSHR(
    9777             :                 state, DXCoilNum, SHR, thisDXCoil.CoolingCoilRuntimeFraction, QLatRated, QLatActual, InletAirDryBulbTemp, InletAirWetBulbC, Mode);
    9778             :             // For multimode coil, if stage-2 operation (modes 2 or 4), adjust Stage1&2 SHR to account for
    9779             :             // Stage 1 operating at full load, so there is no degradation for that portion
    9780             :             // Use the stage 1 bypass fraction to allocate
    9781     7555871 :             if (Mode == 2 || Mode == 4) {
    9782       98314 :                 SHR = SHRUnadjusted * (1.0 - thisDXCoil.BypassedFlowFrac(Mode - 1)) + SHR * thisDXCoil.BypassedFlowFrac(Mode - 1);
    9783             :             }
    9784             : 
    9785             :             //  Calculate full load output conditions
    9786     7555871 :             if (thisDXCoil.UserSHRCurveExists) {
    9787           0 :                 FullLoadOutAirEnth = InletAirEnthalpy - hDelta;
    9788           0 :                 if (SHR < 1.0) {
    9789           0 :                     hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
    9790           0 :                     FullLoadOutAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout);
    9791           0 :                     if (FullLoadOutAirHumRat <= 0.0) {
    9792           0 :                         FullLoadOutAirHumRat = min(DryCoilOutletHumRatioMin, InletAirHumRat);
    9793             :                     }
    9794             :                 } else {
    9795           0 :                     SHR = 1.0;
    9796           0 :                     FullLoadOutAirHumRat = InletAirHumRat;
    9797             :                 }
    9798             :             } else {
    9799     7555871 :                 if (SHR > 1.0 || Counter > 0) SHR = 1.0;
    9800     7555871 :                 FullLoadOutAirEnth = InletAirEnthalpy - TotCap / AirMassFlow;
    9801     7555871 :                 hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
    9802     7555871 :                 if (SHR < 1.0) {
    9803     6302920 :                     FullLoadOutAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout);
    9804             :                 } else {
    9805     1252951 :                     FullLoadOutAirHumRat = InletAirHumRat;
    9806             :                 }
    9807             :             }
    9808     7555871 :             FullLoadOutAirTemp = PsyTdbFnHW(FullLoadOutAirEnth, FullLoadOutAirHumRat);
    9809             : 
    9810             :             // apply latent degradation model to cycling fan when RH control is desired and heating coil operates
    9811             :             // longer than the cooling coil. DXcoolToHeatPLRRatio = Cooling coil PLR / Heating coil PLR.
    9812     7430004 :         } else if (fanOp == HVAC::FanOp::Cycling) {
    9813     7430004 :             if (DXcoolToHeatPLRRatio < 1.0) {
    9814           0 :                 QLatRated = thisDXCoil.RatedTotCap(Mode) * (1.0 - thisDXCoil.RatedSHR(Mode));
    9815           0 :                 QLatActual = TotCap * (1.0 - SHR);
    9816           0 :                 HeatRTF = PartLoadRatio / DXcoolToHeatPLRRatio;
    9817           0 :                 if (thisDXCoil.HeatingCoilPLFCurvePTR > 0) {
    9818           0 :                     HeatingCoilPLF = CurveValue(state, thisDXCoil.HeatingCoilPLFCurvePTR, HeatRTF);
    9819           0 :                     if (HeatingCoilPLF > 0) HeatRTF /= HeatingCoilPLF;
    9820             :                 }
    9821           0 :                 SHRUnadjusted = SHR;
    9822           0 :                 SHR = CalcEffectiveSHR(state,
    9823             :                                        DXCoilNum,
    9824             :                                        SHR,
    9825             :                                        thisDXCoil.CoolingCoilRuntimeFraction,
    9826             :                                        QLatRated,
    9827             :                                        QLatActual,
    9828             :                                        InletAirDryBulbTemp,
    9829             :                                        InletAirWetBulbC,
    9830             :                                        Mode,
    9831             :                                        HeatRTF);
    9832             :                 //   Calculate full load output conditions
    9833           0 :                 if (thisDXCoil.UserSHRCurveExists) {
    9834           0 :                     FullLoadOutAirEnth = InletAirEnthalpy - hDelta;
    9835           0 :                     if (SHR < 1.0) {
    9836           0 :                         hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
    9837           0 :                         FullLoadOutAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout);
    9838           0 :                         if (FullLoadOutAirHumRat <= 0.0) {
    9839           0 :                             FullLoadOutAirHumRat = min(DryCoilOutletHumRatioMin, InletAirHumRat);
    9840             :                         }
    9841             :                     } else {
    9842           0 :                         SHR = 1.0;
    9843           0 :                         FullLoadOutAirHumRat = InletAirHumRat;
    9844             :                     }
    9845             :                 } else {
    9846           0 :                     if (SHR > 1.0 || Counter > 0) SHR = 1.0;
    9847           0 :                     FullLoadOutAirEnth = InletAirEnthalpy - TotCap / AirMassFlow;
    9848           0 :                     hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
    9849           0 :                     if (SHR < 1.0) {
    9850           0 :                         FullLoadOutAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout);
    9851             :                     } else {
    9852           0 :                         FullLoadOutAirHumRat = InletAirHumRat;
    9853             :                     }
    9854             :                 }
    9855           0 :                 FullLoadOutAirTemp = PsyTdbFnHW(FullLoadOutAirEnth, FullLoadOutAirHumRat);
    9856             :             }
    9857             :         }
    9858             : 
    9859             :         //  Calculate actual outlet conditions for the input part load ratio
    9860             :         //  Actual outlet conditions are "average" for time step
    9861             : 
    9862             :         // For multimode coil, if stage-2 operation (modes 2 or 4), return "full load" outlet conditions
    9863    14985875 :         if (((fanOp == HVAC::FanOp::Continuous) && (Mode == 1)) || (Mode == 3)) {
    9864             :             // Continuous fan, cycling compressor
    9865     7457557 :             OutletAirEnthalpy = ((PartLoadRatio * AirFlowRatio) * FullLoadOutAirEnth + (1.0 - (PartLoadRatio * AirFlowRatio)) * InletAirEnthalpy);
    9866     7457557 :             OutletAirHumRat = ((PartLoadRatio * AirFlowRatio) * FullLoadOutAirHumRat + (1.0 - (PartLoadRatio * AirFlowRatio)) * InletAirHumRat);
    9867     7457557 :             OutletAirTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
    9868             :         } else {
    9869             :             // Default to cycling fan, cycling compressor
    9870             :             // Also return this result for stage 2 operation of multimode coil
    9871             :             // Cycling fan typically provides full outlet conditions. When RH control is used, account for additional
    9872             :             // heating run time by using cooing/heating ratio the same as constant fan (otherwise PLRRatio = 1).
    9873     7528318 :             OutletAirEnthalpy = FullLoadOutAirEnth * DXcoolToHeatPLRRatio + InletAirEnthalpy * (1.0 - DXcoolToHeatPLRRatio);
    9874     7528318 :             OutletAirHumRat = FullLoadOutAirHumRat * DXcoolToHeatPLRRatio + InletAirHumRat * (1.0 - DXcoolToHeatPLRRatio);
    9875     7528318 :             OutletAirTemp = FullLoadOutAirTemp * DXcoolToHeatPLRRatio + InletAirDryBulbTemp * (1.0 - DXcoolToHeatPLRRatio);
    9876             :         }
    9877             : 
    9878             :         // Check for saturation error and modify temperature at constant enthalpy
    9879    14985875 :         if (OutletAirTemp < PsyTsatFnHPb(state, OutletAirEnthalpy, OutdoorPressure, calcDoe2DXCoil)) {
    9880      153073 :             OutletAirTemp = PsyTsatFnHPb(state, OutletAirEnthalpy, OutdoorPressure);
    9881             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
    9882             :             //   IF(OutletAirTemp .LT. PsyTsatFnHPb(OutletAirEnthalpy,InletAirPressure)) THEN
    9883             :             //    OutletAirTemp = PsyTsatFnHPb(OutletAirEnthalpy,InletAirPressure)
    9884      153073 :             OutletAirHumRat = PsyWFnTdbH(state, OutletAirTemp, OutletAirEnthalpy);
    9885             :         }
    9886             : 
    9887             :         // Mix with air that was bypassed around coil, if any
    9888    14985875 :         if (BypassFlowFraction > 0.0) {
    9889      103788 :             OutletAirEnthalpy = (1.0 - BypassFlowFraction) * OutletAirEnthalpy + BypassFlowFraction * InletAirEnthalpy;
    9890      103788 :             OutletAirHumRat = (1.0 - BypassFlowFraction) * OutletAirHumRat + BypassFlowFraction * InletAirHumRat;
    9891      103788 :             OutletAirTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
    9892             :             // Check for saturation error and modify temperature at constant enthalpy
    9893      103788 :             if (OutletAirTemp < PsyTsatFnHPb(state, OutletAirEnthalpy, OutdoorPressure)) {
    9894           0 :                 OutletAirTemp = PsyTsatFnHPb(state, OutletAirEnthalpy, OutdoorPressure);
    9895             :                 //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
    9896             :                 //     IF(OutletAirTemp .LT. PsyTsatFnHPb(OutletAirEnthalpy,InletAirPressure)) THEN
    9897             :                 //       OutletAirTemp = PsyTsatFnHPb(OutletAirEnthalpy,InletAirPressure)
    9898           0 :                 OutletAirHumRat = PsyWFnTdbH(state, OutletAirTemp, OutletAirEnthalpy);
    9899             :             }
    9900             :         }
    9901             : 
    9902             :         // Calculate electricity consumed. First, get EIR modifying factors for off-rated conditions
    9903    14985875 :         if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterPumped ||
    9904    14863772 :             thisDXCoil.DXCoilType_Num == HVAC::CoilDX_HeatPumpWaterHeaterWrapped) {
    9905             :             //   Coil:DX:HeatPumpWaterHeater does not have EIR temp or flow curves
    9906      273402 :             EIRTempModFac = 1.0;
    9907      273402 :             EIRFlowModFac = 1.0;
    9908             :         } else {
    9909    14712473 :             EIRTempModFac = CurveValue(state, thisDXCoil.EIRFTemp(Mode), InletAirWetBulbC, CondInletTemp);
    9910             : 
    9911             :             //   Warn user if curve output goes negative
    9912    14712473 :             if (EIRTempModFac < 0.0) {
    9913           0 :                 if (thisDXCoil.EIRFTempErrorIndex == 0) {
    9914           0 :                     ShowWarningMessage(state, format("{}{}=\"{}\":", RoutineName, thisDXCoil.DXCoilType, thisDXCoil.Name));
    9915           0 :                     ShowContinueError(
    9916           0 :                         state, format(" Energy Input Ratio Modifier curve (function of temperature) output is negative ({:.3T}).", EIRTempModFac));
    9917           0 :                     if (state.dataCurveManager->PerfCurve(thisDXCoil.EIRFTemp(Mode))->numDims == 2) {
    9918           0 :                         ShowContinueError(state,
    9919           0 :                                           format(" Negative value occurs using a condenser inlet air temperature of {:.1T} and an inlet air "
    9920             :                                                  "wet-bulb temperature of {:.1T}.",
    9921             :                                                  CondInletTemp,
    9922             :                                                  InletAirWetBulbC));
    9923             :                     } else {
    9924           0 :                         ShowContinueError(state, format(" Negative value occurs using a condenser inlet air temperature of {:.1T}.", CondInletTemp));
    9925             :                     }
    9926           0 :                     if (Mode > 1) {
    9927           0 :                         ShowContinueError(state, format(" Negative output results from stage {} compressor operation.", Mode));
    9928             :                     }
    9929           0 :                     ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
    9930             :                 }
    9931           0 :                 ShowRecurringWarningErrorAtEnd(
    9932             :                     state,
    9933           0 :                     std::string{RoutineName} + thisDXCoil.DXCoilType + "=\"" + thisDXCoil.Name +
    9934             :                         "\": Energy Input Ratio Modifier curve (function of temperature) output is negative warning continues...",
    9935           0 :                     thisDXCoil.EIRFTempErrorIndex,
    9936             :                     EIRTempModFac,
    9937             :                     EIRTempModFac);
    9938           0 :                 EIRTempModFac = 0.0;
    9939             :             }
    9940             : 
    9941    14712473 :             EIRFlowModFac = CurveValue(state, thisDXCoil.EIRFFlow(Mode), AirMassFlowRatio);
    9942             : 
    9943             :             //   Warn user if curve output goes negative
    9944    14712473 :             if (EIRFlowModFac < 0.0) {
    9945           0 :                 if (thisDXCoil.EIRFFlowErrorIndex == 0) {
    9946           0 :                     ShowWarningMessage(state, format("{}{}=\"{}\":", RoutineName, thisDXCoil.DXCoilType, thisDXCoil.Name));
    9947           0 :                     ShowContinueError(
    9948           0 :                         state, format(" Energy Input Ratio Modifier curve (function of flow fraction) output is negative ({:.3T}).", EIRFlowModFac));
    9949           0 :                     ShowContinueError(state, format(" Negative value occurs using an air flow fraction of {:.3T}.", AirMassFlowRatio));
    9950           0 :                     ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
    9951           0 :                     if (Mode > 1) {
    9952           0 :                         ShowContinueError(state, format(" Negative output results from stage {} compressor operation.", Mode));
    9953             :                     }
    9954             :                 }
    9955           0 :                 ShowRecurringWarningErrorAtEnd(
    9956             :                     state,
    9957           0 :                     std::string{RoutineName} + thisDXCoil.DXCoilType + "=\"" + thisDXCoil.Name +
    9958             :                         "\": Energy Input Ratio Modifier curve (function of flow fraction) output is negative warning continues...",
    9959           0 :                     thisDXCoil.EIRFFlowErrorIndex,
    9960             :                     EIRFlowModFac,
    9961             :                     EIRFlowModFac);
    9962           0 :                 EIRFlowModFac = 0.0;
    9963             :             }
    9964             :         }
    9965             : 
    9966    14985875 :         EIR = thisDXCoil.RatedEIR(Mode) * EIRFlowModFac * EIRTempModFac;
    9967             : 
    9968             :         // For multimode coil, if stage-2 operation (Modes 2 or 4), return "full load" power adjusted for PLF
    9969    14985875 :         if (Mode == 1 || Mode == 3) {
    9970    14887561 :             thisDXCoil.ElecCoolingPower = TotCap * EIR * thisDXCoil.CoolingCoilRuntimeFraction;
    9971             :         } else {
    9972       98314 :             thisDXCoil.ElecCoolingPower = TotCap * EIR * thisDXCoil.CoolingCoilRuntimeFraction / PartLoadRatio;
    9973             :         }
    9974             : 
    9975             :         // Reset AirMassFlow to inlet node air mass flow for final total, sensible and latent calculations
    9976             :         // since AirMassFlow might have been modified above (in this subroutine):
    9977             :         //     IF (FanOpMode .EQ. FanOp::Cycling) AirMassFlow = AirMassFlow / PartLoadRatio
    9978             :         // For multimode coil, this should be full flow including bypassed fraction
    9979    14985875 :         AirMassFlow = thisDXCoil.InletAirMassFlowRate;
    9980    14985875 :         CalcComponentSensibleLatentOutput(AirMassFlow,
    9981             :                                           InletAirDryBulbTemp,
    9982             :                                           InletAirHumRat,
    9983             :                                           OutletAirTemp,
    9984             :                                           OutletAirHumRat,
    9985    14985875 :                                           thisDXCoil.SensCoolingEnergyRate,
    9986    14985875 :                                           thisDXCoil.LatCoolingEnergyRate,
    9987    14985875 :                                           thisDXCoil.TotalCoolingEnergyRate);
    9988             : 
    9989             :         // Set DataHeatGlobal heat reclaim variable for use by heat reclaim coil (part load ratio is accounted for)
    9990             :         // Calculation for heat reclaim needs to be corrected to use compressor power (not including condenser fan power)
    9991    14985875 :         state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).AvailCapacity = thisDXCoil.TotalCoolingEnergyRate + thisDXCoil.ElecCoolingPower;
    9992             : 
    9993             :         // Calculate crankcase heater power using the runtime fraction for this DX cooling coil only if there is no companion DX coil.
    9994             :         // Else use the largest runtime fraction of this DX cooling coil and the companion DX heating coil.
    9995    14985875 :         if (thisDXCoil.CompanionUpstreamDXCoil == 0) {
    9996    14985875 :             thisDXCoil.CrankcaseHeaterPower = CrankcaseHeatingPower * (1.0 - thisDXCoil.CoolingCoilRuntimeFraction);
    9997             :         } else {
    9998           0 :             thisDXCoil.CrankcaseHeaterPower =
    9999           0 :                 CrankcaseHeatingPower * (1.0 - max(thisDXCoil.CoolingCoilRuntimeFraction,
   10000           0 :                                                    state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).HeatingCoilRuntimeFraction));
   10001             :         }
   10002             : 
   10003    14985875 :         if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Evap) {
   10004             :             //******************
   10005             :             //             WATER CONSUMPTION IN m3 OF WATER FOR DIRECT
   10006             :             //             H2O [m3/s] = Delta W[kgWater/kgDryAir]*Mass Flow Air[kgDryAir/s]
   10007             :             //                                /RhoWater [kgWater/m3]
   10008             :             //******************
   10009       44986 :             RhoWater = RhoH2O(OutdoorDryBulb);
   10010       44986 :             thisDXCoil.EvapWaterConsumpRate = (CondInletHumRat - OutdoorHumRat) * CondAirMassFlow / RhoWater * thisDXCoil.CoolingCoilRuntimeFraction;
   10011       44986 :             thisDXCoil.EvapCondPumpElecPower = thisDXCoil.EvapCondPumpElecNomPower(Mode) * thisDXCoil.CoolingCoilRuntimeFraction;
   10012             :             // Calculate basin heater power
   10013       44986 :             CalcBasinHeaterPower(state,
   10014             :                                  thisDXCoil.BasinHeaterPowerFTempDiff,
   10015             :                                  thisDXCoil.BasinHeaterSchedulePtr,
   10016             :                                  thisDXCoil.BasinHeaterSetPointTemp,
   10017       44986 :                                  thisDXCoil.BasinHeaterPower);
   10018       44986 :             if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingSingleSpeed) {
   10019       44986 :                 thisDXCoil.BasinHeaterPower *= (1.0 - thisDXCoil.CoolingCoilRuntimeFraction);
   10020             :             }
   10021             :         }
   10022             : 
   10023    14985875 :         thisDXCoil.OutletAirTemp = OutletAirTemp;
   10024    14985875 :         thisDXCoil.OutletAirHumRat = OutletAirHumRat;
   10025    14985875 :         thisDXCoil.OutletAirEnthalpy = OutletAirEnthalpy;
   10026             : 
   10027             :     } else {
   10028             : 
   10029             :         // DX coil is off; just pass through conditions
   10030    24608518 :         thisDXCoil.OutletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   10031    24608518 :         thisDXCoil.OutletAirHumRat = thisDXCoil.InletAirHumRat;
   10032    24608518 :         thisDXCoil.OutletAirTemp = thisDXCoil.InletAirTemp;
   10033             : 
   10034    24608518 :         thisDXCoil.ElecCoolingPower = 0.0;
   10035    24608518 :         thisDXCoil.TotalCoolingEnergyRate = 0.0;
   10036    24608518 :         thisDXCoil.SensCoolingEnergyRate = 0.0;
   10037    24608518 :         thisDXCoil.LatCoolingEnergyRate = 0.0;
   10038    24608518 :         thisDXCoil.EvapCondPumpElecPower = 0.0;
   10039    24608518 :         thisDXCoil.EvapWaterConsumpRate = 0.0;
   10040             : 
   10041             :         // Reset globals when DX coil is OFF for use in heat recovery module
   10042    24608518 :         state.dataDXCoils->DXCoilFullLoadOutAirTemp(DXCoilNum) = 0.0;
   10043    24608518 :         state.dataDXCoils->DXCoilFullLoadOutAirHumRat(DXCoilNum) = 0.0;
   10044             : 
   10045             :         // Calculate crankcase heater power using the runtime fraction for this DX cooling coil (here DXCoolingCoilRTF=0) if
   10046             :         // there is no companion DX coil, or the runtime fraction of the companion DX heating coil (here DXHeatingCoilRTF>=0).
   10047    24608518 :         if (thisDXCoil.CompanionUpstreamDXCoil == 0) {
   10048    24608518 :             thisDXCoil.CrankcaseHeaterPower = CrankcaseHeatingPower;
   10049             :         } else {
   10050           0 :             thisDXCoil.CrankcaseHeaterPower =
   10051           0 :                 CrankcaseHeatingPower * (1.0 - state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).HeatingCoilRuntimeFraction);
   10052             :         }
   10053             : 
   10054             :         // Calculate basin heater power
   10055    24608518 :         if (thisDXCoil.DXCoilType_Num == HVAC::CoilDX_CoolingTwoStageWHumControl) {
   10056       75255 :             if (any_eq(thisDXCoil.CondenserType, DataHeatBalance::RefrigCondenserType::Evap)) {
   10057           0 :                 CalcBasinHeaterPower(state,
   10058             :                                      thisDXCoil.BasinHeaterPowerFTempDiff,
   10059             :                                      thisDXCoil.BasinHeaterSchedulePtr,
   10060             :                                      thisDXCoil.BasinHeaterSetPointTemp,
   10061           0 :                                      thisDXCoil.BasinHeaterPower);
   10062             :             }
   10063             :         } else {
   10064    24533263 :             if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Evap) {
   10065       67370 :                 CalcBasinHeaterPower(state,
   10066             :                                      thisDXCoil.BasinHeaterPowerFTempDiff,
   10067             :                                      thisDXCoil.BasinHeaterSchedulePtr,
   10068             :                                      thisDXCoil.BasinHeaterSetPointTemp,
   10069       67370 :                                      thisDXCoil.BasinHeaterPower);
   10070             :             }
   10071             :         }
   10072             : 
   10073             :     } // end of on/off if - else
   10074             : 
   10075             :     // set water system demand request (if needed)
   10076    39594393 :     if (thisDXCoil.EvapWaterSupplyMode == EvapWaterSupply::FromTank) {
   10077           0 :         state.dataWaterData->WaterStorage(thisDXCoil.EvapWaterSupTankID).VdotRequestDemand(thisDXCoil.EvapWaterTankDemandARRID) =
   10078           0 :             thisDXCoil.EvapWaterConsumpRate;
   10079             :     }
   10080             : 
   10081    39594393 :     state.dataDXCoils->DXCoilOutletTemp(DXCoilNum) = thisDXCoil.OutletAirTemp;
   10082    39594393 :     state.dataDXCoils->DXCoilOutletHumRat(DXCoilNum) = thisDXCoil.OutletAirHumRat;
   10083    39594393 :     state.dataDXCoils->DXCoilPartLoadRatio(DXCoilNum) = thisDXCoil.PartLoadRatio;
   10084    39594393 :     state.dataDXCoils->DXCoilFanOp(DXCoilNum) = fanOp;
   10085    39594393 :     thisDXCoil.CondInletTemp = CondInletTemp;
   10086             : 
   10087             :     // set outlet node conditions
   10088    39594393 :     int airOutletNode = thisDXCoil.AirOutNode;
   10089    39594393 :     state.dataLoopNodes->Node(airOutletNode).Temp = thisDXCoil.OutletAirTemp;
   10090    39594393 :     state.dataLoopNodes->Node(airOutletNode).HumRat = thisDXCoil.OutletAirHumRat;
   10091             : 
   10092             :     // calc secondary coil if specified
   10093    39594393 :     if (thisDXCoil.IsSecondaryDXCoilInZone) {
   10094       81926 :         CalcSecondaryDXCoils(state, DXCoilNum);
   10095             :     }
   10096    39594393 : }
   10097             : 
   10098     1704105 : void CalcVRFCoolingCoil(EnergyPlusData &state,
   10099             :                         int const DXCoilNum,                                 // the number of the DX coil to be simulated
   10100             :                         HVAC::CompressorOp const compressorOp,               // compressor operation; 1=on, 0=off
   10101             :                         bool const FirstHVACIteration,                       // true if this is the first iteration of HVAC
   10102             :                         Real64 const PartLoadRatio,                          // sensible cooling load / full load sensible cooling capacity
   10103             :                         HVAC::FanOp const fanOp,                             // Allows parent object to control fan operation
   10104             :                         Real64 const CompCycRatio,                           // cycling ratio of VRF condenser
   10105             :                         ObjexxFCL::Optional_int_const PerfMode,              // Performance mode for MultiMode DX coil; Always 1 for other coil types
   10106             :                         ObjexxFCL::Optional<Real64 const> OnOffAirFlowRatio, // ratio of compressor on airflow to compressor off airflow
   10107             :                         ObjexxFCL::Optional<Real64 const> MaxCoolCap         // maximum capacity of DX coil
   10108             : )
   10109             : {
   10110             : 
   10111             :     // SUBROUTINE INFORMATION:
   10112             :     //       AUTHOR         Richard Raustad
   10113             :     //       DATE WRITTEN   August 2010
   10114             : 
   10115             :     // PURPOSE OF THIS SUBROUTINE:
   10116             :     // Calculates the air-side performance of a direct-expansion, air-cooled
   10117             :     // VRF terminal unit cooling coil.
   10118             :     // A new subroutine was created in case this DX coil model is significantly
   10119             :     // different from the existing CalcDoe2DXCoil subroutine. The VRF heating coil
   10120             :     // uses the existing DX heating coil subroutine (CalcDXHeatingCoil).
   10121             : 
   10122             :     // METHODOLOGY EMPLOYED:
   10123             :     // This routine simulates the performance of a variable refrigerant flow cooling coil.
   10124             :     // The routine requires the user to enter the total cooling capacity and sensible heat ratio.
   10125             :     // Since different manufacturer's rate their equipment at different air flow rates,
   10126             :     // the supply air flow rate corresponding to the rated capacities must also be
   10127             :     // entered (should be between 300 cfm/ton and 450 cfm/ton). The rated information entered by
   10128             :     // the user should NOT include the thermal or electrical impacts of the supply air fan, as
   10129             :     // this is addressed by another module.
   10130             : 
   10131             :     // With the rated performance data entered by the user, the model employs some of the
   10132             :     // DOE-2.1E curve fits to adjust the capacity and efficiency of the unit as a function
   10133             :     // of entering air temperatures and supply air flow rate (actual vs rated flow). The model
   10134             :     // does NOT employ the exact same methodology to calculate performance as DOE-2.
   10135             :     // This VRF cooling coil model adjusts the rated total cooling capacity by the CAPFT
   10136             :     // and CAP funciton of flow curve/model currently used by the existing DX coil model.
   10137             :     // The part-load ratio is then applied to the total operating capacity to find the capacity
   10138             :     // required to meet the load. This VRF model then uses the ADP/bypass method to find the
   10139             :     // SHR and resulting outlet conditions given that total capacity (or delta H).
   10140             : 
   10141             :     // The model checks for coil dryout conditions, and adjusts the calculated performance
   10142             :     // appropriately.
   10143             : 
   10144             :     // Using/Aliasing
   10145             :     using Curve::CurveValue;
   10146     1704105 :     Real64 SysTimeElapsed = state.dataHVACGlobal->SysTimeElapsed;
   10147     1704105 :     Real64 TimeStepSys = state.dataHVACGlobal->TimeStepSys;
   10148             :     using General::CreateSysTimeIntervalString;
   10149             : 
   10150             :     // SUBROUTINE ARGUMENT DEFINITIONS:
   10151             :     //  REAL(r64), INTENT(IN), OPTIONAL :: CoolingHeatingPLR   ! used for cycling fan RH control
   10152             : 
   10153             :     // SUBROUTINE PARAMETER DEFINITIONS:
   10154             :     static constexpr std::string_view RoutineName("CalcVRFCoolingCoil");
   10155             : 
   10156             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   10157             :     Real64 AirMassFlow;       // dry air mass flow rate through coil [kg/s] (adjusted for bypass if any)
   10158             :     Real64 AirMassFlowRatio;  // Ratio of actual air mass flow to rated air mass flow (adjusted for bypass if any)
   10159             :     Real64 AirVolumeFlowRate; // Air volume flow rate across the cooling coil [m3/s] (adjusted for bypass if any)
   10160             :     // (average flow if cycling fan, full flow if constant fan)
   10161             :     Real64 VolFlowperRatedTotCap; // Air volume flow rate divided by rated total cooling capacity [m3/s-W] (adjusted for bypass)
   10162             :     Real64 TotCap;                // gross total cooling capacity at off-rated conditions [W]
   10163             :     Real64 TotCapTempModFac;      // Total capacity modifier (function of entering wetbulb, outside drybulb)
   10164             :     Real64 TotCapFlowModFac;      // Total capacity modifier (function of actual supply air flow vs rated flow)
   10165             :     Real64 InletAirWetBulbC;      // wetbulb temperature of inlet air [C]
   10166             :     Real64 InletAirDryBulbTemp;   // inlet air dry bulb temperature [C]
   10167             :     Real64 InletAirEnthalpy;      // inlet air enthalpy [J/kg]
   10168             :     Real64 InletAirHumRat;        // inlet air humidity ratio [kg/kg]
   10169             :     Real64 InletAirHumRatTemp;    // inlet air humidity ratio used in ADP/BF loop [kg/kg]
   10170             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   10171             :     // REAL(r64) :: InletAirPressure      ! inlet air pressure [Pa]
   10172             :     Real64 RatedCBF;             // coil bypass factor at rated conditions
   10173             :     Real64 SHR;                  // Sensible Heat Ratio (sensible/total) of the cooling coil
   10174             :     Real64 CBF;                  // coil bypass factor at off rated conditions
   10175             :     Real64 A0;                   // NTU * air mass flow rate, used in CBF calculation
   10176             :     Real64 hDelta;               // Change in air enthalpy across the cooling coil [J/kg]
   10177             :     Real64 hADP;                 // Apparatus dew point enthalpy [J/kg]
   10178             :     Real64 hTinwADP;             // Enthalpy at inlet dry-bulb and wADP [J/kg]
   10179             :     Real64 hTinwout;             // Enthalpy at inlet dry-bulb and outlet humidity ratio [J/kg]
   10180             :     Real64 tADP;                 // Apparatus dew point temperature [C]
   10181             :     Real64 wADP;                 // Apparatus dew point humidity ratio [kg/kg]
   10182             :     Real64 FullLoadOutAirEnth;   // outlet full load enthalpy [J/kg]
   10183             :     Real64 FullLoadOutAirHumRat; // outlet humidity ratio at full load
   10184             :     Real64 FullLoadOutAirTemp;   // outlet air temperature at full load [C]
   10185             :     Real64 PLF;                  // Part load factor, accounts for thermal lag at compressor startup, used in power calculation
   10186             :     Real64 QLatActual;           // operating latent capacity of DX coil
   10187             :     Real64 QLatRated;            // Rated latent capacity of DX coil
   10188             :     Real64 SHRUnadjusted;        // SHR prior to latent degradation effective SHR calculation
   10189             :     int Counter;                 // Counter for dry evaporator iterations
   10190             :     int MaxIter;                 // Maximum number of iterations for dry evaporator calculations
   10191             :     Real64 RF;                   // Relaxation factor for dry evaporator iterations
   10192             :     Real64 Tolerance;            // Error tolerance for dry evaporator iterations
   10193             :     Real64 werror;               // Deviation of humidity ratio in dry evaporator iteration loop
   10194             :     Real64 CondInletTemp;        // Condenser inlet temperature (C). Outdoor dry-bulb temp for air-cooled condenser.
   10195             :     // Outdoor Wetbulb +(1 - effectiveness)*(outdoor drybulb - outdoor wetbulb) for evap condenser.
   10196             :     Real64 CondInletHumRat; // Condenser inlet humidity ratio (kg/kg). Zero for air-cooled condenser.
   10197             :     // For evap condenser, its the humidity ratio of the air leaving the evap cooling pads.
   10198             :     Real64 CondAirMassFlow;       // Condenser air mass flow rate [kg/s]
   10199             :     Real64 RhoAir;                // Density of air [kg/m3]
   10200             :     Real64 CrankcaseHeatingPower; // power due to crankcase heater
   10201     1704105 :     Real64 CompAmbTemp(0.0);      // Ambient temperature at compressor
   10202             :     Real64 AirFlowRatio;          // ratio of compressor on airflow to average timestep airflow
   10203             :     // used when constant fan mode yields different air flow rates when compressor is ON and OFF
   10204             :     // (e.g. Packaged Terminal Heat Pump)
   10205             :     Real64 OutdoorDryBulb;  // Outdoor dry-bulb temperature at condenser (C)
   10206             :     Real64 OutdoorWetBulb;  // Outdoor wet-bulb temperature at condenser (C)
   10207             :     Real64 OutdoorHumRat;   // Outdoor humidity ratio at condenser (kg/kg)
   10208             :     Real64 OutdoorPressure; // Outdoor barometric pressure at condenser (Pa)
   10209             : 
   10210             :     int Mode;                 // Performance mode for Multimode DX coil; Always 1 for other coil types
   10211             :     Real64 OutletAirTemp;     // Supply air temperature (average value if constant fan, full output if cycling fan)
   10212             :     Real64 OutletAirHumRat;   // Supply air humidity ratio (average value if constant fan, full output if cycling fan)
   10213             :     Real64 OutletAirEnthalpy; // Supply air enthalpy (average value if constant fan, full output if cycling fan)
   10214             :     Real64 ADiff;             // Used for exponential
   10215             : 
   10216             :     // If Performance mode not present, then set to 1.  Used only by Multimode/Multispeed DX coil (otherwise mode = 1)
   10217     1704105 :     if (present(PerfMode)) {
   10218           0 :         Mode = PerfMode;
   10219             :     } else {
   10220     1704105 :         Mode = 1;
   10221             :     }
   10222             : 
   10223             :     // If AirFlowRatio not present, then set to 1. Used only by DX coils with different air flow
   10224             :     // during cooling and when no cooling is required (constant fan, fan speed changes)
   10225     1704105 :     if (present(OnOffAirFlowRatio)) {
   10226     1704059 :         AirFlowRatio = OnOffAirFlowRatio;
   10227             :     } else {
   10228          46 :         AirFlowRatio = 1.0;
   10229             :     }
   10230             : 
   10231     1704105 :     auto &DXCT = state.dataHVACGlobal->DXCT;
   10232             : 
   10233     1704105 :     MaxIter = 30;
   10234     1704105 :     RF = 0.4;
   10235     1704105 :     Counter = 0;
   10236     1704105 :     Tolerance = 0.01;
   10237     1704105 :     CondInletTemp = 0.0;
   10238     1704105 :     CondInletHumRat = 0.0;
   10239             : 
   10240     1704105 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   10241             : 
   10242     1704105 :     AirMassFlow = thisDXCoil.InletAirMassFlowRate;
   10243     1704105 :     InletAirDryBulbTemp = thisDXCoil.InletAirTemp;
   10244     1704105 :     InletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   10245     1704105 :     InletAirHumRat = thisDXCoil.InletAirHumRat;
   10246             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   10247             :     // InletAirPressure    = DXCoil(DXCoilNum)%InletAirPressure
   10248     1704105 :     state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).AvailCapacity = 0.0;
   10249     1704105 :     thisDXCoil.CoolingCoilRuntimeFraction = 0.0;
   10250     1704105 :     thisDXCoil.PartLoadRatio = 0.0;
   10251     1704105 :     thisDXCoil.BasinHeaterPower = 0.0;
   10252             : 
   10253     1704105 :     if (thisDXCoil.CondenserInletNodeNum(Mode) != 0) {
   10254     1704105 :         OutdoorDryBulb = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).Temp;
   10255     1704105 :         if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Water) {
   10256      156109 :             OutdoorHumRat = state.dataEnvrn->OutHumRat;
   10257      156109 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
   10258      156109 :             OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   10259             :         } else {
   10260     1547996 :             OutdoorPressure = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).Press;
   10261             :             // If node is not connected to anything, pressure = default, use weather data
   10262     1547996 :             if (OutdoorPressure == state.dataLoopNodes->DefaultNodeValues.Press) {
   10263           0 :                 OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   10264           0 :                 OutdoorHumRat = state.dataEnvrn->OutHumRat;
   10265           0 :                 OutdoorPressure = state.dataEnvrn->OutBaroPress;
   10266           0 :                 OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   10267             :             } else {
   10268     1547996 :                 OutdoorHumRat = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).HumRat;
   10269             :                 // this should use Node%WetBulbTemp or a PSYC function, not OAWB
   10270     1547996 :                 OutdoorWetBulb = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).OutAirWetBulb;
   10271             :             }
   10272             :         }
   10273             :     } else {
   10274           0 :         OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   10275           0 :         OutdoorHumRat = state.dataEnvrn->OutHumRat;
   10276           0 :         OutdoorPressure = state.dataEnvrn->OutBaroPress;
   10277           0 :         OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   10278             :     }
   10279             : 
   10280     1704105 :     if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Evap) {
   10281           0 :         RhoAir = PsyRhoAirFnPbTdbW(state, OutdoorPressure, OutdoorDryBulb, OutdoorHumRat);
   10282           0 :         CondAirMassFlow = RhoAir * thisDXCoil.EvapCondAirFlow(Mode);
   10283             :         // (Outdoor wet-bulb temp from DataEnvironment) + (1.0-EvapCondEffectiveness) * (drybulb - wetbulb)
   10284           0 :         CondInletTemp = OutdoorWetBulb + (OutdoorDryBulb - OutdoorWetBulb) * (1.0 - thisDXCoil.EvapCondEffect(Mode));
   10285           0 :         CondInletHumRat = PsyWFnTdbTwbPb(state, CondInletTemp, OutdoorWetBulb, OutdoorPressure);
   10286           0 :         CompAmbTemp = OutdoorDryBulb;
   10287             :     } else {                            // for air or water-cooled, inlet temp is stored in OutdoorDryBulb temp
   10288     1704105 :         CondInletTemp = OutdoorDryBulb; // Outdoor dry-bulb temp or water inlet temp
   10289     1704105 :         if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Water) {
   10290      156109 :             CompAmbTemp = state.dataEnvrn->OutDryBulbTemp; // for crankcase heater use actual outdoor temp for water-cooled
   10291             :         } else {
   10292     1547996 :             CompAmbTemp = OutdoorDryBulb;
   10293             :         }
   10294             :     }
   10295             : 
   10296             :     // Initialize crankcase heater, operates below OAT defined in input deck for HP DX cooling coil
   10297             :     // If used in a heat pump, the value of MaxOAT in the heating coil overrides that in the cooling coil (in GetInput)
   10298     1704105 :     if (CompAmbTemp < thisDXCoil.MaxOATCrankcaseHeater) {
   10299       90229 :         CrankcaseHeatingPower = thisDXCoil.CrankcaseHeaterCapacity;
   10300       90229 :         if (thisDXCoil.CrankcaseHeaterCapacityCurveIndex > 0) {
   10301           0 :             CrankcaseHeatingPower *= Curve::CurveValue(state, thisDXCoil.CrankcaseHeaterCapacityCurveIndex, CompAmbTemp);
   10302             :         }
   10303             :     } else {
   10304     1613876 :         CrankcaseHeatingPower = 0.0;
   10305             :     }
   10306             : 
   10307             :     // calculate end time of current time step to determine if error messages should be printed
   10308     1704105 :     state.dataDXCoils->CalcVRFCoolingCoilCurrentEndTime = state.dataGlobal->CurrentTime + SysTimeElapsed;
   10309             : 
   10310             :     //   Print warning messages only when valid and only for the first ocurrance. Let summary provide statistics.
   10311             :     //   Wait for next time step to print warnings. If simulation iterates, print out
   10312             :     //   the warning for the last iteration only. Must wait for next time step to accomplish this.
   10313             :     //   If a warning occurs and the simulation down shifts, the warning is not valid.
   10314     1704105 :     if (thisDXCoil.PrintLowAmbMessage) { // .AND. &
   10315           0 :         if (state.dataDXCoils->CalcVRFCoolingCoilCurrentEndTime > thisDXCoil.CurrentEndTimeLast && TimeStepSys >= thisDXCoil.TimeStepSysLast) {
   10316           0 :             if (thisDXCoil.LowAmbErrIndex == 0) {
   10317           0 :                 ShowWarningMessage(state, thisDXCoil.LowAmbBuffer1);
   10318           0 :                 ShowContinueError(state, thisDXCoil.LowAmbBuffer2);
   10319           0 :                 ShowContinueError(state, "... Operation at low inlet temperatures may require special performance curves.");
   10320             :             }
   10321           0 :             ShowRecurringWarningErrorAtEnd(state,
   10322           0 :                                            thisDXCoil.DXCoilType + " \"" + thisDXCoil.Name +
   10323             :                                                "\" - Low condenser inlet temperature error continues...",
   10324           0 :                                            thisDXCoil.LowAmbErrIndex,
   10325           0 :                                            thisDXCoil.LowTempLast,
   10326           0 :                                            thisDXCoil.LowTempLast,
   10327             :                                            _,
   10328             :                                            "[C]",
   10329             :                                            "[C]");
   10330             :         }
   10331             :     }
   10332             : 
   10333     1704105 :     if (thisDXCoil.PrintHighAmbMessage) { // .AND. &
   10334           0 :         if (state.dataDXCoils->CalcVRFCoolingCoilCurrentEndTime > thisDXCoil.CurrentEndTimeLast && TimeStepSys >= thisDXCoil.TimeStepSysLast) {
   10335           0 :             if (thisDXCoil.HighAmbErrIndex == 0) {
   10336           0 :                 ShowWarningMessage(state, thisDXCoil.HighAmbBuffer1);
   10337           0 :                 ShowContinueError(state, thisDXCoil.HighAmbBuffer2);
   10338           0 :                 ShowContinueError(state, "... Operation at high inlet temperatures may require special performance curves.");
   10339             :             }
   10340           0 :             ShowRecurringWarningErrorAtEnd(state,
   10341           0 :                                            thisDXCoil.DXCoilType + " \"" + thisDXCoil.Name +
   10342             :                                                "\" - High condenser inlet temperature error continues...",
   10343           0 :                                            thisDXCoil.HighAmbErrIndex,
   10344           0 :                                            thisDXCoil.HighTempLast,
   10345           0 :                                            thisDXCoil.HighTempLast,
   10346             :                                            _,
   10347             :                                            "[C]",
   10348             :                                            "[C]");
   10349             :         }
   10350             :     }
   10351             : 
   10352     1704105 :     if (thisDXCoil.PrintLowOutTempMessage) {
   10353           0 :         if (state.dataDXCoils->CalcVRFCoolingCoilCurrentEndTime > thisDXCoil.CurrentEndTimeLast && TimeStepSys >= thisDXCoil.TimeStepSysLast) {
   10354           0 :             if (thisDXCoil.LowOutletTempIndex == 0) {
   10355           0 :                 ShowWarningMessage(state, thisDXCoil.LowOutTempBuffer1);
   10356           0 :                 ShowContinueError(state, thisDXCoil.LowOutTempBuffer2);
   10357           0 :                 ShowContinueError(state, "... Possible reasons for low outlet air dry-bulb temperatures are: This DX coil");
   10358           0 :                 ShowContinueError(state,
   10359           0 :                                   format("   1) may have a low inlet air dry-bulb temperature. Inlet air temperature = {:.3T} C.",
   10360           0 :                                          thisDXCoil.FullLoadInletAirTempLast));
   10361           0 :                 ShowContinueError(state, "   2) may have a low air flow rate per watt of cooling capacity. Check inputs.");
   10362           0 :                 ShowContinueError(state,
   10363             :                                   "   3) is used as part of a HX assisted cooling coil which uses a high sensible effectiveness. Check inputs.");
   10364             :             }
   10365           0 :             ShowRecurringWarningErrorAtEnd(state,
   10366           0 :                                            thisDXCoil.DXCoilType + " \"" + thisDXCoil.Name +
   10367             :                                                "\" - Full load outlet temperature indicates a possibility of frost/freeze error continues. "
   10368             :                                                "Outlet air temperature statistics follow:",
   10369           0 :                                            thisDXCoil.LowOutletTempIndex,
   10370           0 :                                            thisDXCoil.FullLoadOutAirTempLast,
   10371           0 :                                            thisDXCoil.FullLoadOutAirTempLast);
   10372             :         }
   10373             :     }
   10374             : 
   10375             :     // save last system time step and last end time of current time step (used to determine if warning is valid)
   10376     1704105 :     thisDXCoil.TimeStepSysLast = TimeStepSys;
   10377     1704105 :     thisDXCoil.CurrentEndTimeLast = state.dataDXCoils->CalcVRFCoolingCoilCurrentEndTime;
   10378     1704105 :     thisDXCoil.PrintLowAmbMessage = false;
   10379     1704105 :     thisDXCoil.PrintLowOutTempMessage = false;
   10380             : 
   10381     1704105 :     if ((AirMassFlow > 0.0) && (GetCurrentScheduleValue(state, thisDXCoil.SchedPtr) > 0.0) && (PartLoadRatio > 0.0) &&
   10382             :         (compressorOp == HVAC::CompressorOp::On)) { // for cycling fan, reset mass flow to full on rate
   10383      933576 :         if (fanOp == HVAC::FanOp::Cycling) {
   10384      252614 :             AirMassFlow /= PartLoadRatio;
   10385      680962 :         } else if (fanOp == HVAC::FanOp::Continuous) {
   10386      680962 :             AirMassFlow *= AirFlowRatio;
   10387             :         } else {
   10388           0 :             AirMassFlow = thisDXCoil.RatedAirMassFlowRate(Mode);
   10389             :         }
   10390             : 
   10391             :         // Check for valid air volume flow per rated total cooling capacity (200 - 500 cfm/ton)
   10392             : 
   10393             :         // for some reason there are diff's when using coil inlet air pressure
   10394             :         // these lines (more to follow) are commented out for the time being
   10395             : 
   10396      933576 :         InletAirWetBulbC = PsyTwbFnTdbWPb(state, InletAirDryBulbTemp, InletAirHumRat, OutdoorPressure);
   10397      933576 :         AirVolumeFlowRate = AirMassFlow / PsyRhoAirFnPbTdbW(state, OutdoorPressure, InletAirDryBulbTemp, InletAirHumRat);
   10398      933576 :         VolFlowperRatedTotCap = AirVolumeFlowRate / thisDXCoil.RatedTotCap(Mode);
   10399             : 
   10400      933576 :         if (thisDXCoil.RatedTotCap(Mode) <= 0.0) {
   10401           0 :             ShowFatalError(state, format("{} \"{}\" - Rated total cooling capacity is zero or less.", thisDXCoil.DXCoilType, thisDXCoil.Name));
   10402             :         }
   10403             : 
   10404      999607 :         if (!FirstHVACIteration && !state.dataGlobal->WarmupFlag &&
   10405       66031 :             ((VolFlowperRatedTotCap < HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) ||
   10406       65703 :              (VolFlowperRatedTotCap > HVAC::MaxCoolVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]))) {
   10407         328 :             if (thisDXCoil.ErrIndex1 == 0) {
   10408           2 :                 ShowWarningMessage(
   10409             :                     state,
   10410           2 :                     format("{} \"{}\" - Air volume flow rate per watt of rated total cooling capacity is out of range at {:.3R} m3/s/W.",
   10411           1 :                            thisDXCoil.DXCoilType,
   10412           1 :                            thisDXCoil.Name,
   10413             :                            VolFlowperRatedTotCap));
   10414           1 :                 ShowContinueErrorTimeStamp(state, "");
   10415           2 :                 ShowContinueError(state,
   10416           2 :                                   format("...Expected range for VolumeFlowPerRatedTotalCapacity=[{:.3R}--{:.3R}]",
   10417           1 :                                          HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   10418           1 :                                          HVAC::MaxCoolVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]));
   10419           1 :                 ShowContinueError(state, "...Possible causes include inconsistent air flow rates in system components,");
   10420           1 :                 ShowContinueError(state, "...or mixing manual inputs with autosize inputs. Also check the following values and calculations.");
   10421           1 :                 ShowContinueError(state, "...Volume Flow Rate per Rated Total Capacity = Volume Flow Rate / Rated Total Capacity");
   10422           1 :                 ShowContinueError(state, "...Volume Flow Rate = Air Mass Flow Rate / Air Density");
   10423           1 :                 ShowContinueError(state, "...Data used for calculations:");
   10424           1 :                 ShowContinueError(state, format("...Rated Total Capacity = {:.2R} W.", thisDXCoil.RatedTotCap(Mode)));
   10425           1 :                 ShowContinueError(state, "...Volume Flow Rate = Air Mass Flow Rate / Air Density");
   10426           1 :                 ShowContinueError(state, format("...Volume Flow Rate   = {:.8R} m3/s.", AirVolumeFlowRate));
   10427           1 :                 ShowContinueError(state, format("...Air Mass Flow Rate = {:.8R} kg/s.", AirMassFlow));
   10428           2 :                 ShowContinueError(
   10429             :                     state,
   10430           2 :                     format("...Air Density        = {:.8R} kg/m3.", PsyRhoAirFnPbTdbW(state, OutdoorPressure, InletAirDryBulbTemp, InletAirHumRat)));
   10431           1 :                 ShowContinueError(state, "...Data used for air density calculation:");
   10432           1 :                 ShowContinueError(state, format("...Outdoor Air Pressure     = {:.3R} Pa.", OutdoorPressure));
   10433           1 :                 ShowContinueError(state, format("...Inlet Air Dry-Bulb Temp  = {:.3R} C.", InletAirDryBulbTemp));
   10434           1 :                 ShowContinueError(state, format("...Inlet Air Humidity Ratio = {:.8R} kgWater/kgDryAir.", InletAirHumRat));
   10435             :             }
   10436         984 :             ShowRecurringWarningErrorAtEnd(
   10437             :                 state,
   10438         656 :                 thisDXCoil.DXCoilType + " \"" + thisDXCoil.Name +
   10439             :                     "\" - Air volume flow rate per watt of rated total cooling capacity is out of range error continues...",
   10440         328 :                 thisDXCoil.ErrIndex1,
   10441             :                 VolFlowperRatedTotCap,
   10442             :                 VolFlowperRatedTotCap);
   10443             :         }
   10444             :         //    Adjust coil bypass factor for actual air flow rate. Use relation CBF = exp(-NTU) where
   10445             :         //    NTU = A0/(m*cp). Relationship models the cooling coil as a heat exchanger with Cmin/Cmax = 0.
   10446             : 
   10447      933576 :         RatedCBF = thisDXCoil.RatedCBF(Mode);
   10448      933576 :         if (RatedCBF > 0.0) {
   10449      933576 :             A0 = -std::log(RatedCBF) * thisDXCoil.RatedAirMassFlowRate(Mode);
   10450             :         } else {
   10451           0 :             A0 = 0.0;
   10452             :         }
   10453      933576 :         ADiff = -A0 / AirMassFlow;
   10454      933576 :         if (ADiff >= DataPrecisionGlobals::EXP_LowerLimit) {
   10455      933576 :             CBF = std::exp(ADiff);
   10456             :         } else {
   10457           0 :             CBF = 0.0;
   10458             :         }
   10459             : 
   10460             :         // check boundary for low ambient temperature and post warnings to individual DX coil buffers to print at end of time step
   10461      933576 :         if (OutdoorDryBulb < thisDXCoil.MinOATCompressor && !state.dataGlobal->WarmupFlag) {
   10462           0 :             thisDXCoil.PrintLowAmbMessage = true;
   10463           0 :             thisDXCoil.LowTempLast = OutdoorDryBulb;
   10464           0 :             if (thisDXCoil.LowAmbErrIndex == 0) {
   10465           0 :                 thisDXCoil.LowAmbBuffer1 = format("{} \"{}\" - Condenser inlet temperature below {:.2R} C. Condenser inlet temperature = {:.2R}",
   10466           0 :                                                   thisDXCoil.DXCoilType,
   10467           0 :                                                   thisDXCoil.Name,
   10468           0 :                                                   thisDXCoil.MinOATCompressor,
   10469           0 :                                                   OutdoorDryBulb);
   10470           0 :                 thisDXCoil.LowAmbBuffer2 = " ... Occurrence info = " + state.dataEnvrn->EnvironmentName + ", " + state.dataEnvrn->CurMnDy + ' ' +
   10471           0 :                                            CreateSysTimeIntervalString(state);
   10472             :             }
   10473             :         }
   10474             : 
   10475             :         // check boundary for high ambient temperature and post warnings to individual DX coil buffers to print at end of time step
   10476      933576 :         if (OutdoorDryBulb > thisDXCoil.MaxOATCompressor && !state.dataGlobal->WarmupFlag) {
   10477           0 :             thisDXCoil.PrintHighAmbMessage = true;
   10478           0 :             thisDXCoil.HighTempLast = OutdoorDryBulb;
   10479           0 :             if (thisDXCoil.HighAmbErrIndex == 0) {
   10480           0 :                 thisDXCoil.HighAmbBuffer1 = format("{} \"{}\" - Condenser inlet temperature above {:.2R} C. Condenser temperature = {:.2R}",
   10481           0 :                                                    thisDXCoil.DXCoilType,
   10482           0 :                                                    thisDXCoil.Name,
   10483           0 :                                                    thisDXCoil.MaxOATCompressor,
   10484           0 :                                                    OutdoorDryBulb);
   10485           0 :                 thisDXCoil.HighAmbBuffer2 = " ... Occurrence info = " + state.dataEnvrn->EnvironmentName + ", " + state.dataEnvrn->CurMnDy + ' ' +
   10486           0 :                                             CreateSysTimeIntervalString(state);
   10487             :             }
   10488             :         }
   10489             : 
   10490             :         //  Get total capacity modifying factor (function of temperature) for off-rated conditions
   10491             :         //  InletAirHumRat may be modified in this ADP/BF loop, use temporary varible for calculations
   10492      933576 :         InletAirHumRatTemp = InletAirHumRat;
   10493             : 
   10494      933576 :     Label50:;
   10495      933576 :         switch (state.dataCurveManager->PerfCurve(thisDXCoil.CCapFTemp(Mode))->numDims) {
   10496      693423 :         case 1:
   10497      693423 :             TotCapTempModFac = CurveValue(state, thisDXCoil.CCapFTemp(Mode), InletAirWetBulbC);
   10498      693423 :             break;
   10499      240153 :         case 2:
   10500             :         default: // this default allows the simulation to continue, but will issue a warning, should be removed eventually
   10501      240153 :             TotCapTempModFac = CurveValue(state, thisDXCoil.CCapFTemp(Mode), InletAirWetBulbC, CondInletTemp);
   10502      240153 :             break;
   10503             :         }
   10504             : 
   10505             :         //  Warn user if curve output goes negative
   10506      933576 :         if (TotCapTempModFac < 0.0) {
   10507           0 :             if (thisDXCoil.CCapFTempErrorIndex == 0) {
   10508           0 :                 ShowWarningMessage(state, format("{} \"{}\":", thisDXCoil.DXCoilType, thisDXCoil.Name));
   10509           0 :                 ShowContinueError(
   10510           0 :                     state, format(" Total Cooling Capacity Modifier curve (function of temperature) output is negative ({:.3T}).", TotCapTempModFac));
   10511           0 :                 ShowContinueError(
   10512             :                     state,
   10513           0 :                     format(" Negative value occurs using a condenser inlet temperature of {:.1T} and an inlet air wet-bulb temperature of {:.1T}.",
   10514             :                            CondInletTemp,
   10515             :                            InletAirWetBulbC));
   10516           0 :                 if (Mode > 1) {
   10517           0 :                     ShowContinueError(state, format(" Negative output results from stage {} compressor operation.", Mode));
   10518             :                 }
   10519           0 :                 ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
   10520             :             }
   10521           0 :             ShowRecurringWarningErrorAtEnd(
   10522             :                 state,
   10523           0 :                 thisDXCoil.DXCoilType + " \"" + thisDXCoil.Name +
   10524             :                     "\": Total Cooling Capacity Modifier curve (function of temperature) output is negative warning continues...",
   10525           0 :                 thisDXCoil.CCapFTempErrorIndex,
   10526             :                 TotCapTempModFac,
   10527             :                 TotCapTempModFac);
   10528           0 :             TotCapTempModFac = 0.0;
   10529             :         }
   10530             : 
   10531             :         //  Get total capacity modifying factor (function of mass flow) for off-rated conditions
   10532      933576 :         AirMassFlowRatio = AirMassFlow / thisDXCoil.RatedAirMassFlowRate(Mode);
   10533      933576 :         TotCapFlowModFac = CurveValue(state, thisDXCoil.CCapFFlow(Mode), AirMassFlowRatio);
   10534             : 
   10535             :         //  Warn user if curve output goes negative
   10536      933576 :         if (TotCapFlowModFac < 0.0) {
   10537           0 :             if (thisDXCoil.CCapFFlowErrorIndex == 0) {
   10538           0 :                 ShowWarningMessage(state, format("{} \"{}\":", thisDXCoil.DXCoilType, thisDXCoil.Name));
   10539           0 :                 ShowContinueError(
   10540             :                     state,
   10541           0 :                     format(" Total Cooling Capacity Modifier curve (function of flow fraction) output is negative ({:.3T}).", TotCapFlowModFac));
   10542           0 :                 ShowContinueError(state, format(" Negative value occurs using an air flow fraction of {:.3T}.", AirMassFlowRatio));
   10543           0 :                 ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
   10544           0 :                 if (Mode > 1) {
   10545           0 :                     ShowContinueError(state, format(" Negative output results from stage {} compressor operation.", Mode));
   10546             :                 }
   10547             :             }
   10548           0 :             ShowRecurringWarningErrorAtEnd(
   10549             :                 state,
   10550           0 :                 thisDXCoil.DXCoilType + " \"" + thisDXCoil.Name +
   10551             :                     "\": Total Cooling Capacity Modifier curve (function of flow fraction) output is negative warning continues...",
   10552           0 :                 thisDXCoil.CCapFFlowErrorIndex,
   10553             :                 TotCapFlowModFac,
   10554             :                 TotCapFlowModFac);
   10555           0 :             TotCapFlowModFac = 0.0;
   10556             :         }
   10557             : 
   10558      933576 :         if (present(MaxCoolCap)) {
   10559      933530 :             TotCap = min(MaxCoolCap, thisDXCoil.RatedTotCap(Mode) * TotCapFlowModFac * TotCapTempModFac);
   10560             :         } else {
   10561          46 :             TotCap = thisDXCoil.RatedTotCap(Mode) * TotCapFlowModFac * TotCapTempModFac;
   10562             :         }
   10563             : 
   10564      933576 :         TotCap *= PartLoadRatio;
   10565             : 
   10566             :         // Calculate apparatus dew point conditions using TotCap and CBF
   10567      933576 :         hDelta = TotCap / AirMassFlow;
   10568             :         // there is an issue here with using CBF to calculate the ADP enthalpy.
   10569             :         // at low loads the bypass factor increases significantly.
   10570      933576 :         hADP = InletAirEnthalpy - hDelta / (1.0 - CBF);
   10571      933576 :         tADP = PsyTsatFnHPb(state, hADP, OutdoorPressure, RoutineName);
   10572             :         //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   10573             :         //  tADP = PsyTsatFnHPb(hADP,InletAirPressure)
   10574      933576 :         wADP = min(InletAirHumRat, PsyWFnTdbH(state, tADP, hADP, RoutineName));
   10575      933576 :         hTinwADP = PsyHFnTdbW(InletAirDryBulbTemp, wADP);
   10576      933576 :         if ((InletAirEnthalpy - hADP) > 1.e-10) {
   10577      853825 :             SHR = min((hTinwADP - hADP) / (InletAirEnthalpy - hADP), 1.0);
   10578             :         } else {
   10579       79751 :             SHR = 1.0;
   10580             :         }
   10581             :         // Check for dry evaporator conditions (win < wadp)
   10582      933576 :         if (wADP > InletAirHumRatTemp || (Counter >= 1 && Counter < MaxIter)) {
   10583           0 :             if (InletAirHumRatTemp == 0.0) InletAirHumRatTemp = 0.00001;
   10584           0 :             werror = (InletAirHumRatTemp - wADP) / InletAirHumRatTemp;
   10585             :             // Increase InletAirHumRatTemp at constant InletAirTemp to find coil dry-out point. Then use the
   10586             :             // capacity at the dry-out point to determine exiting conditions from coil. This is required
   10587             :             // since the TotCapTempModFac doesn't work properly with dry-coil conditions.
   10588           0 :             InletAirHumRatTemp = RF * wADP + (1.0 - RF) * InletAirHumRatTemp;
   10589           0 :             InletAirWetBulbC = PsyTwbFnTdbWPb(state, InletAirDryBulbTemp, InletAirHumRatTemp, OutdoorPressure);
   10590             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   10591             :             //     InletAirWetBulbC = PsyTwbFnTdbWPb(InletAirDryBulbTemp,InletAirHumRatTemp,InletAirPressure)
   10592           0 :             ++Counter;
   10593           0 :             if (std::abs(werror) > Tolerance) goto Label50; // Recalculate with modified inlet conditions
   10594             :         }
   10595             : 
   10596      933576 :         if (thisDXCoil.PLFFPLR(Mode) > 0 && CompCycRatio < 1.0) {
   10597           0 :             PLF = CurveValue(state, thisDXCoil.PLFFPLR(Mode), CompCycRatio); // Calculate part-load factor
   10598             :         } else {
   10599      933576 :             PLF = 1.0;
   10600             :         }
   10601             : 
   10602      933576 :         if (PLF < 0.7) {
   10603           0 :             if (thisDXCoil.ErrIndex2 == 0) {
   10604           0 :                 ShowWarningMessage(
   10605             :                     state,
   10606           0 :                     format(
   10607           0 :                         "The PLF curve value for the DX cooling coil {} ={:.3R} for part-load ratio ={:.3R}", thisDXCoil.Name, PLF, PartLoadRatio));
   10608           0 :                 ShowContinueErrorTimeStamp(state, "PLF curve values must be >= 0.7. PLF has been reset to 0.7 and simulation is continuing.");
   10609           0 :                 ShowContinueError(state, "Check the IO reference manual for PLF curve guidance [Coil:Cooling:DX:SingleSpeed].");
   10610             :             }
   10611           0 :             ShowRecurringWarningErrorAtEnd(
   10612           0 :                 state, thisDXCoil.Name + ", DX cooling coil PLF curve < 0.7 warning continues...", thisDXCoil.ErrIndex2, PLF, PLF);
   10613           0 :             PLF = 0.7;
   10614             :         }
   10615             : 
   10616      933576 :         thisDXCoil.PartLoadRatio = PartLoadRatio;
   10617      933576 :         thisDXCoil.CoolingCoilRuntimeFraction = CompCycRatio / PLF;
   10618      933576 :         if (thisDXCoil.CoolingCoilRuntimeFraction > 1.0 && std::abs(thisDXCoil.CoolingCoilRuntimeFraction - 1.0) > 0.001) {
   10619           0 :             if (thisDXCoil.ErrIndex3 == 0) {
   10620           0 :                 ShowWarningMessage(state,
   10621           0 :                                    format("The runtime fraction for DX cooling coil {} exceeded 1.0. [{:.4R}].",
   10622           0 :                                           thisDXCoil.Name,
   10623           0 :                                           thisDXCoil.CoolingCoilRuntimeFraction));
   10624           0 :                 ShowContinueError(state, "Runtime fraction reset to 1 and the simulation will continue.");
   10625           0 :                 ShowContinueError(state, "Check the IO reference manual for PLF curve guidance [Coil:Cooling:DX:SingleSpeed].");
   10626           0 :                 ShowContinueErrorTimeStamp(state, "");
   10627             :             }
   10628           0 :             ShowRecurringWarningErrorAtEnd(state,
   10629           0 :                                            thisDXCoil.Name + ", DX cooling coil runtime fraction > 1.0 warning continues...",
   10630           0 :                                            thisDXCoil.ErrIndex3,
   10631           0 :                                            thisDXCoil.CoolingCoilRuntimeFraction,
   10632           0 :                                            thisDXCoil.CoolingCoilRuntimeFraction);
   10633           0 :             thisDXCoil.CoolingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   10634      933576 :         } else if (thisDXCoil.CoolingCoilRuntimeFraction > 1.0) {
   10635           0 :             thisDXCoil.CoolingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   10636             :         }
   10637             : 
   10638             :         // If cycling fan, send coil part-load fraction to on/off fan via HVACDataGlobals
   10639      933576 :         if (fanOp == HVAC::FanOp::Cycling) state.dataHVACGlobal->OnOffFanPartLoadFraction = PLF;
   10640             : 
   10641             :         //  Calculate full load output conditions
   10642             :         //            if ( SHR > 1.0 || Counter > 0 ) SHR = 1.0;
   10643      933576 :         if (SHR > 1.0) SHR = 1.0;
   10644      933576 :         FullLoadOutAirEnth = InletAirEnthalpy - TotCap / AirMassFlow;
   10645      933576 :         hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
   10646      933576 :         if (SHR < 1.0) {
   10647      603302 :             FullLoadOutAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout);
   10648             :         } else {
   10649      330274 :             FullLoadOutAirHumRat = InletAirHumRat;
   10650             :         }
   10651      933576 :         FullLoadOutAirTemp = PsyTdbFnHW(FullLoadOutAirEnth, FullLoadOutAirHumRat);
   10652             : 
   10653             :         // Check for saturation error and modify temperature at constant enthalpy
   10654      933576 :         if (FullLoadOutAirTemp < PsyTsatFnHPb(state, FullLoadOutAirEnth, OutdoorPressure)) {
   10655         765 :             FullLoadOutAirTemp = PsyTsatFnHPb(state, FullLoadOutAirEnth, OutdoorPressure);
   10656             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   10657             :             //   IF(FullLoadOutAirTemp .LT. PsyTsatFnHPb(FullLoadOutAirEnth,InletAirPressure)) THEN
   10658             :             //    FullLoadOutAirTemp = PsyTsatFnHPb(FullLoadOutAirEnth,InletAirPressure)
   10659         765 :             FullLoadOutAirHumRat = PsyWFnTdbH(state, FullLoadOutAirTemp, FullLoadOutAirEnth);
   10660             :         }
   10661             : 
   10662             :         // Store actual outlet conditions when DX coil is ON for use in heat recovery module
   10663      933576 :         state.dataDXCoils->DXCoilFullLoadOutAirTemp(DXCoilNum) = FullLoadOutAirTemp;
   10664      933576 :         state.dataDXCoils->DXCoilFullLoadOutAirHumRat(DXCoilNum) = FullLoadOutAirHumRat;
   10665             : 
   10666             :         // Add warning message for cold cooling coil (FullLoadOutAirTemp < 2 C)
   10667      933576 :         if (FullLoadOutAirTemp < 2.0 && !FirstHVACIteration && !state.dataGlobal->WarmupFlag) {
   10668           0 :             thisDXCoil.PrintLowOutTempMessage = true;
   10669           0 :             thisDXCoil.FullLoadOutAirTempLast = FullLoadOutAirTemp;
   10670           0 :             if (thisDXCoil.LowOutletTempIndex == 0) {
   10671           0 :                 thisDXCoil.FullLoadInletAirTempLast = InletAirDryBulbTemp;
   10672           0 :                 thisDXCoil.LowOutTempBuffer1 = format("{} \"{}\" - Full load outlet air dry-bulb temperature < 2C. This indicates the "
   10673             :                                                       "possibility of coil frost/freeze. Outlet temperature = {:.2R} C.",
   10674           0 :                                                       thisDXCoil.DXCoilType,
   10675           0 :                                                       thisDXCoil.Name,
   10676           0 :                                                       FullLoadOutAirTemp);
   10677           0 :                 thisDXCoil.LowOutTempBuffer2 = " ...Occurrence info = " + state.dataEnvrn->EnvironmentName + ", " + state.dataEnvrn->CurMnDy + ' ' +
   10678           0 :                                                CreateSysTimeIntervalString(state);
   10679             :             }
   10680             :         }
   10681             : 
   10682             :         //  If constant fan with cycling compressor, call function to determine "effective SHR"
   10683             :         //  which includes the part-load degradation on latent capacity
   10684      933576 :         if (fanOp == HVAC::FanOp::Continuous && CompCycRatio < 1.0) {
   10685      284079 :             QLatRated = thisDXCoil.RatedTotCap(Mode) * (1.0 - thisDXCoil.RatedSHR(Mode)); // always the same number
   10686      284079 :             QLatActual = TotCap * (1.0 - SHR);
   10687      284079 :             SHRUnadjusted = SHR;
   10688      284079 :             SHR = CalcEffectiveSHR(
   10689             :                 state, DXCoilNum, SHR, thisDXCoil.CoolingCoilRuntimeFraction, QLatRated, QLatActual, InletAirDryBulbTemp, InletAirWetBulbC, Mode);
   10690             : 
   10691             :             //  Calculate full load output conditions
   10692             :             //                if ( SHR > 1.0 || Counter > 0 ) SHR = 1.0;
   10693      284079 :             if (SHR > 1.0) SHR = 1.0;
   10694      284079 :             FullLoadOutAirEnth = InletAirEnthalpy - TotCap / AirMassFlow;
   10695      284079 :             hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
   10696      284079 :             if (SHR < 1.0) {
   10697      183279 :                 FullLoadOutAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout);
   10698             :             } else {
   10699      100800 :                 FullLoadOutAirHumRat = InletAirHumRat;
   10700             :             }
   10701      284079 :             FullLoadOutAirTemp = PsyTdbFnHW(FullLoadOutAirEnth, FullLoadOutAirHumRat);
   10702             :         }
   10703             : 
   10704             :         //  Calculate actual outlet conditions for the input part load ratio
   10705             :         //  Actual outlet conditions are "average" for time step when compressor cycles
   10706             : 
   10707      933576 :         if (fanOp == HVAC::FanOp::Continuous && CompCycRatio < 1.0) {
   10708             :             // Continuous fan, cycling compressor
   10709             :             // hmmm ... this seems wrong. PLR * AirFlowRatio = 1. So we get FullLoadOutAirEnth all this time. This is OK since above TotCap *=
   10710             :             // PLR.
   10711      284079 :             OutletAirEnthalpy = ((PartLoadRatio * AirFlowRatio) * FullLoadOutAirEnth + (1.0 - (PartLoadRatio * AirFlowRatio)) * InletAirEnthalpy);
   10712      284079 :             OutletAirHumRat = ((PartLoadRatio * AirFlowRatio) * FullLoadOutAirHumRat + (1.0 - (PartLoadRatio * AirFlowRatio)) * InletAirHumRat);
   10713      284079 :             OutletAirTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
   10714             :         } else {
   10715             :             // Default to cycling fan, cycling compressor
   10716      649497 :             OutletAirEnthalpy = FullLoadOutAirEnth;
   10717      649497 :             OutletAirHumRat = FullLoadOutAirHumRat;
   10718      649497 :             OutletAirTemp = FullLoadOutAirTemp;
   10719             :         }
   10720             : 
   10721             :         // Check for saturation error and modify temperature at constant enthalpy
   10722      933576 :         if (OutletAirTemp < PsyTsatFnHPb(state, OutletAirEnthalpy, OutdoorPressure, RoutineName)) {
   10723        3982 :             OutletAirTemp = PsyTsatFnHPb(state, OutletAirEnthalpy, OutdoorPressure);
   10724             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   10725             :             //   IF(OutletAirTemp .LT. PsyTsatFnHPb(OutletAirEnthalpy,InletAirPressure)) THEN
   10726             :             //    OutletAirTemp = PsyTsatFnHPb(OutletAirEnthalpy,InletAirPressure)
   10727        3982 :             OutletAirHumRat = PsyWFnTdbH(state, OutletAirTemp, OutletAirEnthalpy);
   10728             :         }
   10729             : 
   10730             :         // Reset AirMassFlow to inlet node air mass flow for final total, sensible and latent calculations
   10731             :         // since AirMassFlow might have been modified above (in this subroutine):
   10732             :         //     IF (FanOpMode .EQ. FanOp::Cycling) AirMassFlow = AirMassFlow / PartLoadRatio
   10733             :         // For multimode coil, this should be full flow including bypassed fraction
   10734      933576 :         AirMassFlow = thisDXCoil.InletAirMassFlowRate;
   10735             : 
   10736             :         // Coil total/sensible/latent cooling rates
   10737      933576 :         CalcComponentSensibleLatentOutput(AirMassFlow,
   10738             :                                           InletAirDryBulbTemp,
   10739             :                                           InletAirHumRat,
   10740             :                                           OutletAirTemp,
   10741             :                                           OutletAirHumRat,
   10742      933576 :                                           thisDXCoil.SensCoolingEnergyRate,
   10743      933576 :                                           thisDXCoil.LatCoolingEnergyRate,
   10744      933576 :                                           thisDXCoil.TotalCoolingEnergyRate);
   10745             : 
   10746      933576 :         thisDXCoil.OutletAirTemp = OutletAirTemp;
   10747      933576 :         thisDXCoil.OutletAirHumRat = OutletAirHumRat;
   10748      933576 :         thisDXCoil.OutletAirEnthalpy = OutletAirEnthalpy;
   10749             : 
   10750             :     } else {
   10751             : 
   10752             :         // DX coil is off; just pass through conditions
   10753      770529 :         thisDXCoil.OutletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   10754      770529 :         thisDXCoil.OutletAirHumRat = thisDXCoil.InletAirHumRat;
   10755      770529 :         thisDXCoil.OutletAirTemp = thisDXCoil.InletAirTemp;
   10756             : 
   10757      770529 :         thisDXCoil.ElecCoolingPower = 0.0;
   10758      770529 :         thisDXCoil.TotalCoolingEnergyRate = 0.0;
   10759      770529 :         thisDXCoil.SensCoolingEnergyRate = 0.0;
   10760      770529 :         thisDXCoil.LatCoolingEnergyRate = 0.0;
   10761      770529 :         thisDXCoil.EvapCondPumpElecPower = 0.0;
   10762      770529 :         thisDXCoil.EvapWaterConsumpRate = 0.0;
   10763             : 
   10764             :         // Reset globals when DX coil is OFF for use in heat recovery module
   10765      770529 :         state.dataDXCoils->DXCoilFullLoadOutAirTemp(DXCoilNum) = 0.0;
   10766      770529 :         state.dataDXCoils->DXCoilFullLoadOutAirHumRat(DXCoilNum) = 0.0;
   10767             : 
   10768             :     } // end of on/off if - else
   10769             : 
   10770             :     // set water system demand request (if needed)
   10771     1704105 :     if (thisDXCoil.EvapWaterSupplyMode == EvapWaterSupply::FromTank) {
   10772           0 :         state.dataWaterData->WaterStorage(thisDXCoil.EvapWaterSupTankID).VdotRequestDemand(thisDXCoil.EvapWaterTankDemandARRID) =
   10773           0 :             thisDXCoil.EvapWaterConsumpRate;
   10774             :     }
   10775             : 
   10776     1704105 :     state.dataDXCoils->DXCoilOutletTemp(DXCoilNum) = thisDXCoil.OutletAirTemp;
   10777     1704105 :     state.dataDXCoils->DXCoilOutletHumRat(DXCoilNum) = thisDXCoil.OutletAirHumRat;
   10778     1704105 :     state.dataDXCoils->DXCoilPartLoadRatio(DXCoilNum) = thisDXCoil.PartLoadRatio;
   10779     1704105 :     state.dataDXCoils->DXCoilFanOp(DXCoilNum) = fanOp;
   10780     1704105 :     thisDXCoil.CondInletTemp = CondInletTemp;
   10781     1704105 :     state.dataDXCoils->DXCoilTotalCooling(DXCoilNum) = thisDXCoil.TotalCoolingEnergyRate;
   10782     1704105 :     state.dataDXCoils->DXCoilCoolInletAirWBTemp(DXCoilNum) = PsyTwbFnTdbWPb(state, InletAirDryBulbTemp, InletAirHumRat, OutdoorPressure);
   10783             : 
   10784             :     // set outlet node conditions
   10785     1704105 :     int airOutletNode = thisDXCoil.AirOutNode;
   10786     1704105 :     state.dataLoopNodes->Node(airOutletNode).Temp = thisDXCoil.OutletAirTemp;
   10787     1704105 :     state.dataLoopNodes->Node(airOutletNode).HumRat = thisDXCoil.OutletAirHumRat;
   10788     1704105 : }
   10789             : 
   10790     7591276 : void CalcDXHeatingCoil(EnergyPlusData &state,
   10791             :                        int const DXCoilNum,                                 // the number of the DX heating coil to be simulated
   10792             :                        Real64 const PartLoadRatio,                          // sensible cooling load / full load sensible cooling capacity
   10793             :                        HVAC::FanOp const fanOp,                             // Allows parent object to control fan mode
   10794             :                        ObjexxFCL::Optional<Real64 const> OnOffAirFlowRatio, // ratio of compressor on airflow to compressor off airflow
   10795             :                        ObjexxFCL::Optional<Real64 const> MaxHeatCap         // maximum allowed heating capacity
   10796             : )
   10797             : {
   10798             : 
   10799             :     // SUBROUTINE INFORMATION:
   10800             :     //       AUTHOR         Richard Raustad
   10801             :     //       DATE WRITTEN   October 2001
   10802             :     //       MODIFIED       Raustad/Shirey Mar 2004
   10803             :     //                      Kenneth Tang 2004 (Sensitivity of TotCapTempModFac & EIRTempModFac  to indoor dry bulb temp)
   10804             :     //                      Feb 2005 M. J. Witte, GARD Analytics, Inc.
   10805             :     //                        Add new coil type COIL:DX:MultiMode:CoolingEmpirical:
   10806             : 
   10807             :     // PURPOSE OF THIS SUBROUTINE:
   10808             :     // Calculates the air-side heating performance and electrical heating energy
   10809             :     // use of a direct-expansion, air-cooled heat pump unit.
   10810             : 
   10811             :     // METHODOLOGY EMPLOYED:
   10812             :     // This routine simulates the performance of air-cooled DX heating equipment.
   10813             :     // The routine requires the user to enter the total heating capacity
   10814             :     // and COP for the unit at ARI 210/240 rating conditions (21.11C [70F] dry-bulb,
   10815             :     // 15.55C [60F] wet-bulb air entering the heating coil, 8.33C [47F] dry-bulb,
   10816             :     // 6.11C [43F] wet-bulb air entering the outdoor condenser. Since different
   10817             :     // manufacturer's rate their equipment at different air flow rates, the supply
   10818             :     // air flow rate corresponding to the rated capacities and rated COP must also
   10819             :     // be entered (should be between 300 cfm/ton and 450 cfm/ton). The rated information
   10820             :     // entered by the user should NOT include the thermal or electrical impacts of the
   10821             :     // supply air fan, as this is addressed by another module.
   10822             : 
   10823             :     // With the rated performance data entered by the user, the model employs some of the
   10824             :     // DOE-2.1E curve fits to adjust the capacity and efficiency of the unit as a function
   10825             :     // of outdoor air temperatures and supply air flow rate (actual vs rated flow). The
   10826             :     // model does NOT employ the exact same methodology to calculate performance as DOE-2,
   10827             :     // although some of the DOE-2 curve fits are employed by this model.
   10828             : 
   10829             :     // REFERENCES:
   10830             :     // Winkelmann, F.C., Birdsall, B.E., Buhl W.F., Ellington, K.L., Erdem, A.E. 1993.
   10831             :     // DOE-2 Supplement Version 2.1E.  Energy and Environment Division, Larwence Berkely
   10832             :     // Laboratory.
   10833             :     // Henderson, H.I. Jr., Y.J. Huang and Danny Parker. 1999. Residential Equipment Part
   10834             :     // Load Curves for Use in DOE-2.  Environmental Energy Technologies Division, Ernest
   10835             :     // Orlando Lawrence Berkeley National Laboratory.
   10836             : 
   10837             :     // Using/Aliasing
   10838             :     using Curve::CurveValue;
   10839             : 
   10840             :     // SUBROUTINE PARAMETER DEFINITIONS:
   10841             :     static constexpr std::string_view RoutineNameFullLoad("CalcDXHeatingCoil:fullload");
   10842             : 
   10843             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   10844             :     Real64 AirMassFlow;           // dry air mass flow rate through coil [kg/s]
   10845             :     Real64 AirMassFlowRatio;      // Ratio of actual air mass flow to rated air mass flow
   10846             :     Real64 AirVolumeFlowRate;     // Air volume flow rate across the cooling coil [m3/s]
   10847             :     Real64 VolFlowperRatedTotCap; // Air volume flow rate divided by rated total cooling capacity [m3/s-W]
   10848             :     Real64 TotCap;                // gross total cooling capacity at off-rated conditions [W]
   10849             :     Real64 TotCapAdj;             // adjusted total cooling capacity at off-rated conditions [W]
   10850             :     Real64 TotCapTempModFac;      // Total capacity modifier (function of entering drybulb, outside drybulb) depending
   10851             :     // on the type of curve
   10852             :     Real64 TotCapFlowModFac;    // Total capacity modifier (function of actual supply air flow vs rated flow)
   10853             :     Real64 InletAirDryBulbTemp; // inlet air dry bulb temperature [C]
   10854             :     Real64 InletAirWetBulbC;    // wetbulb temperature of inlet air [C]
   10855             :     Real64 InletAirEnthalpy;    // inlet air enthalpy [J/kg]
   10856             :     Real64 InletAirHumRat;      // inlet air humidity ratio [kg/kg]
   10857             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   10858             :     // REAL(r64)     :: InletAirPressure            ! inlet air pressure [Pa]
   10859             :     Real64 FullLoadOutAirEnth;   // outlet full load enthalpy [J/kg]
   10860             :     Real64 FullLoadOutAirHumRat; // outlet humidity ratio at full load
   10861             :     Real64 FullLoadOutAirTemp;   // outlet air temperature at full load [C]
   10862             :     Real64 FullLoadOutAirRH;     // outlet air relative humidity at full load
   10863     7591276 :     Real64 EIRTempModFac(0.0);   // EIR modifier (function of entering drybulb, outside drybulb) depending on the
   10864             :     // type of curve
   10865             :     Real64 DefrostEIRTempModFac;      // EIR modifier for defrost (function of entering wetbulb, outside drybulb)
   10866             :     Real64 EIRFlowModFac;             // EIR modifier (function of actual supply air flow vs rated flow)
   10867             :     Real64 EIR;                       // EIR at part load and off rated conditions
   10868             :     Real64 PLF;                       // Part load factor, accounts for thermal lag at compressor startup
   10869             :     Real64 PLRHeating;                // PartLoadRatio in heating
   10870             :     Real64 OutdoorCoilT;              // Outdoor coil temperature (C)
   10871             :     Real64 OutdoorCoildw;             // Outdoor coil delta w assuming coil temp of OutdoorCoilT (kg/kg)
   10872             :     Real64 FractionalDefrostTime;     // Fraction of time step system is in defrost
   10873             :     Real64 HeatingCapacityMultiplier; // Multiplier for heating capacity when system is in defrost
   10874             :     Real64 InputPowerMultiplier;      // Multiplier for power when system is in defrost
   10875             :     Real64 LoadDueToDefrost;          // Additional load due to defrost
   10876             :     Real64 CrankcaseHeatingPower;     // power due to crankcase heater
   10877             :     Real64 OutdoorDryBulb;            // Outdoor dry-bulb temperature at condenser (C)
   10878             :     Real64 OutdoorWetBulb;            // Outdoor wet-bulb temperature at condenser (C)
   10879             :     Real64 OutdoorHumRat;             // Outdoor humidity ratio at condenser (kg/kg)
   10880             :     Real64 OutdoorPressure;           // Outdoor barometric pressure at condenser (Pa)
   10881     7591276 :     constexpr int Mode(1);            // Performance mode for MultiMode DX coil; Always 1 for other coil types
   10882             :     Real64 AirFlowRatio;              // Ratio of compressor on airflow to average timestep airflow
   10883             :     Real64 OutletAirTemp;             // Supply air temperature (average value if constant fan, full output if cycling fan)
   10884             :     Real64 OutletAirHumRat;           // Supply air humidity ratio (average value if constant fan, full output if cycling fan)
   10885             :     Real64 OutletAirEnthalpy;         // Supply air enthalpy (average value if constant fan, full output if cycling fan)
   10886     7591276 :     Real64 CompAmbTemp(0.0);          // Ambient temperature at compressor
   10887             : 
   10888     7591276 :     if (present(OnOffAirFlowRatio)) {
   10889     7591230 :         AirFlowRatio = OnOffAirFlowRatio;
   10890             :     } else {
   10891          46 :         AirFlowRatio = 1.0;
   10892             :     }
   10893             : 
   10894     7591276 :     auto &DXCT = state.dataHVACGlobal->DXCT;
   10895             : 
   10896     7591276 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   10897             : 
   10898             :     // Get condenser outdoor node info from DX Heating Coil
   10899     7591276 :     if (thisDXCoil.CondenserInletNodeNum(1) != 0) {
   10900     2431409 :         OutdoorDryBulb = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).Temp;
   10901     2431409 :         CompAmbTemp = OutdoorDryBulb;
   10902     2431409 :         if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Water) {
   10903      156109 :             OutdoorHumRat = state.dataEnvrn->OutHumRat;
   10904      156109 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
   10905      156109 :             OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   10906      156109 :             CompAmbTemp = state.dataEnvrn->OutDryBulbTemp;
   10907             :         } else {
   10908     2275300 :             OutdoorPressure = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).Press;
   10909             :             // If node is not connected to anything, pressure = default, use weather data
   10910     2275300 :             if (OutdoorPressure == state.dataLoopNodes->DefaultNodeValues.Press) {
   10911           0 :                 OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   10912           0 :                 OutdoorHumRat = state.dataEnvrn->OutHumRat;
   10913           0 :                 OutdoorPressure = state.dataEnvrn->OutBaroPress;
   10914           0 :                 OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   10915             :             } else {
   10916     2275300 :                 OutdoorHumRat = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).HumRat;
   10917             :                 // this should use Node%WetBulbTemp or a PSYC function, not OAWB
   10918     2275300 :                 OutdoorWetBulb = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).OutAirWetBulb;
   10919             :             }
   10920     2275300 :             if (thisDXCoil.IsSecondaryDXCoilInZone) {
   10921           0 :                 auto &secZoneHB = state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr);
   10922           0 :                 OutdoorDryBulb = secZoneHB.ZT;
   10923           0 :                 OutdoorHumRat = secZoneHB.airHumRat;
   10924           0 :                 OutdoorWetBulb = thisDXCoil.EvapInletWetBulb;
   10925           0 :                 OutdoorPressure = state.dataEnvrn->OutBaroPress;
   10926           0 :                 CompAmbTemp = OutdoorDryBulb;
   10927             :             }
   10928             :         }
   10929     5159867 :     } else if (thisDXCoil.IsSecondaryDXCoilInZone) {
   10930       81925 :         auto &secZoneHB = state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr);
   10931       81925 :         OutdoorDryBulb = secZoneHB.ZT;
   10932       81925 :         OutdoorHumRat = secZoneHB.airHumRat;
   10933       81925 :         OutdoorWetBulb = thisDXCoil.EvapInletWetBulb;
   10934       81925 :         OutdoorPressure = state.dataEnvrn->OutBaroPress;
   10935       81925 :         CompAmbTemp = OutdoorDryBulb;
   10936             :     } else {
   10937     5077942 :         OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   10938     5077942 :         OutdoorHumRat = state.dataEnvrn->OutHumRat;
   10939     5077942 :         OutdoorPressure = state.dataEnvrn->OutBaroPress;
   10940     5077942 :         OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   10941     5077942 :         CompAmbTemp = OutdoorDryBulb;
   10942             :     }
   10943             : 
   10944     7591276 :     AirMassFlow = thisDXCoil.InletAirMassFlowRate;
   10945     7591276 :     InletAirDryBulbTemp = thisDXCoil.InletAirTemp;
   10946     7591276 :     InletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   10947     7591276 :     InletAirHumRat = thisDXCoil.InletAirHumRat;
   10948             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   10949             :     // InletAirPressure = DXCoil(DXCoilNum)%InletAirPressure
   10950             :     // InletAirWetBulbC = PsyTwbFnTdbWPb(InletAirDryBulbTemp,InletAirHumRat,InletAirPressure)
   10951     7591276 :     InletAirWetBulbC = PsyTwbFnTdbWPb(state, InletAirDryBulbTemp, InletAirHumRat, OutdoorPressure);
   10952     7591276 :     PLRHeating = 0.0;
   10953     7591276 :     thisDXCoil.HeatingCoilRuntimeFraction = 0.0;
   10954             :     // Initialize crankcase heater, operates below OAT defined in input deck for HP DX heating coil
   10955     7591276 :     if (CompAmbTemp < thisDXCoil.MaxOATCrankcaseHeater) {
   10956     1960774 :         CrankcaseHeatingPower = thisDXCoil.CrankcaseHeaterCapacity;
   10957     1960774 :         if (thisDXCoil.CrankcaseHeaterCapacityCurveIndex > 0) {
   10958       56165 :             CrankcaseHeatingPower *= Curve::CurveValue(state, thisDXCoil.CrankcaseHeaterCapacityCurveIndex, CompAmbTemp);
   10959             :         }
   10960             :     } else {
   10961     5630502 :         CrankcaseHeatingPower = 0.0;
   10962             :     }
   10963             : 
   10964     8826166 :     if ((AirMassFlow > 0.0) && (GetCurrentScheduleValue(state, thisDXCoil.SchedPtr) > 0.0) && (PartLoadRatio > 0.0) &&
   10965     1234890 :         OutdoorDryBulb > thisDXCoil.MinOATCompressor) {
   10966             :         // for cycling fan, reset mass flow to full on rate
   10967      605359 :         if (fanOp == HVAC::FanOp::Cycling) AirMassFlow /= PartLoadRatio;
   10968      605359 :         if (fanOp == HVAC::FanOp::Continuous) AirMassFlow *= AirFlowRatio;
   10969             :         // Check for valid air volume flow per rated total cooling capacity (200 - 600 cfm/ton)
   10970      605359 :         AirVolumeFlowRate = AirMassFlow / PsyRhoAirFnPbTdbW(state, OutdoorPressure, InletAirDryBulbTemp, InletAirHumRat);
   10971             :         //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   10972             :         //  AirVolumeFlowRate = AirMassFlow/PsyRhoAirFnPbTdbW(InletAirPressure,InletAirDryBulbTemp, InletAirHumRat)
   10973      605359 :         VolFlowperRatedTotCap = AirVolumeFlowRate / thisDXCoil.RatedTotCap(Mode);
   10974             : 
   10975     1207638 :         if ((VolFlowperRatedTotCap < HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) ||
   10976      602279 :             (VolFlowperRatedTotCap > HVAC::MaxHeatVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT])) {
   10977        3080 :             if (thisDXCoil.ErrIndex1 == 0) {
   10978           2 :                 ShowWarningMessage(
   10979             :                     state,
   10980           2 :                     format("{} \"{}\" - Air volume flow rate per watt of rated total heating capacity is out of range at {:.3R} m3/s/W.",
   10981           1 :                            thisDXCoil.DXCoilType,
   10982           1 :                            thisDXCoil.Name,
   10983             :                            VolFlowperRatedTotCap));
   10984           1 :                 ShowContinueErrorTimeStamp(state, "");
   10985           2 :                 ShowContinueError(state,
   10986           2 :                                   format("Expected range for VolumeFlowPerRatedTotalCapacity=[{:.3R}--{:.3R}]",
   10987           1 :                                          HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   10988           1 :                                          HVAC::MaxHeatVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]));
   10989           1 :                 ShowContinueError(state, "Possible causes include inconsistent air flow rates in system components or");
   10990           1 :                 ShowContinueError(state, "inconsistent supply air fan operation modes in coil and unitary system objects.");
   10991             :             }
   10992        9240 :             ShowRecurringWarningErrorAtEnd(
   10993             :                 state,
   10994        6160 :                 thisDXCoil.DXCoilType + " \"" + thisDXCoil.Name +
   10995             :                     "\" - Air volume flow rate per watt of rated total heating capacity is out of range error continues...",
   10996        3080 :                 thisDXCoil.ErrIndex1,
   10997             :                 VolFlowperRatedTotCap,
   10998             :                 VolFlowperRatedTotCap);
   10999             :         }
   11000             : 
   11001             :         // Get total capacity modifying factor (function of temperature) for off-rated conditions
   11002             :         // Model was extended to accept bi-quadratic curves. This allows sensitivity of the heating capacity
   11003             :         // to the entering dry-bulb temperature as well as the outside dry-bulb temperature. User is
   11004             :         // advised to use the bi-quaratic curve if sufficient manufacturer data is available.
   11005      605359 :         if (state.dataCurveManager->PerfCurve(thisDXCoil.CCapFTemp(Mode))->numDims == 2) {
   11006       56682 :             switch (thisDXCoil.HeatingPerformanceOATType) {
   11007           1 :             case HVAC::OATType::DryBulb: {
   11008           1 :                 TotCapTempModFac = CurveValue(state, thisDXCoil.CCapFTemp(Mode), InletAirDryBulbTemp, OutdoorDryBulb);
   11009           1 :             } break;
   11010       56681 :             case HVAC::OATType::WetBulb: {
   11011       56681 :                 TotCapTempModFac = CurveValue(state, thisDXCoil.CCapFTemp(Mode), InletAirDryBulbTemp, OutdoorWetBulb);
   11012       56681 :             } break;
   11013           0 :             default: {
   11014           0 :                 TotCapTempModFac = 1.0;
   11015           0 :             } break;
   11016             :             }
   11017             :         } else {
   11018      548677 :             switch (thisDXCoil.HeatingPerformanceOATType) {
   11019      312950 :             case HVAC::OATType::DryBulb: {
   11020      312950 :                 if (thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_Heating && thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_FluidTCtrl_Heating) {
   11021      289170 :                     TotCapTempModFac = CurveValue(state, thisDXCoil.CCapFTemp(Mode), OutdoorDryBulb);
   11022             :                 } else {
   11023       23780 :                     TotCapTempModFac = CurveValue(state, thisDXCoil.CCapFTemp(Mode), InletAirDryBulbTemp);
   11024             :                 }
   11025      312950 :             } break;
   11026      235727 :             case HVAC::OATType::WetBulb: {
   11027      235727 :                 if (thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_Heating && thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_FluidTCtrl_Heating) {
   11028           0 :                     TotCapTempModFac = CurveValue(state, thisDXCoil.CCapFTemp(Mode), OutdoorWetBulb);
   11029             :                 } else {
   11030      235727 :                     TotCapTempModFac = CurveValue(state, thisDXCoil.CCapFTemp(Mode), InletAirDryBulbTemp);
   11031             :                 }
   11032      235727 :             } break;
   11033           0 :             default: {
   11034           0 :                 TotCapTempModFac = 1.0;
   11035           0 :             } break;
   11036             :             }
   11037             :         }
   11038             : 
   11039      605359 :         if (TotCapTempModFac < 0.0) {
   11040           0 :             if (thisDXCoil.CAPFTErrIndex == 0) {
   11041           0 :                 ShowWarningMessage(state,
   11042           0 :                                    format("The TotCapTempModFac curve value for DX heating coil {} ={:.2R}", thisDXCoil.Name, TotCapTempModFac));
   11043           0 :                 ShowContinueError(state,
   11044             :                                   "TotCapTempModFac curve value must be > 0. TotCapTempModFac curve value has been reset to 0.0 and "
   11045             :                                   "simulation is continuing.");
   11046           0 :                 ShowContinueError(state, format("Check the IO reference manual for TotCapTempModFac curve guidance [ {} ].", thisDXCoil.DXCoilType));
   11047           0 :                 ShowContinueErrorTimeStamp(state, "");
   11048             :             }
   11049           0 :             ShowRecurringWarningErrorAtEnd(state,
   11050             :                                            "DX heating coil TotCapTempModFac curve value < 0 warning continues... ",
   11051           0 :                                            thisDXCoil.CAPFTErrIndex,
   11052             :                                            TotCapTempModFac,
   11053             :                                            TotCapTempModFac);
   11054           0 :             TotCapTempModFac = 0.0;
   11055             :         }
   11056             : 
   11057             :         //  Get total capacity modifying factor (function of mass flow) for off-rated conditions
   11058      605359 :         AirMassFlowRatio = AirMassFlow / thisDXCoil.RatedAirMassFlowRate(Mode);
   11059      605359 :         TotCapFlowModFac = CurveValue(state, thisDXCoil.CCapFFlow(Mode), AirMassFlowRatio);
   11060             : 
   11061             :         // Calculate total heating capacity for off-rated conditions
   11062      605359 :         TotCap = thisDXCoil.RatedTotCap(Mode) * TotCapFlowModFac * TotCapTempModFac;
   11063             : 
   11064             :         // Calculating adjustment factors for defrost
   11065             :         // Calculate delta w through outdoor coil by assuming a coil temp of 0.82*DBT-9.7(F) per DOE2.1E
   11066      605359 :         OutdoorCoilT = 0.82 * OutdoorDryBulb - 8.589;
   11067      605359 :         OutdoorCoildw = max(1.0e-6, (OutdoorHumRat - PsyWFnTdpPb(state, OutdoorCoilT, OutdoorPressure)));
   11068             : 
   11069             :         // Initializing defrost adjustment factors
   11070      605359 :         LoadDueToDefrost = 0.0;
   11071      605359 :         HeatingCapacityMultiplier = 1.0;
   11072      605359 :         FractionalDefrostTime = 0.0;
   11073      605359 :         InputPowerMultiplier = 1.0;
   11074             : 
   11075             :         // Check outdoor temperature to determine of defrost is active
   11076      605359 :         if (OutdoorDryBulb <= thisDXCoil.MaxOATDefrost && thisDXCoil.CondenserType(Mode) != DataHeatBalance::RefrigCondenserType::Water) {
   11077             :             // Calculate defrost adjustment factors depending on defrost control type
   11078       88366 :             if (thisDXCoil.DefrostControl == StandardRatings::HPdefrostControl::Timed) {
   11079       87823 :                 FractionalDefrostTime = thisDXCoil.DefrostTime;
   11080       87823 :                 if (FractionalDefrostTime > 0.0) {
   11081       87823 :                     HeatingCapacityMultiplier = 0.909 - 107.33 * OutdoorCoildw;
   11082       87823 :                     InputPowerMultiplier = 0.90 - 36.45 * OutdoorCoildw;
   11083             :                 }
   11084             :             } else { // else defrost control is on-demand
   11085         543 :                 FractionalDefrostTime = 1.0 / (1.0 + 0.01446 / OutdoorCoildw);
   11086         543 :                 HeatingCapacityMultiplier = 0.875 * (1.0 - FractionalDefrostTime);
   11087         543 :                 InputPowerMultiplier = 0.954 * (1.0 - FractionalDefrostTime);
   11088             :             }
   11089             : 
   11090       88366 :             if (FractionalDefrostTime > 0.0) {
   11091             :                 // Calculate defrost adjustment factors depending on defrost control strategy
   11092       88366 :                 if (thisDXCoil.DefrostStrategy == StandardRatings::DefrostStrat::ReverseCycle) {
   11093         543 :                     LoadDueToDefrost = (0.01 * FractionalDefrostTime) * (7.222 - OutdoorDryBulb) * (thisDXCoil.RatedTotCap(Mode) / 1.01667);
   11094         543 :                     DefrostEIRTempModFac = CurveValue(state, thisDXCoil.DefrostEIRFT, max(15.555, InletAirWetBulbC), max(15.555, OutdoorDryBulb));
   11095         543 :                     thisDXCoil.DefrostPower = DefrostEIRTempModFac * (thisDXCoil.RatedTotCap(Mode) / 1.01667) * FractionalDefrostTime;
   11096             :                 } else { // Defrost strategy is resistive
   11097       87823 :                     thisDXCoil.DefrostPower = thisDXCoil.DefrostCapacity * FractionalDefrostTime;
   11098             :                 }
   11099             :             } else { // Defrost is not active because (FractionalDefrostTime .EQ. 0.0)
   11100           0 :                 thisDXCoil.DefrostPower = 0.0;
   11101             :             }
   11102             :         }
   11103             : 
   11104             :         // Modify total heating capacity based on defrost heating capacity multiplier
   11105             :         // MaxHeatCap passed from parent object VRF Condenser and is used to limit capacity of TU's to that available from condenser
   11106      605359 :         if (present(MaxHeatCap)) {
   11107      316142 :             TotCapAdj = min(MaxHeatCap, TotCap * HeatingCapacityMultiplier);
   11108      316142 :             TotCap = min(MaxHeatCap, TotCap);
   11109             :         } else {
   11110      289217 :             TotCapAdj = TotCap * HeatingCapacityMultiplier;
   11111             :         }
   11112             : 
   11113             :         // Calculate full load outlet conditions
   11114      605359 :         FullLoadOutAirEnth = InletAirEnthalpy + TotCapAdj / AirMassFlow;
   11115      605359 :         FullLoadOutAirHumRat = InletAirHumRat;
   11116      605359 :         FullLoadOutAirTemp = PsyTdbFnHW(FullLoadOutAirEnth, FullLoadOutAirHumRat);
   11117      605359 :         FullLoadOutAirRH = PsyRhFnTdbWPb(state, FullLoadOutAirTemp, FullLoadOutAirHumRat, OutdoorPressure, RoutineNameFullLoad);
   11118             :         //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   11119             :         //  FullLoadOutAirRH = PsyRhFnTdbWPb(FullLoadOutAirTemp,FullLoadOutAirHumRat,InletAirPressure)
   11120      605359 :         if (FullLoadOutAirRH > 1.0) { // Limit to saturated conditions at FullLoadOutAirEnth
   11121           0 :             FullLoadOutAirTemp = PsyTsatFnHPb(state, FullLoadOutAirEnth, OutdoorPressure);
   11122             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   11123             :             //    FullLoadOutAirTemp = PsyTsatFnHPb(FullLoadOutAirEnth,InletAirPressure)
   11124           0 :             FullLoadOutAirHumRat = PsyWFnTdbH(state, FullLoadOutAirTemp, FullLoadOutAirEnth);
   11125             :         }
   11126             : 
   11127             :         // Calculate actual outlet conditions for the input part load ratio
   11128             :         // Actual outlet conditions are "average" for time step
   11129      605359 :         if (fanOp == HVAC::FanOp::Continuous) {
   11130             :             // continuous fan, cycling compressor
   11131      352749 :             OutletAirEnthalpy = ((PartLoadRatio * AirFlowRatio) * FullLoadOutAirEnth + (1.0 - (PartLoadRatio * AirFlowRatio)) * InletAirEnthalpy);
   11132      352749 :             OutletAirHumRat = (PartLoadRatio * FullLoadOutAirHumRat + (1.0 - PartLoadRatio) * InletAirHumRat);
   11133      352749 :             OutletAirTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
   11134             :         } else {
   11135             :             // default to cycling fan, cycling compressor
   11136      252610 :             OutletAirEnthalpy = FullLoadOutAirEnth;
   11137      252610 :             OutletAirHumRat = FullLoadOutAirHumRat;
   11138      252610 :             OutletAirTemp = FullLoadOutAirTemp;
   11139             :         }
   11140             :         // Calculate electricity consumed. First, get EIR modifying factors for off-rated conditions
   11141             :         // Model was extended to accept bi-quadratic curves. This allows sensitivity of the EIR
   11142             :         // to the entering dry-bulb temperature as well as the outside dry-bulb temperature. User is
   11143             :         // advised to use the bi-quaratic curve if sufficient manufacturer data is available.
   11144      605359 :         if (thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_Heating && thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_FluidTCtrl_Heating) {
   11145      289171 :             if (state.dataCurveManager->PerfCurve(thisDXCoil.EIRFTemp(Mode))->numDims == 1) {
   11146      289170 :                 EIRTempModFac = CurveValue(state, thisDXCoil.EIRFTemp(Mode), OutdoorDryBulb);
   11147             :             } else {
   11148           1 :                 EIRTempModFac = CurveValue(state, thisDXCoil.EIRFTemp(Mode), InletAirDryBulbTemp, OutdoorDryBulb);
   11149             :             }
   11150      289171 :             EIRFlowModFac = CurveValue(state, thisDXCoil.EIRFFlow(Mode), AirMassFlowRatio);
   11151             :         } else {
   11152      316188 :             EIRTempModFac = 1.0;
   11153      316188 :             EIRFlowModFac = 1.0;
   11154             :         }
   11155             : 
   11156      605359 :         if (EIRTempModFac < 0.0) {
   11157           0 :             if (thisDXCoil.EIRFTErrIndex == 0) {
   11158           0 :                 ShowWarningMessage(state, format("The EIRTempModFac curve value for DX heating coil {} ={:.2R}", thisDXCoil.Name, EIRTempModFac));
   11159           0 :                 ShowContinueError(
   11160             :                     state, "EIRTempModFac curve value must be > 0.  EIRTempModFac curve value has been reset to 0.0 and simulation is continuing.");
   11161           0 :                 ShowContinueError(state, format("Check the IO reference manual for EIRTempModFac curve guidance [ {} ].", thisDXCoil.DXCoilType));
   11162           0 :                 ShowContinueErrorTimeStamp(state, "");
   11163             :             }
   11164           0 :             ShowRecurringWarningErrorAtEnd(state,
   11165             :                                            "DX heating coil EIRTempModFac curve value < 0.0 warning continues... ",
   11166           0 :                                            thisDXCoil.EIRFTErrIndex,
   11167             :                                            EIRTempModFac,
   11168             :                                            EIRTempModFac);
   11169           0 :             EIRTempModFac = 0.0;
   11170             :         }
   11171             : 
   11172      605359 :         EIR = thisDXCoil.RatedEIR(Mode) * EIRTempModFac * EIRFlowModFac;
   11173             :         // Calculate modified PartLoadRatio due to defrost (reverse-cycle defrost only)
   11174      605359 :         if (TotCapAdj > 0.0) {
   11175      605302 :             PLRHeating = min(1.0, (PartLoadRatio + (LoadDueToDefrost * PartLoadRatio) / TotCapAdj));
   11176             :         } else {
   11177          57 :             PLRHeating = 0.0;
   11178             :         }
   11179      605359 :         if (thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_Heating) {
   11180      289171 :             PLF = CurveValue(state, thisDXCoil.PLFFPLR(Mode), PLRHeating); // Calculate part-load factor
   11181             :         } else {
   11182      316188 :             PLF = 1.0;
   11183             :         }
   11184             : 
   11185      605359 :         if (PLF < 0.7) {
   11186           0 :             if (thisDXCoil.PLRErrIndex == 0) {
   11187           0 :                 ShowWarningMessage(
   11188             :                     state,
   11189           0 :                     format("The PLF curve value for DX heating coil {} ={:.2R} for part-load ratio ={:.2R}", thisDXCoil.Name, PLF, PLRHeating));
   11190           0 :                 ShowContinueError(state, "PLF curve values must be >= 0.7. PLF has been reset to 0.7 and simulation is continuing.");
   11191           0 :                 ShowContinueError(state, "Check the IO reference manual for PLF curve guidance [Coil:Heating:DX:SingleSpeed].");
   11192           0 :                 ShowContinueErrorTimeStamp(state, "");
   11193             :             }
   11194           0 :             ShowRecurringWarningErrorAtEnd(state, "DX heating coil PLF curve < 0.7 warning continues... ", thisDXCoil.PLRErrIndex, PLF, PLF);
   11195           0 :             PLF = 0.7;
   11196             :         }
   11197             : 
   11198      605359 :         thisDXCoil.HeatingCoilRuntimeFraction = (PLRHeating / PLF);
   11199      605359 :         if (thisDXCoil.HeatingCoilRuntimeFraction > 1.0 && std::abs(thisDXCoil.HeatingCoilRuntimeFraction - 1.0) > 0.001) {
   11200           0 :             if (thisDXCoil.ErrIndex4 == 0) {
   11201           0 :                 ShowWarningMessage(state,
   11202           0 :                                    format("The runtime fraction for DX heating coil {} exceeded 1.0. [{:.4R}].",
   11203           0 :                                           thisDXCoil.Name,
   11204           0 :                                           thisDXCoil.HeatingCoilRuntimeFraction));
   11205           0 :                 ShowContinueError(state, "Runtime fraction is set to 1.0 and the simulation continues...");
   11206           0 :                 ShowContinueError(state, "Check the IO reference manual for PLF curve guidance [Coil:Heating:DX:SingleSpeed].");
   11207           0 :                 ShowContinueErrorTimeStamp(state, "");
   11208             :             }
   11209           0 :             ShowRecurringWarningErrorAtEnd(state,
   11210           0 :                                            thisDXCoil.Name + ", DX heating coil runtime fraction > 1.0 warning continues...",
   11211           0 :                                            thisDXCoil.ErrIndex4,
   11212           0 :                                            thisDXCoil.HeatingCoilRuntimeFraction,
   11213           0 :                                            thisDXCoil.HeatingCoilRuntimeFraction);
   11214           0 :             thisDXCoil.HeatingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   11215      605359 :         } else if (thisDXCoil.HeatingCoilRuntimeFraction > 1.0) {
   11216           0 :             thisDXCoil.HeatingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   11217             :         }
   11218             :         // if cycling fan, send coil part-load fraction to on/off fan via HVACDataGlobals
   11219      605359 :         if (fanOp == HVAC::FanOp::Cycling) state.dataHVACGlobal->OnOffFanPartLoadFraction = PLF;
   11220      605359 :         thisDXCoil.ElecHeatingPower = TotCap * EIR * thisDXCoil.HeatingCoilRuntimeFraction * InputPowerMultiplier;
   11221             : 
   11222             :         // Calculate crankcase heater power using the runtime fraction for this DX heating coil only if there is no companion DX coil.
   11223             :         // Else use the largest runtime fraction of this DX heating coil and the companion DX cooling coil.
   11224             : 
   11225      605359 :         if (thisDXCoil.CompanionUpstreamDXCoil == 0) {
   11226      316211 :             thisDXCoil.CrankcaseHeaterPower = CrankcaseHeatingPower * (1.0 - thisDXCoil.HeatingCoilRuntimeFraction);
   11227             :         } else {
   11228      289148 :             thisDXCoil.CrankcaseHeaterPower =
   11229      289148 :                 CrankcaseHeatingPower * (1.0 - max(thisDXCoil.HeatingCoilRuntimeFraction,
   11230      289148 :                                                    state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).CoolingCoilRuntimeFraction));
   11231             :         }
   11232             : 
   11233      605359 :         AirMassFlow = thisDXCoil.InletAirMassFlowRate;
   11234      605359 :         thisDXCoil.TotalHeatingEnergyRate = AirMassFlow * (OutletAirEnthalpy - InletAirEnthalpy);
   11235             :         // Adjust defrost power to correct for DOE-2 bug where defrost power is constant regardless of compressor runtime fraction
   11236             :         // Defrosts happen based on compressor run time (frost buildup on outdoor coil), not total elapsed time.
   11237      605359 :         thisDXCoil.DefrostPower *= thisDXCoil.HeatingCoilRuntimeFraction;
   11238             : 
   11239      605359 :         thisDXCoil.OutletAirTemp = OutletAirTemp;
   11240      605359 :         thisDXCoil.OutletAirHumRat = OutletAirHumRat;
   11241      605359 :         thisDXCoil.OutletAirEnthalpy = OutletAirEnthalpy;
   11242      605359 :         thisDXCoil.CompressorPartLoadRatio = PartLoadRatio;
   11243             : 
   11244             :     } else {
   11245             : 
   11246             :         // DX coil is off; just pass through conditions
   11247     6985917 :         thisDXCoil.OutletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   11248     6985917 :         thisDXCoil.OutletAirHumRat = thisDXCoil.InletAirHumRat;
   11249     6985917 :         thisDXCoil.OutletAirTemp = thisDXCoil.InletAirTemp;
   11250             : 
   11251     6985917 :         thisDXCoil.ElecHeatingPower = 0.0;
   11252     6985917 :         thisDXCoil.TotalHeatingEnergyRate = 0.0;
   11253     6985917 :         thisDXCoil.DefrostPower = 0.0;
   11254             : 
   11255             :         // Calculate crankcase heater power using the runtime fraction for this DX heating coil (here DXHeatingCoilRTF=0) if
   11256             :         // there is no companion DX coil, or the runtime fraction of the companion DX cooling coil (here DXCoolingCoilRTF>=0).
   11257     6985917 :         if (thisDXCoil.CompanionUpstreamDXCoil == 0) {
   11258     2520848 :             thisDXCoil.CrankcaseHeaterPower = CrankcaseHeatingPower;
   11259             :         } else {
   11260     4465069 :             thisDXCoil.CrankcaseHeaterPower =
   11261     4465069 :                 CrankcaseHeatingPower * (1.0 - state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).CoolingCoilRuntimeFraction);
   11262             :         }
   11263     6985917 :         thisDXCoil.CompressorPartLoadRatio = 0.0;
   11264             : 
   11265             :     } // end of on/off if - else
   11266             : 
   11267     7591276 :     state.dataDXCoils->DXCoilOutletTemp(DXCoilNum) = thisDXCoil.OutletAirTemp;
   11268     7591276 :     state.dataDXCoils->DXCoilOutletHumRat(DXCoilNum) = thisDXCoil.OutletAirHumRat;
   11269     7591276 :     state.dataDXCoils->DXCoilFanOp(DXCoilNum) = fanOp;
   11270     7591276 :     state.dataDXCoils->DXCoilPartLoadRatio(DXCoilNum) = PLRHeating;
   11271     7591276 :     state.dataDXCoils->DXCoilTotalHeating(DXCoilNum) = thisDXCoil.TotalHeatingEnergyRate;
   11272     7591276 :     state.dataDXCoils->DXCoilHeatInletAirDBTemp(DXCoilNum) = InletAirDryBulbTemp;
   11273     7591276 :     state.dataDXCoils->DXCoilHeatInletAirWBTemp(DXCoilNum) = InletAirWetBulbC;
   11274             : 
   11275             :     // set outlet node conditions
   11276     7591276 :     int airOutletNode = thisDXCoil.AirOutNode;
   11277     7591276 :     state.dataLoopNodes->Node(airOutletNode).Temp = thisDXCoil.OutletAirTemp;
   11278     7591276 :     state.dataLoopNodes->Node(airOutletNode).HumRat = thisDXCoil.OutletAirHumRat;
   11279             : 
   11280             :     // calc secondary coil if specified
   11281     7591276 :     if (thisDXCoil.IsSecondaryDXCoilInZone) {
   11282       81925 :         CalcSecondaryDXCoils(state, DXCoilNum);
   11283             :     }
   11284     7591276 : }
   11285             : 
   11286     4143600 : void CalcMultiSpeedDXCoil(EnergyPlusData &state,
   11287             :                           int const DXCoilNum,     // the number of the DX heating coil to be simulated
   11288             :                           Real64 const SpeedRatio, // = (CompressorSpeed - CompressorSpeedMin) / (CompressorSpeedMax - CompressorSpeedMin)
   11289             :                           Real64 const CycRatio,   // cycling part load ratio
   11290             :                           ObjexxFCL::Optional_bool_const ForceOn)
   11291             : {
   11292             : 
   11293             :     // SUBROUTINE INFORMATION:
   11294             :     //       AUTHOR         Fred Buhl
   11295             :     //       DATE WRITTEN   September 2002
   11296             :     //       MODIFIED       Raustad/Shirey, Feb 2004
   11297             :     //                      Feb 2005 M. J. Witte, GARD Analytics, Inc.
   11298             :     //                        Add new coil type COIL:DX:MultiMode:CoolingEmpirical:
   11299             :     //                      April 2010, Chandan sharma, FSEC, added basin heater
   11300             : 
   11301             :     // PURPOSE OF THIS SUBROUTINE:
   11302             :     // Calculates the air-side performance and electrical energy use of a direct-
   11303             :     // expansion, air-cooled cooling unit with a 2 speed or variable speed compressor.
   11304             : 
   11305             :     // METHODOLOGY EMPLOYED:
   11306             :     // Uses the same methodology as the single speed DX unit model (SUBROUTINE CalcDoe2DXCoil).
   11307             :     // In addition it assumes that the unit performance is obtained by interpolating between
   11308             :     // the performance at high speed and that at low speed. If the output needed is below
   11309             :     // that produced at low speed, the compressor cycles between off and low speed.
   11310             : 
   11311             :     // Using/Aliasing
   11312             :     using Curve::CurveValue;
   11313             : 
   11314             :     // SUBROUTINE ARGUMENT DEFINITIONS:
   11315             :     // SpeedRatio varies between 1.0 (maximum speed) and 0.0 (minimum speed)
   11316             : 
   11317             :     // SUBROUTINE PARAMETER DEFINITIONS:
   11318             :     static constexpr std::string_view RoutineNameHighSpeedOutlet("CalcMultiSpeedDXCoil:highspeedoutlet");
   11319             :     static constexpr std::string_view RoutineNameLowSpeedOutlet("CalcMultiSpeedDXCoil:lowspeedoutlet");
   11320             :     static constexpr std::string_view RoutineNameNewDewPointConditions("CalcMultiSpeedDXCoil:newdewpointconditions");
   11321             : 
   11322             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   11323             :     Real64 AirMassFlow;         // dry air mass flow rate through coil [kg/s]
   11324             :     Real64 AirMassFlowRatio;    // Ratio of max air mass flow to rated air mass flow
   11325             :     Real64 InletAirWetBulbC;    // wetbulb temperature of inlet air [C]
   11326             :     Real64 InletAirDryBulbTemp; // inlet air dry bulb temperature [C]
   11327             :     Real64 InletAirEnthalpy;    // inlet air enthalpy [J/kg]
   11328             :     Real64 InletAirHumRat;      // inlet air humidity ratio [kg/kg]
   11329             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   11330             :     // REAL(r64) :: InletAirPressure    ! inlet air pressure [Pa]
   11331             :     Real64 OutletAirDryBulbTemp;    // outlet air dry bulb temperature [C]
   11332             :     Real64 OutletAirEnthalpy;       // outlet air enthalpy [J/kg]
   11333             :     Real64 OutletAirHumRat;         // outlet air humidity ratio [kg/kg]
   11334             :     Real64 OutletAirDryBulbTempSat; // outlet air dry bulb temp at saturation at the outlet enthalpy [C]
   11335             :     Real64 LSOutletAirDryBulbTemp;  // low speed outlet air dry bulb temperature [C]
   11336             :     Real64 LSOutletAirEnthalpy;     // low speed outlet air enthalpy [J/kg]
   11337             :     Real64 LSOutletAirHumRat;       // low speed outlet air humidity ratio [kg/kg]
   11338             :     Real64 hDelta;                  // Change in air enthalpy across the cooling coil [J/kg]
   11339             :     Real64 hTinwout;                // Enthalpy at inlet dry-bulb and outlet humidity ratio [J/kg]
   11340             :     Real64 hADP;                    // Apparatus dew point enthalpy [J/kg]
   11341             :     Real64 tADP;                    // Apparatus dew point temperature [C]
   11342             :     Real64 wADP;                    // Apparatus dew point humidity ratio [kg/kg]
   11343             :     Real64 hTinwADP;                // Enthalpy at inlet dry-bulb and wADP [J/kg]
   11344             :     Real64 RatedCBFHS;              // coil bypass factor at rated conditions (high speed)
   11345             :     Real64 CBFHS;                   // coil bypass factor at max flow (high speed)
   11346             :     Real64 TotCapHS;                // total capacity at high speed [W]
   11347             :     Real64 SHRHS;                   // sensible heat ratio at high speed
   11348             :     Real64 TotCapLS;                // total capacity at low speed [W]
   11349             :     Real64 SHRLS;                   // sensible heat ratio at low speed
   11350             :     Real64 EIRTempModFacHS;         // EIR modifier (function of entering wetbulb, outside drybulb) (high speed)
   11351             :     Real64 EIRFlowModFacHS;         // EIR modifier (function of actual supply air flow vs rated flow) (high speed)
   11352             :     Real64 EIRHS;                   // EIR at off rated conditions (high speed)
   11353             :     Real64 EIRTempModFacLS;         // EIR modifier (function of entering wetbulb, outside drybulb) (low speed)
   11354             :     Real64 EIRLS;                   // EIR at off rated conditions (low speed)
   11355             :     Real64 TotCap;                  // total capacity at current speed [W]
   11356             :     Real64 SHR;                     // sensible heat ratio at current speed
   11357             :     Real64 EIR;                     // EIR at current speed
   11358             :     Real64 AirMassFlowNom;          // speed ratio weighted average of high and low speed air mass flow rates [kg/s]
   11359             :     Real64 CBFNom;                  // coil bypass factor corresponding to AirMassFlowNom and SpeedRatio
   11360             :     Real64 CBF;                     // CBFNom adjusted for actual air mass flow rate
   11361             :     Real64 PLF;                     // Part load factor, accounts for thermal lag at compressor startup, used in
   11362             :     // power calculation
   11363             :     Real64 CondInletTemp; // Condenser inlet temperature (C). Outdoor dry-bulb temp for air-cooled condenser.
   11364             :     // Outdoor Wetbulb +(1 - effectiveness)*(outdoor drybulb - outdoor wetbulb) for evap condenser.
   11365             :     Real64 CondInletHumRat; // Condenser inlet humidity ratio (kg/kg). Zero for air-cooled condenser.
   11366             :     // For evap condenser, its the humidity ratio of the air leaving the evap cooling pads.
   11367             :     Real64 RhoAir;                // Density of air [kg/m3]
   11368             :     Real64 RhoWater;              // Density of water [kg/m3]
   11369             :     Real64 CondAirMassFlow;       // Condenser air mass flow rate [kg/s]
   11370             :     Real64 EvapCondPumpElecPower; // Evaporative condenser electric pump power [W]
   11371     4143600 :     constexpr int Mode(1);        // Performance mode for MultiMode DX coil; Always 1 for other coil types
   11372             :     Real64 OutdoorDryBulb;        // Outdoor dry-bulb temperature at condenser (C)
   11373             :     Real64 OutdoorWetBulb;        // Outdoor wet-bulb temperature at condenser (C)
   11374             :     Real64 OutdoorHumRat;         // Outdoor humidity ratio at condenser (kg/kg)
   11375             :     Real64 OutdoorPressure;       // Outdoor barometric pressure at condenser (Pa)
   11376             :     bool LocalForceOn;
   11377             :     Real64 AirMassFlowRatio2; // Ratio of low speed air mass flow to rated air mass flow
   11378     4143600 :     Real64 CompAmbTemp(0.0);  // Ambient temperature at compressor
   11379             : 
   11380     4143600 :     if (present(ForceOn)) {
   11381       55368 :         LocalForceOn = true;
   11382             :     } else {
   11383     4088232 :         LocalForceOn = false;
   11384             :     }
   11385             : 
   11386     4143600 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   11387             : 
   11388     4143600 :     if (thisDXCoil.CondenserInletNodeNum(Mode) != 0) {
   11389      332756 :         OutdoorPressure = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).Press;
   11390             :         // If node is not connected to anything, pressure = default, use weather data
   11391      332756 :         if (OutdoorPressure == state.dataLoopNodes->DefaultNodeValues.Press) {
   11392           0 :             OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   11393           0 :             OutdoorHumRat = state.dataEnvrn->OutHumRat;
   11394           0 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
   11395           0 :             OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   11396             :         } else {
   11397      332756 :             OutdoorDryBulb = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).Temp;
   11398      332756 :             OutdoorHumRat = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).HumRat;
   11399      332756 :             OutdoorWetBulb = PsyTwbFnTdbWPb(state, OutdoorDryBulb, OutdoorHumRat, OutdoorPressure);
   11400             :         }
   11401      332756 :         CompAmbTemp = OutdoorDryBulb;
   11402      332756 :         if (thisDXCoil.IsSecondaryDXCoilInZone) {
   11403           0 :             auto &secZoneHB = state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr);
   11404           0 :             OutdoorDryBulb = secZoneHB.ZT;
   11405           0 :             OutdoorHumRat = secZoneHB.airHumRat;
   11406           0 :             OutdoorWetBulb = thisDXCoil.EvapInletWetBulb;
   11407           0 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
   11408           0 :             CompAmbTemp = OutdoorDryBulb;
   11409             :         }
   11410     3810844 :     } else if (thisDXCoil.IsSecondaryDXCoilInZone) {
   11411           0 :         auto &secZoneHB = state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr);
   11412           0 :         OutdoorDryBulb = secZoneHB.ZT;
   11413           0 :         OutdoorHumRat = secZoneHB.airHumRat;
   11414           0 :         OutdoorWetBulb = thisDXCoil.EvapInletWetBulb;
   11415           0 :         OutdoorPressure = state.dataEnvrn->OutBaroPress;
   11416           0 :         CompAmbTemp = OutdoorDryBulb;
   11417             :     } else {
   11418     3810844 :         OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   11419     3810844 :         OutdoorHumRat = state.dataEnvrn->OutHumRat;
   11420     3810844 :         OutdoorPressure = state.dataEnvrn->OutBaroPress;
   11421     3810844 :         OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   11422     3810844 :         CompAmbTemp = OutdoorDryBulb;
   11423             :     }
   11424             : 
   11425     4143600 :     AirMassFlow = thisDXCoil.InletAirMassFlowRate;
   11426     4143600 :     AirMassFlowRatio = thisDXCoil.InletAirMassFlowRateMax / thisDXCoil.RatedAirMassFlowRate(Mode);
   11427     4143600 :     thisDXCoil.CoolingCoilRuntimeFraction = 0.0;
   11428     4143600 :     InletAirDryBulbTemp = thisDXCoil.InletAirTemp;
   11429     4143600 :     InletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   11430     4143600 :     InletAirHumRat = thisDXCoil.InletAirHumRat;
   11431     4143600 :     AirMassFlowRatio2 = 1.0; // DXCoil(DXCoilNum)%RatedAirMassFlowRate2 / DXCoil(DXCoilNum)%RatedAirMassFlowRate(Mode)
   11432             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   11433             :     // InletAirPressure = DXCoil(DXCoilNum)%InletAirPressure
   11434             :     // InletAirWetBulbC = PsyTwbFnTdbWPb(InletAirDryBulbTemp,InletAirHumRat,InletAirPressure)
   11435     4143600 :     InletAirWetBulbC = PsyTwbFnTdbWPb(state, InletAirDryBulbTemp, InletAirHumRat, OutdoorPressure);
   11436     4143600 :     if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Air) {
   11437     4120107 :         CondInletTemp = OutdoorDryBulb; // Outdoor dry-bulb temp
   11438       23493 :     } else if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Evap) {
   11439             :         // Outdoor wet-bulb temp from DataEnvironment + (1.0-EvapCondEffectiveness) * (drybulb - wetbulb)
   11440       23493 :         CondInletTemp = OutdoorWetBulb + (OutdoorDryBulb - OutdoorWetBulb) * (1.0 - thisDXCoil.EvapCondEffect(Mode));
   11441       23493 :         CondInletHumRat = PsyWFnTdbTwbPb(state, CondInletTemp, OutdoorWetBulb, OutdoorPressure);
   11442             :     }
   11443             : 
   11444     3965651 :     if ((AirMassFlow > 0.0 && CompAmbTemp >= thisDXCoil.MinOATCompressor) &&
   11445     8109251 :         ((GetCurrentScheduleValue(state, thisDXCoil.SchedPtr) > 0.0) || (LocalForceOn)) && (SpeedRatio > 0.0 || CycRatio > 0.0)) {
   11446             : 
   11447     3061183 :         RhoAir = PsyRhoAirFnPbTdbW(state, OutdoorPressure, OutdoorDryBulb, OutdoorHumRat);
   11448     3061183 :         if (SpeedRatio > 0.0) {
   11449             :             // Adjust high speed coil bypass factor for actual maximum air flow rate.
   11450     2201122 :             RatedCBFHS = thisDXCoil.RatedCBF(Mode);
   11451     2201122 :             CBFHS = AdjustCBF(RatedCBFHS, thisDXCoil.RatedAirMassFlowRate(Mode), thisDXCoil.InletAirMassFlowRateMax);
   11452             :             // get high speed total capacity and SHR at current conditions
   11453     6603366 :             CalcTotCapSHR(state,
   11454             :                           InletAirDryBulbTemp,
   11455             :                           InletAirHumRat,
   11456             :                           InletAirEnthalpy,
   11457             :                           InletAirWetBulbC,
   11458             :                           AirMassFlowRatio,
   11459             :                           thisDXCoil.InletAirMassFlowRateMax,
   11460     2201122 :                           thisDXCoil.RatedTotCap(Mode),
   11461             :                           CBFHS,
   11462     2201122 :                           thisDXCoil.CCapFTemp(Mode),
   11463     2201122 :                           thisDXCoil.CCapFFlow(Mode),
   11464             :                           TotCapHS,
   11465             :                           SHRHS,
   11466             :                           CondInletTemp,
   11467             :                           OutdoorPressure,
   11468     2201122 :                           thisDXCoil.capModFacTotal);
   11469             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   11470             :             //                       CondInletTemp, Node(DXCoil(DXCoilNum)%AirInNode)%Press)
   11471             :             // get the high speed SHR from user specified SHR modifier curves
   11472     2201122 :             if (thisDXCoil.UserSHRCurveExists) {
   11473        3662 :                 SHRHS = CalcSHRUserDefinedCurves(state,
   11474             :                                                  InletAirDryBulbTemp,
   11475             :                                                  InletAirWetBulbC,
   11476             :                                                  AirMassFlowRatio,
   11477        3662 :                                                  thisDXCoil.SHRFTemp(Mode),
   11478        3662 :                                                  thisDXCoil.SHRFFlow(Mode),
   11479        3662 :                                                  thisDXCoil.RatedSHR(Mode));
   11480             :             }
   11481             :             // get low speed total capacity and SHR at current conditions
   11482     2201122 :             CalcTotCapSHR(state,
   11483             :                           InletAirDryBulbTemp,
   11484             :                           InletAirHumRat,
   11485             :                           InletAirEnthalpy,
   11486             :                           InletAirWetBulbC,
   11487             :                           1.0,
   11488             :                           thisDXCoil.RatedAirMassFlowRate2,
   11489             :                           thisDXCoil.RatedTotCap2,
   11490             :                           thisDXCoil.RatedCBF2,
   11491             :                           thisDXCoil.CCapFTemp2,
   11492     2201122 :                           thisDXCoil.CCapFFlow(Mode),
   11493             :                           TotCapLS,
   11494             :                           SHRLS,
   11495             :                           CondInletTemp,
   11496             :                           OutdoorPressure,
   11497     2201122 :                           thisDXCoil.capModFacTotal);
   11498             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   11499             :             //                       Node(DXCoil(DXCoilNum)%AirInNode)%Press)
   11500             :             // get the low speed SHR from user specified SHR modifier curves
   11501     2201122 :             if (thisDXCoil.UserSHRCurveExists) {
   11502        3662 :                 SHRLS = CalcSHRUserDefinedCurves(state,
   11503             :                                                  InletAirDryBulbTemp,
   11504             :                                                  InletAirWetBulbC,
   11505             :                                                  AirMassFlowRatio2,
   11506             :                                                  thisDXCoil.SHRFTemp2,
   11507             :                                                  thisDXCoil.SHRFFlow2,
   11508             :                                                  thisDXCoil.RatedSHR2);
   11509             :             }
   11510             :             // get high speed EIR at current conditions
   11511     2201122 :             EIRTempModFacHS = CurveValue(state, thisDXCoil.EIRFTemp(Mode), InletAirWetBulbC, CondInletTemp);
   11512     2201122 :             EIRFlowModFacHS = CurveValue(state, thisDXCoil.EIRFFlow(Mode), AirMassFlowRatio);
   11513     2201122 :             EIRHS = thisDXCoil.RatedEIR(Mode) * EIRFlowModFacHS * EIRTempModFacHS;
   11514             :             // get low speed EIR at current conditions
   11515             :             //    EIRTempModFacLS = CurveValue(state, DXCoil(DXCoilNum)%EIRFTemp(Mode),InletAirWetBulbC,CondInletTemp)
   11516             :             //    CR7307 changed EIRTempModFacLS calculation to that shown below.
   11517     2201122 :             EIRTempModFacLS = CurveValue(state, thisDXCoil.EIRFTemp2, InletAirWetBulbC, CondInletTemp);
   11518     2201122 :             EIRLS = thisDXCoil.RatedEIR2 * EIRTempModFacLS;
   11519             : 
   11520             :             // get current total capacity, SHR, EIR
   11521     2201122 :             if (SpeedRatio >= 1.0) {
   11522      703252 :                 TotCap = TotCapHS;
   11523      703252 :                 SHR = SHRHS;
   11524      703252 :                 EIR = EIRHS;
   11525      703252 :                 CBFNom = CBFHS;
   11526      703252 :                 AirMassFlowNom = thisDXCoil.InletAirMassFlowRateMax;
   11527      703252 :                 CondAirMassFlow = RhoAir * thisDXCoil.EvapCondAirFlow(Mode);
   11528      703252 :                 EvapCondPumpElecPower = thisDXCoil.EvapCondPumpElecNomPower(Mode);
   11529             :             } else {
   11530     1497870 :                 TotCap = SpeedRatio * TotCapHS + (1.0 - SpeedRatio) * TotCapLS;
   11531     1497870 :                 EIR = SpeedRatio * EIRHS + (1.0 - SpeedRatio) * EIRLS;
   11532     1497870 :                 CBFNom = SpeedRatio * CBFHS + (1.0 - SpeedRatio) * thisDXCoil.RatedCBF2;
   11533     1497870 :                 AirMassFlowNom = SpeedRatio * thisDXCoil.InletAirMassFlowRateMax + (1.0 - SpeedRatio) * thisDXCoil.RatedAirMassFlowRate2;
   11534     1497870 :                 CondAirMassFlow = RhoAir * (SpeedRatio * thisDXCoil.EvapCondAirFlow(Mode) + (1.0 - SpeedRatio) * thisDXCoil.EvapCondAirFlow2);
   11535     1497870 :                 EvapCondPumpElecPower =
   11536     1497870 :                     SpeedRatio * thisDXCoil.EvapCondPumpElecNomPower(Mode) + (1.0 - SpeedRatio) * thisDXCoil.EvapCondPumpElecNomPower2;
   11537             :             }
   11538     2201122 :             hDelta = TotCap / AirMassFlow;
   11539     2201122 :             if (thisDXCoil.UserSHRCurveExists) {
   11540        3662 :                 if (SpeedRatio >= 1.0) {
   11541        2939 :                     SHR = SHRHS;
   11542             :                 } else {
   11543         723 :                     SHR = min(SpeedRatio * SHRHS + (1.0 - SpeedRatio) * SHRLS, 1.0);
   11544             :                 }
   11545        3662 :                 OutletAirEnthalpy = InletAirEnthalpy - hDelta;
   11546        3662 :                 if (SHR < 1.0) {
   11547        3662 :                     hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
   11548        3662 :                     OutletAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout);
   11549        3662 :                     if (OutletAirHumRat <= 0.0) {
   11550           0 :                         OutletAirHumRat = min(DryCoilOutletHumRatioMin, InletAirHumRat);
   11551             :                     }
   11552             :                 } else {
   11553           0 :                     SHR = 1.0;
   11554           0 :                     OutletAirHumRat = InletAirHumRat;
   11555             :                 }
   11556        3662 :                 OutletAirDryBulbTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
   11557        3662 :                 OutletAirDryBulbTempSat = PsyTdpFnWPb(state, OutletAirHumRat, OutdoorPressure, RoutineNameHighSpeedOutlet);
   11558        3662 :                 if (OutletAirDryBulbTempSat > OutletAirDryBulbTemp) {
   11559        3635 :                     OutletAirDryBulbTemp = OutletAirDryBulbTempSat;
   11560        3635 :                     OutletAirHumRat = PsyWFnTdbH(state, OutletAirDryBulbTemp, OutletAirEnthalpy, RoutineNameHighSpeedOutlet);
   11561             :                 }
   11562             : 
   11563             :             } else {
   11564             :                 // Adjust CBF for off-nominal flow
   11565     2197460 :                 CBF = AdjustCBF(CBFNom, AirMassFlowNom, AirMassFlow);
   11566             :                 // Calculate new apparatus dew point conditions
   11567     2197460 :                 hADP = InletAirEnthalpy - hDelta / (1.0 - CBF);
   11568     2197460 :                 tADP = PsyTsatFnHPb(state, hADP, OutdoorPressure);
   11569             :                 //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   11570             :                 //    tADP = PsyTsatFnHPb(hADP,InletAirPressure)
   11571     2197460 :                 wADP = PsyWFnTdbH(state, tADP, hADP);
   11572     2197460 :                 hTinwADP = PsyHFnTdbW(InletAirDryBulbTemp, wADP);
   11573             :                 // get corresponding SHR
   11574     2197460 :                 if ((InletAirEnthalpy - hADP) > 1.e-10) {
   11575     2197460 :                     SHR = min((hTinwADP - hADP) / (InletAirEnthalpy - hADP), 1.0);
   11576             :                 } else {
   11577           0 :                     SHR = 1.0;
   11578             :                 }
   11579             : 
   11580             :                 // cr8918    SHR = MIN((hTinwADP-hADP)/(InletAirEnthalpy-hADP),1.0d0)
   11581     2197460 :                 OutletAirEnthalpy = InletAirEnthalpy - hDelta;
   11582             :                 // get outlet conditions
   11583     2197460 :                 hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
   11584     2197460 :                 OutletAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout);
   11585             : 
   11586     2197460 :                 OutletAirDryBulbTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
   11587     2197460 :                 OutletAirDryBulbTempSat = PsyTsatFnHPb(state, OutletAirEnthalpy, OutdoorPressure);
   11588     2197460 :                 if (OutletAirDryBulbTemp < OutletAirDryBulbTempSat) { // Limit to saturated conditions at OutletAirEnthalpy
   11589      383753 :                     OutletAirDryBulbTemp = OutletAirDryBulbTempSat;
   11590      383753 :                     OutletAirHumRat = PsyWFnTdbH(state, OutletAirDryBulbTemp, OutletAirEnthalpy);
   11591             :                 }
   11592             :             }
   11593             :             // Coil total/sensible/latent cooling rates and electrical power
   11594     2201122 :             CalcComponentSensibleLatentOutput(AirMassFlow,
   11595             :                                               InletAirDryBulbTemp,
   11596             :                                               InletAirHumRat,
   11597             :                                               OutletAirDryBulbTemp,
   11598             :                                               OutletAirHumRat,
   11599     2201122 :                                               thisDXCoil.SensCoolingEnergyRate,
   11600     2201122 :                                               thisDXCoil.LatCoolingEnergyRate,
   11601     2201122 :                                               thisDXCoil.TotalCoolingEnergyRate);
   11602     2201122 :             thisDXCoil.ElecCoolingPower = TotCap * EIR;
   11603             :             //   Calculation for heat reclaim needs to be corrected to use compressor power (not including condenser fan power)
   11604     2201122 :             state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).AvailCapacity = thisDXCoil.TotalCoolingEnergyRate + thisDXCoil.ElecCoolingPower;
   11605     2201122 :             thisDXCoil.PartLoadRatio = 1.0;
   11606     2201122 :             thisDXCoil.CoolingCoilRuntimeFraction = 1.0;
   11607             : 
   11608     2201122 :             thisDXCoil.OutletAirEnthalpy = OutletAirEnthalpy;
   11609     2201122 :             thisDXCoil.OutletAirHumRat = OutletAirHumRat;
   11610     2201122 :             thisDXCoil.OutletAirTemp = OutletAirDryBulbTemp;
   11611             : 
   11612      860061 :         } else if (CycRatio > 0.0) {
   11613             : 
   11614      860061 :             if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Evap) {
   11615             :                 // Outdoor wet-bulb temp from DataEnvironment + (1.0-EvapCondEffectiveness) * (drybulb - wetbulb)
   11616        6143 :                 CondInletTemp = OutdoorWetBulb + (OutdoorDryBulb - OutdoorWetBulb) * (1.0 - thisDXCoil.EvapCondEffect2);
   11617        6143 :                 CondInletHumRat = PsyWFnTdbTwbPb(state, CondInletTemp, OutdoorWetBulb, OutdoorPressure);
   11618             :             }
   11619             : 
   11620             :             // Adjust low speed coil bypass factor for actual flow rate.
   11621             :             // CBF = AdjustCBF(DXCoil(DXCoilNum)%RatedCBF2,DXCoil(DXCoilNum)%RatedAirMassFlowRate2,AirMassFlow)
   11622             :             // get low speed total capacity and SHR at current conditions
   11623      860061 :             CalcTotCapSHR(state,
   11624             :                           InletAirDryBulbTemp,
   11625             :                           InletAirHumRat,
   11626             :                           InletAirEnthalpy,
   11627             :                           InletAirWetBulbC,
   11628             :                           1.0,
   11629             :                           thisDXCoil.RatedAirMassFlowRate2,
   11630             :                           thisDXCoil.RatedTotCap2,
   11631             :                           thisDXCoil.RatedCBF2,
   11632             :                           thisDXCoil.CCapFTemp2,
   11633      860061 :                           thisDXCoil.CCapFFlow(Mode),
   11634             :                           TotCapLS,
   11635             :                           SHRLS,
   11636             :                           CondInletTemp,
   11637             :                           OutdoorPressure,
   11638      860061 :                           thisDXCoil.capModFacTotal);
   11639             :             // get the low speed SHR from user specified SHR modifier curves
   11640      860061 :             if (thisDXCoil.UserSHRCurveExists) {
   11641        1886 :                 SHRLS = CalcSHRUserDefinedCurves(
   11642             :                     state, InletAirDryBulbTemp, InletAirWetBulbC, 1.0, thisDXCoil.SHRFTemp2, thisDXCoil.SHRFFlow2, thisDXCoil.RatedSHR2);
   11643             :             }
   11644             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   11645             :             //                       Node(DXCoil(DXCoilNum)%AirInNode)%Press)
   11646      860061 :             hDelta = TotCapLS / AirMassFlow;
   11647      860061 :             if (thisDXCoil.UserSHRCurveExists) {
   11648        1886 :                 SHR = SHRLS;
   11649        1886 :                 LSOutletAirEnthalpy = InletAirEnthalpy - hDelta;
   11650        1886 :                 if (SHR < 1.0) {
   11651        1886 :                     hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
   11652        1886 :                     LSOutletAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout);
   11653        1886 :                     if (LSOutletAirHumRat <= 0.0) {
   11654           0 :                         LSOutletAirHumRat = min(DryCoilOutletHumRatioMin, InletAirHumRat);
   11655             :                     }
   11656             :                 } else {
   11657           0 :                     SHR = 1.0;
   11658           0 :                     LSOutletAirHumRat = InletAirHumRat;
   11659             :                 }
   11660        1886 :                 LSOutletAirDryBulbTemp = PsyTdbFnHW(LSOutletAirEnthalpy, LSOutletAirHumRat);
   11661        1886 :                 OutletAirDryBulbTempSat = PsyTdpFnWPb(state, LSOutletAirHumRat, OutdoorPressure, RoutineNameLowSpeedOutlet);
   11662        1886 :                 if (OutletAirDryBulbTempSat > LSOutletAirDryBulbTemp) {
   11663           1 :                     LSOutletAirDryBulbTemp = OutletAirDryBulbTempSat;
   11664           1 :                     LSOutletAirHumRat = PsyWFnTdbH(state, LSOutletAirDryBulbTemp, LSOutletAirEnthalpy, RoutineNameLowSpeedOutlet);
   11665             :                 }
   11666             : 
   11667             :             } else {
   11668             :                 // Adjust CBF for off-nominal flow
   11669      858175 :                 CBF = AdjustCBF(thisDXCoil.RatedCBF2, thisDXCoil.RatedAirMassFlowRate2, AirMassFlow);
   11670             :                 // Calculate new apparatus dew point conditions
   11671      858175 :                 hADP = InletAirEnthalpy - hDelta / (1.0 - CBF);
   11672      858175 :                 tADP = PsyTsatFnHPb(state, hADP, OutdoorPressure, RoutineNameNewDewPointConditions);
   11673             :                 //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   11674             :                 //    tADP = PsyTsatFnHPb(hADP,InletAirPressure)
   11675      858175 :                 wADP = PsyWFnTdbH(state, tADP, hADP, RoutineNameNewDewPointConditions);
   11676      858175 :                 hTinwADP = PsyHFnTdbW(InletAirDryBulbTemp, wADP);
   11677             :                 // get corresponding SHR
   11678      858175 :                 if ((InletAirEnthalpy - hADP) > 1.e-10) {
   11679      858175 :                     SHR = min((hTinwADP - hADP) / (InletAirEnthalpy - hADP), 1.0);
   11680             :                 } else {
   11681           0 :                     SHR = 1.0;
   11682             :                 }
   11683             :                 // cr8918    SHR = MIN((hTinwADP-hADP)/(InletAirEnthalpy-hADP),1.0d0)
   11684             :                 // get low speed outlet conditions
   11685      858175 :                 LSOutletAirEnthalpy = InletAirEnthalpy - hDelta;
   11686      858175 :                 hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
   11687      858175 :                 LSOutletAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout);
   11688      858175 :                 LSOutletAirDryBulbTemp = PsyTdbFnHW(LSOutletAirEnthalpy, LSOutletAirHumRat);
   11689      858175 :                 OutletAirDryBulbTempSat = PsyTsatFnHPb(state, LSOutletAirEnthalpy, OutdoorPressure, RoutineNameLowSpeedOutlet);
   11690      858175 :                 if (LSOutletAirDryBulbTemp < OutletAirDryBulbTempSat) { // Limit to saturated conditions at OutletAirEnthalpy
   11691       84351 :                     LSOutletAirDryBulbTemp = OutletAirDryBulbTempSat;
   11692       84351 :                     LSOutletAirHumRat = PsyWFnTdbH(state, LSOutletAirDryBulbTemp, LSOutletAirEnthalpy, RoutineNameLowSpeedOutlet);
   11693             :                 }
   11694             :             }
   11695             :             // outlet conditions are average of inlet and low speed weighted by CycRatio
   11696      860061 :             OutletAirEnthalpy = CycRatio * LSOutletAirEnthalpy + (1.0 - CycRatio) * InletAirEnthalpy;
   11697      860061 :             OutletAirHumRat = CycRatio * LSOutletAirHumRat + (1.0 - CycRatio) * InletAirHumRat;
   11698      860061 :             OutletAirDryBulbTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
   11699             :             // get low speed EIR at current conditions
   11700             :             //    EIRTempModFacLS = CurveValue(state, DXCoil(DXCoilNum)%EIRFTemp(Mode),InletAirWetBulbC,CondInletTemp)
   11701             :             //    CR7307 changed EIRTempModFacLS calculation to that shown below.
   11702      860061 :             EIRTempModFacLS = CurveValue(state, thisDXCoil.EIRFTemp2, InletAirWetBulbC, CondInletTemp);
   11703      860061 :             EIRLS = thisDXCoil.RatedEIR2 * EIRTempModFacLS;
   11704             :             // get the part load factor that will account for cycling losses
   11705      860061 :             PLF = CurveValue(state, thisDXCoil.PLFFPLR(Mode), CycRatio);
   11706      860061 :             if (PLF < 0.7) {
   11707           0 :                 PLF = 0.7;
   11708             :             }
   11709             :             // calculate the run time fraction
   11710      860061 :             thisDXCoil.CoolingCoilRuntimeFraction = CycRatio / PLF;
   11711      860061 :             thisDXCoil.PartLoadRatio = CycRatio;
   11712      860061 :             if (thisDXCoil.CoolingCoilRuntimeFraction > 1.0) {
   11713           0 :                 thisDXCoil.CoolingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   11714             :             }
   11715             :             // get the eletrical power consumption
   11716      860061 :             thisDXCoil.ElecCoolingPower = TotCapLS * EIRLS * thisDXCoil.CoolingCoilRuntimeFraction;
   11717             : 
   11718             :             // Coil total/sensible/latent cooling rates and electrical power
   11719      860061 :             CalcComponentSensibleLatentOutput(AirMassFlow,
   11720             :                                               InletAirDryBulbTemp,
   11721             :                                               InletAirHumRat,
   11722             :                                               OutletAirDryBulbTemp,
   11723             :                                               OutletAirHumRat,
   11724      860061 :                                               thisDXCoil.SensCoolingEnergyRate,
   11725      860061 :                                               thisDXCoil.LatCoolingEnergyRate,
   11726      860061 :                                               thisDXCoil.TotalCoolingEnergyRate);
   11727      860061 :             state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).AvailCapacity = thisDXCoil.TotalCoolingEnergyRate + thisDXCoil.ElecCoolingPower;
   11728      860061 :             thisDXCoil.OutletAirEnthalpy = OutletAirEnthalpy;
   11729      860061 :             thisDXCoil.OutletAirHumRat = OutletAirHumRat;
   11730      860061 :             thisDXCoil.OutletAirTemp = OutletAirDryBulbTemp;
   11731      860061 :             CondAirMassFlow = RhoAir * thisDXCoil.EvapCondAirFlow2 * thisDXCoil.CoolingCoilRuntimeFraction;
   11732      860061 :             EvapCondPumpElecPower = thisDXCoil.EvapCondPumpElecNomPower2 * thisDXCoil.CoolingCoilRuntimeFraction;
   11733             :         }
   11734             : 
   11735     3061183 :         if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Evap) {
   11736             :             //******************
   11737             :             //             WATER CONSUMPTION IN m3 OF WATER FOR DIRECT
   11738             :             //             H2O [m3/s] = Delta W[kgWater/kgDryAir]*Mass Flow Air[kgDryAir/s]
   11739             :             //                                /RhoWater [kgWater/m3]
   11740             :             //******************
   11741       19013 :             RhoWater = RhoH2O(OutdoorDryBulb);
   11742       19013 :             thisDXCoil.EvapWaterConsumpRate = (CondInletHumRat - OutdoorHumRat) * CondAirMassFlow / RhoWater;
   11743       19013 :             thisDXCoil.EvapCondPumpElecPower = EvapCondPumpElecPower;
   11744             :             // set water system demand request (if needed)
   11745       19013 :             if (thisDXCoil.EvapWaterSupplyMode == EvapWaterSupply::FromTank) {
   11746             : 
   11747           0 :                 state.dataWaterData->WaterStorage(thisDXCoil.EvapWaterSupTankID).VdotRequestDemand(thisDXCoil.EvapWaterTankDemandARRID) =
   11748           0 :                     thisDXCoil.EvapWaterConsumpRate;
   11749             :             }
   11750             : 
   11751             :             // Calculate basin heater power
   11752       19013 :             CalcBasinHeaterPower(state,
   11753             :                                  thisDXCoil.BasinHeaterPowerFTempDiff,
   11754             :                                  thisDXCoil.BasinHeaterSchedulePtr,
   11755             :                                  thisDXCoil.BasinHeaterSetPointTemp,
   11756       19013 :                                  thisDXCoil.BasinHeaterPower);
   11757       19013 :             thisDXCoil.BasinHeaterPower *= (1.0 - thisDXCoil.CoolingCoilRuntimeFraction);
   11758             :         }
   11759             : 
   11760             :     } else {
   11761             : 
   11762             :         // DX coil is off; just pass through conditions
   11763     1082417 :         thisDXCoil.OutletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   11764     1082417 :         thisDXCoil.OutletAirHumRat = thisDXCoil.InletAirHumRat;
   11765     1082417 :         thisDXCoil.OutletAirTemp = thisDXCoil.InletAirTemp;
   11766             : 
   11767     1082417 :         thisDXCoil.ElecCoolingPower = 0.0;
   11768     1082417 :         thisDXCoil.TotalCoolingEnergyRate = 0.0;
   11769     1082417 :         thisDXCoil.SensCoolingEnergyRate = 0.0;
   11770     1082417 :         thisDXCoil.LatCoolingEnergyRate = 0.0;
   11771     1082417 :         thisDXCoil.EvapCondPumpElecPower = 0.0;
   11772     1082417 :         thisDXCoil.EvapWaterConsumpRate = 0.0;
   11773             : 
   11774             :         // Calculate basin heater power
   11775     1082417 :         if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Evap) {
   11776        4480 :             CalcBasinHeaterPower(state,
   11777             :                                  thisDXCoil.BasinHeaterPowerFTempDiff,
   11778             :                                  thisDXCoil.BasinHeaterSchedulePtr,
   11779             :                                  thisDXCoil.BasinHeaterSetPointTemp,
   11780        4480 :                                  thisDXCoil.BasinHeaterPower);
   11781             :         }
   11782             :     }
   11783             : 
   11784     4143600 :     state.dataDXCoils->DXCoilOutletTemp(DXCoilNum) = thisDXCoil.OutletAirTemp;
   11785     4143600 :     state.dataDXCoils->DXCoilOutletHumRat(DXCoilNum) = thisDXCoil.OutletAirHumRat;
   11786     4143600 :     thisDXCoil.CondInletTemp = CondInletTemp; // Save condenser inlet temp in the data structure
   11787             : 
   11788             :     // set outlet node conditions
   11789     4143600 :     int airOutletNode = thisDXCoil.AirOutNode;
   11790     4143600 :     state.dataLoopNodes->Node(airOutletNode).Temp = thisDXCoil.OutletAirTemp;
   11791     4143600 :     state.dataLoopNodes->Node(airOutletNode).HumRat = thisDXCoil.OutletAirHumRat;
   11792             : 
   11793             :     // calc secondary coil if specified
   11794     4143600 :     if (thisDXCoil.IsSecondaryDXCoilInZone) {
   11795           0 :         CalcSecondaryDXCoils(state, DXCoilNum);
   11796             :     }
   11797     4143600 : }
   11798             : 
   11799      130449 : void CalcBasinHeaterPowerForMultiModeDXCoil(EnergyPlusData &state,
   11800             :                                             int const DXCoilNum,             // Index of coil being simulated
   11801             :                                             HVAC::CoilMode const DehumidMode // Dehumidification mode (0=normal, 1=enhanced)
   11802             : )
   11803             : {
   11804             : 
   11805             :     // SUBROUTINE INFORMATION:
   11806             :     //       AUTHOR         Chandan Sharma, FSEC
   11807             :     //       DATE WRITTEN   May 2010
   11808             : 
   11809             :     // PURPOSE OF THIS SUBROUTINE:
   11810             :     // To calculate the basin heater power for multi mode DX cooling coil
   11811             : 
   11812             :     // METHODOLOGY EMPLOYED:
   11813             :     // The methodology employed is as follows:
   11814             :     // 1) If the number of capacity stages is equal to 1 and the CondenserType for stage 1
   11815             :     //    is EvapCooled, then the basin heater power is calculated for (1-runtimefractionstage1) of DX coil
   11816             :     // 2) If the number of capacity stages is greater than 1, then
   11817             :     //    a) If the CondenserType for stage 1 is EvapCooled, then the basin heater power is calculated for
   11818             :     //       (1-runtimefractionofstage1) of DX coil
   11819             :     //    b) Elseif the CondenserType for stage 2 is EvapCooled, then the basin heater power is calculated for
   11820             :     //       (1-runtimefractionofstage2) of DX coil
   11821             : 
   11822             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   11823             :     int PerfMode; // Performance mode for MultiMode DX coil; Always 1 for other coil types
   11824             :     // 1-2=normal mode: 1=stage 1 only, 2=stage 1&2
   11825             :     // 3-4=enhanced dehumidification mode: 3=stage 1 only, 4=stage 1&2
   11826             : 
   11827      130449 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   11828             : 
   11829      130449 :     if (thisDXCoil.NumCapacityStages == 1) {
   11830       11265 :         thisDXCoil.BasinHeaterPower *= (1.0 - thisDXCoil.CoolingCoilRuntimeFraction);
   11831             :     } else {
   11832      119184 :         PerfMode = (int)DehumidMode * 2 + 1;
   11833      119184 :         if (thisDXCoil.CondenserType(PerfMode) == DataHeatBalance::RefrigCondenserType::Evap) {
   11834           0 :             thisDXCoil.BasinHeaterPower *= (1.0 - thisDXCoil.CoolingCoilRuntimeFraction);
   11835      119184 :         } else if (thisDXCoil.CondenserType(PerfMode + 1) == DataHeatBalance::RefrigCondenserType::Evap) {
   11836           0 :             CalcBasinHeaterPower(state,
   11837             :                                  thisDXCoil.BasinHeaterPowerFTempDiff,
   11838             :                                  thisDXCoil.BasinHeaterSchedulePtr,
   11839             :                                  thisDXCoil.BasinHeaterSetPointTemp,
   11840           0 :                                  thisDXCoil.BasinHeaterPower);
   11841           0 :             thisDXCoil.BasinHeaterPower *= (1.0 - thisDXCoil.CoolingCoilStg2RuntimeFrac);
   11842             :         }
   11843             :     }
   11844      130449 : }
   11845             : 
   11846    53239294 : Real64 AdjustCBF(Real64 const CBFNom,             // nominal coil bypass factor
   11847             :                  Real64 const AirMassFlowRateNom, // nominal air mass flow rate [kg/s]
   11848             :                  Real64 const AirMassFlowRate     // actual air mass flow rate [kg/s]
   11849             : )
   11850             : {
   11851             : 
   11852             :     // FUNCTION INFORMATION:
   11853             :     //       AUTHOR         Fred Buhl using Don Shirey's code
   11854             :     //       DATE WRITTEN   September 2002
   11855             : 
   11856             :     // PURPOSE OF THIS FUNCTION:
   11857             :     //    Adjust coil bypass factor for actual air flow rate.
   11858             : 
   11859             :     // METHODOLOGY EMPLOYED:
   11860             :     // Uses relation CBF = exp(-NTU) whereNTU = A0/(m*cp). Relationship models the cooling coil
   11861             :     // as a heat exchanger with Cmin/Cmax = 0.
   11862             : 
   11863             :     // Return value
   11864             :     Real64 CBFAdj; // the result - the adjusted coil bypass factor
   11865             : 
   11866             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   11867             :     Real64 A0;    // intermediate variable
   11868             :     Real64 ADiff; // intermediate variable
   11869             : 
   11870    53239294 :     if (CBFNom > 0.0) {
   11871    53239294 :         A0 = -std::log(CBFNom) * AirMassFlowRateNom;
   11872             :     } else {
   11873           0 :         A0 = 0.0;
   11874             :     }
   11875    53239294 :     ADiff = -A0 / AirMassFlowRate;
   11876    53239294 :     if (ADiff >= DataPrecisionGlobals::EXP_LowerLimit) {
   11877    53212495 :         CBFAdj = std::exp(ADiff);
   11878             :     } else {
   11879       26799 :         CBFAdj = 1.0e-6;
   11880             :     }
   11881             : 
   11882    53239294 :     return CBFAdj;
   11883             : }
   11884             : 
   11885       26335 : Real64 CalcCBF(EnergyPlusData &state,
   11886             :                std::string const &UnitType,
   11887             :                std::string const &UnitName,
   11888             :                Real64 const InletAirTemp,   // inlet air temperature [C]
   11889             :                Real64 const InletAirHumRat, // inlet air humidity ratio [kg water / kg dry air]
   11890             :                Real64 const TotCap,         // total cooling  capacity [Watts]
   11891             :                Real64 const AirVolFlowRate, // the air volume flow rate at the given capacity [m3/s]
   11892             :                Real64 const SHR,            // sensible heat ratio at the given capacity and flow rate
   11893             :                bool const PrintFlag         // flag used to print warnings if desired
   11894             : )
   11895             : {
   11896             : 
   11897             :     // FUNCTION INFORMATION:
   11898             :     //       AUTHOR         Fred Buhl using Don Shirey's code
   11899             :     //       DATE WRITTEN   September 2002
   11900             : 
   11901             :     // PURPOSE OF THIS FUNCTION:
   11902             :     // Calculate the coil bypass factor for a coil given the total capacity at the entering conditions,
   11903             :     // air mass flow rate at the entering conditions, and the sensible heat ratio (SHR) at the
   11904             :     // entering conditions. Standard barometric pressure is used for this model parameter.
   11905             : 
   11906             :     // METHODOLOGY EMPLOYED:
   11907             :     // calculate SlopeRated (deltahumrat/deltaT) using rated unit information provided by
   11908             :     // user. Then hunt along saturation curve of psychrometric chart until the slope of the line
   11909             :     // between the saturation point and rated inlet air humidity ratio and T is the same as SlopeRated.
   11910             :     // When the slopes are equal, then we have located the apparatus dewpoint of the coil at rated
   11911             :     // conditions. From this information, coil bypass factor is calculated.
   11912             : 
   11913             :     // Using/Aliasing
   11914             : 
   11915             :     // Return value
   11916       26335 :     Real64 CBF(0.0); // the result - the coil bypass factor
   11917             : 
   11918             :     // FUNCTION PARAMETER DEFINITIONS:
   11919             :     static constexpr std::string_view RoutineName("CalcCBF");
   11920       26335 :     constexpr Real64 SmallDifferenceTest(0.00000001);
   11921             : 
   11922             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   11923             :     Real64 InletAirEnthalpy;                // Enthalpy of inlet air to evaporator at given conditions [J/kg]
   11924       26335 :     Real64 DeltaH(0.0);                     // Enthalpy drop across evaporator at given conditions [J/kg]
   11925       26335 :     Real64 DeltaT(0.0);                     // Temperature drop across evaporator at given conditions [C]
   11926       26335 :     Real64 DeltaHumRat(0.0);                // Humidity ratio drop across evaporator at given conditions [kg/kg]
   11927       26335 :     Real64 OutletAirTemp(InletAirTemp);     // Outlet dry-bulb temperature from evaporator at given conditions [C]
   11928       26335 :     Real64 OutletAirTempSat(InletAirTemp);  // Saturation dry-bulb temperature from evaporator at outlet air enthalpy [C]
   11929             :     Real64 OutletAirEnthalpy;               // Enthalpy of outlet air at given conditions [J/kg]
   11930       26335 :     Real64 OutletAirHumRat(InletAirHumRat); // Outlet humidity ratio from evaporator at given conditions [kg/kg]
   11931             :     Real64 OutletAirRH;                     // relative humidity of the outlet air
   11932             :     Real64 Error;                           // Error term used in given coil bypass factor (CBF) calculations
   11933             :     Real64 ErrorLast;                       // Error term, from previous iteration
   11934             :     int Iter;                               // Iteration loop counter in CBF calculations
   11935       26335 :     int IterMax(50);                        // Maximum number of iterations in CBF calculations
   11936             :     Real64 ADPTemp;                         // Apparatus dewpoint temperature used in CBF calculations [C]
   11937             :     Real64 ADPHumRat;                       // Apparatus dewpoint humidity used in CBF calculations [kg/kg]
   11938             :     Real64 ADPEnthalpy;                     // Air enthalpy at apparatus dew point [J/kg]
   11939             :     Real64 DeltaADPTemp;                    // Change in Apparatus Dew Point used in CBF calculations [C]
   11940       26335 :     Real64 SlopeAtConds(0.0);               // Slope (DeltaHumRat/DeltaT) at given conditions
   11941       26335 :     Real64 Slope(0.0);                      // Calculated Slope used while hunting for Tadp
   11942             :     Real64 Tolerance;                       // Convergence tolerance for CBF calculations
   11943             :     Real64 HTinHumRatOut;                   // Air enthalpy at inlet air temp and outlet air humidity ratio [J/kg]
   11944             :     Real64 AirMassFlowRate;                 // the standard air mass flow rate at the given capacity [kg/s]
   11945             :     Real64 adjustedSHR;                     // SHR calculated using adjusted outlet air properties []
   11946       26335 :     bool CBFErrors(false);                  // Set to true if errors in CBF calculation, fatal at end of routine
   11947             : 
   11948       26335 :     auto &DXCT = state.dataHVACGlobal->DXCT;
   11949             : 
   11950       26335 :     if (AirVolFlowRate <= 0.0 || TotCap <= 0.0) { // Coil not running or has no capacity, don't calculate CBF
   11951           0 :         return CBF;
   11952             :     }
   11953             : 
   11954       26335 :     AirMassFlowRate = AirVolFlowRate * PsyRhoAirFnPbTdbW(state, DataEnvironment::StdPressureSeaLevel, InletAirTemp, InletAirHumRat, RoutineName);
   11955       26335 :     DeltaH = TotCap / AirMassFlowRate;
   11956       26335 :     InletAirEnthalpy = PsyHFnTdbW(InletAirTemp, InletAirHumRat);
   11957       26335 :     HTinHumRatOut = InletAirEnthalpy - (1.0 - SHR) * DeltaH;
   11958       26335 :     OutletAirHumRat = PsyWFnTdbH(state, InletAirTemp, HTinHumRatOut);
   11959       26335 :     DeltaHumRat = InletAirHumRat - OutletAirHumRat;
   11960       26335 :     OutletAirEnthalpy = InletAirEnthalpy - DeltaH;
   11961       26335 :     OutletAirTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
   11962             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   11963             :     //  Pressure will have to be pass into this subroutine to fix this one
   11964       26335 :     OutletAirRH = PsyRhFnTdbWPb(state, OutletAirTemp, OutletAirHumRat, DataEnvironment::StdPressureSeaLevel, RoutineName);
   11965       26335 :     if (OutletAirRH >= 1.0 && PrintFlag) {
   11966          10 :         ShowWarningError(state, format("For object = {}, name = \"{}\"", UnitType, UnitName));
   11967          10 :         ShowContinueError(state, "Calculated outlet air relative humidity greater than 1. The combination of");
   11968          10 :         ShowContinueError(state, "rated air volume flow rate, total cooling capacity and sensible heat ratio yields coil exiting");
   11969          10 :         ShowContinueError(state, "air conditions above the saturation curve. Possible fixes are to reduce the rated total cooling");
   11970          10 :         ShowContinueError(state, "capacity, increase the rated air volume flow rate, or reduce the rated sensible heat ratio for this coil.");
   11971          10 :         ShowContinueError(state, "If autosizing, it is recommended that all three of these values be autosized.");
   11972          10 :         ShowContinueError(state, "...Inputs used for calculating cooling coil bypass factor.");
   11973          10 :         ShowContinueError(state, format("...Inlet Air Temperature     = {:.2R} C", InletAirTemp));
   11974          10 :         ShowContinueError(state, format("...Outlet Air Temperature    = {:.2R} C", OutletAirTemp));
   11975          10 :         ShowContinueError(state, format("...Inlet Air Humidity Ratio  = {:.6R} kgWater/kgDryAir", InletAirHumRat));
   11976          10 :         ShowContinueError(state, format("...Outlet Air Humidity Ratio = {:.6R} kgWater/kgDryAir", OutletAirHumRat));
   11977          10 :         ShowContinueError(state, format("...Total Cooling Capacity used in calculation = {:.2R} W", TotCap));
   11978          10 :         ShowContinueError(state, format("...Air Mass Flow Rate used in calculation     = {:.6R} kg/s", AirMassFlowRate));
   11979          10 :         ShowContinueError(state, format("...Air Volume Flow Rate used in calculation   = {:.6R} m3/s", AirVolFlowRate));
   11980          10 :         if (TotCap > 0.0) {
   11981          20 :             if (((HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT] - AirVolFlowRate / TotCap) > SmallDifferenceTest) ||
   11982          10 :                 ((AirVolFlowRate / TotCap - HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) > SmallDifferenceTest)) {
   11983           0 :                 ShowContinueError(state,
   11984           0 :                                   format("...Air Volume Flow Rate per Watt of Rated Cooling Capacity is also out of bounds at = {:.7R} m3/s/W",
   11985           0 :                                          AirVolFlowRate / TotCap));
   11986             :             }
   11987             :         }
   11988          10 :         ShowContinueErrorTimeStamp(state, "");
   11989          10 :         OutletAirTempSat = PsyTsatFnHPb(state, OutletAirEnthalpy, DataEnvironment::StdPressureSeaLevel, RoutineName);
   11990          10 :         if (OutletAirTemp < OutletAirTempSat) { // Limit to saturated conditions at OutletAirEnthalpy
   11991          10 :             OutletAirTemp = OutletAirTempSat + 0.005;
   11992          10 :             OutletAirHumRat = PsyWFnTdbH(state, OutletAirTemp, OutletAirEnthalpy, RoutineName);
   11993          10 :             DeltaHumRat = InletAirHumRat - OutletAirHumRat;
   11994          10 :             HTinHumRatOut = PsyHFnTdbW(InletAirTemp, OutletAirHumRat);
   11995          10 :             adjustedSHR = (HTinHumRatOut - OutletAirEnthalpy) / DeltaH;
   11996          10 :             ShowContinueError(state, "CalcCBF: SHR adjusted to achieve valid outlet air properties and the simulation continues.");
   11997          10 :             ShowContinueError(state, format("CalcCBF: initial SHR = {:.5R}", SHR));
   11998          10 :             ShowContinueError(state, format("CalcCBF: adjusted SHR = {:.5R}", adjustedSHR));
   11999             :         }
   12000             :     }
   12001       26335 :     DeltaT = InletAirTemp - OutletAirTemp;
   12002       26335 :     if (DeltaT <= 0.0) {
   12003           0 :         ShowSevereError(state, format("For object = {}, name = \"{}\"", UnitType, UnitName));
   12004           0 :         ShowContinueError(state, "Calculated coil delta T is less than or equal to 0. The combination of");
   12005           0 :         ShowContinueError(state, "rated air volume flow rate, total cooling capacity and sensible heat ratio yields coil exiting");
   12006           0 :         ShowContinueError(state, "air conditions that are not reasonable. Possible fixes are to adjust the rated total cooling");
   12007           0 :         ShowContinueError(state, "capacity, rated air volume flow rate, or rated sensible heat ratio for this coil.");
   12008           0 :         ShowContinueError(state, "If autosizing, it is recommended that all three of these values be autosized.");
   12009           0 :         ShowContinueError(state, "...Inputs used for calculating cooling coil bypass factor.");
   12010           0 :         ShowContinueError(state, format("...Inlet Air Temperature     = {:.2R} C", InletAirTemp));
   12011           0 :         ShowContinueError(state, format("...Outlet Air Temperature    = {:.2R} C", OutletAirTemp));
   12012           0 :         ShowContinueError(state, format("...Inlet Air Humidity Ratio  = {:.6R} kgWater/kgDryAir", InletAirHumRat));
   12013           0 :         ShowContinueError(state, format("...Outlet Air Humidity Ratio = {:.6R} kgWater/kgDryAir", OutletAirHumRat));
   12014           0 :         ShowContinueError(state, format("...Total Cooling Capacity used in calculation = {:.2R} W", TotCap));
   12015           0 :         ShowContinueError(state, format("...Air Mass Flow Rate used in calculation     = {:.6R} kg/s", AirMassFlowRate));
   12016           0 :         ShowContinueError(state, format("...Air Volume Flow Rate used in calculation   = {:.6R} m3/s", AirVolFlowRate));
   12017           0 :         if (TotCap > 0.0) {
   12018           0 :             if (((HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT] - AirVolFlowRate / TotCap) > SmallDifferenceTest) ||
   12019           0 :                 ((AirVolFlowRate / TotCap - HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) > SmallDifferenceTest)) {
   12020           0 :                 ShowContinueError(state,
   12021           0 :                                   format("...Air Volume Flow Rate per Watt of Rated Cooling Capacity is also out of bounds at = {:.7R} m3/s/W",
   12022           0 :                                          AirVolFlowRate / TotCap));
   12023             :             }
   12024             :         }
   12025           0 :         ShowContinueErrorTimeStamp(state, "");
   12026           0 :         ShowFatalError(state, "Check and revise the input data for this coil before rerunning the simulation.");
   12027             :     }
   12028             :     // Calculate slope at given conditions
   12029       26335 :     if (DeltaT > 0.0) SlopeAtConds = DeltaHumRat / DeltaT;
   12030             : 
   12031             :     //  IF (SlopeAtConds .le. .0000001d0 .or. OutletAirHumRat .le. 0.0d0) THEN
   12032       26335 :     if (SlopeAtConds < 0.0 || OutletAirHumRat <= 0.0) {
   12033             :         //   Invalid conditions, slope can't be less than zero (SHR > 1) or
   12034             :         //   outlet air humidity ratio can't be less than zero.
   12035           0 :         ShowSevereError(state, format("{} \"{}\"", UnitType, UnitName));
   12036           0 :         ShowContinueError(state, "...Invalid slope or outlet air condition when calculating cooling coil bypass factor.");
   12037           0 :         ShowContinueError(state, format("...Slope = {:.8R}", SlopeAtConds));
   12038           0 :         ShowContinueError(state, format("...Inlet Air Temperature     = {:.2R} C", InletAirTemp));
   12039           0 :         ShowContinueError(state, format("...Outlet Air Temperature    = {:.2R} C", OutletAirTemp));
   12040           0 :         ShowContinueError(state, format("...Inlet Air Humidity Ratio  = {:.6R} kgWater/kgDryAir", InletAirHumRat));
   12041           0 :         ShowContinueError(state, format("...Outlet Air Humidity Ratio = {:.6R} kgWater/kgDryAir", OutletAirHumRat));
   12042           0 :         ShowContinueError(state, format("...Total Cooling Capacity used in calculation = {:.2R} W", TotCap));
   12043           0 :         ShowContinueError(state, format("...Air Mass Flow Rate used in calculation     = {:.6R} kg/s", AirMassFlowRate));
   12044           0 :         ShowContinueError(state, format("...Air Volume Flow Rate used in calculation   = {:.6R} m3/s", AirVolFlowRate));
   12045           0 :         if (TotCap > 0.0) {
   12046           0 :             if (((HVAC::MinRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT] - AirVolFlowRate / TotCap) > SmallDifferenceTest) ||
   12047           0 :                 ((AirVolFlowRate / TotCap - HVAC::MaxRatedVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) > SmallDifferenceTest)) {
   12048           0 :                 ShowContinueError(state,
   12049           0 :                                   format("...Air Volume Flow Rate per Watt of Rated Cooling Capacity is also out of bounds at = {:.7R} m3/s/W",
   12050           0 :                                          AirVolFlowRate / TotCap));
   12051             :             }
   12052             :         }
   12053           0 :         ShowContinueErrorTimeStamp(state, "");
   12054           0 :         CBFErrors = true;
   12055           0 :         CBF = 0.0; //? Added: Is this what should be returned
   12056             :     } else {
   12057             : 
   12058             :         //   First guess for Tadp is outlet air dew point
   12059             :         //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   12060             :         //  Pressure will have to be pass into this subroutine to fix this one
   12061       26335 :         ADPTemp = PsyTdpFnWPb(state, OutletAirHumRat, DataEnvironment::StdPressureSeaLevel);
   12062             : 
   12063       26335 :         Tolerance = 1.0; // initial conditions for iteration
   12064       26335 :         ErrorLast = 100.0;
   12065       26335 :         Iter = 0;
   12066       26335 :         DeltaADPTemp = 5.0;
   12067      356445 :         while ((Iter <= IterMax) && (Tolerance > 0.001)) {
   12068             :             //     Do for IterMax iterations or until the error gets below .1%
   12069      330110 :             if (Iter > 0) ADPTemp += DeltaADPTemp;
   12070      330110 :             ++Iter;
   12071             : 
   12072             :             //     Find new slope using guessed Tadp
   12073             : 
   12074             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   12075             :             //  Pressure will have to be pass into this subroutine to fix this one
   12076      330110 :             ADPHumRat = min(OutletAirHumRat, PsyWFnTdpPb(state, ADPTemp, DataEnvironment::StdPressureSeaLevel));
   12077      330110 :             Slope = (InletAirHumRat - ADPHumRat) / max(0.001, (InletAirTemp - ADPTemp));
   12078             : 
   12079             :             //     check for convergence (slopes are equal to within error tolerance)
   12080             : 
   12081      330110 :             Error = (Slope - SlopeAtConds) / SlopeAtConds;
   12082      330110 :             if ((Error > 0.0) && (ErrorLast < 0.0)) {
   12083      106468 :                 DeltaADPTemp = -DeltaADPTemp / 2.0;
   12084      223642 :             } else if ((Error < 0.0) && (ErrorLast > 0.0)) {
   12085      120651 :                 DeltaADPTemp = -DeltaADPTemp / 2.0;
   12086      102991 :             } else if (std::abs(Error) > std::abs(ErrorLast)) {
   12087         543 :                 DeltaADPTemp = -DeltaADPTemp / 2.0;
   12088             :             }
   12089      330110 :             ErrorLast = Error;
   12090             : 
   12091      330110 :             Tolerance = std::abs(Error);
   12092             :         }
   12093             : 
   12094             :         //   Calculate Bypass Factor from Enthalpies
   12095             : 
   12096       26335 :         InletAirEnthalpy = PsyHFnTdbW(InletAirTemp, InletAirHumRat);
   12097       26335 :         OutletAirEnthalpy = PsyHFnTdbW(OutletAirTemp, OutletAirHumRat);
   12098       26335 :         ADPEnthalpy = PsyHFnTdbW(ADPTemp, ADPHumRat);
   12099       26335 :         CBF = min(1.0, (OutletAirEnthalpy - ADPEnthalpy) / (InletAirEnthalpy - ADPEnthalpy));
   12100       26335 :         if (Iter > IterMax && PrintFlag) {
   12101           0 :             ShowSevereError(state, format("{} \"{}\" -- coil bypass factor calculation did not converge after max iterations.", UnitType, UnitName));
   12102           0 :             ShowContinueError(state, format("The RatedSHR of [{:.3R}], entered by the user or autosized (see *.eio file),", SHR));
   12103           0 :             ShowContinueError(state, "may be causing this. The line defined by the coil rated inlet air conditions");
   12104           0 :             ShowContinueError(state, "(26.7C drybulb and 19.4C wetbulb) and the RatedSHR (i.e., slope of the line) must intersect");
   12105           0 :             ShowContinueError(state, "the saturation curve of the psychrometric chart. If the RatedSHR is too low, then this");
   12106           0 :             ShowContinueError(state, "intersection may not occur and the coil bypass factor calculation will not converge.");
   12107           0 :             ShowContinueError(state, "If autosizing the SHR, recheck the design supply air humidity ratio and design supply air");
   12108           0 :             ShowContinueError(state, "temperature values in the Sizing:System and Sizing:Zone objects. In general, the temperatures");
   12109           0 :             ShowContinueError(state, "and humidity ratios specified in these two objects should be the same for each system");
   12110           0 :             ShowContinueError(state, "and the zones that it serves.");
   12111           0 :             ShowContinueErrorTimeStamp(state, "");
   12112           0 :             CBFErrors = true; // Didn't converge within MaxIter iterations
   12113             :         }
   12114       26335 :         if (CBF < 0.0 && PrintFlag) {
   12115           0 :             ShowSevereError(state, format("{} \"{}\" -- negative coil bypass factor calculated.", UnitType, UnitName));
   12116           0 :             ShowContinueErrorTimeStamp(state, "");
   12117           0 :             CBFErrors = true; // Negative CBF not valid
   12118             :         }
   12119             :     }
   12120             : 
   12121             :     // Show fatal error for specific coil that caused a CBF error
   12122       26335 :     if (CBFErrors) {
   12123           0 :         ShowFatalError(state, format("{} \"{}\" Errors found in calculating coil bypass factors", UnitType, UnitName));
   12124             :     }
   12125             : 
   12126       26335 :     return CBF;
   12127             : }
   12128             : 
   12129         843 : Real64 ValidateADP(EnergyPlusData &state,
   12130             :                    std::string const &UnitType,      // component name
   12131             :                    std::string const &UnitName,      // component type
   12132             :                    Real64 const RatedInletAirTemp,   // coil inlet air temperature [C]
   12133             :                    Real64 const RatedInletAirHumRat, // coil inlet air humidity ratio [kg/kg]
   12134             :                    Real64 const TotCap,              // coil total capacity [W]
   12135             :                    Real64 const AirVolFlowRate,      // coil air volume flow rate [m3/s]
   12136             :                    Real64 const InitialSHR,          // coil sensible heat ratio []
   12137             :                    std::string const &CallingRoutine // function name calling this routine
   12138             : )
   12139             : {
   12140             : 
   12141             :     // FUNCTION INFORMATION:
   12142             :     //    AUTHOR         Richard Raustad, FSEC
   12143             :     //    DATE WRITTEN   December 2015
   12144             : 
   12145             :     // PURPOSE OF THIS FUNCTION:
   12146             :     //    Validates that the calcualted bypass factor represents valid SHR based on total capacity and air mass flow rate.
   12147             : 
   12148             :     // METHODOLOGY EMPLOYED:
   12149             :     //    With model parameters autosized by the user, the SHR is selected based on an empirical model.
   12150             :     //    This can sometimes lead to an SHR that does not cross the saturation curve, or one that crosses excessively where
   12151             :     //    the coil outlet air conditions exceed the saturation curve (i.e., RH > 1).
   12152             :     //    This function checks to see if the ADP based on coil delta T and calculated bypass factor and the ADP based
   12153             :     //    on coil delta W and calculated bypass factor land on the saturation curve at the same place within a tolerance.
   12154             :     //    The result is passed back to the sizing routine as the new value for SHR.
   12155             :     //    If the SHR is not autosized, this routine will still adjust the design SHR appropriately, however, the hard-sized SHR will not
   12156             :     //    change.
   12157             : 
   12158             :     // Return value
   12159         843 :     Real64 SHR(0.0); // the result - the adjusted design SHR
   12160             : 
   12161             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   12162         843 :     Real64 CBF_calculated(0.0);    // coil bypass factor based on TotCap, AirFlow, SHR, and BaroPress
   12163         843 :     Real64 InletAirEnthalpy(0.0);  // Enthalpy of inlet air to evaporator at given conditions [J/kg]
   12164         843 :     Real64 DeltaH(0.0);            // Enthalpy drop across evaporator at given conditions [J/kg]
   12165         843 :     Real64 HTinHumRatOut(0.0);     // Air enthalpy at inlet air temp and outlet air humidity ratio [J/kg]
   12166         843 :     Real64 DeltaHumRat(0.0);       // Humidity ratio drop across evaporator at given conditions [kg/kg]
   12167         843 :     Real64 OutletAirTemp(0.0);     // Outlet dry-bulb temperature from evaporator at given conditions [C]
   12168         843 :     Real64 OutletAirEnthalpy(0.0); // Enthalpy of outlet air at given conditions [J/kg]
   12169         843 :     Real64 OutletAirHumRat(0.0);   // Outlet humidity ratio from evaporator at given conditions [kg/kg]
   12170         843 :     Real64 OutletAirRH(0.0);       // relative humidity of the outlet air
   12171         843 :     Real64 CalcADPTemp(0.0);       // actual ADP temperature based on bypass factor [C]
   12172         843 :     Real64 CalcADPHumRat(0.0);     // actual ADP humidity ratio based on bypass factor [kg/kg]
   12173         843 :     Real64 CalcADPTempFnHR(0.0);   // actual ADP temperature as a function of humidity ratio based on bypass factor [C]
   12174         843 :     Real64 ADPerror(0.0);          // difference between ADP function of temperature and humidity ratio [deltaC]
   12175         843 :     Real64 AirMassFlow(0.0);       // air mass flow rate based on standard barometric pressure [kg/s]
   12176         843 :     bool bStillValidating(true);   // while loop flag
   12177         843 :     bool bNoReporting(false);      // don't report specific warnings in calcCBF while iterating on result
   12178         843 :     bool bReversePerturb(false);   // identifies when SHR is being lowered based on outlet air RH
   12179             : 
   12180         843 :     SHR = InitialSHR;
   12181         843 :     AirMassFlow =
   12182         843 :         AirVolFlowRate * PsyRhoAirFnPbTdbW(state, DataEnvironment::StdPressureSeaLevel, RatedInletAirTemp, RatedInletAirHumRat, CallingRoutine);
   12183       25706 :     while (bStillValidating) {
   12184       24863 :         CBF_calculated = max(0.0, CalcCBF(state, UnitType, UnitName, RatedInletAirTemp, RatedInletAirHumRat, TotCap, AirMassFlow, SHR, bNoReporting));
   12185       24863 :         DeltaH = TotCap / AirMassFlow;
   12186       24863 :         InletAirEnthalpy = PsyHFnTdbW(RatedInletAirTemp, RatedInletAirHumRat);
   12187       24863 :         HTinHumRatOut = InletAirEnthalpy - (1.0 - SHR) * DeltaH;
   12188       24863 :         OutletAirHumRat = PsyWFnTdbH(state, RatedInletAirTemp, HTinHumRatOut, CallingRoutine);
   12189       24863 :         DeltaHumRat = RatedInletAirHumRat - OutletAirHumRat;
   12190       24863 :         OutletAirEnthalpy = InletAirEnthalpy - DeltaH;
   12191       24863 :         OutletAirTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
   12192       24863 :         OutletAirRH = PsyRhFnTdbWPb(state, OutletAirTemp, OutletAirHumRat, DataEnvironment::StdPressureSeaLevel, CallingRoutine);
   12193       24863 :         if (CBF_calculated < 1) {
   12194       24863 :             CalcADPTemp = RatedInletAirTemp - ((RatedInletAirTemp - OutletAirTemp) / (1 - CBF_calculated));
   12195       24863 :             CalcADPHumRat = RatedInletAirHumRat - ((DeltaHumRat) / (1 - CBF_calculated));
   12196       24863 :             CalcADPTempFnHR = PsyTdpFnWPb(state, CalcADPHumRat, DataEnvironment::StdPressureSeaLevel, CallingRoutine);
   12197       24863 :             ADPerror = CalcADPTemp - CalcADPTempFnHR;
   12198             :         } else {
   12199           0 :             ADPerror = 0; // might be able to check for RH >= 1 and reduce SHR, need defect file for that since can't create one
   12200             :         }
   12201             : 
   12202       24863 :         if (std::abs(ADPerror) > 0.012) {
   12203       24863 :             if (OutletAirRH >= 1.0) { // if RH > 1, reduce SHR until it crosses the saturation curve
   12204         606 :                 SHR -= 0.001;
   12205         606 :                 bReversePerturb = true;
   12206         606 :                 if (SHR < 0.5)
   12207           0 :                     bStillValidating = false; // have to stop somewhere, this is lower than the lower limit of SHR empirical model (see
   12208             :                                               // Autosizing/CoolingSHRSizing)
   12209             :             } else {
   12210       24257 :                 if (bReversePerturb) {
   12211         602 :                     bStillValidating = false; // stop iterating once SHR causes ADP to cross back under saturation curve, take what you get
   12212             :                 } else {
   12213       23655 :                     SHR += 0.001; // increase SHR slowly until ADP temps are resolved
   12214             :                 }
   12215             :             }
   12216       24863 :             if (SHR > 0.8)
   12217         241 :                 bStillValidating = false; // have to stop somewhere, this is the upper limit of SHR empirical model (see Autosizing/CoolingSHRSizing)
   12218             :         } else {
   12219           0 :             bStillValidating = false; // ADP temps are close enough. Normal input files hit this on first pass
   12220             :         }
   12221             :     }
   12222             : 
   12223         843 :     return SHR;
   12224             : }
   12225             : 
   12226     8188828 : Real64 CalcEffectiveSHR(EnergyPlusData &state,
   12227             :                         int const DXCoilNum,                         // Index number for cooling coil
   12228             :                         Real64 const SHRss,                          // Steady-state sensible heat ratio
   12229             :                         Real64 const RTF,                            // Compressor run-time fraction
   12230             :                         Real64 const QLatRated,                      // Rated latent capacity
   12231             :                         Real64 const QLatActual,                     // Actual latent capacity
   12232             :                         Real64 const EnteringDB,                     // Entering air dry-bulb temperature
   12233             :                         Real64 const EnteringWB,                     // Entering air wet-bulb temperature
   12234             :                         ObjexxFCL::Optional_int_const Mode,          // Performance mode for MultiMode DX coil; Always 1 for other coil types
   12235             :                         ObjexxFCL::Optional<Real64 const> HeatingRTF // Used to recalculate Toff for cycling fan systems
   12236             : )
   12237             : {
   12238             : 
   12239             :     // FUNCTION INFORMATION:
   12240             :     //    AUTHOR         Richard Raustad, FSEC
   12241             :     //    DATE WRITTEN   September 2003
   12242             :     //                   Feb 2005 M. J. Witte, GARD Analytics, Inc.
   12243             :     //                    Add new coil type COIL:DX:MultiMode:CoolingEmpirical:
   12244             :     //                   Nov 2008 R. Raustad, FSEC
   12245             :     //                    Modified to allow latent degradation with cycling fan
   12246             : 
   12247             :     // PURPOSE OF THIS FUNCTION:
   12248             :     //    Adjust sensible heat ratio to account for degradation of DX coil latent
   12249             :     //    capacity at part-load (cycling) conditions.
   12250             : 
   12251             :     // METHODOLOGY EMPLOYED:
   12252             :     //    With model parameters entered by the user, the part-load latent performance
   12253             :     //    of a DX cooling coil is determined for a constant air flow system with
   12254             :     //    a cooling coil that cycles on/off. The model calculates the time
   12255             :     //    required for condensate to begin falling from the cooling coil.
   12256             :     //    Runtimes greater than this are integrated to a "part-load" latent
   12257             :     //    capacity which is used to determine the "part-load" sensible heat ratio.
   12258             :     //    See reference below for additional details (linear decay model, Eq. 8b).
   12259             :     // REFERENCES:
   12260             :     //   "A Model to Predict the Latent Capacity of Air Conditioners and
   12261             :     //    Heat Pumps at Part-Load Conditions with Constant Fan Operation"
   12262             :     //    1996 ASHRAE Transactions, Volume 102, Part 1, Pp. 266 - 274,
   12263             :     //    Hugh I. Henderson, Jr., P.E., Kannan Rengarajan, P.E.
   12264             : 
   12265             :     // Return value
   12266             :     Real64 SHReff; // Effective sensible heat ratio, includes degradation due to cycling effects
   12267             : 
   12268             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   12269             :     Real64 Twet; // Nominal time for condensate to begin leaving the coil's condensate drain line
   12270             :     //   at the current operating conditions (sec)
   12271             :     Real64 Gamma; // Initial moisture evaporation rate divided by steady-state AC latent capacity
   12272             :     //   at the current operating conditions
   12273             :     Real64 Twet_Rated;  // Twet at rated conditions (coil air flow rate and air temperatures), sec
   12274             :     Real64 Gamma_Rated; // Gamma at rated conditions (coil air flow rate and air temperatures)
   12275             :     Real64 Twet_max;    // Maximum allowed value for Twet
   12276             :     Real64 Nmax;        // Maximum ON/OFF cycles per hour for the compressor (cycles/hr)
   12277             :     Real64 Tcl;         // Time constant for latent capacity to reach steady state after startup (sec)
   12278             :     Real64 Ton;         // Coil on time (sec)
   12279             :     Real64 Toff;        // Coil off time (sec)
   12280             :     Real64 Toffa;       // Actual coil off time (sec). Equations valid for Toff <= (2.0 * Twet/Gamma)
   12281             :     Real64 aa;          // Intermediate variable
   12282             :     Real64 To1;         // Intermediate variable (first guess at To). To = time to the start of moisture removal
   12283             :     Real64 To2;         // Intermediate variable (second guess at To). To = time to the start of moisture removal
   12284             :     Real64 Error;       // Error for iteration (DO) loop
   12285             :     Real64 LHRmult;     // Latent Heat Ratio (LHR) multiplier. The effective latent heat ratio LHR = (1-SHRss)*LHRmult
   12286             :     Real64 Ton_heating;
   12287             :     Real64 Toff_heating;
   12288             : 
   12289     8188828 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   12290             : 
   12291     8188828 :     if (thisDXCoil.DXCoilType_Num != HVAC::CoilDX_MultiSpeedCooling) {
   12292     7839950 :         Twet_Rated = thisDXCoil.Twet_Rated(Mode);
   12293     7839950 :         Gamma_Rated = thisDXCoil.Gamma_Rated(Mode);
   12294     7839950 :         Nmax = thisDXCoil.MaxONOFFCyclesperHour(Mode);
   12295     7839950 :         Tcl = thisDXCoil.LatentCapacityTimeConstant(Mode);
   12296             :     } else {
   12297      348878 :         Twet_Rated = thisDXCoil.MSTwet_Rated(Mode);
   12298      348878 :         Gamma_Rated = thisDXCoil.MSGamma_Rated(Mode);
   12299      348878 :         Nmax = thisDXCoil.MSMaxONOFFCyclesperHour(Mode);
   12300      348878 :         Tcl = thisDXCoil.MSLatentCapacityTimeConstant(Mode);
   12301             :     }
   12302             : 
   12303             :     //  No moisture evaporation (latent degradation) occurs for runtime fraction of 1.0
   12304             :     //  All latent degradation model parameters cause divide by 0.0 if not greater than 0.0
   12305             :     //  Latent degradation model parameters initialize to 0.0 meaning no evaporation model used.
   12306     8188828 :     if (RTF >= 1.0 || Twet_Rated <= 0.0 || Gamma_Rated <= 0.0 || Nmax <= 0.0 || Tcl <= 0.0) {
   12307     7271442 :         SHReff = SHRss;
   12308     7271442 :         return SHReff;
   12309             :     }
   12310             : 
   12311      917386 :     Twet_max = 9999.0; // high limit for Twet
   12312             : 
   12313             :     //  Calculate the model parameters at the actual operating conditions
   12314      917386 :     Twet = min(Twet_Rated * QLatRated / (QLatActual + 1.e-10), Twet_max);
   12315      917386 :     Gamma = Gamma_Rated * QLatRated * (EnteringDB - EnteringWB) / ((26.7 - 19.4) * QLatActual + 1.e-10);
   12316             : 
   12317             :     //  Calculate the compressor on and off times using a converntional thermostat curve
   12318      917386 :     Ton = 3600.0 / (4.0 * Nmax * (1.0 - RTF)); // duration of cooling coil on-cycle (sec)
   12319      917386 :     Toff = 3600.0 / (4.0 * Nmax * RTF);        // duration of cooling coil off-cycle (sec)
   12320             : 
   12321             :     //  Cap Toff to meet the equation restriction
   12322      917386 :     if (Gamma > 0.0) {
   12323      917386 :         Toffa = min(Toff, 2.0 * Twet / Gamma);
   12324             :     } else {
   12325           0 :         Toffa = Toff;
   12326             :     }
   12327             : 
   12328             :     //  Need to include the reheat coil operation to account for actual fan run time. E+ uses a
   12329             :     //  separate heating coil for heating and reheat (to separate the heating and reheat loads)
   12330             :     //  and real world applications would use a single heating coil for both purposes, the actual
   12331             :     //  fan operation is based on HeatingPLR + ReheatPLR. For cycling fan RH control, latent
   12332             :     //  degradation only occurs when a heating load exists, in this case the reheat load is
   12333             :     //  equal to and oposite in magnitude to the cooling coil sensible output but the reheat
   12334             :     //  coil is not always active. This additional fan run time has not been accounted for at this time.
   12335             :     //  Recalculate Toff for cycling fan systems when heating is active
   12336      917386 :     if (present(HeatingRTF)) {
   12337           0 :         if (HeatingRTF < 1.0 && HeatingRTF > RTF) {
   12338           0 :             Ton_heating = 3600.0 / (4.0 * Nmax * (1.0 - HeatingRTF));
   12339           0 :             Toff_heating = 3600.0 / (4.0 * Nmax * HeatingRTF);
   12340             :             //    add additional heating coil operation during cooling coil off cycle (due to cycling rate difference of coils)
   12341           0 :             Ton_heating += max(0.0, min(Ton_heating, (Ton + Toffa) - (Ton_heating + Toff_heating)));
   12342           0 :             Toffa = min(Toffa, Ton_heating - Ton);
   12343             :         }
   12344             :     }
   12345             : 
   12346             :     //  Use sucessive substitution to solve for To
   12347      917386 :     aa = (Gamma * Toffa) - (0.25 / Twet) * pow_2(Gamma) * pow_2(Toffa);
   12348      917386 :     To1 = aa + Tcl;
   12349      917386 :     Error = 1.0;
   12350     1903934 :     while (Error > 0.001) {
   12351      986548 :         To2 = aa - Tcl * (std::exp(-To1 / Tcl) - 1.0);
   12352      986548 :         Error = std::abs((To2 - To1) / To1);
   12353      986548 :         To1 = To2;
   12354             :     }
   12355             : 
   12356             :     //  Adjust Sensible Heat Ratio (SHR) using Latent Heat Ratio (LHR) multiplier
   12357             :     //  Floating underflow errors occur when -Ton/Tcl is a large negative number.
   12358             :     //  Cap lower limit at -700 to avoid the underflow errors.
   12359      917386 :     aa = std::exp(max(-700.0, -Ton / Tcl));
   12360             :     //  Calculate latent heat ratio multiplier
   12361      917386 :     LHRmult = max(((Ton - To2) / (Ton + Tcl * (aa - 1.0))), 0.0);
   12362             : 
   12363             :     //  Calculate part-load or "effective" sensible heat ratio
   12364      917386 :     SHReff = 1.0 - (1.0 - SHRss) * LHRmult;
   12365             : 
   12366      917386 :     if (SHReff < SHRss) SHReff = SHRss; // Effective SHR can be less than the steady-state SHR
   12367      917386 :     if (SHReff > 1.0) SHReff = 1.0;     // Effective sensible heat ratio can't be greater than 1.0
   12368             : 
   12369      917386 :     return SHReff;
   12370             : }
   12371             : 
   12372     8635964 : void CalcTotCapSHR(EnergyPlusData &state,
   12373             :                    Real64 const InletDryBulb,     // inlet air dry bulb temperature [C]
   12374             :                    Real64 const InletHumRat,      // inlet air humidity ratio [kg water / kg dry air]
   12375             :                    Real64 const InletEnthalpy,    // inlet air specific enthalpy [J/kg]
   12376             :                    Real64 const InletWetBulb,     // inlet air wet bulb temperature [C]
   12377             :                    Real64 const AirMassFlowRatio, // Ratio of actual air mass flow to nominal air mass flow
   12378             :                    Real64 const AirMassFlow,      // actual mass flow for capacity and SHR calculation
   12379             :                    Real64 const TotCapNom,        // nominal total capacity [W]
   12380             :                    Real64 const CBF,              // coil bypass factor
   12381             :                    int const CCapFTemp,           // capacity modifier curve index, function of entering wetbulb
   12382             :                    int const CCapFFlow,           // capacity modifier curve, function of actual flow vs rated flow
   12383             :                    Real64 &TotCap,                // total capacity at the given conditions [W]
   12384             :                    Real64 &SHR,                   // sensible heat ratio at the given conditions
   12385             :                    Real64 const CondInletTemp,    // Condenser inlet temperature [C]
   12386             :                    Real64 const Pressure,         // air pressure [Pa]
   12387             :                    Real64 &TotCapModFac           // capacity modification factor, func of temp and func of flow
   12388             : )
   12389             : {
   12390             : 
   12391             :     // SUBROUTINE INFORMATION:
   12392             :     //       AUTHOR         Fred Buhl using Don Shirey's code
   12393             :     //       DATE WRITTEN   September 2002
   12394             : 
   12395             :     // PURPOSE OF THIS SUBROUTINE:
   12396             :     // Calculates total capacity and sensible heat ratio of a DX coil at the specified conditions
   12397             : 
   12398             :     // METHODOLOGY EMPLOYED:
   12399             :     // With the rated performance data entered by the user, the model employs some of the
   12400             :     // DOE-2.1E curve fits to adjust the capacity and SHR of the unit as a function
   12401             :     // of entering air temperatures and supply air flow rate (actual vs rated flow). The model
   12402             :     // does NOT employ the exact same methodology to calculate performance as DOE-2, although
   12403             :     // some of the DOE-2 curve fits are employed by this model.
   12404             : 
   12405             :     // The model checks for coil dryout conditions, and adjusts the calculated performance
   12406             :     // appropriately.
   12407             : 
   12408             :     // REFERENCES:
   12409             :     // ASHRAE HVAC 2 Toolkit page 4-81.
   12410             :     // Henderson, H.I. Jr., K. Rengarajan and D.B. Shirey, III. 1992.The impact of comfort
   12411             :     // control on air conditioner energy use in humid climates. ASHRAE Transactions 98(2):
   12412             :     // 104-113.
   12413             :     // Henderson, H.I. Jr., Danny Parker and Y.J. Huang. 2000.Improving DOE-2's RESYS routine:
   12414             :     // User Defined Functions to Provide More Accurate Part Load Energy Use and Humidity
   12415             :     // Predictions. Proceedings of ACEEE Conference.
   12416             : 
   12417             :     // Using/Aliasing
   12418             :     using Curve::CurveValue;
   12419             : 
   12420             :     // Locals
   12421             :     // SUBROUTINE ARGUMENT DEFINITIONS:
   12422             :     // and outside drybulb
   12423             : 
   12424             :     // SUBROUTINE PARAMETER DEFINITIONS:
   12425     8635964 :     constexpr int MaxIter(30);               // Maximum number of iterations for dry evaporator calculations
   12426     8635964 :     constexpr Real64 RF(0.4);                // Relaxation factor for dry evaporator iterations
   12427     8635964 :     constexpr Real64 Tolerance(0.01);        // Error tolerance for dry evaporator iterations
   12428     8635964 :     constexpr Real64 MinHumRatCalc(0.00001); // Error tolerance for dry evaporator iterations
   12429             : 
   12430             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   12431             :     Real64 InletWetBulbCalc; // calculated inlet wetbulb temperature used for finding dry coil point [C]
   12432             :     Real64 InletHumRatCalc;  // calculated inlet humidity ratio used for finding dry coil point [kg water / kg dry air]
   12433             :     Real64 TotCapTempModFac; // Total capacity modifier (function of entering wetbulb, outside drybulb)
   12434             :     Real64 TotCapFlowModFac; // Total capacity modifier (function of actual supply air flow vs nominal flow)
   12435             :     Real64 hDelta;           // Change in air enthalpy across the cooling coil [J/kg]
   12436             :     Real64 hADP;             // Apparatus dew point enthalpy [J/kg]
   12437             :     Real64 tADP;             // Apparatus dew point temperature [C]
   12438             :     Real64 wADP;             // Apparatus dew point humidity ratio [kg/kg]
   12439             :     Real64 hTinwADP;         // Enthalpy at inlet dry-bulb and wADP [J/kg]
   12440             :     Real64 SHRCalc;          // temporary calculated value of SHR
   12441             :     Real64 TotCapCalc;       // temporary calculated value of total capacity [W]
   12442             :     int Counter;             // Counter for dry evaporator iterations
   12443             :     Real64 werror;           // Deviation of humidity ratio in dry evaporator iteration loop
   12444             : 
   12445             :     //  MaxIter = 30
   12446             :     //  RF = 0.4d0
   12447     8635964 :     Counter = 0;
   12448             :     //  Tolerance = 0.01d0
   12449     8635964 :     werror = 0.0;
   12450             : 
   12451     8635964 :     InletWetBulbCalc = InletWetBulb;
   12452     8635964 :     InletHumRatCalc = InletHumRat;
   12453             : 
   12454     8635964 :     if (AirMassFlow <= 0.00001) {
   12455          61 :         TotCap = 0.0;
   12456          61 :         SHR = 0.0;
   12457          61 :         return;
   12458             :     }
   12459             : 
   12460             :     //  DO WHILE (ABS(werror) .gt. Tolerance .OR. Counter == 0)
   12461             :     //   Get capacity modifying factor (function of inlet wetbulb & outside drybulb) for off-rated conditions
   12462             :     while (true) {
   12463    13245937 :         TotCapTempModFac = CurveValue(state, CCapFTemp, InletWetBulbCalc, CondInletTemp);
   12464             :         //   Get capacity modifying factor (function of mass flow) for off-rated conditions
   12465    13245937 :         TotCapFlowModFac = CurveValue(state, CCapFFlow, AirMassFlowRatio);
   12466             :         //   Get total capacity
   12467    13245937 :         TotCapCalc = TotCapNom * TotCapFlowModFac * TotCapTempModFac;
   12468             : 
   12469             :         //   Calculate apparatus dew point conditions using TotCap and CBF
   12470    13245937 :         hDelta = TotCapCalc / AirMassFlow;
   12471    13245937 :         hADP = InletEnthalpy - hDelta / (1.0 - CBF);
   12472    13245937 :         tADP = PsyTsatFnHPb(state, hADP, Pressure);
   12473    13245937 :         wADP = PsyWFnTdbH(state, tADP, hADP);
   12474    13245937 :         hTinwADP = PsyHFnTdbW(InletDryBulb, wADP);
   12475    13245937 :         if ((InletEnthalpy - hADP) > 1.e-10) {
   12476    13245937 :             SHRCalc = min((hTinwADP - hADP) / (InletEnthalpy - hADP), 1.0);
   12477             :         } else {
   12478           0 :             SHRCalc = 1.0;
   12479             :         }
   12480             :         //   Check for dry evaporator conditions (win < wadp)
   12481    13245937 :         if (wADP > InletHumRatCalc || (Counter >= 1 && Counter < MaxIter)) {
   12482     5806652 :             if (InletHumRatCalc == 0.0) InletHumRatCalc = MinHumRatCalc;
   12483             :             //      InletHumRatCalc=MAX(InletHumRatCalc,MinHumRatCalc)  ! proposed.
   12484             : 
   12485     5806652 :             werror = (InletHumRatCalc - wADP) / InletHumRatCalc;
   12486             :             //     Increase InletHumRatCalc at constant inlet air temp to find coil dry-out point. Then use the
   12487             :             //     capacity at the dry-out point to determine exiting conditions from coil. This is required
   12488             :             //     since the TotCapTempModFac doesn't work properly with dry-coil conditions.
   12489     5806652 :             InletHumRatCalc = RF * wADP + (1.0 - RF) * InletHumRatCalc;
   12490     5806652 :             InletWetBulbCalc = PsyTwbFnTdbWPb(state, InletDryBulb, InletHumRatCalc, Pressure);
   12491     5806652 :             ++Counter;
   12492     5806652 :             if (std::abs(werror) > Tolerance) continue; // Recalculate with modified inlet conditions
   12493     1196618 :             break;                                      // conditions are satisfied
   12494             :         } else {
   12495             :             break; // conditions are satisfied
   12496             :         }
   12497             :     }
   12498             : 
   12499             :     // END DO
   12500             : 
   12501             :     //  Calculate full load output conditions
   12502     8635903 :     if (SHRCalc > 1.0 || Counter > 0) SHRCalc = 1.0;
   12503             : 
   12504     8635903 :     SHR = SHRCalc;
   12505     8635903 :     TotCap = TotCapCalc;
   12506     8635903 :     TotCapModFac = TotCapTempModFac * TotCapFlowModFac;
   12507             : }
   12508             : 
   12509     6868538 : void CalcMultiSpeedDXCoilCooling(EnergyPlusData &state,
   12510             :                                  int const DXCoilNum,     // the number of the DX heating coil to be simulated
   12511             :                                  Real64 const SpeedRatio, // = (CompressorSpeed - CompressorSpeedMin) / (CompressorSpeedMax - CompressorSpeedMin)
   12512             :                                  Real64 const CycRatio,   // cycling part load ratio
   12513             :                                  int const SpeedNum,      // Speed number
   12514             :                                  HVAC::FanOp const fanOp, // Sets fan control to FanOp::Cycling or FanOp::Continuous
   12515             :                                  HVAC::CompressorOp const compressorOp, // Compressor on/off; 1=on, 0=off
   12516             :                                  int const SingleMode                   // Single mode operation Yes/No; 1=Yes, 0=No
   12517             : )
   12518             : {
   12519             : 
   12520             :     // SUBROUTINE INFORMATION:
   12521             :     //       AUTHOR         Lixing Gu, FSEC
   12522             :     //       DATE WRITTEN   June 2007
   12523             :     //       MODIFIED       April 2010, Chandan sharma, FSEC, added basin heater
   12524             :     //       RE-ENGINEERED  Revised based on CalcMultiSpeedDXCoil
   12525             : 
   12526             :     // PURPOSE OF THIS SUBROUTINE:
   12527             :     // Calculates the air-side performance and electrical energy use of a direct-
   12528             :     // expansion, air-cooled cooling unit with a multispeed compressor.
   12529             : 
   12530             :     // METHODOLOGY EMPLOYED:
   12531             :     // Uses the same methodology as the single speed DX unit model (SUBROUTINE CalcDoe2DXCoil).
   12532             :     // In addition it assumes that the unit performance is obtained by interpolating between
   12533             :     // the performance at high speed and that at low speed. If the output needed is below
   12534             :     // that produced at low speed, the compressor cycles between off and low speed.
   12535             : 
   12536             :     // Using/Aliasing
   12537             :     using Curve::CurveValue;
   12538     6868538 :     Real64 MSHPMassFlowRateHigh = state.dataHVACGlobal->MSHPMassFlowRateHigh;
   12539     6868538 :     Real64 MSHPMassFlowRateLow = state.dataHVACGlobal->MSHPMassFlowRateLow;
   12540     6868538 :     auto &MSHPWasteHeat = state.dataHVACGlobal->MSHPWasteHeat;
   12541             : 
   12542             :     // Locals
   12543             :     // SUBROUTINE ARGUMENT DEFINITIONS:
   12544             :     // SpeedRatio varies between 1.0 (maximum speed) and 0.0 (minimum speed)
   12545             : 
   12546             :     // SUBROUTINE PARAMETER DEFINITIONS:
   12547             :     static constexpr std::string_view RoutineName("CalcMultiSpeedDXCoilCooling");
   12548             :     static constexpr std::string_view RoutineNameHighSpeedAlt("CalcMultiSpeedDXCoilCooling highspeed");
   12549             : 
   12550             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   12551             :     Real64 AirMassFlow;         // dry air mass flow rate through coil [kg/s]
   12552             :     Real64 InletAirWetBulbC;    // wetbulb temperature of inlet air [C]
   12553             :     Real64 InletAirDryBulbTemp; // inlet air dry bulb temperature [C]
   12554             :     Real64 InletAirEnthalpy;    // inlet air enthalpy [J/kg]
   12555             :     Real64 InletAirHumRat;      // inlet air humidity ratio [kg/kg]
   12556             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   12557             :     // REAL(r64)   :: InletAirPressure    ! inlet air pressure [Pa]
   12558             :     Real64 OutletAirDryBulbTemp;    // outlet air dry bulb temperature [C]
   12559             :     Real64 OutletAirEnthalpy;       // outlet air enthalpy [J/kg]
   12560             :     Real64 OutletAirHumRat;         // outlet air humidity ratio [kg/kg]
   12561             :     Real64 OutletAirDryBulbTempSat; // outlet air dry bulb temp at saturation at the outlet enthalpy [C]
   12562             :     Real64 LSOutletAirDryBulbTemp;  // low speed outlet air dry bulb temperature [C]
   12563             :     Real64 LSOutletAirEnthalpy;     // low speed outlet air enthalpy [J/kg]
   12564             :     Real64 LSOutletAirHumRat;       // low speed outlet air humidity ratio [kg/kg]
   12565             :     Real64 HSOutletAirDryBulbTemp;  // hihg speed outlet air dry bulb temperature [C]
   12566             :     Real64 HSOutletAirEnthalpy;     // high speed outlet air enthalpy [J/kg]
   12567             :     Real64 HSOutletAirHumRat;       // high speed outlet air humidity ratio [kg/kg]
   12568             :     Real64 hDelta;                  // Change in air enthalpy across the cooling coil [J/kg]
   12569             :     Real64 hTinwout;                // Enthalpy at inlet dry-bulb and outlet humidity ratio [J/kg]
   12570             :     Real64 hADP;                    // Apparatus dew point enthalpy [J/kg]
   12571             :     Real64 tADP;                    // Apparatus dew point temperature [C]
   12572             :     Real64 wADP;                    // Apparatus dew point humidity ratio [kg/kg]
   12573             :     Real64 hTinwADP;                // Enthalpy at inlet dry-bulb and wADP [J/kg]
   12574             :     Real64 RatedCBFHS;              // coil bypass factor at rated conditions (high speed)
   12575             :     Real64 CBFHS;                   // coil bypass factor at max flow (high speed)
   12576             :     Real64 RatedCBFLS;              // coil bypass factor at rated conditions (low speed)
   12577             :     Real64 CBFLS;                   // coil bypass factor at max flow (low speed)
   12578             :     Real64 TotCapHS;                // total capacity at high speed [W]
   12579             :     Real64 SHRHS;                   // sensible heat ratio at high speed
   12580             :     Real64 TotCapLS;                // total capacity at low speed [W]
   12581             :     Real64 SHRLS;                   // sensible heat ratio at low speed
   12582             :     Real64 EIRTempModFacHS;         // EIR modifier (function of entering wetbulb, outside drybulb) (high speed)
   12583             :     Real64 EIRFlowModFacHS;         // EIR modifier (function of actual supply air flow vs rated flow) (high speed)
   12584             :     Real64 EIRHS;                   // EIR at off rated conditions (high speed)
   12585             :     Real64 EIRTempModFacLS;         // EIR modifier (function of entering wetbulb, outside drybulb) (low speed)
   12586             :     Real64 EIRFlowModFacLS;         // EIR modifier (function of actual supply air flow vs rated flow) (low speed)
   12587             :     Real64 EIRLS;                   // EIR at off rated conditions (low speed)
   12588             :     Real64 SHR;                     // sensible heat ratio at current speed
   12589             :     Real64 EIR;                     // EIR at current speed
   12590             :     Real64 CBF;                     // CBFNom adjusted for actual air mass flow rate
   12591             :     Real64 PLF;                     // Part load factor, accounts for thermal lag at compressor startup, used in
   12592             :     // power calculation
   12593             :     Real64 CondInletTemp; // Condenser inlet temperature (C). Outdoor dry-bulb temp for air-cooled condenser.
   12594             :     // Outdoor Wetbulb +(1 - effectiveness)*(outdoor drybulb - outdoor wetbulb) for evap condenser.
   12595             :     Real64 CondInletHumRat; // Condenser inlet humidity ratio (kg/kg). Zero for air-cooled condenser.
   12596             :     // For evap condenser, its the humidity ratio of the air leaving the evap cooling pads.
   12597             :     Real64 RhoAir;                // Density of air [kg/m3]
   12598             :     Real64 RhoWater;              // Density of water [kg/m3]
   12599             :     Real64 CondAirMassFlow;       // Condenser air mass flow rate [kg/s]
   12600             :     Real64 EvapCondPumpElecPower; // Evaporative condenser electric pump power [W]
   12601     6868538 :     constexpr int DXMode(1);      // Performance mode for MultiMode DX coil; Always 1 for other coil types
   12602             :     Real64 OutdoorDryBulb;        // Outdoor dry-bulb temperature at condenser (C)
   12603             :     Real64 OutdoorWetBulb;        // Outdoor wet-bulb temperature at condenser (C)
   12604             :     Real64 OutdoorHumRat;         // Outdoor humidity ratio at condenser (kg/kg)
   12605             :     Real64 OutdoorPressure;       // Outdoor barometric pressure at condenser (Pa)
   12606             :     int SpeedNumHS;               // High speed number
   12607             :     int SpeedNumLS;               // Low speed number
   12608             :     Real64 SHRUnadjusted;         // Temp SHR
   12609             :     Real64 QLatRated;             // Qlatent at rated conditions of indoor(TDB,TWB)=(26.7C,19.4C)
   12610             :     Real64 QLatActual;            // Qlatent at actual operating conditions
   12611             :     Real64 AirMassFlowRatioLS;    // airflow ratio at low speed
   12612             :     Real64 AirMassFlowRatioHS;    // airflow ratio at high speed
   12613             :     Real64 WasteHeatLS;           // Waste heat at low speed
   12614             :     Real64 WasteHeatHS;           // Waste heat at high speed
   12615             :     Real64 LSElecCoolingPower;    // low speed power [W]
   12616             :     Real64 HSElecCoolingPower;    // high speed power [W]
   12617             :     Real64 CrankcaseHeatingPower; // Power due to crank case heater
   12618             :     Real64 AirVolumeFlowRate;     // Air volume flow rate across the heating coil
   12619             :     Real64 VolFlowperRatedTotCap; // Air volume flow rate divided by rated total heating capacity
   12620             : 
   12621     6868538 :     auto &DXCT = state.dataHVACGlobal->DXCT;
   12622             : 
   12623     6868538 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   12624             : 
   12625     6868538 :     if (thisDXCoil.CondenserInletNodeNum(DXMode) != 0) {
   12626     3430422 :         OutdoorPressure = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(DXMode)).Press;
   12627             :         // If node is not connected to anything, pressure = default, use weather data
   12628     3430422 :         if (OutdoorPressure == state.dataLoopNodes->DefaultNodeValues.Press) {
   12629           0 :             OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   12630           0 :             OutdoorHumRat = state.dataEnvrn->OutHumRat;
   12631           0 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
   12632           0 :             OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   12633             :         } else {
   12634     3430422 :             OutdoorDryBulb = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(DXMode)).Temp;
   12635     3430422 :             OutdoorHumRat = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(DXMode)).HumRat;
   12636     3430422 :             OutdoorWetBulb = PsyTwbFnTdbWPb(state, OutdoorDryBulb, OutdoorHumRat, OutdoorPressure, RoutineName);
   12637             :         }
   12638     3430422 :         if (thisDXCoil.IsSecondaryDXCoilInZone) {
   12639           0 :             auto &secZoneHB = state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr);
   12640           0 :             OutdoorDryBulb = secZoneHB.ZT;
   12641           0 :             OutdoorHumRat = secZoneHB.airHumRat;
   12642           0 :             OutdoorWetBulb = thisDXCoil.EvapInletWetBulb;
   12643           0 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
   12644             :         }
   12645     3438116 :     } else if (thisDXCoil.IsSecondaryDXCoilInZone) {
   12646           0 :         auto &secZoneHB = state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr);
   12647           0 :         OutdoorDryBulb = secZoneHB.ZT;
   12648           0 :         OutdoorHumRat = secZoneHB.airHumRat;
   12649           0 :         OutdoorWetBulb = thisDXCoil.EvapInletWetBulb;
   12650           0 :         OutdoorPressure = state.dataEnvrn->OutBaroPress;
   12651             :     } else {
   12652     3438116 :         OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   12653     3438116 :         OutdoorHumRat = state.dataEnvrn->OutHumRat;
   12654     3438116 :         OutdoorPressure = state.dataEnvrn->OutBaroPress;
   12655     3438116 :         OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   12656             :     }
   12657             : 
   12658     6868538 :     if (SpeedNum > 1) {
   12659     1809618 :         SpeedNumLS = SpeedNum - 1;
   12660     1809618 :         SpeedNumHS = SpeedNum;
   12661     1809618 :         if (SpeedNum > thisDXCoil.NumOfSpeeds) {
   12662           0 :             SpeedNumLS = thisDXCoil.NumOfSpeeds - 1;
   12663           0 :             SpeedNumHS = thisDXCoil.NumOfSpeeds;
   12664             :         }
   12665             :     } else {
   12666     5058920 :         SpeedNumLS = 1;
   12667     5058920 :         SpeedNumHS = 1;
   12668             :     }
   12669             : 
   12670     6868538 :     MSHPWasteHeat = 0.0;
   12671     6868538 :     AirMassFlow = thisDXCoil.InletAirMassFlowRate;
   12672     6868538 :     AirMassFlowRatioLS = MSHPMassFlowRateLow / thisDXCoil.MSRatedAirMassFlowRate(SpeedNumLS);
   12673     6868538 :     AirMassFlowRatioHS = MSHPMassFlowRateHigh / thisDXCoil.MSRatedAirMassFlowRate(SpeedNumHS);
   12674     6868538 :     if ((AirMassFlow > 0.0) && (CycRatio > 0.0) && (MSHPMassFlowRateHigh == 0.0)) {
   12675           0 :         ShowSevereError(
   12676             :             state,
   12677           0 :             format("CalcMultiSpeedDXCoilCooling: {} \"{} Developer error - inconsistent airflow rates.", thisDXCoil.DXCoilType, thisDXCoil.Name));
   12678           0 :         if (MSHPMassFlowRateLow == 0.0 && SpeedNum > 1) {
   12679           0 :             ShowContinueError(state,
   12680             :                               "When AirMassFlow > 0.0 and CycRatio > 0.0 and SpeedNum > 1, then MSHPMassFlowRateLow and MSHPMassFlowRateHigh "
   12681             :                               "must also be > 0.0");
   12682           0 :             ShowContinueErrorTimeStamp(state, "");
   12683           0 :             ShowContinueError(state,
   12684           0 :                               format("AirMassFlow={:.3R},CycRatio={:.3R},SpeedNum={:.0R}, MSHPMassFlowRateLow={:.3R}, MSHPMassFlowRateHigh={:.3R}",
   12685             :                                      AirMassFlow,
   12686           0 :                                      double(SpeedNum),
   12687             :                                      CycRatio,
   12688             :                                      MSHPMassFlowRateLow,
   12689             :                                      MSHPMassFlowRateHigh));
   12690           0 :             ShowFatalError(state, "Preceding condition(s) causes termination.");
   12691             :         } else {
   12692           0 :             ShowContinueError(state, "When AirMassFlow > 0.0 and CycRatio > 0.0, then MSHPMassFlowRateHigh must also be > 0.0");
   12693           0 :             ShowContinueErrorTimeStamp(state, "");
   12694           0 :             ShowContinueError(state,
   12695           0 :                               format("AirMassFlow={:.3R},CycRatio={:.3R}, MSHPMassFlowRateHigh={:.3R}", AirMassFlow, CycRatio, MSHPMassFlowRateHigh));
   12696           0 :             ShowFatalError(state, "Preceding condition(s) causes termination.");
   12697             :         }
   12698     6868538 :     } else if (CycRatio > 1.0 || SpeedRatio > 1.0) {
   12699           0 :         ShowSevereError(
   12700             :             state,
   12701           0 :             format("CalcMultiSpeedDXCoilCooling: {} \"{} Developer error - inconsistent speed ratios.", thisDXCoil.DXCoilType, thisDXCoil.Name));
   12702           0 :         ShowContinueError(state, "CycRatio and SpeedRatio must be between 0.0 and 1.0");
   12703           0 :         ShowContinueErrorTimeStamp(state, "");
   12704           0 :         ShowContinueError(state, format("CycRatio={:.1R}, SpeedRatio = {:.1R}", CycRatio, SpeedRatio));
   12705           0 :         ShowFatalError(state, "Preceding condition(s) causes termination.");
   12706             :     }
   12707             : 
   12708     6868538 :     thisDXCoil.PartLoadRatio = 0.0;
   12709     6868538 :     state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).AvailCapacity = 0.0;
   12710     6868538 :     thisDXCoil.CoolingCoilRuntimeFraction = 0.0;
   12711     6868538 :     InletAirDryBulbTemp = thisDXCoil.InletAirTemp;
   12712     6868538 :     InletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   12713     6868538 :     InletAirHumRat = thisDXCoil.InletAirHumRat;
   12714             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   12715             :     // InletAirPressure = DXCoil(DXCoilNum)%InletAirPressure
   12716             :     // InletAirWetBulbC = PsyTwbFnTdbWPb(InletAirDryBulbTemp,InletAirHumRat,InletAirPressure)
   12717     6868538 :     InletAirWetBulbC = PsyTwbFnTdbWPb(state, InletAirDryBulbTemp, InletAirHumRat, OutdoorPressure, RoutineName);
   12718     6868538 :     if (thisDXCoil.CondenserType(DXMode) == DataHeatBalance::RefrigCondenserType::Air) {
   12719     6868538 :         CondInletTemp = OutdoorDryBulb; // Outdoor dry-bulb temp
   12720           0 :     } else if (thisDXCoil.CondenserType(DXMode) == DataHeatBalance::RefrigCondenserType::Evap) {
   12721             :         // Outdoor wet-bulb temp from DataEnvironment + (1.0-EvapCondEffectiveness) * (drybulb - wetbulb)
   12722           0 :         CondInletTemp = OutdoorWetBulb + (OutdoorDryBulb - OutdoorWetBulb) * (1.0 - thisDXCoil.MSEvapCondEffect(SpeedNumHS));
   12723           0 :         CondInletHumRat = PsyWFnTdbTwbPb(state, CondInletTemp, OutdoorWetBulb, OutdoorPressure, RoutineName);
   12724             :     }
   12725     6868538 :     if (OutdoorDryBulb < thisDXCoil.MaxOATCrankcaseHeater) {
   12726     3430633 :         CrankcaseHeatingPower = thisDXCoil.CrankcaseHeaterCapacity;
   12727     3430633 :         if (thisDXCoil.CrankcaseHeaterCapacityCurveIndex > 0) {
   12728           0 :             CrankcaseHeatingPower *= Curve::CurveValue(state, thisDXCoil.CrankcaseHeaterCapacityCurveIndex, OutdoorDryBulb);
   12729             :         }
   12730             :     } else {
   12731     3437905 :         CrankcaseHeatingPower = 0.0;
   12732             :     }
   12733             : 
   12734     5796844 :     if ((AirMassFlow > 0.0 && CondInletTemp >= thisDXCoil.MinOATCompressor) && (GetCurrentScheduleValue(state, thisDXCoil.SchedPtr) > 0.0) &&
   12735    12665382 :         ((SpeedRatio > 0.0 && SingleMode == 0) || CycRatio > 0.0) && (compressorOp == HVAC::CompressorOp::On)) {
   12736             : 
   12737     2104426 :         RhoAir = PsyRhoAirFnPbTdbW(state, OutdoorPressure, OutdoorDryBulb, OutdoorHumRat, RoutineName);
   12738     2104426 :         if (SpeedNum > 1 && SingleMode == 0) {
   12739             : 
   12740             :             // Check for valid air volume flow per rated total cooling capacity (200 - 500 cfm/ton) at low speed
   12741     1269233 :             AirVolumeFlowRate = MSHPMassFlowRateLow / PsyRhoAirFnPbTdbW(state, OutdoorPressure, InletAirDryBulbTemp, InletAirHumRat, RoutineName);
   12742             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   12743             :             //  AirVolumeFlowRate = AirMassFlow/PsyRhoAirFnPbTdbW(InletAirPressure,InletAirDryBulbTemp, InletAirHumRat)
   12744     1269233 :             VolFlowperRatedTotCap = AirVolumeFlowRate / thisDXCoil.MSRatedTotCap(SpeedNumLS);
   12745     1269233 :             if (((VolFlowperRatedTotCap < HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) ||
   12746     1759167 :                  (VolFlowperRatedTotCap > HVAC::MaxCoolVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT])) &&
   12747      489934 :                 state.dataHVACGlobal->MSUSEconoSpeedNum == 0) {
   12748      489934 :                 if (thisDXCoil.MSErrIndex(SpeedNumLS) == 0) {
   12749          64 :                     ShowWarningMessage(
   12750             :                         state,
   12751          64 :                         format("{} \"{}\" - Air volume flow rate per watt of rated total cooling capacity is out of range at speed {}.",
   12752          32 :                                thisDXCoil.DXCoilType,
   12753          32 :                                thisDXCoil.Name,
   12754             :                                SpeedNumLS));
   12755          32 :                     ShowContinueErrorTimeStamp(state, "");
   12756          64 :                     ShowContinueError(state,
   12757          64 :                                       format("Expected range for VolumeFlowPerRatedTotalCapacity=[{:.3R}--{:.3R}] Current value is {:.3R} m3/s/W",
   12758          32 :                                              HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   12759          32 :                                              HVAC::MaxCoolVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   12760             :                                              VolFlowperRatedTotCap));
   12761          32 :                     ShowContinueError(state, "Possible causes include inconsistent air flow rates in system components or");
   12762          32 :                     ShowContinueError(state, "inconsistent supply air fan operation modes in coil and unitary system objects.");
   12763             :                 }
   12764     1469802 :                 ShowRecurringWarningErrorAtEnd(state,
   12765      979868 :                                                format("{} \"{}\" - Air volume flow rate per watt of rated total cooling capacity is out of range "
   12766             :                                                       "at speed {} error continues...",
   12767      489934 :                                                       thisDXCoil.DXCoilType,
   12768      489934 :                                                       thisDXCoil.Name,
   12769             :                                                       SpeedNumLS),
   12770             :                                                thisDXCoil.MSErrIndex(SpeedNumLS),
   12771             :                                                VolFlowperRatedTotCap,
   12772             :                                                VolFlowperRatedTotCap);
   12773             :             }
   12774             : 
   12775             :             // Check for valid air volume flow per rated total cooling capacity (200 - 500 cfm/ton) at high speed
   12776     1269233 :             AirVolumeFlowRate = MSHPMassFlowRateHigh / PsyRhoAirFnPbTdbW(state, OutdoorPressure, InletAirDryBulbTemp, InletAirHumRat, RoutineName);
   12777             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   12778             :             //  AirVolumeFlowRate = AirMassFlow/PsyRhoAirFnPbTdbW(InletAirPressure,InletAirDryBulbTemp, InletAirHumRat)
   12779     1269233 :             VolFlowperRatedTotCap = AirVolumeFlowRate / thisDXCoil.MSRatedTotCap(SpeedNumHS);
   12780     1269233 :             if (((VolFlowperRatedTotCap < HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) ||
   12781     1390534 :                  (VolFlowperRatedTotCap > HVAC::MaxCoolVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT])) &&
   12782      121301 :                 state.dataHVACGlobal->MSUSEconoSpeedNum == 0) {
   12783      121301 :                 if (thisDXCoil.MSErrIndex(SpeedNumHS) == 0) {
   12784          32 :                     ShowWarningMessage(
   12785             :                         state,
   12786          32 :                         format("{} \"{}\" - Air volume flow rate per watt of rated total cooling capacity is out of range at speed {}.",
   12787          16 :                                thisDXCoil.DXCoilType,
   12788          16 :                                thisDXCoil.Name,
   12789             :                                SpeedNumHS));
   12790          16 :                     ShowContinueErrorTimeStamp(state, "");
   12791          32 :                     ShowContinueError(state,
   12792          32 :                                       format("Expected range for VolumeFlowPerRatedTotalCapacity=[{:.3R}--{:.3R}] Current value is {:.3R} m3/s/W",
   12793          16 :                                              HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   12794          16 :                                              HVAC::MaxCoolVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   12795             :                                              VolFlowperRatedTotCap));
   12796          16 :                     ShowContinueError(state, "Possible causes include inconsistent air flow rates in system components or");
   12797          16 :                     ShowContinueError(state, "inconsistent supply air fan operation modes in coil and unitary system objects.");
   12798             :                 }
   12799      363903 :                 ShowRecurringWarningErrorAtEnd(state,
   12800      242602 :                                                format("{} \"{}\" - Air volume flow rate per watt of rated total cooling capacity is out of range "
   12801             :                                                       "at speed {} error continues...",
   12802      121301 :                                                       thisDXCoil.DXCoilType,
   12803      121301 :                                                       thisDXCoil.Name,
   12804             :                                                       SpeedNumHS),
   12805             :                                                thisDXCoil.MSErrIndex(SpeedNumHS),
   12806             :                                                VolFlowperRatedTotCap,
   12807             :                                                VolFlowperRatedTotCap);
   12808             :             }
   12809             : 
   12810             :             // Adjust high speed coil bypass factor for actual maximum air flow rate.
   12811     1269233 :             RatedCBFHS = thisDXCoil.MSRatedCBF(SpeedNumHS);
   12812     1269233 :             CBFHS = AdjustCBF(RatedCBFHS, thisDXCoil.MSRatedAirMassFlowRate(SpeedNumHS), MSHPMassFlowRateHigh);
   12813     1269233 :             RatedCBFLS = thisDXCoil.MSRatedCBF(SpeedNumLS);
   12814     1269233 :             CBFLS = AdjustCBF(RatedCBFLS, thisDXCoil.MSRatedAirMassFlowRate(SpeedNumLS), MSHPMassFlowRateLow);
   12815             :             // get low speed total capacity and SHR at current conditions
   12816     3807699 :             CalcTotCapSHR(state,
   12817             :                           InletAirDryBulbTemp,
   12818             :                           InletAirHumRat,
   12819             :                           InletAirEnthalpy,
   12820             :                           InletAirWetBulbC,
   12821             :                           AirMassFlowRatioLS,
   12822             :                           MSHPMassFlowRateLow,
   12823     1269233 :                           thisDXCoil.MSRatedTotCap(SpeedNumLS),
   12824             :                           CBFLS,
   12825     1269233 :                           thisDXCoil.MSCCapFTemp(SpeedNumLS),
   12826     1269233 :                           thisDXCoil.MSCCapFFlow(SpeedNumLS),
   12827             :                           TotCapLS,
   12828             :                           SHRLS,
   12829             :                           CondInletTemp,
   12830             :                           OutdoorPressure,
   12831     1269233 :                           thisDXCoil.capModFacTotal);
   12832             :             // get low speed outlet conditions
   12833     1269233 :             hDelta = TotCapLS / MSHPMassFlowRateLow;
   12834             :             // Calculate new apparatus dew point conditions
   12835     1269233 :             hADP = InletAirEnthalpy - hDelta / (1.0 - CBFLS);
   12836     1269233 :             tADP = PsyTsatFnHPb(state, hADP, OutdoorPressure, RoutineNameHighSpeedAlt);
   12837             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   12838             :             //  tADP = PsyTsatFnHPb(hADP,InletAirPressure)
   12839     1269233 :             wADP = PsyWFnTdbH(state, tADP, hADP, RoutineName);
   12840     1269233 :             hTinwADP = PsyHFnTdbW(InletAirDryBulbTemp, wADP);
   12841             :             // get corresponding SHR
   12842     1269233 :             if ((InletAirEnthalpy - hADP) > 1.e-10) {
   12843     1269233 :                 SHRLS = min((hTinwADP - hADP) / (InletAirEnthalpy - hADP), 1.0);
   12844             :             } else {
   12845           0 :                 SHRLS = 1.0;
   12846             :             }
   12847             :             // cr8918    SHRLS = MIN((hTinwADP-hADP)/(InletAirEnthalpy-hADP),1.0d0)
   12848             :             // get low speed outlet conditions
   12849     1269233 :             LSOutletAirEnthalpy = InletAirEnthalpy - hDelta;
   12850     1269233 :             hTinwout = InletAirEnthalpy - (1.0 - SHRLS) * hDelta;
   12851     1269233 :             LSOutletAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout, RoutineName);
   12852     1269233 :             LSOutletAirDryBulbTemp = PsyTdbFnHW(LSOutletAirEnthalpy, LSOutletAirHumRat);
   12853     1269233 :             OutletAirDryBulbTempSat = PsyTsatFnHPb(state, LSOutletAirEnthalpy, OutdoorPressure, RoutineName);
   12854     1269233 :             if (LSOutletAirDryBulbTemp < OutletAirDryBulbTempSat) { // Limit to saturated conditions at OutletAirEnthalpy
   12855         630 :                 LSOutletAirDryBulbTemp = OutletAirDryBulbTempSat;
   12856         630 :                 LSOutletAirHumRat = PsyWFnTdbH(state, LSOutletAirDryBulbTemp, LSOutletAirEnthalpy, RoutineName);
   12857             :             }
   12858             : 
   12859             :             // get high speed total capacity and SHR at current conditions
   12860             : 
   12861     3807699 :             CalcTotCapSHR(state,
   12862             :                           InletAirDryBulbTemp,
   12863             :                           InletAirHumRat,
   12864             :                           InletAirEnthalpy,
   12865             :                           InletAirWetBulbC,
   12866             :                           AirMassFlowRatioHS,
   12867             :                           MSHPMassFlowRateHigh,
   12868     1269233 :                           thisDXCoil.MSRatedTotCap(SpeedNumHS),
   12869             :                           CBFHS,
   12870     1269233 :                           thisDXCoil.MSCCapFTemp(SpeedNumHS),
   12871     1269233 :                           thisDXCoil.MSCCapFFlow(SpeedNumHS),
   12872             :                           TotCapHS,
   12873             :                           SHRHS,
   12874             :                           CondInletTemp,
   12875             :                           OutdoorPressure,
   12876     1269233 :                           thisDXCoil.capModFacTotal);
   12877     1269233 :             hDelta = TotCapHS / MSHPMassFlowRateHigh;
   12878             :             // Calculate new apparatus dew point conditions
   12879     1269233 :             hADP = InletAirEnthalpy - hDelta / (1.0 - CBFHS);
   12880     1269233 :             tADP = PsyTsatFnHPb(state, hADP, OutdoorPressure, RoutineName);
   12881             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   12882             :             //  tADP = PsyTsatFnHPb(hADP,InletAirPressure)
   12883     1269233 :             wADP = PsyWFnTdbH(state, tADP, hADP, RoutineName);
   12884     1269233 :             hTinwADP = PsyHFnTdbW(InletAirDryBulbTemp, wADP);
   12885             :             // get corresponding SHR
   12886     1269233 :             if ((InletAirEnthalpy - hADP) > 1.e-10) {
   12887     1269233 :                 SHRHS = min((hTinwADP - hADP) / (InletAirEnthalpy - hADP), 1.0);
   12888             :             } else {
   12889           0 :                 SHRHS = 1.0;
   12890             :             }
   12891             :             // cr8918    SHRHS = MIN((hTinwADP-hADP)/(InletAirEnthalpy-hADP),1.0d0)
   12892             :             // get the part load factor that will account for cycling losses
   12893     1269233 :             PLF = CurveValue(state, thisDXCoil.MSPLFFPLR(SpeedNumHS), SpeedRatio);
   12894     1269233 :             if (PLF < 0.7) {
   12895           0 :                 PLF = 0.7;
   12896             :             }
   12897             :             // calculate the run time fraction
   12898     1269233 :             thisDXCoil.CoolingCoilRuntimeFraction = SpeedRatio / PLF;
   12899     1269233 :             thisDXCoil.PartLoadRatio = SpeedRatio;
   12900             : 
   12901     1269233 :             if (thisDXCoil.CoolingCoilRuntimeFraction > 1.0) {
   12902           0 :                 thisDXCoil.CoolingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   12903             :             }
   12904             : 
   12905             :             // get high speed outlet conditions
   12906     1269233 :             HSOutletAirEnthalpy = InletAirEnthalpy - hDelta;
   12907     1269233 :             hTinwout = InletAirEnthalpy - (1.0 - SHRHS) * hDelta;
   12908     1269233 :             HSOutletAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout, RoutineName);
   12909     1269233 :             HSOutletAirDryBulbTemp = PsyTdbFnHW(HSOutletAirEnthalpy, HSOutletAirHumRat);
   12910     1269233 :             OutletAirDryBulbTempSat = PsyTsatFnHPb(state, HSOutletAirEnthalpy, OutdoorPressure, RoutineName);
   12911     1269233 :             if (HSOutletAirDryBulbTemp < OutletAirDryBulbTempSat) { // Limit to saturated conditions at OutletAirEnthalpy
   12912         634 :                 HSOutletAirDryBulbTemp = OutletAirDryBulbTempSat;
   12913         634 :                 HSOutletAirHumRat = PsyWFnTdbH(state, HSOutletAirDryBulbTemp, HSOutletAirEnthalpy, RoutineName);
   12914             :             }
   12915             : 
   12916             :             //  If constant fan with cycling compressor, call function to determine "effective SHR"
   12917             :             //  which includes the part-load degradation on latent capacity
   12918     1269233 :             if (thisDXCoil.LatentImpact && fanOp == HVAC::FanOp::Continuous && SpeedRatio > 0.0) {
   12919           0 :                 QLatRated = thisDXCoil.MSRatedTotCap(SpeedNumHS) * (1.0 - thisDXCoil.MSRatedSHR(SpeedNumHS));
   12920           0 :                 QLatActual = TotCapHS * (1.0 - SHRHS);
   12921           0 :                 SHRUnadjusted = SHRHS;
   12922           0 :                 SHR = CalcEffectiveSHR(state,
   12923             :                                        DXCoilNum,
   12924             :                                        SHRHS,
   12925             :                                        thisDXCoil.CoolingCoilRuntimeFraction,
   12926             :                                        QLatRated,
   12927             :                                        QLatActual,
   12928             :                                        InletAirDryBulbTemp,
   12929             :                                        InletAirWetBulbC,
   12930             :                                        SpeedNumHS);
   12931             :                 // Calculate full load output conditions
   12932           0 :                 if (SHR > 1.0) SHR = 1.0;
   12933           0 :                 hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
   12934           0 :                 if (SHR < 1.0) {
   12935           0 :                     HSOutletAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout, RoutineName);
   12936             :                 } else {
   12937           0 :                     HSOutletAirHumRat = InletAirHumRat;
   12938             :                 }
   12939           0 :                 HSOutletAirDryBulbTemp = PsyTdbFnHW(HSOutletAirEnthalpy, HSOutletAirHumRat);
   12940             :             }
   12941             : 
   12942             :             // get high speed EIR at current conditions
   12943     1269233 :             EIRTempModFacHS = CurveValue(state, thisDXCoil.MSEIRFTemp(SpeedNumHS), InletAirWetBulbC, CondInletTemp);
   12944     1269233 :             EIRFlowModFacHS = CurveValue(state, thisDXCoil.MSEIRFFlow(SpeedNumHS), AirMassFlowRatioHS);
   12945     1269233 :             EIRHS = 1.0 / thisDXCoil.MSRatedCOP(SpeedNumHS) * EIRFlowModFacHS * EIRTempModFacHS;
   12946             :             // get low speed EIR at current conditions
   12947     1269233 :             EIRTempModFacLS = CurveValue(state, thisDXCoil.MSEIRFTemp(SpeedNumLS), InletAirWetBulbC, CondInletTemp);
   12948     1269233 :             EIRFlowModFacLS = CurveValue(state, thisDXCoil.MSEIRFFlow(SpeedNumLS), AirMassFlowRatioLS);
   12949     1269233 :             EIRLS = 1.0 / thisDXCoil.MSRatedCOP(SpeedNumLS) * EIRTempModFacLS * EIRFlowModFacLS;
   12950             : 
   12951             :             // get current total capacity, SHR, EIR
   12952     1269233 :             if (SpeedRatio >= 1.0) {
   12953      702041 :                 SHR = SHRHS;
   12954      702041 :                 EIR = EIRHS;
   12955      702041 :                 CondAirMassFlow = RhoAir * thisDXCoil.MSEvapCondAirFlow(SpeedNumHS);
   12956      702041 :                 EvapCondPumpElecPower = thisDXCoil.MSEvapCondPumpElecNomPower(SpeedNumHS);
   12957             :             } else {
   12958      567192 :                 EIR = SpeedRatio * EIRHS + (1.0 - SpeedRatio) * EIRLS;
   12959      567192 :                 SHR = SpeedRatio * SHRHS + (1.0 - SpeedRatio) * SHRLS;
   12960      567192 :                 CondAirMassFlow =
   12961      567192 :                     RhoAir * (SpeedRatio * thisDXCoil.MSEvapCondAirFlow(SpeedNumHS) + (1.0 - SpeedRatio) * thisDXCoil.MSEvapCondAirFlow(SpeedNumLS));
   12962      567192 :                 EvapCondPumpElecPower = SpeedRatio * thisDXCoil.MSEvapCondPumpElecNomPower(SpeedNumHS) +
   12963      567192 :                                         (1.0 - SpeedRatio) * thisDXCoil.MSEvapCondPumpElecNomPower(SpeedNumLS);
   12964             :             }
   12965             : 
   12966             :             // Outlet calculation
   12967     1269233 :             Real64 SensibleOutputLS(0.0); // low speed sensible output rate
   12968     1269233 :             Real64 LatentOutputLS(0.0);   // low speed latent output rate
   12969     1269233 :             Real64 TotalOutputLS(0.0);    // low speed total output rate
   12970     1269233 :             Real64 SensibleOutputHS(0.0); // high speed sensible output rate
   12971     1269233 :             Real64 LatentOutputHS(0.0);   // high speed latent output rate
   12972     1269233 :             Real64 TotalOutputHS(0.0);    // high speed total output rate
   12973     1269233 :             CalcComponentSensibleLatentOutput(MSHPMassFlowRateLow,
   12974             :                                               InletAirDryBulbTemp,
   12975             :                                               InletAirHumRat,
   12976             :                                               LSOutletAirDryBulbTemp,
   12977             :                                               LSOutletAirHumRat,
   12978             :                                               SensibleOutputLS,
   12979             :                                               LatentOutputLS,
   12980             :                                               TotalOutputLS);
   12981     1269233 :             CalcComponentSensibleLatentOutput(MSHPMassFlowRateHigh,
   12982             :                                               InletAirDryBulbTemp,
   12983             :                                               InletAirHumRat,
   12984             :                                               HSOutletAirDryBulbTemp,
   12985             :                                               HSOutletAirHumRat,
   12986             :                                               SensibleOutputHS,
   12987             :                                               LatentOutputHS,
   12988             :                                               TotalOutputHS);
   12989     1269233 :             thisDXCoil.TotalCoolingEnergyRate = TotalOutputHS * SpeedRatio + TotalOutputLS * (1.0 - SpeedRatio);
   12990     1269233 :             thisDXCoil.SensCoolingEnergyRate = SensibleOutputHS * SpeedRatio + SensibleOutputLS * (1.0 - SpeedRatio);
   12991     1269233 :             thisDXCoil.LatCoolingEnergyRate = LatentOutputHS * SpeedRatio + LatentOutputLS * (1.0 - SpeedRatio);
   12992             :             // Average outlet enthalpy
   12993     1269233 :             OutletAirEnthalpy = InletAirEnthalpy - thisDXCoil.TotalCoolingEnergyRate / thisDXCoil.InletAirMassFlowRate;
   12994             : 
   12995     1269233 :             if (fanOp == HVAC::FanOp::Cycling) state.dataHVACGlobal->OnOffFanPartLoadFraction = 1.0;
   12996             :             // Update outlet conditions
   12997     1269233 :             if (SpeedRatio == 0.0 && fanOp == HVAC::FanOp::Cycling) {
   12998        6743 :                 OutletAirEnthalpy = LSOutletAirEnthalpy;
   12999        6743 :                 OutletAirHumRat = LSOutletAirHumRat;
   13000        6743 :                 OutletAirDryBulbTemp = LSOutletAirDryBulbTemp;
   13001     1262490 :             } else if (SpeedRatio >= 1.0 && fanOp == HVAC::FanOp::Cycling) {
   13002      152102 :                 OutletAirEnthalpy = HSOutletAirEnthalpy;
   13003      152102 :                 OutletAirHumRat = HSOutletAirHumRat;
   13004      152102 :                 OutletAirDryBulbTemp = HSOutletAirDryBulbTemp;
   13005             :             } else {
   13006     1110388 :                 OutletAirHumRat =
   13007     1110388 :                     ((HSOutletAirHumRat * SpeedRatio * MSHPMassFlowRateHigh) + (LSOutletAirHumRat * (1.0 - SpeedRatio) * MSHPMassFlowRateLow)) /
   13008     1110388 :                     thisDXCoil.InletAirMassFlowRate;
   13009     1110388 :                 OutletAirDryBulbTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
   13010     1110388 :                 if (OutletAirDryBulbTemp < OutletAirDryBulbTempSat) { // Limit to saturated conditions at OutletAirEnthalpy
   13011        9005 :                     OutletAirDryBulbTemp = OutletAirDryBulbTempSat;
   13012        9005 :                     OutletAirHumRat = PsyWFnTdbH(state, OutletAirDryBulbTemp, OutletAirEnthalpy, RoutineName);
   13013        9005 :                     CalcComponentSensibleLatentOutput(AirMassFlow,
   13014             :                                                       InletAirDryBulbTemp,
   13015             :                                                       InletAirHumRat,
   13016             :                                                       OutletAirDryBulbTemp,
   13017             :                                                       OutletAirHumRat,
   13018        9005 :                                                       thisDXCoil.SensCoolingEnergyRate,
   13019        9005 :                                                       thisDXCoil.LatCoolingEnergyRate,
   13020        9005 :                                                       thisDXCoil.TotalCoolingEnergyRate);
   13021             :                 }
   13022             :             }
   13023             : 
   13024     1269233 :             LSElecCoolingPower = TotCapLS * EIRLS;
   13025     1269233 :             HSElecCoolingPower = TotCapHS * EIRHS;
   13026             : 
   13027             :             // Power calculation
   13028     1269233 :             if (!thisDXCoil.PLRImpact) {
   13029     1269233 :                 thisDXCoil.ElecCoolingPower = SpeedRatio * HSElecCoolingPower + (1.0 - SpeedRatio) * LSElecCoolingPower;
   13030             :             } else {
   13031           0 :                 thisDXCoil.ElecCoolingPower =
   13032           0 :                     thisDXCoil.CoolingCoilRuntimeFraction * HSElecCoolingPower + (1.0 - thisDXCoil.CoolingCoilRuntimeFraction) * LSElecCoolingPower;
   13033             :             }
   13034             :             // Now reset runtime fraction to 1.0 (because LS is running the full timestep)
   13035     1269233 :             thisDXCoil.CoolingCoilRuntimeFraction = 1.0;
   13036             : 
   13037             :             //   Calculation for heat reclaim needs to be corrected to use compressor power (not including condenser fan power)
   13038     1269233 :             state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).AvailCapacity = thisDXCoil.TotalCoolingEnergyRate + thisDXCoil.ElecCoolingPower;
   13039             : 
   13040             :             // Waste heat calculation
   13041             :             // TODO: waste heat not considered even if defined in Cooling:DX:MultiSpeed, N16, \field Speed 1 Rated Waste Heat Fraction of
   13042             :             // Power Input
   13043     1269233 :             if (thisDXCoil.FuelType != Constant::eFuel::Electricity) {
   13044      317468 :                 if (thisDXCoil.MSWasteHeat(SpeedNumLS) == 0) {
   13045           0 :                     WasteHeatLS = thisDXCoil.MSWasteHeatFrac(SpeedNumLS);
   13046             :                 } else {
   13047      317468 :                     WasteHeatLS = CurveValue(state, thisDXCoil.MSWasteHeat(SpeedNumLS), OutdoorDryBulb, InletAirDryBulbTemp) *
   13048      317468 :                                   thisDXCoil.MSWasteHeatFrac(SpeedNumLS);
   13049             :                 }
   13050      317468 :                 if (thisDXCoil.MSWasteHeat(SpeedNumHS) == 0) {
   13051           0 :                     WasteHeatHS = thisDXCoil.MSWasteHeatFrac(SpeedNumHS);
   13052             :                 } else {
   13053      317468 :                     WasteHeatHS = CurveValue(state, thisDXCoil.MSWasteHeat(SpeedNumHS), OutdoorDryBulb, InletAirDryBulbTemp) *
   13054      317468 :                                   thisDXCoil.MSWasteHeatFrac(SpeedNumHS);
   13055             :                 }
   13056      317468 :                 thisDXCoil.MSFuelWasteHeat = (SpeedRatio * WasteHeatHS + (1.0 - SpeedRatio) * WasteHeatLS) * thisDXCoil.ElecCoolingPower;
   13057      317468 :                 if (thisDXCoil.MSHPHeatRecActive) {
   13058           0 :                     MSHPWasteHeat = thisDXCoil.MSFuelWasteHeat;
   13059             :                 }
   13060             :             }
   13061             : 
   13062             :             // Energy use for other fuel types
   13063     1269233 :             if (thisDXCoil.FuelType != Constant::eFuel::Electricity) {
   13064      317468 :                 thisDXCoil.FuelUsed = thisDXCoil.ElecCoolingPower;
   13065      317468 :                 thisDXCoil.ElecCoolingPower = 0.0;
   13066             :             }
   13067             : 
   13068     1269233 :             thisDXCoil.OutletAirEnthalpy = OutletAirEnthalpy;
   13069     1269233 :             thisDXCoil.OutletAirHumRat = OutletAirHumRat;
   13070     1269233 :             thisDXCoil.OutletAirTemp = OutletAirDryBulbTemp;
   13071     1269233 :             thisDXCoil.CrankcaseHeaterPower = 0.0;
   13072             : 
   13073     2104426 :         } else if (CycRatio > 0.0) {
   13074             : 
   13075      835193 :             if (fanOp == HVAC::FanOp::Cycling) AirMassFlow /= CycRatio;
   13076      835193 :             if (fanOp == HVAC::FanOp::Continuous) AirMassFlow = MSHPMassFlowRateHigh;
   13077             : 
   13078             :             // Check for valid air volume flow per rated total cooling capacity (200 - 500 cfm/ton) at low speed
   13079      835193 :             AirVolumeFlowRate = MSHPMassFlowRateHigh / PsyRhoAirFnPbTdbW(state, OutdoorPressure, InletAirDryBulbTemp, InletAirHumRat, RoutineName);
   13080             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   13081             :             //  AirVolumeFlowRate = AirMassFlow/PsyRhoAirFnPbTdbW(InletAirPressure,InletAirDryBulbTemp, InletAirHumRat)
   13082      835193 :             VolFlowperRatedTotCap = AirVolumeFlowRate / thisDXCoil.MSRatedTotCap(SpeedNum);
   13083      835193 :             if (((VolFlowperRatedTotCap < HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) ||
   13084     1158066 :                  (VolFlowperRatedTotCap > HVAC::MaxCoolVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT])) &&
   13085      322873 :                 state.dataHVACGlobal->MSUSEconoSpeedNum == 0) {
   13086      310293 :                 if (thisDXCoil.MSErrIndex(SpeedNum) == 0) {
   13087           2 :                     ShowWarningMessage(
   13088             :                         state,
   13089           2 :                         format("{} \"{}\" - Air volume flow rate per watt of rated total cooling capacity is out of range at speed {}.",
   13090           1 :                                thisDXCoil.DXCoilType,
   13091           1 :                                thisDXCoil.Name,
   13092             :                                SpeedNum));
   13093           1 :                     ShowContinueErrorTimeStamp(state, "");
   13094           2 :                     ShowContinueError(state,
   13095           2 :                                       format("Expected range for VolumeFlowPerRatedTotalCapacity=[{:.3R}--{:.3R}] Current value is {:.3R} m3/s/W",
   13096           1 :                                              HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   13097           1 :                                              HVAC::MaxCoolVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   13098             :                                              VolFlowperRatedTotCap));
   13099           1 :                     ShowContinueError(state, "Possible causes include inconsistent air flow rates in system components or");
   13100           1 :                     ShowContinueError(state, "inconsistent supply air fan operation modes in coil and unitary system objects.");
   13101             :                 }
   13102      930879 :                 ShowRecurringWarningErrorAtEnd(state,
   13103      620586 :                                                format("{} \"{}\" - Air volume flow rate per watt of rated total cooling capacity is out of range "
   13104             :                                                       "at speed {} error continues...",
   13105      310293 :                                                       thisDXCoil.DXCoilType,
   13106      310293 :                                                       thisDXCoil.Name,
   13107             :                                                       SpeedNumHS),
   13108             :                                                thisDXCoil.MSErrIndex(SpeedNumHS),
   13109             :                                                VolFlowperRatedTotCap,
   13110             :                                                VolFlowperRatedTotCap);
   13111             :             }
   13112             : 
   13113      835193 :             if (thisDXCoil.CondenserType(SpeedNum) == DataHeatBalance::RefrigCondenserType::Evap) {
   13114             :                 // Outdoor wet-bulb temp from DataEnvironment + (1.0-EvapCondEffectiveness) * (drybulb - wetbulb)
   13115           0 :                 CondInletTemp = OutdoorWetBulb + (OutdoorDryBulb - OutdoorWetBulb) * (1.0 - thisDXCoil.MSEvapCondEffect(SpeedNum));
   13116           0 :                 CondInletHumRat = PsyWFnTdbTwbPb(state, CondInletTemp, OutdoorWetBulb, OutdoorPressure, RoutineName);
   13117             :             }
   13118             : 
   13119      835193 :             RatedCBFLS = thisDXCoil.MSRatedCBF(SpeedNum);
   13120      835193 :             CBFLS = AdjustCBF(RatedCBFLS, thisDXCoil.MSRatedAirMassFlowRate(SpeedNum), MSHPMassFlowRateHigh);
   13121             : 
   13122             :             // Adjust low speed coil bypass factor for actual flow rate.
   13123             :             // CBF = AdjustCBF(DXCoil(DXCoilNum)%RatedCBF2,DXCoil(DXCoilNum)%RatedAirMassFlowRate2,AirMassFlow)
   13124             :             // get low speed total capacity and SHR at current conditions
   13125     2505579 :             CalcTotCapSHR(state,
   13126             :                           InletAirDryBulbTemp,
   13127             :                           InletAirHumRat,
   13128             :                           InletAirEnthalpy,
   13129             :                           InletAirWetBulbC,
   13130             :                           AirMassFlowRatioLS,
   13131             :                           MSHPMassFlowRateHigh,
   13132      835193 :                           thisDXCoil.MSRatedTotCap(SpeedNum),
   13133             :                           CBFLS,
   13134      835193 :                           thisDXCoil.MSCCapFTemp(SpeedNum),
   13135      835193 :                           thisDXCoil.MSCCapFFlow(SpeedNum),
   13136             :                           TotCapLS,
   13137             :                           SHRLS,
   13138             :                           CondInletTemp,
   13139             :                           OutdoorPressure,
   13140      835193 :                           thisDXCoil.capModFacTotal);
   13141             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   13142             :             //  Node(DXCoil(DXCoilNum)%AirInNode)%Press)
   13143      835193 :             hDelta = TotCapLS / AirMassFlow;
   13144             :             // Adjust CBF for off-nominal flow
   13145      835193 :             CBF = AdjustCBF(thisDXCoil.MSRatedCBF(SpeedNum), thisDXCoil.MSRatedAirMassFlowRate(SpeedNum), AirMassFlow);
   13146             :             // Calculate new apparatus dew point conditions
   13147      835193 :             hADP = InletAirEnthalpy - hDelta / (1.0 - CBF);
   13148      835193 :             tADP = PsyTsatFnHPb(state, hADP, OutdoorPressure, RoutineName);
   13149             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   13150             :             //  tADP = PsyTsatFnHPb(hADP,InletAirPressure)
   13151      835193 :             wADP = PsyWFnTdbH(state, tADP, hADP, RoutineName);
   13152      835193 :             hTinwADP = PsyHFnTdbW(InletAirDryBulbTemp, wADP);
   13153             :             // get corresponding SHR
   13154      835193 :             if ((InletAirEnthalpy - hADP) > 1.e-10) {
   13155      835193 :                 SHR = min((hTinwADP - hADP) / (InletAirEnthalpy - hADP), 1.0);
   13156             :             } else {
   13157           0 :                 SHR = 1.0;
   13158             :             }
   13159             :             // cr8918    SHR = MIN((hTinwADP-hADP)/(InletAirEnthalpy-hADP),1.0d0)
   13160             : 
   13161             :             // get the part load factor that will account for cycling losses
   13162      835193 :             PLF = CurveValue(state, thisDXCoil.MSPLFFPLR(SpeedNum), CycRatio);
   13163      835193 :             if (fanOp == HVAC::FanOp::Cycling && CycRatio == 1.0 && PLF != 1.0) {
   13164           0 :                 if (thisDXCoil.PLFErrIndex == 0) {
   13165           0 :                     ShowWarningMessage(state,
   13166           0 :                                        format("The PLF curve value for DX cooling coil {} ={:.2R} for part-load ratio = 1", thisDXCoil.Name, PLF));
   13167           0 :                     ShowContinueError(state, "PLF curve value must be = 1.0 and has been reset to 1.0. Simulation is continuing.");
   13168           0 :                     ShowContinueErrorTimeStamp(state, "");
   13169             :                 }
   13170           0 :                 ShowRecurringWarningErrorAtEnd(
   13171           0 :                     state, thisDXCoil.Name + "\": DX cooling coil PLF curve value <> 1.0 warning continues...", thisDXCoil.PLFErrIndex, PLF, PLF);
   13172           0 :                 PLF = 1.0;
   13173             :             }
   13174             : 
   13175      835193 :             if (PLF < 0.7) {
   13176           0 :                 PLF = 0.7;
   13177             :             }
   13178             :             // calculate the run time fraction
   13179      835193 :             thisDXCoil.CoolingCoilRuntimeFraction = CycRatio / PLF;
   13180      835193 :             thisDXCoil.PartLoadRatio = CycRatio;
   13181             : 
   13182      835193 :             if (thisDXCoil.CoolingCoilRuntimeFraction > 1.0) {
   13183           0 :                 thisDXCoil.CoolingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   13184             :             }
   13185             : 
   13186             :             // get low speed outlet conditions
   13187      835193 :             LSOutletAirEnthalpy = InletAirEnthalpy - hDelta;
   13188      835193 :             hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
   13189      835193 :             LSOutletAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout, RoutineName);
   13190      835193 :             LSOutletAirDryBulbTemp = PsyTdbFnHW(LSOutletAirEnthalpy, LSOutletAirHumRat);
   13191      835193 :             OutletAirDryBulbTempSat = PsyTsatFnHPb(state, LSOutletAirEnthalpy, OutdoorPressure, RoutineName);
   13192      835193 :             if (LSOutletAirDryBulbTemp < OutletAirDryBulbTempSat) { // Limit to saturated conditions at OutletAirEnthalpy
   13193         321 :                 LSOutletAirDryBulbTemp = OutletAirDryBulbTempSat;
   13194         321 :                 LSOutletAirHumRat = PsyWFnTdbH(state, LSOutletAirDryBulbTemp, LSOutletAirEnthalpy, RoutineName);
   13195             :             }
   13196             : 
   13197             :             //  If constant fan with cycling compressor, call function to determine "effective SHR"
   13198             :             //  which includes the part-load degradation on latent capacity
   13199      835193 :             if (fanOp == HVAC::FanOp::Continuous) {
   13200      348878 :                 QLatRated = thisDXCoil.MSRatedTotCap(SpeedNum) * (1.0 - thisDXCoil.MSRatedSHR(SpeedNum));
   13201      348878 :                 QLatActual = TotCapLS * (1.0 - SHR);
   13202      348878 :                 SHRUnadjusted = SHR;
   13203      348878 :                 SHR = CalcEffectiveSHR(state,
   13204             :                                        DXCoilNum,
   13205             :                                        SHR,
   13206             :                                        thisDXCoil.CoolingCoilRuntimeFraction,
   13207             :                                        QLatRated,
   13208             :                                        QLatActual,
   13209             :                                        InletAirDryBulbTemp,
   13210             :                                        InletAirWetBulbC,
   13211             :                                        SpeedNum);
   13212             :                 // Calculate full load output conditions
   13213      348878 :                 if (SHR > 1.0) SHR = 1.0;
   13214      348878 :                 hTinwout = InletAirEnthalpy - (1.0 - SHR) * hDelta;
   13215      348878 :                 if (SHR < 1.0) {
   13216      244591 :                     LSOutletAirHumRat = PsyWFnTdbH(state, InletAirDryBulbTemp, hTinwout, RoutineName);
   13217             :                 } else {
   13218      104287 :                     LSOutletAirHumRat = InletAirHumRat;
   13219             :                 }
   13220      348878 :                 LSOutletAirDryBulbTemp = PsyTdbFnHW(LSOutletAirEnthalpy, LSOutletAirHumRat);
   13221             :             }
   13222             : 
   13223      835193 :             if (fanOp == HVAC::FanOp::Cycling) state.dataHVACGlobal->OnOffFanPartLoadFraction = PLF;
   13224      835193 :             if (fanOp == HVAC::FanOp::Continuous) {
   13225             :                 // outlet conditions are average of inlet and low speed weighted by CycRatio
   13226             :                 // Continuous fan, cycling compressor
   13227      348878 :                 Real64 CycAirFlowRatio =
   13228      348878 :                     CycRatio * AirMassFlow / thisDXCoil.InletAirMassFlowRate; // ratio of compressor on airflow to average timestep airflow
   13229      348878 :                 OutletAirEnthalpy = CycAirFlowRatio * LSOutletAirEnthalpy + (1.0 - CycAirFlowRatio) * InletAirEnthalpy;
   13230      348878 :                 OutletAirHumRat = CycAirFlowRatio * LSOutletAirHumRat + (1.0 - CycAirFlowRatio) * InletAirHumRat;
   13231      348878 :                 OutletAirDryBulbTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
   13232             :             } else {
   13233      486315 :                 OutletAirHumRat = LSOutletAirHumRat;
   13234      486315 :                 OutletAirDryBulbTemp = LSOutletAirDryBulbTemp;
   13235      486315 :                 OutletAirEnthalpy = LSOutletAirEnthalpy;
   13236             :             }
   13237             : 
   13238             :             // get low speed EIR at current conditions
   13239      835193 :             EIRTempModFacLS = CurveValue(state, thisDXCoil.MSEIRFTemp(SpeedNum), InletAirWetBulbC, CondInletTemp);
   13240      835193 :             EIRFlowModFacLS = CurveValue(state, thisDXCoil.MSEIRFFlow(SpeedNum), AirMassFlowRatioLS);
   13241      835193 :             EIRLS = 1.0 / thisDXCoil.MSRatedCOP(SpeedNum) * EIRTempModFacLS * EIRFlowModFacLS;
   13242             : 
   13243             :             // get the eletrical power consumption
   13244      835193 :             thisDXCoil.ElecCoolingPower = TotCapLS * EIRLS * thisDXCoil.CoolingCoilRuntimeFraction;
   13245             :             // calculate cooling output power
   13246             :             //    AirMassFlow = DXCoil(DXCoilNum)%InletAirMassFlowRate
   13247      835193 :             CalcComponentSensibleLatentOutput(AirMassFlow,
   13248             :                                               InletAirDryBulbTemp,
   13249             :                                               InletAirHumRat,
   13250             :                                               LSOutletAirDryBulbTemp,
   13251             :                                               LSOutletAirHumRat,
   13252      835193 :                                               thisDXCoil.SensCoolingEnergyRate,
   13253      835193 :                                               thisDXCoil.LatCoolingEnergyRate,
   13254      835193 :                                               thisDXCoil.TotalCoolingEnergyRate);
   13255      835193 :             thisDXCoil.TotalCoolingEnergyRate = thisDXCoil.TotalCoolingEnergyRate * CycRatio;
   13256      835193 :             thisDXCoil.SensCoolingEnergyRate = thisDXCoil.SensCoolingEnergyRate * CycRatio;
   13257      835193 :             thisDXCoil.LatCoolingEnergyRate = thisDXCoil.LatCoolingEnergyRate * CycRatio;
   13258             : 
   13259             :             //   Calculation for heat reclaim needs to be corrected to use compressor power (not including condenser fan power)
   13260      835193 :             state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).AvailCapacity = thisDXCoil.TotalCoolingEnergyRate + thisDXCoil.ElecCoolingPower;
   13261      835193 :             thisDXCoil.OutletAirEnthalpy = OutletAirEnthalpy;
   13262      835193 :             thisDXCoil.OutletAirHumRat = OutletAirHumRat;
   13263      835193 :             thisDXCoil.OutletAirTemp = OutletAirDryBulbTemp;
   13264      835193 :             CondAirMassFlow = RhoAir * thisDXCoil.MSEvapCondAirFlow(SpeedNum) * thisDXCoil.CoolingCoilRuntimeFraction;
   13265      835193 :             EvapCondPumpElecPower = thisDXCoil.MSEvapCondPumpElecNomPower(SpeedNum) * thisDXCoil.CoolingCoilRuntimeFraction;
   13266             : 
   13267             :             // Waste heat
   13268      835193 :             if (thisDXCoil.MSHPHeatRecActive) {
   13269           0 :                 if (thisDXCoil.MSWasteHeat(SpeedNum) == 0) {
   13270           0 :                     thisDXCoil.MSFuelWasteHeat = thisDXCoil.MSWasteHeatFrac(SpeedNum) * thisDXCoil.ElecCoolingPower;
   13271             :                 } else {
   13272           0 :                     thisDXCoil.MSFuelWasteHeat = CurveValue(state, thisDXCoil.MSWasteHeat(SpeedNum), OutdoorDryBulb, InletAirDryBulbTemp) *
   13273           0 :                                                  thisDXCoil.MSWasteHeatFrac(SpeedNum) * thisDXCoil.ElecCoolingPower;
   13274             :                 }
   13275           0 :                 if (thisDXCoil.MSHPHeatRecActive) {
   13276           0 :                     MSHPWasteHeat = thisDXCoil.MSFuelWasteHeat;
   13277             :                 }
   13278             :             }
   13279             :             // Energy use for other fuel types
   13280      835193 :             if (thisDXCoil.FuelType != Constant::eFuel::Electricity) {
   13281       98244 :                 thisDXCoil.FuelUsed = thisDXCoil.ElecCoolingPower;
   13282       98244 :                 thisDXCoil.ElecCoolingPower = 0.0;
   13283             :             }
   13284             : 
   13285      835193 :             if (thisDXCoil.CompanionUpstreamDXCoil == 0) {
   13286      835193 :                 thisDXCoil.CrankcaseHeaterPower = CrankcaseHeatingPower * (1.0 - thisDXCoil.CoolingCoilRuntimeFraction);
   13287             :             } else {
   13288           0 :                 thisDXCoil.CrankcaseHeaterPower =
   13289           0 :                     CrankcaseHeatingPower * (1.0 - max(thisDXCoil.CoolingCoilRuntimeFraction,
   13290           0 :                                                        state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).HeatingCoilRuntimeFraction));
   13291             :             }
   13292             :         }
   13293             : 
   13294     2104426 :         if (thisDXCoil.CondenserType(DXMode) == DataHeatBalance::RefrigCondenserType::Evap) {
   13295             :             //******************
   13296             :             //             WATER CONSUMPTION IN m3 OF WATER FOR DIRECT
   13297             :             //             H2O [m3/s] = Delta W[kgWater/kgDryAir]*Mass Flow Air[kgDryAir/s]
   13298             :             //                                /RhoWater [kgWater/m3]
   13299             :             //******************
   13300           0 :             RhoWater = RhoH2O(OutdoorDryBulb);
   13301           0 :             thisDXCoil.EvapWaterConsumpRate = (CondInletHumRat - OutdoorHumRat) * CondAirMassFlow / RhoWater;
   13302           0 :             thisDXCoil.EvapCondPumpElecPower = EvapCondPumpElecPower;
   13303             :             // set water system demand request (if needed)
   13304           0 :             if (thisDXCoil.EvapWaterSupplyMode == EvapWaterSupply::FromTank) {
   13305           0 :                 state.dataWaterData->WaterStorage(thisDXCoil.EvapWaterSupTankID).VdotRequestDemand(thisDXCoil.EvapWaterTankDemandARRID) =
   13306           0 :                     thisDXCoil.EvapWaterConsumpRate;
   13307             :             }
   13308             : 
   13309             :             // Calculate basin heater power
   13310           0 :             CalcBasinHeaterPower(state,
   13311             :                                  thisDXCoil.BasinHeaterPowerFTempDiff,
   13312             :                                  thisDXCoil.BasinHeaterSchedulePtr,
   13313             :                                  thisDXCoil.BasinHeaterSetPointTemp,
   13314           0 :                                  thisDXCoil.BasinHeaterPower);
   13315           0 :             thisDXCoil.BasinHeaterPower *= (1.0 - thisDXCoil.CoolingCoilRuntimeFraction);
   13316             :         }
   13317             : 
   13318             :     } else {
   13319             : 
   13320             :         // DX coil is off; just pass through conditions
   13321     4764112 :         thisDXCoil.OutletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   13322     4764112 :         thisDXCoil.OutletAirHumRat = thisDXCoil.InletAirHumRat;
   13323     4764112 :         thisDXCoil.OutletAirTemp = thisDXCoil.InletAirTemp;
   13324             : 
   13325     4764112 :         thisDXCoil.FuelUsed = 0.0;
   13326     4764112 :         thisDXCoil.ElecCoolingPower = 0.0;
   13327     4764112 :         thisDXCoil.TotalCoolingEnergyRate = 0.0;
   13328     4764112 :         thisDXCoil.SensCoolingEnergyRate = 0.0;
   13329     4764112 :         thisDXCoil.LatCoolingEnergyRate = 0.0;
   13330     4764112 :         thisDXCoil.EvapCondPumpElecPower = 0.0;
   13331     4764112 :         thisDXCoil.EvapWaterConsumpRate = 0.0;
   13332             : 
   13333     4764112 :         if (thisDXCoil.CompanionUpstreamDXCoil == 0) {
   13334     4764112 :             thisDXCoil.CrankcaseHeaterPower = CrankcaseHeatingPower;
   13335             :         } else {
   13336           0 :             thisDXCoil.CrankcaseHeaterPower =
   13337           0 :                 CrankcaseHeatingPower * (1.0 - state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).HeatingCoilRuntimeFraction);
   13338             :         }
   13339             : 
   13340             :         // Calculate basin heater power
   13341     4764112 :         if (thisDXCoil.CondenserType(DXMode) == DataHeatBalance::RefrigCondenserType::Evap) {
   13342           0 :             CalcBasinHeaterPower(state,
   13343             :                                  thisDXCoil.BasinHeaterPowerFTempDiff,
   13344             :                                  thisDXCoil.BasinHeaterSchedulePtr,
   13345             :                                  thisDXCoil.BasinHeaterSetPointTemp,
   13346           0 :                                  thisDXCoil.BasinHeaterPower);
   13347             :         }
   13348             :     }
   13349             : 
   13350     6868538 :     state.dataDXCoils->DXCoilOutletTemp(DXCoilNum) = thisDXCoil.OutletAirTemp;
   13351     6868538 :     state.dataDXCoils->DXCoilOutletHumRat(DXCoilNum) = thisDXCoil.OutletAirHumRat;
   13352     6868538 :     state.dataDXCoils->DXCoilPartLoadRatio(DXCoilNum) = thisDXCoil.PartLoadRatio;
   13353     6868538 :     state.dataDXCoils->DXCoilFanOp(DXCoilNum) = fanOp;
   13354     6868538 :     thisDXCoil.CondInletTemp = CondInletTemp; // Save condenser inlet temp in the data structure
   13355             : 
   13356             :     // set outlet node conditions
   13357     6868538 :     int airOutletNode = thisDXCoil.AirOutNode;
   13358     6868538 :     state.dataLoopNodes->Node(airOutletNode).Temp = thisDXCoil.OutletAirTemp;
   13359     6868538 :     state.dataLoopNodes->Node(airOutletNode).HumRat = thisDXCoil.OutletAirHumRat;
   13360             : 
   13361             :     // calc secondary coil if specified
   13362     6868538 :     if (thisDXCoil.IsSecondaryDXCoilInZone) {
   13363           0 :         CalcSecondaryDXCoils(state, DXCoilNum);
   13364             :     }
   13365     6868538 : }
   13366             : 
   13367     6858982 : void CalcMultiSpeedDXCoilHeating(EnergyPlusData &state,
   13368             :                                  int const DXCoilNum,     // the number of the DX heating coil to be simulated
   13369             :                                  Real64 const SpeedRatio, // = (CompressorSpeed - CompressorSpeedMin) / (CompressorSpeedMax - CompressorSpeedMin)
   13370             :                                  Real64 const CycRatio,   // cycling part load ratio
   13371             :                                  int const SpeedNum,      // Speed number
   13372             :                                  HVAC::FanOp const fanOp, // Fan operation mode
   13373             :                                  int const SingleMode     // Single mode operation Yes/No; 1=Yes, 0=No
   13374             : )
   13375             : {
   13376             : 
   13377             :     // SUBROUTINE INFORMATION:
   13378             :     //       AUTHOR         Lixing Gu, FSEC
   13379             :     //       DATE WRITTEN   June 2007
   13380             :     //       RE-ENGINEERED  Revised based on CalcDXHeatingCoil
   13381             : 
   13382             :     // PURPOSE OF THIS SUBROUTINE:
   13383             :     // Calculates the air-side performance and electrical energy use of a direct-
   13384             :     // expansion, air-cooled cooling unit with a multispeed compressor.
   13385             : 
   13386             :     // METHODOLOGY EMPLOYED:
   13387             :     // Uses the same methodology as the single speed DX heating unit model (SUBROUTINE CalcDXHeatingCoil).
   13388             :     // In addition it assumes that the unit performance is obtained by interpolating between
   13389             :     // the performance at high speed and that at low speed. If the output needed is below
   13390             :     // that produced at low speed, the compressor cycles between off and low speed.
   13391             : 
   13392             :     // Using/Aliasing
   13393             :     using Curve::CurveValue;
   13394     6858982 :     Real64 MSHPMassFlowRateHigh = state.dataHVACGlobal->MSHPMassFlowRateHigh;
   13395     6858982 :     Real64 MSHPMassFlowRateLow = state.dataHVACGlobal->MSHPMassFlowRateLow;
   13396     6858982 :     auto &MSHPWasteHeat = state.dataHVACGlobal->MSHPWasteHeat;
   13397             : 
   13398             :     // SUBROUTINE ARGUMENT DEFINITIONS:
   13399             :     // SpeedRatio varies between 1.0 (maximum speed) and 0.0 (minimum speed)
   13400             : 
   13401             :     // SUBROUTINE PARAMETER DEFINITIONS:
   13402             :     static constexpr std::string_view RoutineName("CalcMultiSpeedDXCoilHeating");
   13403             :     static constexpr std::string_view RoutineNameAverageLoad("CalcMultiSpeedDXCoilHeating:Averageload");
   13404             :     static constexpr std::string_view RoutineNameFullLoad("CalcMultiSpeedDXCoilHeating:fullload");
   13405             : 
   13406             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   13407             :     Real64 AirMassFlow;         // dry air mass flow rate through coil [kg/s]
   13408             :     Real64 InletAirWetBulbC;    // wetbulb temperature of inlet air [C]
   13409             :     Real64 InletAirDryBulbTemp; // inlet air dry bulb temperature [C]
   13410             :     Real64 InletAirEnthalpy;    // inlet air enthalpy [J/kg]
   13411             :     Real64 InletAirHumRat;      // inlet air humidity ratio [kg/kg]
   13412             :     Real64 OutletAirEnthalpy;   // outlet air enthalpy [J/kg]
   13413             :     Real64 OutletAirHumRat;     // outlet air humidity ratio [kg/kg]
   13414             :     Real64 TotCapHS;            // total capacity at high speed [W]
   13415             :     Real64 TotCapLS;            // total capacity at low speed [W]
   13416             :     Real64 TotCapHSAdj;         // total adjusted capacity at high speed [W]
   13417             :     Real64 TotCapLSAdj;         // total adjusted capacity at low speed [W]
   13418             :     Real64 EIRHS;               // EIR at off rated conditions (high speed)
   13419             :     Real64 EIRLS;               // EIR at off rated conditions (low speed)
   13420             :     Real64 TotCap;              // total capacity at current speed [W]
   13421             :     Real64 TotCapAdj;           // total adjusted capacity at current speed [W]
   13422             :     Real64 EIR;                 // EIR at current speed
   13423             :     Real64 PLF;                 // Part load factor, accounts for thermal lag at compressor startup, used in
   13424             :     // power calculation
   13425             :     Real64 OutdoorDryBulb;            // Outdoor dry-bulb temperature at condenser (C)
   13426             :     Real64 OutdoorHumRat;             // Outdoor humidity ratio at condenser (kg/kg)
   13427             :     Real64 OutdoorPressure;           // Outdoor barometric pressure at condenser (Pa)
   13428             :     int SpeedNumHS;                   // High speed number
   13429             :     int SpeedNumLS;                   // Low speed number
   13430             :     Real64 AirMassFlowRatioLS;        // airflow ratio at low speed
   13431             :     Real64 AirMassFlowRatioHS;        // airflow ratio at high speed
   13432             :     Real64 AirFlowRatio;              // Airflow ratio
   13433             :     Real64 PLRHeating;                // Part load ratio in heating
   13434             :     Real64 CrankcaseHeatingPower;     // Power due to crank case heater
   13435             :     Real64 AirVolumeFlowRate;         // Air volume flow rate across the heating coil
   13436             :     Real64 VolFlowperRatedTotCap;     // Air volume flow rate divided by rated total heating capacity
   13437     6858982 :     Real64 TotCapTempModFac(0.0);     // Total capacity modifier as a function ot temperature
   13438             :     Real64 TotCapFlowModFac;          // Total capacity modifier as a function of flow ratio
   13439             :     Real64 OutdoorCoilT;              // Outdoor coil temperature
   13440             :     Real64 OutdoorCoildw;             // Outdoor coil delta w assuming coil temperature of OutdoorCoilT
   13441             :     Real64 LoadDueToDefrost;          // Additonal load due to defrost
   13442             :     Real64 LoadDueToDefrostLS;        // Additonal load due to defrost at low speed
   13443             :     Real64 LoadDueToDefrostHS;        // Additonal load due to defrost at high speed
   13444             :     Real64 HeatingCapacityMultiplier; // Multiplier for heating capacity when system is in defrost
   13445             :     Real64 FractionalDefrostTime;     // Fraction of time step when system is in defrost
   13446             :     Real64 InputPowerMultiplier;      // Multiplier for poer when system is in defrost
   13447             :     Real64 DefrostEIRTempModFac;      // EIR modifier for defrost
   13448             :     Real64 FullLoadOutAirEnth;        // Outlet full load enthalpy
   13449             :     Real64 FullLoadOutAirHumRat;      // Outlet humidity ratio at full load
   13450             :     Real64 FullLoadOutAirTemp;        // Outlet temperature at full load
   13451             :     Real64 FullLoadOutAirRH;          // Outler relative humidity at full load
   13452             :     Real64 OutletAirTemp;             // Supply ari temperature
   13453     6858982 :     Real64 EIRTempModFac(0.0);        // EIR modifier as a function of temperature
   13454             :     Real64 EIRFlowModFac;             // EIR modifier as a function of airflow ratio
   13455             :     Real64 WasteHeatLS;               // Waste heat at low speed
   13456             :     Real64 WasteHeatHS;               // Waste heat at high speed
   13457             :     Real64 LSFullLoadOutAirEnth;      // Outlet full load enthalpy at low speed
   13458             :     Real64 HSFullLoadOutAirEnth;      // Outlet full load enthalpy at high speed
   13459             :     Real64 LSElecHeatingPower;        // Full load power at low speed
   13460             :     Real64 HSElecHeatingPower;        // Full load power at high speed
   13461             :     Real64 DefrostPowerLS;            // Defrost power at low speed [W]
   13462             :     Real64 DefrostPowerHS;            // Defrost power at high speed [W]
   13463             : 
   13464             :     // Autodesk:Uninit Initialize variables used uninitialized
   13465     6858982 :     FullLoadOutAirEnth = 0.0; // Autodesk:Uninit Force default initialization
   13466             : 
   13467     6858982 :     auto &DXCT = state.dataHVACGlobal->DXCT;
   13468     6858982 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   13469             : 
   13470     6858982 :     if (SpeedNum > 1) {
   13471     1207252 :         SpeedNumLS = SpeedNum - 1;
   13472     1207252 :         SpeedNumHS = SpeedNum;
   13473     1207252 :         if (SpeedNum > thisDXCoil.NumOfSpeeds) {
   13474           0 :             SpeedNumLS = thisDXCoil.NumOfSpeeds - 1;
   13475           0 :             SpeedNumHS = thisDXCoil.NumOfSpeeds;
   13476             :         }
   13477             :     } else {
   13478     5651730 :         SpeedNumLS = 1;
   13479     5651730 :         SpeedNumHS = 1;
   13480             :     }
   13481             : 
   13482     6858982 :     AirMassFlow = thisDXCoil.InletAirMassFlowRate;
   13483     6858982 :     AirMassFlowRatioLS = MSHPMassFlowRateLow / thisDXCoil.MSRatedAirMassFlowRate(SpeedNumLS);
   13484     6858982 :     AirMassFlowRatioHS = MSHPMassFlowRateHigh / thisDXCoil.MSRatedAirMassFlowRate(SpeedNumHS);
   13485     6858982 :     if ((AirMassFlow > 0.0) && (CycRatio > 0.0) && (MSHPMassFlowRateHigh == 0.0)) {
   13486           0 :         ShowSevereError(
   13487             :             state,
   13488           0 :             format("CalcMultiSpeedDXCoilHeating: {} \"{} Developer error - inconsistent airflow rates.", thisDXCoil.DXCoilType, thisDXCoil.Name));
   13489           0 :         if (MSHPMassFlowRateLow == 0.0 && SpeedNum > 1) {
   13490           0 :             ShowContinueError(state,
   13491             :                               "When AirMassFlow > 0.0 and CycRatio > 0.0 and SpeedNum > 1, then MSHPMassFlowRateLow and MSHPMassFlowRateHigh "
   13492             :                               "must also be > 0.0");
   13493           0 :             ShowContinueErrorTimeStamp(state, "");
   13494           0 :             ShowContinueError(state,
   13495           0 :                               format("AirMassFlow={:.3R},CycRatio={:.3R},SpeedNum={:.0R}, MSHPMassFlowRateLow={:.3R}, MSHPMassFlowRateHigh={:.3R}",
   13496             :                                      AirMassFlow,
   13497           0 :                                      double(SpeedNum),
   13498             :                                      CycRatio,
   13499             :                                      MSHPMassFlowRateLow,
   13500             :                                      MSHPMassFlowRateHigh));
   13501           0 :             ShowFatalError(state, "Preceding condition(s) causes termination.");
   13502             :         } else {
   13503           0 :             ShowContinueError(state, "When AirMassFlow > 0.0 and CycRatio > 0.0, then MSHPMassFlowRateHigh must also be > 0.0");
   13504           0 :             ShowContinueErrorTimeStamp(state, "");
   13505           0 :             ShowContinueError(state,
   13506           0 :                               format("AirMassFlow={:.3R},CycRatio={:.3R}, MSHPMassFlowRateHigh={:.3R}", AirMassFlow, CycRatio, MSHPMassFlowRateHigh));
   13507           0 :             ShowFatalError(state, "Preceding condition(s) causes termination.");
   13508             :         }
   13509     6858982 :     } else if (CycRatio > 1.0 || SpeedRatio > 1.0) {
   13510           0 :         ShowSevereError(
   13511             :             state,
   13512           0 :             format("CalcMultiSpeedDXCoilHeating: {} \"{} Developer error - inconsistent speed ratios.", thisDXCoil.DXCoilType, thisDXCoil.Name));
   13513           0 :         ShowContinueError(state, "CycRatio and SpeedRatio must be between 0.0 and 1.0");
   13514           0 :         ShowContinueErrorTimeStamp(state, "");
   13515           0 :         ShowContinueError(state, format("CycRatio={:.1R}, SpeedRatio = {:.1R}", CycRatio, SpeedRatio));
   13516           0 :         ShowFatalError(state, "Preceding condition(s) causes termination.");
   13517             :     }
   13518             : 
   13519     6858982 :     AirFlowRatio = 1.0;
   13520     6858982 :     if (thisDXCoil.CompanionUpstreamDXCoil == 0) MSHPWasteHeat = 0.0;
   13521             : 
   13522             :     // Get condenser outdoor node info from DX Heating Coil
   13523     6858982 :     if (thisDXCoil.CondenserInletNodeNum(1) != 0) {
   13524     2703794 :         OutdoorPressure = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).Press;
   13525             :         // If node is not connected to anything, pressure = default, use weather data
   13526     2703794 :         if (OutdoorPressure == state.dataLoopNodes->DefaultNodeValues.Press) {
   13527           0 :             OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   13528           0 :             OutdoorHumRat = state.dataEnvrn->OutHumRat;
   13529           0 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
   13530             :         } else {
   13531     2703794 :             OutdoorDryBulb = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).Temp;
   13532     2703794 :             OutdoorHumRat = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).HumRat;
   13533             :         }
   13534     2703794 :         if (thisDXCoil.IsSecondaryDXCoilInZone) {
   13535           0 :             auto &secZoneHB = state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr);
   13536           0 :             OutdoorDryBulb = secZoneHB.ZT;
   13537           0 :             OutdoorHumRat = secZoneHB.airHumRat;
   13538             :             // OutdoorWetBulb = DXCoil( DXCoilNum ).EvapInletWetBulb;
   13539           0 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
   13540             :         }
   13541     4155188 :     } else if (thisDXCoil.IsSecondaryDXCoilInZone) {
   13542           0 :         auto &secZoneHB = state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr);
   13543           0 :         OutdoorDryBulb = secZoneHB.ZT;
   13544           0 :         OutdoorHumRat = secZoneHB.airHumRat;
   13545             :         // OutdoorWetBulb = DXCoil( DXCoilNum ).EvapInletWetBulb;
   13546           0 :         OutdoorPressure = state.dataEnvrn->OutBaroPress;
   13547             :     } else {
   13548     4155188 :         OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   13549     4155188 :         OutdoorHumRat = state.dataEnvrn->OutHumRat;
   13550     4155188 :         OutdoorPressure = state.dataEnvrn->OutBaroPress;
   13551             :     }
   13552             : 
   13553     6858982 :     InletAirDryBulbTemp = thisDXCoil.InletAirTemp;
   13554     6858982 :     InletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   13555     6858982 :     InletAirHumRat = thisDXCoil.InletAirHumRat;
   13556             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   13557             :     // InletAirPressure = DXCoil(DXCoilNum)%InletAirPressure
   13558             :     // InletAirWetBulbC = PsyTwbFnTdbWPb(InletAirDryBulbTemp,InletAirHumRat,InletAirPressure)
   13559     6858982 :     InletAirWetBulbC = PsyTwbFnTdbWPb(state, InletAirDryBulbTemp, InletAirHumRat, OutdoorPressure, RoutineName);
   13560     6858982 :     PLRHeating = 0.0;
   13561     6858982 :     thisDXCoil.HeatingCoilRuntimeFraction = 0.0;
   13562             :     // Initialize crankcase heater, operates below OAT defined in input deck for HP DX heating coil
   13563     6858982 :     if (OutdoorDryBulb < thisDXCoil.MaxOATCrankcaseHeater) {
   13564     2865655 :         CrankcaseHeatingPower = thisDXCoil.CrankcaseHeaterCapacity;
   13565     2865655 :         if (thisDXCoil.CrankcaseHeaterCapacityCurveIndex > 0) {
   13566           0 :             CrankcaseHeatingPower *= Curve::CurveValue(state, thisDXCoil.CrankcaseHeaterCapacityCurveIndex, OutdoorDryBulb);
   13567             :         }
   13568             :     } else {
   13569     3993327 :         CrankcaseHeatingPower = 0.0;
   13570             :     }
   13571     6858982 :     thisDXCoil.PartLoadRatio = 0.0;
   13572     6858982 :     state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).AvailCapacity = 0.0;
   13573             : 
   13574     5967060 :     if ((AirMassFlow > 0.0) && (GetCurrentScheduleValue(state, thisDXCoil.SchedPtr) > 0.0) &&
   13575    12826042 :         ((CycRatio > 0.0) || (SpeedRatio > 0.0 && SingleMode == 0)) && OutdoorDryBulb > thisDXCoil.MinOATCompressor) {
   13576             : 
   13577     1014233 :         if (SpeedNum > 1 && SingleMode == 0) {
   13578             : 
   13579             :             // Check for valid air volume flow per rated total cooling capacity (200 - 600 cfm/ton) at low speed
   13580      305149 :             AirVolumeFlowRate = MSHPMassFlowRateLow / PsyRhoAirFnPbTdbW(state, OutdoorPressure, InletAirDryBulbTemp, InletAirHumRat, RoutineName);
   13581             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   13582             :             //  AirVolumeFlowRate = AirMassFlow/PsyRhoAirFnPbTdbW(InletAirPressure,InletAirDryBulbTemp, InletAirHumRat)
   13583      305149 :             VolFlowperRatedTotCap = AirVolumeFlowRate / thisDXCoil.MSRatedTotCap(SpeedNumLS);
   13584      610298 :             if ((VolFlowperRatedTotCap < HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) ||
   13585      305149 :                 (VolFlowperRatedTotCap > HVAC::MaxHeatVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT])) {
   13586      283862 :                 if (thisDXCoil.MSErrIndex(SpeedNumLS) == 0) {
   13587           8 :                     ShowWarningMessage(
   13588             :                         state,
   13589           8 :                         format("{} \"{}\" - Air volume flow rate per watt of rated total heating capacity is out of range at speed {}.",
   13590           4 :                                thisDXCoil.DXCoilType,
   13591           4 :                                thisDXCoil.Name,
   13592             :                                SpeedNumLS));
   13593           4 :                     ShowContinueErrorTimeStamp(state, "");
   13594           8 :                     ShowContinueError(state,
   13595           8 :                                       format("Expected range for VolumeFlowPerRatedTotalCapacity=[{:.3R}--{:.3R}] Current value is {:.3R} m3/s/W",
   13596           4 :                                              HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   13597           4 :                                              HVAC::MaxHeatVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   13598             :                                              VolFlowperRatedTotCap));
   13599           4 :                     ShowContinueError(state, "Possible causes include inconsistent air flow rates in system components or");
   13600           4 :                     ShowContinueError(state, "inconsistent supply air fan operation modes in coil and unitary system objects.");
   13601             :                 }
   13602      851586 :                 ShowRecurringWarningErrorAtEnd(state,
   13603      567724 :                                                format("{} \"{}\" - Air volume flow rate per watt of rated total heating capacity is out of range "
   13604             :                                                       "at speed {} error continues...",
   13605      283862 :                                                       thisDXCoil.DXCoilType,
   13606      283862 :                                                       thisDXCoil.Name,
   13607             :                                                       SpeedNumLS),
   13608             :                                                thisDXCoil.MSErrIndex(SpeedNumLS),
   13609             :                                                VolFlowperRatedTotCap,
   13610             :                                                VolFlowperRatedTotCap);
   13611             :             }
   13612             : 
   13613             :             // Check for valid air volume flow per rated total cooling capacity (200 - 600 cfm/ton) at high speed
   13614      305149 :             AirVolumeFlowRate = MSHPMassFlowRateHigh / PsyRhoAirFnPbTdbW(state, OutdoorPressure, InletAirDryBulbTemp, InletAirHumRat, RoutineName);
   13615             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   13616             :             //  AirVolumeFlowRate = AirMassFlow/PsyRhoAirFnPbTdbW(InletAirPressure,InletAirDryBulbTemp, InletAirHumRat)
   13617      305149 :             VolFlowperRatedTotCap = AirVolumeFlowRate / thisDXCoil.MSRatedTotCap(SpeedNumHS);
   13618      610298 :             if ((VolFlowperRatedTotCap < HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) ||
   13619      305149 :                 (VolFlowperRatedTotCap > HVAC::MaxHeatVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT])) {
   13620      283646 :                 if (thisDXCoil.MSErrIndex(SpeedNumHS) == 0) {
   13621           4 :                     ShowWarningMessage(
   13622             :                         state,
   13623           4 :                         format("{} \"{}\" - Air volume flow rate per watt of rated total heating capacity is out of range at speed {}.",
   13624           2 :                                thisDXCoil.DXCoilType,
   13625           2 :                                thisDXCoil.Name,
   13626             :                                SpeedNumHS));
   13627           2 :                     ShowContinueErrorTimeStamp(state, "");
   13628           4 :                     ShowContinueError(state,
   13629           4 :                                       format("Expected range for VolumeFlowPerRatedTotalCapacity=[{:.3R}--{:.3R}] Current value is {:.3R} m3/s/W",
   13630           2 :                                              HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   13631           2 :                                              HVAC::MaxHeatVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   13632             :                                              VolFlowperRatedTotCap));
   13633           2 :                     ShowContinueError(state, "Possible causes include inconsistent air flow rates in system components or");
   13634           2 :                     ShowContinueError(state, "inconsistent supply air fan operation modes in coil and unitary system objects.");
   13635             :                 }
   13636      850938 :                 ShowRecurringWarningErrorAtEnd(state,
   13637      567292 :                                                format("{} \"{}\" - Air volume flow rate per watt of rated total heating capacity is out of range "
   13638             :                                                       "at speed {} error continues...",
   13639      283646 :                                                       thisDXCoil.DXCoilType,
   13640      283646 :                                                       thisDXCoil.Name,
   13641             :                                                       SpeedNumHS),
   13642             :                                                thisDXCoil.MSErrIndex(SpeedNumHS),
   13643             :                                                VolFlowperRatedTotCap,
   13644             :                                                VolFlowperRatedTotCap);
   13645             :             }
   13646             : 
   13647             :             // Get total capacity modifying factor (function of temperature) for off-rated conditions
   13648             :             // Model was extended to accept bi-quadratic curves. This allows sensitivity of the heating capacity
   13649             :             // to the entering dry-bulb temperature as well as the outside dry-bulb temperature. User is
   13650             :             // advised to use the bi-quaratic curve if sufficient manufacturer data is available.
   13651             :             // Low speed
   13652      305149 :             if (state.dataCurveManager->PerfCurve(thisDXCoil.MSCCapFTemp(SpeedNumLS))->numDims == 1) {
   13653           0 :                 TotCapTempModFac = CurveValue(state, thisDXCoil.MSCCapFTemp(SpeedNumLS), OutdoorDryBulb);
   13654             :             } else {
   13655      305149 :                 TotCapTempModFac = CurveValue(state, thisDXCoil.MSCCapFTemp(SpeedNumLS), InletAirDryBulbTemp, OutdoorDryBulb);
   13656             :             }
   13657             :             //  Get total capacity modifying factor (function of mass flow) for off-rated conditions
   13658      305149 :             TotCapFlowModFac = CurveValue(state, thisDXCoil.MSCCapFFlow(SpeedNumLS), AirMassFlowRatioLS);
   13659             :             // Calculate total heating capacity for off-rated conditions
   13660      305149 :             TotCapLS = thisDXCoil.MSRatedTotCap(SpeedNumLS) * TotCapFlowModFac * TotCapTempModFac;
   13661             :             // High speed
   13662      305149 :             if (state.dataCurveManager->PerfCurve(thisDXCoil.MSCCapFTemp(SpeedNumHS))->numDims == 1) {
   13663           0 :                 TotCapTempModFac = CurveValue(state, thisDXCoil.MSCCapFTemp(SpeedNumHS), OutdoorDryBulb);
   13664             :             } else {
   13665      305149 :                 TotCapTempModFac = CurveValue(state, thisDXCoil.MSCCapFTemp(SpeedNumHS), InletAirDryBulbTemp, OutdoorDryBulb);
   13666             :             }
   13667             :             //  Get total capacity modifying factor (function of mass flow) for off-rated conditions
   13668      305149 :             TotCapFlowModFac = CurveValue(state, thisDXCoil.MSCCapFFlow(SpeedNumHS), AirMassFlowRatioHS);
   13669             :             // Calculate total heating capacity for off-rated conditions
   13670      305149 :             TotCapHS = thisDXCoil.MSRatedTotCap(SpeedNumHS) * TotCapFlowModFac * TotCapTempModFac;
   13671             :             // Calculate electricity consumed. First, get EIR modifying factors for off-rated conditions
   13672             :             // Model was extended to accept bi-quadratic curves. This allows sensitivity of the EIR
   13673             :             // to the entering dry-bulb temperature as well as the outside dry-bulb temperature. User is
   13674             :             // advised to use the bi-quaratic curve if sufficient manufacturer data is available.
   13675             :             // Low Speed
   13676      305149 :             if (state.dataCurveManager->PerfCurve(thisDXCoil.MSEIRFTemp(SpeedNumLS))->numDims == 1) {
   13677           0 :                 EIRTempModFac = CurveValue(state, thisDXCoil.MSEIRFTemp(SpeedNumLS), OutdoorDryBulb);
   13678             :             } else {
   13679      305149 :                 EIRTempModFac = CurveValue(state, thisDXCoil.MSEIRFTemp(SpeedNumLS), InletAirDryBulbTemp, OutdoorDryBulb);
   13680             :             }
   13681      305149 :             EIRFlowModFac = CurveValue(state, thisDXCoil.MSEIRFFlow(SpeedNumLS), AirMassFlowRatioLS);
   13682      305149 :             EIRLS = 1.0 / thisDXCoil.MSRatedCOP(SpeedNumLS) * EIRTempModFac * EIRFlowModFac;
   13683             :             // High Speed
   13684      305149 :             if (state.dataCurveManager->PerfCurve(thisDXCoil.MSEIRFTemp(SpeedNumHS))->numDims == 1) {
   13685           0 :                 EIRTempModFac = CurveValue(state, thisDXCoil.MSEIRFTemp(SpeedNumHS), OutdoorDryBulb);
   13686             :             } else {
   13687      305149 :                 EIRTempModFac = CurveValue(state, thisDXCoil.MSEIRFTemp(SpeedNumHS), InletAirDryBulbTemp, OutdoorDryBulb);
   13688             :             }
   13689      305149 :             EIRFlowModFac = CurveValue(state, thisDXCoil.MSEIRFFlow(SpeedNumHS), AirMassFlowRatioHS);
   13690      305149 :             EIRHS = 1.0 / thisDXCoil.MSRatedCOP(SpeedNumHS) * EIRTempModFac * EIRFlowModFac;
   13691             : 
   13692             :             // Calculating adjustment factors for defrost
   13693             :             // Calculate delta w through outdoor coil by assuming a coil temp of 0.82*DBT-9.7(F) per DOE2.1E
   13694      305149 :             OutdoorCoilT = 0.82 * OutdoorDryBulb - 8.589;
   13695      305149 :             OutdoorCoildw = max(1.0e-6, (OutdoorHumRat - PsyWFnTdpPb(state, OutdoorCoilT, OutdoorPressure, RoutineName)));
   13696             : 
   13697             :             // Initializing defrost adjustment factors
   13698      305149 :             LoadDueToDefrostLS = 0.0;
   13699      305149 :             LoadDueToDefrostHS = 0.0;
   13700      305149 :             HeatingCapacityMultiplier = 1.0;
   13701      305149 :             FractionalDefrostTime = 0.0;
   13702      305149 :             InputPowerMultiplier = 1.0;
   13703      305149 :             DefrostPowerLS = 0.0;
   13704      305149 :             DefrostPowerHS = 0.0;
   13705             : 
   13706             :             // Check outdoor temperature to determine if defrost is active
   13707      305149 :             if (OutdoorDryBulb <= thisDXCoil.MaxOATDefrost) {
   13708             :                 // Calculate defrost adjustment factors depending on defrost control type
   13709      303898 :                 if (thisDXCoil.DefrostControl == StandardRatings::HPdefrostControl::Timed) {
   13710      303898 :                     FractionalDefrostTime = thisDXCoil.DefrostTime;
   13711      303898 :                     if (FractionalDefrostTime > 0.0) {
   13712      303898 :                         HeatingCapacityMultiplier = 0.909 - 107.33 * OutdoorCoildw;
   13713      303898 :                         InputPowerMultiplier = 0.90 - 36.45 * OutdoorCoildw;
   13714             :                     }
   13715             :                 } else { // else defrost control is on-demand
   13716           0 :                     FractionalDefrostTime = 1.0 / (1.0 + 0.01446 / OutdoorCoildw);
   13717           0 :                     HeatingCapacityMultiplier = 0.875 * (1.0 - FractionalDefrostTime);
   13718           0 :                     InputPowerMultiplier = 0.954 * (1.0 - FractionalDefrostTime);
   13719             :                 }
   13720             : 
   13721      303898 :                 if (FractionalDefrostTime > 0.0) {
   13722             :                     // Calculate defrost adjustment factors depending on defrost control strategy
   13723      303898 :                     if (thisDXCoil.DefrostStrategy == StandardRatings::DefrostStrat::ReverseCycle) {
   13724      303898 :                         DefrostEIRTempModFac = CurveValue(state, thisDXCoil.DefrostEIRFT, max(15.555, InletAirWetBulbC), max(15.555, OutdoorDryBulb));
   13725      303898 :                         LoadDueToDefrostLS =
   13726      303898 :                             (0.01 * FractionalDefrostTime) * (7.222 - OutdoorDryBulb) * (thisDXCoil.MSRatedTotCap(SpeedNumLS) / 1.01667);
   13727      303898 :                         DefrostPowerLS = DefrostEIRTempModFac * (thisDXCoil.MSRatedTotCap(SpeedNumLS) / 1.01667) * FractionalDefrostTime;
   13728      303898 :                         LoadDueToDefrostHS =
   13729      303898 :                             (0.01 * FractionalDefrostTime) * (7.222 - OutdoorDryBulb) * (thisDXCoil.MSRatedTotCap(SpeedNumHS) / 1.01667);
   13730      303898 :                         DefrostPowerHS = DefrostEIRTempModFac * (thisDXCoil.MSRatedTotCap(SpeedNumHS) / 1.01667) * FractionalDefrostTime;
   13731             :                     } else { // Defrost strategy is resistive
   13732           0 :                         thisDXCoil.DefrostPower = thisDXCoil.DefrostCapacity * FractionalDefrostTime;
   13733             :                     }
   13734             :                 } else { // Defrost is not active because (OutDryBulbTemp .GT. DXCoil(DXCoilNum)%MaxOATDefrost)
   13735           0 :                     thisDXCoil.DefrostPower = 0.0;
   13736             :                 }
   13737             :             }
   13738             : 
   13739      305149 :             TotCapLSAdj = TotCapLS * HeatingCapacityMultiplier;
   13740      305149 :             TotCapHSAdj = TotCapHS * HeatingCapacityMultiplier;
   13741             : 
   13742             :             // Calculate modified PartLoadRatio due to defrost (reverse-cycle defrost only)
   13743      305149 :             PLRHeating = min(1.0, (SpeedRatio + LoadDueToDefrostHS / TotCapHSAdj));
   13744      305149 :             PLF = CurveValue(state, thisDXCoil.MSPLFFPLR(SpeedNumHS), PLRHeating); // Calculate part-load factor
   13745             : 
   13746      305149 :             if (PLF < 0.7) {
   13747           0 :                 if (thisDXCoil.PLRErrIndex == 0) {
   13748           0 :                     ShowWarningMessage(
   13749             :                         state,
   13750           0 :                         format("The PLF curve value at high speed for DX multispeed heating coil {} ={:.2R} for part-load ratio ={:.2R}",
   13751           0 :                                thisDXCoil.Name,
   13752             :                                PLF,
   13753             :                                PLRHeating));
   13754           0 :                     ShowContinueError(state, "PLF curve values must be >= 0.7. PLF has been reset to 0.7 and simulation is continuing.");
   13755           0 :                     ShowContinueError(state, "Check the IO reference manual for PLF curve guidance [Coil:Heating:DX:MultiSpeed].");
   13756           0 :                     ShowContinueErrorTimeStamp(state, "");
   13757             :                 }
   13758           0 :                 ShowRecurringWarningErrorAtEnd(state, "DX heating coil PLF curve < 0.7 warning continues... ", thisDXCoil.PLRErrIndex, PLF, PLF);
   13759           0 :                 PLF = 0.7;
   13760             :             }
   13761             : 
   13762      305149 :             thisDXCoil.HeatingCoilRuntimeFraction = (PLRHeating / PLF);
   13763      305149 :             if (thisDXCoil.HeatingCoilRuntimeFraction > 1.0 && std::abs(thisDXCoil.HeatingCoilRuntimeFraction - 1.0) > 0.001) {
   13764           0 :                 if (thisDXCoil.ErrIndex4 == 0) {
   13765           0 :                     ShowWarningMessage(state,
   13766           0 :                                        format("The runtime fraction at high speed for DX multispeed heating coil {} exceeded 1.0. [{:.4R}].",
   13767           0 :                                               thisDXCoil.Name,
   13768           0 :                                               thisDXCoil.HeatingCoilRuntimeFraction));
   13769           0 :                     ShowContinueError(state, "Runtime fraction is set to 1.0 and the simulation continues...");
   13770           0 :                     ShowContinueError(state, "Check the IO reference manual for PLF curve guidance [Coil:Heating:DX:SingleSpeed].");
   13771           0 :                     ShowContinueErrorTimeStamp(state, "");
   13772             :                 }
   13773           0 :                 ShowRecurringWarningErrorAtEnd(state,
   13774           0 :                                                thisDXCoil.Name + ", DX heating coil runtime fraction > 1.0 warning continues...",
   13775           0 :                                                thisDXCoil.ErrIndex4,
   13776           0 :                                                thisDXCoil.HeatingCoilRuntimeFraction,
   13777           0 :                                                thisDXCoil.HeatingCoilRuntimeFraction);
   13778           0 :                 thisDXCoil.HeatingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   13779      305149 :             } else if (thisDXCoil.HeatingCoilRuntimeFraction > 1.0) {
   13780           0 :                 thisDXCoil.HeatingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   13781             :             }
   13782             : 
   13783             :             // Get full load output and power
   13784      305149 :             LSFullLoadOutAirEnth = InletAirEnthalpy + TotCapLSAdj / MSHPMassFlowRateLow;
   13785      305149 :             HSFullLoadOutAirEnth = InletAirEnthalpy + TotCapHSAdj / MSHPMassFlowRateHigh;
   13786      305149 :             LSElecHeatingPower = TotCapLS * EIRLS * InputPowerMultiplier;
   13787      305149 :             HSElecHeatingPower = TotCapHS * EIRHS * InputPowerMultiplier;
   13788      305149 :             OutletAirHumRat = InletAirHumRat;
   13789             : 
   13790             :             // if cycling fan, send coil part-load fraction to on/off fan via HVACDataGlobals
   13791      305149 :             if (fanOp == HVAC::FanOp::Cycling) state.dataHVACGlobal->OnOffFanPartLoadFraction = 1.0;
   13792             : 
   13793             :             // Power calculation
   13794      305149 :             if (!thisDXCoil.PLRImpact) {
   13795      305149 :                 thisDXCoil.ElecHeatingPower = SpeedRatio * HSElecHeatingPower + (1.0 - SpeedRatio) * LSElecHeatingPower;
   13796             :             } else {
   13797           0 :                 thisDXCoil.ElecHeatingPower =
   13798           0 :                     thisDXCoil.HeatingCoilRuntimeFraction * HSElecHeatingPower + (1.0 - thisDXCoil.HeatingCoilRuntimeFraction) * LSElecHeatingPower;
   13799             :             }
   13800             : 
   13801      305149 :             thisDXCoil.TotalHeatingEnergyRate = MSHPMassFlowRateHigh * (HSFullLoadOutAirEnth - InletAirEnthalpy) * SpeedRatio +
   13802      305149 :                                                 MSHPMassFlowRateLow * (LSFullLoadOutAirEnth - InletAirEnthalpy) * (1.0 - SpeedRatio);
   13803      305149 :             OutletAirEnthalpy = InletAirEnthalpy + thisDXCoil.TotalHeatingEnergyRate / thisDXCoil.InletAirMassFlowRate;
   13804      305149 :             OutletAirTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
   13805      305149 :             FullLoadOutAirRH = PsyRhFnTdbWPb(state, OutletAirTemp, OutletAirHumRat, OutdoorPressure, RoutineNameAverageLoad);
   13806      305149 :             if (FullLoadOutAirRH > 1.0) { // Limit to saturated conditions at FullLoadOutAirEnth
   13807           0 :                 OutletAirTemp = PsyTsatFnHPb(state,
   13808             :                                              FullLoadOutAirEnth,
   13809             :                                              OutdoorPressure,
   13810             :                                              RoutineName); // Autodesk:Uninit FullLoadOutAirEnth was possibly uninitialized
   13811           0 :                 OutletAirHumRat = PsyWFnTdbH(
   13812             :                     state, OutletAirTemp, FullLoadOutAirEnth, RoutineName); // Autodesk:Uninit FullLoadOutAirEnth was possibly uninitialized
   13813             :             }
   13814             : 
   13815             :             // Waste heat calculation
   13816      305149 :             if (thisDXCoil.FuelType != Constant::eFuel::Electricity) {
   13817           0 :                 if (thisDXCoil.MSWasteHeat(SpeedNumLS) == 0) {
   13818           0 :                     WasteHeatLS = thisDXCoil.MSWasteHeatFrac(SpeedNumLS);
   13819             :                 } else {
   13820           0 :                     WasteHeatLS = CurveValue(state, thisDXCoil.MSWasteHeat(SpeedNumLS), OutdoorDryBulb, InletAirDryBulbTemp) *
   13821           0 :                                   thisDXCoil.MSWasteHeatFrac(SpeedNumLS);
   13822             :                 }
   13823           0 :                 if (thisDXCoil.MSWasteHeat(SpeedNumHS) == 0) {
   13824           0 :                     WasteHeatHS = thisDXCoil.MSWasteHeatFrac(SpeedNumHS);
   13825             :                 } else {
   13826           0 :                     WasteHeatHS = CurveValue(state, thisDXCoil.MSWasteHeat(SpeedNumHS), OutdoorDryBulb, InletAirDryBulbTemp) *
   13827           0 :                                   thisDXCoil.MSWasteHeatFrac(SpeedNumHS);
   13828             :                 }
   13829           0 :                 thisDXCoil.MSFuelWasteHeat = (SpeedRatio * WasteHeatHS + (1.0 - SpeedRatio) * WasteHeatLS) * thisDXCoil.ElecCoolingPower;
   13830           0 :                 if (thisDXCoil.MSHPHeatRecActive) {
   13831           0 :                     MSHPWasteHeat = thisDXCoil.MSFuelWasteHeat;
   13832             :                 }
   13833             :             }
   13834      305149 :             if (thisDXCoil.FuelType != Constant::eFuel::Electricity) {
   13835             : 
   13836           0 :                 thisDXCoil.FuelUsed = thisDXCoil.ElecHeatingPower;
   13837           0 :                 thisDXCoil.ElecHeatingPower = 0.0;
   13838             :             }
   13839             : 
   13840             :             // Adjust defrost power to correct for DOE-2 bug where defrost power is constant regardless of compressor runtime fraction
   13841             :             // Defrosts happen based on compressor run time (frost buildup on outdoor coil), not total elapsed time.
   13842      305149 :             if (thisDXCoil.DefrostStrategy == StandardRatings::DefrostStrat::ReverseCycle) {
   13843      305149 :                 if (!thisDXCoil.PLRImpact) {
   13844      305149 :                     thisDXCoil.DefrostPower = DefrostPowerHS * SpeedRatio + DefrostPowerLS * (1.0 - SpeedRatio);
   13845             :                 } else {
   13846           0 :                     thisDXCoil.DefrostPower =
   13847           0 :                         DefrostPowerHS * thisDXCoil.HeatingCoilRuntimeFraction + DefrostPowerLS * (1.0 - thisDXCoil.HeatingCoilRuntimeFraction);
   13848             :                 }
   13849             :             }
   13850      305149 :             thisDXCoil.OutletAirTemp = OutletAirTemp;
   13851      305149 :             thisDXCoil.OutletAirHumRat = OutletAirHumRat;
   13852      305149 :             thisDXCoil.OutletAirEnthalpy = OutletAirEnthalpy;
   13853      305149 :             thisDXCoil.CrankcaseHeaterPower = 0.0;
   13854             : 
   13855             :             // Stage 1
   13856      709084 :         } else if (CycRatio > 0.0 || (CycRatio > 0.0 && SingleMode == 1)) {
   13857             : 
   13858             :             // for cycling fan, reset mass flow to full on rate
   13859      709084 :             if (fanOp == HVAC::FanOp::Cycling) AirMassFlow /= CycRatio;
   13860      709084 :             if (fanOp == HVAC::FanOp::Continuous) AirMassFlow = MSHPMassFlowRateHigh;
   13861             :             // Check for valid air volume flow per rated total cooling capacity (200 - 600 cfm/ton)
   13862      709084 :             AirVolumeFlowRate = AirMassFlow / PsyRhoAirFnPbTdbW(state, OutdoorPressure, InletAirDryBulbTemp, InletAirHumRat, RoutineName);
   13863             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   13864             :             //  AirVolumeFlowRate = AirMassFlow/PsyRhoAirFnPbTdbW(InletAirPressure,InletAirDryBulbTemp, InletAirHumRat)
   13865      709084 :             VolFlowperRatedTotCap = AirVolumeFlowRate / thisDXCoil.MSRatedTotCap(SpeedNum);
   13866             : 
   13867     1418168 :             if ((VolFlowperRatedTotCap < HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT]) ||
   13868      709084 :                 (VolFlowperRatedTotCap > HVAC::MaxHeatVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT])) {
   13869      698193 :                 if (thisDXCoil.ErrIndex1 == 0) {
   13870          12 :                     ShowWarningMessage(state,
   13871          12 :                                        format("{} \"{}\" - Air volume flow rate per watt of rated total heating capacity is out of range at speed 1.",
   13872           6 :                                               thisDXCoil.DXCoilType,
   13873           6 :                                               thisDXCoil.Name));
   13874           6 :                     ShowContinueErrorTimeStamp(state, "");
   13875          12 :                     ShowContinueError(state,
   13876          12 :                                       format("Expected range for VolumeFlowPerRatedTotalCapacity=[{:.3R}--{:.3R}] Current value is {:.3R} m3/s/W",
   13877           6 :                                              HVAC::MinOperVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   13878           6 :                                              HVAC::MaxHeatVolFlowPerRatedTotCap[(int)state.dataHVACGlobal->DXCT],
   13879             :                                              VolFlowperRatedTotCap));
   13880           6 :                     ShowContinueError(state, "Possible causes include inconsistent air flow rates in system components or");
   13881           6 :                     ShowContinueError(state, "inconsistent supply air fan operation modes in coil and unitary system objects.");
   13882             :                 }
   13883     2094579 :                 ShowRecurringWarningErrorAtEnd(
   13884             :                     state,
   13885     1396386 :                     thisDXCoil.DXCoilType + " \"" + thisDXCoil.Name +
   13886             :                         "\" - Air volume flow rate per watt of rated total heating capacity is out of range error continues at speed 1...",
   13887      698193 :                     thisDXCoil.ErrIndex1,
   13888             :                     VolFlowperRatedTotCap,
   13889             :                     VolFlowperRatedTotCap);
   13890             :             }
   13891             : 
   13892             :             // Get total capacity modifying factor (function of temperature) for off-rated conditions
   13893             :             // Model was extended to accept bi-quadratic curves. This allows sensitivity of the heating capacity
   13894             :             // to the entering dry-bulb temperature as well as the outside dry-bulb temperature. User is
   13895             :             // advised to use the bi-quaratic curve if sufficient manufacturer data is available.
   13896      709084 :             if (state.dataCurveManager->PerfCurve(thisDXCoil.MSCCapFTemp(SpeedNum))->numDims == 1) {
   13897      638208 :                 TotCapTempModFac = CurveValue(state, thisDXCoil.MSCCapFTemp(SpeedNum), OutdoorDryBulb);
   13898             :             } else {
   13899       70876 :                 TotCapTempModFac = CurveValue(state, thisDXCoil.MSCCapFTemp(SpeedNum), InletAirDryBulbTemp, OutdoorDryBulb);
   13900             :             }
   13901             : 
   13902             :             //  Get total capacity modifying factor (function of mass flow) for off-rated conditions
   13903             :             //    AirMassFlowRatio = AirMassFlow/DXCoil(DXCoilNum)%MSRatedAirMassFlowRate(SpeedNumLS)
   13904             :             //    TotCapFlowModFac = CurveValue(state, DXCoil(DXCoilNum)%MSCCapFFlow(SpeedNumLS),AirMassFlowRatio)
   13905      709084 :             TotCapFlowModFac = CurveValue(state, thisDXCoil.MSCCapFFlow(SpeedNum), AirMassFlowRatioLS);
   13906             :             // Calculate total heating capacity for off-rated conditions
   13907      709084 :             TotCap = thisDXCoil.MSRatedTotCap(SpeedNum) * TotCapFlowModFac * TotCapTempModFac;
   13908             : 
   13909             :             // Calculating adjustment factors for defrost
   13910             :             // Calculate delta w through outdoor coil by assuming a coil temp of 0.82*DBT-9.7(F) per DOE2.1E
   13911      709084 :             OutdoorCoilT = 0.82 * OutdoorDryBulb - 8.589;
   13912      709084 :             OutdoorCoildw = max(1.0e-6, (OutdoorHumRat - PsyWFnTdpPb(state, OutdoorCoilT, OutdoorPressure, RoutineName)));
   13913             : 
   13914             :             // Initializing defrost adjustment factors
   13915      709084 :             LoadDueToDefrost = 0.0;
   13916      709084 :             HeatingCapacityMultiplier = 1.0;
   13917      709084 :             FractionalDefrostTime = 0.0;
   13918      709084 :             InputPowerMultiplier = 1.0;
   13919             : 
   13920             :             // Check outdoor temperature to determine of defrost is active
   13921      709084 :             if (OutdoorDryBulb <= thisDXCoil.MaxOATDefrost) {
   13922             :                 // Calculate defrost adjustment factors depending on defrost control type
   13923      449664 :                 if (thisDXCoil.DefrostControl == StandardRatings::HPdefrostControl::Timed) {
   13924      449664 :                     FractionalDefrostTime = thisDXCoil.DefrostTime;
   13925      449664 :                     if (FractionalDefrostTime > 0.0) {
   13926      449664 :                         HeatingCapacityMultiplier = 0.909 - 107.33 * OutdoorCoildw;
   13927      449664 :                         InputPowerMultiplier = 0.90 - 36.45 * OutdoorCoildw;
   13928             :                     }
   13929             :                 } else { // else defrost control is on-demand
   13930           0 :                     FractionalDefrostTime = 1.0 / (1.0 + 0.01446 / OutdoorCoildw);
   13931           0 :                     HeatingCapacityMultiplier = 0.875 * (1.0 - FractionalDefrostTime);
   13932           0 :                     InputPowerMultiplier = 0.954 * (1.0 - FractionalDefrostTime);
   13933             :                 }
   13934             : 
   13935      449664 :                 if (FractionalDefrostTime > 0.0) {
   13936             :                     // Calculate defrost adjustment factors depending on defrost control strategy
   13937      449664 :                     if (thisDXCoil.DefrostStrategy == StandardRatings::DefrostStrat::ReverseCycle) {
   13938      449664 :                         LoadDueToDefrost = (0.01 * FractionalDefrostTime) * (7.222 - OutdoorDryBulb) * (thisDXCoil.MSRatedTotCap(1) / 1.01667);
   13939      449664 :                         DefrostEIRTempModFac = CurveValue(state, thisDXCoil.DefrostEIRFT, max(15.555, InletAirWetBulbC), max(15.555, OutdoorDryBulb));
   13940      449664 :                         thisDXCoil.DefrostPower = DefrostEIRTempModFac * (thisDXCoil.MSRatedTotCap(1) / 1.01667) * FractionalDefrostTime;
   13941             :                     } else { // Defrost strategy is resistive
   13942           0 :                         thisDXCoil.DefrostPower = thisDXCoil.DefrostCapacity * FractionalDefrostTime;
   13943             :                     }
   13944             :                 } else { // Defrost is not active because (OutDryBulbTemp .GT. DXCoil(DXCoilNum)%MaxOATDefrost)
   13945           0 :                     thisDXCoil.DefrostPower = 0.0;
   13946             :                 }
   13947             :             }
   13948             : 
   13949             :             // Modify total heating capacity based on defrost heating capacity multiplier
   13950      709084 :             TotCapAdj = TotCap * HeatingCapacityMultiplier;
   13951             : 
   13952             :             // Calculate full load outlet conditions
   13953      709084 :             FullLoadOutAirEnth = InletAirEnthalpy + TotCapAdj / AirMassFlow;
   13954      709084 :             FullLoadOutAirHumRat = InletAirHumRat;
   13955      709084 :             FullLoadOutAirTemp = PsyTdbFnHW(FullLoadOutAirEnth, FullLoadOutAirHumRat);
   13956      709084 :             FullLoadOutAirRH = PsyRhFnTdbWPb(state, FullLoadOutAirTemp, FullLoadOutAirHumRat, OutdoorPressure, RoutineNameFullLoad);
   13957             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   13958             :             //  FullLoadOutAirRH = PsyRhFnTdbWPb(FullLoadOutAirTemp,FullLoadOutAirHumRat,InletAirPressure)
   13959      709084 :             if (FullLoadOutAirRH > 1.0) { // Limit to saturated conditions at FullLoadOutAirEnth
   13960           0 :                 FullLoadOutAirTemp = PsyTsatFnHPb(state, FullLoadOutAirEnth, OutdoorPressure, RoutineName);
   13961             :                 //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   13962             :                 //  FullLoadOutAirTemp = PsyTsatFnHPb(FullLoadOutAirEnth,InletAirPressure)
   13963           0 :                 FullLoadOutAirHumRat = PsyWFnTdbH(state, FullLoadOutAirTemp, FullLoadOutAirEnth, RoutineName);
   13964             :             }
   13965             : 
   13966             :             // Set outlet conditions from the full load calculation
   13967      709084 :             OutletAirEnthalpy = FullLoadOutAirEnth;
   13968      709084 :             OutletAirHumRat = FullLoadOutAirHumRat;
   13969      709084 :             OutletAirTemp = FullLoadOutAirTemp;
   13970             :             // Calculate electricity consumed. First, get EIR modifying factors for off-rated conditions
   13971             :             // Model was extended to accept bi-quadratic curves. This allows sensitivity of the EIR
   13972             :             // to the entering dry-bulb temperature as well as the outside dry-bulb temperature. User is
   13973             :             // advised to use the bi-quadratic curve if sufficient manufacturer data is available.
   13974      709084 :             if (state.dataCurveManager->PerfCurve(thisDXCoil.MSEIRFTemp(1))->numDims == 1) {
   13975      638208 :                 EIRTempModFac = CurveValue(state, thisDXCoil.MSEIRFTemp(1), OutdoorDryBulb);
   13976             :             } else {
   13977       70876 :                 EIRTempModFac = CurveValue(state, thisDXCoil.MSEIRFTemp(1), InletAirDryBulbTemp, OutdoorDryBulb);
   13978             :             }
   13979      709084 :             EIRFlowModFac = CurveValue(state, thisDXCoil.MSEIRFFlow(1), AirMassFlowRatioLS);
   13980      709084 :             EIR = 1.0 / thisDXCoil.MSRatedCOP(1) * EIRTempModFac * EIRFlowModFac;
   13981             :             // Calculate modified PartLoadRatio due to defrost (reverse-cycle defrost only)
   13982      709084 :             PLRHeating = min(1.0, (CycRatio + LoadDueToDefrost / TotCapAdj));
   13983      709084 :             PLF = CurveValue(state, thisDXCoil.MSPLFFPLR(1), PLRHeating); // Calculate part-load factor
   13984      709084 :             if (fanOp == HVAC::FanOp::Cycling && CycRatio == 1.0 && PLF != 1.0) {
   13985           0 :                 if (thisDXCoil.PLFErrIndex == 0) {
   13986           0 :                     ShowWarningMessage(state,
   13987           0 :                                        format("The PLF curve value for DX heating coil {} ={:.2R} for part-load ratio = 1", thisDXCoil.Name, PLF));
   13988           0 :                     ShowContinueError(state, "PLF curve value must be = 1.0 and has been reset to 1.0. Simulation is continuing.");
   13989           0 :                     ShowContinueErrorTimeStamp(state, "");
   13990             :                 }
   13991           0 :                 ShowRecurringWarningErrorAtEnd(
   13992           0 :                     state, thisDXCoil.Name + "\": DX heating coil PLF curve value <> 1.0 warning continues...", thisDXCoil.PLFErrIndex, PLF, PLF);
   13993           0 :                 PLF = 1.0;
   13994             :             }
   13995             : 
   13996      709084 :             if (PLF < 0.7) {
   13997           0 :                 if (thisDXCoil.PLRErrIndex == 0) {
   13998           0 :                     ShowWarningMessage(
   13999             :                         state,
   14000           0 :                         format("The PLF curve value for DX heating coil {} ={:.2R} for part-load ratio ={:.2R}", thisDXCoil.Name, PLF, PLRHeating));
   14001           0 :                     ShowContinueError(state, "PLF curve values must be >= 0.7. PLF has been reset to 0.7 and simulation is continuing.");
   14002           0 :                     ShowContinueError(state, "Check the IO reference manual for PLF curve guidance [Coil:Heating:DX:SingleSpeed].");
   14003           0 :                     ShowContinueErrorTimeStamp(state, "");
   14004             :                 }
   14005           0 :                 ShowRecurringWarningErrorAtEnd(state, "DX heating coil PLF curve < 0.7 warning continues... ", thisDXCoil.PLRErrIndex, PLF, PLF);
   14006           0 :                 PLF = 0.7;
   14007             :             }
   14008             : 
   14009      709084 :             thisDXCoil.HeatingCoilRuntimeFraction = (PLRHeating / PLF);
   14010      709084 :             if (thisDXCoil.HeatingCoilRuntimeFraction > 1.0 && std::abs(thisDXCoil.HeatingCoilRuntimeFraction - 1.0) > 0.001) {
   14011           0 :                 if (thisDXCoil.ErrIndex4 == 0) {
   14012           0 :                     ShowWarningMessage(state,
   14013           0 :                                        format("The runtime fraction for DX heating coil {} exceeded 1.0. [{:.4R}].",
   14014           0 :                                               thisDXCoil.Name,
   14015           0 :                                               thisDXCoil.HeatingCoilRuntimeFraction));
   14016           0 :                     ShowContinueError(state, "Runtime fraction is set to 1.0 and the simulation continues...");
   14017           0 :                     ShowContinueError(state, "Check the IO reference manual for PLF curve guidance [Coil:Heating:DX:SingleSpeed].");
   14018           0 :                     ShowContinueErrorTimeStamp(state, "");
   14019             :                 }
   14020           0 :                 ShowRecurringWarningErrorAtEnd(state,
   14021           0 :                                                thisDXCoil.Name + ", DX heating coil runtime fraction > 1.0 warning continues...",
   14022           0 :                                                thisDXCoil.ErrIndex4,
   14023           0 :                                                thisDXCoil.HeatingCoilRuntimeFraction,
   14024           0 :                                                thisDXCoil.HeatingCoilRuntimeFraction);
   14025           0 :                 thisDXCoil.HeatingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   14026      709084 :             } else if (thisDXCoil.HeatingCoilRuntimeFraction > 1.0) {
   14027           0 :                 thisDXCoil.HeatingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   14028             :             }
   14029             :             // if cycling fan, send coil part-load fraction to on/off fan via HVACDataGlobals
   14030      709084 :             if (fanOp == HVAC::FanOp::Cycling) state.dataHVACGlobal->OnOffFanPartLoadFraction = PLF;
   14031      709084 :             thisDXCoil.ElecHeatingPower = TotCap * EIR * thisDXCoil.HeatingCoilRuntimeFraction * InputPowerMultiplier;
   14032             : 
   14033             :             // Calculate crankcase heater power using the runtime fraction for this DX heating coil only if there is no companion DX coil.
   14034             :             // Else use the largest runtime fraction of this DX heating coil and the companion DX cooling coil.
   14035             : 
   14036      709084 :             if (thisDXCoil.CompanionUpstreamDXCoil == 0) {
   14037      352687 :                 thisDXCoil.CrankcaseHeaterPower = CrankcaseHeatingPower * (1.0 - thisDXCoil.HeatingCoilRuntimeFraction);
   14038             :             } else {
   14039      356397 :                 thisDXCoil.CrankcaseHeaterPower =
   14040      356397 :                     CrankcaseHeatingPower * (1.0 - max(thisDXCoil.HeatingCoilRuntimeFraction,
   14041      356397 :                                                        state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).CoolingCoilRuntimeFraction));
   14042             :             }
   14043             : 
   14044      709084 :             thisDXCoil.TotalHeatingEnergyRate = AirMassFlow * (FullLoadOutAirEnth - InletAirEnthalpy) * CycRatio;
   14045      709084 :             if (fanOp == HVAC::FanOp::Continuous) {
   14046      590415 :                 OutletAirEnthalpy = InletAirEnthalpy + thisDXCoil.TotalHeatingEnergyRate / thisDXCoil.InletAirMassFlowRate;
   14047      590415 :                 OutletAirTemp = PsyTdbFnHW(OutletAirEnthalpy, OutletAirHumRat);
   14048             :             }
   14049      709084 :             if (thisDXCoil.MSHPHeatRecActive || thisDXCoil.FuelType != Constant::eFuel::Electricity) {
   14050           0 :                 if (thisDXCoil.MSWasteHeat(SpeedNum) == 0) {
   14051           0 :                     thisDXCoil.MSFuelWasteHeat = thisDXCoil.MSWasteHeatFrac(SpeedNum) * thisDXCoil.ElecHeatingPower;
   14052             :                 } else {
   14053           0 :                     thisDXCoil.MSFuelWasteHeat = CurveValue(state, thisDXCoil.MSWasteHeat(SpeedNum), OutdoorDryBulb, InletAirDryBulbTemp) *
   14054           0 :                                                  thisDXCoil.MSWasteHeatFrac(SpeedNum) * thisDXCoil.ElecHeatingPower;
   14055             :                 }
   14056           0 :                 if (thisDXCoil.MSHPHeatRecActive) {
   14057           0 :                     MSHPWasteHeat = thisDXCoil.MSFuelWasteHeat;
   14058             :                 }
   14059             :             }
   14060      709084 :             if (thisDXCoil.FuelType != Constant::eFuel::Electricity) {
   14061             : 
   14062           0 :                 thisDXCoil.FuelUsed = thisDXCoil.ElecHeatingPower;
   14063           0 :                 thisDXCoil.ElecHeatingPower = 0.0;
   14064             :             }
   14065             :             // Adjust defrost power to correct for DOE-2 bug where defrost power is constant regardless of compressor runtime fraction
   14066             :             // Defrosts happen based on compressor run time (frost buildup on outdoor coil), not total elapsed time.
   14067      709084 :             thisDXCoil.DefrostPower *= thisDXCoil.HeatingCoilRuntimeFraction;
   14068             : 
   14069      709084 :             thisDXCoil.OutletAirTemp = OutletAirTemp;
   14070      709084 :             thisDXCoil.OutletAirHumRat = OutletAirHumRat;
   14071      709084 :             thisDXCoil.OutletAirEnthalpy = OutletAirEnthalpy;
   14072             :         }
   14073             : 
   14074             :     } else {
   14075             : 
   14076             :         // DX coil is off; just pass through conditions
   14077     5844749 :         thisDXCoil.OutletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   14078     5844749 :         thisDXCoil.OutletAirHumRat = thisDXCoil.InletAirHumRat;
   14079     5844749 :         thisDXCoil.OutletAirTemp = thisDXCoil.InletAirTemp;
   14080             : 
   14081     5844749 :         thisDXCoil.ElecHeatingPower = 0.0;
   14082     5844749 :         thisDXCoil.FuelUsed = 0.0;
   14083     5844749 :         thisDXCoil.TotalHeatingEnergyRate = 0.0;
   14084     5844749 :         thisDXCoil.DefrostPower = 0.0;
   14085             : 
   14086             :         // Calculate crankcase heater power using the runtime fraction for this DX heating coil (here DXHeatingCoilRTF=0) if
   14087             :         // there is no companion DX coil, or the runtime fraction of the companion DX cooling coil (here DXCoolingCoilRTF>=0).
   14088     5844749 :         if (thisDXCoil.CompanionUpstreamDXCoil == 0) {
   14089     2457297 :             thisDXCoil.CrankcaseHeaterPower = CrankcaseHeatingPower;
   14090             :         } else {
   14091     3387452 :             thisDXCoil.CrankcaseHeaterPower =
   14092     3387452 :                 CrankcaseHeatingPower * (1.0 - state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).CoolingCoilRuntimeFraction);
   14093             :         }
   14094             : 
   14095             :     } // end of on/off if - else
   14096             : 
   14097     6858982 :     state.dataDXCoils->DXCoilOutletTemp(DXCoilNum) = thisDXCoil.OutletAirTemp;
   14098     6858982 :     state.dataDXCoils->DXCoilOutletHumRat(DXCoilNum) = thisDXCoil.OutletAirHumRat;
   14099     6858982 :     thisDXCoil.PartLoadRatio = PLRHeating;
   14100     6858982 :     state.dataDXCoils->DXCoilFanOp(DXCoilNum) = fanOp;
   14101     6858982 :     state.dataDXCoils->DXCoilPartLoadRatio(DXCoilNum) = PLRHeating;
   14102     6858982 :     thisDXCoil.MSSpeedNumLS = SpeedNumLS;
   14103     6858982 :     thisDXCoil.MSSpeedNumHS = SpeedNumHS;
   14104     6858982 :     thisDXCoil.MSSpeedRatio = SpeedRatio;
   14105     6858982 :     thisDXCoil.MSCycRatio = CycRatio;
   14106             : 
   14107             :     // set outlet node conditions
   14108     6858982 :     int airOutletNode = thisDXCoil.AirOutNode;
   14109     6858982 :     state.dataLoopNodes->Node(airOutletNode).Temp = thisDXCoil.OutletAirTemp;
   14110     6858982 :     state.dataLoopNodes->Node(airOutletNode).HumRat = thisDXCoil.OutletAirHumRat;
   14111             : 
   14112             :     // calc secondary coil if specified
   14113     6858982 :     if (thisDXCoil.IsSecondaryDXCoilInZone) {
   14114           0 :         CalcSecondaryDXCoils(state, DXCoilNum);
   14115             :     }
   14116     6858982 : }
   14117             : 
   14118    63535486 : void UpdateDXCoil(EnergyPlusData &state, int const DXCoilNum) // number of the current fan coil unit being simulated
   14119             : {
   14120             : 
   14121             :     // SUBROUTINE INFORMATION:
   14122             :     //       AUTHOR         Fred Buhl
   14123             :     //       DATE WRITTEN   May 2000
   14124             : 
   14125             :     // PURPOSE OF THIS SUBROUTINE:
   14126             :     // This subroutine is for passing results to the outlet air node.
   14127             : 
   14128             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   14129             :     int AirOutletNode; // air outlet node number
   14130             :     int AirInletNode;  // air inlet node number
   14131             : 
   14132    63535486 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   14133             : 
   14134    63535486 :     AirOutletNode = thisDXCoil.AirOutNode;
   14135    63535486 :     AirInletNode = thisDXCoil.AirInNode;
   14136             :     // changed outputs
   14137    63535486 :     state.dataLoopNodes->Node(AirOutletNode).Enthalpy = thisDXCoil.OutletAirEnthalpy;
   14138    63535486 :     state.dataLoopNodes->Node(AirOutletNode).Temp = thisDXCoil.OutletAirTemp;
   14139    63535486 :     state.dataLoopNodes->Node(AirOutletNode).HumRat = thisDXCoil.OutletAirHumRat;
   14140    63535486 :     state.dataLoopNodes->Node(AirOutletNode).MassFlowRate = thisDXCoil.InletAirMassFlowRate;
   14141             :     // pass through outputs
   14142    63535486 :     state.dataLoopNodes->Node(AirOutletNode).Quality = state.dataLoopNodes->Node(AirInletNode).Quality;
   14143    63535486 :     state.dataLoopNodes->Node(AirOutletNode).Press = state.dataLoopNodes->Node(AirInletNode).Press;
   14144    63535486 :     state.dataLoopNodes->Node(AirOutletNode).MassFlowRateMin = state.dataLoopNodes->Node(AirInletNode).MassFlowRateMin;
   14145    63535486 :     state.dataLoopNodes->Node(AirOutletNode).MassFlowRateMax = state.dataLoopNodes->Node(AirInletNode).MassFlowRateMax;
   14146    63535486 :     state.dataLoopNodes->Node(AirOutletNode).MassFlowRateMinAvail = state.dataLoopNodes->Node(AirInletNode).MassFlowRateMinAvail;
   14147    63535486 :     state.dataLoopNodes->Node(AirOutletNode).MassFlowRateMaxAvail = state.dataLoopNodes->Node(AirInletNode).MassFlowRateMaxAvail;
   14148             : 
   14149    63535486 :     if (state.dataContaminantBalance->Contaminant.CO2Simulation) {
   14150     1314605 :         state.dataLoopNodes->Node(AirOutletNode).CO2 = state.dataLoopNodes->Node(AirInletNode).CO2;
   14151             :     }
   14152    63535486 :     if (state.dataContaminantBalance->Contaminant.GenericContamSimulation) {
   14153      173539 :         state.dataLoopNodes->Node(AirOutletNode).GenContam = state.dataLoopNodes->Node(AirInletNode).GenContam;
   14154             :     }
   14155    63535486 : }
   14156             : 
   14157    63535486 : void ReportDXCoil(EnergyPlusData &state, int const DXCoilNum) // number of the current fan coil unit being simulated
   14158             : {
   14159             : 
   14160             :     // SUBROUTINE INFORMATION:
   14161             :     //       AUTHOR         Fred Buhl
   14162             :     //       DATE WRITTEN   May 2000
   14163             :     //       MODIFIED       Richard Raustad/Don Shirey Oct 2001, Feb 2004
   14164             :     //                      Feb 2005 M. J. Witte, GARD Analytics, Inc.
   14165             :     //                        Always update evap value to support new coil type COIL:DX:MultiMode:CoolingEmpirical:
   14166             :     //                      Lixing Gu. Jan. 5, 2007, pass information to the AirflowNetwork model
   14167             : 
   14168             :     // PURPOSE OF THIS SUBROUTINE:
   14169             :     // Fills some of the report variables for the DX coils
   14170             : 
   14171             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   14172             : 
   14173    63535486 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   14174             : 
   14175    63535486 :     if (thisDXCoil.reportCoilFinalSizes) {
   14176    16840723 :         if (!state.dataGlobal->WarmupFlag && !state.dataGlobal->DoingHVACSizingSimulations && !state.dataGlobal->DoingSizing) {
   14177         971 :             Real64 ratedSensCap(0.0);
   14178         971 :             ratedSensCap = thisDXCoil.RatedTotCap(1) * thisDXCoil.RatedSHR(1);
   14179         971 :             state.dataRptCoilSelection->coilSelectionReportObj->setCoilFinalSizes(
   14180         971 :                 state, thisDXCoil.Name, thisDXCoil.DXCoilType, thisDXCoil.RatedTotCap(1), ratedSensCap, thisDXCoil.RatedAirVolFlowRate(1), -999.0);
   14181         971 :             thisDXCoil.reportCoilFinalSizes = false;
   14182             :         }
   14183             :     }
   14184             : 
   14185    63535486 :     Real64 ReportingConstant = state.dataHVACGlobal->TimeStepSysSec;
   14186             : 
   14187    63535486 :     switch (thisDXCoil.DXCoilType_Num) {
   14188     8275125 :     case HVAC::CoilDX_HeatingEmpirical:
   14189             :     case HVAC::CoilVRF_Heating:
   14190             :     case HVAC::CoilVRF_FluidTCtrl_Heating: {
   14191     8275125 :         thisDXCoil.TotalHeatingEnergy = thisDXCoil.TotalHeatingEnergyRate * ReportingConstant;
   14192     8275125 :         thisDXCoil.ElecHeatingConsumption = thisDXCoil.ElecHeatingPower * ReportingConstant;
   14193     8275125 :         thisDXCoil.DefrostConsumption = thisDXCoil.DefrostPower * ReportingConstant;
   14194     8275125 :         thisDXCoil.CrankcaseHeaterConsumption = thisDXCoil.CrankcaseHeaterPower * ReportingConstant;
   14195     8275125 :         state.dataHVACGlobal->DXElecHeatingPower = thisDXCoil.ElecHeatingPower + thisDXCoil.CrankcaseHeaterPower;
   14196     8275125 :         state.dataHVACGlobal->DefrostElecPower = thisDXCoil.DefrostPower;
   14197     8275125 :     } break;
   14198     6858976 :     case HVAC::CoilDX_MultiSpeedHeating: {
   14199     6858976 :         thisDXCoil.TotalHeatingEnergy = thisDXCoil.TotalHeatingEnergyRate * ReportingConstant;
   14200     6858976 :         if (thisDXCoil.FuelType == Constant::eFuel::Electricity) {
   14201     6219724 :             thisDXCoil.ElecHeatingConsumption = thisDXCoil.ElecHeatingPower * ReportingConstant;
   14202             :         } else {
   14203      639252 :             thisDXCoil.FuelConsumed = thisDXCoil.FuelUsed * ReportingConstant;
   14204             :         }
   14205     6858976 :         thisDXCoil.DefrostConsumption = thisDXCoil.DefrostPower * ReportingConstant;
   14206     6858976 :         thisDXCoil.CrankcaseHeaterConsumption = thisDXCoil.CrankcaseHeaterPower * ReportingConstant;
   14207     6858976 :         state.dataHVACGlobal->DXElecHeatingPower = thisDXCoil.ElecHeatingPower + thisDXCoil.CrankcaseHeaterPower;
   14208     6858976 :         state.dataHVACGlobal->DefrostElecPower = thisDXCoil.DefrostPower;
   14209     6858976 :     } break;
   14210     6868303 :     case HVAC::CoilDX_MultiSpeedCooling: {
   14211     6868303 :         thisDXCoil.TotalCoolingEnergy = thisDXCoil.TotalCoolingEnergyRate * ReportingConstant;
   14212     6868303 :         thisDXCoil.SensCoolingEnergy = thisDXCoil.SensCoolingEnergyRate * ReportingConstant;
   14213     6868303 :         thisDXCoil.LatCoolingEnergy = thisDXCoil.TotalCoolingEnergy - thisDXCoil.SensCoolingEnergy;
   14214     6868303 :         thisDXCoil.CrankcaseHeaterConsumption = thisDXCoil.CrankcaseHeaterPower * ReportingConstant;
   14215     6868303 :         state.dataHVACGlobal->DXElecCoolingPower = thisDXCoil.ElecCoolingPower;
   14216     6868303 :         thisDXCoil.EvapCondPumpElecConsumption = thisDXCoil.EvapCondPumpElecPower * ReportingConstant;
   14217     6868303 :         thisDXCoil.EvapWaterConsump = thisDXCoil.EvapWaterConsumpRate * ReportingConstant;
   14218     6868303 :         if (thisDXCoil.FuelType == Constant::eFuel::Electricity) {
   14219     5611681 :             thisDXCoil.ElecCoolingConsumption = thisDXCoil.ElecCoolingPower * ReportingConstant;
   14220             :         } else {
   14221     1256622 :             thisDXCoil.FuelConsumed = thisDXCoil.FuelUsed * ReportingConstant;
   14222             :         }
   14223     6868303 :         if (any_eq(thisDXCoil.CondenserType, DataHeatBalance::RefrigCondenserType::Evap)) {
   14224           0 :             thisDXCoil.BasinHeaterConsumption = thisDXCoil.BasinHeaterPower * ReportingConstant;
   14225             :         }
   14226     6868303 :     } break;
   14227      631844 :     case HVAC::CoilDX_HeatPumpWaterHeaterPumped:
   14228             :     case HVAC::CoilDX_HeatPumpWaterHeaterWrapped: {
   14229             :         // water heating energy for HP water heater DX Coil condenser
   14230      631844 :         thisDXCoil.TotalHeatingEnergy = thisDXCoil.TotalHeatingEnergyRate * ReportingConstant;
   14231             :         // water heating power for HP water heater
   14232      631844 :         thisDXCoil.ElecWaterHeatingConsumption = thisDXCoil.ElecWaterHeatingPower * ReportingConstant;
   14233             :         // other usual DX cooling coil outputs
   14234      631844 :         thisDXCoil.TotalCoolingEnergy = thisDXCoil.TotalCoolingEnergyRate * ReportingConstant;
   14235      631844 :         thisDXCoil.SensCoolingEnergy = thisDXCoil.SensCoolingEnergyRate * ReportingConstant;
   14236      631844 :         thisDXCoil.LatCoolingEnergy = thisDXCoil.TotalCoolingEnergy - thisDXCoil.SensCoolingEnergy;
   14237      631844 :         thisDXCoil.ElecCoolingConsumption = thisDXCoil.ElecCoolingPower * ReportingConstant;
   14238      631844 :         thisDXCoil.CrankcaseHeaterConsumption = thisDXCoil.CrankcaseHeaterPower * ReportingConstant;
   14239             :         // DXElecCoolingPower global is only used for air-to-air cooling and heating coils
   14240      631844 :         state.dataHVACGlobal->DXElecCoolingPower = 0.0;
   14241      631844 :     } break;
   14242    40901238 :     default: {
   14243    40901238 :         thisDXCoil.TotalCoolingEnergy = thisDXCoil.TotalCoolingEnergyRate * ReportingConstant;
   14244    40901238 :         thisDXCoil.SensCoolingEnergy = thisDXCoil.SensCoolingEnergyRate * ReportingConstant;
   14245    40901238 :         thisDXCoil.LatCoolingEnergy = thisDXCoil.TotalCoolingEnergy - thisDXCoil.SensCoolingEnergy;
   14246    40901238 :         thisDXCoil.ElecCoolingConsumption = thisDXCoil.ElecCoolingPower * ReportingConstant;
   14247    40901238 :         thisDXCoil.CrankcaseHeaterConsumption = thisDXCoil.CrankcaseHeaterPower * ReportingConstant;
   14248    40901238 :         state.dataHVACGlobal->DXElecCoolingPower = thisDXCoil.ElecCoolingPower;
   14249    40901238 :         thisDXCoil.EvapCondPumpElecConsumption = thisDXCoil.EvapCondPumpElecPower * ReportingConstant;
   14250    40901238 :         thisDXCoil.EvapWaterConsump = thisDXCoil.EvapWaterConsumpRate * ReportingConstant;
   14251    40901238 :         if (any_eq(thisDXCoil.CondenserType, DataHeatBalance::RefrigCondenserType::Evap)) {
   14252      122565 :             thisDXCoil.BasinHeaterConsumption = thisDXCoil.BasinHeaterPower * ReportingConstant;
   14253             :         }
   14254    40901238 :     } break;
   14255             :     }
   14256             : 
   14257    63535486 :     if (thisDXCoil.CondensateCollectMode == CondensateCollectAction::ToTank) {
   14258             :         // calculate and report condensation rates  (how much water extracted from the air stream)
   14259             :         // water flow of water in m3/s for water system interactions
   14260             :         //  put here to catch all types of DX coils
   14261           0 :         Real64 Tavg = (thisDXCoil.InletAirTemp + thisDXCoil.OutletAirTemp) / 2.0;
   14262             :         // CR9155 Remove specific humidity calculations
   14263             :         //  mdot * del HumRat / rho water
   14264           0 :         thisDXCoil.CondensateVdot =
   14265           0 :             max(0.0, (thisDXCoil.InletAirMassFlowRate * (thisDXCoil.InletAirHumRat - thisDXCoil.OutletAirHumRat) / Psychrometrics::RhoH2O(Tavg)));
   14266           0 :         thisDXCoil.CondensateVol = thisDXCoil.CondensateVdot * ReportingConstant;
   14267             : 
   14268           0 :         state.dataWaterData->WaterStorage(thisDXCoil.CondensateTankID).VdotAvailSupply(thisDXCoil.CondensateTankSupplyARRID) =
   14269           0 :             thisDXCoil.CondensateVdot;
   14270           0 :         state.dataWaterData->WaterStorage(thisDXCoil.CondensateTankID).TwaterSupply(thisDXCoil.CondensateTankSupplyARRID) = thisDXCoil.OutletAirTemp;
   14271             :     }
   14272             : 
   14273    63535486 :     state.dataAirLoop->LoopDXCoilRTF = max(thisDXCoil.CoolingCoilRuntimeFraction, thisDXCoil.HeatingCoilRuntimeFraction);
   14274    63535486 :     if (thisDXCoil.AirLoopNum > 0) {
   14275     4710328 :         state.dataAirLoop->AirLoopAFNInfo(thisDXCoil.AirLoopNum).AFNLoopDXCoilRTF =
   14276     4710328 :             max(thisDXCoil.CoolingCoilRuntimeFraction, thisDXCoil.HeatingCoilRuntimeFraction);
   14277             :     }
   14278    63535486 : }
   14279             : 
   14280          66 : void CalcTwoSpeedDXCoilStandardRating(EnergyPlusData &state, int const DXCoilNum)
   14281             : {
   14282             :     // SUBROUTINE INFORMATION:
   14283             :     //       AUTHOR         B. Griffith, (Derived from CalcDXCoilStandardRating by Bereket Nigusse & Chandan Sharma)
   14284             :     //       DATE WRITTEN   July 2012
   14285             : 
   14286             :     // PURPOSE OF THIS SUBROUTINE:
   14287             :     // Calculate the following
   14288             :     //                 (1) Standard Rated (net) Cooling Capacity
   14289             :     //                 (2) Energy Efficiency Ratio (EER),
   14290             :     //                 (3) Integrated Energy Efficiency Ratio (IEER)
   14291             : 
   14292             :     // REFERENCES:
   14293             :     // ANSI/AHRI Standard 340/360-2007, Performance Rating of Commercial and Industrial Unitary Air-Conditioning and
   14294             :     //  Heat Pump Equipment, Air-Conditioning, Heating, and Refrigeration Institute, Arlington VA.
   14295             : 
   14296             :     // Using/Aliasing
   14297             :     using Curve::CurveValue;
   14298             :     using namespace OutputReportPredefined;
   14299             : 
   14300             :     // SUBROUTINE PARAMETER DEFINITIONS:
   14301             :     // AHRI Standard 340/360-2007 Performance Rating of Commercial and Industrial Unitary Air-Conditioning and Heat Pump Equipment
   14302          66 :     Real64 constexpr CoolingCoilInletAirWetBulbTempRated(19.4); // 19.44C (67F)
   14303          66 :     Real64 constexpr CoolingCoilInletAirDryBulbTempRated(26.7);
   14304          66 :     Real64 constexpr OutdoorUnitInletAirDryBulbTempRated(35.0); // 35.00C (95F)
   14305          66 :     static Array1D<Real64> const OutdoorUnitInletAirDryBulbTempPLTestPoint(3, {27.5, 20.0, 18.3});
   14306          66 :     static Array1D<Real64> const NetCapacityFactorPLTestPoint(3, {0.75, 0.50, 0.25});
   14307          66 :     Real64 constexpr ConvFromSIToIP(3.412141633); // Conversion from SI to IP [3.412 Btu/hr-W]
   14308             : 
   14309          66 :     Real64 constexpr AirMassFlowRatioRated(1.0); // AHRI test is at the design flow rate
   14310             :     // and hence AirMassFlowRatio is 1.0
   14311             : 
   14312          66 :     Real64 constexpr DefaultFanPowerPerEvapAirFlowRate(773.3);      // 365 W/1000 scfm or 773.3 W/(m3/s). The AHRI standard
   14313          66 :     Real64 constexpr DefaultFanPowerPerEvapAirFlowRateSEER2(934.4); // 441 W/1000 scfm or 934.4 W/(m3/s). The AHRI standard
   14314             :     // specifies a nominal/default fan electric power consumption per rated air
   14315             :     // volume flow rate to account for indoor fan electric power consumption
   14316             :     // when the standard tests are conducted on units that do not have an
   14317             :     // indoor air circulating fan. Used if user doesn't enter a specific value.
   14318             : 
   14319             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   14320             :     static constexpr std::string_view RoutineName("CalcTwoSpeedDXCoilStandardRating");
   14321             : 
   14322          66 :     auto &NetCoolingCapRated = state.dataDXCoils->NetCoolingCapRated;
   14323          66 :     auto &EER = state.dataDXCoils->EER;
   14324          66 :     auto &IEER = state.dataDXCoils->IEER;
   14325          66 :     auto &TotCapTempModFac = state.dataDXCoils->TotCapTempModFac;
   14326          66 :     auto &TotCapFlowModFac = state.dataDXCoils->TotCapFlowModFac;
   14327          66 :     auto &EIRTempModFac = state.dataDXCoils->EIRTempModFac;
   14328          66 :     auto &EIRFlowModFac = state.dataDXCoils->EIRFlowModFac;
   14329          66 :     auto &TempDryBulb_Leaving_Apoint = state.dataDXCoils->TempDryBulb_Leaving_Apoint;
   14330             : 
   14331          66 :     constexpr Real64 AccuracyTolerance(0.2); // tolerance in AHRI 340/360 Table 6 note 1
   14332          66 :     constexpr int MaximumIterations(1000);
   14333             :     Real64 EIR;
   14334             :     Real64 TotalElecPowerRated;
   14335          66 :     Array1D<Real64> EER_TestPoint_SI(4);      // 1 = A, 2 = B, 3= C, 4= D
   14336          66 :     Array1D<Real64> EER_TestPoint_IP(4);      // 1 = A, 2 = B, 3= C, 4= D
   14337          66 :     Array1D<Real64> NetCapacity_TestPoint(4); // 1 = A, 2 = B, 3= C, 4= D
   14338          66 :     Array1D<Real64> NetPower_TestPoint(4);    // 1 = A, 2 = B, 3= C, 4= D
   14339          66 :     Array1D<Real64> SupAirMdot_TestPoint(4);  // 1 = A, 2 = B, 3= C, 4= D
   14340             : 
   14341             :     Real64 HighSpeedNetCoolingCap;
   14342             :     Real64 LowSpeedNetCoolingCap;
   14343             : 
   14344             :     Real64 PartLoadAirMassFlowRate;
   14345             :     Real64 AirMassFlowRatio;
   14346             :     int SolverFlag;
   14347             :     Real64 EIR_HighSpeed;
   14348             :     Real64 EIR_LowSpeed;
   14349             :     int FanInletNode;
   14350             :     int FanOutletNode;
   14351             :     int Iter;
   14352             :     Real64 ExternalStatic;
   14353             :     Real64 FanStaticPressureRise;
   14354             :     Real64 FanHeatCorrection;
   14355             :     Real64 FanPowerCorrection;
   14356          66 :     Real64 FanPowerPerEvapAirFlowRate = 0.0;
   14357             :     Real64 FanPowerPerEvapAirFlowRateSEER2;
   14358             :     Real64 SpeedRatio;
   14359             :     Real64 CycRatio;
   14360             :     Real64 TargetNetCapacity;
   14361             :     Real64 SupplyAirHumRat;
   14362             :     Real64 SupplyAirRho;
   14363             :     Real64 SupplyAirVolFlowRate;
   14364             :     Real64 HighSpeedTotCoolingCap;
   14365             :     Real64 LowSpeedTotCoolingCap;
   14366             :     Real64 TotCoolingCap;
   14367             :     Real64 NetCoolingCap;
   14368             :     Real64 PLF;
   14369             :     Real64 RunTimeFraction;
   14370             :     Real64 LowerBoundMassFlowRate;
   14371             :     int PartLoadTestPoint;
   14372             :     int countStaticInputs;
   14373             :     int index;
   14374             : 
   14375             :     // Formats
   14376             :     static constexpr std::string_view Header(
   14377             :         "! <VAV DX Cooling Coil Standard Rating Information>, DX Coil Type, DX Coil Name, Fan Type, Fan Name, Standard Net Cooling Capacity "
   14378             :         "{{W}}, Standard Net Cooling Capacity {{Btu/h}}, IEER {{Btu/W-h}}, COP 100% Capacity {{W/W}}, COP 75% Capacity {{W/W}}, COP 50% Capacity "
   14379             :         "{{W/W}}, COP 25% Capacity {{W/W}}, EER 100% Capacity {{Btu/W-h}}, EER 75% Capacity {{Btu/W-h}}, EER 50% Capacity {{Btu/W-h}}, EER 25% "
   14380             :         "Capacity {{Btu/W-h}}, Supply Air Flow 100% {{kg/s}}, Supply Air Flow 75% {{kg/s}},Supply Air Flow 50% {{kg/s}},Supply Air Flow 25% "
   14381             :         "{{kg/s}}\n");
   14382             : 
   14383             :     static constexpr std::string_view Format_891{
   14384             :         " VAV DX Cooling Coil Standard Rating Information, "
   14385             :         "{},{},{},{},{:.2R},{:.2R},{:.2R},{:.2R},{:.2R},{:.2R},{:.2R},{:.2R},{:.2R},{:.2R},{:.2R},{:.4R},{:.4R},{:.4R},{:.4R},\n"};
   14386             : 
   14387          66 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   14388             : 
   14389             :     // Get fan index and name if not already available
   14390          66 :     if (thisDXCoil.SupplyFanIndex == 0)
   14391          66 :         GetFanIndexForTwoSpeedCoil(state, DXCoilNum, thisDXCoil.SupplyFanIndex, thisDXCoil.SupplyFanName, thisDXCoil.supplyFanType);
   14392          66 :     if (thisDXCoil.SupplyFanIndex == 0) { // didn't find VAV fan, do not rate this coil
   14393          14 :         thisDXCoil.RateWithInternalStaticAndFanObject = false;
   14394          28 :         ShowWarningError(state,
   14395          28 :                          format("CalcTwoSpeedDXCoilStandardRating: Did not find an appropriate fan associated with DX coil named = \"{}\". Standard "
   14396             :                                 "Ratings will not be calculated.",
   14397          14 :                                 thisDXCoil.Name));
   14398          14 :         return;
   14399             :     }
   14400          52 :     bool saveTurnFansOn = state.dataHVACGlobal->TurnFansOn;
   14401          52 :     bool saveTurnFansOff = state.dataHVACGlobal->TurnFansOff;
   14402          52 :     state.dataHVACGlobal->TurnFansOn = true; // enable fans, will override fan availability schedule if needed
   14403          52 :     state.dataHVACGlobal->TurnFansOff = false;
   14404             : 
   14405             :     // Calculate the Indoor fan electric power consumption.  The electric power consumption is estimated
   14406             :     // using either user supplied or AHRI default value for fan power per air volume flow rate
   14407          52 :     if (thisDXCoil.RateWithInternalStaticAndFanObject) {
   14408             : 
   14409          29 :         TotCapFlowModFac = CurveValue(state, thisDXCoil.CCapFFlow(1), AirMassFlowRatioRated);
   14410          29 :         TotCapTempModFac = CurveValue(state, thisDXCoil.CCapFTemp(1), CoolingCoilInletAirWetBulbTempRated, OutdoorUnitInletAirDryBulbTempRated);
   14411         145 :         for (Iter = 1; Iter <= 4; ++Iter) { // iterative solution in the event that net capacity is near a threshold for external static
   14412             :             // Obtain external static pressure from Table 5 in ANSI/AHRI Std. 340/360-2007
   14413         116 :             if (NetCoolingCapRated <= 21000.0) {
   14414          14 :                 ExternalStatic = 50.0;
   14415         102 :             } else if (21000.0 < NetCoolingCapRated && NetCoolingCapRated <= 30800.0) {
   14416           0 :                 ExternalStatic = 60.0;
   14417         102 :             } else if (30800.0 < NetCoolingCapRated && NetCoolingCapRated <= 39300.0) {
   14418           0 :                 ExternalStatic = 70.0;
   14419         102 :             } else if (39300.0 < NetCoolingCapRated && NetCoolingCapRated <= 61500.0) {
   14420          11 :                 ExternalStatic = 90.0;
   14421          91 :             } else if (61500.0 < NetCoolingCapRated && NetCoolingCapRated <= 82100.0) {
   14422           3 :                 ExternalStatic = 100.0;
   14423          88 :             } else if (82100.0 < NetCoolingCapRated && NetCoolingCapRated <= 103000.0) {
   14424           0 :                 ExternalStatic = 110.0;
   14425          88 :             } else if (103000.0 < NetCoolingCapRated && NetCoolingCapRated <= 117000.0) {
   14426           0 :                 ExternalStatic = 140.0;
   14427          88 :             } else if (117000.0 < NetCoolingCapRated && NetCoolingCapRated <= 147000.0) {
   14428          16 :                 ExternalStatic = 160.0;
   14429          72 :             } else if (147000.0 < NetCoolingCapRated) {
   14430          72 :                 ExternalStatic = 190.0;
   14431             :             }
   14432         116 :             FanStaticPressureRise = ExternalStatic + thisDXCoil.InternalStaticPressureDrop;
   14433         116 :             FanInletNode = state.dataFans->fans(thisDXCoil.SupplyFanIndex)->inletNodeNum;
   14434         116 :             FanOutletNode = state.dataFans->fans(thisDXCoil.SupplyFanIndex)->outletNodeNum;
   14435             : 
   14436             :             // set node state variables in preparation for fan model.
   14437         116 :             state.dataLoopNodes->Node(FanInletNode).MassFlowRate = thisDXCoil.RatedAirMassFlowRate(1);
   14438         116 :             state.dataLoopNodes->Node(FanOutletNode).MassFlowRate = thisDXCoil.RatedAirMassFlowRate(1);
   14439         116 :             state.dataLoopNodes->Node(FanInletNode).Temp = CoolingCoilInletAirDryBulbTempRated;
   14440         116 :             state.dataLoopNodes->Node(FanInletNode).HumRat = PsyWFnTdbTwbPb(
   14441         116 :                 state, CoolingCoilInletAirDryBulbTempRated, CoolingCoilInletAirWetBulbTempRated, state.dataEnvrn->OutBaroPress, RoutineName);
   14442         116 :             state.dataLoopNodes->Node(FanInletNode).Enthalpy =
   14443         116 :                 PsyHFnTdbW(CoolingCoilInletAirDryBulbTempRated, state.dataLoopNodes->Node(FanInletNode).HumRat);
   14444         116 :             state.dataFans->fans(thisDXCoil.SupplyFanIndex)->simulate(state, true, _, FanStaticPressureRise);
   14445         116 :             FanPowerCorrection = state.dataFans->fans(thisDXCoil.SupplyFanIndex)->totalPower;
   14446             : 
   14447         116 :             FanHeatCorrection = state.dataLoopNodes->Node(FanInletNode).MassFlowRate *
   14448         116 :                                 (state.dataLoopNodes->Node(FanOutletNode).Enthalpy - state.dataLoopNodes->Node(FanInletNode).Enthalpy);
   14449             : 
   14450         116 :             NetCoolingCapRated = thisDXCoil.RatedTotCap(1) * TotCapTempModFac * TotCapFlowModFac - FanHeatCorrection;
   14451             :         }
   14452             : 
   14453             :     } else {
   14454          23 :         FanPowerPerEvapAirFlowRate = DefaultFanPowerPerEvapAirFlowRate;
   14455          23 :         FanPowerPerEvapAirFlowRateSEER2 = DefaultFanPowerPerEvapAirFlowRateSEER2;
   14456          23 :         FanPowerCorrection = DefaultFanPowerPerEvapAirFlowRate * thisDXCoil.RatedAirVolFlowRate(1);
   14457          23 :         FanHeatCorrection = DefaultFanPowerPerEvapAirFlowRate * thisDXCoil.RatedAirVolFlowRate(1);
   14458          23 :         TotCapFlowModFac = CurveValue(state, thisDXCoil.CCapFFlow(1), AirMassFlowRatioRated);
   14459          23 :         TotCapTempModFac = CurveValue(state, thisDXCoil.CCapFTemp(1), CoolingCoilInletAirWetBulbTempRated, OutdoorUnitInletAirDryBulbTempRated);
   14460          23 :         NetCoolingCapRated = thisDXCoil.RatedTotCap(1) * TotCapTempModFac * TotCapFlowModFac - FanHeatCorrection;
   14461             :     }
   14462             : 
   14463          52 :     SupAirMdot_TestPoint(1) = thisDXCoil.RatedAirMassFlowRate(1);
   14464             : 
   14465             :     // Calculate Energy Efficiency Ratio (EER) at (19.44C WB and 35.0C DB ), ANSI/AHRI Std. 340/360
   14466          52 :     EIRTempModFac = CurveValue(state, thisDXCoil.EIRFTemp(1), CoolingCoilInletAirWetBulbTempRated, OutdoorUnitInletAirDryBulbTempRated);
   14467          52 :     EIRFlowModFac = CurveValue(state, thisDXCoil.EIRFFlow(1), AirMassFlowRatioRated);
   14468          52 :     if (thisDXCoil.RatedCOP(1) > 0.0) {
   14469             :         // RatedCOP <= 0.0 is trapped in GetInput, but keep this as "safety"
   14470          52 :         EIR = EIRTempModFac * EIRFlowModFac / thisDXCoil.RatedCOP(1);
   14471             :     } else {
   14472           0 :         EIR = 0.0;
   14473             :     }
   14474          52 :     TotalElecPowerRated = EIR * (thisDXCoil.RatedTotCap(1) * TotCapTempModFac * TotCapFlowModFac) + FanPowerCorrection;
   14475             : 
   14476          52 :     if (TotalElecPowerRated > 0.0) {
   14477          52 :         EER = NetCoolingCapRated / TotalElecPowerRated;
   14478             :     } else {
   14479           0 :         EER = 0.0;
   14480             :     }
   14481             : 
   14482             :     // IEER - A point 100 % net capacity
   14483          52 :     EER_TestPoint_SI(1) = EER;
   14484          52 :     EER_TestPoint_IP(1) = EER * ConvFromSIToIP;
   14485             : 
   14486             :     // find coil leaving drybulb at point A, with full rated air flow rate.
   14487             :     // init coil
   14488          52 :     thisDXCoil.InletAirMassFlowRate = thisDXCoil.RatedAirMassFlowRate(1);
   14489          52 :     thisDXCoil.InletAirMassFlowRateMax = thisDXCoil.RatedAirMassFlowRate(1);
   14490          52 :     thisDXCoil.InletAirTemp = 26.7;
   14491          52 :     thisDXCoil.InletAirHumRat = PsyWFnTdbTwbPb(state, 26.7, 19.4, state.dataEnvrn->OutBaroPress, RoutineName);
   14492          52 :     thisDXCoil.InletAirEnthalpy = PsyHFnTdbW(26.7, thisDXCoil.InletAirHumRat);
   14493             : 
   14494          52 :     Real64 const heldOutDryBulb = state.dataEnvrn->OutDryBulbTemp;
   14495          52 :     if (thisDXCoil.CondenserInletNodeNum(1) != 0) {
   14496           8 :         state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).Temp = OutdoorUnitInletAirDryBulbTempRated;
   14497             :     } else {
   14498          44 :         state.dataEnvrn->OutDryBulbTemp = OutdoorUnitInletAirDryBulbTempRated;
   14499             :     }
   14500          52 :     SpeedRatio = 1.0;
   14501          52 :     CycRatio = 1.0;
   14502          52 :     CalcMultiSpeedDXCoil(state, DXCoilNum, SpeedRatio, CycRatio, true);
   14503          52 :     TempDryBulb_Leaving_Apoint = state.dataDXCoils->DXCoilOutletTemp(DXCoilNum); // store result
   14504             : 
   14505             :     // IEER - part load test points ***************************************************
   14506         208 :     for (PartLoadTestPoint = 1; PartLoadTestPoint <= 3; ++PartLoadTestPoint) {
   14507             :         // determine minimum unloading capacity fraction at point B conditions.
   14508         156 :         if (thisDXCoil.CondenserInletNodeNum(1) != 0) {
   14509          24 :             state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(1)).Temp = OutdoorUnitInletAirDryBulbTempPLTestPoint(PartLoadTestPoint);
   14510             :         } else {
   14511         132 :             state.dataEnvrn->OutDryBulbTemp = OutdoorUnitInletAirDryBulbTempPLTestPoint(PartLoadTestPoint);
   14512             :         }
   14513             : 
   14514         156 :         TargetNetCapacity = NetCapacityFactorPLTestPoint(PartLoadTestPoint) * NetCoolingCapRated;
   14515             : 
   14516             :         // set up parameters for the solver here
   14517         156 :         Real64 const par3 = OutdoorUnitInletAirDryBulbTempPLTestPoint(PartLoadTestPoint);
   14518         156 :         Real64 par7 = FanPowerPerEvapAirFlowRate;
   14519         156 :         int fanInNode = 0;
   14520         156 :         int fanOutNode = 0;
   14521         156 :         Real64 externalStatic = 0.0;
   14522         156 :         int fanIndex = 0;
   14523         156 :         if (thisDXCoil.RateWithInternalStaticAndFanObject) {
   14524          87 :             par7 = 0.0;
   14525          87 :             fanInNode = FanInletNode;
   14526          87 :             fanOutNode = FanOutletNode;
   14527          87 :             externalStatic = ExternalStatic;
   14528          87 :             fanIndex = thisDXCoil.SupplyFanIndex;
   14529             :         }
   14530             : 
   14531         156 :         LowerBoundMassFlowRate = 0.01 * thisDXCoil.RatedAirMassFlowRate(1);
   14532             : 
   14533             :         // OK, so there are two variables here which are const at compile time.  The question is whether compile time data needs to be
   14534             :         // explicitly captured in the lambda capture block.
   14535             :         // For GCC it currently doesn't mind whether they are captured or not, no warnings.
   14536             :         // On Clang, if you list them, there is a compiler warning.
   14537             :         // On our version of MSVC, if you take them out, the compiler will fail.  On newer versions, I think it's OK.  Should be soon anyway.
   14538             :         // To avoid this, you could pragma away the Clang warning in this section, or tell Clang to hush via compiler flags.  However, to keep things
   14539             :         // really simple, I'm just going to use two local variables and capture them instead of the original data.
   14540             :         // I'm not sure if there are any more of these instances in the codebase.  If so I am going to tag all of them with CONST_LAMBDA_CAPTURE.
   14541         156 :         Real64 dbRated = CoolingCoilInletAirDryBulbTempRated;
   14542         156 :         Real64 wbRated = CoolingCoilInletAirWetBulbTempRated;
   14543             :         auto f = // (AUTO_OK_LAMBDA)
   14544       55472 :             [&state, DXCoilNum, TempDryBulb_Leaving_Apoint, TargetNetCapacity, par3, par7, fanInNode, fanOutNode, externalStatic, dbRated, wbRated](
   14545     1204644 :                 Real64 SupplyAirMassFlowRate) {
   14546             :                 static constexpr std::string_view RoutineName("CalcTwoSpeedDXCoilIEERResidual");
   14547       55316 :                 auto &coil = state.dataDXCoils->DXCoil(DXCoilNum);
   14548       55316 :                 Real64 AirMassFlowRatio = 0.0;
   14549       55316 :                 if (coil.RatedAirMassFlowRate(1) > 0.0) {
   14550       55316 :                     AirMassFlowRatio = SupplyAirMassFlowRate / coil.RatedAirMassFlowRate(1);
   14551             :                 }
   14552       55316 :                 Real64 SupplyAirHumRat = PsyWFnTdbTwbPb(state, dbRated, wbRated, state.dataEnvrn->OutBaroPress, RoutineName);
   14553       55316 :                 Real64 SupplyAirRho = PsyRhoAirFnPbTdbW(state, state.dataEnvrn->OutBaroPress, dbRated, SupplyAirHumRat, RoutineName);
   14554       55316 :                 Real64 SupplyAirVolFlowRate = SupplyAirMassFlowRate / SupplyAirRho;
   14555             : 
   14556             :                 Real64 FanHeatCorrection;
   14557       55316 :                 if (coil.RateWithInternalStaticAndFanObject) {
   14558             :                     // modify external static per AHRI 340/360, Table 6, note 1.
   14559       33034 :                     Real64 FanStaticPressureRise = coil.InternalStaticPressureDrop + (externalStatic * pow_2(AirMassFlowRatio));
   14560       33034 :                     auto &inletNode = state.dataLoopNodes->Node(fanInNode);
   14561       33034 :                     auto &outletNode = state.dataLoopNodes->Node(fanOutNode);
   14562       33034 :                     inletNode.MassFlowRate = SupplyAirMassFlowRate;
   14563       33034 :                     outletNode.MassFlowRate = SupplyAirMassFlowRate;
   14564       33034 :                     inletNode.Temp = dbRated;
   14565       33034 :                     inletNode.HumRat = PsyWFnTdbTwbPb(state, dbRated, wbRated, state.dataEnvrn->OutBaroPress, RoutineName);
   14566       33034 :                     inletNode.Enthalpy = PsyHFnTdbW(dbRated, inletNode.HumRat);
   14567       33034 :                     state.dataFans->fans(coil.SupplyFanIndex)->simulate(state, true, _, FanStaticPressureRise);
   14568       33034 :                     FanHeatCorrection = SupplyAirMassFlowRate * (outletNode.Enthalpy - inletNode.Enthalpy);
   14569             :                 } else {
   14570       22282 :                     FanHeatCorrection = par7 * SupplyAirVolFlowRate;
   14571             :                 }
   14572             : 
   14573       55316 :                 Real64 TotCapFlowModFac = Curve::CurveValue(state, coil.CCapFFlow(1), AirMassFlowRatio);
   14574       55316 :                 Real64 TotCapTempModFac = Curve::CurveValue(state, coil.CCapFTemp(1), wbRated, par3);
   14575       55316 :                 Real64 HighSpeedNetCoolingCap = coil.RatedTotCap(1) * TotCapTempModFac * TotCapFlowModFac - FanHeatCorrection;
   14576             : 
   14577             :                 // TotCapFlowModFac = CurveManager::CurveValue(state, coil.CCapFFlow(1), AirMassFlowRatio);
   14578       55316 :                 TotCapTempModFac = Curve::CurveValue(state, coil.CCapFTemp2, wbRated, par3);
   14579       55316 :                 Real64 LowSpeedNetCoolingCap = coil.RatedTotCap2 * TotCapTempModFac * TotCapFlowModFac - FanHeatCorrection;
   14580             : 
   14581             :                 Real64 SpeedRatio;
   14582             :                 Real64 CycRatio;
   14583       55316 :                 if (LowSpeedNetCoolingCap <= TargetNetCapacity) {
   14584       42199 :                     CycRatio = 1.0;
   14585       42199 :                     SpeedRatio = (TargetNetCapacity - LowSpeedNetCoolingCap) / (HighSpeedNetCoolingCap - LowSpeedNetCoolingCap);
   14586             :                 } else { // minimum unloading limit exceeded for no cycling
   14587       13117 :                     SpeedRatio = 0.0;
   14588       13117 :                     CycRatio = TargetNetCapacity / LowSpeedNetCoolingCap;
   14589             :                 }
   14590             : 
   14591       55316 :                 coil.InletAirMassFlowRate = SupplyAirMassFlowRate;
   14592       55316 :                 CalcMultiSpeedDXCoil(state, DXCoilNum, SpeedRatio, CycRatio, true);
   14593       55316 :                 Real64 OutletAirTemp = state.dataDXCoils->DXCoilOutletTemp(DXCoilNum);
   14594       55316 :                 return TempDryBulb_Leaving_Apoint - OutletAirTemp;
   14595         156 :             };
   14596         156 :         General::SolveRoot(state,
   14597             :                            AccuracyTolerance,
   14598             :                            MaximumIterations,
   14599             :                            SolverFlag,
   14600             :                            PartLoadAirMassFlowRate,
   14601             :                            f,
   14602             :                            LowerBoundMassFlowRate,
   14603         156 :                            thisDXCoil.RatedAirMassFlowRate(1));
   14604             : 
   14605         156 :         if (SolverFlag == -1) {
   14606             : 
   14607           0 :             ShowWarningError(state, "CalcTwoSpeedDXCoilStandardRating: air flow rate solver failed. Iteration limit exceeded ");
   14608             : 
   14609           0 :             SupAirMdot_TestPoint(1 + PartLoadTestPoint) = -999.0;
   14610           0 :             EER_TestPoint_SI(1 + PartLoadTestPoint) = -999.0;
   14611           0 :             EER_TestPoint_IP(1 + PartLoadTestPoint) = -999.0;
   14612           0 :             NetCapacity_TestPoint(1 + PartLoadTestPoint) = -999.0;
   14613           0 :             NetPower_TestPoint(1 + PartLoadTestPoint) = -999.0;
   14614             : 
   14615         156 :         } else if (SolverFlag == -2) {
   14616           0 :             ShowWarningError(state, "CalcTwoSpeedDXCoilStandardRating: air flow rate solver failed. root not bounded ");
   14617             : 
   14618           0 :             SupAirMdot_TestPoint(1 + PartLoadTestPoint) = -999.0;
   14619           0 :             EER_TestPoint_SI(1 + PartLoadTestPoint) = -999.0;
   14620           0 :             EER_TestPoint_IP(1 + PartLoadTestPoint) = -999.0;
   14621           0 :             NetCapacity_TestPoint(1 + PartLoadTestPoint) = -999.0;
   14622           0 :             NetPower_TestPoint(1 + PartLoadTestPoint) = -999.0;
   14623             :         } else {
   14624             :             // now we have the supply air flow rate
   14625         156 :             SupAirMdot_TestPoint(1 + PartLoadTestPoint) = PartLoadAirMassFlowRate;
   14626         156 :             AirMassFlowRatio = PartLoadAirMassFlowRate / thisDXCoil.RatedAirMassFlowRate(1);
   14627         156 :             SupplyAirHumRat = PsyWFnTdbTwbPb(
   14628         156 :                 state, CoolingCoilInletAirDryBulbTempRated, CoolingCoilInletAirWetBulbTempRated, state.dataEnvrn->OutBaroPress, RoutineName);
   14629         156 :             SupplyAirRho = PsyRhoAirFnPbTdbW(state, state.dataEnvrn->OutBaroPress, CoolingCoilInletAirDryBulbTempRated, SupplyAirHumRat, RoutineName);
   14630         156 :             SupplyAirVolFlowRate = PartLoadAirMassFlowRate / SupplyAirRho;
   14631             : 
   14632         156 :             if (thisDXCoil.RateWithInternalStaticAndFanObject) {
   14633          87 :                 FanStaticPressureRise = thisDXCoil.InternalStaticPressureDrop + (ExternalStatic * pow_2(AirMassFlowRatio));
   14634          87 :                 state.dataLoopNodes->Node(FanInletNode).MassFlowRate = PartLoadAirMassFlowRate;
   14635          87 :                 state.dataLoopNodes->Node(FanInletNode).Temp = CoolingCoilInletAirDryBulbTempRated;
   14636          87 :                 state.dataLoopNodes->Node(FanInletNode).HumRat = SupplyAirHumRat;
   14637          87 :                 state.dataLoopNodes->Node(FanInletNode).Enthalpy = PsyHFnTdbW(CoolingCoilInletAirDryBulbTempRated, SupplyAirHumRat);
   14638             : 
   14639          87 :                 state.dataFans->fans(thisDXCoil.SupplyFanIndex)->simulate(state, true, _, FanStaticPressureRise);
   14640          87 :                 FanPowerCorrection = state.dataFans->fans(thisDXCoil.SupplyFanIndex)->totalPower;
   14641             : 
   14642          87 :                 FanHeatCorrection =
   14643          87 :                     PartLoadAirMassFlowRate * (state.dataLoopNodes->Node(FanOutletNode).Enthalpy - state.dataLoopNodes->Node(FanInletNode).Enthalpy);
   14644             : 
   14645             :             } else {
   14646          69 :                 FanPowerCorrection = FanPowerPerEvapAirFlowRate * PartLoadAirMassFlowRate;
   14647          69 :                 FanHeatCorrection = FanPowerPerEvapAirFlowRate * PartLoadAirMassFlowRate;
   14648             :             }
   14649             : 
   14650         156 :             TotCapFlowModFac = CurveValue(state, thisDXCoil.CCapFFlow(1), AirMassFlowRatio);
   14651             :             //    Warn user if curve output goes negative
   14652         156 :             if (TotCapFlowModFac < 0.0) {
   14653           0 :                 if (thisDXCoil.CCapFFlowErrorIndex == 0) {
   14654           0 :                     ShowWarningMessage(state, format("{}{} \"{}\":", RoutineName, thisDXCoil.DXCoilType, thisDXCoil.Name));
   14655           0 :                     ShowContinueError(
   14656             :                         state,
   14657           0 :                         format(" Total Cooling Capacity Modifier curve (function of flow fraction) output is negative ({:.3T}).", TotCapFlowModFac));
   14658           0 :                     ShowContinueError(state, format(" Negative value occurs using an air flow fraction of {:.3T}.", AirMassFlowRatio));
   14659           0 :                     ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
   14660             :                 }
   14661           0 :                 ShowRecurringWarningErrorAtEnd(
   14662             :                     state,
   14663           0 :                     format("{}{}\"{}\": Total Cooling Capacity Modifier curve (function of flow fraction) output is negative warning continues...",
   14664             :                            RoutineName,
   14665           0 :                            thisDXCoil.DXCoilType,
   14666           0 :                            thisDXCoil.Name),
   14667           0 :                     thisDXCoil.CCapFFlowErrorIndex,
   14668             :                     TotCapFlowModFac,
   14669             :                     TotCapFlowModFac);
   14670           0 :                 TotCapFlowModFac = 0.0;
   14671             :             }
   14672             : 
   14673         468 :             TotCapTempModFac = CurveValue(
   14674         156 :                 state, thisDXCoil.CCapFTemp(1), CoolingCoilInletAirWetBulbTempRated, OutdoorUnitInletAirDryBulbTempPLTestPoint(PartLoadTestPoint));
   14675             :             //    Warn user if curve output goes negative
   14676         156 :             if (TotCapTempModFac < 0.0) {
   14677           0 :                 if (thisDXCoil.CCapFTempErrorIndex == 0) {
   14678           0 :                     ShowWarningMessage(state, format("{}{} \"{}\":", RoutineName, thisDXCoil.DXCoilType, thisDXCoil.Name));
   14679           0 :                     ShowContinueError(
   14680             :                         state,
   14681           0 :                         format(" Total Cooling Capacity Modifier curve (function of temperature) output is negative ({:.3T}).", TotCapTempModFac));
   14682           0 :                     ShowContinueError(state,
   14683           0 :                                       format(" Negative value occurs using a coil inlet wet-bulb temperature of {:.1T} and an outdoor unit inlet air "
   14684             :                                              "dry-bulb temperature of {:.1T}.",
   14685             :                                              CoolingCoilInletAirWetBulbTempRated,
   14686             :                                              OutdoorUnitInletAirDryBulbTempPLTestPoint(PartLoadTestPoint)));
   14687           0 :                     ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
   14688             :                 }
   14689           0 :                 ShowRecurringWarningErrorAtEnd(
   14690             :                     state,
   14691           0 :                     format("{}{} \"{}\": Total Cooling Capacity Modifier curve (function of temperature) output is negative warning continues...",
   14692             :                            RoutineName,
   14693           0 :                            thisDXCoil.DXCoilType,
   14694           0 :                            thisDXCoil.Name),
   14695           0 :                     thisDXCoil.CCapFTempErrorIndex,
   14696             :                     TotCapTempModFac,
   14697             :                     TotCapTempModFac);
   14698           0 :                 TotCapTempModFac = 0.0;
   14699             :             }
   14700             : 
   14701         156 :             HighSpeedTotCoolingCap = thisDXCoil.RatedTotCap(1) * TotCapTempModFac * TotCapFlowModFac;
   14702         156 :             HighSpeedNetCoolingCap = HighSpeedTotCoolingCap - FanHeatCorrection;
   14703             : 
   14704         468 :             EIRTempModFac = CurveValue(
   14705         156 :                 state, thisDXCoil.EIRFTemp(1), CoolingCoilInletAirWetBulbTempRated, OutdoorUnitInletAirDryBulbTempPLTestPoint(PartLoadTestPoint));
   14706         156 :             EIRFlowModFac = CurveValue(state, thisDXCoil.EIRFFlow(1), AirMassFlowRatio);
   14707         156 :             if (thisDXCoil.RatedCOP(1) > 0.0) {
   14708             :                 // RatedCOP <= 0.0 is trapped in GetInput, but keep this as "safety"
   14709         156 :                 EIR_HighSpeed = EIRTempModFac * EIRFlowModFac / thisDXCoil.RatedCOP(1);
   14710             :             } else {
   14711           0 :                 EIR = 0.0;
   14712             :             }
   14713             : 
   14714             :             // TotCapFlowModFac = CurveValue(state, thisDXCoil.CCapFFlow(1), AirMassFlowRatio);
   14715         312 :             TotCapTempModFac = CurveValue(
   14716         156 :                 state, thisDXCoil.CCapFTemp2, CoolingCoilInletAirWetBulbTempRated, OutdoorUnitInletAirDryBulbTempPLTestPoint(PartLoadTestPoint));
   14717             :             //    Warn user if curve output goes negative
   14718         156 :             if (TotCapTempModFac < 0.0) {
   14719           0 :                 if (thisDXCoil.CCapFTempErrorIndex == 0) {
   14720           0 :                     ShowWarningMessage(state, format("{}{} \"{}\":", RoutineName, thisDXCoil.DXCoilType, thisDXCoil.Name));
   14721           0 :                     ShowContinueError(
   14722             :                         state,
   14723           0 :                         format(" Total Cooling Capacity Modifier curve (function of temperature) output is negative ({:.3T}).", TotCapTempModFac));
   14724           0 :                     ShowContinueError(state,
   14725           0 :                                       format(" Negative value occurs using a coil inlet wet-bulb temperature of {:.1T} and an outdoor unit inlet air "
   14726             :                                              "dry-bulb temperature of {:.1T}.",
   14727             :                                              CoolingCoilInletAirWetBulbTempRated,
   14728             :                                              OutdoorUnitInletAirDryBulbTempPLTestPoint(PartLoadTestPoint)));
   14729           0 :                     ShowContinueErrorTimeStamp(state, " Resetting curve output to zero and continuing simulation.");
   14730             :                 }
   14731           0 :                 ShowRecurringWarningErrorAtEnd(
   14732             :                     state,
   14733           0 :                     format("{}{} \"{}\": Total Cooling Capacity Modifier curve (function of temperature) output is negative warning continues...",
   14734             :                            RoutineName,
   14735           0 :                            thisDXCoil.DXCoilType,
   14736           0 :                            thisDXCoil.Name),
   14737           0 :                     thisDXCoil.CCapFTempErrorIndex,
   14738             :                     TotCapTempModFac,
   14739             :                     TotCapTempModFac);
   14740           0 :                 TotCapTempModFac = 0.0;
   14741             :             }
   14742             : 
   14743         156 :             LowSpeedTotCoolingCap = thisDXCoil.RatedTotCap2 * TotCapTempModFac * TotCapFlowModFac;
   14744         156 :             LowSpeedNetCoolingCap = LowSpeedTotCoolingCap - FanHeatCorrection;
   14745             : 
   14746         312 :             EIRTempModFac = CurveValue(
   14747         156 :                 state, thisDXCoil.EIRFTemp2, CoolingCoilInletAirWetBulbTempRated, OutdoorUnitInletAirDryBulbTempPLTestPoint(PartLoadTestPoint));
   14748         156 :             EIRFlowModFac = CurveValue(state, thisDXCoil.EIRFFlow(1), AirMassFlowRatio);
   14749         156 :             if (thisDXCoil.RatedCOP2 > 0.0) {
   14750             :                 // RatedCOP <= 0.0 is trapped in GetInput, but keep this as "safety"
   14751         156 :                 EIR_LowSpeed = EIRTempModFac * EIRFlowModFac / thisDXCoil.RatedCOP2;
   14752             :             } else {
   14753           0 :                 EIR_LowSpeed = 0.0;
   14754             :             }
   14755             : 
   14756         156 :             if (LowSpeedNetCoolingCap <= TargetNetCapacity) {
   14757         104 :                 CycRatio = 1.0;
   14758         104 :                 SpeedRatio = (TargetNetCapacity - LowSpeedNetCoolingCap) / (HighSpeedNetCoolingCap - LowSpeedNetCoolingCap);
   14759         104 :                 TotCoolingCap = HighSpeedTotCoolingCap * SpeedRatio + LowSpeedTotCoolingCap * (1.0 - SpeedRatio);
   14760         104 :                 NetCoolingCap = TotCoolingCap - FanHeatCorrection;
   14761         104 :                 EIR = EIR_HighSpeed * SpeedRatio + EIR_LowSpeed * (1.0 - SpeedRatio);
   14762         104 :                 TotalElecPowerRated = TotCoolingCap * EIR + FanPowerCorrection;
   14763         104 :                 EER_TestPoint_SI(1 + PartLoadTestPoint) = NetCoolingCap / TotalElecPowerRated;
   14764         104 :                 EER_TestPoint_IP(1 + PartLoadTestPoint) = EER_TestPoint_SI(1 + PartLoadTestPoint) * ConvFromSIToIP;
   14765         104 :                 NetCapacity_TestPoint(1 + PartLoadTestPoint) = NetCoolingCap;
   14766         104 :                 NetPower_TestPoint(1 + PartLoadTestPoint) = TotalElecPowerRated;
   14767             :             } else { // minimum unloading limit exceeded without cycling, so cycle
   14768          52 :                 SpeedRatio = 0.0;
   14769          52 :                 CycRatio = TargetNetCapacity / LowSpeedNetCoolingCap;
   14770          52 :                 PLF = CurveValue(state, thisDXCoil.PLFFPLR(1), CycRatio);
   14771          52 :                 if (PLF < 0.7) {
   14772           0 :                     PLF = 0.7;
   14773             :                 }
   14774          52 :                 RunTimeFraction = CycRatio / PLF;
   14775          52 :                 RunTimeFraction = min(RunTimeFraction, 1.0);
   14776          52 :                 TotCoolingCap = LowSpeedTotCoolingCap * RunTimeFraction;
   14777          52 :                 NetCoolingCap = TotCoolingCap - FanHeatCorrection;
   14778          52 :                 TotalElecPowerRated = LowSpeedTotCoolingCap * EIR_LowSpeed * RunTimeFraction + FanPowerCorrection;
   14779          52 :                 EER_TestPoint_SI(1 + PartLoadTestPoint) = NetCoolingCap / TotalElecPowerRated;
   14780          52 :                 EER_TestPoint_IP(1 + PartLoadTestPoint) = EER_TestPoint_SI(1 + PartLoadTestPoint) * ConvFromSIToIP;
   14781          52 :                 NetCapacity_TestPoint(1 + PartLoadTestPoint) = NetCoolingCap;
   14782          52 :                 NetPower_TestPoint(1 + PartLoadTestPoint) = TotalElecPowerRated;
   14783             :             }
   14784             :         }
   14785             :     } // loop over 3 part load test points
   14786          52 :     state.dataHVACGlobal->TurnFansOn = saveTurnFansOn;
   14787          52 :     state.dataHVACGlobal->TurnFansOff = saveTurnFansOff;
   14788             : 
   14789          52 :     IEER = (0.02 * EER_TestPoint_IP(1)) + (0.617 * EER_TestPoint_IP(2)) + (0.238 * EER_TestPoint_IP(3)) + (0.125 * EER_TestPoint_IP(4));
   14790             :     // CalcMultiSpeedDXCoilCooling() //??
   14791             :     // begin output
   14792          52 :     if (state.dataDXCoils->CalcTwoSpeedDXCoilStandardRatingOneTimeEIOHeaderWrite) {
   14793          23 :         print(state.files.eio, Header);
   14794          23 :         state.dataDXCoils->CalcTwoSpeedDXCoilStandardRatingOneTimeEIOHeaderWrite = false;
   14795          46 :         state.dataOutRptPredefined->pdstVAVDXCoolCoil =
   14796          23 :             newPreDefSubTable(state, state.dataOutRptPredefined->pdrEquip, "VAV DX Cooling Standard Rating Details");
   14797          46 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilType =
   14798          23 :             newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "DX Cooling Coil Type");
   14799          23 :         state.dataOutRptPredefined->pdchVAVDXFanName = newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "Assocated Fan");
   14800          46 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilNetCapSI =
   14801          23 :             newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "Net Cooling Capacity [W]");
   14802          23 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilCOP = newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "COP [W/W]");
   14803          23 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilEERIP = newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "EER [Btu/W-h]");
   14804          23 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilIEERIP = newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "IEER [Btu/W-h]");
   14805          46 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilMdotA =
   14806          23 :             newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "Supply Air Flow 100% [kg/s]");
   14807          46 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilCOP_B =
   14808          23 :             newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "COP 75% Capacity [W/W]");
   14809          46 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilEER_B_IP =
   14810          23 :             newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "EER 75% Capacity [Btu/W-h]");
   14811          46 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilMdotB =
   14812          23 :             newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "Supply Air Flow 75% [kg/s]");
   14813          46 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilCOP_C =
   14814          23 :             newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "COP 50% Capacity [W/W]");
   14815          46 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilEER_C_IP =
   14816          23 :             newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "EER 50% Capacity [Btu/W-h]");
   14817          46 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilMdotC =
   14818          23 :             newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "Supply Air Flow 50% [kg/s]");
   14819          46 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilCOP_D =
   14820          23 :             newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "COP 25% Capacity [W/W]");
   14821          46 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilEER_D_IP =
   14822          23 :             newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "EER 25% Capacity [Btu/W-h]");
   14823          46 :         state.dataOutRptPredefined->pdchVAVDXCoolCoilMdotD =
   14824          23 :             newPreDefColumn(state, state.dataOutRptPredefined->pdstVAVDXCoolCoil, "Supply Air Flow 25% [kg/s]");
   14825             : 
   14826             :         // determine footnote content
   14827          23 :         countStaticInputs = 0;
   14828          92 :         for (index = 1; index <= state.dataDXCoils->NumDXCoils; ++index) {
   14829             : 
   14830          98 :             if (state.dataDXCoils->DXCoil(index).RateWithInternalStaticAndFanObject &&
   14831          29 :                 state.dataDXCoils->DXCoil(index).DXCoilType_Num == HVAC::CoilDX_CoolingTwoSpeed) {
   14832          29 :                 ++countStaticInputs;
   14833             :             }
   14834             :         }
   14835             : 
   14836          23 :         if (countStaticInputs == state.dataDXCoils->NumDXMulSpeedCoils) {
   14837          22 :             addFootNoteSubTable(state,
   14838          11 :                                 state.dataOutRptPredefined->pdstVAVDXCoolCoil,
   14839             :                                 "Packaged VAV unit ratings per ANSI/AHRI Standard 340/360-2007 with Addenda 1 and 2");
   14840          12 :         } else if (countStaticInputs == 0) {
   14841          24 :             addFootNoteSubTable(state,
   14842          12 :                                 state.dataOutRptPredefined->pdstVAVDXCoolCoil,
   14843             :                                 "Indoor-coil-only unit ratings per ANSI/AHRI Standard 340/360-2007 with Addenda 1 and 2, with "
   14844             :                                 "supply fan specific power at 365 {{W/1000cfm}} (773.3 {{W/(m3/s)}})");
   14845             :         } else { // both
   14846           0 :             addFootNoteSubTable(state,
   14847           0 :                                 state.dataOutRptPredefined->pdstVAVDXCoolCoil,
   14848             :                                 "Packaged VAV unit ratings per ANSI/AHRI Standard 340/360-2007 with Addenda 1 and 2, "
   14849             :                                 "indoor-coil-only units with supply fan specific power at 365 {{W/1000cfm}} (773.3 {{W/(m3/s)}})");
   14850             :         }
   14851             :     }
   14852             : 
   14853          52 :     const auto &fan_type_name = [&]() -> std::pair<const char *, std::string> {
   14854          52 :         if (thisDXCoil.RateWithInternalStaticAndFanObject) {
   14855          58 :             return {"Fan:VariableVolume", thisDXCoil.SupplyFanName};
   14856             :         } else {
   14857          46 :             return {"N/A", "N/A"};
   14858             :         }
   14859          52 :     }();
   14860             : 
   14861          52 :     print(state.files.eio,
   14862             :           Format_891,
   14863             :           "Coil:Cooling:DX:TwoSpeed",
   14864          52 :           thisDXCoil.Name,
   14865          52 :           fan_type_name.first,
   14866          52 :           fan_type_name.second,
   14867             :           NetCoolingCapRated,
   14868          52 :           (NetCoolingCapRated * ConvFromSIToIP),
   14869             :           IEER,
   14870             :           EER_TestPoint_SI(1),
   14871             :           EER_TestPoint_SI(2),
   14872             :           EER_TestPoint_SI(3),
   14873             :           EER_TestPoint_SI(4),
   14874             :           EER_TestPoint_IP(1),
   14875             :           EER_TestPoint_IP(2),
   14876             :           EER_TestPoint_IP(3),
   14877             :           EER_TestPoint_IP(4),
   14878             :           SupAirMdot_TestPoint(1),
   14879             :           SupAirMdot_TestPoint(2),
   14880             :           SupAirMdot_TestPoint(3),
   14881             :           SupAirMdot_TestPoint(4));
   14882             : 
   14883          52 :     if (state.dataHVACGlobal->StandardRatingsMyCoolOneTimeFlag) {
   14884             :         static constexpr std::string_view Format_994(
   14885             :             "! <DX Cooling Coil Standard Rating Information>, Component Type, Component Name, Standard Rating (Net) "
   14886             :             "Cooling Capacity {W}, Standard Rating Net COP {W/W}, EER {Btu/W-h}, SEER User {Btu/W-h}, SEER Standard {Btu/W-h}, "
   14887             :             "IEER "
   14888             :             "{Btu/W-h}");
   14889          22 :         print(state.files.eio, "{}\n", Format_994);
   14890          22 :         state.dataHVACGlobal->StandardRatingsMyCoolOneTimeFlag = false;
   14891             :     }
   14892             :     static constexpr std::string_view Format_995(" DX Cooling Coil Standard Rating Information, {}, {}, {:.1R}, {}, {}, {}, {}, {}\n");
   14893          52 :     print(state.files.eio,
   14894             :           Format_995,
   14895             :           "Coil:Cooling:DX:TwoSpeed",
   14896          52 :           thisDXCoil.Name,
   14897             :           NetCoolingCapRated,
   14898             :           EER_TestPoint_SI(1),
   14899             :           EER_TestPoint_IP(1),
   14900             :           "N/A",
   14901             :           "N/A",
   14902             :           IEER);
   14903             : 
   14904          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchDXCoolCoilType, thisDXCoil.Name, "Coil:Cooling:DX:TwoSpeed");
   14905             :     // W to tons
   14906          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchDXCoolCoilNetCapSI, thisDXCoil.Name, NetCoolingCapRated, 1);
   14907             : 
   14908             :     // TODO: Commercial and industrial unitary air-conditioning condensing units with a capacity greater than 135,000 Btu/h (39564.59445 Watts)
   14909             :     // as defined in ANSI/AHRI Standard 365(I-P). | Scope 2.2.6 (ANSI/AHRI 340-360 2022)
   14910             :     //
   14911             :     // These will convert with a factor of 1 which is ok
   14912             :     // SEER | Capacity less than 65K Btu/h (19050 W) - calculated as per AHRI Standard 210/240-2023.
   14913          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchDXCoolCoilCOP, thisDXCoil.Name, EER_TestPoint_SI(1), 2);
   14914          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchDXCoolCoilEERIP, thisDXCoil.Name, EER_TestPoint_IP(1), 2);
   14915             :     // These will convert with a factor of 1 which is ok
   14916             :     // IEER | Capacity of 65K Btu/h (19050 W) to less than 135K Btu/h (39565 W) - calculated as per AHRI Standard 340/360-2022.
   14917          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchDXCoolCoilIEERIP, thisDXCoil.Name, IEER, 1);
   14918          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchDXCoolCoilSEERUserIP, thisDXCoil.Name, "N/A");
   14919          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchDXCoolCoilSEERStandardIP, thisDXCoil.Name, "N/A");
   14920             : 
   14921         104 :     addFootNoteSubTable(
   14922             :         state,
   14923          52 :         state.dataOutRptPredefined->pdstDXCoolCoil,
   14924             :         "ANSI/AHRI ratings account for supply air fan heat and electric power. <br/>"
   14925             :         "1 - EnergyPlus object type. <br/>"
   14926             :         "2 - Capacity less than 65K Btu/h (19050 W) - calculated as per AHRI Standard 210/240-2017. <br/>"
   14927             :         "&emsp;&nbsp;Capacity of 65K Btu/h (19050 W) to less than 135K Btu/h (39565 W) - calculated as per AHRI Standard 340/360-2007. <br/>"
   14928             :         "&emsp;&nbsp;Capacity from 135K (39565 W) to 250K Btu/hr (73268 W) - calculated as per AHRI Standard 365-2009 - Ratings not yet supported in "
   14929             :         "EnergyPlus. <br/>"
   14930             :         "3 - SEER (User) is calculated using user-input PLF curve and cooling coefficient of degradation. <br/>"
   14931             :         "&emsp;&nbsp;SEER (Standard) is calculated using the default PLF curve and cooling coefficient of degradation"
   14932             :         "from the appropriate AHRI standard.");
   14933             : 
   14934          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilType, thisDXCoil.Name, "Coil:Cooling:DX:TwoSpeed");
   14935          52 :     if (thisDXCoil.RateWithInternalStaticAndFanObject) {
   14936          29 :         PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXFanName, thisDXCoil.Name, thisDXCoil.SupplyFanName);
   14937             :     } else {
   14938          23 :         PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXFanName, thisDXCoil.Name, "None");
   14939             :     }
   14940          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilNetCapSI, thisDXCoil.Name, NetCoolingCapRated, 2);
   14941          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilCOP, thisDXCoil.Name, EER_TestPoint_SI(1), 2);
   14942          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilIEERIP, thisDXCoil.Name, IEER, 2);
   14943          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilEERIP, thisDXCoil.Name, EER_TestPoint_IP(1), 2);
   14944          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilMdotA, thisDXCoil.Name, SupAirMdot_TestPoint(1), 4);
   14945          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilCOP_B, thisDXCoil.Name, EER_TestPoint_SI(2), 2);
   14946          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilEER_B_IP, thisDXCoil.Name, EER_TestPoint_IP(2), 2);
   14947          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilMdotB, thisDXCoil.Name, SupAirMdot_TestPoint(2), 4);
   14948          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilCOP_C, thisDXCoil.Name, EER_TestPoint_SI(3), 2);
   14949          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilEER_C_IP, thisDXCoil.Name, EER_TestPoint_IP(3), 2);
   14950          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilMdotC, thisDXCoil.Name, SupAirMdot_TestPoint(3), 4);
   14951          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilCOP_D, thisDXCoil.Name, EER_TestPoint_SI(4), 2);
   14952          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilEER_D_IP, thisDXCoil.Name, EER_TestPoint_IP(4), 2);
   14953          52 :     PreDefTableEntry(state, state.dataOutRptPredefined->pdchVAVDXCoolCoilMdotD, thisDXCoil.Name, SupAirMdot_TestPoint(4), 4);
   14954             : 
   14955          52 :     state.dataEnvrn->OutDryBulbTemp = heldOutDryBulb; // reset the outdoor dry bulb when done with it
   14956         122 : }
   14957             : 
   14958          66 : void GetFanIndexForTwoSpeedCoil(
   14959             :     EnergyPlusData &state, int const CoolingCoilIndex, int &SupplyFanIndex, std::string &SupplyFanName, HVAC::FanType &supplyFanType)
   14960             : {
   14961             : 
   14962             :     // SUBROUTINE INFORMATION:
   14963             :     //       AUTHOR         <author>
   14964             :     //       DATE WRITTEN   <date_written>
   14965             : 
   14966             :     // PURPOSE OF THIS SUBROUTINE:
   14967             :     // This routine looks up the given TwoSpeed DX coil and returns the companion supply fan index
   14968             : 
   14969             :     // Using/Aliasing
   14970          66 :     int NumPrimaryAirSys = state.dataHVACGlobal->NumPrimaryAirSys;
   14971             : 
   14972             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   14973             :     int FoundBranch;
   14974             :     int FoundAirSysNum;
   14975             :     int AirSysNum;
   14976             :     int BranchNum;
   14977             :     int CompNum;
   14978             : 
   14979          66 :     FoundBranch = 0;
   14980          66 :     FoundAirSysNum = 0;
   14981          66 :     SupplyFanIndex = 0;
   14982          66 :     SupplyFanName = "n/a";
   14983         322 :     for (AirSysNum = 1; AirSysNum <= NumPrimaryAirSys; ++AirSysNum) {
   14984             : 
   14985         512 :         for (BranchNum = 1; BranchNum <= state.dataAirSystemsData->PrimaryAirSystems(AirSysNum).NumBranches; ++BranchNum) {
   14986             : 
   14987        1066 :             for (CompNum = 1; CompNum <= state.dataAirSystemsData->PrimaryAirSystems(AirSysNum).Branch(BranchNum).TotalComponents; ++CompNum) {
   14988             : 
   14989         876 :                 if (state.dataAirSystemsData->PrimaryAirSystems(AirSysNum).Branch(BranchNum).Comp(CompNum).CompType_Num ==
   14990             :                     SimAirServingZones::CompType::DXSystem) {
   14991             : 
   14992         224 :                     if (Util::SameString(state.dataAirSystemsData->PrimaryAirSystems(AirSysNum).Branch(BranchNum).Comp(CompNum).Name,
   14993         224 :                                          state.dataDXCoils->DXCoil(CoolingCoilIndex).CoilSystemName)) {
   14994          66 :                         FoundBranch = BranchNum;
   14995          66 :                         FoundAirSysNum = AirSysNum;
   14996          66 :                         break;
   14997             :                     }
   14998             :                     // these are specified in SimAirServingZones and need to be moved to a Data* file. UnitarySystem=19
   14999         652 :                 } else if (state.dataAirSystemsData->PrimaryAirSystems(AirSysNum).Branch(BranchNum).Comp(CompNum).CompType_Num ==
   15000             :                            SimAirServingZones::CompType::UnitarySystemModel) {
   15001             : 
   15002          12 :                     if (Util::SameString(state.dataAirSystemsData->PrimaryAirSystems(AirSysNum).Branch(BranchNum).Comp(CompNum).Name,
   15003          12 :                                          state.dataDXCoils->DXCoil(CoolingCoilIndex).CoilSystemName)) {
   15004           0 :                         FoundBranch = BranchNum;
   15005           0 :                         FoundAirSysNum = AirSysNum;
   15006           0 :                         break;
   15007             :                     }
   15008             :                 }
   15009             :             }
   15010             : 
   15011         256 :             if (FoundBranch > 0 && FoundAirSysNum > 0) {
   15012         657 :                 for (CompNum = 1; CompNum <= state.dataAirSystemsData->PrimaryAirSystems(FoundAirSysNum).Branch(FoundBranch).TotalComponents;
   15013             :                      ++CompNum) {
   15014         604 :                     if (state.dataAirSystemsData->PrimaryAirSystems(FoundAirSysNum).Branch(FoundBranch).Comp(CompNum).CompType_Num ==
   15015             :                         SimAirServingZones::CompType::Fan_Simple_VAV) {
   15016          99 :                         SupplyFanName = state.dataAirSystemsData->PrimaryAirSystems(FoundAirSysNum).Branch(FoundBranch).Comp(CompNum).Name;
   15017          99 :                         SupplyFanIndex = Fans::GetFanIndex(state, SupplyFanName);
   15018          99 :                         supplyFanType = HVAC::FanType::VAV;
   15019          99 :                         break;
   15020             :                         // these are specified in SimAirServingZones and need to be moved to a Data* file. UnitarySystem=19
   15021         505 :                     } else if (state.dataAirSystemsData->PrimaryAirSystems(FoundAirSysNum).Branch(FoundBranch).Comp(CompNum).CompType_Num ==
   15022             :                                SimAirServingZones::CompType::Fan_System_Object) {
   15023          12 :                         SupplyFanName = state.dataAirSystemsData->PrimaryAirSystems(FoundAirSysNum).Branch(FoundBranch).Comp(CompNum).Name;
   15024          12 :                         SupplyFanIndex = Fans::GetFanIndex(state, SupplyFanName);
   15025          12 :                         supplyFanType = HVAC::FanType::SystemModel;
   15026             : 
   15027         493 :                     } else if (state.dataAirSystemsData->PrimaryAirSystems(FoundAirSysNum).Branch(FoundBranch).Comp(CompNum).CompType_Num ==
   15028             :                                SimAirServingZones::CompType::UnitarySystemModel) {
   15029             :                         // fan may not be specified in a unitary system object, keep looking
   15030             :                         // Unitary System will "set" the fan index to the DX coil if contained within the HVAC system
   15031           0 :                         if (state.dataDXCoils->DXCoil(CoolingCoilIndex).SupplyFanIndex > 0) break;
   15032             :                     }
   15033             :                 }
   15034             :             }
   15035             :         }
   15036             :     }
   15037          66 : }
   15038             : 
   15039         981 : void GetDXCoilIndex(EnergyPlusData &state,
   15040             :                     std::string const &DXCoilName,
   15041             :                     int &DXCoilIndex,
   15042             :                     bool &ErrorsFound,
   15043             :                     std::string_view const ThisObjectType,
   15044             :                     bool const SuppressWarning)
   15045             : {
   15046             : 
   15047             :     // SUBROUTINE INFORMATION:
   15048             :     //       AUTHOR         Richard Raustad
   15049             :     //       DATE WRITTEN   March 2005
   15050             : 
   15051             :     // PURPOSE OF THIS SUBROUTINE:
   15052             :     // This subroutine sets an index for a given DX Coil -- issues error message if that
   15053             :     // DX Coil is not a legal DX Coil.
   15054             : 
   15055         981 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15056         139 :         GetDXCoils(state);
   15057         139 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15058             :     }
   15059             : 
   15060         981 :     DXCoilIndex = Util::FindItemInList(DXCoilName, state.dataDXCoils->DXCoil);
   15061         981 :     if (DXCoilIndex == 0) {
   15062           7 :         if (!SuppressWarning) {
   15063             :             //     No warning printed if only searching for the existence of a DX Coil
   15064           0 :             if (!ThisObjectType.empty()) {
   15065           0 :                 ShowSevereError(state, fmt::format("{}, GetDXCoilIndex: DX Coil not found={}", ThisObjectType, DXCoilName));
   15066             :             } else {
   15067           0 :                 ShowSevereError(state, format("GetDXCoilIndex: DX Coil not found={}", DXCoilName));
   15068             :             }
   15069             :         }
   15070           7 :         ErrorsFound = true;
   15071             :     }
   15072         981 : }
   15073             : 
   15074             : std::string
   15075          15 : GetDXCoilName(EnergyPlusData &state, int &DXCoilIndex, bool &ErrorsFound, std::string_view const ThisObjectType, bool const SuppressWarning)
   15076             : {
   15077             : 
   15078             :     // SUBROUTINE INFORMATION:
   15079             :     //       AUTHOR         Richard Raustad
   15080             :     //       DATE WRITTEN   May 2017
   15081             : 
   15082             :     // PURPOSE OF THIS SUBROUTINE:
   15083             :     // This subroutine gets a name for a given DX Coil -- issues error message if that
   15084             :     // DX Coil is not a legal DX Coil.
   15085             : 
   15086          15 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15087           0 :         GetDXCoils(state);
   15088           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15089             :     }
   15090             : 
   15091          15 :     if (DXCoilIndex == 0) {
   15092           0 :         if (!SuppressWarning) {
   15093             :             //     No warning printed if only searching for the existence of a DX Coil
   15094           0 :             if (!ThisObjectType.empty()) {
   15095           0 :                 ShowSevereError(state, fmt::format("{}, GetDXCoilIndex: DX Coil not found ", ThisObjectType));
   15096             :             } else {
   15097           0 :                 ShowSevereError(state, "GetDXCoilIndex: DX Coil not found ");
   15098             :             }
   15099             :         }
   15100           0 :         ErrorsFound = true;
   15101           0 :         return " "; // This does not seem great
   15102             : 
   15103             :     } else {
   15104          15 :         return state.dataDXCoils->DXCoil(DXCoilIndex).Name;
   15105             :     }
   15106             : }
   15107             : 
   15108         242 : Real64 GetCoilCapacity(EnergyPlusData &state,
   15109             :                        std::string const &CoilType, // must match coil types in this module
   15110             :                        std::string const &CoilName, // must match coil names for the coil type
   15111             :                        bool &ErrorsFound            // set to true if problem
   15112             : )
   15113             : {
   15114             : 
   15115             :     // FUNCTION INFORMATION:
   15116             :     //       AUTHOR         Linda Lawrie
   15117             :     //       DATE WRITTEN   February 2006
   15118             : 
   15119             :     // PURPOSE OF THIS FUNCTION:
   15120             :     // This function looks up the coil capacity for the given coil and returns it.  If
   15121             :     // incorrect coil type or name is given, ErrorsFound is returned as true and capacity is returned
   15122             :     // as negative.
   15123             : 
   15124             :     // Return value
   15125             :     Real64 CoilCapacity; // returned capacity of matched coil
   15126             : 
   15127             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   15128             :     int WhichCoil;
   15129             : 
   15130             :     // Obtains and Allocates DXCoils
   15131         242 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15132           0 :         GetDXCoils(state);
   15133           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15134             :     }
   15135             : 
   15136         242 :     if (Util::SameString(CoilType, "Coil:Heating:DX:SingleSpeed") || Util::SameString(CoilType, "Coil:Cooling:DX:SingleSpeed")) {
   15137         242 :         WhichCoil = Util::FindItem(CoilName, state.dataDXCoils->DXCoil);
   15138         242 :         if (WhichCoil != 0) {
   15139         242 :             CoilCapacity = state.dataDXCoils->DXCoil(WhichCoil).RatedTotCap(1);
   15140             :         }
   15141           0 :     } else if (Util::SameString(CoilType, "Coil:Cooling:DX:TwoStageWithHumidityControlMode")) {
   15142           0 :         WhichCoil = Util::FindItem(CoilName, state.dataDXCoils->DXCoil);
   15143           0 :         if (WhichCoil != 0) {
   15144           0 :             CoilCapacity = state.dataDXCoils->DXCoil(WhichCoil).RatedTotCap(state.dataDXCoils->DXCoil(WhichCoil).NumCapacityStages);
   15145             :         }
   15146           0 :     } else if (Util::SameString(CoilType, "Coil:Cooling:DX:TwoSpeed")) {
   15147           0 :         WhichCoil = Util::FindItem(CoilName, state.dataDXCoils->DXCoil);
   15148           0 :         if (WhichCoil != 0) {
   15149           0 :             CoilCapacity = state.dataDXCoils->DXCoil(WhichCoil).RatedTotCap(1);
   15150             :         }
   15151           0 :     } else if (Util::SameString(CoilType, "Coil:Cooling:DX:MultiSpeed") || Util::SameString(CoilType, "Coil:Heating:DX:MultiSpeed")) {
   15152           0 :         WhichCoil = Util::FindItem(CoilName, state.dataDXCoils->DXCoil);
   15153           0 :         if (WhichCoil != 0) {
   15154           0 :             CoilCapacity = state.dataDXCoils->DXCoil(WhichCoil).MSRatedTotCap(state.dataDXCoils->DXCoil(WhichCoil).NumOfSpeeds);
   15155             :         }
   15156             :     } else {
   15157           0 :         WhichCoil = 0;
   15158             :     }
   15159             : 
   15160         242 :     if (WhichCoil == 0) {
   15161           0 :         ShowSevereError(state, format("GetCoilCapacity: Could not find Coil, Type=\"{}\" Name=\"{}\"", CoilType, CoilName));
   15162           0 :         ShowContinueError(state, "... returning capacity as -1000.");
   15163           0 :         ErrorsFound = true;
   15164           0 :         CoilCapacity = -1000.0;
   15165             :     }
   15166             : 
   15167         242 :     return CoilCapacity;
   15168             : }
   15169             : 
   15170         432 : Real64 GetCoilCapacityByIndexType(EnergyPlusData &state,
   15171             :                                   int const CoilIndex,    // must match coil index for the coil type
   15172             :                                   int const CoilType_Num, // must match coil types in this module
   15173             :                                   bool &ErrorsFound       // set to true if problem
   15174             : )
   15175             : {
   15176             : 
   15177             :     // FUNCTION INFORMATION:
   15178             :     //       AUTHOR         Richard Raustad
   15179             :     //       DATE WRITTEN   October 2010
   15180             : 
   15181             :     // PURPOSE OF THIS FUNCTION:
   15182             :     // This function looks up the coil capacity for the given coil and returns it.  If
   15183             :     // incorrect coil index or type is given, ErrorsFound is returned as true and capacity is returned
   15184             :     // as negative.
   15185             : 
   15186             :     // Return value
   15187             :     Real64 CoilCapacity; // returned capacity of matched coil
   15188             : 
   15189             :     // Obtains and Allocates DXCoils
   15190         432 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15191           0 :         GetDXCoils(state);
   15192           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15193             :     }
   15194             : 
   15195         432 :     if (CoilIndex == 0) {
   15196           0 :         ShowSevereError(state, "GetCoilCapacityByIndexType: Invalid index passed = 0");
   15197           0 :         ShowContinueError(state, "... returning capacity as -1000.");
   15198           0 :         ErrorsFound = true;
   15199           0 :         CoilCapacity = -1000.0;
   15200           0 :         return CoilCapacity;
   15201             :     }
   15202             : 
   15203         432 :     if (CoilType_Num != state.dataDXCoils->DXCoil(CoilIndex).DXCoilType_Num) {
   15204           0 :         ShowSevereError(state, "GetCoilCapacityByIndexType: Index passed does not match DX Coil type passed.");
   15205           0 :         ShowContinueError(state, "... returning capacity as -1000.");
   15206           0 :         ErrorsFound = true;
   15207           0 :         CoilCapacity = -1000.0;
   15208             :     } else {
   15209         432 :         switch (state.dataDXCoils->DXCoil(CoilIndex).DXCoilType_Num) {
   15210          33 :         case HVAC::CoilDX_MultiSpeedCooling:
   15211             :         case HVAC::CoilDX_MultiSpeedHeating: {
   15212          33 :             CoilCapacity = state.dataDXCoils->DXCoil(CoilIndex).MSRatedTotCap(state.dataDXCoils->DXCoil(CoilIndex).NumOfSpeeds);
   15213          33 :         } break;
   15214         399 :         default: {
   15215         399 :             CoilCapacity = state.dataDXCoils->DXCoil(CoilIndex).RatedTotCap(state.dataDXCoils->DXCoil(CoilIndex).NumCapacityStages);
   15216         399 :         } break;
   15217             :         }
   15218             :     }
   15219             : 
   15220         432 :     return CoilCapacity;
   15221             : }
   15222             : 
   15223         406 : int GetCoilTypeNum(EnergyPlusData &state,
   15224             :                    std::string const &CoilType,                // must match coil types in this module
   15225             :                    std::string const &CoilName,                // must match coil names for the coil type
   15226             :                    bool &ErrorsFound,                          // set to true if problem
   15227             :                    ObjexxFCL::Optional_bool_const PrintWarning // prints warning when true
   15228             : )
   15229             : {
   15230             : 
   15231             :     // FUNCTION INFORMATION:
   15232             :     //       AUTHOR         R. Raustad - FSEC
   15233             :     //       DATE WRITTEN   August 2008
   15234             : 
   15235             :     // PURPOSE OF THIS FUNCTION:
   15236             :     // This function looks up the integerized coil type for the given coil and returns it.  If
   15237             :     // incorrect coil type or name is given, ErrorsFound is returned as true and capacity is returned
   15238             :     // as negative.
   15239             : 
   15240             :     // Return value
   15241             :     int TypeNum; // returned integerized type of matched coil
   15242             : 
   15243             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   15244             :     int WhichCoil;
   15245             :     bool PrintMessage;
   15246             : 
   15247             :     // Obtains and Allocates DXCoils
   15248         406 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15249         101 :         GetDXCoils(state);
   15250         101 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15251             :     }
   15252             : 
   15253         406 :     if (present(PrintWarning)) {
   15254         374 :         PrintMessage = PrintWarning;
   15255             :     } else {
   15256          32 :         PrintMessage = true;
   15257             :     }
   15258             : 
   15259         406 :     WhichCoil = Util::FindItemInList(CoilName, state.dataDXCoils->DXCoil);
   15260         406 :     if (WhichCoil != 0) {
   15261         403 :         TypeNum = state.dataDXCoils->DXCoil(WhichCoil).DXCoilType_Num;
   15262             :     } else {
   15263           3 :         if (PrintMessage) {
   15264           0 :             ShowSevereError(state, format("GetCoilTypeNum: Could not find Coil, Type=\"{}\" Name=\"{}\"", CoilType, CoilName));
   15265             :         }
   15266           3 :         ErrorsFound = true;
   15267           3 :         TypeNum = 0;
   15268             :     }
   15269             : 
   15270         406 :     return TypeNum;
   15271             : }
   15272             : 
   15273         811 : Real64 GetMinOATCompressor(EnergyPlusData &state,
   15274             :                            int const CoilIndex, // index to cooling coil
   15275             :                            bool &ErrorsFound    // set to true if problem
   15276             : )
   15277             : {
   15278             : 
   15279             :     // Obtains and Allocates DXCoils
   15280         811 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15281           0 :         GetDXCoils(state);
   15282           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15283             :     }
   15284             : 
   15285         811 :     if (CoilIndex == 0) {
   15286           0 :         ShowSevereError(state, "GetMinOATCompressor: Index passed = 0");
   15287           0 :         ShowContinueError(state, "... returning Min OAT for compressor operation as -1000.");
   15288           0 :         ErrorsFound = true;
   15289           0 :         return -1000.0;
   15290             :     } else {
   15291         811 :         return state.dataDXCoils->DXCoil(CoilIndex).MinOATCompressor;
   15292             :     }
   15293             : }
   15294             : 
   15295         387 : int GetCoilInletNode(EnergyPlusData &state,
   15296             :                      std::string const &CoilType, // must match coil types in this module
   15297             :                      std::string const &CoilName, // must match coil names for the coil type
   15298             :                      bool &ErrorsFound            // set to true if problem
   15299             : )
   15300             : {
   15301             : 
   15302             :     // FUNCTION INFORMATION:
   15303             :     //       AUTHOR         Linda Lawrie
   15304             :     //       DATE WRITTEN   February 2006
   15305             : 
   15306             :     // PURPOSE OF THIS FUNCTION:
   15307             :     // This function looks up the given coil and returns the inlet node number.  If
   15308             :     // incorrect coil type or name is given, ErrorsFound is returned as true and node number is returned
   15309             :     // as zero.
   15310             : 
   15311             :     // Return value
   15312             :     int NodeNumber; // returned node number of matched coil
   15313             : 
   15314             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   15315             :     int WhichCoil;
   15316             : 
   15317             :     // Obtains and Allocates DXCoils
   15318         387 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15319           1 :         GetDXCoils(state);
   15320           1 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15321             :     }
   15322             : 
   15323         387 :     WhichCoil = Util::FindItemInList(CoilName, state.dataDXCoils->DXCoil);
   15324         387 :     if (WhichCoil != 0) {
   15325         387 :         NodeNumber = state.dataDXCoils->DXCoil(WhichCoil).AirInNode;
   15326             :     } else {
   15327           0 :         ShowSevereError(state, format("GetCoilInletNode: Could not find Coil, Type=\"{}\" Name=\"{}\"", CoilType, CoilName));
   15328           0 :         ErrorsFound = true;
   15329           0 :         NodeNumber = 0;
   15330             :     }
   15331             : 
   15332         387 :     return NodeNumber;
   15333             : }
   15334             : 
   15335           0 : int getCoilInNodeIndex(EnergyPlusData &state,
   15336             :                        int const CoilIndex, // coil index
   15337             :                        bool &ErrorsFound    // set to true if problem
   15338             : )
   15339             : {
   15340             : 
   15341             :     int NodeNumber; // returned node number of matched coil
   15342             : 
   15343             :     // Obtains and Allocates DXCoils
   15344           0 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15345           0 :         GetDXCoils(state);
   15346           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15347             :     }
   15348             : 
   15349           0 :     if (CoilIndex != 0) {
   15350           0 :         NodeNumber = state.dataDXCoils->DXCoil(CoilIndex).AirInNode;
   15351             :     } else {
   15352           0 :         ShowSevereError(state, "GetCoilInletNode: Could not find Coil Type");
   15353           0 :         ErrorsFound = true;
   15354           0 :         NodeNumber = 0;
   15355             :     }
   15356             : 
   15357           0 :     return NodeNumber;
   15358             : }
   15359             : 
   15360         408 : int GetCoilOutletNode(EnergyPlusData &state,
   15361             :                       std::string const &CoilType, // must match coil types in this module
   15362             :                       std::string const &CoilName, // must match coil names for the coil type
   15363             :                       bool &ErrorsFound            // set to true if problem
   15364             : )
   15365             : {
   15366             : 
   15367             :     // FUNCTION INFORMATION:
   15368             :     //       AUTHOR         Linda Lawrie
   15369             :     //       DATE WRITTEN   February 2006
   15370             : 
   15371             :     // PURPOSE OF THIS FUNCTION:
   15372             :     // This function looks up the given coil and returns the inlet node number.  If
   15373             :     // incorrect coil type or name is given, ErrorsFound is returned as true and node number is returned
   15374             :     // as zero.
   15375             : 
   15376             :     // Return value
   15377             :     int NodeNumber; // returned node number of matched coil
   15378             : 
   15379             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   15380             :     int WhichCoil;
   15381             : 
   15382             :     // Obtains and Allocates DXCoils
   15383         408 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15384           6 :         GetDXCoils(state);
   15385           6 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15386             :     }
   15387             : 
   15388         408 :     WhichCoil = Util::FindItemInList(CoilName, state.dataDXCoils->DXCoil);
   15389         408 :     if (WhichCoil != 0) {
   15390         408 :         NodeNumber = state.dataDXCoils->DXCoil(WhichCoil).AirOutNode;
   15391             :     } else {
   15392           0 :         ShowSevereError(
   15393             :             state,
   15394           0 :             format("GetCoilOutletNode: Could not find Coil, Type=\"{}\" Name=\"{}\" when accessing coil outlet node number.", CoilType, CoilName));
   15395           0 :         ErrorsFound = true;
   15396           0 :         NodeNumber = 0;
   15397             :     }
   15398             : 
   15399         408 :     return NodeNumber;
   15400             : }
   15401             : 
   15402           0 : int getCoilOutNodeIndex(EnergyPlusData &state,
   15403             :                         int const CoilIndex, // must match coil types in this module
   15404             :                         bool &ErrorsFound    // set to true if problem
   15405             : )
   15406             : {
   15407             : 
   15408             :     int NodeNumber; // returned node number of matched coil
   15409             : 
   15410             :     // Obtains and Allocates DXCoils
   15411           0 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15412           0 :         GetDXCoils(state);
   15413           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15414             :     }
   15415             : 
   15416           0 :     if (CoilIndex != 0) {
   15417           0 :         NodeNumber = state.dataDXCoils->DXCoil(CoilIndex).AirOutNode;
   15418             :     } else {
   15419           0 :         ShowSevereError(state, "GetCoilOutletNode: Could not find Coil Type");
   15420           0 :         ErrorsFound = true;
   15421           0 :         NodeNumber = 0;
   15422             :     }
   15423             : 
   15424           0 :     return NodeNumber;
   15425             : }
   15426             : 
   15427         593 : int GetCoilCondenserInletNode(EnergyPlusData &state,
   15428             :                               std::string const &CoilType, // must match coil types in this module
   15429             :                               std::string const &CoilName, // must match coil names for the coil type
   15430             :                               bool &ErrorsFound            // set to true if problem
   15431             : )
   15432             : {
   15433             : 
   15434             :     // FUNCTION INFORMATION:
   15435             :     //       AUTHOR         R. Raustad
   15436             :     //       DATE WRITTEN   January 2007
   15437             : 
   15438             :     // PURPOSE OF THIS FUNCTION:
   15439             :     // This function looks up the given coil and returns the condenser inlet node.  If
   15440             :     // incorrect coil type or name is given, ErrorsFound is returned as true.
   15441             : 
   15442             :     // Return value
   15443             :     int CondNode; // returned condenser node number of matched coil
   15444             : 
   15445             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   15446             :     int WhichCoil;
   15447             : 
   15448             :     // Obtains and Allocates DXCoils
   15449         593 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15450           0 :         GetDXCoils(state);
   15451           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15452             :     }
   15453             : 
   15454         593 :     WhichCoil = Util::FindItemInList(CoilName, state.dataDXCoils->DXCoil);
   15455         593 :     if (WhichCoil != 0) {
   15456         593 :         CondNode = state.dataDXCoils->DXCoil(WhichCoil).CondenserInletNodeNum(1);
   15457             :     } else {
   15458           0 :         ShowSevereError(state, format("GetCoilCondenserInletNode: Invalid DX Coil, Type= \"{}\" Name=\"{}\"", CoilType, CoilName));
   15459           0 :         ErrorsFound = true;
   15460           0 :         CondNode = 0;
   15461             :     }
   15462             : 
   15463         593 :     return CondNode;
   15464             : }
   15465             : 
   15466           1 : Real64 GetDXCoilBypassedFlowFrac(EnergyPlusData &state,
   15467             :                                  std::string const &CoilType, // must match coil types in this module
   15468             :                                  std::string const &CoilName, // must match coil names for the coil type
   15469             :                                  bool &ErrorsFound            // set to true if problem
   15470             : )
   15471             : {
   15472             : 
   15473             :     // FUNCTION INFORMATION:
   15474             :     //       AUTHOR         R. Raustad
   15475             :     //       DATE WRITTEN   June 2007
   15476             : 
   15477             :     // PURPOSE OF THIS FUNCTION:
   15478             :     // This function looks up the given coil and returns the bypassed air flow fraction.
   15479             :     // Bypassed air flow fraction can only be greater than 0 for multimode DX cooling coils and is typical for 1st stage
   15480             :     // If incorrect coil type or name is given, ErrorsFound is returned as true.
   15481             : 
   15482             :     // Return value
   15483             :     Real64 BypassFraction; // returned bypass air fraction of matched coil
   15484             : 
   15485             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   15486             :     int WhichCoil;
   15487             : 
   15488             :     // Obtains and Allocates DXCoils
   15489           1 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15490           0 :         GetDXCoils(state);
   15491           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15492             :     }
   15493             : 
   15494           1 :     WhichCoil = Util::FindItemInList(CoilName, state.dataDXCoils->DXCoil);
   15495           1 :     if (WhichCoil != 0) {
   15496           1 :         BypassFraction = state.dataDXCoils->DXCoil(WhichCoil).BypassedFlowFrac(1);
   15497             :     } else {
   15498           0 :         ShowSevereError(state, format("GetDXCoilBypassedFlowFrac: Invalid DX Coil Type=\"{}\" Name=\"{}\"", CoilType, CoilName));
   15499           0 :         ErrorsFound = true;
   15500           0 :         BypassFraction = 0.0;
   15501             :     }
   15502             : 
   15503           1 :     return BypassFraction;
   15504             : }
   15505             : 
   15506     3923968 : int GetHPCoolingCoilIndex(EnergyPlusData &state,
   15507             :                           std::string const &HeatingCoilType, // Type of DX heating coil used in HP
   15508             :                           std::string const &HeatingCoilName, // Name of DX heating coil used in HP
   15509             :                           int const HeatingCoilIndex          // Index of DX heating coil used in HP
   15510             : )
   15511             : {
   15512             : 
   15513             :     // FUNCTION INFORMATION:
   15514             :     //       AUTHOR         R. Raustad
   15515             :     //       DATE WRITTEN   February 2007
   15516             : 
   15517             :     // PURPOSE OF THIS FUNCTION:
   15518             :     // This function looks up the given DX heating coil and returns the companion DX cooling coil.
   15519             : 
   15520             :     // Return value
   15521             :     int DXCoolingCoilIndex; // Index of HP DX cooling coil returned from this function
   15522             : 
   15523             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   15524             :     int WhichComp;           // DO loop counter to find correct comp set
   15525             :     int WhichCompanionComp;  // DO loop counter to find companion coil comp set
   15526             :     int WhichHXAssistedComp; // DO loop counter when DX coil is used in a HX assisted cooling coil
   15527             : 
   15528     3923968 :     DXCoolingCoilIndex = 0;
   15529             : 
   15530             :     DataLoopNode::ConnectionObjectType HeatingCoilTypeNum = static_cast<DataLoopNode::ConnectionObjectType>(
   15531     3923968 :         getEnumValue(BranchNodeConnections::ConnectionObjectTypeNamesUC, Util::makeUPPER(HeatingCoilType)));
   15532             : 
   15533             :     DataLoopNode::ConnectionObjectType CompSetsParentType; // Parent object type which uses DX heating coil pass into this function
   15534     3923968 :     std::string CompSetsParentName;
   15535   133255165 :     for (WhichComp = 1; WhichComp <= state.dataBranchNodeConnections->NumCompSets; ++WhichComp) {
   15536             : 
   15537   139677864 :         if (HeatingCoilTypeNum != state.dataBranchNodeConnections->CompSets(WhichComp).ComponentObjectType ||
   15538     6422699 :             !Util::SameString(HeatingCoilName, state.dataBranchNodeConnections->CompSets(WhichComp).CName))
   15539   129331197 :             continue;
   15540     3923968 :         CompSetsParentType = state.dataBranchNodeConnections->CompSets(WhichComp).ParentObjectType;
   15541     3923968 :         CompSetsParentName = state.dataBranchNodeConnections->CompSets(WhichComp).ParentCName;
   15542     3923968 :         if ((CompSetsParentType == DataLoopNode::ConnectionObjectType::AirLoopHVACUnitaryHeatPumpAirToAir) ||
   15543     3923911 :             (CompSetsParentType == DataLoopNode::ConnectionObjectType::ZoneHVACPackagedTerminalHeatPump) ||
   15544     3923902 :             (CompSetsParentType == DataLoopNode::ConnectionObjectType::AirLoopHVACUnitaryHeatPumpAirToAirMultiSpeed) ||
   15545     3923902 :             (CompSetsParentType == DataLoopNode::ConnectionObjectType::AirLoopHVACUnitaryHeatCoolVAVChangeoverBypass) ||
   15546             :             (CompSetsParentType == DataLoopNode::ConnectionObjectType::AirLoopHVACUnitarySystem)) {
   15547             :             //       Search for DX cooling coils
   15548   145253174 :             for (WhichCompanionComp = 1; WhichCompanionComp <= state.dataBranchNodeConnections->NumCompSets; ++WhichCompanionComp) {
   15549   157006622 :                 if (!Util::SameString(state.dataBranchNodeConnections->CompSets(WhichCompanionComp).ParentCName, CompSetsParentName) ||
   15550    15677356 :                     (state.dataBranchNodeConnections->CompSets(WhichCompanionComp).ComponentObjectType !=
   15551             :                      DataLoopNode::ConnectionObjectType::CoilCoolingDXSingleSpeed))
   15552   141329206 :                     continue;
   15553             :                 DXCoolingCoilIndex =
   15554          60 :                     Util::FindItemInList(state.dataBranchNodeConnections->CompSets(WhichCompanionComp).CName, state.dataDXCoils->DXCoil);
   15555          60 :                 break;
   15556             :             }
   15557   145253803 :             for (WhichCompanionComp = 1; WhichCompanionComp <= state.dataBranchNodeConnections->NumCompSets; ++WhichCompanionComp) {
   15558   157007345 :                 if (!Util::SameString(state.dataBranchNodeConnections->CompSets(WhichCompanionComp).ParentCName, CompSetsParentName) ||
   15559    15677496 :                     (state.dataBranchNodeConnections->CompSets(WhichCompanionComp).ComponentObjectType !=
   15560             :                      DataLoopNode::ConnectionObjectType::CoilCoolingDXMultiSpeed))
   15561   141329835 :                     continue;
   15562             :                 DXCoolingCoilIndex =
   15563          14 :                     Util::FindItemInList(state.dataBranchNodeConnections->CompSets(WhichCompanionComp).CName, state.dataDXCoils->DXCoil);
   15564          14 :                 break;
   15565             :             }
   15566             :             //       Search for Heat Exchanger Assisted DX cooling coils
   15567     3923968 :             if (DXCoolingCoilIndex == 0) {
   15568   145252366 :                 for (WhichHXAssistedComp = 1; WhichHXAssistedComp <= state.dataBranchNodeConnections->NumCompSets; ++WhichHXAssistedComp) {
   15569   157005679 :                     if (!Util::SameString(state.dataBranchNodeConnections->CompSets(WhichHXAssistedComp).ParentCName, CompSetsParentName) ||
   15570    15677207 :                         (state.dataBranchNodeConnections->CompSets(WhichHXAssistedComp).ComponentObjectType !=
   15571             :                          DataLoopNode::ConnectionObjectType::CoilSystemCoolingDXHeatExchangerAssisted))
   15572   141328472 :                         continue;
   15573             :                     DataLoopNode::ConnectionObjectType HXCompSetsParentType; // Used when DX cooling coil is a child of a HX assisted cooling coil
   15574           0 :                     HXCompSetsParentType = state.dataBranchNodeConnections->CompSets(WhichHXAssistedComp).ComponentObjectType;
   15575           0 :                     std::string const &HXCompSetsParentName = state.dataBranchNodeConnections->CompSets(WhichHXAssistedComp).CName;
   15576           0 :                     for (WhichCompanionComp = 1; WhichCompanionComp <= state.dataBranchNodeConnections->NumCompSets; ++WhichCompanionComp) {
   15577           0 :                         if (!Util::SameString(state.dataBranchNodeConnections->CompSets(WhichCompanionComp).ParentCName, HXCompSetsParentName) ||
   15578           0 :                             (state.dataBranchNodeConnections->CompSets(WhichCompanionComp).ComponentObjectType !=
   15579             :                              DataLoopNode::ConnectionObjectType::CoilCoolingDXSingleSpeed))
   15580           0 :                             continue;
   15581             :                         DXCoolingCoilIndex =
   15582           0 :                             Util::FindItemInList(state.dataBranchNodeConnections->CompSets(WhichCompanionComp).CName, state.dataDXCoils->DXCoil);
   15583           0 :                         break;
   15584             :                     }
   15585           0 :                     break;
   15586             :                 }
   15587             :             }
   15588     3923968 :         } else {
   15589             :             //     ErrorFound, Coil:Heating:DX:SingleSpeed is used in wrong type of parent object (should never get here)
   15590           0 :             ShowSevereError(state,
   15591           0 :                             format("Configuration error in {}\"{}\"",
   15592           0 :                                    BranchNodeConnections::ConnectionObjectTypeNames[static_cast<int>(CompSetsParentType)],
   15593             :                                    CompSetsParentName));
   15594           0 :             ShowContinueError(state, "DX heating coil not allowed in this configuration.");
   15595           0 :             ShowFatalError(state, "Preceding condition(s) causes termination.");
   15596             :         }
   15597     3923968 :         break;
   15598             :     }
   15599             : 
   15600             :     // Check and warn user is crankcase heater power or max OAT for crankcase heater differs in DX cooling and heating coils
   15601     3923968 :     if (DXCoolingCoilIndex > 0) {
   15602          74 :         if (state.dataDXCoils->DXCoil(DXCoolingCoilIndex).CrankcaseHeaterCapacity != 0.0) {
   15603          14 :             if (state.dataDXCoils->DXCoil(DXCoolingCoilIndex).CrankcaseHeaterCapacity !=
   15604          28 :                     state.dataDXCoils->DXCoil(HeatingCoilIndex).CrankcaseHeaterCapacity ||
   15605          14 :                 state.dataDXCoils->DXCoil(DXCoolingCoilIndex).MaxOATCrankcaseHeater !=
   15606          14 :                     state.dataDXCoils->DXCoil(HeatingCoilIndex).MaxOATCrankcaseHeater) {
   15607           0 :                 ShowWarningError(state, "Crankcase heater capacity or max outdoor temp for crankcase heater operation specified in");
   15608           0 :                 ShowContinueError(state, format("Coil:Cooling:DX:SingleSpeed = {}", state.dataDXCoils->DXCoil(DXCoolingCoilIndex).Name));
   15609           0 :                 ShowContinueError(state, format("is different than that specified in Coil:Heating:DX:SingleSpeed = {}.", HeatingCoilName));
   15610           0 :                 ShowContinueError(state,
   15611           0 :                                   format("Both of these DX coils are part of {}={}.",
   15612           0 :                                          BranchNodeConnections::ConnectionObjectTypeNames[static_cast<int>(CompSetsParentType)],
   15613             :                                          CompSetsParentName));
   15614           0 :                 ShowContinueError(state, "The value specified in the DX heating coil will be used and the simulation continues...");
   15615             :             }
   15616             :         }
   15617             :     }
   15618             : 
   15619     3923968 :     return DXCoolingCoilIndex;
   15620     3923968 : }
   15621             : 
   15622          20 : int GetDXCoilNumberOfSpeeds(EnergyPlusData &state,
   15623             :                             std::string const &CoilType, // must match coil types in this module
   15624             :                             std::string const &CoilName, // must match coil names for the coil type
   15625             :                             bool &ErrorsFound            // set to true if problem
   15626             : )
   15627             : {
   15628             : 
   15629             :     // FUNCTION INFORMATION:
   15630             :     //       AUTHOR         L. Gu
   15631             :     //       DATE WRITTEN   July 2007
   15632             : 
   15633             :     // PURPOSE OF THIS FUNCTION:
   15634             :     // This function looks up the given coil and returns the number of speeds for multispeed coils.
   15635             :     // If incorrect coil type or name is given, ErrorsFound is returned as true.
   15636             : 
   15637             :     // Return value
   15638             :     int NumberOfSpeeds; // returned the number of speed of matched coil
   15639             : 
   15640             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   15641             :     int WhichCoil;
   15642             : 
   15643             :     // Obtains and Allocates DXCoils
   15644          20 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15645           0 :         GetDXCoils(state);
   15646           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15647             :     }
   15648             : 
   15649          20 :     WhichCoil = Util::FindItemInList(CoilName, state.dataDXCoils->DXCoil);
   15650          20 :     if (WhichCoil != 0) {
   15651          20 :         NumberOfSpeeds = state.dataDXCoils->DXCoil(WhichCoil).NumOfSpeeds;
   15652             :     } else {
   15653           0 :         ShowSevereError(state, format("GetDXCoilNumberOfSpeeds: Invalid DX Coil Type=\"{}\" Name=\"{}\"", CoilType, CoilName));
   15654           0 :         ErrorsFound = true;
   15655           0 :         NumberOfSpeeds = 0;
   15656             :     }
   15657             : 
   15658          20 :     return NumberOfSpeeds;
   15659             : }
   15660             : 
   15661      148005 : int GetDXCoilAvailSchPtr(EnergyPlusData &state,
   15662             :                          std::string const &CoilType,            // must match coil types in this module
   15663             :                          std::string const &CoilName,            // must match coil names for the coil type
   15664             :                          bool &ErrorsFound,                      // set to true if problem
   15665             :                          ObjexxFCL::Optional_int_const CoilIndex // Coil index number
   15666             : )
   15667             : {
   15668             : 
   15669             :     // FUNCTION INFORMATION:
   15670             :     //       AUTHOR         Richard Raustad
   15671             :     //       DATE WRITTEN   January 2013
   15672             : 
   15673             :     // PURPOSE OF THIS FUNCTION:
   15674             :     // This function looks up the given coil and returns the availability schedule index.  If
   15675             :     // incorrect coil type or name is given, ErrorsFound is returned as true and schedule index is returned
   15676             :     // as -1.
   15677             : 
   15678             :     // Return value
   15679             :     int SchPtr; // returned availabiltiy schedule of matched coil
   15680             : 
   15681             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   15682             :     int WhichCoil;
   15683             : 
   15684             :     // Obtains and Allocates DXCoils
   15685      148005 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15686           0 :         GetDXCoils(state);
   15687           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15688             :     }
   15689             : 
   15690      148005 :     if (present(CoilIndex)) {
   15691      147880 :         if (CoilIndex == 0) {
   15692           0 :             ShowSevereError(state, "GetDXCoilAvailSchPtr: Invalid index passed = 0");
   15693           0 :             ShowContinueError(state, "... returning DXCoilAvailSchPtr as -1.");
   15694           0 :             ErrorsFound = true;
   15695           0 :             SchPtr = -1;
   15696           0 :             return SchPtr;
   15697             :         } else {
   15698      147880 :             WhichCoil = CoilIndex;
   15699             :         }
   15700             :     } else {
   15701         125 :         WhichCoil = Util::FindItemInList(CoilName, state.dataDXCoils->DXCoil);
   15702             :     }
   15703      148005 :     if (WhichCoil != 0) {
   15704      148005 :         SchPtr = state.dataDXCoils->DXCoil(WhichCoil).SchedPtr;
   15705             :     } else {
   15706           0 :         if (!present(CoilIndex)) {
   15707           0 :             ShowSevereError(state,
   15708           0 :                             format("GetDXCoilAvailSch: Could not find Coil, Type=\"{}\" Name=\"{}\" when accessing coil availability schedule index.",
   15709             :                                    CoilType,
   15710             :                                    CoilName));
   15711             :         }
   15712           0 :         ErrorsFound = true;
   15713           0 :         SchPtr = -1;
   15714             :     }
   15715             : 
   15716      148005 :     return SchPtr;
   15717             : }
   15718             : 
   15719           1 : Real64 GetDXCoilAirFlow(EnergyPlusData &state,
   15720             :                         std::string const &CoilType, // must match coil types in this module
   15721             :                         std::string const &CoilName, // must match coil names for the coil type
   15722             :                         bool &ErrorsFound            // set to true if problem
   15723             : )
   15724             : {
   15725             : 
   15726             :     // FUNCTION INFORMATION:
   15727             :     //       AUTHOR         Richard Raustad
   15728             :     //       DATE WRITTEN   January 2013
   15729             : 
   15730             :     // PURPOSE OF THIS FUNCTION:
   15731             :     // This function looks up the given coil and returns the availability schedule index.  If
   15732             :     // incorrect coil type or name is given, ErrorsFound is returned as true and schedule index is returned
   15733             :     // as -1.
   15734             : 
   15735             :     // Return value
   15736             :     Real64 AirFlow; // returned coil air flow rate
   15737             : 
   15738             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   15739             :     int WhichCoil;
   15740             : 
   15741             :     // Obtains and Allocates DXCoils
   15742           1 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15743           0 :         GetDXCoils(state);
   15744           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15745             :     }
   15746             : 
   15747           1 :     WhichCoil = Util::FindItemInList(CoilName, state.dataDXCoils->DXCoil);
   15748           1 :     if (WhichCoil != 0) {
   15749           1 :         switch (state.dataDXCoils->DXCoil(WhichCoil).DXCoilType_Num) {
   15750           1 :         case HVAC::CoilDX_CoolingSingleSpeed:
   15751             :         case HVAC::CoilDX_CoolingTwoSpeed:
   15752             :         case HVAC::CoilDX_HeatingEmpirical:
   15753             :         case HVAC::CoilDX_CoolingTwoStageWHumControl: {
   15754           1 :             AirFlow = state.dataDXCoils->DXCoil(WhichCoil).RatedAirVolFlowRate(1);
   15755           1 :         } break;
   15756           0 :         case HVAC::CoilDX_MultiSpeedCooling:
   15757             :         case HVAC::CoilDX_MultiSpeedHeating: {
   15758           0 :             AirFlow = state.dataDXCoils->DXCoil(WhichCoil).MSRatedAirVolFlowRate(1);
   15759           0 :         } break;
   15760           0 :         default: {
   15761           0 :             ShowSevereError(
   15762             :                 state,
   15763           0 :                 format("GetDXCoilAirFlow: Could not find Coil, Type=\"{}\" Name=\"{}\" when accessing coil air flow rate.", CoilType, CoilName));
   15764           0 :             ErrorsFound = true;
   15765           0 :             AirFlow = -1.0;
   15766           0 :         } break;
   15767             :         }
   15768             :     } else {
   15769           0 :         ShowSevereError(
   15770           0 :             state, format("GetDXCoilAirFlow: Could not find Coil, Type=\"{}\" Name=\"{}\" when accessing coil air flow rate.", CoilType, CoilName));
   15771           0 :         ErrorsFound = true;
   15772           0 :         AirFlow = -1.0;
   15773             :     }
   15774             : 
   15775           1 :     return AirFlow;
   15776             : }
   15777             : 
   15778         576 : int GetDXCoilCapFTCurveIndex(EnergyPlusData &state,
   15779             :                              int const CoilIndex, // coil index pointer
   15780             :                              bool &ErrorsFound    // set to true if problem
   15781             : )
   15782             : {
   15783             : 
   15784             :     // FUNCTION INFORMATION:
   15785             :     //       AUTHOR         Richard Raustad
   15786             :     //       DATE WRITTEN   August 2013
   15787             : 
   15788             :     // PURPOSE OF THIS FUNCTION:
   15789             :     // This function looks up the given coil and returns the CapFT schedule index.  If
   15790             :     // incorrect coil index is given, ErrorsFound is returned as true and schedule index is returned
   15791             :     // as -1.
   15792             : 
   15793             :     // Return value
   15794             :     int CapFTCurveIndex; // returned coil CapFT curve index
   15795             : 
   15796             :     // Obtains and Allocates DXCoils
   15797         576 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15798           0 :         GetDXCoils(state);
   15799           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15800             :     }
   15801             : 
   15802         576 :     if (CoilIndex != 0) {
   15803         576 :         switch (state.dataDXCoils->DXCoil(CoilIndex).DXCoilType_Num) {
   15804         449 :         case HVAC::CoilDX_CoolingSingleSpeed:
   15805             :         case HVAC::CoilDX_CoolingTwoSpeed:
   15806             :         case HVAC::CoilDX_HeatingEmpirical:
   15807             :         case HVAC::CoilDX_CoolingTwoStageWHumControl: {
   15808         449 :             CapFTCurveIndex = state.dataDXCoils->DXCoil(CoilIndex).CCapFTemp(1);
   15809         449 :         } break;
   15810          51 :         case HVAC::CoilDX_MultiSpeedCooling:
   15811             :         case HVAC::CoilDX_MultiSpeedHeating: {
   15812          51 :             CapFTCurveIndex = state.dataDXCoils->DXCoil(CoilIndex).MSCCapFTemp(state.dataDXCoils->DXCoil(CoilIndex).NumOfSpeeds);
   15813          51 :         } break;
   15814          76 :         case HVAC::CoilVRF_Heating: {
   15815          76 :             CapFTCurveIndex = state.dataDXCoils->DXCoil(CoilIndex).CCapFTemp(1);
   15816          76 :         } break;
   15817           0 :         default: {
   15818             :             //        CALL ShowSevereError(state, 'GetDXCoilCapFTCurveIndex: Could not find Coil, Type="'// &
   15819             :             //             TRIM(cAllCoilTypes(DXCoil(CoilIndex)%DXCoilType_Num))//'" Name="'//TRIM(DXCoil(CoilIndex)%Name)//  &
   15820             :             //              '" when accessing coil capacity as a function of temperture curve.')
   15821           0 :             ErrorsFound = true;
   15822           0 :             CapFTCurveIndex = 0;
   15823           0 :         } break;
   15824             :         }
   15825             :     } else {
   15826             :         //    CALL ShowSevereError(state, 'GetDXCoilCapFTCurveIndex: Could not find Coil, Index = 0'// &
   15827             :         //          ' when accessing coil air flow rate.')
   15828           0 :         ErrorsFound = true;
   15829           0 :         CapFTCurveIndex = 0;
   15830             :     }
   15831             : 
   15832         576 :     return CapFTCurveIndex;
   15833             : }
   15834             : 
   15835        1228 : void SetDXCoolingCoilData(
   15836             :     EnergyPlusData &state,
   15837             :     int const DXCoilNum,                                                     // Number of DX Cooling Coil
   15838             :     bool &ErrorsFound,                                                       // Set to true if certain errors found
   15839             :     ObjexxFCL::Optional_int HeatingCoilPLFCurvePTR,                          // Parameter equivalent of heating coil PLR curve index
   15840             :     ObjexxFCL::Optional<DataHeatBalance::RefrigCondenserType> CondenserType, // Parameter equivalent of condenser type parameter
   15841             :     ObjexxFCL::Optional_int CondenserInletNodeNum,                           // Parameter equivalent of condenser inlet node number
   15842             :     ObjexxFCL::Optional<Real64> MaxOATCrankcaseHeater,                       // Parameter equivalent of condenser Max OAT for Crank Case Heater temp
   15843             :     ObjexxFCL::Optional<Real64> MinOATCooling,                    // Parameter equivalent of condenser Min OAT for compressor cooling operation
   15844             :     ObjexxFCL::Optional<Real64> MaxOATCooling,                    // Parameter equivalent of condenser Max OAT for compressor cooling operation
   15845             :     ObjexxFCL::Optional<Real64> MinOATHeating,                    // Parameter equivalent of condenser Min OAT for compressor heating operation
   15846             :     ObjexxFCL::Optional<Real64> MaxOATHeating,                    // Parameter equivalent of condenser Max OAT for compressor heating operation
   15847             :     ObjexxFCL::Optional<HVAC::OATType> HeatingPerformanceOATType, // Parameter equivalent to condenser entering air temp type (1-db, 2=wb)
   15848             :     ObjexxFCL::Optional<StandardRatings::DefrostStrat> DefrostStrategy,
   15849             :     ObjexxFCL::Optional<StandardRatings::HPdefrostControl> DefrostControl,
   15850             :     ObjexxFCL::Optional_int DefrostEIRPtr,
   15851             :     ObjexxFCL::Optional<Real64> DefrostFraction,
   15852             :     ObjexxFCL::Optional<Real64> DefrostCapacity,
   15853             :     ObjexxFCL::Optional<Real64> MaxOATDefrost,
   15854             :     ObjexxFCL::Optional_bool CoolingCoilPresent,
   15855             :     ObjexxFCL::Optional_bool HeatingCoilPresent,
   15856             :     ObjexxFCL::Optional<Real64> HeatSizeRatio,
   15857             :     ObjexxFCL::Optional<Real64> TotCap,
   15858             :     ObjexxFCL::Optional_int SupplyFanIndex,
   15859             :     ObjexxFCL::Optional_string SupplyFanName,
   15860             :     ObjexxFCL::Optional<HVAC::FanType> supplyFanType)
   15861             : {
   15862             : 
   15863             :     // SUBROUTINE INFORMATION:
   15864             :     //       AUTHOR         Richard Raustad, FSEC
   15865             :     //       DATE WRITTEN   December 2008
   15866             : 
   15867             :     // PURPOSE OF THIS SUBROUTINE:
   15868             :     // This routine was designed to allow the DX coil to access information from a gas or
   15869             :     // electric heating coil when these coils are each used in a parent object.
   15870             :     // Also, this is an illustration of setting Data from an outside source.
   15871             : 
   15872             :     // Using/Aliasing
   15873             : 
   15874             :     // Obtains and Allocates DXCoils
   15875        1228 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   15876           0 :         GetDXCoils(state);
   15877           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   15878             :     }
   15879             : 
   15880        1228 :     if (DXCoilNum <= 0 || DXCoilNum > state.dataDXCoils->NumDXCoils) {
   15881           0 :         ShowSevereError(state,
   15882           0 :                         format("SetDXCoolingCoilData: called with DX Cooling Coil Number out of range={} should be >0 and <{}",
   15883             :                                DXCoilNum,
   15884           0 :                                state.dataDXCoils->NumDXCoils));
   15885           0 :         ErrorsFound = true;
   15886           0 :         return;
   15887             :     }
   15888             : 
   15889        1228 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   15890        1228 :     if (present(HeatingCoilPLFCurvePTR)) {
   15891          48 :         thisDXCoil.HeatingCoilPLFCurvePTR = HeatingCoilPLFCurvePTR;
   15892             :     }
   15893             : 
   15894        1228 :     if (present(CondenserType)) {
   15895         124 :         thisDXCoil.CondenserType = CondenserType;
   15896             :     }
   15897             : 
   15898        1228 :     if (present(CondenserInletNodeNum)) {
   15899         124 :         thisDXCoil.CondenserInletNodeNum(1) = CondenserInletNodeNum;
   15900             :     }
   15901             : 
   15902        1228 :     if (present(MaxOATCrankcaseHeater)) {
   15903         124 :         thisDXCoil.MaxOATCrankcaseHeater = MaxOATCrankcaseHeater;
   15904             :     }
   15905             : 
   15906        1228 :     if (present(MaxOATCooling)) {
   15907          62 :         thisDXCoil.MaxOATCompressor = MaxOATCooling;
   15908             :     }
   15909             : 
   15910        1228 :     if (present(MaxOATHeating)) {
   15911          16 :         thisDXCoil.MaxOATCompressor = MaxOATHeating;
   15912             :     }
   15913             : 
   15914        1228 :     if (present(MinOATCooling)) {
   15915          62 :         thisDXCoil.MinOATCompressor = MinOATCooling;
   15916             :     }
   15917             : 
   15918        1228 :     if (present(MinOATHeating)) {
   15919          62 :         thisDXCoil.MinOATCompressor = MinOATHeating;
   15920             :     }
   15921             : 
   15922        1228 :     if (present(HeatingPerformanceOATType)) {
   15923          62 :         thisDXCoil.HeatingPerformanceOATType = HeatingPerformanceOATType;
   15924             :     }
   15925             : 
   15926        1228 :     if (present(DefrostStrategy)) {
   15927          62 :         thisDXCoil.DefrostStrategy = DefrostStrategy;
   15928             :     }
   15929             : 
   15930        1228 :     if (present(DefrostControl)) {
   15931          62 :         thisDXCoil.DefrostControl = DefrostControl;
   15932             :     }
   15933             : 
   15934        1228 :     if (present(DefrostEIRPtr)) {
   15935          62 :         thisDXCoil.DefrostEIRFT = DefrostEIRPtr;
   15936             :     }
   15937             : 
   15938        1228 :     if (present(DefrostFraction)) {
   15939          62 :         thisDXCoil.DefrostTime = DefrostFraction;
   15940             :     }
   15941             : 
   15942        1228 :     if (present(DefrostCapacity)) {
   15943          62 :         thisDXCoil.DefrostCapacity = DefrostCapacity;
   15944             :     }
   15945             : 
   15946        1228 :     if (present(MaxOATDefrost)) {
   15947          62 :         thisDXCoil.MaxOATDefrost = MaxOATDefrost;
   15948             :     }
   15949             : 
   15950        1228 :     if (present(CoolingCoilPresent)) {
   15951          62 :         thisDXCoil.CoolingCoilPresent = CoolingCoilPresent;
   15952             :     }
   15953             : 
   15954        1228 :     if (present(HeatingCoilPresent)) {
   15955          62 :         thisDXCoil.HeatingCoilPresent = HeatingCoilPresent;
   15956             :     }
   15957             : 
   15958        1228 :     if (present(HeatSizeRatio)) {
   15959           0 :         thisDXCoil.HeatSizeRatio = HeatSizeRatio;
   15960             :     }
   15961             : 
   15962        1228 :     if (present(TotCap)) {
   15963           0 :         thisDXCoil.RatedTotCap(1) = TotCap;
   15964             :     }
   15965             : 
   15966        1228 :     if (present(SupplyFanIndex)) {
   15967          16 :         thisDXCoil.SupplyFanIndex = SupplyFanIndex;
   15968             :     }
   15969             : 
   15970        1228 :     if (present(SupplyFanName)) {
   15971          16 :         thisDXCoil.SupplyFanName = SupplyFanName;
   15972             :     }
   15973             : 
   15974        1228 :     if (present(supplyFanType)) {
   15975          16 :         thisDXCoil.supplyFanType = supplyFanType;
   15976          16 :         if (thisDXCoil.SupplyFanIndex > 0) {
   15977          16 :             state.dataRptCoilSelection->coilSelectionReportObj->setCoilSupplyFanInfo(state,
   15978          16 :                                                                                      thisDXCoil.Name,
   15979          16 :                                                                                      thisDXCoil.DXCoilType,
   15980          16 :                                                                                      state.dataFans->fans(thisDXCoil.SupplyFanIndex)->Name,
   15981          16 :                                                                                      state.dataFans->fans(thisDXCoil.SupplyFanIndex)->type,
   15982             :                                                                                      thisDXCoil.SupplyFanIndex);
   15983             :         }
   15984             :     }
   15985             : }
   15986             : 
   15987           2 : void SetCoilSystemHeatingDXFlag(EnergyPlusData &state,
   15988             :                                 std::string const &CoilType, // must match coil types in this module
   15989             :                                 std::string const &CoilName  // must match coil names for the coil type
   15990             : )
   15991             : {
   15992             : 
   15993             :     // SUBROUTINE INFORMATION:
   15994             :     //       AUTHOR         B. Griffith
   15995             :     //       DATE WRITTEN   Jan. 2012
   15996             : 
   15997             :     // PURPOSE OF THIS SUBROUTINE:
   15998             :     // inform DX heating coil that is is part of a CoilSystem:Heating:DX
   15999             :     // and therefore it need not find its companion cooling coil
   16000             : 
   16001             :     // METHODOLOGY EMPLOYED:
   16002             :     // set value of logical flag FindCompanionUpStreamCoil to true
   16003             : 
   16004             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   16005             :     int WhichCoil;
   16006             : 
   16007             :     // Obtains and Allocates DXCoils
   16008           2 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   16009           0 :         GetDXCoils(state);
   16010           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   16011             :     }
   16012             : 
   16013           2 :     WhichCoil = Util::FindItemInList(CoilName, state.dataDXCoils->DXCoil);
   16014           2 :     if (WhichCoil != 0) {
   16015           2 :         state.dataDXCoils->DXCoil(WhichCoil).FindCompanionUpStreamCoil = false;
   16016             :     } else {
   16017           0 :         ShowSevereError(state, format("SetCoilSystemHeatingDXFlag: Could not find Coil, Type=\"{}\"Name=\"{}\"", CoilType, CoilName));
   16018             :     }
   16019           2 : }
   16020             : 
   16021          67 : void SetCoilSystemCoolingData(EnergyPlusData &state,
   16022             :                               std::string const &CoilName, // must match coil names for the coil type
   16023             :                               std::string const &CoilSystemName)
   16024             : {
   16025             : 
   16026             :     // SUBROUTINE INFORMATION:
   16027             :     //       AUTHOR         B. Griffith
   16028             :     //       DATE WRITTEN   July 2012
   16029             : 
   16030             :     // PURPOSE OF THIS SUBROUTINE:
   16031             :     // inform the child DX coil what the name of its parent is.
   16032             : 
   16033             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   16034             :     int WhichCoil;
   16035             : 
   16036          67 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   16037           0 :         GetDXCoils(state);
   16038           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   16039             :     }
   16040             : 
   16041          67 :     WhichCoil = Util::FindItemInList(CoilName, state.dataDXCoils->DXCoil);
   16042          67 :     if (WhichCoil != 0) {
   16043          67 :         state.dataDXCoils->DXCoil(WhichCoil).CoilSystemName = CoilSystemName;
   16044             :     } else {
   16045           0 :         ShowSevereError(state, format("SetCoilSystemCoolingData: Could not find Coil \"Name=\"{}\"", CoilName));
   16046             :     }
   16047          67 : }
   16048             : 
   16049       39471 : Real64 CalcSHRUserDefinedCurves(EnergyPlusData &state,
   16050             :                                 Real64 const InletDryBulb,     // inlet air dry bulb temperature [C]
   16051             :                                 Real64 const InletWetBulb,     // inlet air wet bulb temperature [C]
   16052             :                                 Real64 const AirMassFlowRatio, // ratio of actual air mass flow to rated air mass flow
   16053             :                                 int const SHRFTempCurveIndex,  // SHR modifier curve index
   16054             :                                 int const SHRFFlowCurveIndex,  // SHR modifier curve index
   16055             :                                 Real64 const SHRRated          // rated sensible heat ratio, user input
   16056             : )
   16057             : {
   16058             : 
   16059             :     // SUBROUTINE INFORMATION:
   16060             :     //       AUTHOR         Bereket Nigusse, FSEC
   16061             :     //       DATE WRITTEN   December 2012
   16062             : 
   16063             :     // PURPOSE OF THIS FUNCTION:
   16064             :     //    Returns the oprating sensible heat ratio for a given Rated SHR abd coil entering
   16065             :     //    air DBT and WBT, and supply air mass flow fraction.
   16066             : 
   16067             :     // METHODOLOGY EMPLOYED:
   16068             :     //    Model uses user specified rated SHR, and SHR modifying curves for temperature and flow
   16069             :     //    fraction.  The curves adjust the rated SHR based on biquadratic curve for temperatures
   16070             :     //    and quadratic function for supply air mass flow ratio (actual vs rated).
   16071             :     //    The biquadratic and quadratic curves are normalized caurves generated from manufacturer's
   16072             :     //    performance data
   16073             : 
   16074             :     // Using/Aliasing
   16075             :     using Curve::CurveValue;
   16076             : 
   16077             :     // Return value
   16078             :     Real64 SHRopr; // operating SHR, corrected for Temp and Flow Fraction
   16079             : 
   16080             :     // FUNCTION LOCAL VARIABLE DECLARATIONS:
   16081             :     Real64 SHRTempModFac; // Sensible Heat Ratio modifier (function of entering wetbulb, entering drybulb)
   16082             :     Real64 SHRFlowModFac; // Sensible Heat Ratio modifier (function of actual vs rated flow)
   16083             : 
   16084             :     //   Get SHR modifying factor (function of inlet wetbulb & drybulb) for off-rated conditions
   16085       39471 :     if (SHRFTempCurveIndex == 0) {
   16086           0 :         SHRTempModFac = 1.0;
   16087             :     } else {
   16088       39471 :         SHRTempModFac = CurveValue(state, SHRFTempCurveIndex, InletWetBulb, InletDryBulb);
   16089       39471 :         if (SHRTempModFac < 0.0) {
   16090           0 :             SHRTempModFac = 0.0;
   16091             :         }
   16092             :     }
   16093             :     //   Get SHR modifying factor (function of mass flow ratio) for off-rated conditions
   16094       39471 :     if (SHRFFlowCurveIndex == 0) {
   16095           0 :         SHRFlowModFac = 1.0;
   16096             :     } else {
   16097       39471 :         SHRFlowModFac = CurveValue(state, SHRFFlowCurveIndex, AirMassFlowRatio);
   16098       39471 :         if (SHRFlowModFac < 0.0) {
   16099           0 :             SHRFlowModFac = 0.0;
   16100             :         }
   16101             :     }
   16102             :     //  Calculate "operating" sensible heat ratio
   16103       39471 :     SHRopr = SHRRated * SHRTempModFac * SHRFlowModFac;
   16104             : 
   16105       39471 :     if (SHRopr < 0.0) SHRopr = 0.0; // SHR cannot be less than zero
   16106       39471 :     if (SHRopr > 1.0) SHRopr = 1.0; // SHR cannot be greater than 1.0
   16107             : 
   16108       39471 :     return SHRopr;
   16109             : }
   16110             : 
   16111           5 : void SetDXCoilTypeData(EnergyPlusData &state, std::string const &CoilName) // must match coil names for the coil type
   16112             : {
   16113             : 
   16114             :     // SUBROUTINE INFORMATION:
   16115             :     //       AUTHOR         B. Nigusse
   16116             :     //       DATE WRITTEN   January 2013
   16117             : 
   16118             :     // PURPOSE OF THIS SUBROUTINE:
   16119             :     // inform the child DX coil if the DX cooling coil is for 100% DOAS application.
   16120             : 
   16121             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   16122             :     int WhichCoil;
   16123             : 
   16124           5 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   16125           0 :         GetDXCoils(state);
   16126           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   16127             :     }
   16128             : 
   16129           5 :     WhichCoil = Util::FindItemInList(CoilName, state.dataDXCoils->DXCoil);
   16130           5 :     if (WhichCoil != 0) {
   16131           5 :         state.dataDXCoils->DXCoil(WhichCoil).ISHundredPercentDOASDXCoil = true;
   16132             :     } else {
   16133             :         // DXCoil(WhichCoil)%ISHundredPercentDOASDXCoil = .FALSE. //Autodesk:BoundsViolation DXCoil(0): DXCoil is not allocated with a 0
   16134             :         // element: Commented out
   16135           0 :         ShowSevereError(state, format("SetDXCoilTypeData: Could not find Coil \"Name=\"{}\"", CoilName));
   16136             :     }
   16137           5 : }
   16138             : 
   16139      163851 : void CalcSecondaryDXCoils(EnergyPlusData &state, int const DXCoilNum)
   16140             : {
   16141             : 
   16142             :     // SUBROUTINE INFORMATION:
   16143             :     //       AUTHOR         B. Nigusse
   16144             :     //       DATE WRITTEN   February 2015
   16145             : 
   16146             :     // PURPOSE OF THIS SUBROUTINE:
   16147             :     // Calculates secondary zone heat gain from secondary DX coils placed in a zone.
   16148             : 
   16149             :     // METHODOLOGY EMPLOYED:
   16150             :     // Energy balance:
   16151             :     //  (1) Condenser placed in a zone, the zone total (sensible) heat
   16152             :     //      gain rate is given Qcond = QEvap + WcompPluscondFanPower
   16153             :     //  (2) Evaporator placed in a zone, the zone total heat removal
   16154             :     //      rate is given Qevap = Qcond - WcompPluscondFanPower
   16155             :     //      Furthermore, the evaporator total heat removal is split into
   16156             :     //      latent and sensible components using user specified SHR
   16157             : 
   16158             :     // Using/Aliasing
   16159             :     using Curve::CurveValue;
   16160             : 
   16161             :     // SUBROUTINE PARAMETER DEFINITIONS:
   16162             :     static constexpr std::string_view RoutineName("CalcSecondaryDXCoils");
   16163             : 
   16164             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   16165             :     Real64 CondInletDryBulb;       // condenser entering air dry-bulb temperature (C)
   16166             :     Real64 EvapAirMassFlow;        // Condenser air mass flow rate [kg/s]
   16167             :     Real64 EvapInletDryBulb;       // evaporator inlet air drybulb [C]
   16168             :     Real64 EvapInletHumRat;        // evaporator inlet air humidity ratio [kg/kg]
   16169             :     Real64 EvapInletWetBulb;       // evaporator inlet air wetbulb [C]
   16170             :     Real64 EvapInletEnthalpy;      // evaporator inlet air enthalpy [J/kg]
   16171             :     Real64 FullLoadOutAirEnth;     // evaporator outlet full load enthalpy [J/kg]
   16172             :     Real64 FullLoadOutAirHumRat;   // evaporator outlet humidity ratio at full load
   16173             :     Real64 FullLoadOutAirTemp;     // evaporator outlet air temperature at full load [C]
   16174             :     Real64 hTinwout;               // Enthalpy at inlet dry-bulb and outlet humidity ratio [J/kg]
   16175      163851 :     Real64 SHR(0);                 // sensible heat ratio
   16176             :     Real64 RhoAir;                 // secondary coil entering air density [kg/m3]
   16177      163851 :     Real64 PartLoadRatio(0);       // primary coil part-load ratio [-]
   16178             :     Real64 SecCoilRatedSHR;        // secondary DX coil nominal or rated sensible heat ratio
   16179             :     Real64 SecCoilFlowFraction;    // secondary coil flow fraction, is 1.0 for single speed machine
   16180             :     Real64 TotalHeatRemovalRate;   // secondary coil total heat removal rate
   16181             :     Real64 TotalHeatRejectionRate; // secondary coil total heat rejection rate
   16182             :     int SecCoilSHRFT;              // index of the SHR modifier curve for temperature of a secondary DX coil
   16183             :     int SecCoilSHRFF;              // index of the sHR modifier curve for flow fraction of a secondary DX coil
   16184             :     int MSSpeedNumLS;              // current low speed number of multspeed HP
   16185             :     int MSSpeedNumHS;              // current high speed number of multspeed HP
   16186             :     Real64 MSSpeedRatio;           // current speed ratio of multspeed HP
   16187             :     Real64 MSCycRatio;             // current cycling ratio of multspeed HP
   16188             :     Real64 SHRHighSpeed;           // sensible heat ratio at high speed
   16189             :     Real64 SHRLowSpeed;            // sensible heat ratio at low speed
   16190             : 
   16191      163851 :     EvapAirMassFlow = 0.0;
   16192             : 
   16193      163851 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   16194             : 
   16195      163851 :     if (thisDXCoil.IsSecondaryDXCoilInZone) {
   16196      163851 :         auto &secZoneHB = state.dataZoneTempPredictorCorrector->zoneHeatBalance(thisDXCoil.SecZonePtr);
   16197             :         // Select the correct unit type
   16198      163851 :         switch (thisDXCoil.DXCoilType_Num) {
   16199       81926 :         case HVAC::CoilDX_CoolingSingleSpeed:
   16200             :         case HVAC::CoilDX_CoolingTwoSpeed:
   16201             :         case HVAC::CoilDX_MultiSpeedCooling: {
   16202             :             // total sensible heat gain of the secondary zone from the secondary coil (condenser)
   16203       81926 :             if (thisDXCoil.ElecCoolingPower > 0.0) {
   16204       18553 :                 TotalHeatRejectionRate = thisDXCoil.TotalCoolingEnergyRate + thisDXCoil.ElecCoolingPower;
   16205             :             } else {
   16206       63373 :                 TotalHeatRejectionRate = 0.0;
   16207       63373 :                 return;
   16208             :             }
   16209       18553 :             thisDXCoil.SecCoilSensibleHeatGainRate = TotalHeatRejectionRate;
   16210       18553 :         } break;
   16211       81925 :         case HVAC::CoilDX_HeatingEmpirical: {
   16212             :             // evaporator coil in the secondary zone
   16213       81925 :             if (thisDXCoil.ElecHeatingPower > 0.0) {
   16214       30261 :                 TotalHeatRemovalRate = max(0.0, thisDXCoil.TotalHeatingEnergyRate - thisDXCoil.ElecHeatingPower);
   16215             :             } else {
   16216       51664 :                 TotalHeatRemovalRate = 0.0;
   16217       51664 :                 thisDXCoil.SecCoilSHR = 0.0;
   16218       51664 :                 return;
   16219             :             }
   16220       30261 :             thisDXCoil.SecCoilTotalHeatRemovalRate = -TotalHeatRemovalRate; // +DXCoil( DXCoilNum ).DefrostPower;
   16221       30261 :             EvapInletDryBulb = secZoneHB.ZT;
   16222       30261 :             EvapInletHumRat = secZoneHB.airHumRat;
   16223       30261 :             RhoAir = PsyRhoAirFnPbTdbW(state, state.dataEnvrn->OutBaroPress, EvapInletDryBulb, EvapInletHumRat);
   16224       30261 :             EvapAirMassFlow = RhoAir * thisDXCoil.SecCoilAirFlow;
   16225             :             ;
   16226       30261 :             PartLoadRatio = thisDXCoil.CompressorPartLoadRatio;
   16227       30261 :             SecCoilRatedSHR = thisDXCoil.SecCoilRatedSHR;
   16228       30261 :             if ((EvapAirMassFlow > HVAC::SmallMassFlow) && (PartLoadRatio > 0.0) &&
   16229       30261 :                 (EvapInletDryBulb > thisDXCoil.MinOATCompressor)) { // coil is running
   16230       30261 :                 SecCoilFlowFraction = 1.0;                          // for single speed DX coil the secondary coil (condenser) flow fraction is 1.0
   16231       30261 :                 CondInletDryBulb = state.dataLoopNodes->Node(thisDXCoil.AirInNode).Temp;
   16232       30261 :                 EvapInletWetBulb = PsyTwbFnTdbWPb(state, EvapInletDryBulb, EvapInletHumRat, state.dataEnvrn->OutBaroPress, RoutineName);
   16233       30261 :                 EvapInletEnthalpy = PsyHFnTdbW(EvapInletDryBulb, EvapInletHumRat);
   16234       30261 :                 SecCoilSHRFT = thisDXCoil.SecCoilSHRFT;
   16235       30261 :                 SecCoilSHRFF = thisDXCoil.SecCoilSHRFF;
   16236             :                 // determine the current SHR
   16237       30261 :                 SHR = CalcSecondaryDXCoilsSHR(state,
   16238             :                                               DXCoilNum,
   16239             :                                               EvapAirMassFlow,
   16240             :                                               TotalHeatRemovalRate,
   16241             :                                               PartLoadRatio,
   16242             :                                               SecCoilRatedSHR,
   16243             :                                               EvapInletDryBulb,
   16244             :                                               EvapInletHumRat,
   16245             :                                               EvapInletWetBulb,
   16246             :                                               EvapInletEnthalpy,
   16247             :                                               CondInletDryBulb,
   16248             :                                               SecCoilFlowFraction,
   16249             :                                               SecCoilSHRFT,
   16250             :                                               SecCoilSHRFF);
   16251             :                 // Calculate full load output conditions
   16252       30261 :                 FullLoadOutAirEnth = EvapInletEnthalpy - (TotalHeatRemovalRate / PartLoadRatio) / EvapAirMassFlow;
   16253       30261 :                 hTinwout = EvapInletEnthalpy - (1.0 - SHR) * ((TotalHeatRemovalRate / PartLoadRatio) / EvapAirMassFlow);
   16254       30261 :                 FullLoadOutAirHumRat = PsyWFnTdbH(state, EvapInletDryBulb, hTinwout, RoutineName, true);
   16255       30261 :                 FullLoadOutAirTemp = PsyTdbFnHW(FullLoadOutAirEnth, FullLoadOutAirHumRat);
   16256             :                 // when the air outlet temperature falls below the saturation temperature, it is reset to saturation temperature
   16257       30261 :                 if (FullLoadOutAirTemp < PsyTsatFnHPb(state, FullLoadOutAirEnth, state.dataEnvrn->OutBaroPress, RoutineName)) {
   16258           0 :                     FullLoadOutAirTemp = PsyTsatFnHPb(state, FullLoadOutAirEnth, state.dataEnvrn->OutBaroPress, RoutineName);
   16259           0 :                     FullLoadOutAirHumRat = PsyWFnTdbH(state, FullLoadOutAirTemp, FullLoadOutAirEnth, RoutineName);
   16260             :                     // Adjust SHR for the new outlet condition that balances energy
   16261           0 :                     hTinwout = PsyHFnTdbW(EvapInletDryBulb, FullLoadOutAirHumRat);
   16262           0 :                     SHR = 1.0 - (EvapInletEnthalpy - hTinwout) / ((TotalHeatRemovalRate / PartLoadRatio) / EvapAirMassFlow);
   16263           0 :                     SHR = min(SHR, 1.0);
   16264             :                 }
   16265             :                 // calculate the sensible and latent zone heat removal (extraction) rate by the secondary coil
   16266       30261 :                 thisDXCoil.SecCoilSensibleHeatRemovalRate = thisDXCoil.SecCoilTotalHeatRemovalRate * SHR;
   16267       30261 :                 thisDXCoil.SecCoilLatentHeatRemovalRate = thisDXCoil.SecCoilTotalHeatRemovalRate - thisDXCoil.SecCoilSensibleHeatRemovalRate;
   16268             :             } else {
   16269             :                 // DX coil is off;
   16270           0 :                 thisDXCoil.SecCoilTotalHeatRemovalRate = 0.0;
   16271           0 :                 thisDXCoil.SecCoilSensibleHeatRemovalRate = 0.0;
   16272           0 :                 thisDXCoil.SecCoilLatentHeatRemovalRate = 0.0;
   16273           0 :                 SHR = 0.0; // SHR is set to zero if the coil is off
   16274             :             }
   16275       30261 :             thisDXCoil.SecCoilSHR = SHR;
   16276       30261 :         } break;
   16277           0 :         case HVAC::CoilDX_MultiSpeedHeating: {
   16278           0 :             EvapInletDryBulb = secZoneHB.ZT;
   16279           0 :             EvapInletHumRat = secZoneHB.airHumRat;
   16280           0 :             RhoAir = PsyRhoAirFnPbTdbW(state, state.dataEnvrn->OutBaroPress, EvapInletDryBulb, EvapInletHumRat);
   16281           0 :             MSSpeedRatio = thisDXCoil.MSSpeedRatio;
   16282           0 :             MSCycRatio = thisDXCoil.MSCycRatio;
   16283           0 :             MSSpeedNumHS = thisDXCoil.MSSpeedNumHS;
   16284           0 :             MSSpeedNumLS = thisDXCoil.MSSpeedNumLS;
   16285           0 :             if (MSSpeedRatio > 0.0) {
   16286           0 :                 EvapAirMassFlow = RhoAir * (thisDXCoil.MSSecCoilAirFlow(MSSpeedNumHS) * MSSpeedRatio +
   16287           0 :                                             thisDXCoil.MSSecCoilAirFlow(MSSpeedNumLS) * (1.0 - MSSpeedRatio));
   16288           0 :             } else if (MSCycRatio > 0.0) {
   16289           0 :                 EvapAirMassFlow = RhoAir * thisDXCoil.MSSecCoilAirFlow(MSSpeedNumLS);
   16290             :             }
   16291           0 :             if (thisDXCoil.ElecHeatingPower > 0.0) {
   16292           0 :                 TotalHeatRemovalRate = max(0.0, thisDXCoil.TotalHeatingEnergyRate - thisDXCoil.ElecHeatingPower);
   16293             :             } else {
   16294           0 :                 TotalHeatRemovalRate = 0.0;
   16295           0 :                 return;
   16296             :             }
   16297           0 :             thisDXCoil.SecCoilTotalHeatRemovalRate = -TotalHeatRemovalRate; // +DXCoil( DXCoilNum ).DefrostPower;
   16298           0 :             if ((EvapAirMassFlow > HVAC::SmallMassFlow) && (MSSpeedRatio > 0.0 || MSCycRatio > 0.0) &&
   16299           0 :                 (EvapInletDryBulb > thisDXCoil.MinOATCompressor)) { // coil is running
   16300           0 :                 SecCoilFlowFraction = 1.0;                          // for single speed DX coil the secondary coil (condenser) flow fraction is 1.0
   16301           0 :                 CondInletDryBulb = state.dataLoopNodes->Node(thisDXCoil.AirInNode).Temp;
   16302           0 :                 EvapInletWetBulb = PsyTwbFnTdbWPb(state, EvapInletDryBulb, EvapInletHumRat, state.dataEnvrn->OutBaroPress, RoutineName);
   16303           0 :                 EvapInletEnthalpy = PsyHFnTdbW(EvapInletDryBulb, EvapInletHumRat);
   16304             :                 // determine the current SHR
   16305           0 :                 if (MSSpeedRatio > 0.0) {
   16306             :                     // calculate SHR for the higher speed
   16307           0 :                     PartLoadRatio = 1.0;
   16308           0 :                     SecCoilFlowFraction = 1.0;
   16309           0 :                     SecCoilSHRFT = thisDXCoil.MSSecCoilSHRFT(MSSpeedNumHS);
   16310           0 :                     SecCoilSHRFF = thisDXCoil.MSSecCoilSHRFF(MSSpeedNumHS);
   16311           0 :                     SecCoilRatedSHR = thisDXCoil.MSSecCoilRatedSHR(MSSpeedNumHS);
   16312           0 :                     SHRHighSpeed = CalcSecondaryDXCoilsSHR(state,
   16313             :                                                            DXCoilNum,
   16314             :                                                            EvapAirMassFlow,
   16315             :                                                            TotalHeatRemovalRate,
   16316             :                                                            PartLoadRatio,
   16317             :                                                            SecCoilRatedSHR,
   16318             :                                                            EvapInletDryBulb,
   16319             :                                                            EvapInletHumRat,
   16320             :                                                            EvapInletWetBulb,
   16321             :                                                            EvapInletEnthalpy,
   16322             :                                                            CondInletDryBulb,
   16323             :                                                            SecCoilFlowFraction,
   16324             :                                                            SecCoilSHRFT,
   16325             :                                                            SecCoilSHRFF);
   16326             :                     // calculate SHR for the lower speed
   16327           0 :                     SecCoilSHRFT = thisDXCoil.MSSecCoilSHRFT(MSSpeedNumLS);
   16328           0 :                     SecCoilSHRFF = thisDXCoil.MSSecCoilSHRFF(MSSpeedNumLS);
   16329           0 :                     SecCoilRatedSHR = thisDXCoil.MSSecCoilRatedSHR(MSSpeedNumLS);
   16330           0 :                     SHRLowSpeed = CalcSecondaryDXCoilsSHR(state,
   16331             :                                                           DXCoilNum,
   16332             :                                                           EvapAirMassFlow,
   16333             :                                                           TotalHeatRemovalRate,
   16334             :                                                           PartLoadRatio,
   16335             :                                                           SecCoilRatedSHR,
   16336             :                                                           EvapInletDryBulb,
   16337             :                                                           EvapInletHumRat,
   16338             :                                                           EvapInletWetBulb,
   16339             :                                                           EvapInletEnthalpy,
   16340             :                                                           CondInletDryBulb,
   16341             :                                                           SecCoilFlowFraction,
   16342             :                                                           SecCoilSHRFT,
   16343             :                                                           SecCoilSHRFF);
   16344           0 :                     SHR = SHRHighSpeed * MSSpeedRatio + SHRLowSpeed * (1.0 - MSSpeedRatio);
   16345             : 
   16346           0 :                 } else if (MSCycRatio > 0.0) {
   16347             :                     // calculate SHR for the lower speed
   16348           0 :                     PartLoadRatio = MSCycRatio;
   16349           0 :                     SecCoilSHRFT = thisDXCoil.MSSecCoilSHRFT(MSSpeedNumLS);
   16350           0 :                     SecCoilSHRFF = thisDXCoil.MSSecCoilSHRFF(MSSpeedNumLS);
   16351           0 :                     SecCoilRatedSHR = thisDXCoil.MSSecCoilRatedSHR(MSSpeedNumLS);
   16352           0 :                     SecCoilFlowFraction = 1.0;
   16353           0 :                     SHRLowSpeed = CalcSecondaryDXCoilsSHR(state,
   16354             :                                                           DXCoilNum,
   16355             :                                                           EvapAirMassFlow,
   16356             :                                                           TotalHeatRemovalRate,
   16357             :                                                           MSCycRatio,
   16358             :                                                           SecCoilRatedSHR,
   16359             :                                                           EvapInletDryBulb,
   16360             :                                                           EvapInletHumRat,
   16361             :                                                           EvapInletWetBulb,
   16362             :                                                           EvapInletEnthalpy,
   16363             :                                                           CondInletDryBulb,
   16364             :                                                           SecCoilFlowFraction,
   16365             :                                                           SecCoilSHRFT,
   16366             :                                                           SecCoilSHRFF);
   16367           0 :                     SHR = SHRLowSpeed;
   16368             :                 }
   16369             :                 // Calculate full load output conditions
   16370           0 :                 FullLoadOutAirEnth = EvapInletEnthalpy - (TotalHeatRemovalRate / PartLoadRatio) / EvapAirMassFlow;
   16371           0 :                 hTinwout = EvapInletEnthalpy - (1.0 - SHR) * ((TotalHeatRemovalRate / PartLoadRatio) / EvapAirMassFlow);
   16372           0 :                 FullLoadOutAirHumRat = PsyWFnTdbH(state, EvapInletDryBulb, hTinwout, RoutineName, true);
   16373           0 :                 FullLoadOutAirTemp = PsyTdbFnHW(FullLoadOutAirEnth, FullLoadOutAirHumRat);
   16374             :                 // when the air outlet temperature falls below the saturation temperature, it is reset to saturation temperature
   16375           0 :                 if (FullLoadOutAirTemp < PsyTsatFnHPb(state, FullLoadOutAirEnth, state.dataEnvrn->OutBaroPress, RoutineName)) {
   16376           0 :                     FullLoadOutAirTemp = PsyTsatFnHPb(state, FullLoadOutAirEnth, state.dataEnvrn->OutBaroPress, RoutineName);
   16377           0 :                     FullLoadOutAirHumRat = PsyWFnTdbH(state, FullLoadOutAirTemp, FullLoadOutAirEnth, RoutineName);
   16378             :                     // Adjust SHR for the new outlet condition that balances energy
   16379           0 :                     hTinwout = PsyHFnTdbW(EvapInletDryBulb, FullLoadOutAirHumRat);
   16380           0 :                     SHR = 1.0 - (EvapInletEnthalpy - hTinwout) / (TotalHeatRemovalRate / PartLoadRatio) / EvapAirMassFlow;
   16381           0 :                     SHR = min(SHR, 1.0);
   16382             :                 }
   16383             :                 // calculate the sensible and latent zone heat removal (extraction) rate by the secondary coil
   16384           0 :                 thisDXCoil.SecCoilSensibleHeatRemovalRate = thisDXCoil.SecCoilTotalHeatRemovalRate * SHR;
   16385           0 :                 thisDXCoil.SecCoilLatentHeatRemovalRate = thisDXCoil.SecCoilTotalHeatRemovalRate - thisDXCoil.SecCoilSensibleHeatRemovalRate;
   16386             :             } else {
   16387             :                 // DX coil is off;
   16388           0 :                 thisDXCoil.SecCoilTotalHeatRemovalRate = 0.0;
   16389           0 :                 thisDXCoil.SecCoilSensibleHeatRemovalRate = 0.0;
   16390           0 :                 thisDXCoil.SecCoilLatentHeatRemovalRate = 0.0;
   16391           0 :                 SHR = 0.0; // SHR is set to rated value if the coil is off
   16392             :             }
   16393           0 :             thisDXCoil.SecCoilSHR = SHR;
   16394           0 :         } break;
   16395           0 :         default:
   16396           0 :             break;
   16397             :         }
   16398             : 
   16399             :     } else {
   16400           0 :         thisDXCoil.SecCoilSensibleHeatGainRate = 0.0;
   16401           0 :         thisDXCoil.SecCoilTotalHeatRemovalRate = 0.0;
   16402           0 :         thisDXCoil.SecCoilSensibleHeatRemovalRate = 0.0;
   16403           0 :         thisDXCoil.SecCoilLatentHeatRemovalRate = 0.0;
   16404             :     }
   16405             : }
   16406             : 
   16407       30261 : Real64 CalcSecondaryDXCoilsSHR(EnergyPlusData &state,
   16408             :                                [[maybe_unused]] int const DXCoilNum,
   16409             :                                Real64 const EvapAirMassFlow,
   16410             :                                Real64 const TotalHeatRemovalRate,
   16411             :                                Real64 const PartLoadRatio,
   16412             :                                Real64 const SecCoilRatedSHR,
   16413             :                                Real64 const EvapInletDryBulb,
   16414             :                                Real64 const EvapInletHumRat,
   16415             :                                Real64 const EvapInletWetBulb,
   16416             :                                Real64 const EvapInletEnthalpy,
   16417             :                                Real64 const CondInletDryBulb,
   16418             :                                Real64 const SecCoilFlowFraction,
   16419             :                                int const SecCoilSHRFT,
   16420             :                                int const SecCoilSHRFF)
   16421             : {
   16422             : 
   16423             :     // SUBROUTINE INFORMATION:
   16424             :     //       AUTHOR         B. Nigusse
   16425             :     //       DATE WRITTEN   February 2015
   16426             : 
   16427             :     // PURPOSE OF THIS SUBROUTINE:
   16428             :     // Calculates secondary coil (evaporator) sensible heat ratio.
   16429             : 
   16430             :     // METHODOLOGY EMPLOYED:
   16431             :     // Energy balance:
   16432             :     //  (1) checks if the seconday coil operation is dry and calculates appliavle SHR.
   16433             :     //  (2) determines SHR from user specified rated SHR values and SHR modifier curves for
   16434             :     //      temperature and flor fraction.
   16435             :     //  (3) if secondary coil operates dry then the larger of the user SHR value and dry
   16436             :     //      coil operation SHR is selected.
   16437             : 
   16438             :     // Using/Aliasing
   16439             :     using Curve::CurveValue;
   16440             : 
   16441             :     // SUBROUTINE PARAMETER DEFINITIONS:
   16442       30261 :     int constexpr MaxIter(30);
   16443       30261 :     Real64 constexpr RelaxationFactor(0.4);
   16444       30261 :     Real64 constexpr Tolerance(0.1);
   16445       30261 :     Real64 constexpr DryCoilTestEvapInletHumRatReset(0.00001);
   16446             :     static constexpr std::string_view RoutineName("CalcSecondaryDXCoilsSHR");
   16447             : 
   16448             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   16449             :     Real64 DryCoilTestEvapInletHumRat;  // evaporator coil inlet humidity ratio test for dry coil
   16450             :     Real64 DryCoilTestEvapInletWetBulb; // evaporator coil inlet dry bulb temperature test for dry coil
   16451             :     Real64 FullLoadOutAirEnth;          // evaporator outlet full load enthalpy [J/kg]
   16452             :     Real64 FullLoadOutAirTemp;          // evaporator outlet air temperature at full load [C]
   16453             :     Real64 hTinwADP;                    // enthaly of air at secondary coil entering temperature and Humidity ratio at ADP
   16454             :     Real64 SHRadp;                      // Sensible heat ratio
   16455             :     Real64 hADP;                        // enthaly of air at secondary coil at ADP
   16456             :     Real64 tADP;                        // dry bulb temperature of air at secondary coil at ADP
   16457             :     Real64 wADP;                        // humidity ratio of air at secondary coil at ADP
   16458             :     Real64 HumRatError;                 // humidity ratio error
   16459             :     bool CoilMightBeDry;                // TRUE means the secondary DX coi runs dry
   16460             :     int Counter;                        // iteration counter
   16461             :     bool Converged;                     // convergence flag
   16462             :     Real64 SHR;                         // current time step sensible heat ratio of secondary coil
   16463             : 
   16464       30261 :     CoilMightBeDry = false;
   16465       30261 :     FullLoadOutAirEnth = EvapInletEnthalpy - (TotalHeatRemovalRate / PartLoadRatio) / EvapAirMassFlow;
   16466       30261 :     FullLoadOutAirTemp = PsyTdbFnHW(FullLoadOutAirEnth, EvapInletHumRat);
   16467       30261 :     if (FullLoadOutAirTemp > PsyTsatFnHPb(state, FullLoadOutAirEnth, state.dataEnvrn->OutBaroPress, RoutineName)) {
   16468       30261 :         CoilMightBeDry = true;
   16469             :         // find wADP, humidity ratio at apparatus dewpoint and inlet hum rat that would have dry coil
   16470       30261 :         DryCoilTestEvapInletHumRat = EvapInletHumRat;
   16471       30261 :         DryCoilTestEvapInletWetBulb = EvapInletWetBulb;
   16472       30261 :         Counter = 0;
   16473       30261 :         Converged = false;
   16474       60522 :         while (!Converged) {
   16475             :             // assumes coil bypass factor (CBF) = 0.0
   16476       30261 :             hADP = EvapInletEnthalpy - (TotalHeatRemovalRate / PartLoadRatio) / EvapAirMassFlow;
   16477       30261 :             tADP = PsyTsatFnHPb(state, hADP, state.dataEnvrn->OutBaroPress, RoutineName);
   16478       30261 :             wADP = min(EvapInletHumRat, PsyWFnTdbH(state, tADP, hADP, RoutineName));
   16479       30261 :             hTinwADP = PsyHFnTdbW(EvapInletDryBulb, wADP);
   16480       30261 :             if ((EvapInletEnthalpy - hADP) > 1.e-10) {
   16481       30261 :                 SHRadp = min((hTinwADP - hADP) / (EvapInletEnthalpy - hADP), 1.0);
   16482             :             } else {
   16483           0 :                 SHRadp = 1.0;
   16484             :             }
   16485       30261 :             if ((wADP > DryCoilTestEvapInletHumRat) || (Counter >= 1 && Counter < MaxIter)) {
   16486           0 :                 if (DryCoilTestEvapInletHumRat <= 0.0) DryCoilTestEvapInletHumRat = DryCoilTestEvapInletHumRatReset;
   16487           0 :                 HumRatError = (DryCoilTestEvapInletHumRat - wADP) / DryCoilTestEvapInletHumRat;
   16488           0 :                 DryCoilTestEvapInletHumRat = RelaxationFactor * wADP + (1.0 - RelaxationFactor) * DryCoilTestEvapInletHumRat;
   16489             :                 DryCoilTestEvapInletWetBulb =
   16490           0 :                     PsyTwbFnTdbWPb(state, EvapInletDryBulb, DryCoilTestEvapInletHumRat, state.dataEnvrn->OutBaroPress, RoutineName);
   16491           0 :                 ++Counter;
   16492           0 :                 if (std::abs(HumRatError) <= Tolerance) {
   16493           0 :                     Converged = true;
   16494             :                 } else {
   16495           0 :                     Converged = false;
   16496             :                 }
   16497             :             } else {
   16498       30261 :                 Converged = true;
   16499             :             }
   16500             :         }
   16501             :     }
   16502             :     // determine SHR from user specified nominal value and SHR modifier curves
   16503       30261 :     SHR = CalcSHRUserDefinedCurves(state, CondInletDryBulb, EvapInletWetBulb, SecCoilFlowFraction, SecCoilSHRFT, SecCoilSHRFF, SecCoilRatedSHR);
   16504       30261 :     if (CoilMightBeDry) {
   16505       30261 :         if ((EvapInletHumRat < DryCoilTestEvapInletHumRat) && (SHRadp > SHR)) { // coil is dry for sure
   16506           0 :             SHR = 1.0;
   16507       30261 :         } else if (SHRadp > SHR) {
   16508           0 :             SHR = SHRadp;
   16509             :         }
   16510             :     }
   16511       30261 :     return SHR;
   16512             : }
   16513             : 
   16514      683992 : void CalcVRFCoolingCoil_FluidTCtrl(EnergyPlusData &state,
   16515             :                                    int const DXCoilNum,                    // the number of the DX coil to be simulated
   16516             :                                    HVAC::CompressorOp const compressorOp,  // compressor operation; 1=on, 0=off
   16517             :                                    bool const FirstHVACIteration,          // true if this is the first iteration of HVAC
   16518             :                                    Real64 const PartLoadRatio,             // sensible cooling load / full load sensible cooling capacity
   16519             :                                    HVAC::FanOp const fanOp,                // Allows parent object to control fan operation
   16520             :                                    Real64 const CompCycRatio,              // cycling ratio of VRF condenser
   16521             :                                    ObjexxFCL::Optional_int_const PerfMode, // Performance mode for MultiMode DX coil; Always 1 for other coil types
   16522             :                                    ObjexxFCL::Optional<Real64 const> OnOffAirFlowRatio // ratio of compressor on airflow to compressor off airflow
   16523             : )
   16524             : {
   16525             :     // SUBROUTINE INFORMATION:
   16526             :     //       AUTHOR         Xiufeng Pang, LBNL
   16527             :     //       DATE WRITTEN   Jan 2013
   16528             :     //       MODIFIED       Nov 2015, RP Zhang, LBNL
   16529             : 
   16530             :     // PURPOSE OF THIS SUBROUTINE:
   16531             :     //         Calculates the air-side performance of a direct-expansion, air-cooled
   16532             :     //         VRF terminal unit cooling coil, for the VRF_FluidTCtrl model.
   16533             : 
   16534             :     // METHODOLOGY EMPLOYED:
   16535             :     //         This subroutine is derived from CalcVRFCoolingCoil, and implements the new VRF model for FluidTCtrl.
   16536             : 
   16537             :     // Using/Aliasing
   16538             :     using Curve::CurveValue;
   16539      683992 :     Real64 SysTimeElapsed = state.dataHVACGlobal->SysTimeElapsed;
   16540      683992 :     Real64 TimeStepSys = state.dataHVACGlobal->TimeStepSys;
   16541             :     using General::CreateSysTimeIntervalString;
   16542             : 
   16543             :     using namespace HVACVariableRefrigerantFlow;
   16544             : 
   16545             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   16546             : 
   16547             :     Real64 AirMassFlow;       // dry air mass flow rate through coil [kg/s] (adjusted for bypass if any)
   16548             :     Real64 AirVolumeFlowRate; // Air volume flow rate across the cooling coil [m3/s] (adjusted for bypass if any)
   16549             :     // (average flow if cycling fan, full flow if constant fan)
   16550             :     Real64 VolFlowperRatedTotCap; // Air volume flow rate divided by rated total cooling capacity [m3/s-W] (adjusted for bypass)
   16551             :     Real64 TotCap;                // gross total cooling capacity at off-rated conditions [W]
   16552             :     Real64 InletAirDryBulbTemp;   // inlet air dry bulb temperature [C]
   16553             :     Real64 InletAirEnthalpy;      // inlet air enthalpy [J/kg]
   16554             :     Real64 InletAirHumRat;        // inlet air humidity ratio [kg/kg]
   16555             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   16556             :     Real64 RatedCBF;      // coil bypass factor at rated conditions
   16557             :     Real64 CBF;           // coil bypass factor at off rated conditions
   16558             :     Real64 A0;            // NTU * air mass flow rate, used in CBF calculation
   16559             :     Real64 PLF;           // Part load factor, accounts for thermal lag at compressor startup, used in power calculation
   16560             :     Real64 CondInletTemp; // Condenser inlet temperature (C). Outdoor dry-bulb temp for air-cooled condenser.
   16561             :     // Outdoor Wetbulb +(1 - effectiveness)*(outdoor drybulb - outdoor wetbulb) for evap condenser.
   16562             :     Real64 CondInletHumRat; // Condenser inlet humidity ratio (kg/kg). Zero for air-cooled condenser.
   16563             :     // For evap condenser, its the humidity ratio of the air leaving the evap cooling pads.
   16564             :     Real64 CondAirMassFlow;       // Condenser air mass flow rate [kg/s]
   16565             :     Real64 RhoAir;                // Density of air [kg/m3]
   16566             :     Real64 CrankcaseHeatingPower; // power due to crankcase heater
   16567      683992 :     Real64 CompAmbTemp(0.0);      // Ambient temperature at compressor
   16568             :     Real64 AirFlowRatio;          // ratio of compressor on airflow to average timestep airflow
   16569             :     // used when constant fan mode yields different air flow rates when compressor is ON and OFF
   16570             :     // (e.g. Packaged Terminal Heat Pump)
   16571             :     Real64 OutdoorDryBulb;  // Outdoor dry-bulb temperature at condenser (C)
   16572             :     Real64 OutdoorWetBulb;  // Outdoor wet-bulb temperature at condenser (C)
   16573             :     Real64 OutdoorHumRat;   // Outdoor humidity ratio at condenser (kg/kg)
   16574             :     Real64 OutdoorPressure; // Outdoor barometric pressure at condenser (Pa)
   16575             : 
   16576             :     int Mode;                 // Performance mode for Multimode DX coil; Always 1 for other coil types
   16577             :     Real64 OutletAirTemp;     // Supply air temperature (average value if constant fan, full output if cycling fan)
   16578             :     Real64 OutletAirHumRat;   // Supply air humidity ratio (average value if constant fan, full output if cycling fan)
   16579             :     Real64 OutletAirEnthalpy; // Supply air enthalpy (average value if constant fan, full output if cycling fan)
   16580             :     Real64 ADiff;             // Used for exponential
   16581             : 
   16582             :     // Followings for VRF FluidTCtrl Only
   16583             :     Real64 QCoilReq;       // Coil load (W)
   16584             :     Real64 FanSpdRatio;    // Fan speed ratio
   16585             :     Real64 AirMassFlowMin; // Min air mass flow rate due to OA requirement [kg/s]
   16586             :     Real64 ActualSH;       // Super heating degrees (C)
   16587             :     Real64 ActualSC;       // Sub cooling degrees (C)
   16588             : 
   16589             :     // If Performance mode not present, then set to 1.  Used only by Multimode/Multispeed DX coil (otherwise mode = 1)
   16590      683992 :     if (present(PerfMode)) {
   16591           0 :         Mode = PerfMode;
   16592             :     } else {
   16593      683992 :         Mode = 1;
   16594             :     }
   16595             : 
   16596             :     // If AirFlowRatio not present, then set to 1. Used only by DX coils with different air flow
   16597             :     // during cooling and when no cooling is required (constant fan, fan speed changes)
   16598      683992 :     if (present(OnOffAirFlowRatio)) {
   16599           0 :         AirFlowRatio = OnOffAirFlowRatio;
   16600             :     } else {
   16601      683992 :         AirFlowRatio = 1.0;
   16602             :     }
   16603             : 
   16604      683992 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   16605             : 
   16606             :     // Initialize coil air side parameters
   16607      683992 :     CondInletTemp = 0.0;
   16608      683992 :     CondInletHumRat = 0.0;
   16609      683992 :     AirMassFlow = thisDXCoil.InletAirMassFlowRate;
   16610      683992 :     InletAirDryBulbTemp = thisDXCoil.InletAirTemp;
   16611      683992 :     InletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   16612      683992 :     InletAirHumRat = thisDXCoil.InletAirHumRat;
   16613      683992 :     state.dataHeatBal->HeatReclaimDXCoil(DXCoilNum).AvailCapacity = 0.0;
   16614      683992 :     thisDXCoil.CoolingCoilRuntimeFraction = 0.0;
   16615      683992 :     thisDXCoil.PartLoadRatio = 0.0;
   16616      683992 :     thisDXCoil.BasinHeaterPower = 0.0;
   16617      683992 :     thisDXCoil.EvaporatingTemp = state.dataHVACVarRefFlow->VRF(thisDXCoil.VRFOUPtr).IUEvaporatingTemp;
   16618             : 
   16619      683992 :     if (thisDXCoil.CondenserInletNodeNum(Mode) != 0) {
   16620           0 :         OutdoorDryBulb = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).Temp;
   16621           0 :         if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Water) {
   16622           0 :             OutdoorHumRat = state.dataEnvrn->OutHumRat;
   16623           0 :             OutdoorPressure = state.dataEnvrn->OutBaroPress;
   16624           0 :             OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   16625             :         } else {
   16626           0 :             OutdoorPressure = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).Press;
   16627             :             // If node is not connected to anything, pressure = default, use weather data
   16628           0 :             if (OutdoorPressure == state.dataLoopNodes->DefaultNodeValues.Press) {
   16629           0 :                 OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   16630           0 :                 OutdoorHumRat = state.dataEnvrn->OutHumRat;
   16631           0 :                 OutdoorPressure = state.dataEnvrn->OutBaroPress;
   16632           0 :                 OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   16633             :             } else {
   16634           0 :                 OutdoorHumRat = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).HumRat;
   16635           0 :                 OutdoorWetBulb = state.dataLoopNodes->Node(thisDXCoil.CondenserInletNodeNum(Mode)).OutAirWetBulb;
   16636             :             }
   16637             :         }
   16638             :     } else {
   16639      683992 :         OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   16640      683992 :         OutdoorHumRat = state.dataEnvrn->OutHumRat;
   16641      683992 :         OutdoorPressure = state.dataEnvrn->OutBaroPress;
   16642      683992 :         OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   16643             :     }
   16644             : 
   16645      683992 :     if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Evap) {
   16646           0 :         RhoAir = PsyRhoAirFnPbTdbW(state, OutdoorPressure, OutdoorDryBulb, OutdoorHumRat);
   16647           0 :         CondAirMassFlow = RhoAir * thisDXCoil.EvapCondAirFlow(Mode);
   16648             :         // (Outdoor wet-bulb temp from DataEnvironment) + (1.0-EvapCondEffectiveness) * (drybulb - wetbulb)
   16649           0 :         CondInletTemp = OutdoorWetBulb + (OutdoorDryBulb - OutdoorWetBulb) * (1.0 - thisDXCoil.EvapCondEffect(Mode));
   16650           0 :         CondInletHumRat = PsyWFnTdbTwbPb(state, CondInletTemp, OutdoorWetBulb, OutdoorPressure);
   16651           0 :         CompAmbTemp = OutdoorDryBulb;
   16652             :     } else {                            // for air or water-cooled, inlet temp is stored in OutdoorDryBulb temp
   16653      683992 :         CondInletTemp = OutdoorDryBulb; // Outdoor dry-bulb temp or water inlet temp
   16654      683992 :         if (thisDXCoil.CondenserType(Mode) == DataHeatBalance::RefrigCondenserType::Water) {
   16655           0 :             CompAmbTemp = state.dataEnvrn->OutDryBulbTemp; // for crankcase heater use actual outdoor temp for water-cooled
   16656             :         } else {
   16657      683992 :             CompAmbTemp = OutdoorDryBulb;
   16658             :         }
   16659             :     }
   16660             : 
   16661             :     // Initialize crankcase heater, operates below OAT defined in input deck for HP DX cooling coil
   16662             :     // If used in a heat pump, the value of MaxOAT in the heating coil overrides that in the cooling coil (in GetInput)
   16663      683992 :     if (CompAmbTemp < thisDXCoil.MaxOATCrankcaseHeater) {
   16664       60444 :         CrankcaseHeatingPower = thisDXCoil.CrankcaseHeaterCapacity;
   16665       60444 :         if (thisDXCoil.CrankcaseHeaterCapacityCurveIndex > 0) {
   16666           0 :             CrankcaseHeatingPower *= Curve::CurveValue(state, thisDXCoil.CrankcaseHeaterCapacityCurveIndex, CompAmbTemp);
   16667             :         }
   16668             :     } else {
   16669      623548 :         CrankcaseHeatingPower = 0.0;
   16670             :     }
   16671             : 
   16672             :     // calculate end time of current time step to determine if error messages should be printed
   16673      683992 :     state.dataDXCoils->CalcVRFCoolingCoil_FluidTCtrlCurrentEndTime = state.dataGlobal->CurrentTime + SysTimeElapsed;
   16674             : 
   16675             :     // The following checks are not necessary for VRF-FluidTCtrl model. (1) OAT check is already performed in the VRF OU routines (2)
   16676             :     // VRF-FluidTCtrl model is physics based, not system curve based, and thus doesn't require special performance curves for operations at
   16677             :     // low inlet temperatures
   16678             :     //   Print warning messages only when valid and only for the first occurrence. Let summary provide statistics.
   16679             :     //   Wait for next time step to print warnings. If simulation iterates, print out
   16680             :     //   the warning for the last iteration only. Must wait for next time step to accomplish this.
   16681             :     //   If a warning occurs and the simulation down shifts, the warning is not valid.
   16682             :     // if ( DXCoil( DXCoilNum ).PrintLowAmbMessage ) { // .AND. &
   16683             :     //     if ( CurrentEndTime > DXCoil( DXCoilNum ).CurrentEndTimeLast && TimeStepSys >= DXCoil( DXCoilNum ).TimeStepSysLast ) {
   16684             :     //         if ( DXCoil( DXCoilNum ).LowAmbErrIndex == 0 ) {
   16685             :     //             ShowWarningMessage(state,  DXCoil( DXCoilNum ).LowAmbBuffer1 );
   16686             :     //             ShowContinueError(state,  DXCoil( DXCoilNum ).LowAmbBuffer2 );
   16687             :     //             ShowContinueError(state,  "... Operation at low inlet temperatures may require special performance curves." );
   16688             :     //         }
   16689             :     //         ShowRecurringWarningErrorAtEnd(state,  DXCoil( DXCoilNum ).DXCoilType + " \"" + DXCoil( DXCoilNum ).Name + "\" - Low condenser inlet
   16690             :     // temperature error continues...", DXCoil( DXCoilNum ).LowAmbErrIndex, DXCoil( DXCoilNum ).LowTempLast, DXCoil( DXCoilNum ).LowTempLast,
   16691             :     // _,
   16692             :     // "[C]", "[C]" );
   16693             :     //     }
   16694             :     // }
   16695             :     //
   16696             :     // if ( DXCoil( DXCoilNum ).PrintHighAmbMessage ) { // .AND. &
   16697             :     //     if ( CurrentEndTime > DXCoil( DXCoilNum ).CurrentEndTimeLast && TimeStepSys >= DXCoil( DXCoilNum ).TimeStepSysLast ) {
   16698             :     //         if ( DXCoil( DXCoilNum ).HighAmbErrIndex == 0 ) {
   16699             :     //             ShowWarningMessage(state,  DXCoil( DXCoilNum ).HighAmbBuffer1 );
   16700             :     //             ShowContinueError(state,  DXCoil( DXCoilNum ).HighAmbBuffer2 );
   16701             :     //             ShowContinueError(state,  "... Operation at high inlet temperatures may require special performance curves." );
   16702             :     //         }
   16703             :     //         ShowRecurringWarningErrorAtEnd(state,  DXCoil( DXCoilNum ).DXCoilType + " \"" + DXCoil( DXCoilNum ).Name + "\" - High condenser inlet
   16704             :     // temperature error continues...", DXCoil( DXCoilNum ).HighAmbErrIndex, DXCoil( DXCoilNum ).HighTempLast, DXCoil( DXCoilNum
   16705             :     // ).HighTempLast,
   16706             :     // _, "[C]", "[C]" );
   16707             :     //     }
   16708             :     // }
   16709             : 
   16710      683992 :     if (thisDXCoil.PrintLowOutTempMessage) {
   16711           0 :         if ((state.dataDXCoils->CalcVRFCoolingCoil_FluidTCtrlCurrentEndTime > thisDXCoil.CurrentEndTimeLast) &&
   16712           0 :             (TimeStepSys >= thisDXCoil.TimeStepSysLast)) {
   16713           0 :             if (thisDXCoil.LowOutletTempIndex == 0) {
   16714           0 :                 ShowWarningMessage(state, thisDXCoil.LowOutTempBuffer1);
   16715           0 :                 ShowContinueError(state, thisDXCoil.LowOutTempBuffer2);
   16716           0 :                 ShowContinueError(state, "... Possible reasons for low outlet air dry-bulb temperatures are: This DX coil");
   16717           0 :                 ShowContinueError(state,
   16718           0 :                                   format("   1) may have a low inlet air dry-bulb temperature. Inlet air temperature = {:.3T} C.",
   16719           0 :                                          thisDXCoil.FullLoadInletAirTempLast));
   16720           0 :                 ShowContinueError(state, "   2) may have a low air flow rate per watt of cooling capacity. Check inputs.");
   16721           0 :                 ShowContinueError(state,
   16722             :                                   "   3) is used as part of a HX assisted cooling coil which uses a high sensible effectiveness. Check inputs.");
   16723             :             }
   16724           0 :             ShowRecurringWarningErrorAtEnd(state,
   16725           0 :                                            thisDXCoil.DXCoilType + " \"" + thisDXCoil.Name +
   16726             :                                                "\" - Full load outlet temperature indicates a possibility of frost/freeze error continues. "
   16727             :                                                "Outlet air temperature statistics follow:",
   16728           0 :                                            thisDXCoil.LowOutletTempIndex,
   16729           0 :                                            thisDXCoil.FullLoadOutAirTempLast,
   16730           0 :                                            thisDXCoil.FullLoadOutAirTempLast);
   16731             :         }
   16732             :     }
   16733             : 
   16734             :     // save last system time step and last end time of current time step (used to determine if warning is valid)
   16735      683992 :     thisDXCoil.TimeStepSysLast = TimeStepSys;
   16736      683992 :     thisDXCoil.CurrentEndTimeLast = state.dataDXCoils->CalcVRFCoolingCoil_FluidTCtrlCurrentEndTime;
   16737      683992 :     thisDXCoil.PrintLowAmbMessage = false;
   16738      683992 :     thisDXCoil.PrintLowOutTempMessage = false;
   16739             : 
   16740      683992 :     if ((AirMassFlow > 0.0) && (GetCurrentScheduleValue(state, thisDXCoil.SchedPtr) > 0.0) && (PartLoadRatio > 0.0) &&
   16741             :         (compressorOp == HVAC::CompressorOp::On)) { // for cycling fan, reset mass flow to full on rate
   16742             : 
   16743      304587 :         if (thisDXCoil.RatedTotCap(Mode) <= 0.0) {
   16744           0 :             ShowFatalError(state, format("{} \"{}\" - Rated total cooling capacity is zero or less.", thisDXCoil.DXCoilType, thisDXCoil.Name));
   16745             :         }
   16746             : 
   16747      304587 :         TotCap = thisDXCoil.RatedTotCap(Mode);
   16748      304587 :         QCoilReq = -PartLoadRatio * TotCap;
   16749      304587 :         if (PartLoadRatio == 0.0) {
   16750           0 :             AirMassFlowMin = state.dataHVACVarRefFlow->OACompOffMassFlow;
   16751             :         } else {
   16752      304587 :             AirMassFlowMin = state.dataHVACVarRefFlow->OACompOnMassFlow;
   16753             :         }
   16754             : 
   16755             :         // Call ControlVRFIUCoil to calculate: (1) FanSpdRatio, (2) coil inlet/outlet conditions, and (3) SH/SC
   16756      304587 :         ControlVRFIUCoil(state,
   16757             :                          DXCoilNum,
   16758             :                          QCoilReq,
   16759             :                          thisDXCoil.InletAirTemp,
   16760             :                          thisDXCoil.InletAirHumRat,
   16761             :                          thisDXCoil.EvaporatingTemp,
   16762             :                          AirMassFlowMin,
   16763             :                          FanSpdRatio,
   16764             :                          OutletAirHumRat,
   16765             :                          OutletAirTemp,
   16766             :                          OutletAirEnthalpy,
   16767             :                          ActualSH,
   16768             :                          ActualSC);
   16769      304587 :         AirMassFlow = FanSpdRatio * thisDXCoil.RatedAirMassFlowRate(Mode);
   16770             : 
   16771      304587 :         AirVolumeFlowRate = AirMassFlow / PsyRhoAirFnPbTdbW(state, OutdoorPressure, InletAirDryBulbTemp, InletAirHumRat);
   16772      304587 :         VolFlowperRatedTotCap = AirVolumeFlowRate / thisDXCoil.RatedTotCap(Mode);
   16773             :         // VolFlowperRatedTotCap was checked at the initialization step
   16774             :         // No need to check VolFlowperRatedTotCap at the simulation
   16775             :         // New VRF_FluidTCtrl model implements VAV fan which can vary air flow rate during simulation
   16776             : 
   16777      304587 :         RatedCBF = thisDXCoil.RatedCBF(Mode);
   16778      304587 :         if (RatedCBF > 0.0) {
   16779      304587 :             A0 = -std::log(RatedCBF) * thisDXCoil.RatedAirMassFlowRate(Mode);
   16780             :         } else {
   16781           0 :             A0 = 0.0;
   16782             :         }
   16783      304587 :         ADiff = -A0 / AirMassFlow;
   16784      304587 :         if (ADiff >= DataPrecisionGlobals::EXP_LowerLimit) {
   16785      304587 :             CBF = std::exp(ADiff);
   16786             :         } else {
   16787           0 :             CBF = 0.0;
   16788             :         }
   16789             : 
   16790             :         // The following checks are not necessary for VRF-FluidTCtrl model. (1) OAT check is already performed in the VRF OU routines (2)
   16791             :         // VRF-FluidTCtrl model is physics based, not system curve based, and thus doesn't require special performance curves for operations
   16792             :         // at low inlet temperatures
   16793             :         // // check boundary for low ambient temperature and post warnings to individual DX coil buffers to print at end of time step
   16794             :         // if ( OutdoorDryBulb < DXCoil( DXCoilNum ).MinOATCompressor && ! WarmupFlag ) {
   16795             :         //     DXCoil( DXCoilNum ).PrintLowAmbMessage = true;
   16796             :         //     DXCoil( DXCoilNum ).LowTempLast = OutdoorDryBulb;
   16797             :         //     if ( DXCoil( DXCoilNum ).LowAmbErrIndex == 0 ) {
   16798             :         //         DXCoil( DXCoilNum ).LowAmbBuffer1 = DXCoil( DXCoilNum ).DXCoilType + " \"" + DXCoil( DXCoilNum ).Name + "\" - Condenser
   16799             :         // inlet temperature below " + RoundSigDigits( DXCoil( DXCoilNum ).MinOATCompressor, 2 ) + " C. Condenser inlet temperature = " +
   16800             :         // RoundSigDigits( OutdoorDryBulb, 2 );
   16801             :         //         DXCoil( DXCoilNum ).LowAmbBuffer2 = " ... Occurrence info = " + EnvironmentName + ", " + CurMnDy + " " +
   16802             :         // CreateSysTimeIntervalString();
   16803             :         //     }
   16804             :         // }
   16805             :         //
   16806             :         // // check boundary for high ambient temperature and post warnings to individual DX coil buffers to print at end of time step
   16807             :         // if ( OutdoorDryBulb > DXCoil( DXCoilNum ).MaxOATCompressor && ! WarmupFlag ) {
   16808             :         //     DXCoil( DXCoilNum ).PrintHighAmbMessage = true;
   16809             :         //     DXCoil( DXCoilNum ).HighTempLast = OutdoorDryBulb;
   16810             :         //     if ( DXCoil( DXCoilNum ).HighAmbErrIndex == 0 ) {
   16811             :         //         DXCoil( DXCoilNum ).HighAmbBuffer1 = DXCoil( DXCoilNum ).DXCoilType + " \"" + DXCoil( DXCoilNum ).Name + "\" - Condenser
   16812             :         // inlet temperature above " + RoundSigDigits( DXCoil( DXCoilNum ).MaxOATCompressor, 2 ) + " C. Condenser temperature = " +
   16813             :         // RoundSigDigits( OutdoorDryBulb, 2 );         DXCoil( DXCoilNum ).HighAmbBuffer2 = " ... Occurrence info = " + EnvironmentName + ",
   16814             :         // "
   16815             :         // + CurMnDy + " " + CreateSysTimeIntervalString();
   16816             :         //     }
   16817             :         // }
   16818             : 
   16819             :         //  Get total capacity modifying factor (function of temperature) for off-rated conditions
   16820             :         //  InletAirHumRat may be modified in this ADP/BF loop, use temporary varible for calculations
   16821             : 
   16822             :         // commented, not used issue #6950
   16823             :         // InletAirHumRatTemp = InletAirHumRat;
   16824             : 
   16825             :         //// Calculate apparatus dew point conditions using TotCap and CBF
   16826             :         // hDelta = TotCap / AirMassFlow;
   16827             :         //// there is an issue here with using CBF to calculate the ADP enthalpy.
   16828             :         //// at low loads the bypass factor increases significantly.
   16829             :         // hADP = InletAirEnthalpy - hDelta / (1.0 - CBF);
   16830             :         // tADP = PsyTsatFnHPb(hADP, OutdoorPressure, RoutineName);
   16831             :         ////  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   16832             :         ////  tADP = PsyTsatFnHPb(hADP,InletAirPressure)
   16833             :         // wADP = min(InletAirHumRat, PsyWFnTdbH(tADP, hADP, RoutineName));
   16834             :         // hTinwADP = PsyHFnTdbW(InletAirDryBulbTemp, wADP);
   16835             :         // if ((InletAirEnthalpy - hADP) > 1.e-10) {
   16836             :         //    SHR = min((hTinwADP - hADP) / (InletAirEnthalpy - hADP), 1.0);
   16837             :         //} else {
   16838             :         //    SHR = 1.0;
   16839             :         //}
   16840             :         // commented, not used issue #6950 ends here
   16841             : 
   16842      304587 :         if (thisDXCoil.PLFFPLR(Mode) > 0 && CompCycRatio < 1.0) {
   16843           0 :             PLF = CurveValue(state, thisDXCoil.PLFFPLR(Mode), CompCycRatio); // Calculate part-load factor
   16844             :         } else {
   16845      304587 :             PLF = 1.0;
   16846             :         }
   16847             : 
   16848      304587 :         if (PLF < 0.7) {
   16849           0 :             if (thisDXCoil.ErrIndex2 == 0) {
   16850           0 :                 ShowWarningMessage(
   16851             :                     state,
   16852           0 :                     format(
   16853           0 :                         "The PLF curve value for the DX cooling coil {} ={:.3R} for part-load ratio ={:.3R}", thisDXCoil.Name, PLF, PartLoadRatio));
   16854           0 :                 ShowContinueErrorTimeStamp(state, "PLF curve values must be >= 0.7. PLF has been reset to 0.7 and simulation is continuing.");
   16855           0 :                 ShowContinueError(state, "Check the IO reference manual for PLF curve guidance [Coil:Cooling:DX:SingleSpeed].");
   16856             :             }
   16857           0 :             ShowRecurringWarningErrorAtEnd(
   16858           0 :                 state, thisDXCoil.Name + ", DX cooling coil PLF curve < 0.7 warning continues...", thisDXCoil.ErrIndex2, PLF, PLF);
   16859           0 :             PLF = 0.7;
   16860             :         }
   16861             : 
   16862      304587 :         thisDXCoil.PartLoadRatio = PartLoadRatio;
   16863      304587 :         thisDXCoil.CoolingCoilRuntimeFraction = CompCycRatio / PLF;
   16864      304587 :         if (thisDXCoil.CoolingCoilRuntimeFraction > 1.0 && std::abs(thisDXCoil.CoolingCoilRuntimeFraction - 1.0) > 0.001) {
   16865           0 :             if (thisDXCoil.ErrIndex3 == 0) {
   16866           0 :                 ShowWarningMessage(state,
   16867           0 :                                    format("The runtime fraction for DX cooling coil {} exceeded 1.0. [{:.4R}].",
   16868           0 :                                           thisDXCoil.Name,
   16869           0 :                                           thisDXCoil.CoolingCoilRuntimeFraction));
   16870           0 :                 ShowContinueError(state, "Runtime fraction reset to 1 and the simulation will continue.");
   16871           0 :                 ShowContinueError(state, "Check the IO reference manual for PLF curve guidance [Coil:Cooling:DX:SingleSpeed].");
   16872           0 :                 ShowContinueErrorTimeStamp(state, "");
   16873             :             }
   16874           0 :             ShowRecurringWarningErrorAtEnd(state,
   16875           0 :                                            thisDXCoil.Name + ", DX cooling coil runtime fraction > 1.0 warning continues...",
   16876           0 :                                            thisDXCoil.ErrIndex3,
   16877           0 :                                            thisDXCoil.CoolingCoilRuntimeFraction,
   16878           0 :                                            thisDXCoil.CoolingCoilRuntimeFraction);
   16879           0 :             thisDXCoil.CoolingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   16880      304587 :         } else if (thisDXCoil.CoolingCoilRuntimeFraction > 1.0) {
   16881           0 :             thisDXCoil.CoolingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   16882             :         }
   16883             : 
   16884             :         // If cycling fan, send coil part-load fraction to on/off fan via HVACDataGlobals
   16885      304587 :         if (fanOp == HVAC::FanOp::Cycling) state.dataHVACGlobal->OnOffFanPartLoadFraction = PLF;
   16886             : 
   16887             :         // Check for saturation error and modify temperature at constant enthalpy
   16888      304587 :         if (OutletAirTemp < PsyTsatFnHPb(state, OutletAirEnthalpy, OutdoorPressure)) {
   16889         150 :             OutletAirTemp = PsyTsatFnHPb(state, OutletAirEnthalpy, OutdoorPressure);
   16890             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   16891             :             //   IF(FullLoadOutAirTemp .LT. PsyTsatFnHPb(FullLoadOutAirEnth,InletAirPressure)) THEN
   16892             :             //    FullLoadOutAirTemp = PsyTsatFnHPb(FullLoadOutAirEnth,InletAirPressure)
   16893         150 :             OutletAirHumRat = PsyWFnTdbH(state, OutletAirTemp, OutletAirEnthalpy);
   16894             :         }
   16895             : 
   16896             :         // Store actual outlet conditions when DX coil is ON for use in heat recovery module
   16897      304587 :         state.dataDXCoils->DXCoilFullLoadOutAirTemp(DXCoilNum) = OutletAirTemp;
   16898      304587 :         state.dataDXCoils->DXCoilFullLoadOutAirHumRat(DXCoilNum) = OutletAirHumRat;
   16899             : 
   16900             :         // Add warning message for cold cooling coil (OutletAirTemp < 2 C)
   16901      304587 :         if (OutletAirTemp < 2.0 && !FirstHVACIteration && !state.dataGlobal->WarmupFlag) {
   16902           0 :             thisDXCoil.PrintLowOutTempMessage = true;
   16903           0 :             thisDXCoil.FullLoadOutAirTempLast = OutletAirTemp;
   16904           0 :             if (thisDXCoil.LowOutletTempIndex == 0) {
   16905           0 :                 thisDXCoil.FullLoadInletAirTempLast = InletAirDryBulbTemp;
   16906           0 :                 thisDXCoil.LowOutTempBuffer1 = format("{} \"{}\" - Full load outlet air dry-bulb temperature < 2C. This indicates the "
   16907             :                                                       "possibility of coil frost/freeze. Outlet temperature = {:.2R} C.",
   16908           0 :                                                       thisDXCoil.DXCoilType,
   16909           0 :                                                       thisDXCoil.Name,
   16910           0 :                                                       OutletAirTemp);
   16911           0 :                 thisDXCoil.LowOutTempBuffer2 = " ...Occurrence info = " + state.dataEnvrn->EnvironmentName + ", " + state.dataEnvrn->CurMnDy + " " +
   16912           0 :                                                CreateSysTimeIntervalString(state);
   16913             :             }
   16914             :         }
   16915             : 
   16916             :         // Coil total cooling
   16917      304587 :         Real64 AirMassFlowRate = thisDXCoil.InletAirMassFlowRate;
   16918             :         // Coil total/sensible/latent cooling rates
   16919      304587 :         CalcComponentSensibleLatentOutput(AirMassFlowRate,
   16920             :                                           InletAirDryBulbTemp,
   16921             :                                           InletAirHumRat,
   16922             :                                           OutletAirTemp,
   16923             :                                           OutletAirHumRat,
   16924      304587 :                                           thisDXCoil.SensCoolingEnergyRate,
   16925      304587 :                                           thisDXCoil.LatCoolingEnergyRate,
   16926      304587 :                                           thisDXCoil.TotalCoolingEnergyRate);
   16927             : 
   16928             :         // Coil outlet conditions
   16929      304587 :         thisDXCoil.OutletAirTemp = OutletAirTemp;
   16930      304587 :         thisDXCoil.OutletAirHumRat = OutletAirHumRat;
   16931      304587 :         thisDXCoil.OutletAirEnthalpy = OutletAirEnthalpy;
   16932             : 
   16933             :         // Coil SH/SC
   16934      304587 :         thisDXCoil.ActualSH = ActualSH;
   16935      304587 :         thisDXCoil.ActualSC = ActualSC;
   16936             : 
   16937             :     } else {
   16938             :         // DX coil is off; just pass through conditions
   16939             : 
   16940      379405 :         thisDXCoil.OutletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   16941      379405 :         thisDXCoil.OutletAirHumRat = thisDXCoil.InletAirHumRat;
   16942      379405 :         thisDXCoil.OutletAirTemp = thisDXCoil.InletAirTemp;
   16943             : 
   16944      379405 :         thisDXCoil.ElecCoolingPower = 0.0;
   16945      379405 :         thisDXCoil.TotalCoolingEnergyRate = 0.0;
   16946      379405 :         thisDXCoil.SensCoolingEnergyRate = 0.0;
   16947      379405 :         thisDXCoil.LatCoolingEnergyRate = 0.0;
   16948      379405 :         thisDXCoil.EvapCondPumpElecPower = 0.0;
   16949      379405 :         thisDXCoil.EvapWaterConsumpRate = 0.0;
   16950             : 
   16951      379405 :         thisDXCoil.ActualSH = 999.0;
   16952      379405 :         thisDXCoil.ActualSC = 999.0;
   16953             : 
   16954             :         // Reset globals when DX coil is OFF for use in heat recovery module
   16955      379405 :         state.dataDXCoils->DXCoilFullLoadOutAirTemp(DXCoilNum) = 0.0;
   16956      379405 :         state.dataDXCoils->DXCoilFullLoadOutAirHumRat(DXCoilNum) = 0.0;
   16957             : 
   16958             :     } // end of on/off
   16959             : 
   16960             :     // set water system demand request (if needed)
   16961      683992 :     if (thisDXCoil.EvapWaterSupplyMode == EvapWaterSupply::FromTank) {
   16962           0 :         state.dataWaterData->WaterStorage(thisDXCoil.EvapWaterSupTankID).VdotRequestDemand(thisDXCoil.EvapWaterTankDemandARRID) =
   16963           0 :             thisDXCoil.EvapWaterConsumpRate;
   16964             :     }
   16965             : 
   16966      683992 :     state.dataDXCoils->DXCoilOutletTemp(DXCoilNum) = thisDXCoil.OutletAirTemp;
   16967      683992 :     state.dataDXCoils->DXCoilOutletHumRat(DXCoilNum) = thisDXCoil.OutletAirHumRat;
   16968      683992 :     state.dataDXCoils->DXCoilPartLoadRatio(DXCoilNum) = thisDXCoil.PartLoadRatio;
   16969      683992 :     state.dataDXCoils->DXCoilFanOp(DXCoilNum) = fanOp;
   16970      683992 :     thisDXCoil.CondInletTemp = CondInletTemp;
   16971      683992 :     state.dataDXCoils->DXCoilTotalCooling(DXCoilNum) = thisDXCoil.TotalCoolingEnergyRate;
   16972      683992 :     state.dataDXCoils->DXCoilCoolInletAirWBTemp(DXCoilNum) = PsyTwbFnTdbWPb(state, InletAirDryBulbTemp, InletAirHumRat, OutdoorPressure);
   16973      683992 : }
   16974             : 
   16975      683992 : void CalcVRFHeatingCoil_FluidTCtrl(EnergyPlusData &state,
   16976             :                                    HVAC::CompressorOp const compressorOp,               // compressor operation; 1=on, 0=off
   16977             :                                    int const DXCoilNum,                                 // the number of the DX heating coil to be simulated
   16978             :                                    Real64 const PartLoadRatio,                          // sensible cooling load / full load sensible cooling capacity
   16979             :                                    HVAC::FanOp const fanOp,                             // Allows parent object to control fan mode
   16980             :                                    ObjexxFCL::Optional<Real64 const> OnOffAirFlowRatio, // ratio of compressor on airflow to compressor off airflow
   16981             :                                    ObjexxFCL::Optional<Real64 const> MaxHeatCap         // maximum allowed heating capacity
   16982             : )
   16983             : {
   16984             :     // SUBROUTINE INFORMATION:
   16985             :     //       AUTHOR         Xiufeng Pang (XP), LBNL
   16986             :     //       DATE WRITTEN   Mar 2013
   16987             :     //       MODIFIED       Nov 2015, RP Zhang, LBNL
   16988             : 
   16989             :     // PURPOSE OF THIS SUBROUTINE:
   16990             :     //         Calculates the air-side performance of a direct-expansion, air-cooled
   16991             :     //         VRF terminal unit heating coil, for the new VRF model.
   16992             : 
   16993             :     // METHODOLOGY EMPLOYED:
   16994             :     //         This subroutine is derived from CalcVRFCoolingCoil, and implements the new VRF model for FluidTCtrl.
   16995             : 
   16996             :     // Using/Aliasing
   16997             :     using Curve::CurveValue;
   16998             : 
   16999             :     using namespace HVACVariableRefrigerantFlow;
   17000             : 
   17001             :     // INTERFACE BLOCK SPECIFICATIONS
   17002             :     static constexpr std::string_view RoutineNameFullLoad("CalcVRFHeatingCoil_FluidTCtrl:fullload");
   17003             : 
   17004             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   17005             :     Real64 AirMassFlow;           // dry air mass flow rate through coil [kg/s]
   17006             :     Real64 AirMassFlowRatio;      // Ratio of actual air mass flow to rated air mass flow
   17007             :     Real64 AirVolumeFlowRate;     // Air volume flow rate across the cooling coil [m3/s]
   17008             :     Real64 VolFlowperRatedTotCap; // Air volume flow rate divided by rated total cooling capacity [m3/s-W]
   17009             :     Real64 TotCap;                // gross total cooling capacity at off-rated conditions [W]
   17010             :     Real64 TotCapAdj;             // adjusted total cooling capacity at off-rated conditions [W]
   17011             :     // on the type of curve
   17012             :     Real64 InletAirDryBulbTemp;  // inlet air dry bulb temperature [C]
   17013             :     Real64 InletAirWetBulbC;     // wetbulb temperature of inlet air [C]
   17014             :     Real64 InletAirEnthalpy;     // inlet air enthalpy [J/kg]
   17015             :     Real64 InletAirHumRat;       // inlet air humidity ratio [kg/kg]
   17016             :     Real64 FullLoadOutAirEnth;   // outlet full load enthalpy [J/kg]
   17017             :     Real64 FullLoadOutAirHumRat; // outlet humidity ratio at full load
   17018             :     Real64 FullLoadOutAirTemp;   // outlet air temperature at full load [C]
   17019             :     Real64 FullLoadOutAirRH;     // outlet air relative humidity at full load
   17020      683992 :     Real64 EIRTempModFac(0.0);   // EIR modifier (function of entering drybulb, outside drybulb) depending on the
   17021             :     //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   17022             :     // type of curve
   17023             :     // Real64 DefrostEIRTempModFac; // EIR modifier for defrost (function of entering wetbulb, outside drybulb)
   17024             :     Real64 EIRFlowModFac;             // EIR modifier (function of actual supply air flow vs rated flow)
   17025             :     Real64 EIR;                       // EIR at part load and off rated conditions
   17026             :     Real64 PLF;                       // Part load factor, accounts for thermal lag at compressor startup
   17027             :     Real64 PLRHeating;                // PartLoadRatio in heating
   17028             :     Real64 OutdoorCoilT;              // Outdoor coil temperature (C)
   17029             :     Real64 OutdoorCoildw;             // Outdoor coil delta w assuming coil temp of OutdoorCoilT (kg/kg)
   17030             :     Real64 FractionalDefrostTime;     // Fraction of time step system is in defrost
   17031             :     Real64 HeatingCapacityMultiplier; // Multiplier for heating capacity when system is in defrost
   17032             :     Real64 InputPowerMultiplier;      // Multiplier for power when system is in defrost
   17033             :     Real64 LoadDueToDefrost;          // Additional load due to defrost
   17034             :     Real64 CrankcaseHeatingPower;     // power due to crankcase heater
   17035             :     Real64 OutdoorDryBulb;            // Outdoor dry-bulb temperature at condenser (C)
   17036             :     Real64 OutdoorWetBulb;            // Outdoor wet-bulb temperature at condenser (C)
   17037             :     Real64 OutdoorHumRat;             // Outdoor humidity ratio at condenser (kg/kg)
   17038             :     Real64 OutdoorPressure;           // Outdoor barometric pressure at condenser (Pa)
   17039      683992 :     constexpr int Mode(1);            // Performance mode for MultiMode DX coil. Always 1 for other coil types
   17040             :     Real64 AirFlowRatio;              // Ratio of compressor on airflow to average timestep airflow
   17041             :     Real64 OutletAirTemp;             // Supply air temperature (average value if constant fan, full output if cycling fan)
   17042             :     Real64 OutletAirHumRat;           // Supply air humidity ratio (average value if constant fan, full output if cycling fan)
   17043             :     Real64 OutletAirEnthalpy;         // Supply air enthalpy (average value if constant fan, full output if cycling fan)
   17044             : 
   17045             :     // Followings for VRF FluidTCtrl Only
   17046             :     Real64 QCoilReq;       // Coil load (W)
   17047             :     Real64 FanSpdRatio;    // Fan Speed Ratio
   17048             :     Real64 AirMassFlowMin; // Min air mass flow rate due to OA requirement [kg/s]
   17049             :     Real64 ActualSH;       // Actual Super Heating
   17050             :     Real64 ActualSC;       // Actual Sub Cooling
   17051             : 
   17052      683992 :     if (present(OnOffAirFlowRatio)) {
   17053           0 :         AirFlowRatio = OnOffAirFlowRatio;
   17054             :     } else {
   17055      683992 :         AirFlowRatio = 1.0;
   17056             :     }
   17057             : 
   17058             :     // Air cooled condenser
   17059      683992 :     OutdoorDryBulb = state.dataEnvrn->OutDryBulbTemp;
   17060      683992 :     OutdoorWetBulb = state.dataEnvrn->OutWetBulbTemp;
   17061      683992 :     OutdoorHumRat = state.dataEnvrn->OutHumRat;
   17062      683992 :     OutdoorPressure = state.dataEnvrn->OutBaroPress;
   17063             : 
   17064      683992 :     auto &thisDXCoil = state.dataDXCoils->DXCoil(DXCoilNum);
   17065             : 
   17066      683992 :     AirMassFlow = thisDXCoil.InletAirMassFlowRate;
   17067      683992 :     InletAirDryBulbTemp = thisDXCoil.InletAirTemp;
   17068      683992 :     InletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   17069      683992 :     InletAirHumRat = thisDXCoil.InletAirHumRat;
   17070      683992 :     InletAirWetBulbC = PsyTwbFnTdbWPb(state, InletAirDryBulbTemp, InletAirHumRat, OutdoorPressure);
   17071      683992 :     PLRHeating = 0.0;
   17072      683992 :     thisDXCoil.HeatingCoilRuntimeFraction = 0.0;
   17073      683992 :     thisDXCoil.CondensingTemp = state.dataHVACVarRefFlow->VRF(thisDXCoil.VRFOUPtr).IUCondensingTemp;
   17074             : 
   17075             :     // Initialize crankcase heater, operates below OAT defined in input deck for HP DX heating coil
   17076      683992 :     if (OutdoorDryBulb < thisDXCoil.MaxOATCrankcaseHeater) {
   17077       60444 :         CrankcaseHeatingPower = thisDXCoil.CrankcaseHeaterCapacity;
   17078       60444 :         if (thisDXCoil.CrankcaseHeaterCapacityCurveIndex > 0) {
   17079           0 :             CrankcaseHeatingPower *= Curve::CurveValue(state, thisDXCoil.CrankcaseHeaterCapacityCurveIndex, OutdoorDryBulb);
   17080             :         }
   17081             :     } else {
   17082      623548 :         CrankcaseHeatingPower = 0.0;
   17083             :     }
   17084             : 
   17085      676634 :     if ((AirMassFlow > 0.0) && (compressorOp == HVAC::CompressorOp::On) && (GetCurrentScheduleValue(state, thisDXCoil.SchedPtr) > 0.0) &&
   17086     1360626 :         (PartLoadRatio > 0.0) && (OutdoorDryBulb > thisDXCoil.MinOATCompressor)) {
   17087             : 
   17088      133476 :         TotCap = thisDXCoil.RatedTotCap(Mode);
   17089      133476 :         HeatingCapacityMultiplier = 1.0;
   17090             :         // Modify total heating capacity based on defrost heating capacity multiplier
   17091             :         // MaxHeatCap passed from parent object VRF Condenser and is used to limit capacity of TU's to that available from condenser
   17092      133476 :         if (present(MaxHeatCap)) {
   17093      133460 :             TotCapAdj = min(MaxHeatCap, TotCap * HeatingCapacityMultiplier);
   17094      133460 :             TotCap = min(MaxHeatCap, TotCap);
   17095             :         } else {
   17096          16 :             TotCapAdj = TotCap * HeatingCapacityMultiplier;
   17097             :         }
   17098             : 
   17099      133476 :         QCoilReq = PartLoadRatio * TotCap;
   17100      133476 :         if (PartLoadRatio == 0.0) {
   17101           0 :             AirMassFlowMin = state.dataHVACVarRefFlow->OACompOffMassFlow;
   17102             :         } else {
   17103      133476 :             AirMassFlowMin = state.dataHVACVarRefFlow->OACompOnMassFlow;
   17104             :         }
   17105             : 
   17106             :         // Call ControlVRFIUCoil to calculate: (1) FanSpdRatio, (2) coil inlet/outlet conditions, and (3) SH/SC
   17107      133476 :         ControlVRFIUCoil(state,
   17108             :                          DXCoilNum,
   17109             :                          QCoilReq,
   17110             :                          thisDXCoil.InletAirTemp,
   17111             :                          thisDXCoil.InletAirHumRat,
   17112             :                          thisDXCoil.CondensingTemp,
   17113             :                          AirMassFlowMin,
   17114             :                          FanSpdRatio,
   17115             :                          OutletAirHumRat,
   17116             :                          OutletAirTemp,
   17117             :                          OutletAirEnthalpy,
   17118             :                          ActualSH,
   17119             :                          ActualSC);
   17120      133476 :         AirMassFlow = FanSpdRatio * thisDXCoil.RatedAirMassFlowRate(Mode);
   17121             : 
   17122      133476 :         AirVolumeFlowRate = AirMassFlow / PsyRhoAirFnPbTdbW(state, OutdoorPressure, InletAirDryBulbTemp, InletAirHumRat);
   17123             :         // Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   17124      133476 :         VolFlowperRatedTotCap = AirVolumeFlowRate / thisDXCoil.RatedTotCap(Mode);
   17125             :         // VolFlowperRatedTotCap was checked at the initialization step
   17126             :         // No need to check VolFlowperRatedTotCap at the simulation
   17127             :         // New VRF_FluidTCtrl model implements VAV fan which can vary air flow rate during simulation
   17128             : 
   17129      133476 :         AirMassFlowRatio = AirMassFlow / thisDXCoil.RatedAirMassFlowRate(Mode);
   17130             : 
   17131             :         // Calculating adjustment factors for defrost
   17132             :         // Calculate delta w through outdoor coil by assuming a coil temp of 0.82*DBT-9.7(F) per DOE2.1E
   17133      133476 :         OutdoorCoilT = 0.82 * OutdoorDryBulb - 8.589;
   17134      133476 :         OutdoorCoildw = max(1.0e-6, (OutdoorHumRat - PsyWFnTdpPb(state, OutdoorCoilT, OutdoorPressure)));
   17135             : 
   17136             :         // Initializing defrost adjustment factors
   17137      133476 :         LoadDueToDefrost = 0.0;
   17138      133476 :         FractionalDefrostTime = 0.0;
   17139      133476 :         InputPowerMultiplier = 1.0;
   17140             : 
   17141             :         // Calculate full load outlet conditions
   17142      133476 :         FullLoadOutAirEnth = InletAirEnthalpy + TotCapAdj / AirMassFlow;
   17143      133476 :         FullLoadOutAirHumRat = InletAirHumRat;
   17144      133476 :         FullLoadOutAirTemp = PsyTdbFnHW(FullLoadOutAirEnth, FullLoadOutAirHumRat);
   17145      133476 :         FullLoadOutAirRH = PsyRhFnTdbWPb(state, FullLoadOutAirTemp, FullLoadOutAirHumRat, OutdoorPressure, RoutineNameFullLoad);
   17146             :         //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   17147             :         //  FullLoadOutAirRH = PsyRhFnTdbWPb(FullLoadOutAirTemp,FullLoadOutAirHumRat,InletAirPressure)
   17148      133476 :         if (FullLoadOutAirRH > 1.0) { // Limit to saturated conditions at FullLoadOutAirEnth
   17149           0 :             FullLoadOutAirTemp = PsyTsatFnHPb(state, FullLoadOutAirEnth, OutdoorPressure);
   17150             :             //  Eventually inlet air conditions will be used in DX Coil, these lines are commented out and marked with this comment line
   17151             :             //    FullLoadOutAirTemp = PsyTsatFnHPb(FullLoadOutAirEnth,InletAirPressure)
   17152           0 :             FullLoadOutAirHumRat = PsyWFnTdbH(state, FullLoadOutAirTemp, FullLoadOutAirEnth);
   17153             :         }
   17154             : 
   17155             :         // Calculate electricity consumed. First, get EIR modifying factors for off-rated conditions
   17156             :         // Model was extended to accept bi-quadratic curves. This allows sensitivity of the EIR
   17157             :         // to the entering dry-bulb temperature as well as the outside dry-bulb temperature. User is
   17158             :         // advised to use the bi-quaratic curve if sufficient manufacturer data is available.
   17159      133476 :         if (thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_Heating && thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_FluidTCtrl_Heating) {
   17160           0 :             if (state.dataCurveManager->PerfCurve(thisDXCoil.EIRFTemp(Mode))->numDims == 1) {
   17161           0 :                 EIRTempModFac = CurveValue(state, thisDXCoil.EIRFTemp(Mode), OutdoorDryBulb);
   17162             :             } else {
   17163           0 :                 EIRTempModFac = CurveValue(state, thisDXCoil.EIRFTemp(Mode), InletAirDryBulbTemp, OutdoorDryBulb);
   17164             :             }
   17165           0 :             EIRFlowModFac = CurveValue(state, thisDXCoil.EIRFFlow(Mode), AirMassFlowRatio);
   17166             :         } else {
   17167      133476 :             EIRTempModFac = 1.0;
   17168      133476 :             EIRFlowModFac = 1.0;
   17169             :         }
   17170      133476 :         EIR = thisDXCoil.RatedEIR(Mode) * EIRTempModFac * EIRFlowModFac;
   17171             : 
   17172             :         // Calculate PLRHeating: modified PartLoadRatio due to defrost ( reverse-cycle defrost only )
   17173      133476 :         if (TotCap > 0.0) {
   17174      133476 :             PLRHeating = min(1.0, (PartLoadRatio + LoadDueToDefrost / TotCap));
   17175             :         } else {
   17176           0 :             PLRHeating = min(1.0, PartLoadRatio);
   17177             :         }
   17178             : 
   17179      133476 :         if (thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_Heating && thisDXCoil.DXCoilType_Num != HVAC::CoilVRF_FluidTCtrl_Heating) {
   17180           0 :             PLF = CurveValue(state, thisDXCoil.PLFFPLR(Mode), PLRHeating); // Calculate part-load factor
   17181             :         } else {
   17182      133476 :             PLF = 1.0;
   17183             :         }
   17184             : 
   17185      133476 :         if (PLF < 0.7) {
   17186           0 :             if (thisDXCoil.PLRErrIndex == 0) {
   17187           0 :                 ShowWarningMessage(
   17188             :                     state,
   17189           0 :                     format("The PLF curve value for DX heating coil {} ={:.2R} for part-load ratio ={:.2R}", thisDXCoil.Name, PLF, PLRHeating));
   17190           0 :                 ShowContinueError(state, "PLF curve values must be >= 0.7. PLF has been reset to 0.7 and simulation is continuing.");
   17191           0 :                 ShowContinueError(state, "Check the IO reference manual for PLF curve guidance [Coil:Heating:DX:SingleSpeed].");
   17192           0 :                 ShowContinueErrorTimeStamp(state, "");
   17193             :             }
   17194           0 :             ShowRecurringWarningErrorAtEnd(state, "DX heating coil PLF curve < 0.7 warning continues... ", thisDXCoil.PLRErrIndex, PLF, PLF);
   17195           0 :             PLF = 0.7;
   17196             :         }
   17197             : 
   17198      133476 :         thisDXCoil.HeatingCoilRuntimeFraction = (PLRHeating / PLF);
   17199      133476 :         if (thisDXCoil.HeatingCoilRuntimeFraction > 1.0 && std::abs(thisDXCoil.HeatingCoilRuntimeFraction - 1.0) > 0.001) {
   17200           0 :             if (thisDXCoil.ErrIndex4 == 0) {
   17201           0 :                 ShowWarningMessage(state,
   17202           0 :                                    format("The runtime fraction for DX heating coil {} exceeded 1.0. [{:.4R}].",
   17203           0 :                                           thisDXCoil.Name,
   17204           0 :                                           thisDXCoil.HeatingCoilRuntimeFraction));
   17205           0 :                 ShowContinueError(state, "Runtime fraction is set to 1.0 and the simulation continues...");
   17206           0 :                 ShowContinueError(state, "Check the IO reference manual for PLF curve guidance [Coil:Heating:DX:SingleSpeed].");
   17207           0 :                 ShowContinueErrorTimeStamp(state, "");
   17208             :             }
   17209           0 :             ShowRecurringWarningErrorAtEnd(state,
   17210           0 :                                            thisDXCoil.Name + ", DX heating coil runtime fraction > 1.0 warning continues...",
   17211           0 :                                            thisDXCoil.ErrIndex4,
   17212           0 :                                            thisDXCoil.HeatingCoilRuntimeFraction,
   17213           0 :                                            thisDXCoil.HeatingCoilRuntimeFraction);
   17214           0 :             thisDXCoil.HeatingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   17215      133476 :         } else if (thisDXCoil.HeatingCoilRuntimeFraction > 1.0) {
   17216           0 :             thisDXCoil.HeatingCoilRuntimeFraction = 1.0; // Reset coil runtime fraction to 1.0
   17217             :         }
   17218             : 
   17219             :         // if cycling fan, send coil part-load fraction to on / off fan via HVACDataGlobals
   17220      133476 :         if (fanOp == HVAC::FanOp::Cycling) state.dataHVACGlobal->OnOffFanPartLoadFraction = PLF;
   17221      133476 :         thisDXCoil.ElecHeatingPower = TotCap * EIR * thisDXCoil.HeatingCoilRuntimeFraction * InputPowerMultiplier;
   17222             : 
   17223             :         // Calculate crankcase heater power using the runtime fraction for this DX heating coil only if there is no companion DX coil.
   17224             :         // Else use the largest runtime fraction of this DX heating coil and the companion DX cooling coil.
   17225      133476 :         if (thisDXCoil.CompanionUpstreamDXCoil == 0) {
   17226      133476 :             thisDXCoil.CrankcaseHeaterPower = CrankcaseHeatingPower * (1.0 - thisDXCoil.HeatingCoilRuntimeFraction);
   17227             :         } else {
   17228           0 :             thisDXCoil.CrankcaseHeaterPower =
   17229           0 :                 CrankcaseHeatingPower * (1.0 - max(thisDXCoil.HeatingCoilRuntimeFraction,
   17230           0 :                                                    state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).CoolingCoilRuntimeFraction));
   17231             :         }
   17232             : 
   17233      133476 :         thisDXCoil.OutletAirTemp = OutletAirTemp;
   17234      133476 :         thisDXCoil.OutletAirHumRat = OutletAirHumRat;
   17235      133476 :         thisDXCoil.OutletAirEnthalpy = OutletAirEnthalpy;
   17236      133476 :         thisDXCoil.CompressorPartLoadRatio = PartLoadRatio;
   17237      133476 :         thisDXCoil.ActualSH = ActualSH;
   17238      133476 :         thisDXCoil.ActualSC = ActualSC;
   17239      133476 :         thisDXCoil.TotalHeatingEnergyRate = AirMassFlow * (OutletAirEnthalpy - InletAirEnthalpy) * PartLoadRatio;
   17240      133476 :         thisDXCoil.DefrostPower = thisDXCoil.DefrostPower * thisDXCoil.HeatingCoilRuntimeFraction;
   17241             : 
   17242             :     } else {
   17243             :         // DX coil is off; just pass through conditions
   17244             : 
   17245      550516 :         thisDXCoil.OutletAirEnthalpy = thisDXCoil.InletAirEnthalpy;
   17246      550516 :         thisDXCoil.OutletAirHumRat = thisDXCoil.InletAirHumRat;
   17247      550516 :         thisDXCoil.OutletAirTemp = thisDXCoil.InletAirTemp;
   17248             : 
   17249      550516 :         thisDXCoil.ElecHeatingPower = 0.0;
   17250      550516 :         thisDXCoil.TotalHeatingEnergyRate = 0.0;
   17251      550516 :         thisDXCoil.DefrostPower = 0.0;
   17252             : 
   17253             :         // Calculate crankcase heater power using the runtime fraction for this DX heating coil (here DXHeatingCoilRTF=0) if
   17254             :         // there is no companion DX coil, or the runtime fraction of the companion DX cooling coil (here DXCoolingCoilRTF>=0).
   17255      550516 :         if (thisDXCoil.CompanionUpstreamDXCoil == 0) {
   17256      550516 :             thisDXCoil.CrankcaseHeaterPower = CrankcaseHeatingPower;
   17257             :         } else {
   17258           0 :             thisDXCoil.CrankcaseHeaterPower =
   17259           0 :                 CrankcaseHeatingPower * (1.0 - state.dataDXCoils->DXCoil(thisDXCoil.CompanionUpstreamDXCoil).CoolingCoilRuntimeFraction);
   17260             :         }
   17261      550516 :         thisDXCoil.CompressorPartLoadRatio = 0.0;
   17262             : 
   17263      550516 :         thisDXCoil.ActualSH = 999.0;
   17264      550516 :         thisDXCoil.ActualSC = 999.0;
   17265             :     } // end of on/off if - else
   17266             : 
   17267      683992 :     state.dataDXCoils->DXCoilOutletTemp(DXCoilNum) = thisDXCoil.OutletAirTemp;
   17268      683992 :     state.dataDXCoils->DXCoilOutletHumRat(DXCoilNum) = thisDXCoil.OutletAirHumRat;
   17269      683992 :     state.dataDXCoils->DXCoilFanOp(DXCoilNum) = fanOp;
   17270      683992 :     state.dataDXCoils->DXCoilPartLoadRatio(DXCoilNum) = PLRHeating;
   17271      683992 :     state.dataDXCoils->DXCoilTotalHeating(DXCoilNum) = thisDXCoil.TotalHeatingEnergyRate;
   17272      683992 :     state.dataDXCoils->DXCoilHeatInletAirDBTemp(DXCoilNum) = InletAirDryBulbTemp;
   17273      683992 :     state.dataDXCoils->DXCoilHeatInletAirWBTemp(DXCoilNum) = InletAirWetBulbC;
   17274             : 
   17275             :     // calc secondary coil if specified
   17276      683992 :     if (thisDXCoil.IsSecondaryDXCoilInZone) {
   17277           0 :         CalcSecondaryDXCoils(state, DXCoilNum);
   17278             :     }
   17279      683992 : }
   17280             : 
   17281     1846744 : void ControlVRFIUCoil(EnergyPlusData &state,
   17282             :                       int const CoilIndex,     // index to VRFTU coil
   17283             :                       Real64 const QCoil,      // coil load
   17284             :                       Real64 const Tin,        // inlet air temperature
   17285             :                       Real64 const Win,        // inlet air humidity ratio
   17286             :                       Real64 const TeTc,       // evaporating or condensing temperature
   17287             :                       Real64 const OAMassFlow, // mass flow rate of outdoor air
   17288             :                       Real64 &FanSpdRatio,     // fan speed ratio: actual flow rate / rated flow rate
   17289             :                       Real64 &Wout,            // outlet air humidity ratio
   17290             :                       Real64 &Tout,            // outlet air temperature
   17291             :                       Real64 &Hout,            // outlet air enthalpy
   17292             :                       Real64 &SHact,           // actual SH
   17293             :                       Real64 &SCact            // actual SC
   17294             : )
   17295             : {
   17296             :     // SUBROUTINE INFORMATION:
   17297             :     //       AUTHOR         Xiufeng Pang, LBNL
   17298             :     //       DATE WRITTEN   Feb 2013
   17299             :     //       MODIFIED       Nov 2015, RP Zhang, LBNL
   17300             :     //
   17301             :     // PURPOSE OF THIS SUBROUTINE:
   17302             :     //       Analyze the VRF Indoor Unit operations given coil loads.
   17303             :     //       Calculated parameters include: (1) Fan Speed Ratio (2) SH/SC, (3) Coil Outlet conditions
   17304             :     //
   17305             :     // METHODOLOGY EMPLOYED:
   17306             :     //       A new physics based VRF model applicable for Fluid Temperature Control.
   17307             :     //
   17308             :     // USE STATEMENTS:
   17309             :     using Psychrometrics::PsyHFnTdbW;
   17310             : 
   17311             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   17312     1846744 :     int MaxIter(500);              // Max iteration numbers (-)
   17313             :     int SolFla;                    // Solving flag for SolveRoot (-)
   17314     1846744 :     int constexpr FlagCoolMode(0); // Flag for cooling mode
   17315     1846744 :     int constexpr FlagHeatMode(1); // Flag for heating mode
   17316             :     Real64 BF;                     // Bypass factor (-)
   17317             :     Real64 C1Tevap;                // Coefficient for indoor unit coil evaporating temperature curve (-)
   17318             :     Real64 C2Tevap;                // Coefficient for indoor unit coil evaporating temperature curve (-)
   17319             :     Real64 C3Tevap;                // Coefficient for indoor unit coil evaporating temperature curve (-)
   17320             :     Real64 C1Tcond;                // Coefficient for indoor unit coil condensing temperature curve (-)
   17321             :     Real64 C2Tcond;                // Coefficient for indoor unit coil condensing temperature curve (-)
   17322             :     Real64 C3Tcond;                // Coefficient for indoor unit coil condensing temperature curve (-)
   17323             :     Real64 CoilOnOffRatio;         // coil on/off ratio: time coil is on divided by total time
   17324             :     Real64 deltaT;                 // Difference between evaporating/condensing temperature and coil surface temperature (C)
   17325             :     Real64 FanSpdRatioMin;         // Min fan speed ratio, below which the cycling will be activated (-)
   17326             :     Real64 FanSpdRatioMax;         // Max fan speed ratio (-)
   17327             :     Real64 Garate;                 // Nominal air mass flow rate (m3/s)
   17328             :     Real64 MaxSH;                  // Max super heating degrees (C)
   17329             :     Real64 MaxSC;                  // Max subcooling degrees (C)
   17330             :     Real64 QinSenMin1;             // Coil capacity at minimum fan speed, corresponding to real SH (W)
   17331             :     Real64 QinSenMin2;             // Coil capacity at minimum fan speed, corresponding to corresponds maximum SH (W)
   17332             :     Real64 QinSenPerFlowRate;      // Coil capacity per air mass flow rate(W-s/kg)
   17333             :     Real64 QCoilSenCoolingLoad;    // Coil sensible cooling load (W)
   17334             :     Real64 QCoilSenHeatingLoad;    // Coil sensible heating load (W)
   17335             :     Real64 Ratio1;                 // Fan speed ratio (-)
   17336             :     Real64 RHsat;                  // Relative humidity of the air at saturated condition(-)
   17337             :     Real64 SH;                     // Super heating degrees (C)
   17338             :     Real64 SC;                     // Subcooling degrees (C)
   17339             :     Real64 Ts_1;                   // Air temperature at the coil surface, corresponding to SH (C)
   17340             :     Real64 Ts_2;                   // Air temperature at the coil surface, corresponding to MaxSH (C)
   17341             :     Real64 To_1;                   // Air temperature at the coil outlet, corresponding to SH (C)
   17342             :     Real64 To_2;                   // Air temperature at the coil outlet, corresponding to MaxSH (C)
   17343             :     Real64 Ts;                     // Air temperature at the coil surface (C)
   17344             :     Real64 Ws;                     // Air humidity ratio at the coil surface (kg/kg)
   17345             : 
   17346     1846744 :     RHsat = 0.98; // Saturated RH
   17347     1846744 :     MaxSH = 15;
   17348     1846744 :     MaxSC = 20;
   17349     1846744 :     Garate = state.dataDXCoils->DXCoil(CoilIndex).RatedAirMassFlowRate(1);
   17350             :     // why always limit the minimum fan speed ratio to 0.65?
   17351     1846744 :     FanSpdRatioMin = min(max(OAMassFlow / Garate, 0.65), 1.0); // ensure that coil flow rate is higher than OA flow rate
   17352             : 
   17353     1846744 :     if (QCoil == 0) {
   17354             :         // No Heating or Cooling
   17355           0 :         FanSpdRatio = OAMassFlow / Garate;
   17356           0 :         CoilOnOffRatio = 0.0;
   17357             : 
   17358           0 :         SHact = 999.0;
   17359           0 :         SCact = 999.0;
   17360           0 :         Tout = Tin;
   17361           0 :         Hout = PsyHFnTdbW(Tin, Win);
   17362           0 :         Wout = Win;
   17363             : 
   17364     1846744 :     } else if (QCoil < 0) {
   17365             :         // Cooling Mode
   17366             : 
   17367             :         // Obtain coil cooling loads
   17368     1293837 :         QCoilSenCoolingLoad = -QCoil;
   17369             : 
   17370             :         // Coefficients describing coil performance
   17371     1293837 :         SH = state.dataDXCoils->DXCoil(CoilIndex).SH;
   17372     1293837 :         C1Tevap = state.dataDXCoils->DXCoil(CoilIndex).C1Te;
   17373     1293837 :         C2Tevap = state.dataDXCoils->DXCoil(CoilIndex).C2Te;
   17374     1293837 :         C3Tevap = state.dataDXCoils->DXCoil(CoilIndex).C3Te;
   17375     1293837 :         BF = state.dataDXCoils->DXCoil(CoilIndex).RateBFVRFIUEvap;
   17376             : 
   17377             :         // Coil sensible heat transfer_minimum value
   17378     1293837 :         CalcVRFCoilSenCap(state, FlagCoolMode, CoilIndex, Tin, TeTc, SH, BF, QinSenPerFlowRate, Ts_1);
   17379     1293837 :         To_1 = Tin - QinSenPerFlowRate / 1005;
   17380     1293837 :         QinSenMin1 = FanSpdRatioMin * Garate * QinSenPerFlowRate; // Corresponds real SH
   17381             : 
   17382     1293837 :         CalcVRFCoilSenCap(state, FlagCoolMode, CoilIndex, Tin, TeTc, MaxSH, BF, QinSenPerFlowRate, Ts_2);
   17383     1293837 :         To_2 = Tin - QinSenPerFlowRate / 1005;
   17384     1293837 :         QinSenMin2 = FanSpdRatioMin * Garate * QinSenPerFlowRate; // Corresponds maximum SH
   17385             : 
   17386     1293837 :         if (QCoilSenCoolingLoad > QinSenMin1) {
   17387             :             // Increase fan speed to meet room sensible load; SH is not updated
   17388      784204 :             FanSpdRatioMax = 1.0;
   17389     2053140 :             auto f = [QCoilSenCoolingLoad, Ts_1, Tin, Garate, BF](Real64 FanSpdRto) {
   17390     2053140 :                 return FanSpdResidualCool(FanSpdRto, QCoilSenCoolingLoad, Ts_1, Tin, Garate, BF);
   17391      784204 :             };
   17392      784204 :             General::SolveRoot(state, 1.0e-3, MaxIter, SolFla, Ratio1, f, FanSpdRatioMin, FanSpdRatioMax);
   17393      784204 :             if (SolFla < 0) Ratio1 = FanSpdRatioMax; // over capacity
   17394      784204 :             FanSpdRatio = Ratio1;
   17395      784204 :             CoilOnOffRatio = 1.0;
   17396             : 
   17397      784204 :             Tout = To_1; // Since SH is not updated
   17398      784204 :             Ws = PsyWFnTdbRhPb(state, Ts_1, RHsat, state.dataEnvrn->OutBaroPress, "ControlVRFIUCoil");
   17399      784204 :             if (Ws < Win) {
   17400      779645 :                 Wout = Win - (Win - Ws) * (1 - BF);
   17401             :             } else {
   17402        4559 :                 Wout = Win;
   17403             :             }
   17404      784204 :             Hout = PsyHFnTdbW(Tout, Wout);
   17405      784204 :             SCact = 999.0;
   17406      784204 :             SHact = SH;
   17407             : 
   17408             :         } else {
   17409             :             // Low load modification algorithm
   17410             :             // Need to increase SH to further reduce coil capacity
   17411             :             // May further implement coil cycling control if SC modification is not enough
   17412             : 
   17413      509633 :             FanSpdRatio = FanSpdRatioMin;
   17414             : 
   17415      509633 :             CoilOnOffRatio = 1.0;
   17416             : 
   17417      509633 :             Tout = Tin - QCoilSenCoolingLoad / 1005.0 / FanSpdRatioMin / Garate;
   17418      509633 :             Ts = Tin - (Tin - Tout) / (1 - BF);
   17419      509633 :             deltaT = Ts - TeTc;
   17420             : 
   17421             :             // Update SH
   17422      509633 :             if (C3Tevap <= 0.0) {
   17423      507605 :                 if (C2Tevap > 0.0) {
   17424      507605 :                     SHact = (deltaT - C1Tevap) / C2Tevap;
   17425             :                 } else {
   17426           0 :                     SHact = 998.0;
   17427             :                 }
   17428             :             } else {
   17429        2028 :                 SHact = (-C2Tevap + sqrt(pow_2(C2Tevap) - 4 * C3Tevap * (C1Tevap - deltaT))) / 2 / C3Tevap;
   17430             :             }
   17431             : 
   17432      509633 :             Ws = PsyWFnTdbRhPb(state, Ts, RHsat, state.dataEnvrn->OutBaroPress, "ControlVRFIUCoil");
   17433      509633 :             if (Ws < Win) {
   17434      340869 :                 Wout = Win - (Win - Ws) * (1 - BF);
   17435             :             } else {
   17436      168764 :                 Wout = Win;
   17437             :             }
   17438             : 
   17439      509633 :             if (SHact > MaxSH) {
   17440             :                 // Further implement On/Off Control
   17441      141368 :                 SHact = MaxSH;
   17442      141368 :                 CoilOnOffRatio = QCoilSenCoolingLoad / QinSenMin2;
   17443             : 
   17444      141368 :                 Ts = Ts_2;
   17445      141368 :                 Ws = PsyWFnTdbRhPb(state, Ts, RHsat, state.dataEnvrn->OutBaroPress, "ControlVRFIUCoil");
   17446      141368 :                 if (Ws < Win) {
   17447      128867 :                     Wout = Win - (Win - Ws) * (1 - BF);
   17448             :                 } else {
   17449       12501 :                     Wout = Win;
   17450             :                 }
   17451             : 
   17452             :                 // outlet air temperature and humidity ratio is time-weighted
   17453      141368 :                 Tout = CoilOnOffRatio * To_2 + (1 - CoilOnOffRatio) * Tin;
   17454      141368 :                 Wout = CoilOnOffRatio * Wout + (1 - CoilOnOffRatio) * Win;
   17455             :             }
   17456             : 
   17457      509633 :             Hout = PsyHFnTdbW(Tout, Wout);
   17458      509633 :             SCact = 999.0;
   17459             :         }
   17460             : 
   17461      552907 :     } else if (QCoil > 0) {
   17462             :         // Heating Mode
   17463             : 
   17464             :         // Obtain zonal heating loads
   17465      552907 :         QCoilSenHeatingLoad = QCoil;
   17466             : 
   17467             :         // Coefficients describing coil performance
   17468      552907 :         SC = state.dataDXCoils->DXCoil(CoilIndex).SC;
   17469      552907 :         C1Tcond = state.dataDXCoils->DXCoil(CoilIndex).C1Tc;
   17470      552907 :         C2Tcond = state.dataDXCoils->DXCoil(CoilIndex).C2Tc;
   17471      552907 :         C3Tcond = state.dataDXCoils->DXCoil(CoilIndex).C3Tc;
   17472      552907 :         BF = state.dataDXCoils->DXCoil(CoilIndex).RateBFVRFIUCond;
   17473             : 
   17474             :         // Coil sensible heat transfer_minimum value
   17475      552907 :         CalcVRFCoilSenCap(state, FlagHeatMode, CoilIndex, Tin, TeTc, SC, BF, QinSenPerFlowRate, Ts_1);
   17476      552907 :         To_1 = QinSenPerFlowRate / 1005 + Tin;
   17477      552907 :         QinSenMin1 = FanSpdRatioMin * Garate * QinSenPerFlowRate; // Corresponds real SH
   17478             : 
   17479      552907 :         CalcVRFCoilSenCap(state, FlagHeatMode, CoilIndex, Tin, TeTc, MaxSC, BF, QinSenPerFlowRate, Ts_2);
   17480      552907 :         To_2 = QinSenPerFlowRate / 1005 + Tin;
   17481      552907 :         QinSenMin2 = FanSpdRatioMin * Garate * QinSenPerFlowRate; // Corresponds maximum SH
   17482             : 
   17483      552907 :         if (QCoilSenHeatingLoad > QinSenMin1) {
   17484             :             // Modulate fan speed to meet room sensible load; SC is not updated
   17485      134083 :             FanSpdRatioMax = 1.0;
   17486      363165 :             auto f = [QCoilSenHeatingLoad, Ts_1, Tin, Garate, BF](Real64 FanSpdRto) {
   17487      363165 :                 return FanSpdResidualHeat(FanSpdRto, QCoilSenHeatingLoad, Ts_1, Tin, Garate, BF);
   17488      134083 :             };
   17489      134083 :             General::SolveRoot(state, 1.0e-3, MaxIter, SolFla, Ratio1, f, FanSpdRatioMin, FanSpdRatioMax);
   17490             :             // this will likely cause problems eventually, -1 and -2 mean different things
   17491      134083 :             if (SolFla < 0) Ratio1 = FanSpdRatioMax; // over capacity
   17492      134083 :             FanSpdRatio = Ratio1;
   17493      134083 :             CoilOnOffRatio = 1.0;
   17494             : 
   17495      134083 :             Tout = Tin + (Ts_1 - Tin) * (1 - BF);
   17496      134083 :             Wout = Win;
   17497      134083 :             Hout = PsyHFnTdbW(Tout, Wout);
   17498      134083 :             SHact = 999.0;
   17499      134083 :             SCact = SC;
   17500             : 
   17501             :         } else {
   17502             :             // Low load modification algorithm
   17503             :             // Need to increase SC to further reduce coil heating capacity
   17504             :             // May further implement coil cycling control if SC modification is not enough
   17505             : 
   17506      418824 :             FanSpdRatio = FanSpdRatioMin;
   17507      418824 :             CoilOnOffRatio = 1.0;
   17508             : 
   17509      418824 :             Tout = Tin + QCoilSenHeatingLoad / 1005.0 / FanSpdRatio / Garate;
   17510      418824 :             Ts = Tin + (Tout - Tin) / (1 - BF);
   17511      418824 :             deltaT = TeTc - Ts;
   17512             : 
   17513             :             // Update SC
   17514      418824 :             if (C3Tcond <= 0.0) {
   17515           0 :                 if (C2Tcond > 0.0) {
   17516           0 :                     SCact = (deltaT - C1Tcond) / C2Tcond;
   17517             :                 } else {
   17518           0 :                     SCact = 998.0;
   17519             :                 }
   17520             :             } else {
   17521      418824 :                 SCact = (-C2Tcond + sqrt(pow_2(C2Tcond) - 4 * C3Tcond * (C1Tcond - deltaT))) / 2 / C3Tcond;
   17522             :             }
   17523             : 
   17524      418824 :             if (SCact > MaxSC) {
   17525             :                 // Implement On/Off Control
   17526      271995 :                 SCact = MaxSC;
   17527      271995 :                 CoilOnOffRatio = QCoilSenHeatingLoad / QinSenMin2;
   17528             :                 // outlet air temperature is time-weighted
   17529      271995 :                 Tout = CoilOnOffRatio * To_2 + (1 - CoilOnOffRatio) * Tin;
   17530             :             }
   17531      418824 :             Wout = Win;
   17532      418824 :             Hout = PsyHFnTdbW(Tout, Wout);
   17533      418824 :             SHact = 999.0;
   17534             :         }
   17535             :     }
   17536     1846744 : }
   17537             : 
   17538     3693520 : void CalcVRFCoilSenCap(EnergyPlusData &state,
   17539             :                        int const OperationMode, // mode 0 for cooling, 1 for heating
   17540             :                        int const CoilNum,       // index to VRFTU cooling or heating coil
   17541             :                        Real64 const Tinlet,     // dry bulb temperature of air entering the coil
   17542             :                        Real64 const TeTc,       // evaporating or condensing temperature
   17543             :                        Real64 const SHSC,       // SH at cooling /SC at heating
   17544             :                        Real64 const BF,         // Bypass factor
   17545             :                        Real64 &Q_sen,           // VRF coil sensible capacity per air mass flow rate
   17546             :                        Real64 &T_coil_surf      // Air temperature at coil surface
   17547             : )
   17548             : {
   17549             :     // SUBROUTINE INFORMATION:
   17550             :     //       AUTHOR         Rongpeng Zhang, LBNL
   17551             :     //       DATE WRITTEN   Jul 2015
   17552             :     //
   17553             :     // PURPOSE OF THIS SUBROUTINE:
   17554             :     //        Calculate the VRF coil sensible capacity per air mass flow rate, given:
   17555             :     //        (1) refrigerant temperature (Te or Tc), (2) SH or SC, and (3) inlet air temperature.
   17556             :     //
   17557             :     // METHODOLOGY EMPLOYED:
   17558             :     //        A new physics based VRF model appliable for Fluid Temperature Control.
   17559             :     //
   17560             : 
   17561     3693520 :     int constexpr FlagCoolMode(0); // Flag for cooling mode
   17562     3693520 :     int constexpr FlagHeatMode(1); // Flag for heating mode
   17563             :     Real64 C1Tevap;                // Coefficient for indoor unit coil evaporating temperature curve (-)
   17564             :     Real64 C2Tevap;                // Coefficient for indoor unit coil evaporating temperature curve (-)
   17565             :     Real64 C3Tevap;                // Coefficient for indoor unit coil evaporating temperature curve (-)
   17566             :     Real64 C1Tcond;                // Coefficient for indoor unit coil condensing temperature curve (-)
   17567             :     Real64 C2Tcond;                // Coefficient for indoor unit coil condensing temperature curve (-)
   17568             :     Real64 C3Tcond;                // Coefficient for indoor unit coil condensing temperature curve (-)
   17569             :     Real64 deltaT;                 // Difference between Te/Tc and coil surface temperature (C)
   17570             :     Real64 SH;                     // Super heating at cooling mode(C)
   17571             :     Real64 SC;                     // Subcooling at heating mode (C)
   17572             :     Real64 T_coil_in;              // Air temperature at coil inlet (C)
   17573             :     Real64 T_coil_out;             // Air temperature at coil outlet (C)
   17574             : 
   17575     3693520 :     if (OperationMode == FlagCoolMode) {
   17576             :         // Cooling: OperationMode 0
   17577             : 
   17578     2587706 :         C1Tevap = state.dataDXCoils->DXCoil(CoilNum).C1Te;
   17579     2587706 :         C2Tevap = state.dataDXCoils->DXCoil(CoilNum).C2Te;
   17580     2587706 :         C3Tevap = state.dataDXCoils->DXCoil(CoilNum).C3Te;
   17581     2587706 :         SH = SHSC;
   17582     2587706 :         T_coil_in = Tinlet;
   17583             : 
   17584             :         // Coil surface temperature
   17585     2587706 :         deltaT = C3Tevap * SH * SH + C2Tevap * SH + C1Tevap;
   17586     2587706 :         T_coil_surf = TeTc + deltaT;
   17587             : 
   17588             :         // Outlet air temperature
   17589     2587706 :         T_coil_out = T_coil_in - (T_coil_in - T_coil_surf) * (1 - BF);
   17590             : 
   17591             :         // Coil sensilbe heat transfer per mass flow rate
   17592     2587706 :         Q_sen = max(1005 * (T_coil_in - T_coil_out), 0.0);
   17593             : 
   17594     1105814 :     } else if (OperationMode == FlagHeatMode) {
   17595             :         // Heating: OperationMode 1
   17596             : 
   17597     1105814 :         C1Tcond = state.dataDXCoils->DXCoil(CoilNum).C1Tc;
   17598     1105814 :         C2Tcond = state.dataDXCoils->DXCoil(CoilNum).C2Tc;
   17599     1105814 :         C3Tcond = state.dataDXCoils->DXCoil(CoilNum).C3Tc;
   17600     1105814 :         SC = SHSC;
   17601     1105814 :         T_coil_in = Tinlet;
   17602             : 
   17603             :         // Coil surface temperature
   17604     1105814 :         deltaT = C3Tcond * SC * SC + C2Tcond * SC + C1Tcond;
   17605     1105814 :         T_coil_surf = TeTc - deltaT;
   17606             : 
   17607             :         // Coil outlet air temperature
   17608     1105814 :         T_coil_out = T_coil_in + (T_coil_surf - T_coil_in) * (1 - BF);
   17609             : 
   17610             :         // Coil sensilbe heat transfer_minimum value
   17611     1105814 :         Q_sen = max(1005 * (T_coil_out - T_coil_in), 0.0);
   17612             :     }
   17613     3693520 : }
   17614             : 
   17615          16 : void CalcVRFCoilCapModFac(EnergyPlusData &state,
   17616             :                           int const OperationMode,                   // mode 0 for cooling, 1 for heating
   17617             :                           ObjexxFCL::Optional<int const> CoilIndex,  // index to VRFTU cooling or heating coil
   17618             :                           ObjexxFCL::Optional<std::string> CoilName, // name of VRFTU cooling or heating coil
   17619             :                           Real64 const Tinlet,                       // dry bulb temperature of air entering the coil
   17620             :                           ObjexxFCL::Optional<Real64 const> TeTc,    // evaporating or condensing temperature
   17621             :                           ObjexxFCL::Optional<Real64 const> SHSC,    // SH at cooling /SC at heating
   17622             :                           ObjexxFCL::Optional<Real64 const> BF,      // Bypass factor
   17623             :                           Real64 &CapModFac                          // Coil capacity modification factor
   17624             : )
   17625             : {
   17626             :     // SUBROUTINE INFORMATION:
   17627             :     //       AUTHOR         Rongpeng Zhang, LBNL
   17628             :     //       DATE WRITTEN   Jul 2015
   17629             :     //
   17630             :     // PURPOSE OF THIS SUBROUTINE:
   17631             :     //        Calculate the VRF coil capacity modification factor, which is the ratio of
   17632             :     //        the capacity at real conditions and that at rated conditions.
   17633             :     //        This is used for the coil sizing subroutine.
   17634             :     //
   17635             :     // METHODOLOGY EMPLOYED:
   17636             :     //        A new physics based VRF model applicable for Fluid Temperature Control.
   17637             :     //
   17638             : 
   17639          16 :     bool ErrorsFound(false);       // Flag for errors
   17640          16 :     int constexpr FlagCoolMode(0); // Flag for cooling mode
   17641          16 :     int constexpr FlagHeatMode(1); // Flag for heating mode
   17642          16 :     Real64 constexpr SH_rate(3);   // Super heating at cooling mode, default 3(C)
   17643          16 :     Real64 constexpr SC_rate(5);   // Subcooling at heating mode, default 5 (C)
   17644          16 :     Real64 constexpr Te_rate(6);   // Evaporating temperature at cooling mode, default 6 (C)
   17645          16 :     Real64 constexpr Tc_rate(44);  // Condensing temperature at heating mode, default 44 (C)
   17646             :     int CoilNum;                   // index to VRFTU cooling or heating coil
   17647             :     Real64 BF_real;                // Bypass factor (-)
   17648             :     Real64 BFC_rate;               // Bypass factor at cooling mode (-)
   17649             :     Real64 BFH_rate;               // Bypass factor at heating mode (-)
   17650             :     Real64 SHSC_real;              // Super heating or Subcooling (C)
   17651             :     Real64 TeTc_real;              // Evaporating temperature or condensing temperature (C)
   17652             :     Real64 Ts;                     // Air temperature at coil surface (C)
   17653             :     Real64 Q_real;                 // Coil capacity at given condition (W)
   17654             :     Real64 Q_rate;                 // Coil capacity at rated condition (W)
   17655             : 
   17656          16 :     if (present(CoilIndex)) {
   17657           0 :         CoilNum = CoilIndex;
   17658             :     } else {
   17659          16 :         GetDXCoilIndex(state, CoilName, CoilNum, ErrorsFound, "", true);
   17660             :     }
   17661             : 
   17662          16 :     BFC_rate = state.dataDXCoils->DXCoil(CoilNum).RateBFVRFIUEvap;
   17663          16 :     BFH_rate = state.dataDXCoils->DXCoil(CoilNum).RateBFVRFIUCond;
   17664             : 
   17665          16 :     if (OperationMode == FlagCoolMode) {
   17666             :         // Cooling: OperationMode 0
   17667             : 
   17668          16 :         if (present(BF)) {
   17669           0 :             BF_real = BF;
   17670             :         } else {
   17671          16 :             BF_real = BFC_rate;
   17672             :         }
   17673          16 :         if (present(TeTc)) {
   17674           0 :             TeTc_real = TeTc;
   17675             :         } else {
   17676          16 :             TeTc_real = Te_rate;
   17677             :         }
   17678          16 :         if (present(SHSC)) {
   17679           0 :             SHSC_real = SHSC;
   17680             :         } else {
   17681          16 :             SHSC_real = SH_rate;
   17682             :         }
   17683             : 
   17684             :         // Coil capacity at rated conditions
   17685          16 :         CalcVRFCoilSenCap(state, FlagCoolMode, CoilNum, 26, Te_rate, SH_rate, BFC_rate, Q_rate, Ts);
   17686             : 
   17687             :         // Coil capacity at given conditions
   17688          16 :         CalcVRFCoilSenCap(state, FlagCoolMode, CoilNum, Tinlet, TeTc_real, SHSC_real, BF_real, Q_real, Ts);
   17689             : 
   17690          16 :         if (Q_rate > 0) {
   17691          16 :             CapModFac = Q_real / Q_rate;
   17692             :         } else {
   17693           0 :             CapModFac = 1.0;
   17694             :         }
   17695             : 
   17696           0 :     } else if (OperationMode == FlagHeatMode) {
   17697             :         // Heating: OperationMode 1
   17698             : 
   17699           0 :         if (present(BF)) {
   17700           0 :             BF_real = BF;
   17701             :         } else {
   17702           0 :             BF_real = BFH_rate;
   17703             :         }
   17704           0 :         if (present(TeTc)) {
   17705           0 :             TeTc_real = TeTc;
   17706             :         } else {
   17707           0 :             TeTc_real = Tc_rate;
   17708             :         }
   17709           0 :         if (present(SHSC)) {
   17710           0 :             SHSC_real = SHSC;
   17711             :         } else {
   17712           0 :             SHSC_real = SC_rate;
   17713             :         }
   17714             : 
   17715             :         // Coil capacity at rated conditions
   17716           0 :         CalcVRFCoilSenCap(state, FlagHeatMode, CoilNum, 20, Tc_rate, SC_rate, BFH_rate, Q_rate, Ts);
   17717             : 
   17718             :         // Coil capacity at given conditions
   17719           0 :         CalcVRFCoilSenCap(state, FlagHeatMode, CoilNum, Tinlet, TeTc_real, SHSC_real, BF_real, Q_real, Ts);
   17720             : 
   17721           0 :         if (Q_rate > 0) {
   17722           0 :             CapModFac = Q_real / Q_rate;
   17723             :         } else {
   17724           0 :             CapModFac = 1.0;
   17725             :         }
   17726             :     }
   17727          16 : }
   17728             : 
   17729     2053140 : Real64 FanSpdResidualCool(
   17730             :     Real64 const FanSpdRto, Real64 const QCoilSenCoolingLoad, Real64 const Ts_1, Real64 const Tin, Real64 const Garate, Real64 const BF)
   17731             : {
   17732             :     // FUNCTION INFORMATION:
   17733             :     //       AUTHOR         Xiufeng Pang (XP)
   17734             :     //       DATE WRITTEN   Mar 2013
   17735             :     //       MODIFIED       Nov 2015, RP Zhang, LBNL
   17736             :     //
   17737             :     // PURPOSE OF THIS FUNCTION:
   17738             :     //       Calculates residual function (desired zone cooling load - actual coil cooling capacity)
   17739             :     //       This is used to modify the fan speed to adjust the coil cooling capacity to match
   17740             :     //       the zone cooling load.
   17741             :     //
   17742     2053140 :     Real64 ZnSenLoad = QCoilSenCoolingLoad;
   17743             :     // +-100 W minimum zone load?
   17744     2053140 :     if (std::abs(ZnSenLoad) < 100.0) ZnSenLoad = sign(100.0, ZnSenLoad);
   17745     2053140 :     Real64 Tout = Tin - (Tin - Ts_1) * (1 - BF);
   17746     2053140 :     Real64 TotCap = FanSpdRto * Garate * 1005.0 * (Tin - Tout);
   17747     2053140 :     return (TotCap - ZnSenLoad) / ZnSenLoad;
   17748             : }
   17749             : 
   17750      363165 : Real64 FanSpdResidualHeat(Real64 FanSpdRto, Real64 QCoilSenHeatingLoad, Real64 Ts_1, Real64 Tin, Real64 Garate, Real64 BF)
   17751             : {
   17752             : 
   17753             :     // FUNCTION INFORMATION:
   17754             :     //       AUTHOR         Xiufeng Pang (XP)
   17755             :     //       DATE WRITTEN   Mar 2013
   17756             :     //       MODIFIED       Nov 2015, RP Zhang, LBNL
   17757             :     //
   17758             :     // PURPOSE OF THIS FUNCTION:
   17759             :     //       Calculates residual function (desired zone heating load - actual heating coil capacity)
   17760             :     //       This is used to modify the fan speed to adjust the coil heating capacity to match
   17761             :     //       the zone heating load.
   17762             :     //
   17763             : 
   17764      363165 :     Real64 ZnSenLoad = QCoilSenHeatingLoad;
   17765             :     // +-100 W minimum zone load?
   17766      363165 :     if (std::abs(ZnSenLoad) < 100.0) ZnSenLoad = sign(100.0, ZnSenLoad);
   17767      363165 :     Real64 Tout = Tin + (Ts_1 - Tin) * (1 - BF);
   17768      363165 :     Real64 TotCap = FanSpdRto * Garate * 1005.0 * (Tout - Tin);
   17769      363165 :     return (TotCap - ZnSenLoad) / ZnSenLoad;
   17770             : }
   17771             : 
   17772           0 : void SetMSHPDXCoilHeatRecoveryFlag(EnergyPlusData &state, int const DXCoilNum)
   17773             : {
   17774             : 
   17775             :     // SUBROUTINE INFORMATION:
   17776             :     //       AUTHOR         L. Gu
   17777             :     //       DATE WRITTEN   Sep. 2015
   17778             : 
   17779             :     // PURPOSE OF THIS SUBROUTINE:
   17780             :     // Set the heat recovery flag true when the parent object requests heat recovery.
   17781             : 
   17782           0 :     if (state.dataDXCoils->DXCoil(DXCoilNum).FuelType != Constant::eFuel::Electricity) {
   17783           0 :         state.dataDXCoils->DXCoil(DXCoilNum).MSHPHeatRecActive = true;
   17784             :     }
   17785           0 : }
   17786             : 
   17787          32 : void SetDXCoilAirLoopNumber(EnergyPlusData &state, std::string const &CoilName, int const AirLoopNum)
   17788             : {
   17789             :     // SUBROUTINE INFORMATION:
   17790             :     //       AUTHOR         L. Gu
   17791             :     //       DATE WRITTEN   March, 2018
   17792             : 
   17793             :     // PURPOSE OF THIS SUBROUTINE:
   17794             :     // Set AirLoopNum for AFN model with multiple AirLoops
   17795             : 
   17796             :     // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
   17797             :     int WhichCoil;
   17798             : 
   17799          32 :     if (state.dataDXCoils->GetCoilsInputFlag) {
   17800           0 :         GetDXCoils(state);
   17801           0 :         state.dataDXCoils->GetCoilsInputFlag = false;
   17802             :     }
   17803             : 
   17804          32 :     WhichCoil = Util::FindItemInList(CoilName, state.dataDXCoils->DXCoil);
   17805          32 :     if (WhichCoil != 0) {
   17806          32 :         state.dataDXCoils->DXCoil(WhichCoil).AirLoopNum = AirLoopNum;
   17807             :     } else {
   17808           0 :         ShowSevereError(state, format("SetDXCoilAirLoopNumber: Could not find Coil \"Name=\"{}\"", CoilName));
   17809             :     }
   17810          32 : } // must match coil names for the coil type
   17811             : 
   17812           1 : void DisableLatentDegradation(EnergyPlusData &state, int const DXCoilNum)
   17813             : {
   17814             :     // SUBROUTINE INFORMATION:
   17815             :     //       AUTHOR         L. Gu
   17816             :     //       DATE WRITTEN   JUne, 2019
   17817             : 
   17818             :     // PURPOSE OF THIS SUBROUTINE:
   17819             :     // Disable latent degradation when direct solution is used.
   17820             : 
   17821           1 :     state.dataDXCoils->DXCoil(DXCoilNum).Twet_Rated(1) = 0.0;
   17822           1 : }
   17823             : 
   17824             : } // namespace EnergyPlus::DXCoils

Generated by: LCOV version 1.14