openstudio-standards 0.2.12.rc4 → 0.2.13.rc3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (541) hide show
  1. checksums.yaml +4 -4
  2. data/data/geometry/ASHRAE90120162019HighriseApartment.json +1042 -0
  3. data/data/geometry/ASHRAE90120162019Hospital.json +199 -0
  4. data/data/geometry/ASHRAE90120162019LargeHotel.json +73 -0
  5. data/data/geometry/ASHRAE90120162019LargeOffice.json +109 -0
  6. data/data/geometry/ASHRAE90120162019SecondarySchool.json +205 -0
  7. data/data/geometry/ASHRAECourthouse.json +112 -0
  8. data/data/geometry/ASHRAECourthouse.osm +26470 -0
  9. data/data/geometry/ASHRAELargeHotel.osm +11 -1
  10. data/data/geometry/ASHRAELargeOffice.json +4 -0
  11. data/data/geometry/ASHRAESmallDataCenter.json +1 -1
  12. data/data/standards/OpenStudio_Standards-ashrae_90_1(space_types).xlsx +0 -0
  13. data/data/standards/OpenStudio_Standards-ashrae_90_1-ALL-comstock(space_types).xlsx +0 -0
  14. data/data/standards/OpenStudio_Standards-ashrae_90_1.xlsx +0 -0
  15. data/data/standards/exclude_list.csv +19 -0
  16. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.boilers.json +49 -0
  17. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.chillers.json +293 -0
  18. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.construction_properties.json +25426 -0
  19. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.construction_sets.json +1600 -0
  20. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.economizers.json +564 -0
  21. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.elevators.json +349 -0
  22. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.ext_ltg.json +164 -0
  23. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.ground_temperatures.json +10663 -0
  24. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.heat_pumps.json +508 -0
  25. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.heat_pumps_heating.json +156 -0
  26. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.heat_rejection.json +44 -0
  27. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.motors.json +184 -0
  28. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.prototype_inputs.json +3094 -0
  29. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.ref_cases.json +829 -0
  30. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.ref_lnup.json +562 -0
  31. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.refrigeration_compressors.json +52 -0
  32. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.refrigeration_condenser.json +220 -0
  33. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.refrigeration_system.json +156 -0
  34. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.refrigeration_walkins.json +1316 -0
  35. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.spc_typ.json +21446 -0
  36. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.unitary_acs.json +554 -0
  37. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.water_heaters.json +68 -0
  38. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.water_source_heat_pumps.json +28 -0
  39. data/data/standards/export/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.water_source_heat_pumps_heating.json +12 -0
  40. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.boilers.json +49 -0
  41. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.chillers.json +293 -0
  42. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.construction_properties.json +12487 -0
  43. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.construction_sets.json +1600 -0
  44. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.economizers.json +564 -0
  45. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.elevators.json +349 -0
  46. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.ext_ltg.json +164 -0
  47. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.ground_temperatures.json +10663 -0
  48. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.heat_pumps.json +466 -0
  49. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.heat_pumps_heating.json +137 -0
  50. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.heat_rejection.json +44 -0
  51. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.motors.json +184 -0
  52. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.prototype_inputs.json +3094 -0
  53. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.ref_cases.json +829 -0
  54. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.ref_lnup.json +562 -0
  55. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.refrigeration_compressors.json +52 -0
  56. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.refrigeration_condenser.json +220 -0
  57. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.refrigeration_system.json +156 -0
  58. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.refrigeration_walkins.json +1316 -0
  59. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.spc_typ.json +21380 -0
  60. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.unitary_acs.json +554 -0
  61. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.water_heaters.json +68 -0
  62. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.water_source_heat_pumps.json +28 -0
  63. data/data/standards/export/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.water_source_heat_pumps_heating.json +12 -0
  64. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.boilers.json +49 -0
  65. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.chillers.json +395 -0
  66. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.construction_properties.json +12487 -0
  67. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.construction_sets.json +1600 -0
  68. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.economizers.json +592 -0
  69. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.elevators.json +349 -0
  70. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.energy_recovery.json +550 -0
  71. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.ext_ltg.json +164 -0
  72. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.ground_temperatures.json +10663 -0
  73. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.heat_pumps.json +466 -0
  74. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.heat_pumps_heating.json +137 -0
  75. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.heat_rejection.json +44 -0
  76. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.motors.json +238 -0
  77. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.prototype_inputs.json +3094 -0
  78. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.ref_cases.json +829 -0
  79. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.ref_lnup.json +562 -0
  80. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.refrigeration_compressors.json +52 -0
  81. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.refrigeration_condenser.json +220 -0
  82. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.refrigeration_system.json +156 -0
  83. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.refrigeration_walkins.json +1316 -0
  84. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.spc_typ.json +21548 -0
  85. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.unitary_acs.json +554 -0
  86. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.water_heaters.json +68 -0
  87. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.water_source_heat_pumps.json +28 -0
  88. data/data/standards/export/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.water_source_heat_pumps_heating.json +12 -0
  89. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.boilers.json +64 -0
  90. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.chillers.json +871 -0
  91. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.construction_properties.json +12487 -0
  92. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.construction_sets.json +1600 -0
  93. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.economizers.json +592 -0
  94. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.elevators.json +349 -0
  95. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.energy_recovery.json +1096 -0
  96. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.ext_ltg.json +164 -0
  97. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.ground_temperatures.json +10663 -0
  98. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.heat_pumps.json +886 -0
  99. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.heat_pumps_heating.json +194 -0
  100. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.heat_rejection.json +44 -0
  101. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.motors.json +247 -0
  102. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.prototype_inputs.json +3094 -0
  103. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.ref_cases.json +829 -0
  104. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.ref_lnup.json +562 -0
  105. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.refrigeration_compressors.json +52 -0
  106. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.refrigeration_condenser.json +220 -0
  107. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.refrigeration_system.json +156 -0
  108. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.refrigeration_walkins.json +1316 -0
  109. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.spc_typ.json +22079 -0
  110. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.unitary_acs.json +994 -0
  111. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.water_heaters.json +68 -0
  112. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.water_source_heat_pumps.json +28 -0
  113. data/data/standards/export/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.water_source_heat_pumps_heating.json +12 -0
  114. data/data/standards/manage_OpenStudio_Standards.rb +87 -37
  115. data/data/standards/metadata_units_OpenStudio_Standards-ashrae_90_1-ALL-comstockspace_types.csv +236 -0
  116. data/data/standards/metadata_units_OpenStudio_Standards-ashrae_90_1.csv +622 -0
  117. data/data/standards/metadata_units_OpenStudio_Standards-ashrae_90_1space_types.csv +191 -0
  118. data/data/standards/openstudio_standards_duplicates_log.csv +17 -0
  119. data/data/standards/test_performance_expected_dd_results.csv +1971 -1171
  120. data/lib/openstudio-standards.rb +76 -18
  121. data/lib/openstudio-standards/btap/btap.model.rb +1 -1
  122. data/lib/openstudio-standards/btap/economics.rb +14 -11
  123. data/lib/openstudio-standards/btap/envelope.rb +185 -257
  124. data/lib/openstudio-standards/btap/fileio.rb +1 -0
  125. data/lib/openstudio-standards/btap/geometry.rb +21 -1
  126. data/lib/openstudio-standards/btap/measures.rb +12 -11
  127. data/lib/openstudio-standards/btap/schedules.rb +3 -12
  128. data/lib/openstudio-standards/hvac_sizing/Siz.AirLoopHVACUnitaryHeatPumpAirToAirMultiSpeed.rb +178 -0
  129. data/lib/openstudio-standards/hvac_sizing/Siz.CoilCoolingDXMultiSpeed.rb +8 -8
  130. data/lib/openstudio-standards/hvac_sizing/Siz.Model.rb +3 -0
  131. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2004/ashrae_90_1_2004.PumpVariableSpeed.rb +28 -0
  132. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2007/ashrae_90_1_2007.FanVariableVolume.rb +0 -1
  133. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2007/ashrae_90_1_2007.PumpVariableSpeed.rb +28 -0
  134. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2010/ashrae_90_1_2010.Model.rb +53 -2
  135. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2010/ashrae_90_1_2010.PumpVariableSpeed.rb +29 -0
  136. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2013/ashrae_90_1_2013.Model.rb +157 -2
  137. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2013/ashrae_90_1_2013.PumpVariableSpeed.rb +29 -0
  138. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.AirTerminalSingleDuctVAVReheat.rb +24 -0
  139. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.FanConstantVolume.rb +32 -0
  140. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.FanOnOff.rb +33 -0
  141. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.FanVariableVolume.rb +32 -0
  142. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.Model.elevators.rb +25 -0
  143. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.Model.rb +366 -0
  144. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.PumpVariableSpeed.rb +144 -0
  145. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.hvac_systems.rb +11 -0
  146. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.AirTerminalSingleDuctVAVReheat.rb +24 -0
  147. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.FanConstantVolume.rb +32 -0
  148. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.FanOnOff.rb +33 -0
  149. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.FanVariableVolume.rb +32 -0
  150. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.Model.elevators.rb +25 -0
  151. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.Model.rb +367 -0
  152. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.PumpVariableSpeed.rb +144 -0
  153. data/lib/openstudio-standards/prototypes/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.hvac_systems.rb +11 -0
  154. data/lib/openstudio-standards/prototypes/ashrae_90_1/doe_ref_1980_2004/doe_ref_1980_2004.AirTerminalSingleDuctVAVReheat.rb +0 -1
  155. data/lib/openstudio-standards/prototypes/ashrae_90_1/doe_ref_pre_1980/doe_ref_pre_1980.AirTerminalSingleDuctVAVReheat.rb +0 -1
  156. data/lib/openstudio-standards/prototypes/ashrae_90_1/nrel_nze_ready_2017/nrel_zne_ready_2017.HeatExchangerAirToAirSensibleAndLatent.rb +1 -1
  157. data/lib/openstudio-standards/prototypes/ashrae_90_1/nrel_nze_ready_2017/nrel_zne_ready_2017.Model.rb +1 -1
  158. data/lib/openstudio-standards/prototypes/ashrae_90_1/ze_aedg_multifamily/ze_aedg_multifamily.HeatExchangerAirToAirSensibleAndLatent.rb +1 -1
  159. data/lib/openstudio-standards/prototypes/ashrae_90_1/ze_aedg_multifamily/ze_aedg_multifamily.Model.rb +1 -1
  160. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.College.rb +3 -3
  161. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.Courthouse.rb +74 -0
  162. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.FullServiceRestaurant.rb +46 -30
  163. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.HighRiseApartment.rb +23 -8
  164. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.Hospital.rb +26 -15
  165. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.Laboratory.rb +8 -11
  166. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.LargeDataCenterHighITE.rb +54 -60
  167. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.LargeDataCenterLowITE.rb +56 -60
  168. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.LargeHotel.rb +38 -12
  169. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.LargeOffice.rb +218 -134
  170. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.LargeOfficeDetailed.rb +6 -2
  171. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.MediumOffice.rb +230 -134
  172. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.MediumOfficeDetailed.rb +60 -62
  173. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.MidriseApartment.rb +25 -15
  174. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.Outpatient.rb +34 -22
  175. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.PrimarySchool.rb +31 -7
  176. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.QuickServiceRestaurant.rb +43 -28
  177. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.RetailStandalone.rb +48 -38
  178. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.RetailStripmall.rb +9 -5
  179. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.SecondarySchool.rb +575 -345
  180. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.SmallDataCenterHighITE.rb +13 -19
  181. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.SmallDataCenterLowITE.rb +13 -17
  182. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.SmallHotel.rb +9 -5
  183. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.SmallOffice.rb +79 -51
  184. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.SmallOfficeDetailed.rb +60 -60
  185. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.SuperMarket.rb +2 -4
  186. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.SuperTallBuilding.rb +133 -120
  187. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.TallBuilding.rb +124 -112
  188. data/lib/openstudio-standards/prototypes/common/buildings/Prototype.Warehouse.rb +138 -66
  189. data/lib/openstudio-standards/prototypes/common/do_not_edit_metaclasses.rb +7275 -199
  190. data/lib/openstudio-standards/prototypes/common/objects/Prototype.AirConditionerVariableRefrigerantFlow.rb +35 -35
  191. data/lib/openstudio-standards/prototypes/common/objects/Prototype.BoilerHotWater.rb +2 -2
  192. data/lib/openstudio-standards/prototypes/common/objects/Prototype.CentralAirSourceHeatPump.rb +2 -2
  193. data/lib/openstudio-standards/prototypes/common/objects/Prototype.CoilCoolingDXSingleSpeed.rb +3 -3
  194. data/lib/openstudio-standards/prototypes/common/objects/Prototype.CoilCoolingDXTwoSpeed.rb +1 -1
  195. data/lib/openstudio-standards/prototypes/common/objects/Prototype.CoilCoolingWater.rb +2 -2
  196. data/lib/openstudio-standards/prototypes/common/objects/Prototype.CoilCoolingWaterToAirHeatPumpEquationFit.rb +2 -2
  197. data/lib/openstudio-standards/prototypes/common/objects/Prototype.CoilHeatingDXSingleSpeed.rb +1 -1
  198. data/lib/openstudio-standards/prototypes/common/objects/Prototype.CoilHeatingElectric.rb +2 -2
  199. data/lib/openstudio-standards/prototypes/common/objects/Prototype.CoilHeatingWater.rb +2 -2
  200. data/lib/openstudio-standards/prototypes/common/objects/Prototype.CoilHeatingWaterToAirHeatPumpEquationFit.rb +2 -2
  201. data/lib/openstudio-standards/prototypes/common/objects/Prototype.CoolingTower.rb +1 -1
  202. data/lib/openstudio-standards/prototypes/common/objects/Prototype.Fan.rb +4 -3
  203. data/lib/openstudio-standards/prototypes/common/objects/Prototype.FanConstantVolume.rb +7 -8
  204. data/lib/openstudio-standards/prototypes/common/objects/Prototype.FanOnOff.rb +7 -8
  205. data/lib/openstudio-standards/prototypes/common/objects/Prototype.FanVariableVolume.rb +13 -14
  206. data/lib/openstudio-standards/prototypes/common/objects/Prototype.FanZoneExhaust.rb +7 -5
  207. data/lib/openstudio-standards/prototypes/common/objects/Prototype.Model.elevators.rb +4 -1
  208. data/lib/openstudio-standards/prototypes/common/objects/Prototype.Model.exterior_lights.rb +0 -1
  209. data/lib/openstudio-standards/prototypes/common/objects/Prototype.Model.hvac.rb +25 -14
  210. data/lib/openstudio-standards/prototypes/common/objects/Prototype.Model.rb +474 -89
  211. data/lib/openstudio-standards/prototypes/common/objects/Prototype.Model.swh.rb +35 -33
  212. data/lib/openstudio-standards/prototypes/common/objects/Prototype.Pump.rb +3 -0
  213. data/lib/openstudio-standards/prototypes/common/objects/Prototype.PumpVariableSpeed.rb +72 -0
  214. data/lib/openstudio-standards/prototypes/common/objects/Prototype.ServiceWaterHeating.rb +120 -120
  215. data/lib/openstudio-standards/prototypes/common/objects/Prototype.hvac_systems.rb +142 -154
  216. data/lib/openstudio-standards/prototypes/common/objects/Prototype.radiant_system_controls.rb +9 -3
  217. data/lib/openstudio-standards/prototypes/common/objects/Prototype.refrigeration.rb +11 -5
  218. data/lib/openstudio-standards/prototypes/common/objects/Prototype.utilities.rb +26 -14
  219. data/lib/openstudio-standards/prototypes/common/prototype_metaprogramming.rb +270 -247
  220. data/lib/openstudio-standards/prototypes/deer/deer.Model.rb +1 -1
  221. data/lib/openstudio-standards/refs/references.rb +5 -2
  222. data/lib/openstudio-standards/standards/Standards.AirLoopHVAC.rb +70 -51
  223. data/lib/openstudio-standards/standards/Standards.AirTerminalSingleDuctVAVReheat.rb +0 -1
  224. data/lib/openstudio-standards/standards/Standards.BoilerHotWater.rb +0 -1
  225. data/lib/openstudio-standards/standards/Standards.BuildingStory.rb +1 -0
  226. data/lib/openstudio-standards/standards/Standards.ChillerElectricEIR.rb +2 -4
  227. data/lib/openstudio-standards/standards/Standards.CoilCoolingDXMultiSpeed.rb +91 -2
  228. data/lib/openstudio-standards/standards/Standards.CoilCoolingDXSingleSpeed.rb +4 -5
  229. data/lib/openstudio-standards/standards/Standards.CoilCoolingDXTwoSpeed.rb +0 -1
  230. data/lib/openstudio-standards/standards/Standards.CoilCoolingWaterToAirHeatPumpEquationFit.rb +1 -1
  231. data/lib/openstudio-standards/standards/Standards.CoilDX.rb +30 -9
  232. data/lib/openstudio-standards/standards/Standards.CoilHeatingDXMultiSpeed.rb +2 -1
  233. data/lib/openstudio-standards/standards/Standards.CoilHeatingDXSingleSpeed.rb +3 -1
  234. data/lib/openstudio-standards/standards/Standards.CoilHeatingGas.rb +0 -3
  235. data/lib/openstudio-standards/standards/Standards.CoilHeatingGasMultiStage.rb +37 -1
  236. data/lib/openstudio-standards/standards/Standards.CoilHeatingWaterToAirHeatPumpEquationFit.rb +1 -3
  237. data/lib/openstudio-standards/standards/Standards.Construction.rb +124 -118
  238. data/lib/openstudio-standards/standards/Standards.CoolingTower.rb +0 -1
  239. data/lib/openstudio-standards/standards/Standards.CoolingTowerSingleSpeed.rb +0 -1
  240. data/lib/openstudio-standards/standards/Standards.CoolingTowerTwoSpeed.rb +0 -1
  241. data/lib/openstudio-standards/standards/Standards.CoolingTowerVariableSpeed.rb +0 -1
  242. data/lib/openstudio-standards/standards/Standards.Fan.rb +0 -1
  243. data/lib/openstudio-standards/standards/Standards.FanConstantVolume.rb +0 -1
  244. data/lib/openstudio-standards/standards/Standards.FanOnOff.rb +0 -1
  245. data/lib/openstudio-standards/standards/Standards.FanVariableVolume.rb +2 -4
  246. data/lib/openstudio-standards/standards/Standards.FanZoneExhaust.rb +0 -1
  247. data/lib/openstudio-standards/standards/Standards.FluidCooler.rb +10 -3
  248. data/lib/openstudio-standards/standards/Standards.HeaderedPumpsConstantSpeed.rb +0 -1
  249. data/lib/openstudio-standards/standards/Standards.HeaderedPumpsVariableSpeed.rb +0 -1
  250. data/lib/openstudio-standards/standards/Standards.Model.rb +305 -247
  251. data/lib/openstudio-standards/standards/Standards.PlanarSurface.rb +2 -0
  252. data/lib/openstudio-standards/standards/Standards.PlantLoop.rb +11 -9
  253. data/lib/openstudio-standards/standards/Standards.Pump.rb +0 -1
  254. data/lib/openstudio-standards/standards/Standards.PumpConstantSpeed.rb +0 -1
  255. data/lib/openstudio-standards/standards/Standards.PumpVariableSpeed.rb +0 -1
  256. data/lib/openstudio-standards/standards/Standards.ScheduleCompact.rb +0 -1
  257. data/lib/openstudio-standards/standards/Standards.ScheduleConstant.rb +0 -1
  258. data/lib/openstudio-standards/standards/Standards.ScheduleRuleset.rb +103 -121
  259. data/lib/openstudio-standards/standards/Standards.Space.rb +42 -35
  260. data/lib/openstudio-standards/standards/Standards.SpaceType.rb +9 -17
  261. data/lib/openstudio-standards/standards/Standards.SubSurface.rb +25 -27
  262. data/lib/openstudio-standards/standards/Standards.Surface.rb +97 -52
  263. data/lib/openstudio-standards/standards/Standards.ThermalZone.rb +76 -25
  264. data/lib/openstudio-standards/standards/Standards.WaterHeaterMixed.rb +6 -7
  265. data/lib/openstudio-standards/standards/Standards.ZoneHVACComponent.rb +85 -7
  266. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1.Standards.FanVariableVolume.rb +0 -1
  267. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2004/ashrae_90_1_2004.AirLoopHVAC.rb +10 -2
  268. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2004/ashrae_90_1_2004.Model.rb +2 -2
  269. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2004/comstock_ashrae_90_1_2004/data/ashrae_90_1.schedules.json +63 -99
  270. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2004/comstock_ashrae_90_1_2004/data/comstock_ashrae_90_1_2004.ext_ltg.json +7 -7
  271. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.construction_properties.json +2420 -0
  272. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.economizers.json +32 -0
  273. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.heat_rejection.json +9 -0
  274. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.prototype_inputs.json +70 -40
  275. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.spc_typ.json +105 -40
  276. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2004/data/ashrae_90_1_2004.unitary_acs.json +15 -15
  277. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2007/ashrae_90_1_2007.AirLoopHVAC.rb +5 -1
  278. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2007/comstock_ashrae_90_1_2007/data/ashrae_90_1.schedules.json +63 -99
  279. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2007/comstock_ashrae_90_1_2007/data/comstock_ashrae_90_1_2007.ext_ltg.json +7 -7
  280. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.construction_properties.json +1460 -0
  281. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.economizers.json +32 -0
  282. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.heat_rejection.json +9 -0
  283. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.prototype_inputs.json +123 -39
  284. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.spc_typ.json +104 -17
  285. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2007/data/ashrae_90_1_2007.unitary_acs.json +15 -15
  286. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2010/ashrae_90_1_2010.AirLoopHVAC.rb +32 -15
  287. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2010/ashrae_90_1_2010.Space.rb +1 -1
  288. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2010/comstock_ashrae_90_1_2010/data/ashrae_90_1.schedules.json +63 -99
  289. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2010/comstock_ashrae_90_1_2010/data/comstock_ashrae_90_1_2010.ext_ltg.json +7 -7
  290. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.construction_properties.json +1460 -0
  291. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.economizers.json +64 -0
  292. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.energy_recovery.json +52 -0
  293. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.heat_rejection.json +9 -0
  294. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.prototype_inputs.json +123 -39
  295. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.spc_typ.json +112 -25
  296. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2010/data/ashrae_90_1_2010.unitary_acs.json +5 -5
  297. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/ashrae_90_1_2013.AirLoopHVAC.rb +37 -14
  298. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/ashrae_90_1_2013.WaterHeaterMixed.rb +1 -1
  299. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/comstock_ashrae_90_1_2013/data/ashrae_90_1.schedules.json +63 -99
  300. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/comstock_ashrae_90_1_2013/data/comstock_ashrae_90_1_2013.ext_ltg.json +7 -7
  301. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.boilers.json +1 -1
  302. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.chillers.json +2 -2
  303. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.construction_properties.json +1460 -0
  304. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.economizers.json +64 -0
  305. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.energy_recovery.json +104 -0
  306. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.heat_rejection.json +9 -0
  307. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.prototype_inputs.json +125 -41
  308. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.spc_typ.json +172 -55
  309. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.unitary_acs.json +15 -15
  310. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.water_heaters.json +4 -4
  311. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2013/data/ashrae_90_1_2013.water_source_heat_pumps_heating.json +1 -1
  312. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.AirLoopHVAC.rb +456 -0
  313. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.AirTerminalSingleDuctVAVReheat.rb +24 -0
  314. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.CoolingTower.rb +19 -0
  315. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.CoolingTowerSingleSpeed.rb +5 -0
  316. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.CoolingTowerTwoSpeed.rb +5 -0
  317. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.CoolingTowerVariableSpeed.rb +16 -0
  318. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.FanVariableVolume.rb +37 -0
  319. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.Space.rb +189 -0
  320. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.ThermalZone.rb +57 -0
  321. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.ZoneHVACComponent.rb +22 -0
  322. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/ashrae_90_1_2016.rb +16 -0
  323. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.boilers.json +68 -0
  324. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.chillers.json +490 -0
  325. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.construction_properties.json +21244 -0
  326. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.construction_sets.json +2111 -0
  327. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.economizers.json +676 -0
  328. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.elevators.json +372 -0
  329. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.energy_recovery.json +1096 -0
  330. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.ext_ltg.json +169 -0
  331. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.heat_pumps.json +532 -0
  332. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.heat_pumps_heating.json +164 -0
  333. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.heat_rejection.json +49 -0
  334. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.motors.json +274 -0
  335. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.prototype_inputs.json +3094 -0
  336. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.ref_cases.json +854 -0
  337. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.ref_lnup.json +562 -0
  338. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.refrigeration_compressors.json +58 -0
  339. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.refrigeration_condenser.json +238 -0
  340. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.refrigeration_system.json +12 -0
  341. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.refrigeration_walkins.json +1316 -0
  342. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.spc_typ.json +23067 -0
  343. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.unitary_acs.json +648 -0
  344. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.water_heaters.json +72 -0
  345. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.water_source_heat_pumps.json +31 -0
  346. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2016/data/ashrae_90_1_2016.water_source_heat_pumps_heating.json +13 -0
  347. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.AirLoopHVAC.rb +456 -0
  348. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.AirTerminalSingleDuctVAVReheat.rb +24 -0
  349. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.CoolingTower.rb +19 -0
  350. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.CoolingTowerSingleSpeed.rb +5 -0
  351. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.CoolingTowerTwoSpeed.rb +5 -0
  352. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.CoolingTowerVariableSpeed.rb +16 -0
  353. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.FanVariableVolume.rb +37 -0
  354. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.Space.rb +189 -0
  355. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.ThermalZone.rb +57 -0
  356. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.ZoneHVACComponent.rb +22 -0
  357. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/ashrae_90_1_2019.rb +16 -0
  358. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.boilers.json +68 -0
  359. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.chillers.json +490 -0
  360. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.construction_properties.json +21244 -0
  361. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.construction_sets.json +2111 -0
  362. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.economizers.json +676 -0
  363. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.elevators.json +372 -0
  364. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.energy_recovery.json +1096 -0
  365. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.ext_ltg.json +169 -0
  366. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.heat_pumps.json +664 -0
  367. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.heat_pumps_heating.json +204 -0
  368. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.heat_rejection.json +49 -0
  369. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.motors.json +274 -0
  370. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.prototype_inputs.json +3094 -0
  371. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.ref_cases.json +854 -0
  372. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.ref_lnup.json +562 -0
  373. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.refrigeration_compressors.json +58 -0
  374. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.refrigeration_condenser.json +238 -0
  375. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.refrigeration_system.json +12 -0
  376. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.refrigeration_walkins.json +1316 -0
  377. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.spc_typ.json +23067 -0
  378. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.unitary_acs.json +671 -0
  379. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.water_heaters.json +72 -0
  380. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.water_source_heat_pumps.json +31 -0
  381. data/lib/openstudio-standards/standards/ashrae_90_1/ashrae_90_1_2019/data/ashrae_90_1_2019.water_source_heat_pumps_heating.json +13 -0
  382. data/lib/openstudio-standards/standards/ashrae_90_1/data/ashrae_90_1.constructions.json +1662 -332
  383. data/lib/openstudio-standards/standards/ashrae_90_1/data/ashrae_90_1.fans.json +1 -1
  384. data/lib/openstudio-standards/standards/ashrae_90_1/data/ashrae_90_1.materials.json +4994 -234
  385. data/lib/openstudio-standards/standards/ashrae_90_1/data/ashrae_90_1.schedules.json +1743 -161
  386. data/lib/openstudio-standards/standards/ashrae_90_1/doe_ref_1980_2004/comstock_doe_ref_1980_2004/data/ashrae_90_1.schedules.json +63 -99
  387. data/lib/openstudio-standards/standards/ashrae_90_1/doe_ref_1980_2004/comstock_doe_ref_1980_2004/data/comstock_doe_ref_1980_2004.ext_ltg.json +11 -11
  388. data/lib/openstudio-standards/standards/ashrae_90_1/doe_ref_1980_2004/data/doe_ref_1980_2004.heat_rejection.json +9 -0
  389. data/lib/openstudio-standards/standards/ashrae_90_1/doe_ref_1980_2004/data/doe_ref_1980_2004.prototype_inputs.json +8 -8
  390. data/lib/openstudio-standards/standards/ashrae_90_1/doe_ref_1980_2004/data/doe_ref_1980_2004.spc_typ.json +5967 -2727
  391. data/lib/openstudio-standards/standards/ashrae_90_1/doe_ref_1980_2004/doe_ref_1980_2004.Model.rb +4 -4
  392. data/lib/openstudio-standards/standards/ashrae_90_1/doe_ref_pre_1980/comstock_doe_ref_pre_1980/data/ashrae_90_1.schedules.json +63 -99
  393. data/lib/openstudio-standards/standards/ashrae_90_1/doe_ref_pre_1980/comstock_doe_ref_pre_1980/data/comstock_doe_ref_pre_1980.ext_ltg.json +10 -10
  394. data/lib/openstudio-standards/standards/ashrae_90_1/doe_ref_pre_1980/data/doe_ref_pre_1980.heat_rejection.json +9 -0
  395. data/lib/openstudio-standards/standards/ashrae_90_1/doe_ref_pre_1980/data/doe_ref_pre_1980.prototype_inputs.json +7 -7
  396. data/lib/openstudio-standards/standards/ashrae_90_1/doe_ref_pre_1980/data/doe_ref_pre_1980.spc_typ.json +5920 -2700
  397. data/lib/openstudio-standards/standards/ashrae_90_1/doe_ref_pre_1980/doe_ref_pre_1980.Model.rb +4 -4
  398. data/lib/openstudio-standards/standards/ashrae_90_1/nrel_zne_ready_2017/data/nrel_zne_ready_2017.heat_rejection.json +9 -0
  399. data/lib/openstudio-standards/standards/ashrae_90_1/nrel_zne_ready_2017/data/nrel_zne_ready_2017.spc_typ.json +2011 -1112
  400. data/lib/openstudio-standards/standards/ashrae_90_1/nrel_zne_ready_2017/nrel_zne_ready_2017.AirLoopHVAC.rb +0 -1
  401. data/lib/openstudio-standards/standards/ashrae_90_1/nrel_zne_ready_2017/nrel_zne_ready_2017.Model.rb +4 -4
  402. data/lib/openstudio-standards/standards/ashrae_90_1/nrel_zne_ready_2017/nrel_zne_ready_2017.PlantLoop.rb +1 -1
  403. data/lib/openstudio-standards/standards/ashrae_90_1/nrel_zne_ready_2017/nrel_zne_ready_2017.ZoneHVACComponent.rb +1 -1
  404. data/lib/openstudio-standards/standards/ashrae_90_1/ze_aedg_multifamily/data/ze_aedg_multifamily.heat_rejection.json +9 -0
  405. data/lib/openstudio-standards/standards/ashrae_90_1/ze_aedg_multifamily/data/ze_aedg_multifamily.spc_typ.json +1946 -1106
  406. data/lib/openstudio-standards/standards/ashrae_90_1/ze_aedg_multifamily/data/ze_aedg_multifamily.water_heaters.json +2 -2
  407. data/lib/openstudio-standards/standards/ashrae_90_1/ze_aedg_multifamily/ze_aedg_multifamily.AirLoopHVAC.rb +3 -6
  408. data/lib/openstudio-standards/standards/ashrae_90_1/ze_aedg_multifamily/ze_aedg_multifamily.Model.rb +4 -4
  409. data/lib/openstudio-standards/standards/ashrae_90_1/ze_aedg_multifamily/ze_aedg_multifamily.PlantLoop.rb +1 -1
  410. data/lib/openstudio-standards/standards/ashrae_90_1/ze_aedg_multifamily/ze_aedg_multifamily.ZoneHVACComponent.rb +1 -1
  411. data/lib/openstudio-standards/standards/cbes/cbes.Model.rb +1 -3
  412. data/lib/openstudio-standards/standards/cbes/cbes.rb +1 -1
  413. data/lib/openstudio-standards/standards/deer/deer.AirLoopHVAC.rb +8 -13
  414. data/lib/openstudio-standards/standards/deer/deer.Model.rb +2 -2
  415. data/lib/openstudio-standards/standards/deer/deer.PlanarSurface.rb +2 -0
  416. data/lib/openstudio-standards/standards/deer/deer.Space.rb +1 -1
  417. data/lib/openstudio-standards/standards/deer/deer_2011/deer_2011.rb +0 -1
  418. data/lib/openstudio-standards/standards/deer/deer_2014/deer_2014.Space.rb +0 -1
  419. data/lib/openstudio-standards/standards/deer/deer_2014/deer_2014.rb +0 -1
  420. data/lib/openstudio-standards/standards/deer/deer_2015/deer_2015.Space.rb +0 -1
  421. data/lib/openstudio-standards/standards/deer/deer_2017/deer_2017.Space.rb +0 -1
  422. data/lib/openstudio-standards/standards/deer/deer_2020/deer_2020.AirLoopHVAC.rb +1 -1
  423. data/lib/openstudio-standards/standards/deer/deer_2020/deer_2020.FanVariableVolume.rb +1 -1
  424. data/lib/openstudio-standards/standards/deer/deer_2020/deer_2020.Space.rb +0 -1
  425. data/lib/openstudio-standards/standards/deer/deer_2025/deer_2025.AirLoopHVAC.rb +1 -1
  426. data/lib/openstudio-standards/standards/deer/deer_2025/deer_2025.FanVariableVolume.rb +1 -1
  427. data/lib/openstudio-standards/standards/deer/deer_2025/deer_2025.Space.rb +0 -1
  428. data/lib/openstudio-standards/standards/deer/deer_2030/deer_2030.AirLoopHVAC.rb +1 -1
  429. data/lib/openstudio-standards/standards/deer/deer_2030/deer_2030.FanVariableVolume.rb +1 -1
  430. data/lib/openstudio-standards/standards/deer/deer_2030/deer_2030.Space.rb +0 -1
  431. data/lib/openstudio-standards/standards/deer/deer_2035/deer_2035.AirLoopHVAC.rb +1 -1
  432. data/lib/openstudio-standards/standards/deer/deer_2035/deer_2035.FanVariableVolume.rb +1 -1
  433. data/lib/openstudio-standards/standards/deer/deer_2035/deer_2035.Space.rb +0 -1
  434. data/lib/openstudio-standards/standards/deer/deer_2040/deer_2040.AirLoopHVAC.rb +1 -1
  435. data/lib/openstudio-standards/standards/deer/deer_2040/deer_2040.FanVariableVolume.rb +1 -1
  436. data/lib/openstudio-standards/standards/deer/deer_2040/deer_2040.Space.rb +0 -1
  437. data/lib/openstudio-standards/standards/deer/deer_2045/deer_2045.AirLoopHVAC.rb +1 -1
  438. data/lib/openstudio-standards/standards/deer/deer_2045/deer_2045.FanVariableVolume.rb +1 -1
  439. data/lib/openstudio-standards/standards/deer/deer_2045/deer_2045.Space.rb +0 -1
  440. data/lib/openstudio-standards/standards/deer/deer_2050/deer_2050.AirLoopHVAC.rb +1 -1
  441. data/lib/openstudio-standards/standards/deer/deer_2050/deer_2050.FanVariableVolume.rb +1 -1
  442. data/lib/openstudio-standards/standards/deer/deer_2050/deer_2050.Space.rb +0 -1
  443. data/lib/openstudio-standards/standards/deer/deer_2055/deer_2055.AirLoopHVAC.rb +1 -1
  444. data/lib/openstudio-standards/standards/deer/deer_2055/deer_2055.FanVariableVolume.rb +1 -1
  445. data/lib/openstudio-standards/standards/deer/deer_2055/deer_2055.Space.rb +0 -1
  446. data/lib/openstudio-standards/standards/deer/deer_2060/deer_2060.AirLoopHVAC.rb +1 -1
  447. data/lib/openstudio-standards/standards/deer/deer_2060/deer_2060.FanVariableVolume.rb +1 -1
  448. data/lib/openstudio-standards/standards/deer/deer_2060/deer_2060.Space.rb +0 -1
  449. data/lib/openstudio-standards/standards/deer/deer_2065/deer_2065.AirLoopHVAC.rb +1 -1
  450. data/lib/openstudio-standards/standards/deer/deer_2065/deer_2065.FanVariableVolume.rb +1 -1
  451. data/lib/openstudio-standards/standards/deer/deer_2065/deer_2065.Space.rb +0 -1
  452. data/lib/openstudio-standards/standards/deer/deer_2070/deer_2070.AirLoopHVAC.rb +1 -1
  453. data/lib/openstudio-standards/standards/deer/deer_2070/deer_2070.FanVariableVolume.rb +1 -1
  454. data/lib/openstudio-standards/standards/deer/deer_2070/deer_2070.Space.rb +0 -1
  455. data/lib/openstudio-standards/standards/deer/deer_2075/deer_2075.AirLoopHVAC.rb +1 -1
  456. data/lib/openstudio-standards/standards/deer/deer_2075/deer_2075.FanVariableVolume.rb +1 -1
  457. data/lib/openstudio-standards/standards/deer/deer_2075/deer_2075.Space.rb +0 -1
  458. data/lib/openstudio-standards/standards/icc_iecc/icc_iecc_2015/icc_iecc_2015.rb +0 -1
  459. data/lib/openstudio-standards/standards/necb/BTAP1980TO2010/btap_1980to2010.rb +2 -18
  460. data/lib/openstudio-standards/standards/necb/BTAP1980TO2010/data/space_types.json +1677 -1005
  461. data/lib/openstudio-standards/standards/necb/BTAPPRE1980/btap_pre1980.rb +87 -15
  462. data/lib/openstudio-standards/standards/necb/BTAPPRE1980/building_envelope.rb +31 -19
  463. data/lib/openstudio-standards/standards/necb/BTAPPRE1980/data/curves.json +75 -0
  464. data/lib/openstudio-standards/standards/necb/BTAPPRE1980/data/heat_pumps.json +16 -16
  465. data/lib/openstudio-standards/standards/necb/BTAPPRE1980/data/space_types.json +1677 -1005
  466. data/lib/openstudio-standards/standards/necb/BTAPPRE1980/hvac_system_3_and_8_single_speed.rb +16 -2
  467. data/lib/openstudio-standards/standards/necb/BTAPPRE1980/hvac_system_4.rb +15 -0
  468. data/lib/openstudio-standards/standards/necb/BTAPPRE1980/hvac_system_6.rb +14 -0
  469. data/lib/openstudio-standards/standards/necb/ECMS/data/boiler_set.json +29 -0
  470. data/lib/openstudio-standards/standards/necb/ECMS/data/curves.json +913 -0
  471. data/lib/openstudio-standards/standards/necb/ECMS/data/equip_eff_lim.json +52 -0
  472. data/lib/openstudio-standards/standards/necb/ECMS/data/erv.json +109 -0
  473. data/lib/openstudio-standards/standards/necb/ECMS/data/furnace_set.json +23 -0
  474. data/lib/openstudio-standards/standards/necb/ECMS/data/heat_pumps.json +803 -0
  475. data/lib/openstudio-standards/standards/necb/ECMS/data/heat_pumps_heating.json +787 -0
  476. data/lib/openstudio-standards/standards/necb/ECMS/data/pv.json +112 -0
  477. data/lib/openstudio-standards/standards/necb/ECMS/data/shw_set.json +29 -0
  478. data/lib/openstudio-standards/standards/necb/ECMS/data/unitary_acs.json +50 -0
  479. data/lib/openstudio-standards/standards/necb/ECMS/ecms.rb +100 -0
  480. data/lib/openstudio-standards/standards/necb/ECMS/erv.rb +33 -0
  481. data/lib/openstudio-standards/standards/necb/ECMS/hvac_systems.rb +1729 -0
  482. data/lib/openstudio-standards/standards/necb/ECMS/nv.rb +189 -0
  483. data/lib/openstudio-standards/standards/necb/ECMS/pv_ground.rb +104 -0
  484. data/lib/openstudio-standards/standards/necb/NECB2011/autozone.rb +68 -33
  485. data/lib/openstudio-standards/standards/necb/NECB2011/beps_compliance_path.rb +24 -13
  486. data/lib/openstudio-standards/standards/necb/NECB2011/building_envelope.rb +110 -99
  487. data/lib/openstudio-standards/standards/necb/NECB2011/data/constants.json +24 -24
  488. data/lib/openstudio-standards/standards/necb/NECB2011/data/curves.json +50 -0
  489. data/lib/openstudio-standards/standards/necb/NECB2011/data/erv.json +31 -0
  490. data/lib/openstudio-standards/standards/necb/NECB2011/data/geometry/LowriseApartment.osm +39278 -0
  491. data/lib/openstudio-standards/standards/necb/NECB2011/data/led_lighting_data.json +2028 -0
  492. data/lib/openstudio-standards/standards/necb/NECB2011/data/space_types.json +1745 -1297
  493. data/lib/openstudio-standards/standards/necb/NECB2011/daylighting_control.md +70 -0
  494. data/lib/openstudio-standards/standards/necb/NECB2011/demand_controlled_ventilation.md +46 -0
  495. data/lib/openstudio-standards/standards/necb/NECB2011/hvac_system_1_multi_speed.rb +69 -107
  496. data/lib/openstudio-standards/standards/necb/NECB2011/hvac_system_1_single_speed.rb +41 -2
  497. data/lib/openstudio-standards/standards/necb/NECB2011/hvac_system_2_and_5.rb +15 -0
  498. data/lib/openstudio-standards/standards/necb/NECB2011/hvac_system_3_and_8_multi_speed.rb +139 -141
  499. data/lib/openstudio-standards/standards/necb/NECB2011/hvac_system_3_and_8_single_speed.rb +38 -2
  500. data/lib/openstudio-standards/standards/necb/NECB2011/hvac_system_4.rb +13 -0
  501. data/lib/openstudio-standards/standards/necb/NECB2011/hvac_system_6.rb +12 -0
  502. data/lib/openstudio-standards/standards/necb/NECB2011/hvac_systems.rb +492 -240
  503. data/lib/openstudio-standards/standards/necb/NECB2011/led_lighting.md +51 -0
  504. data/lib/openstudio-standards/standards/necb/NECB2011/lighting.rb +75 -9
  505. data/lib/openstudio-standards/standards/necb/NECB2011/necb_2011.rb +1229 -37
  506. data/lib/openstudio-standards/standards/necb/NECB2011/nv.md +74 -0
  507. data/lib/openstudio-standards/standards/necb/NECB2011/pv_ground.md +44 -0
  508. data/lib/openstudio-standards/standards/necb/NECB2011/qaqc/necb_qaqc.rb +11 -3
  509. data/lib/openstudio-standards/standards/necb/NECB2011/qaqc/qaqc_resources/neb_end_use_prices.csv +39 -84
  510. data/lib/openstudio-standards/standards/necb/NECB2011/service_water_heating.rb +1 -1
  511. data/lib/openstudio-standards/standards/necb/NECB2015/data/led_lighting_data.json +2883 -0
  512. data/lib/openstudio-standards/standards/necb/NECB2015/data/space_types.json +2554 -1916
  513. data/lib/openstudio-standards/standards/necb/NECB2015/necb_2015.rb +32 -1
  514. data/lib/openstudio-standards/standards/necb/NECB2017/data/led_lighting_data.json +2883 -0
  515. data/lib/openstudio-standards/standards/necb/NECB2017/data/space_types.json +2554 -1916
  516. data/lib/openstudio-standards/standards/necb/NECB2017/necb_2017.rb +29 -0
  517. data/lib/openstudio-standards/standards/oeesc/oeesc_2014/oeesc_2014.rb +0 -1
  518. data/lib/openstudio-standards/standards/standard.rb +6 -5
  519. data/lib/openstudio-standards/utilities/Add_template_field_to_json.rb +3 -3
  520. data/lib/openstudio-standards/utilities/convert_surfaces_to_adiabatic_necb_8426.rb +54 -54
  521. data/lib/openstudio-standards/utilities/generate_prototype_database.rb +2 -2
  522. data/lib/openstudio-standards/utilities/generate_space_types.rb +3 -3
  523. data/lib/openstudio-standards/utilities/logging.rb +7 -7
  524. data/lib/openstudio-standards/utilities/necb_to_epw_map.rb +14 -14
  525. data/lib/openstudio-standards/utilities/os_sim_extract.rb +25 -25
  526. data/lib/openstudio-standards/utilities/rename_surfaces.rb +10 -13
  527. data/lib/openstudio-standards/utilities/round_surf_coords.rb +18 -20
  528. data/lib/openstudio-standards/utilities/sched_create.rb +39 -41
  529. data/lib/openstudio-standards/utilities/set_mult_to_adiabatic.rb +31 -31
  530. data/lib/openstudio-standards/utilities/simulation.rb +13 -21
  531. data/lib/openstudio-standards/utilities/speacetype_map_converter.rb +10 -11
  532. data/lib/openstudio-standards/utilities/sqlfile.rb +6 -8
  533. data/lib/openstudio-standards/utilities/template_measure/measure.rb +108 -0
  534. data/lib/openstudio-standards/utilities/template_measure/measure.xml +162 -0
  535. data/lib/openstudio-standards/utilities/template_measure/resources/BTAPMeasureHelper.rb +448 -0
  536. data/lib/openstudio-standards/utilities/template_measure/tests/test.rb +160 -0
  537. data/lib/openstudio-standards/utilities/weatherData1_xlsx_to_json.rb +23 -26
  538. data/lib/openstudio-standards/version.rb +1 -1
  539. data/lib/openstudio-standards/weather/Weather.Model.rb +112 -87
  540. data/lib/openstudio-standards/weather/Weather.stat_file.rb +17 -17
  541. metadata +236 -2
@@ -0,0 +1,112 @@
1
+ {
2
+ "tables": {
3
+ "pv": {
4
+ "data_type": "table",
5
+ "refs": [
6
+ "assumption"
7
+ ],
8
+ "table": [
9
+ {
10
+ "pv_module_description": "Solarland 12V SLP100-12U 26.57 x 41.81 x 1.18",
11
+ "pv_module_type": "Standard",
12
+ "pv_module_wattage": 100
13
+ },
14
+ {
15
+ "pv_module_description": "Solarland 12V SLP120-12U 26.57 x 48.98 x 1.38",
16
+ "pv_module_type": "Standard",
17
+ "pv_module_wattage": 120
18
+ },
19
+ {
20
+ "pv_module_description": "Astronergy CHSM6612M Silver Mono PERC 38.98 x 76.93 x 1.57 ",
21
+ "pv_module_type": "Standard",
22
+ "pv_module_wattage": 365
23
+ },
24
+ {
25
+ "pv_module_description": "Canadian Solar MC4 CS3k-320MS Black Mon PERC 39.1 x 65.9 x 1.38",
26
+ "pv_module_type": "Standard",
27
+ "pv_module_wattage": 320
28
+ },
29
+ {
30
+ "pv_module_description": "Mission Solar Black Mon PERC 39.33 x 65.53 x 1.58",
31
+ "pv_module_type": "Standard",
32
+ "pv_module_wattage": 310
33
+ },
34
+ {
35
+ "pv_module_description": "Canadian Solar CS3k-325MS Black Mon PERC 39.1 x 65.9 x 1.38",
36
+ "pv_module_type": "Standard",
37
+ "pv_module_wattage": 325
38
+ },
39
+ {
40
+ "pv_module_description": "Canadian Solar 72 Cell Maxpower 325 38.7 x 76.9 x 1.57",
41
+ "pv_module_type": "Standard",
42
+ "pv_module_wattage": 325
43
+ },
44
+ {
45
+ "pv_module_description": "Hanwha 72 Cell Quantum HSQ-340-72P 39.7 x 78.5 x 1.38",
46
+ "pv_module_type": "Standard",
47
+ "pv_module_wattage": 340
48
+ },
49
+ {
50
+ "pv_module_description": "Hanwha SF220-30-P225 37 x 65.04 x 1.97",
51
+ "pv_module_type": "Standard",
52
+ "pv_module_wattage": 220
53
+ },
54
+ {
55
+ "pv_module_description": "HES-160-36PV 26.6 x 58.3 x 1.38",
56
+ "pv_module_type": "Standard",
57
+ "pv_module_wattage": 160
58
+ },
59
+ {
60
+ "pv_module_description": "HES-265-60PV 39 x 64.6 x 1.36",
61
+ "pv_module_type": "Standard",
62
+ "pv_module_wattage": 265
63
+ },
64
+ {
65
+ "pv_module_description": "Solarland 12V SLP175S-12 26.57 x 59.06 x 1.38",
66
+ "pv_module_type": "Premium",
67
+ "pv_module_wattage": 175
68
+ },
69
+ {
70
+ "pv_module_description": "Heliene Black 60 cell 39.4 x 65.5 x 1.6 ",
71
+ "pv_module_type": "Premium",
72
+ "pv_module_wattage": 320
73
+ },
74
+ {
75
+ "pv_module_description": "Panasonic Black Frame HIT 60 cell 41.5 x 62.5 x 1.6 ",
76
+ "pv_module_type": "Premium",
77
+ "pv_module_wattage": 325
78
+ },
79
+ {
80
+ "pv_module_description": "LG NeON2 LG-335N1K-V5 Black/Black 40 x 66.4 x 1.57 ",
81
+ "pv_module_type": "Premium",
82
+ "pv_module_wattage": 335
83
+ },
84
+ {
85
+ "pv_module_description": "Hanwha Mono 39.4 x 65.7 x 1.26",
86
+ "pv_module_type": "Premium",
87
+ "pv_module_wattage": 310
88
+ },
89
+ {
90
+ "pv_module_description": "Heliene 36HD 26.6 x 58.6 x 1.6",
91
+ "pv_module_type": "Premium",
92
+ "pv_module_wattage": 160
93
+ },
94
+ {
95
+ "pv_module_description": "Global Solar Energy PowerFlex+ flexible thin film (CIGS) for awnings, BIPV 19.4 x 81.4 x 0.12",
96
+ "pv_module_type": "ThinFilm",
97
+ "pv_module_wattage": 100
98
+ },
99
+ {
100
+ "pv_module_description": "Powerfilm, Soltronic Semi-Flex with Sunpower cells, 21 x 44.5 x 0.08",
101
+ "pv_module_type": "ThinFilm",
102
+ "pv_module_wattage": 100
103
+ },
104
+ {
105
+ "pv_module_description": "Go Power, GP-Flex - 100E, Flexible with Sunpower cells, 21.3 x 41.7 x 0.1",
106
+ "pv_module_type": "ThinFilm",
107
+ "pv_module_wattage": 100
108
+ }
109
+ ]
110
+ }
111
+ }
112
+ }
@@ -0,0 +1,29 @@
1
+ {
2
+ "tables": {
3
+ "shw_eff_ecm": {
4
+ "refs": [
5
+ "assumption"
6
+ ],
7
+ "table": [
8
+ {
9
+ "name": "NECB_Default",
10
+ "efficiency": null,
11
+ "part_load_curve": null,
12
+ "notes": "Do nothing."
13
+ },
14
+ {
15
+ "name": "Natural Gas Power Vent with Electric Ignition",
16
+ "efficiency": 0.94,
17
+ "part_load_curve": "SWH-EFFFPLR-NECB2011",
18
+ "notes": "From AHRI."
19
+ },
20
+ {
21
+ "name": "Natural Gas Direct Vent with Electric Ignition",
22
+ "efficiency": 0.91,
23
+ "part_load_curve": "SWH-EFFFPLR-NECB2011",
24
+ "notes": "From AHRI."
25
+ }
26
+ ]
27
+ }
28
+ }
29
+ }
@@ -0,0 +1,50 @@
1
+ {
2
+ "tables": {
3
+ "unitary_cop_ecm": {
4
+ "refs": [
5
+ "assumption"
6
+ ],
7
+ "table": [
8
+ {
9
+ "name": "Carrier WeatherExpert",
10
+ "minimum_capacity": 0.0,
11
+ "maximum_capacity": 19044.8,
12
+ "minimum_energy_efficiency_ratio": null,
13
+ "minimum_seasonal_energy_efficiency_ratio": 17.3,
14
+ "cool_cap_ft": null,
15
+ "cool_cap_fflow": null,
16
+ "cool_eir_ft": null,
17
+ "cool_eir_fflow": null,
18
+ "cool_plf_fplr": null,
19
+ "notes": "Carrier WeatherExpert 3-5 Nominal Tons average"
20
+ },
21
+ {
22
+ "name": "Carrier WeatherExpert",
23
+ "minimum_capacity": 19044.8,
24
+ "maximum_capacity": 77960.0,
25
+ "minimum_energy_efficiency_ratio": 13.1,
26
+ "minimum_seasonal_energy_efficiency_ratio": null,
27
+ "cool_cap_ft": null,
28
+ "cool_cap_fflow": null,
29
+ "cool_eir_ft": null,
30
+ "cool_eir_fflow": null,
31
+ "cool_plf_fplr": null,
32
+ "notes": "Carrier WeatherExpert 6-10 Nominal Tons average"
33
+ },
34
+ {
35
+ "name": "Carrier WeatherExpert",
36
+ "minimum_capacity": 77960.0,
37
+ "maximum_capacity": 9999999.0,
38
+ "minimum_energy_efficiency_ratio": 12.0,
39
+ "minimum_seasonal_energy_efficiency_ratio": null,
40
+ "cool_cap_ft": null,
41
+ "cool_cap_fflow": null,
42
+ "cool_eir_ft": null,
43
+ "cool_eir_fflow": null,
44
+ "cool_plf_fplr": null,
45
+ "notes": "Carrier WeatherExpert 12.5-23 Tons average"
46
+ }
47
+ ]
48
+ }
49
+ }
50
+ }
@@ -0,0 +1,100 @@
1
+ class ECMS < NECB2011
2
+
3
+ @template = self.new.class.name
4
+ register_standard(@template)
5
+
6
+ # Combine the data from the JSON files into a single hash
7
+ # Load JSON files differently depending on whether loading from
8
+ # the OpenStudio CLI embedded filesystem or from typical gem installation
9
+ def load_standards_database_new()
10
+ @standards_data = {}
11
+ @standards_data["tables"] = {}
12
+
13
+ if __dir__[0] == ':' # Running from OpenStudio CLI
14
+ embedded_files_relative('data/', /.*\.json/).each do |file|
15
+ data = JSON.parse(EmbeddedScripting.getFileAsString(file))
16
+ if not data["tables"].nil? and data["tables"].first["data_type"] == "table"
17
+ @standards_data["tables"] << data["tables"].first
18
+ else
19
+ @standards_data[data.keys.first] = data[data.keys.first]
20
+ end
21
+ end
22
+ else
23
+ files = Dir.glob("#{File.dirname(__FILE__)}/data/*.json").select { |e| File.file? e }
24
+ files.each do |file|
25
+ data = JSON.parse(File.read(file))
26
+ if not data["tables"].nil?
27
+ @standards_data["tables"] = [*@standards_data["tables"], *data["tables"]].to_h
28
+ else
29
+ @standards_data[data.keys.first] = data[data.keys.first]
30
+ end
31
+ end
32
+ end
33
+
34
+ return @standards_data
35
+ end
36
+
37
+ def initialize
38
+ super()
39
+ @template = self.class.name
40
+ @standards_data = self.load_standards_database_new()
41
+ @standards_data['curves'] = standards_data['tables']["curves"]['table']
42
+ end
43
+
44
+ def apply_system_ecm(model:, ecm_system_name: nil, template_standard:, runner: nil, primary_heating_fuel: nil)
45
+ # Do nothing if nil or other usual suspects.. covering all bases for now.
46
+ return if ecm_system_name.nil? || ecm_system_name == 'none' || ecm_system_name == 'NECB_Default'
47
+
48
+ ecm_std = Standard.build("ECMS")
49
+ systems = model.getAirLoopHVACs
50
+ map_system_to_zones, system_doas_flags = ecm_std.get_map_systems_to_zones(systems)
51
+ zone_clg_eqpt_type = ecm_std.get_zone_clg_eqpt_type(model)
52
+ # when the ecm is associated with adding a new HVAC system, then remove existing system components and loops
53
+ ecm_add_method_name = "add_ecm_#{ecm_system_name.downcase}"
54
+
55
+ raise("the method #{ecm_add_method_name} does not exist in the ECM class. Please verify that this should be called.") unless ecm_std.respond_to? ecm_add_method_name
56
+
57
+ ecm_std.remove_all_zone_eqpt(systems)
58
+ ecm_std.remove_air_loops(model)
59
+ ecm_std.remove_hw_loops(model)
60
+ ecm_std.remove_chw_loops(model)
61
+ ecm_std.remove_cw_loops(model)
62
+
63
+ # Rather than go through every add_ecm class to add 'the primary_heating_fuel' argument I added this statement to
64
+ # only include it when it is used (for now in the add_ecm_remove_airloops_add_zone_baseboards method).
65
+ unless (ecm_add_method_name == "add_ecm_remove_airloops_add_zone_baseboards")
66
+ ecm_std.send(ecm_add_method_name,
67
+ model: model,
68
+ system_zones_map: map_system_to_zones,
69
+ system_doas_flags: system_doas_flags,
70
+ zone_clg_eqpt_type: zone_clg_eqpt_type,
71
+ standard: template_standard)
72
+ else
73
+ ecm_std.send(ecm_add_method_name,
74
+ model: model,
75
+ system_zones_map: map_system_to_zones,
76
+ system_doas_flags: system_doas_flags,
77
+ zone_clg_eqpt_type: zone_clg_eqpt_type,
78
+ standard: template_standard,
79
+ primary_heating_fuel: primary_heating_fuel)
80
+ end
81
+ #ecm_std.add_ecm_hs09_ccashpsys(model:model,system_zones_map:,system_doas_flags:,zone_clg_eqpt_type: nil,standard:,baseboard_flag: true)
82
+
83
+ end
84
+
85
+ def apply_system_efficiencies_ecm(model:, ecm_system_name: nil)
86
+ # Do nothing if nil.
87
+ return if ecm_system_name.nil? || ecm_system_name == 'none' || ecm_system_name == 'NECB_Default' || ecm_system_name.to_s.downcase == 'remove_airloops_add_zone_baseboards'
88
+ ecm_std = Standard.build("ECMS")
89
+ # Get method name that should be present in the ECM class.
90
+ ecm_apply_eff_method_name = "apply_efficiency_ecm_#{ecm_system_name.downcase}"
91
+ # Raise exception if method does not exists.
92
+ raise("the method #{ecm_apply_eff_method_name} does not exist in the ECM class. Please verify that this should be called.") unless ecm_std.respond_to?(ecm_apply_eff_method_name)
93
+
94
+ # apply system eff method.
95
+ ecm_std.send(ecm_apply_eff_method_name, model: model, ecm_name: ecm_system_name)
96
+ end
97
+
98
+
99
+
100
+ end
@@ -0,0 +1,33 @@
1
+ class ECMS
2
+ # This method will add a skeleton erv to all air loops if requested.
3
+ def apply_erv_ecm(model:, erv_package: nil)
4
+ # If erv is nil.. do nothing.
5
+ return if erv_package.nil? || erv_package == 'none' || erv_package == 'NECB_Default'
6
+ erv_info = @standards_data['tables']['erv']['table'].detect { |item| item['erv_name'] == erv_package }
7
+ # Check if we were able to get data.
8
+ if erv_info.nil?
9
+ # Get name of ERVs in erv.json.
10
+ valid = @standards_data['tables']['erv']['table'].map{|x| x['erv_name']}
11
+ #tell user.
12
+ raise("ERV package name #{erv_package} does not exist. must be #{valid} /n Stopping.")
13
+ end
14
+ if erv_info['application'] == "Add_ERVs_To_All_Airloops"
15
+ #remove all existing ERVs
16
+ model.getHeatExchangerAirToAirSensibleAndLatents.each { |erv| erv.remove}
17
+ #add ervs
18
+ model.getAirLoopHVACs.each do |air_loop|
19
+ # Adds default erv to all air_loops. This will be changed in the set efficiency methods.
20
+ air_loop_hvac_apply_energy_recovery_ventilator(air_loop, nil)
21
+ end
22
+ end
23
+ end
24
+
25
+ # This method will set the properties of the ERV that was added above. Must be run after the standard efficiency is complete as this will overwrite
26
+ # those values. See data/erv.json to view/add different erv packages.
27
+ def apply_erv_ecm_efficiency(model:, erv_package: nil)
28
+ # If erv is nil.. do nothing.
29
+ return if erv_package.nil? || erv_package == 'none' || erv_package == 'NECB_Default'
30
+ # This calls the NECB2011 implementation of the method.
31
+ model.getHeatExchangerAirToAirSensibleAndLatents.each { |erv| heat_exchanger_air_to_air_sensible_and_latent_apply_efficiency(erv, erv_package) }
32
+ end
33
+ end
@@ -0,0 +1,1729 @@
1
+ class ECMS
2
+
3
+ # =============================================================================================================================
4
+ # Remove existing zone equipment
5
+ def remove_all_zone_eqpt(sys_objs)
6
+ sys_objs.each do |isys|
7
+ isys.thermalZones.each do |izone|
8
+ if(izone.equipment.empty?) then next end
9
+ izone.equipment.each {|icomp| icomp.remove}
10
+ end
11
+ end
12
+ end
13
+
14
+ # =============================================================================================================================
15
+ # Remove hot-water plant loops
16
+ def remove_hw_loops(model)
17
+ model.getPlantLoops.each do |iloop|
18
+ hw_loop = false
19
+ iloop.supplyComponents.each do |icomp|
20
+ if(icomp.to_BoilerHotWater.is_initialized)
21
+ hw_loop = true
22
+ break
23
+ end
24
+ end
25
+ if hw_loop then iloop.remove end
26
+ end
27
+ end
28
+
29
+ # =============================================================================================================================
30
+ # Remove chilled-water plant loops
31
+ def remove_chw_loops(model)
32
+ model.getPlantLoops.each do |iloop|
33
+ chw_loop = false
34
+ iloop.supplyComponents.each do |icomp|
35
+ if(icomp.to_ChillerElectricEIR.is_initialized)
36
+ chw_loop = true
37
+ break
38
+ end
39
+ end
40
+ if chw_loop then iloop.remove end
41
+ end
42
+ end
43
+
44
+ # =============================================================================================================================
45
+ # Remove condenser-water plant loops
46
+ def remove_cw_loops(model)
47
+ model.getPlantLoops.each do |iloop|
48
+ cw_loop = false
49
+ iloop.supplyComponents.each do |icomp|
50
+ if(icomp.to_CoolingTowerSingleSpeed.is_initialized)
51
+ cw_loop = true
52
+ end
53
+ end
54
+ if cw_loop then iloop.remove end
55
+ end
56
+ end
57
+
58
+ # =============================================================================================================================
59
+ # Remove air loops
60
+ def remove_air_loops(model)
61
+ # remove air loops
62
+ model.getAirLoopHVACs.each do |iloop|
63
+ iloop.remove
64
+ end
65
+ end
66
+
67
+ # =============================================================================================================================
68
+ # Return map of systems to zones and set flag for dedicated outdoor air unit for each system
69
+ def get_map_systems_to_zones(systems)
70
+ map_systems_to_zones = {}
71
+ system_doas_flags = {}
72
+ systems.each do |system|
73
+ zones = system.thermalZones
74
+ map_systems_to_zones[system.name.to_s] = zones
75
+ if system.sizingSystem.typeofLoadtoSizeOn.to_s == "VentilationRequirement"
76
+ system_doas_flags[system.name.to_s] = true
77
+ else
78
+ system_doas_flags[system.name.to_s] = false
79
+ end
80
+ end
81
+ return map_systems_to_zones,system_doas_flags
82
+ end
83
+
84
+ # =============================================================================================================================
85
+ # Return hash of zone and cooling equipment type in the zone
86
+ def get_zone_clg_eqpt_type(model)
87
+ zone_clg_eqpt_type = {}
88
+ model.getThermalZones.each do |zone|
89
+ zone.equipment.each do |eqpt|
90
+ if eqpt.to_ZoneHVACPackagedTerminalAirConditioner.is_initialized
91
+ zone_clg_eqpt_type[zone.name.to_s] = "ZoneHVACPackagedTerminalAirConditioner"
92
+ break
93
+ end
94
+ end
95
+ end
96
+ return zone_clg_eqpt_type
97
+ end
98
+
99
+ # =============================================================================================================================
100
+ # Return hash of flags for whether storey is conditioned and average ceiling z-coordinates of building storeys.
101
+ def get_storey_avg_clg_zcoords(model)
102
+ storey_avg_clg_zcoords = {}
103
+ model.getBuildingStorys.each do |storey|
104
+ storey_avg_clg_zcoords[storey] = []
105
+ storey_cond = false
106
+ total_area = 0.0
107
+ sum = 0.0
108
+ storey.spaces.each do |space|
109
+ # Determine if any of the spaces/zones of the storey are conditioned? If yes then the floor is considered to be conditioned
110
+ if space.thermalZone.is_initialized
111
+ zone = space.thermalZone.get
112
+ if zone.thermostat.is_initialized
113
+ if zone.thermostat.get.to_ThermostatSetpointDualSetpoint.is_initialized
114
+ if zone.thermostat.get.to_ThermostatSetpointDualSetpoint.get.heatingSetpointTemperatureSchedule.is_initialized ||
115
+ zone.thermostat.get.to_ThermostatSetpointDualSetpoint.get.coolingSetpointTemperatureSchedule.is_initialized
116
+ storey_cond = true
117
+ end
118
+ end
119
+ end
120
+ end
121
+ # Find average height of z-coordinates of ceiling/roof of floor
122
+ space.surfaces.each do |surf|
123
+ if (surf.surfaceType.to_s.upcase == "ROOFCEILING")
124
+ sum += (surf.centroid.z.to_f + space.zOrigin.to_f) * surf.grossArea.to_f
125
+ total_area += surf.grossArea.to_f
126
+ end
127
+ end
128
+ end
129
+ storey_avg_clg_zcoords[storey] << storey_cond
130
+ storey_avg_clg_zcoords[storey] << (sum / total_area)
131
+ end
132
+
133
+ return storey_avg_clg_zcoords
134
+ end
135
+
136
+ # =============================================================================================================================
137
+ # Return x,y,z coordinates of exterior wall with largest area on the lowest floor
138
+ def get_lowest_floor_ext_wall_centroid_coords(storeys_clg_zcoords)
139
+ ext_wall,ext_wall_x,ext_wall_y,ext_wall_z = nil,nil,nil,nil
140
+ storeys_clg_zcoords.keys.each do |storey|
141
+ max_area = 0.0
142
+ sorted_spaces = storey.spaces.sort_by {|space| space.name.to_s}
143
+ sorted_spaces.each do |space|
144
+ ext_walls = space.surfaces.select {|surf| (surf.surfaceType.to_s.upcase == "WALL") && (surf.outsideBoundaryCondition.to_s.upcase == "OUTDOORS")}
145
+ ext_walls = ext_walls.sort_by {|wall| wall.grossArea.to_f}
146
+ if not ext_walls.empty?
147
+ if ext_walls.last.grossArea.to_f > max_area
148
+ max_area = ext_walls.last.grossArea.to_f
149
+ ext_wall_x = ext_walls.last.centroid.x.to_f + space.xOrigin.to_f
150
+ ext_wall_y = ext_walls.last.centroid.y.to_f + space.yOrigin.to_f
151
+ ext_wall_z = ext_walls.last.centroid.z.to_f + space.zOrigin.to_f
152
+ ext_wall = ext_walls.last
153
+ end
154
+ end
155
+ end
156
+ break unless not ext_wall
157
+ end
158
+ if not ext_wall
159
+ OpenStudio.logFree(OpenStudio::Info, 'openstudiostandards.get_lowest_floor_ext_wall_centroid_coords','Did not find an exteior wall in the building!')
160
+ end
161
+
162
+ return ext_wall_x,ext_wall_y,ext_wall_z
163
+ end
164
+
165
+ # =============================================================================================================================
166
+ # Return x,y,z coordinates of space centroid
167
+ def get_space_centroid_coords(space)
168
+ total_area = 0.0
169
+ sum_x,sum_y,sum_z = 0.0,0.0,0.0
170
+ space.surfaces.each do |surf|
171
+ total_area += surf.grossArea.to_f
172
+ sum_x += (surf.centroid.x.to_f + space.xOrigin.to_f) * surf.grossArea.to_f
173
+ sum_y += (surf.centroid.y.to_f + space.yOrigin.to_f) * surf.grossArea.to_f
174
+ sum_z += (surf.centroid.z.to_f + space.zOrigin.to_f) * surf.grossArea.to_f
175
+ end
176
+ space_centroid_x = sum_x / total_area
177
+ space_centroid_y = sum_y / total_area
178
+ space_centroid_z = sum_z / total_area
179
+
180
+ return space_centroid_x,space_centroid_y,space_centroid_z
181
+ end
182
+
183
+ # =============================================================================================================================
184
+ # Return x,y,z coordinates of the centroid of the roof of the storey
185
+ def get_roof_centroid_coords(storey)
186
+ sum_x,sum_y,sum_z,total_area = 0.0,0.0,0.0,0.0
187
+ cent_x,cent_y,cent_z = nil,nil,nil
188
+ storey.spaces.each do |space|
189
+ roof_surfaces = space.surfaces.select {|surf| (surf.surfaceType.to_s.upcase == "ROOFCEILING") && (surf.outsideBoundaryCondition.to_s.upcase == "OUTDOORS")}
190
+ roof_surfaces.each do |surf|
191
+ sum_x += (surf.centroid.x.to_f + space.xOrigin.to_f) * surf.grossArea.to_f
192
+ sum_y += (surf.centroid.y.to_f + space.yOrigin.to_f) * surf.grossArea.to_f
193
+ sum_z += (surf.centroid.z.to_f + space.zOrigin.to_f) * surf.grossArea.to_f
194
+ total_area += surf.grossArea.to_f
195
+ end
196
+ end
197
+ if total_area > 0.0
198
+ cent_x = sum_x / total_area
199
+ cent_y = sum_y / total_area
200
+ cent_z = sum_z / total_area
201
+ else
202
+ OpenStudio.logFree(OpenStudio::Info, 'openstudiostandards.get_roof_centroid_coords','Did not find a roof on the top floor!')
203
+ end
204
+
205
+ return cent_x,cent_y,cent_z
206
+ end
207
+
208
+ # =============================================================================================================================
209
+ # Determine maximum equivalent and net vertical pipe runs for VRF model
210
+ def get_max_vrf_pipe_lengths(model)
211
+ # Get and sort floors average ceilings z-coordinates hash
212
+ storeys_clg_zcoords = get_storey_avg_clg_zcoords(model)
213
+ storeys_clg_zcoords = storeys_clg_zcoords.sort_by {|key,value| value[1]}.to_h # sort storeys hash based on ceiling/roof z-coordinate
214
+ if storeys_clg_zcoords.values.last[0]
215
+ # If the top floor is conditioned, then assume the top floor is not an attic floor and place the VRF outdoor unit at the roof centroid
216
+ location_cent_x,location_cent_y,location_cent_z = get_roof_centroid_coords(storeys_clg_zcoords.keys.last)
217
+ else
218
+ # If the top floor is not conditioned, then assume it's an attic floor. In this case place the VRF outdoor unit next to the centroid
219
+ # of the exterior wall with the largest area on the lowest floor.
220
+ location_cent_x,location_cent_y,location_cent_z = get_lowest_floor_ext_wall_centroid_coords(storeys_clg_zcoords)
221
+ end
222
+ # Initialize distances
223
+ max_equiv_distance = 0.0
224
+ max_vert_distance = 0.0
225
+ min_vert_distance = 0.0
226
+ storeys_clg_zcoords.keys.each do |storey|
227
+ next unless storeys_clg_zcoords[storey][0]
228
+ storey.spaces.each do |space|
229
+ # Is there a VRF terminal unit in the space/zone?
230
+ vrf_term_units = []
231
+ if space.thermalZone.is_initialized
232
+ vrf_term_units = space.thermalZone.get.equipment.select {|eqpt| eqpt.to_ZoneHVACTerminalUnitVariableRefrigerantFlow.is_initialized}
233
+ end
234
+ next unless not vrf_term_units.empty?
235
+ space_centroid_x,space_centroid_y,space_centroid_z = get_space_centroid_coords(space)
236
+ # Update max horizontal and vertical distances if needed
237
+ equiv_distance = (location_cent_x.to_f - space_centroid_x.to_f).abs +
238
+ (location_cent_y.to_f - space_centroid_y.to_f).abs +
239
+ (location_cent_z.to_f - space_centroid_z.to_f).abs
240
+ if equiv_distance > max_equiv_distance then max_equiv_distance = equiv_distance end
241
+ pos_vert_distance = [space_centroid_z.to_f-location_cent_z.to_f,0.0].max
242
+ if pos_vert_distance > max_vert_distance then max_vert_distance = pos_vert_distance end
243
+ neg_vert_distance = [space_centroid_z.to_f-location_cent_z.to_f,0.0].min
244
+ if neg_vert_distance < min_vert_distance then min_vert_distance = neg_vert_distance end
245
+ end
246
+ end
247
+ max_net_vert_distance = max_vert_distance + min_vert_distance
248
+ max_net_vert_distance = [max_net_vert_distance,0.000001].max
249
+
250
+ return max_equiv_distance,max_net_vert_distance
251
+ end
252
+
253
+ # =============================================================================================================================
254
+ # Add an outdoor VRF unit
255
+ def add_outdoor_vrf_unit(model:,ecm_name: nil,condenser_type: "AirCooled")
256
+ outdoor_vrf_unit = OpenStudio::Model::AirConditionerVariableRefrigerantFlow.new(model)
257
+ outdoor_vrf_unit.setName("VRF Outdoor Unit")
258
+ outdoor_vrf_unit.setHeatPumpWasteHeatRecovery(true)
259
+ outdoor_vrf_unit.setRatedHeatingCOP(4.0)
260
+ outdoor_vrf_unit.setRatedCoolingCOP(4.0)
261
+ outdoor_vrf_unit.setMinimumOutdoorTemperatureinHeatingMode(-25.0)
262
+ outdoor_vrf_unit.setHeatingPerformanceCurveOutdoorTemperatureType("WetBulbTemperature")
263
+ outdoor_vrf_unit.setMasterThermostatPriorityControlType("ThermostatOffsetPriority")
264
+ outdoor_vrf_unit.setDefrostControl('OnDemand')
265
+ outdoor_vrf_unit.setDefrostStrategy('ReverseCycle')
266
+ outdoor_vrf_unit.autosizeResistiveDefrostHeaterCapacity
267
+ outdoor_vrf_unit.setPipingCorrectionFactorforHeightinHeatingModeCoefficient(-0.00019231)
268
+ outdoor_vrf_unit.setPipingCorrectionFactorforHeightinCoolingModeCoefficient(-0.00019231)
269
+ outdoor_vrf_unit.setMinimumOutdoorTemperatureinHeatRecoveryMode(-5.0)
270
+ outdoor_vrf_unit.setMaximumOutdoorTemperatureinHeatRecoveryMode(26.2)
271
+ outdoor_vrf_unit.setInitialHeatRecoveryCoolingCapacityFraction(0.5)
272
+ outdoor_vrf_unit.setHeatRecoveryCoolingCapacityTimeConstant(0.15)
273
+ outdoor_vrf_unit.setInitialHeatRecoveryCoolingEnergyFraction(1.0)
274
+ outdoor_vrf_unit.setHeatRecoveryCoolingEnergyTimeConstant(0.0)
275
+ outdoor_vrf_unit.setInitialHeatRecoveryHeatingCapacityFraction(1.0)
276
+ outdoor_vrf_unit.setHeatRecoveryHeatingCapacityTimeConstant(0.15)
277
+ outdoor_vrf_unit.setInitialHeatRecoveryHeatingEnergyFraction(1.0)
278
+ outdoor_vrf_unit.setHeatRecoveryCoolingEnergyTimeConstant(0.0)
279
+ outdoor_vrf_unit.setMinimumHeatPumpPartLoadRatio(0.5)
280
+ outdoor_vrf_unit.setCondenserType(condenser_type)
281
+ outdoor_vrf_unit.setCrankcaseHeaterPowerperCompressor(0.001)
282
+ heat_defrost_eir_ft = nil
283
+ if ecm_name
284
+ search_criteria = coil_dx_find_search_criteria(outdoor_vrf_unit)
285
+ props = model_find_object(standards_data['tables']["heat_pumps_heating_ecm_#{ecm_name.downcase}"]['table'], search_criteria, 1.0, Date.today)
286
+ heat_defrost_eir_ft = model_add_curve(model, props['heat_defrost_eir_ft'])
287
+ end
288
+ if heat_defrost_eir_ft
289
+ outdoor_vrf_unit.setDefrostEnergyInputRatioModifierFunctionofTemperatureCurve(heat_defrost_eir_ft)
290
+ else
291
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{outdoor_vrf_unit.name}, cannot find heat_defrost_eir_ft curve, will not be set.")
292
+ end
293
+
294
+ return outdoor_vrf_unit
295
+ end
296
+
297
+ # =============================================================================================================================
298
+ # Add indoor VRF units and update horizontal and vertical pipe runs for outdoor VRF unit
299
+ def add_indoor_vrf_units(model:,system_zones_map:,outdoor_vrf_unit:)
300
+ always_on = model.alwaysOnDiscreteSchedule
301
+ always_off = model.alwaysOffDiscreteSchedule
302
+ system_zones_map.sort.each do |sname,zones|
303
+ zones.sort.each do |izone|
304
+ zone_vrf_fan = OpenStudio::Model::FanOnOff.new(model, always_on)
305
+ zone_vrf_fan.setName("#{izone.name} VRF Fan")
306
+ zone_vrf_clg_coil = OpenStudio::Model::CoilCoolingDXVariableRefrigerantFlow.new(model)
307
+ zone_vrf_clg_coil.setName("#{izone.name} VRF Clg Coil")
308
+ zone_vrf_htg_coil = OpenStudio::Model::CoilHeatingDXVariableRefrigerantFlow.new(model)
309
+ zone_vrf_htg_coil.setName("#{izone.name} VRF Htg Coil")
310
+ zone_vrf_unit = OpenStudio::Model::ZoneHVACTerminalUnitVariableRefrigerantFlow.new(model,zone_vrf_clg_coil,zone_vrf_htg_coil,zone_vrf_fan)
311
+ zone_vrf_unit.setName("#{izone.name} VRF Indoor Unit")
312
+ zone_vrf_unit.setOutdoorAirFlowRateDuringCoolingOperation(0.000001)
313
+ zone_vrf_unit.setOutdoorAirFlowRateDuringHeatingOperation(0.000001)
314
+ zone_vrf_unit.setOutdoorAirFlowRateWhenNoCoolingorHeatingisNeeded(0.000001)
315
+ zone_vrf_unit.setZoneTerminalUnitOffParasiticElectricEnergyUse(0.000001)
316
+ zone_vrf_unit.setZoneTerminalUnitOnParasiticElectricEnergyUse(0.000001)
317
+ zone_vrf_unit.setSupplyAirFanOperatingModeSchedule(always_off)
318
+ zone_vrf_unit.setRatedTotalHeatingCapacitySizingRatio(1.3)
319
+ zone_vrf_unit.addToThermalZone(izone)
320
+ outdoor_vrf_unit.addTerminal(zone_vrf_unit)
321
+ # VRF terminal unit does not have a backup coil, use a unit heater as backup coil
322
+ zone_unitheater_fan = OpenStudio::Model::FanConstantVolume.new(model, always_on) # OS does not support an OnOff fan for unit heaters
323
+ zone_unitheater_fan.setName("#{izone.name} Unit Heater Fan")
324
+ zone_unitheater_htg_coil = OpenStudio::Model::CoilHeatingElectric.new(model, always_on)
325
+ zone_unitheater_htg_coil.setName("#{izone.name} Unit Heater Htg Coil")
326
+ zone_unit_heater = OpenStudio::Model::ZoneHVACUnitHeater.new(model,always_on,zone_unitheater_fan,zone_unitheater_htg_coil)
327
+ zone_unit_heater.setName("#{izone.name} Unit Heater")
328
+ zone_unit_heater.setFanControlType("OnOff")
329
+ zone_unit_heater.addToThermalZone(izone)
330
+ end
331
+ end
332
+ # Now we can find and apply maximum horizontal and vertical distances between outdoor vrf unit and zones with vrf terminal units
333
+ max_hor_pipe_length,max_vert_pipe_length = get_max_vrf_pipe_lengths(model)
334
+ #raise("test1:#{max_hor_pipe_length},#{max_vert_pipe_length}")
335
+ outdoor_vrf_unit.setEquivalentPipingLengthusedforPipingCorrectionFactorinCoolingMode(max_hor_pipe_length)
336
+ outdoor_vrf_unit.setEquivalentPipingLengthusedforPipingCorrectionFactorinHeatingMode(max_hor_pipe_length)
337
+ outdoor_vrf_unit.setVerticalHeightusedforPipingCorrectionFactor(max_vert_pipe_length)
338
+ end
339
+
340
+ # =============================================================================================================================
341
+ # Add a dedicated outside air loop with cold-climate heat pump with electric backup
342
+ # Add cold-climate zonal terminal VRF units
343
+ def add_ecm_hs08_vrfzonal(model:,system_zones_map:,system_doas_flags:,zone_clg_eqpt_type:, standard:)
344
+ # Update system doas flags
345
+ system_doas_flags.keys.each {|sname| system_doas_flags[sname] = true}
346
+ # Add doas with cold-climate air-source heat pump and electric backup
347
+ add_ecm_hs09_ccashpsys(model: model,system_zones_map: system_zones_map,system_doas_flags: system_doas_flags,standard: standard,baseboard_flag: false)
348
+ # Add outdoor VRF unit
349
+ outdoor_vrf_unit = add_outdoor_vrf_unit(model: model,ecm_name: "hs08_vrfzonal")
350
+ # Add indoor VRF terminal units
351
+ add_indoor_vrf_units(model: model,system_zones_map: system_zones_map,outdoor_vrf_unit: outdoor_vrf_unit)
352
+ end
353
+
354
+ # =============================================================================================================================
355
+ # Apply efficiencies and performance curves for ECM 'hs08_vrfzonal'
356
+ def apply_efficiency_ecm_hs08_vrfzonal(model:,ecm_name:)
357
+ # Use same performance data as ECM "hs09_ccashpsys" for air system
358
+ apply_efficiency_ecm_hs09_ccashpsys(model: model,ecm_name: "hs09_ccashpsys")
359
+ # Apply efficiency and curves for VRF units
360
+ model.getAirConditionerVariableRefrigerantFlows.sort.each do |vrf_unit|
361
+ airconditioner_variablerefrigerantflow_cooling_apply_efficiency_and_curves(vrf_unit,ecm_name)
362
+ airconditioner_variablerefrigerantflow_heating_apply_efficiency_and_curves(vrf_unit,ecm_name)
363
+ end
364
+ # Set fan size of VRF terminal units
365
+ fan_power_per_flow_rate = 150.0 # based on Mitsubishi data: 100 low and 200 high (W-s/m3)
366
+ model.getZoneHVACTerminalUnitVariableRefrigerantFlows.each do |iunit|
367
+ fan = iunit.supplyAirFan.to_FanOnOff.get
368
+ fan_pr_rise = fan_power_per_flow_rate*(fan.fanEfficiency*fan.motorEfficiency)
369
+ fan.setPressureRise(fan_pr_rise)
370
+ end
371
+ # Set fan size of unit heaters
372
+ model.getZoneHVACUnitHeaters.each do |iunit|
373
+ fan = iunit.supplyAirFan.to_FanConstantVolume.get
374
+ fan_pr_rise = fan_power_per_flow_rate*(fan.fanEfficiency*fan.motorEfficiency)
375
+ fan.setPressureRise(fan_pr_rise)
376
+ end
377
+ end
378
+
379
+ # =============================================================================================================================
380
+ # Add air loops with cold-climate heat pump with electric backup coil.
381
+ # Add zone electric baseboards
382
+ def add_ecm_hs09_ccashpsys(model:,system_zones_map:,system_doas_flags:,zone_clg_eqpt_type: nil,standard:,baseboard_flag: true)
383
+ always_on = model.alwaysOnDiscreteSchedule
384
+ always_off = model.alwaysOffDiscreteSchedule
385
+ systems = []
386
+ system_zones_map.sort.each do |sys_name,zones|
387
+ system_data = {}
388
+ system_data[:PreheatDesignTemperature] = 7.0
389
+ system_data[:PreheatDesignHumidityRatio] = 0.008
390
+ system_data[:PrecoolDesignTemperature] = 13.0
391
+ system_data[:PrecoolDesignHumidityRatio] = 0.008
392
+ system_data[:SizingOption] = 'NonCoincident'
393
+ system_data[:CoolingDesignAirFlowMethod] = 'DesignDay'
394
+ system_data[:CoolingDesignAirFlowRate] = 0.0
395
+ system_data[:HeatingDesignAirFlowMethod] = 'DesignDay'
396
+ system_data[:HeatingDesignAirFlowRate] = 0.0
397
+ system_data[:SystemOutdoorAirMethod] = 'ZoneSum'
398
+ system_data[:CentralCoolingDesignSupplyAirHumidityRatio] = 0.0085
399
+ system_data[:CentralHeatingDesignSupplyAirHumidityRatio] = 0.0080
400
+ system_data[:MinimumSystemAirFlowRatio] = 1.0
401
+ system_data[:system_supply_air_temperature] = 20.0
402
+ system_data[:ZoneCoolingDesignSupplyAirTemperature] = 13.0
403
+ system_data[:ZoneHeatingDesignSupplyAirTemperature] = 43.0
404
+ system_data[:ZoneCoolingSizingFactor] = 1.1
405
+ system_data[:ZoneHeatingSizingFactor] = 1.3
406
+ if system_doas_flags[sys_name.to_s]
407
+ system_data[:name] = sys_name.to_s
408
+ system_data[:AllOutdoorAirinCooling] = true
409
+ system_data[:AllOutdoorAirinHeating] = true
410
+ system_data[:TypeofLoadtoSizeOn] = 'VentilationRequirement'
411
+ system_data[:CentralCoolingDesignSupplyAirTemperature] = 19.9
412
+ system_data[:CentralHeatingDesignSupplyAirTemperature] = 20.0
413
+ sat_sch = OpenStudio::Model::ScheduleRuleset.new(model)
414
+ sat_sch.setName('Makeup-Air Unit Supply Air Temp')
415
+ sat_sch.defaultDaySchedule.setName('Makeup Air Unit Supply Air Temp Default')
416
+ sat_sch.defaultDaySchedule.addValue(OpenStudio::Time.new(0, 24, 0, 0), system_data[:system_supply_air_temperature])
417
+ setpoint_mgr = OpenStudio::Model::SetpointManagerScheduled.new(model, sat_sch)
418
+ else
419
+ system_data[:name] = sys_name.to_s
420
+ system_data[:AllOutdoorAirinCooling] = false
421
+ system_data[:AllOutdoorAirinHeating] = false
422
+ system_data[:TypeofLoadtoSizeOn] = 'Sensible'
423
+ system_data[:CentralCoolingDesignSupplyAirTemperature] = 13.0
424
+ system_data[:CentralHeatingDesignSupplyAirTemperature] = 43.0
425
+ if zones.size == 1
426
+ setpoint_mgr = OpenStudio::Model::SetpointManagerSingleZoneReheat.new(model)
427
+ setpoint_mgr.setControlZone(zones[0])
428
+ setpoint_mgr.setMinimumSupplyAirTemperature(13.0)
429
+ setpoint_mgr.setMaximumSupplyAirTemperature(43.0)
430
+ else
431
+ setpoint_mgr = OpenStudio::Model::SetpointManagerWarmest.new(model)
432
+ setpoint_mgr.setMinimumSetpointTemperature(13.0)
433
+ setpoint_mgr.setMaximumSetpointTemperature(43.0)
434
+ end
435
+ end
436
+ airloop = standard.common_air_loop(model: model, system_data: system_data)
437
+ # Fan
438
+ if system_doas_flags[sys_name.to_s] || zones.size == 1
439
+ sys_supply_fan = OpenStudio::Model::FanConstantVolume.new(model)
440
+ else
441
+ sys_supply_fan = OpenStudio::Model::FanVariableVolume.new(model)
442
+ sys_return_fan = OpenStudio::Model::FanVariableVolume.new(model)
443
+ sys_return_fan.setName("System Return Fan")
444
+ end
445
+ sys_supply_fan.setName("System Supply Fan")
446
+ # Cooling coil
447
+ sys_clg_coil = OpenStudio::Model::CoilCoolingDXVariableSpeed.new(model)
448
+ sys_clg_coil.setName("CoilCoolingDXVariableSpeed_CCASHP")
449
+ sys_clg_coil_speeddata1 = OpenStudio::Model::CoilCoolingDXVariableSpeedSpeedData.new(model)
450
+ sys_clg_coil.addSpeed(sys_clg_coil_speeddata1)
451
+ sys_clg_coil.setNominalSpeedLevel(1)
452
+ # Electric supplemental heating coil
453
+ sys_elec_htg_coil = OpenStudio::Model::CoilHeatingElectric.new(model, always_on)
454
+ sys_elec_htg_coil.setName("CoilHeatingElectric")
455
+ # DX heating coil
456
+ sys_dx_htg_coil = OpenStudio::Model::CoilHeatingDXVariableSpeed.new(model)
457
+ sys_dx_htg_coil.setName("CoilHeatingDXVariableSpeed_CCASHP")
458
+ sys_dx_htg_coil_speed1 = OpenStudio::Model::CoilHeatingDXVariableSpeedSpeedData.new(model)
459
+ sys_dx_htg_coil.addSpeed(sys_dx_htg_coil_speed1)
460
+ sys_dx_htg_coil.setNominalSpeedLevel(1)
461
+ sys_dx_htg_coil.setMinimumOutdoorDryBulbTemperatureforCompressorOperation(-25.0)
462
+ sys_dx_htg_coil.setDefrostStrategy("ReverseCycle")
463
+ #sys_dx_htg_coil.setDefrostStrategy("Resistive")
464
+ #sys_dx_htg_coil.setResistiveDefrostHeaterCapacity(0.001)
465
+ sys_dx_htg_coil.setDefrostControl("OnDemand")
466
+ sys_dx_htg_coil.setCrankcaseHeaterCapacity(0.001)
467
+ search_criteria = coil_dx_find_search_criteria(sys_dx_htg_coil)
468
+ props = model_find_object(standards_data['tables']["heat_pumps_heating_ecm_hs09_ccashpsys"]['table'], search_criteria, 1.0, Date.today)
469
+ heat_defrost_eir_ft = model_add_curve(model, props['heat_defrost_eir_ft'])
470
+ # This defrost curve has to be assigned here before sizing
471
+ if heat_defrost_eir_ft
472
+ sys_dx_htg_coil.setDefrostEnergyInputRatioFunctionofTemperatureCurve(heat_defrost_eir_ft)
473
+ else
474
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilHeatingDXVariableSpeed', "For #{sys_dx_htg_coil.name}, cannot find heat_defrost_eir_ft curve, will not be set.")
475
+ end
476
+ sys_clg_coil.addToNode(airloop.supplyOutletNode)
477
+ sys_dx_htg_coil.addToNode(airloop.supplyOutletNode)
478
+ sys_elec_htg_coil.addToNode(airloop.supplyOutletNode)
479
+ sys_supply_fan.addToNode(airloop.supplyOutletNode)
480
+ setpoint_mgr.addToNode(airloop.supplyOutletNode)
481
+ # OA controller
482
+ oa_controller = OpenStudio::Model::ControllerOutdoorAir.new(model)
483
+ oa_controller.autosizeMinimumOutdoorAirFlowRate
484
+ oa_system = OpenStudio::Model::AirLoopHVACOutdoorAirSystem.new(model, oa_controller)
485
+ oa_system.addToNode(airloop.supplyInletNode)
486
+ zones.each do |zone|
487
+ zone.sizingZone.setZoneCoolingDesignSupplyAirTemperature(13.0)
488
+ zone.sizingZone.setZoneHeatingDesignSupplyAirTemperature(43.0)
489
+ zone.sizingZone.setZoneCoolingSizingFactor(1.1)
490
+ zone.sizingZone.setZoneHeatingSizingFactor(1.3)
491
+ if zone_clg_eqpt_type
492
+ case zone_clg_eqpt_type[zone.name.to_s]
493
+ when "ZoneHVACPackagedTerminalAirConditioner"
494
+ standard.add_ptac_dx_cooling(model,zone,true)
495
+ end
496
+ end
497
+ if system_doas_flags[sys_name.to_s] || zones.size == 1
498
+ diffuser = OpenStudio::Model::AirTerminalSingleDuctUncontrolled.new(model, always_on)
499
+ else
500
+ reheat_coil = OpenStudio::Model::CoilHeatingElectric.new(model, always_on)
501
+ diffuser = OpenStudio::Model::AirTerminalSingleDuctVAVReheat.new(model, always_on, reheat_coil)
502
+ sys_return_fan.addToNode(airloop.returnAirNode.get)
503
+ diffuser.setFixedMinimumAirFlowRate(0.002 * zone.floorArea )
504
+ diffuser.setMaximumReheatAirTemperature(43.0)
505
+ diffuser.setDamperHeatingAction('Normal')
506
+ end
507
+ airloop.removeBranchForZone(zone)
508
+ airloop.addBranchForZone(zone, diffuser.to_StraightComponent)
509
+ if baseboard_flag then standard.add_zone_baseboards(baseboard_type: 'Electric', hw_loop: nil, model: model, zone: zone) end
510
+ end
511
+ update_sys_name(airloop,
512
+ sys_abbr: nil,
513
+ sys_oa: nil,
514
+ sys_hr: nil,
515
+ sys_htg: "ccashp",
516
+ sys_clg: "ccashp",
517
+ sys_sf: nil,
518
+ zone_htg: "b-e",
519
+ zone_clg: "none",
520
+ sys_rf: nil)
521
+ systems << airloop
522
+ end
523
+
524
+ return systems
525
+ end
526
+
527
+ # =============================================================================================================================
528
+ # Apply efficiencies and performance curves for ECM 'hs09_ccashpsys'
529
+ def apply_efficiency_ecm_hs09_ccashpsys(model:,ecm_name:)
530
+ # fraction of electric backup heating coil capacity assigned to dx heating coil
531
+ fr_backup_coil_cap_as_dx_coil_cap = 0.5
532
+ model.getAirLoopHVACs.each do |isys|
533
+ clg_dx_coil = nil
534
+ htg_dx_coil = nil
535
+ backup_coil = nil
536
+ fans = []
537
+ # Find the components on the air loop
538
+ isys.supplyComponents.each do |icomp|
539
+ if icomp.to_CoilCoolingDXVariableSpeed.is_initialized
540
+ clg_dx_coil = icomp.to_CoilCoolingDXVariableSpeed.get
541
+ elsif icomp.to_CoilHeatingDXVariableSpeed.is_initialized
542
+ htg_dx_coil = icomp.to_CoilHeatingDXVariableSpeed.get
543
+ elsif icomp.to_CoilHeatingElectric.is_initialized
544
+ backup_coil = icomp.to_CoilHeatingElectric.get
545
+ elsif icomp.to_FanConstantVolume.is_initialized
546
+ fans << icomp.to_FanConstantVolume.get
547
+ elsif icomp.to_FanVariableVolume.is_initialized
548
+ fans << icomp.to_FanVariableVolume.get
549
+ end
550
+ end
551
+ if clg_dx_coil && htg_dx_coil && backup_coil
552
+ clg_dx_coil_cap = clg_dx_coil.autosizedGrossRatedTotalCoolingCapacityAtSelectedNominalSpeedLevel.to_f
553
+ htg_dx_coil_cap = htg_dx_coil.autosizedRatedHeatingCapacityAtSelectedNominalSpeedLevel.to_f
554
+ backup_coil_cap = backup_coil.autosizedNominalCapacity.to_f
555
+ fan_power = 0.0
556
+ fans.each do |ifan|
557
+ fan_power += ifan.pressureRise.to_f*ifan.autosizedMaximumFlowRate.to_f/ifan.fanEfficiency.to_f
558
+ end
559
+ # Set the DX capacities to the maximum of the fraction of the backup coil capacity or the cooling capacity needed
560
+ dx_cap = fr_backup_coil_cap_as_dx_coil_cap*backup_coil_cap
561
+ if dx_cap < (clg_dx_coil_cap+fan_power) then dx_cap = clg_dx_coil_cap+fan_power end
562
+ clg_dx_coil.setGrossRatedTotalCoolingCapacityAtSelectedNominalSpeedLevel(dx_cap)
563
+ htg_dx_coil.setRatedHeatingCapacityAtSelectedNominalSpeedLevel(dx_cap)
564
+ end
565
+ end
566
+ # Assign performance curves and COPs
567
+ model.getCoilCoolingDXVariableSpeeds.sort.each {|coil| coil_cooling_dx_variable_speed_apply_efficiency_and_curves(coil,ecm_name)}
568
+ model.getCoilHeatingDXVariableSpeeds.sort.each {|coil| coil_heating_dx_variable_speed_apply_efficiency_and_curves(coil,ecm_name)}
569
+ end
570
+
571
+ # =============================================================================================================================
572
+ # Applies the standard efficiency ratings and typical performance curves "CoilCoolingDXVariableSpeed" object.
573
+ def coil_cooling_dx_variable_speed_apply_efficiency_and_curves(coil_cooling_dx_variable_speed,ecm_name)
574
+ successfully_set_all_properties = true
575
+
576
+ # Get the search criteria
577
+ search_criteria = coil_dx_find_search_criteria(coil_cooling_dx_variable_speed)
578
+
579
+ # Get the capacity
580
+ capacity_w = coil_cooling_dx_variable_speed_find_capacity(coil_cooling_dx_variable_speed)
581
+ capacity_btu_per_hr = OpenStudio.convert(capacity_w, 'W', 'Btu/hr').get
582
+ capacity_kbtu_per_hr = OpenStudio.convert(capacity_w, 'W', 'kBtu/hr').get
583
+
584
+ # Lookup efficiencies depending on whether it is a unitary AC or a heat pump
585
+ ac_props = if coil_dx_heat_pump?(coil_cooling_dx_variable_speed)
586
+ model_find_object(standards_data['tables']["heat_pumps_ecm_#{ecm_name.downcase}"]['table'], search_criteria, capacity_btu_per_hr, Date.today)
587
+ else
588
+ model_find_object(standards_data['tables']["unitary_acs_ecm_#{ecm_name.downcase}"]['table'], search_criteria, capacity_btu_per_hr, Date.today)
589
+ end
590
+
591
+ # Check to make sure properties were found
592
+ if ac_props.nil?
593
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standard.CoilCoolingDXVariableSpeed', "For #{coil_cooling_dx_single_speed.name}, cannot find efficiency info using #{search_criteria}, cannot apply efficiency.")
594
+ successfully_set_all_properties = false
595
+ end
596
+
597
+ # Make the COOL-CAP-FT curve
598
+ cool_cap_ft = model_add_curve(coil_cooling_dx_variable_speed.model, ac_props['cool_cap_ft'])
599
+ if cool_cap_ft
600
+ coil_cooling_dx_variable_speed.speeds.each {|speed| speed.setTotalCoolingCapacityFunctionofTemperatureCurve(cool_cap_ft)}
601
+ else
602
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standard.CoilCoolingDXVariableSpeed', "For #{coil_cooling_dx_variable_speed.name}, cannot find cool_cap_ft curve, will not be set.")
603
+ successfully_set_all_properties = false
604
+ end
605
+
606
+ # Make the COOL-CAP-FFLOW curve
607
+ cool_cap_fflow = model_add_curve(coil_cooling_dx_variable_speed.model, ac_props['cool_cap_fflow'])
608
+ if cool_cap_fflow
609
+ coil_cooling_dx_variable_speed.speeds.each {|speed| speed.setTotalCoolingCapacityFunctionofAirFlowFractionCurve(cool_cap_fflow)}
610
+ else
611
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standard.CoilCoolingDXVariableSpeed', "For #{coil_cooling_dx_variable_speed.name}, cannot find cool_cap_fflow curve, will not be set.")
612
+ successfully_set_all_properties = false
613
+ end
614
+
615
+ # Make the COOL-EIR-FT curve
616
+ cool_eir_ft = model_add_curve(coil_cooling_dx_variable_speed.model, ac_props['cool_eir_ft'])
617
+ if cool_eir_ft
618
+ coil_cooling_dx_variable_speed.speeds.each {|speed| speed.setEnergyInputRatioFunctionofTemperatureCurve(cool_eir_ft)}
619
+ else
620
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilCoolingDXVariableSpeed', "For #{coil_cooling_dx_variable_speed.name}, cannot find cool_eir_ft curve, will not be set.")
621
+ successfully_set_all_properties = false
622
+ end
623
+
624
+ # Make the COOL-EIR-FFLOW curve
625
+ cool_eir_fflow = model_add_curve(coil_cooling_dx_variable_speed.model, ac_props['cool_eir_fflow'])
626
+ if cool_eir_fflow
627
+ coil_cooling_dx_variable_speed.speeds.each {|speed| speed.setEnergyInputRatioFunctionofAirFlowFractionCurve(cool_eir_fflow)}
628
+ else
629
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilCoolingDXVariableSpeed', "For #{coil_cooling_dx_variable_speed.name}, cannot find cool_eir_fflow curve, will not be set.")
630
+ successfully_set_all_properties = false
631
+ end
632
+
633
+ # Make the COOL-PLF-FPLR curve
634
+ cool_plf_fplr = model_add_curve(coil_cooling_dx_variable_speed.model, ac_props['cool_plf_fplr'])
635
+ if cool_plf_fplr
636
+ coil_cooling_dx_variable_speed.setEnergyPartLoadFractionCurve(cool_plf_fplr)
637
+ else
638
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilCoolingDXVariableSpeed', "For #{coil_cooling_dx_variable_speed.name}, cannot find cool_plf_fplr curve, will not be set.")
639
+ successfully_set_all_properties = false
640
+ end
641
+
642
+ # Find the minimum COP and rename with efficiency rating
643
+ cop = coil_cooling_dx_variable_speed_standard_minimum_cop(coil_cooling_dx_variable_speed, true,ecm_name)
644
+
645
+ # Set the efficiency values
646
+ unless cop.nil?
647
+ coil_cooling_dx_variable_speed.speeds.each {|speed| speed.setReferenceUnitGrossRatedCoolingCOP(cop.to_f)}
648
+ end
649
+
650
+ end
651
+
652
+ # =============================================================================================================================
653
+ # Applies the standard efficiency ratings and typical performance curves to "CoilHeatingVariableSpeed" object.
654
+ def coil_heating_dx_variable_speed_apply_efficiency_and_curves(coil_heating_dx_variable_speed,ecm_name)
655
+ successfully_set_all_properties = true
656
+
657
+ # Get the search criteria
658
+ search_criteria = coil_dx_find_search_criteria(coil_heating_dx_variable_speed)
659
+
660
+ # Get the capacity
661
+ capacity_w = coil_heating_dx_variable_speed_find_capacity(coil_heating_dx_variable_speed)
662
+ capacity_btu_per_hr = OpenStudio.convert(capacity_w, 'W', 'Btu/hr').get
663
+ capacity_kbtu_per_hr = OpenStudio.convert(capacity_w, 'W', 'kBtu/hr').get
664
+
665
+ # Lookup efficiencies
666
+ props = model_find_object(standards_data['tables']["heat_pumps_heating_ecm_#{ecm_name.downcase}"]['table'], search_criteria, capacity_btu_per_hr, Date.today)
667
+
668
+ # Check to make sure properties were found
669
+ if props.nil?
670
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilHeatingDXVariableSpeed', "For #{coil_heating_dx_single_speed.name}, cannot find efficiency info using #{search_criteria}, cannot apply efficiency standard.")
671
+ successfully_set_all_properties = false
672
+ end
673
+
674
+ # Make the HEAT-CAP-FT curve
675
+ heat_cap_ft = model_add_curve(coil_heating_dx_variable_speed.model, props['heat_cap_ft'])
676
+ if heat_cap_ft
677
+ coil_heating_dx_variable_speed.speeds.each {|speed| speed.setHeatingCapacityFunctionofTemperatureCurve(heat_cap_ft)}
678
+ else
679
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilHeatingDXVariableSpeed', "For #{coil_heating_dx_variable_speed.name}, cannot find heat_cap_ft curve, will not be set.")
680
+ successfully_set_all_properties = false
681
+ end
682
+
683
+ # Make the HEAT-CAP-FFLOW curve
684
+ heat_cap_fflow = model_add_curve(coil_heating_dx_variable_speed.model, props['heat_cap_fflow'])
685
+ if heat_cap_fflow
686
+ coil_heating_dx_variable_speed.speeds.each {|speed| speed.setTotalHeatingCapacityFunctionofAirFlowFractionCurve(heat_cap_fflow)}
687
+ else
688
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilHeatingDXVariableSpeed', "For #{coil_heating_dx_variable_speed.name}, cannot find heat_cap_fflow curve, will not be set.")
689
+ successfully_set_all_properties = false
690
+ end
691
+
692
+ # Make the HEAT-EIR-FT curve
693
+ heat_eir_ft = model_add_curve(coil_heating_dx_variable_speed.model, props['heat_eir_ft'])
694
+ if heat_eir_ft
695
+ coil_heating_dx_variable_speed.speeds.each {|speed| speed.setEnergyInputRatioFunctionofTemperatureCurve(heat_eir_ft)}
696
+ else
697
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilHeatingDXVariableSingleSpeed', "For #{coil_heating_dx_variable_speed.name}, cannot find heat_eir_ft curve, will not be set.")
698
+ successfully_set_all_properties = false
699
+ end
700
+
701
+ # Make the HEAT-EIR-FFLOW curve
702
+ heat_eir_fflow = model_add_curve(coil_heating_dx_variable_speed.model, props['heat_eir_fflow'])
703
+ if heat_eir_fflow
704
+ coil_heating_dx_variable_speed.speeds.each {|speed| speed.setEnergyInputRatioFunctionofAirFlowFractionCurve(heat_eir_fflow)}
705
+ else
706
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilHeatingDXVariableSpeed', "For #{coil_heating_dx_variable_speed.name}, cannot find heat_eir_fflow curve, will not be set.")
707
+ successfully_set_all_properties = false
708
+ end
709
+
710
+ # Make the HEAT-PLF-FPLR curve
711
+ heat_plf_fplr = model_add_curve(coil_heating_dx_variable_speed.model, props['heat_plf_fplr'])
712
+ if heat_plf_fplr
713
+ coil_heating_dx_variable_speed.setEnergyPartLoadFractionCurve(heat_plf_fplr)
714
+ else
715
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilHeatingDXVariableSpeed', "For #{coil_heating_dx_variable_speed.name}, cannot find heat_plf_fplr curve, will not be set.")
716
+ successfully_set_all_properties = false
717
+ end
718
+
719
+ # Find the minimum COP and rename with efficiency rating
720
+ cop = coil_heating_dx_variable_speed_standard_minimum_cop(coil_heating_dx_variable_speed, true,ecm_name)
721
+
722
+ # Set the efficiency values
723
+ unless cop.nil?
724
+ coil_heating_dx_variable_speed.speeds.each {|speed| speed.setReferenceUnitGrossRatedHeatingCOP(cop.to_f)}
725
+ end
726
+
727
+ end
728
+
729
+ # =============================================================================================================================
730
+ # Applies the standard cooling efficiency ratings and typical performance curves to "AirConditionerVariableRefrigerantFlow" object.
731
+ def airconditioner_variablerefrigerantflow_cooling_apply_efficiency_and_curves(airconditioner_variablerefrigerantflow,ecm_name)
732
+ successfully_set_all_properties = true
733
+
734
+ # Get the search criteria
735
+ search_criteria = coil_dx_find_search_criteria(airconditioner_variablerefrigerantflow)
736
+
737
+ # Get the capacity
738
+ capacity_w = airconditioner_variablerefrigerantflow_cooling_find_capacity(airconditioner_variablerefrigerantflow)
739
+ capacity_btu_per_hr = OpenStudio.convert(capacity_w, 'W', 'Btu/hr').get
740
+ capacity_kbtu_per_hr = OpenStudio.convert(capacity_w, 'W', 'kBtu/hr').get
741
+
742
+ # Lookup efficiencies
743
+ props = model_find_object(standards_data['tables']["heat_pumps_ecm_#{ecm_name.downcase}"]['table'], search_criteria, capacity_btu_per_hr, Date.today)
744
+
745
+ # Check to make sure properties were found
746
+ if props.nil?
747
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standard.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find efficiency info using #{search_criteria}, cannot apply efficiency.")
748
+ successfully_set_all_properties = false
749
+ end
750
+
751
+ # Make the COOL-CAP-FT Low curve
752
+ cool_cap_ft_low = model_add_curve(airconditioner_variablerefrigerantflow.model, props['cool_cap_ft_low'])
753
+ if cool_cap_ft_low
754
+ airconditioner_variablerefrigerantflow.setCoolingCapacityRatioModifierFunctionofLowTemperatureCurve(cool_cap_ft_low)
755
+ else
756
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standard.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_cap_ft_low curve, will not be set.")
757
+ successfully_set_all_properties = false
758
+ end
759
+
760
+ # Make the COOL-CAP-FT boundary curve
761
+ cool_cap_ft_boundary = model_add_curve(airconditioner_variablerefrigerantflow.model, props['cool_cap_ft_boundary'])
762
+ if cool_cap_ft_boundary
763
+ airconditioner_variablerefrigerantflow.setCoolingCapacityRatioBoundaryCurve(cool_cap_ft_boundary)
764
+ else
765
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standard.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_cap_ft_boundary curve, will not be set.")
766
+ successfully_set_all_properties = false
767
+ end
768
+
769
+ # Make the COOL-CAP-FT high curve
770
+ cool_cap_ft_high = model_add_curve(airconditioner_variablerefrigerantflow.model, props['cool_cap_ft_high'])
771
+ if cool_cap_ft_high
772
+ airconditioner_variablerefrigerantflow.setCoolingCapacityRatioModifierFunctionofHighTemperatureCurve(cool_cap_ft_high)
773
+ else
774
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_cap_ft_high curve, will not be set.")
775
+ successfully_set_all_properties = false
776
+ end
777
+
778
+ # Make the COOL-EIR-FT low curve
779
+ cool_eir_ft_low = model_add_curve(airconditioner_variablerefrigerantflow.model, props['cool_eir_ft_low'])
780
+ if cool_eir_ft_low
781
+ airconditioner_variablerefrigerantflow.setCoolingEnergyInputRatioModifierFunctionofLowTemperatureCurve(cool_eir_ft_low)
782
+ else
783
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_eir_ft_low curve, will not be set.")
784
+ successfully_set_all_properties = false
785
+ end
786
+
787
+ # Make the COOL-EIR-FT boundary curve
788
+ cool_eir_ft_boundary = model_add_curve(airconditioner_variablerefrigerantflow.model, props['cool_eir_ft_boundary'])
789
+ if cool_eir_ft_boundary
790
+ airconditioner_variablerefrigerantflow.setCoolingEnergyInputRatioBoundaryCurve(cool_eir_ft_boundary)
791
+ else
792
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_eir_ft_boundary curve, will not be set.")
793
+ successfully_set_all_properties = false
794
+ end
795
+
796
+ # Make the COOL-EIR-FT high curve
797
+ cool_eir_ft_high = model_add_curve(airconditioner_variablerefrigerantflow.model, props['cool_eir_ft_high'])
798
+ if cool_eir_ft_high
799
+ airconditioner_variablerefrigerantflow.setCoolingEnergyInputRatioModifierFunctionofHighTemperatureCurve(cool_eir_ft_high)
800
+ else
801
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_eir_ft_high curve, will not be set.")
802
+ successfully_set_all_properties = false
803
+ end
804
+
805
+ # Make the COOL-EIR-FPLR low curve
806
+ cool_eir_fplr_low = model_add_curve(airconditioner_variablerefrigerantflow.model, props['cool_eir_fplr_low'])
807
+ if cool_eir_fplr_low
808
+ airconditioner_variablerefrigerantflow.setCoolingEnergyInputRatioModifierFunctionofLowPartLoadRatioCurve(cool_eir_fplr_low)
809
+ else
810
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_eir_fplr_low curve, will not be set.")
811
+ successfully_set_all_properties = false
812
+ end
813
+
814
+ # Make the COOL-EIR-FPLR high curve
815
+ cool_eir_fplr_high = model_add_curve(airconditioner_variablerefrigerantflow.model, props['cool_eir_fplr_high'])
816
+ if cool_eir_fplr_high
817
+ airconditioner_variablerefrigerantflow.setCoolingEnergyInputRatioModifierFunctionofHighPartLoadRatioCurve(cool_eir_fplr_high)
818
+ else
819
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_eir_fplr_high curve, will not be set.")
820
+ successfully_set_all_properties = false
821
+ end
822
+
823
+ # Make the COOL-CCR curve
824
+ cool_ccr = model_add_curve(airconditioner_variablerefrigerantflow.model, props['cool_ccr'])
825
+ if cool_ccr
826
+ airconditioner_variablerefrigerantflow.setCoolingCombinationRatioCorrectionFactorCurve(cool_ccr)
827
+ else
828
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_ccr curve, will not be set.")
829
+ successfully_set_all_properties = false
830
+ end
831
+
832
+ # Make the COOL-PLF-FPLR curve
833
+ cool_plf_fplr = model_add_curve(airconditioner_variablerefrigerantflow.model, props['cool_plf_fplr'])
834
+ if cool_plf_fplr
835
+ airconditioner_variablerefrigerantflow.setCoolingPartLoadFractionCorrelationCurve(cool_plf_fplr)
836
+ else
837
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_plf_fplr curve, will not be set.")
838
+ successfully_set_all_properties = false
839
+ end
840
+
841
+ # Make the COOL-PLF-FPLR curve
842
+ cool_plf_fplr = model_add_curve(airconditioner_variablerefrigerantflow.model, props['cool_plf_fplr'])
843
+ if cool_plf_fplr
844
+ airconditioner_variablerefrigerantflow.setCoolingPartLoadFractionCorrelationCurve(cool_plf_fplr)
845
+ else
846
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_plf_fplr curve, will not be set.")
847
+ successfully_set_all_properties = false
848
+ end
849
+
850
+ # Make the COOL-CAP-FPL curve
851
+ cool_cap_fpl = model_add_curve(airconditioner_variablerefrigerantflow.model, props['cool_cap_fpl'])
852
+ if cool_cap_fpl
853
+ airconditioner_variablerefrigerantflow.setPipingCorrectionFactorforLengthinCoolingModeCurve(cool_cap_fpl)
854
+ else
855
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_cap_fpl curve, will not be set.")
856
+ successfully_set_all_properties = false
857
+ end
858
+
859
+ # Find the minimum COP
860
+ cop = airconditioner_variablerefrigerantflow_cooling_standard_minimum_cop(airconditioner_variablerefrigerantflow, false, ecm_name)
861
+
862
+ # Set the efficiency values
863
+ unless cop.nil?
864
+ airconditioner_variablerefrigerantflow.setRatedCoolingCOP(cop.to_f)
865
+ end
866
+
867
+ end
868
+
869
+ # =============================================================================================================================
870
+ # Applies the standard heating efficiency ratings and typical performance curves to "AirConditionerVariableRefrigerantFlow" object.
871
+ def airconditioner_variablerefrigerantflow_heating_apply_efficiency_and_curves(airconditioner_variablerefrigerantflow,ecm_name)
872
+ successfully_set_all_properties = true
873
+
874
+ # Get the search criteria
875
+ search_criteria = coil_dx_find_search_criteria(airconditioner_variablerefrigerantflow)
876
+
877
+ # Get the capacity
878
+ capacity_w = airconditioner_variablerefrigerantflow_heating_find_capacity(airconditioner_variablerefrigerantflow)
879
+ capacity_btu_per_hr = OpenStudio.convert(capacity_w, 'W', 'Btu/hr').get
880
+ capacity_kbtu_per_hr = OpenStudio.convert(capacity_w, 'W', 'kBtu/hr').get
881
+
882
+ # Lookup efficiencies
883
+ props = model_find_object(standards_data['tables']["heat_pumps_heating_ecm_#{ecm_name.downcase}"]['table'], search_criteria, capacity_btu_per_hr, Date.today)
884
+
885
+ # Check to make sure properties were found
886
+ if props.nil?
887
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standard.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find heating efficiency info using #{search_criteria}, cannot apply efficiency.")
888
+ successfully_set_all_properties = false
889
+ end
890
+
891
+ # Make the HEAT-CAP-FT Low curve
892
+ heat_cap_ft_low = model_add_curve(airconditioner_variablerefrigerantflow.model, props['heat_cap_ft_low'])
893
+ if heat_cap_ft_low
894
+ airconditioner_variablerefrigerantflow.setHeatingCapacityRatioModifierFunctionofLowTemperatureCurve(heat_cap_ft_low)
895
+ else
896
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standard.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find heat_cap_ft_low curve, will not be set.")
897
+ successfully_set_all_properties = false
898
+ end
899
+
900
+ # Make the HEAT-CAP-FT boundary curve
901
+ heat_cap_ft_boundary = model_add_curve(airconditioner_variablerefrigerantflow.model, props['heat_cap_ft_boundary'])
902
+ if heat_cap_ft_boundary
903
+ airconditioner_variablerefrigerantflow.setHeatingCapacityRatioBoundaryCurve(heat_cap_ft_boundary)
904
+ else
905
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standard.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find heat_cap_ft_boundary curve, will not be set.")
906
+ successfully_set_all_properties = false
907
+ end
908
+
909
+ # Make the HEAT-CAP-FT high curve
910
+ heat_cap_ft_high = model_add_curve(airconditioner_variablerefrigerantflow.model, props['heat_cap_ft_high'])
911
+ if heat_cap_ft_high
912
+ airconditioner_variablerefrigerantflow.setHeatingCapacityRatioModifierFunctionofHighTemperatureCurve(heat_cap_ft_high)
913
+ else
914
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find heat_cap_ft_high curve, will not be set.")
915
+ successfully_set_all_properties = false
916
+ end
917
+
918
+ # Make the HEAT-EIR-FT low curve
919
+ heat_eir_ft_low = model_add_curve(airconditioner_variablerefrigerantflow.model, props['heat_eir_ft_low'])
920
+ if heat_eir_ft_low
921
+ airconditioner_variablerefrigerantflow.setHeatingEnergyInputRatioModifierFunctionofLowTemperatureCurve(heat_eir_ft_low)
922
+ else
923
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find heat_eir_ft_low curve, will not be set.")
924
+ successfully_set_all_properties = false
925
+ end
926
+
927
+ # Make the HEAT-EIR-FT boundary curve
928
+ heat_eir_ft_boundary = model_add_curve(airconditioner_variablerefrigerantflow.model, props['heat_eir_ft_boundary'])
929
+ if heat_eir_ft_boundary
930
+ airconditioner_variablerefrigerantflow.setHeatingEnergyInputRatioBoundaryCurve(heat_eir_ft_boundary)
931
+ else
932
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find heat_eir_ft_boundary curve, will not be set.")
933
+ successfully_set_all_properties = false
934
+ end
935
+
936
+ # Make the HEAT-EIR-FT high curve
937
+ heat_eir_ft_high = model_add_curve(airconditioner_variablerefrigerantflow.model, props['heat_eir_ft_high'])
938
+ if heat_eir_ft_high
939
+ airconditioner_variablerefrigerantflow.setHeatingEnergyInputRatioModifierFunctionofHighTemperatureCurve(heat_eir_ft_high)
940
+ else
941
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find heat_eir_ft_high curve, will not be set.")
942
+ successfully_set_all_properties = false
943
+ end
944
+
945
+ # Make the HEAT-EIR-FPLR low curve
946
+ heat_eir_fplr_low = model_add_curve(airconditioner_variablerefrigerantflow.model, props['heat_eir_fplr_low'])
947
+ if heat_eir_fplr_low
948
+ airconditioner_variablerefrigerantflow.setHeatingEnergyInputRatioModifierFunctionofLowPartLoadRatioCurve(heat_eir_fplr_low)
949
+ else
950
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find heat_eir_fplr_low curve, will not be set.")
951
+ successfully_set_all_properties = false
952
+ end
953
+
954
+ # Make the HEAT-EIR-FPLR high curve
955
+ heat_eir_fplr_high = model_add_curve(airconditioner_variablerefrigerantflow.model, props['heat_eir_fplr_high'])
956
+ if heat_eir_fplr_high
957
+ airconditioner_variablerefrigerantflow.setHeatingEnergyInputRatioModifierFunctionofHighPartLoadRatioCurve(heat_eir_fplr_high)
958
+ else
959
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find heat_eir_fplr_high curve, will not be set.")
960
+ successfully_set_all_properties = false
961
+ end
962
+
963
+ # Make the HEAT-HCR curve
964
+ heat_hcr = model_add_curve(airconditioner_variablerefrigerantflow.model, props['heat_hcr'])
965
+ if heat_hcr
966
+ airconditioner_variablerefrigerantflow.setHeatingCombinationRatioCorrectionFactorCurve(heat_hcr)
967
+ else
968
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find heat_hcr curve, will not be set.")
969
+ successfully_set_all_properties = false
970
+ end
971
+
972
+ # Make the HEAT-PLF-FPLR curve
973
+ heat_plf_fplr = model_add_curve(airconditioner_variablerefrigerantflow.model, props['heat_plf_fplr'])
974
+ if heat_plf_fplr
975
+ airconditioner_variablerefrigerantflow.setHeatingPartLoadFractionCorrelationCurve(heat_plf_fplr)
976
+ else
977
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find cool_plf_fplr curve, will not be set.")
978
+ successfully_set_all_properties = false
979
+ end
980
+
981
+ # Make the HEAT-CAP-FPL curve
982
+ heat_cap_fpl = model_add_curve(airconditioner_variablerefrigerantflow.model, props['heat_cap_fpl'])
983
+ if heat_cap_fpl
984
+ airconditioner_variablerefrigerantflow.setPipingCorrectionFactorforLengthinHeatingModeCurve(heat_cap_fpl)
985
+ else
986
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find heat_cap_fpl curve, will not be set.")
987
+ successfully_set_all_properties = false
988
+ end
989
+
990
+ # Find the minimum COP and rename with efficiency rating
991
+ cop = airconditioner_variablerefrigerantflow_heating_standard_minimum_cop(airconditioner_variablerefrigerantflow, true, ecm_name)
992
+
993
+ # Set the efficiency values
994
+ unless cop.nil?
995
+ airconditioner_variablerefrigerantflow.setRatedHeatingCOP(cop.to_f)
996
+ end
997
+
998
+ end
999
+
1000
+ # =============================================================================================================================
1001
+ # Find minimum efficiency for "CoilCoolingDXVariableSpeed" object
1002
+ def coil_cooling_dx_variable_speed_standard_minimum_cop(coil_cooling_dx_variable_speed, rename = false,ecm_name)
1003
+ search_criteria = coil_dx_find_search_criteria(coil_cooling_dx_variable_speed)
1004
+ cooling_type = search_criteria['cooling_type']
1005
+ heating_type = search_criteria['heating_type']
1006
+ sub_category = search_criteria['subcategory']
1007
+ capacity_w = coil_cooling_dx_variable_speed_find_capacity(coil_cooling_dx_variable_speed)
1008
+ capacity_btu_per_hr = OpenStudio.convert(capacity_w, 'W', 'Btu/hr').get
1009
+ capacity_kbtu_per_hr = OpenStudio.convert(capacity_w, 'W', 'kBtu/hr').get
1010
+
1011
+ # Look up the efficiency characteristics
1012
+ ac_props = if coil_dx_heat_pump?(coil_cooling_dx_variable_speed)
1013
+ model_find_object(standards_data['tables']["heat_pumps_ecm_#{ecm_name.downcase}"]['table'], search_criteria, capacity_btu_per_hr, Date.today)
1014
+ else
1015
+ model_find_object(standards_data['tables']["unitary_acs_ecm_#{ecm_name.downcase}"]['table'], search_criteria, capacity_btu_per_hr, Date.today)
1016
+ end
1017
+
1018
+ # Check to make sure properties were found
1019
+ if ac_props.nil?
1020
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilCoolingDXVariableSpeed', "For #{coil_cooling_dx_variable_speed.name}, cannot find efficiency info using #{search_criteria}, cannot apply efficiency standard.")
1021
+ successfully_set_all_properties = false
1022
+ return successfully_set_all_properties
1023
+ end
1024
+
1025
+ # Get the minimum efficiency standards
1026
+ cop = nil
1027
+
1028
+ # If specified as SEER
1029
+ unless ac_props['minimum_seasonal_energy_efficiency_ratio'].nil?
1030
+ min_seer = ac_props['minimum_seasonal_energy_efficiency_ratio']
1031
+ cop = seer_to_cop_cooling_with_fan(min_seer)
1032
+ new_comp_name = "#{coil_cooling_dx_variable_speed.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_seer}SEER"
1033
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.CoilCoolingDXVariableSpeed', "For #{template}: #{coil_cooling_dx_variable_speed.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; SEER = #{min_seer}")
1034
+ end
1035
+
1036
+ # If specified as EER
1037
+ unless ac_props['minimum_energy_efficiency_ratio'].nil?
1038
+ min_eer = ac_props['minimum_energy_efficiency_ratio']
1039
+ cop = eer_to_cop(min_eer)
1040
+ new_comp_name = "#{coil_cooling_dx_variable_speed.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_eer}EER"
1041
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.CoilCoolingDXVariableSpeed', "For #{template}: #{coil_cooling_dx_variable_speed.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; EER = #{min_eer}")
1042
+ end
1043
+
1044
+ # if specified as SEER (heat pump)
1045
+ unless ac_props['minimum_seasonal_efficiency'].nil?
1046
+ min_seer = ac_props['minimum_seasonal_efficiency']
1047
+ cop = seer_to_cop_cooling_with_fan(min_seer)
1048
+ new_comp_name = "#{coil_cooling_dx_variable_speed.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_seer}SEER"
1049
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.CoilCoolingDXVariableSpeed', "For #{template}: #{coil_cooling_dx_variable_speed.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; SEER = #{min_seer}")
1050
+ end
1051
+
1052
+ # If specified as EER (heat pump)
1053
+ unless ac_props['minimum_full_load_efficiency'].nil?
1054
+ min_eer = ac_props['minimum_full_load_efficiency']
1055
+ cop = eer_to_cop(min_eer)
1056
+ new_comp_name = "#{coil_cooling_dx_variable_speed.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_eer}EER"
1057
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.CoilCoolingDXVariableSpeed', "For #{template}: #{coil_cooling_dx_variable_speed.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; EER = #{min_eer}")
1058
+ end
1059
+
1060
+ # If specified as COP
1061
+ unless ac_props['minimum_coefficient_of_performance_cooling'].nil?
1062
+ cop = ac_props['minimum_coefficient_of_performance_cooling']
1063
+ new_comp_name = "#{coil_cooling_dx_variable_speed.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{cop}COP"
1064
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.CoilCoolingDXVariableSpeed', "For #{template}: #{coil_cooling_dx_variable_speed.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; COP = #{cop}")
1065
+ end
1066
+
1067
+ # Rename
1068
+ if rename
1069
+ coil_cooling_dx_variable_speed.setName(new_comp_name)
1070
+ end
1071
+
1072
+ return cop
1073
+ end
1074
+
1075
+ # =============================================================================================================================
1076
+ # Find minimum efficiency for "CoilHeatingDXVariableSingleSpeed" object
1077
+ def coil_heating_dx_variable_speed_standard_minimum_cop(coil_heating_dx_variable_speed, rename = false,ecm_name)
1078
+ search_criteria = coil_dx_find_search_criteria(coil_heating_dx_variable_speed)
1079
+ cooling_type = search_criteria['cooling_type']
1080
+ heating_type = search_criteria['heating_type']
1081
+ sub_category = search_criteria['subcategory']
1082
+ capacity_w = coil_heating_dx_variable_speed_find_capacity(coil_heating_dx_variable_speed)
1083
+ capacity_btu_per_hr = OpenStudio.convert(capacity_w, 'W', 'Btu/hr').get
1084
+ capacity_kbtu_per_hr = OpenStudio.convert(capacity_w, 'W', 'kBtu/hr').get
1085
+
1086
+ # Look up the efficiency characteristics
1087
+ props = model_find_object(standards_data['tables']["heat_pumps_heating_ecm_#{ecm_name.downcase}"], search_criteria, capacity_btu_per_hr, Date.today)
1088
+
1089
+ # Check to make sure properties were found
1090
+ if props.nil?
1091
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilHeatingDXVariableSpeed', "For #{coil_heating_dx_variable_speed.name}, cannot find efficiency info using #{search_criteria}, cannot apply efficiency standard.")
1092
+ successfully_set_all_properties = false
1093
+ return successfully_set_all_properties
1094
+ end
1095
+
1096
+ # Get the minimum efficiency standards
1097
+ cop = nil
1098
+
1099
+ # If specified as EER
1100
+ unless props['minimum_energy_efficiency_ratio'].nil?
1101
+ min_eer = props['minimum_energy_efficiency_ratio']
1102
+ cop = eer_to_cop(min_eer)
1103
+ new_comp_name = "#{coil_heating_dx_variable_speed.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_eer}EER"
1104
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.CoilHeatingDXVariableSpeed', "For #{template}: #{coil_heating_dx_variable_speed.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; EER = #{min_eer}")
1105
+ end
1106
+
1107
+ # if specified as HSPF (heat pump)
1108
+ unless props['minimum_heating_seasonal_performance_factor'].nil?
1109
+ min_hspf = props['minimum_heating_seasonal_performance_factor']
1110
+ cop = hspf_to_cop_heating_with_fan(min_hspf)
1111
+ new_comp_name = "#{coil_heating_dx_variable_speed.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_seer}HSPF"
1112
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.CoilHeatingDXVariableSpeed', "For #{template}: #{coil_heating_dx_variable_speed.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; SEER = #{min_seer}")
1113
+ end
1114
+
1115
+ # If specified as EER (heat pump)
1116
+ unless props['minimum_full_load_efficiency'].nil?
1117
+ min_eer = props['minimum_full_load_efficiency']
1118
+ cop = eer_to_cop(min_eer)
1119
+ new_comp_name = "#{coil_heating_dx_variable_speed.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_eer}EER"
1120
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.CoilHeatingDXVariableSpeed', "For #{template}: #{coil_heating_dx_variable_speed.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; EER = #{min_eer}")
1121
+ end
1122
+
1123
+ # If specified as COP
1124
+ unless props['minimum_coefficient_of_performance_heating'].nil?
1125
+ cop = props['minimum_coefficient_of_performance_heating']
1126
+ new_comp_name = "#{coil_heating_dx_variable_speed.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{cop}COP"
1127
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.CoilHeatingDXVariableSpeed', "For #{template}: #{coil_heating_dx_variable_speed.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; EER = #{min_eer}")
1128
+ end
1129
+
1130
+ # Rename
1131
+ if rename
1132
+ coil_heating_dx_variable_speed.setName(new_comp_name)
1133
+ end
1134
+
1135
+ return cop
1136
+ end
1137
+
1138
+ # =============================================================================================================================
1139
+ # Find minimum cooling efficiency for "AirConditionerVariableRefrigerantFlow" object
1140
+ def airconditioner_variablerefrigerantflow_cooling_standard_minimum_cop(airconditioner_variablerefrigerantflow, rename = false, ecm_name)
1141
+ search_criteria = coil_dx_find_search_criteria(airconditioner_variablerefrigerantflow)
1142
+ cooling_type = search_criteria['cooling_type']
1143
+ heating_type = search_criteria['heating_type']
1144
+ sub_category = search_criteria['subcategory']
1145
+ capacity_w = airconditioner_variablerefrigerantflow_cooling_find_capacity(airconditioner_variablerefrigerantflow)
1146
+ capacity_btu_per_hr = OpenStudio.convert(capacity_w, 'W', 'Btu/hr').get
1147
+ capacity_kbtu_per_hr = OpenStudio.convert(capacity_w, 'W', 'kBtu/hr').get
1148
+
1149
+ # Look up the efficiency characteristics
1150
+ props = model_find_object(standards_data['tables']["heat_pumps_ecm_#{ecm_name.downcase}"], search_criteria, capacity_btu_per_hr, Date.today)
1151
+
1152
+ # Check to make sure properties were found
1153
+ if props.nil?
1154
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find efficiency info using #{search_criteria}, cannot apply efficiency standard.")
1155
+ successfully_set_all_properties = false
1156
+ return successfully_set_all_properties
1157
+ end
1158
+
1159
+ # Get the minimum efficiency standards
1160
+ cop = nil
1161
+
1162
+ # If specified as EER
1163
+ unless props['minimum_energy_efficiency_ratio'].nil?
1164
+ min_eer = props['minimum_energy_efficiency_ratio']
1165
+ cop = eer_to_cop(min_eer)
1166
+ new_comp_name = "#{airconditioner_variablerefrigerantflow.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_eer}EER"
1167
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{template}: #{airconditioner_variablerefrigerantflow.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; EER = #{min_eer}")
1168
+ end
1169
+
1170
+ # if specified as HSPF (heat pump)
1171
+ unless props['minimum_heating_seasonal_performance_factor'].nil?
1172
+ min_hspf = props['minimum_heating_seasonal_performance_factor']
1173
+ cop = hspf_to_cop_heating_with_fan(min_hspf)
1174
+ new_comp_name = "#{coil_heating_dx_variable_speed.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_seer}HSPF"
1175
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{template}: #{airconditioner_variablerefrigerantflow.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; SEER = #{min_seer}")
1176
+ end
1177
+
1178
+ # If specified as EER (heat pump)
1179
+ unless props['minimum_full_load_efficiency'].nil?
1180
+ min_eer = props['minimum_full_load_efficiency']
1181
+ cop = eer_to_cop(min_eer)
1182
+ new_comp_name = "#{airconditioner_variablerefrigerantflow.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_eer}EER"
1183
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{template}: #{airconditioner_variablerefrigerantflow.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; EER = #{min_eer}")
1184
+ end
1185
+
1186
+ # If specified as COP
1187
+ unless props['minimum_coefficient_of_performance_cooling'].nil?
1188
+ cop = props['minimum_coefficient_of_performance_cooling']
1189
+ new_comp_name = "#{airconditioner_variablerefrigerantflow.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{cop}COP"
1190
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{template}: #{airconditioner_variablerefrigerantflow.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; EER = #{min_eer}")
1191
+ end
1192
+
1193
+ # Rename
1194
+ if rename
1195
+ airconditioner_variablerefrigerantflow.setName(new_comp_name)
1196
+ end
1197
+
1198
+ return cop
1199
+ end
1200
+
1201
+ # =============================================================================================================================
1202
+ # Find minimum heating efficiency for "AirConditionerVariableRefrigerantFlow" object
1203
+ def airconditioner_variablerefrigerantflow_heating_standard_minimum_cop(airconditioner_variablerefrigerantflow, rename = false, ecm_name)
1204
+ search_criteria = coil_dx_find_search_criteria(airconditioner_variablerefrigerantflow)
1205
+ cooling_type = search_criteria['cooling_type']
1206
+ heating_type = search_criteria['heating_type']
1207
+ sub_category = search_criteria['subcategory']
1208
+ capacity_w = airconditioner_variablerefrigerantflow_heating_find_capacity(airconditioner_variablerefrigerantflow)
1209
+ capacity_btu_per_hr = OpenStudio.convert(capacity_w, 'W', 'Btu/hr').get
1210
+ capacity_kbtu_per_hr = OpenStudio.convert(capacity_w, 'W', 'kBtu/hr').get
1211
+
1212
+ # Look up the efficiency characteristics
1213
+ props = model_find_object(standards_data['tables']["heat_pumps_heating_ecm_#{ecm_name.downcase}"], search_criteria, capacity_btu_per_hr, Date.today)
1214
+
1215
+ # Check to make sure properties were found
1216
+ if props.nil?
1217
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name}, cannot find heating efficiency info using #{search_criteria}, cannot apply efficiency standard.")
1218
+ successfully_set_all_properties = false
1219
+ return successfully_set_all_properties
1220
+ end
1221
+
1222
+ # Get the minimum efficiency standards
1223
+ cop = nil
1224
+
1225
+ # If specified as EER
1226
+ unless props['minimum_energy_efficiency_ratio'].nil?
1227
+ min_eer = props['minimum_energy_efficiency_ratio']
1228
+ cop = eer_to_cop(min_eer)
1229
+ new_comp_name = "#{airconditioner_variablerefrigerantflow.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_eer}EER"
1230
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{template}: #{airconditioner_variablerefrigerantflow.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; EER = #{min_eer}")
1231
+ end
1232
+
1233
+ # if specified as HSPF (heat pump)
1234
+ unless props['minimum_heating_seasonal_performance_factor'].nil?
1235
+ min_hspf = props['minimum_heating_seasonal_performance_factor']
1236
+ cop = hspf_to_cop_heating_with_fan(min_hspf)
1237
+ new_comp_name = "#{coil_heating_dx_variable_speed.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_seer}HSPF"
1238
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{template}: #{airconditioner_variablerefrigerantflow.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; SEER = #{min_seer}")
1239
+ end
1240
+
1241
+ # If specified as EER (heat pump)
1242
+ unless props['minimum_full_load_efficiency'].nil?
1243
+ min_eer = props['minimum_full_load_efficiency']
1244
+ cop = eer_to_cop(min_eer)
1245
+ new_comp_name = "#{airconditioner_variablerefrigerantflow.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{min_eer}EER"
1246
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{template}: #{airconditioner_variablerefrigerantflow.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; EER = #{min_eer}")
1247
+ end
1248
+
1249
+ # If specified as COP
1250
+ unless props['minimum_coefficient_of_performance_heating'].nil?
1251
+ cop = props['minimum_coefficient_of_performance_heating']
1252
+ new_comp_name = "#{airconditioner_variablerefrigerantflow.name} #{capacity_kbtu_per_hr.round}kBtu/hr #{cop}COP"
1253
+ OpenStudio.logFree(OpenStudio::Info, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{template}: #{airconditioner_variablerefrigerantflow.name}: #{cooling_type} #{heating_type} #{sub_category} Capacity = #{capacity_kbtu_per_hr.round}kBtu/hr; EER = #{min_eer}")
1254
+ end
1255
+
1256
+ # Rename
1257
+ if rename
1258
+ airconditioner_variablerefrigerantflow.setName(new_comp_name)
1259
+ end
1260
+
1261
+ return cop
1262
+ end
1263
+
1264
+ # =============================================================================================================================
1265
+ # Find cooling capacity for "CoilCoolingDXVariableSpeed" object
1266
+ def coil_cooling_dx_variable_speed_find_capacity(coil_cooling_dx_variable_speed)
1267
+ capacity_w = nil
1268
+ if coil_cooling_dx_variable_speed.grossRatedTotalCoolingCapacityAtSelectedNominalSpeedLevel.is_initialized
1269
+ capacity_w = coil_cooling_dx_variable_speed.grossRatedTotalCoolingCapacityAtSelectedNominalSpeedLevel.get
1270
+ elsif coil_cooling_dx_variable_speed.autosizedGrossRatedTotalCoolingCapacityAtSelectedNominalSpeedLevel.is_initialized
1271
+ capacity_w = coil_cooling_dx_variable_speed.autosizedGrossRatedTotalCoolingCapacityAtSelectedNominalSpeedLevel.get
1272
+ else
1273
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilCoolingDXVariableSpeed', "For #{coil_cooling_dx_variable_speed.name} capacity is not available, cannot apply efficiency standard.")
1274
+ return 0.0
1275
+ end
1276
+
1277
+ return capacity_w
1278
+ end
1279
+
1280
+ # =============================================================================================================================
1281
+ # Find heating capacity for "CoilHeatingDXVariableSpeed" object
1282
+ def coil_heating_dx_variable_speed_find_capacity(coil_heating_dx_variable_speed)
1283
+ capacity_w = nil
1284
+ if coil_heating_dx_variable_speed.ratedHeatingCapacityAtSelectedNominalSpeedLevel.is_initialized
1285
+ capacity_w = coil_heating_dx_variable_speed.ratedHeatingCapacityAtSelectedNominalSpeedLevel.get
1286
+ elsif coil_heating_dx_variable_speed.autosizedRatedHeatingCapacityAtSelectedNominalSpeedLevel.is_initialized
1287
+ capacity_w = coil_heating_dx_variable_speed.autosizedRatedHeatingCapacityAtSelectedNominalSpeedLevel.get
1288
+ else
1289
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.CoilHeatingDXVariableSpeed', "For #{coil_heating_dx_variable_speed.name} capacity is not available, cannot apply efficiency standard.")
1290
+ return 0.0
1291
+ end
1292
+
1293
+ return capacity_w
1294
+ end
1295
+
1296
+ # =============================================================================================================================
1297
+ # Find cooling capacity for "AirConditionerVariableRefrigerantFlow" object
1298
+ def airconditioner_variablerefrigerantflow_cooling_find_capacity(airconditioner_variablerefrigerantflow)
1299
+ capacity_w = nil
1300
+ if airconditioner_variablerefrigerantflow.ratedTotalCoolingCapacity.is_initialized
1301
+ capacity_w = airconditioner_variablerefrigerantflow.ratedTotalCoolingCapacity.get
1302
+ elsif airconditioner_variablerefrigerantflow.autosizedRatedTotalCoolingCapacity.is_initialized
1303
+ capacity_w = airconditioner_variablerefrigerantflow.autosizedRatedTotalCoolingCapacity.get
1304
+ airconditioner_variablerefrigerantflow.setRatedTotalCoolingCapacity(capacity_w)
1305
+ else
1306
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name} cooling capacity is not available, cannot apply efficiency standard.")
1307
+ return 0.0
1308
+ end
1309
+
1310
+ return capacity_w
1311
+ end
1312
+
1313
+ # =============================================================================================================================
1314
+ # Find heating capacity for "AirConditionerVariableRefrigerantFlow" object
1315
+ def airconditioner_variablerefrigerantflow_heating_find_capacity(airconditioner_variablerefrigerantflow)
1316
+ capacity_w = nil
1317
+ if airconditioner_variablerefrigerantflow.ratedTotalHeatingCapacity.is_initialized
1318
+ capacity_w = airconditioner_variablerefrigerantflow.ratedTotalHeatingCapacity.get
1319
+ elsif airconditioner_variablerefrigerantflow.autosizedRatedTotalHeatingCapacity.is_initialized
1320
+ capacity_w = airconditioner_variablerefrigerantflow.autosizedRatedTotalHeatingCapacity.get
1321
+ airconditioner_variablerefrigerantflow.setRatedTotalHeatingCapacity(capacity_w)
1322
+ else
1323
+ OpenStudio.logFree(OpenStudio::Warn, 'openstudio.standards.AirConditionerVariableRefrigerantFlow', "For #{airconditioner_variablerefrigerantflow.name} heating capacity is not available, cannot apply efficiency standard.")
1324
+ return 0.0
1325
+ end
1326
+
1327
+ return capacity_w
1328
+ end
1329
+
1330
+ # ============================================================================================================================
1331
+ # Apply boiler efficiency
1332
+ # This model takes an OS model and a boiler efficiency string or hash sent to it with the following form:
1333
+ # "boiler_eff": {
1334
+ # "name" => "NECB 88% Efficient Condensing Boiler",
1335
+ # "efficiency" => 0.88,
1336
+ # "part_load_curve" => "BOILER-EFFPLR-COND-NECB2011",
1337
+ # "notes" => "From NECB 2011."
1338
+ # }
1339
+ # If boiler_eff is nill then it does nothing. If both "efficiency" and "part_load_curve" are nil then it does
1340
+ # nothing. If a boiler_eff is passed as a string and not a hash then it looks for a "name" field in the
1341
+ # boiler_set.json file that matches boiler_eff and gets the associated boiler performance details from the file.
1342
+ # If an efficiency is set but is not between 0.01 and 1.0 it returns an error. Otherwise, it looks for plant loop
1343
+ # supply components that match the "OS_BoilerHotWater" type. If it finds one it then calls the
1344
+ # "reset_boiler_efficiency method which resets the the boiler efficiency and looks for the part load efficiency curve
1345
+ # in the curves.json file. If it finds a curve it sets the part load curve to that, otherwise it returns an error.
1346
+ # It also renames the boiler to include the "boiler_eff"["name"].
1347
+ def modify_boiler_efficiency(model:, boiler_eff: nil)
1348
+ return if boiler_eff.nil?
1349
+ # If boiler_eff is a string rather than a hash then assume it is the name of a boiler efficiency package and look
1350
+ # for a package with that name in boiler_set.json.
1351
+ if boiler_eff.is_a?(String)
1352
+ eff_packages = @standards_data['tables']['boiler_eff_ecm']['table']
1353
+ eff_package = eff_packages.select{|eff_pack_info| eff_pack_info["name"] == boiler_eff}
1354
+ if eff_package.empty?
1355
+ raise "Cannot not find #{boiler_eff} in the ECMS boiler_set.json file. Please check that the name is correctly spelled in the ECMS class boiler_set.json and in the code calling (directly or through another method) the ECMS class modify_boiler_efficiency method."
1356
+ elsif eff_package.size > 1
1357
+ raise "More than one boiler efficiency package with the name #{boiler_eff} was found. Please check the ECMS class boiler_set.json file and make sure that each boiler efficiency package has a unique name."
1358
+ else
1359
+ ecm_name = boiler_eff
1360
+ boiler_eff = {
1361
+ "name" => ecm_name,
1362
+ "efficiency" => eff_package[0]['efficiency'],
1363
+ "part_load_curve" => eff_package[0]['part_load_curve']
1364
+ }
1365
+ end
1366
+ end
1367
+ # If nothing is passed in the boiler_eff hash then assume this was not supposed to be used and return without doing
1368
+ # anything.
1369
+ return if boiler_eff["name"].nil? && boiler_eff["efficiency"].nil? && boiler_eff["part_load_curve"].nil?
1370
+ # If no efficiency or partload curve are found (either passed directly or via the boiler_set.json file) then assume
1371
+ # that the current SHW setting should not be changed. Return without changing anything.
1372
+ return if boiler_eff["efficiency"].nil? && boiler_eff["part_load_curve"].nil?
1373
+ raise "You attempted to set the efficiency of boilers in this model to nil. Please check the ECMS class boiler_set.json and make sure the efficiency is properly set" if boiler_eff["efficiency"].nil?
1374
+ raise "You attempted to set the efficiency of boilers in this model to: #{boiler_eff['efficiency']}. Please check the ECMS class boiler_set.json and make sure the efficiency you set is between 0.01 and 1.0." if (boiler_eff['efficiency'] < 0.01 || boiler_eff['efficiency'] > 1.0)
1375
+ raise "You attempted to set the part load curve of boilers in this model to nil. Please check the ECMS class boiler_set.json file and ensure that both the efficiency and part load curve are set." if boiler_eff['part_load_curve'].nil?
1376
+ model.getBoilerHotWaters.sort.each do |mod_boiler|
1377
+ reset_boiler_efficiency(model: model, component: mod_boiler.to_BoilerHotWater.get, eff: boiler_eff)
1378
+ end
1379
+ end
1380
+
1381
+ # This method takes an OS model, a "OS_BoilerHotWater" type compenent, condensing efficiency limit and an efficiency
1382
+ # hash which looks like:
1383
+ # "eff": {
1384
+ # "name": "NECB 88% Efficient Condensing Boiler",
1385
+ # "efficiency" => 0.88,
1386
+ # "part_load_curve" => "BOILER-EFFPLR-COND-NECB2011",
1387
+ # "notes" => "From NECB 2011."
1388
+ # }
1389
+ # This method sets efficiency of the boiler to whatever is entered in eff["efficiency"]. It then looks for the
1390
+ # "part_load_curve" value in the curves.json file. If it does not find one it returns an error. If it finds one it
1391
+ # reset the part load curve to whatever was found. It then determines the nominal capacity of the boiler. If the
1392
+ # nominal capacity is greater than 1W the boiler is considered a primary boiler (for the name only) if the capacity is
1393
+ # less than 1W the boiler is considered a secondary boiler (for the name only). It then renames the boiler according
1394
+ # to the following pattern:
1395
+ # "Primary/Secondary eff["name"] capacity kBtu/hr".
1396
+ def reset_boiler_efficiency(model:, component:, eff:)
1397
+ component.setNominalThermalEfficiency(eff['efficiency'])
1398
+ part_load_curve_name = eff["part_load_curve"].to_s
1399
+ existing_curve = @standards_data['curves'].select { |curve| curve['name'] == part_load_curve_name }
1400
+ raise "No boiler with the name #{part_load_curve_name} could be found in the ECMS class curves.json file. Please check both the ECMS class boiler_set.json and class curves.json files to ensure the curve is entered and referenced correctly." if existing_curve.empty?
1401
+ part_load_curve_data = (@standards_data["curves"].select { |curve| curve['name'] == part_load_curve_name })[0]
1402
+ if part_load_curve_data['independent_variable_1'].to_s.upcase == 'TEnteringBoiler'.upcase || part_load_curve_data['independent_variable_2'].to_s.upcase == 'TEnteringBoiler'.upcase
1403
+ component.setEfficiencyCurveTemperatureEvaluationVariable('EnteringBoiler')
1404
+ elsif part_load_curve_data['independent_variable_1'].to_s.upcase == 'TLeavingBoiler'.upcase || part_load_curve_data['independent_variable_2'].to_s.upcase == 'TLeavingBoiler'.upcase
1405
+ component.setEfficiencyCurveTemperatureEvaluationVariable('LeavingBoiler')
1406
+ end
1407
+ part_load_curve = model_add_curve(model, part_load_curve_name)
1408
+ if part_load_curve
1409
+ component.setNormalizedBoilerEfficiencyCurve(part_load_curve)
1410
+ if component.isNominalCapacityAutosized
1411
+ boiler_size_W = model.getAutosizedValue(component, 'Design Size Nominal Capacity', 'W').to_f
1412
+ else
1413
+ boiler_size_W = component.nominalCapacity.to_f
1414
+ end
1415
+ boiler_size_kbtu_per_hour = (OpenStudio.convert(boiler_size_W, 'W', 'kBtu/h').get)
1416
+ boiler_primacy = 'Primary '
1417
+ if boiler_size_W < 1.0
1418
+ boiler_primacy = 'Secondary '
1419
+ end
1420
+ if eff['name'].nil?
1421
+ eff_measure_name = "Revised Performance Boiler"
1422
+ else
1423
+ eff_measure_name = eff['name']
1424
+ end
1425
+ new_boiler_name = boiler_primacy + eff_measure_name + " #{boiler_size_kbtu_per_hour.round(0)}kBtu/hr #{component.nominalThermalEfficiency} Thermal Eff"
1426
+ component.setName(new_boiler_name)
1427
+ else
1428
+ raise "There was a problem setting the boiler part load curve named #{part_load_curve_name} for #{component.name}. Please ensure that the curve is entered and referenced correctly in the ECMS class curves.json and boiler_set.json files."
1429
+ end
1430
+ end
1431
+
1432
+ # ============================================================================================================================
1433
+ # Apply Furnace efficiency
1434
+ # This model takes an OS model and a furnace efficiency string or hash sent to it with the following form:
1435
+ # "furnace_eff": {
1436
+ # "name" => "NECB 85% Efficient Condensing Furnace",
1437
+ # "efficiency" => 0.85,
1438
+ # "part_load_curve" => "FURNACE-EFFPLR-COND-NECB2011",
1439
+ # "notes" => "From NECB 2011."
1440
+ # }
1441
+ # If furnace_eff is nil then it does nothing. If both "efficiency" and "part_load_curve" are nil then it does
1442
+ # nothing. If a furnace_eff is a string it looks for furnace_eff as a "name" in the furnace_set.json file to find
1443
+ # the performance details. If an efficiency is set but is not between 0.01 and 1.0 it returns an error. Otherwise,
1444
+ # it looks for air loop supply components that match the "OS_CoilHeatingGas" type. If it finds one it then calls the
1445
+ # reset_furnace_efficiency method which resets the the furnace efficiency and looks for the part load efficiency curve
1446
+ # in the curves.json file. If it finds a curve it sets the part load curve to that, otherwise it returns an error. It
1447
+ # also renames the furnace to include the "furnace_eff"["name"].
1448
+ def modify_furnace_efficiency(model:, furnace_eff: nil)
1449
+ return if furnace_eff.nil?
1450
+ # If furnace_eff is a string rather than a hash then assume it is the name of a furnace efficiency package and look
1451
+ # for a package with that name in furnace_set.json.
1452
+ if furnace_eff.is_a?(String)
1453
+ eff_packages = @standards_data['tables']['furnace_eff_ecm']['table']
1454
+ eff_package = eff_packages.select{|eff_pack_info| eff_pack_info["name"] == furnace_eff}
1455
+ if eff_package.empty?
1456
+ raise "Cannot not find #{furnace_eff} in the ECMS furnace_set.json file. Please check that the name is correctly spelled in the ECMS class furnace_set.json and in the code calling (directly or through another method) the ECMS class modify_furnace_efficiency method."
1457
+ elsif eff_package.size > 1
1458
+ raise "More than one furnace efficiency package with the name #{furnace_eff} was found. Please check the ECMS class furnace_set.json file and make sure that each furnace efficiency package has a unique name."
1459
+ else
1460
+ ecm_name = furnace_eff
1461
+ furnace_eff = {
1462
+ "name" => ecm_name,
1463
+ "efficiency" => eff_package[0]['efficiency'],
1464
+ "part_load_curve" => eff_package[0]['part_load_curve']
1465
+ }
1466
+ end
1467
+ end
1468
+ # If nothing is passed in the furnace_eff hash then assume this was not supposed to be used and return without doing
1469
+ # anything.
1470
+ return if furnace_eff["name"].nil? && furnace_eff["efficiency"].nil? && furnace_eff["part_load_curve"].nil?
1471
+ # If no efficiency or partload curve are found (either passed directly or via the furnace_set.json file) then assume
1472
+ # that the current furance performance settings should not be changed. Return without changing anything.
1473
+ return if furnace_eff["efficiency"].nil? && furnace_eff["part_load_curve"].nil?
1474
+ raise "You attempted to set the efficiency of furnaces in this model to nil. Please check the ECMS class furnace_set.json file and make sure the efficiency is set" if furnace_eff["efficiency"].nil?
1475
+ raise "You attempted to set the efficiency of furnaces in this model to: #{furnace_eff['efficiency']}. Please check the ECMS class furnace_set.json file and make sure the efficiency you set is between 0.01 and 1.0." if (furnace_eff['efficiency'] < 0.01 || furnace_eff['efficiency'] > 1.0)
1476
+ raise "You attempted to set the part load curve of furnaces in this model to nil. Please check the ECMS class furnace_set.json file and ensure that both the efficiency and part load curve are set." if furnace_eff['part_load_curve'].nil?
1477
+ model.getCoilHeatingGass.sort.each do |mod_furnace|
1478
+ reset_furnace_efficiency(model: model, component: mod_furnace.to_CoilHeatingGas.get, eff: furnace_eff)
1479
+ end
1480
+ end
1481
+
1482
+ # This method takes an OS model, a "OS_CoilHeatingGas" type compenent, and an efficiency hash which looks like:
1483
+ # "eff": {
1484
+ # "name": "NECB 85% Efficient Condensing Furnace",
1485
+ # "efficiency" => 0.85,
1486
+ # "part_load_curve" => "FURNACE-EFFPLR-COND-NECB2011",
1487
+ # "notes" => "From NECB 2011."
1488
+ # }
1489
+ # This method sets the efficiency of the furnace to whatever is entered in eff["efficiency"]. It then looks for the
1490
+ # "part_load_curve" value in the curves.json file. If it does not find one it returns an error. If it finds one it
1491
+ # reset the part load curve to whatever was found. It then renames the furnace according to the following pattern:
1492
+ # "eff["name"] + <furnace number (whatever was there before)>".
1493
+ def reset_furnace_efficiency(model:, component:, eff:)
1494
+ component.setGasBurnerEfficiency(eff['efficiency'])
1495
+ part_load_curve_name = eff["part_load_curve"].to_s
1496
+ existing_curve = @standards_data['curves'].select { |curve| curve['name'] == part_load_curve_name }
1497
+ raise "No furnace part load curve with the name #{part_load_curve_name} could be found in the ECMS class curves.json file. Please check both the ECMS class curves.json and the measure furnace_set.json files to ensure the curve is entered and referenced correctly." if existing_curve.empty?
1498
+ part_load_curve = model_add_curve(model, part_load_curve_name)
1499
+ raise "There was a problem setting the furnace part load curve named #{part_load_curve_name} for #{component.name}. Please ensure that the curve is entered and referenced correctly in the ECMS class curves.json or measure furnace_set.json files." unless part_load_curve
1500
+ component.setPartLoadFractionCorrelationCurve(part_load_curve)
1501
+ if eff['name'].nil?
1502
+ ecm_package_name = "Revised Performance Furnace"
1503
+ else
1504
+ ecm_package_name = eff['name']
1505
+ end
1506
+ furnace_num = component.name.to_s.gsub(/[^0-9]/, '')
1507
+ new_furnace_name = ecm_package_name + " #{furnace_num}"
1508
+ component.setName(new_furnace_name)
1509
+ end
1510
+
1511
+ # ============================================================================================================================
1512
+ # Apply shw efficiency
1513
+ # This model takes an OS model and a shw efficiency string or hash sent to it with the following form:
1514
+ # "shw_eff": {
1515
+ # "name" => "Natural Gas Power Vent with Electric Ignition",
1516
+ # "efficiency" => 0.94,
1517
+ # "part_load_curve" => "SWH-EFFFPLR-NECB2011"
1518
+ # "notes" => "From NECB 2011."
1519
+ # }
1520
+ # If shw_eff is nil then it does nothing. If both "efficiency" and "part_load_curve" are nil then it does nothing.
1521
+ # If shw_eff is a string then it looks for shw_eff as a "name" in the shw_set.json file for the details on the tank.
1522
+ # If an efficiency is set but is not between 0.01 and 1.0 it returns an error. Otherwise, it looks for mixed water
1523
+ # heaters. If it finds any it then calls the reset_shw_efficiency method which resets the the shw efficiency and the
1524
+ # part load curve. It also renames the shw tank with the following pattern:
1525
+ # {valume}Gal {eff_name} Water Heater - {Capacity}kBtu/hr {efficiency} Therm Eff
1526
+ def modify_shw_efficiency(model:, shw_eff: nil)
1527
+ return if shw_eff.nil?
1528
+ # If shw_eff is a string rather than a hash then assume it is the name of a shw efficiency package and look
1529
+ # for a package with that name in shw_set.json.
1530
+ if shw_eff.is_a?(String)
1531
+ eff_packages = @standards_data['tables']['shw_eff_ecm']['table']
1532
+ eff_package = eff_packages.select{|eff_pack_info| eff_pack_info["name"] == shw_eff}
1533
+ if eff_package.empty?
1534
+ raise "Cannot not find #{shw_eff} in the ECMS shw_set.json file. Please check that the name is correctly spelled in the ECMS class shw_set.json and in the code calling (directly or through another method) the ECMS class modify_shw_efficiency method."
1535
+ elsif eff_package.size > 1
1536
+ raise "More than one shw tank efficiency package with the name #{shw_eff} was found. Please check the ECMS class shw_set.json file and make sure that each shw tank efficiency package has a unique name."
1537
+ else
1538
+ ecm_name = shw_eff
1539
+ shw_eff = {
1540
+ "name" => ecm_name,
1541
+ "efficiency" => eff_package[0]['efficiency'],
1542
+ "part_load_curve" => eff_package[0]['part_load_curve']
1543
+ }
1544
+ end
1545
+ end
1546
+ # If nothing is passed in the shw_eff hash then assume this was not supposed to be used and return without doing
1547
+ # anything.
1548
+ return if shw_eff["name"].nil? && shw_eff["efficiency"].nil? && shw_eff["part_load_curve"].nil?
1549
+ # If no efficiency or partload curve are found (either passed directly or via the shw_set.json file) then assume
1550
+ # that the current shw performance settings should not be changed. Return without changing anything.
1551
+ return if shw_eff["efficiency"].nil? && shw_eff["part_load_curve"].nil?
1552
+ raise "You attempted to set the efficiency of shw tanks in this model to nil. Please check the ECMS class shw_set.json file and make sure the efficiency is set" if shw_eff["efficiency"].nil?
1553
+ raise "You attempted to set the efficiency of shw tanks in this model to: #{shw_eff['efficiency']}. Please check the ECMS class shw_set.json and make sure the efficiency you set is between 0.01 and 1.0." if (shw_eff['efficiency'] < 0.01 || shw_eff['efficiency'] > 1.0)
1554
+ raise "You attempted to set the part load curve of shw tanks in this model to nil. Please check the ECMS class shw_set.json file and ensure that both the efficiency and part load curve are set." if shw_eff['part_load_curve'].nil?
1555
+ model.getWaterHeaterMixeds.sort.each do |shw_mod|
1556
+ reset_shw_efficiency(model: model, component: shw_mod, eff: shw_eff)
1557
+ end
1558
+ end
1559
+
1560
+ # This method takes an OS model, a "OS_WaterHeaterMixed" type compenent, and an efficiency hash which looks like:
1561
+ # "eff": {
1562
+ # "name": "Natural Gas Power Vent with Electric Ignition",
1563
+ # "efficiency" => 0.94,
1564
+ # "part_load_curve" => "SWH-EFFFPLR-NECB2011",
1565
+ # "notes" => "From NECB 2011."
1566
+ # }
1567
+ # This method sets the efficiency of the shw heater to whatever is entered in eff["efficiency"]. It then looks for the
1568
+ # "part_load_curve" value in the curves.json file. If it does not find one it returns an error. If it finds one it
1569
+ # resets the part load curve to whatever was found. It then renames the shw tank according to the following pattern:
1570
+ # {valume}Gal {eff_name} Water Heater - {Capacity}kBtu/hr {efficiency} Therm Eff
1571
+ def reset_shw_efficiency(model:, component:, eff:)
1572
+ return if component.heaterFuelType.to_s.upcase == 'ELECTRICITY'
1573
+ eff_result = component.setHeaterThermalEfficiency(eff['efficiency'].to_f)
1574
+ raise "There was a problem setting the efficiency of the SHW #{component.name.to_s}. Please check the ECMS class shw_set.json file or the model." unless eff_result
1575
+ part_load_curve_name = eff["part_load_curve"].to_s
1576
+ existing_curve = @standards_data['curves'].select { |curve| curve['name'] == part_load_curve_name }
1577
+ raise "No shw tank part load curve with the name #{part_load_curve_name} could be found in the ECMS class curves.json file. Please check both the ECMS class curves.json and the measure shw_set.json files to ensure the curve is entered and referenced correctly." if existing_curve.empty?
1578
+ part_load_curve = model_add_curve(model, part_load_curve_name)
1579
+ raise "There was a problem setting the shw tank part load curve named #{part_load_curve_name} for #{component.name}. Please ensure that the curve is entered and referenced correctly in the ECMS class curves.json and shw_set.json files." unless part_load_curve
1580
+ component.setPartLoadFactorCurve(part_load_curve)
1581
+ #Get the volume and capacity of the SHW tank.
1582
+ if component.isTankVolumeAutosized
1583
+ shw_vol_gal = "auto_size"
1584
+ else
1585
+ shw_vol_m3 = component.tankVolume.to_f
1586
+ shw_vol_gal = (OpenStudio.convert(shw_vol_m3, 'm^3', 'gal').get).to_f.round(0)
1587
+ end
1588
+ if component.isHeaterMaximumCapacityAutosized
1589
+ shw_capacity_kBtu_hr = "auto_cap"
1590
+ else
1591
+ shw_capacity_W = component.heaterMaximumCapacity.to_f
1592
+ shw_capacity_kBtu_hr = (OpenStudio.convert(shw_capacity_W, 'W', 'kBtu/h').get).to_f.round(0)
1593
+ end
1594
+ # Set a default revised shw tank name if no name is present in the eff hash.
1595
+ if eff["name"].nil?
1596
+ shw_ecm_package_name = "Revised"
1597
+ else
1598
+ shw_ecm_package_name = eff["name"]
1599
+ end
1600
+ shw_name = "#{shw_vol_gal} Gal #{shw_ecm_package_name} Water Heater - #{shw_capacity_kBtu_hr}kBtu/hr #{eff["efficiency"]} Therm Eff"
1601
+ component.setName(shw_name)
1602
+ end
1603
+
1604
+ # ============================================================================================================================
1605
+ # Method to update the cop and/or the performance curves of unitary dx coils. The method input 'unitary_cop' can either be a
1606
+ # string or a hash. When it's a string it's used to find a hash in the json table 'unitary_cop_ecm'. When it's a hash it holds
1607
+ # the parameters needed to update the cop and/or the performance curves of the unitary coil.
1608
+ def modify_unitary_cop(model:, unitary_cop:,sql_db_vars_map:)
1609
+ return if (unitary_cop.nil? || (unitary_cop.to_s == "NECB_Default"))
1610
+ coils = model.getCoilCoolingDXSingleSpeeds + model.getCoilCoolingDXMultiSpeeds
1611
+ unitary_cop_copy = unitary_cop.dup
1612
+ coils.sort.each do |coil|
1613
+ coil_type = "SingleSpeed"
1614
+ coil_type = "MultiSpeed" if coil.class.name.to_s.include? 'CoilCoolingDXMultiSpeed'
1615
+ # if the parameter 'unitary_cop' is a string then get the information on the new parameters for the coils from
1616
+ # the json table 'unitary_cop_ecm'
1617
+ if unitary_cop_copy.is_a?(String)
1618
+ search_criteria = {}
1619
+ search_criteria['name'] = unitary_cop_copy
1620
+ coil_name = coil.name.to_s
1621
+ coil.setName(sql_db_vars_map[coil_name])
1622
+ if coil_type == "SingleSpeed"
1623
+ capacity_w = coil_cooling_dx_single_speed_find_capacity(coil)
1624
+ elsif coil_type == "MultiSpeed"
1625
+ capacity_w = coil_cooling_dx_multi_speed_find_capacity(coil)
1626
+ end
1627
+ coil.setName(coil_name)
1628
+ cop_package = model_find_object(@standards_data['tables']['unitary_cop_ecm'], search_criteria, capacity_w)
1629
+ raise "Cannot not find #{unitary_cop_ecm} in the ECMS unitary_acs.json file. Please check that the name is correctly spelled in the ECMS class unitary_acs.json file and in the code calling (directly or through another method) the ECMS class modify_unitary_eff method." if cop_package.empty?
1630
+ ecm_name = unitary_cop_copy
1631
+ unitary_cop = {
1632
+ "name" => ecm_name,
1633
+ "minimum_energy_efficiency_ratio" => cop_package['minimum_energy_efficiency_ratio'],
1634
+ "minimum_seasonal_energy_efficiency_ratio" => cop_package['minimum_seasonal_energy_efficiency_ratio'],
1635
+ "cool_cap_ft" => cop_package['cool_cap_ft'],
1636
+ "cool_cap_fflow" => cop_package['cool_cap_fflow'],
1637
+ "cool_eir_ft" => cop_package['cool_eir_ft'],
1638
+ "cool_eir_fflow" => cop_package['cool_eir_fflow'],
1639
+ "cool_plf_fplr" => cop_package['cool_eir_fplr']
1640
+ }
1641
+ end
1642
+ next if (unitary_cop['minimum_energy_efficiency_ratio'].nil? && unitary_cop['minimum_seasonal_energy_efficiency_ratio'].nil? && unitary_cop['cool_cap_ft'].nil? &&
1643
+ unitary_cop['cool_cap_fflow'].nil? && unitary_cop['cool_eir_ft'].nil? && unitary_cop['cool_eir_fflow'].nil? && unitary_cop['cool_plf_fplr'].nil?)
1644
+
1645
+ # If the dx coil is on an air loop then update its cop and the performance curves when these are specified in the ecm data
1646
+ if (coil_type == "SingleSpeed" && coil.airLoopHVAC.is_initialized) ||
1647
+ (coil_type == "MultiSpeed" && coil.containingHVACComponent.get.airLoopHVAC.is_initialized)
1648
+ cop = nil
1649
+ if unitary_cop['minimum_energy_efficiency_ratio']
1650
+ cop = eer_to_cop(unitary_cop['minimum_energy_efficiency_ratio'].to_f)
1651
+ elsif unitary_cop['minimum_seasonal_energy_efficiency_ratio']
1652
+ cop = seer_to_cop_cooling_with_fan(unitary_cop['minimum_seasonal_energy_efficiency_ratio'].to_f)
1653
+ end
1654
+ cool_cap_ft = nil
1655
+ cool_cap_ft = @standards_data['curves'].select { |curve| curve['name'] == unitary_cop['cool_cap_ft'] } if unitary_cop['cool_cap_ft']
1656
+ cool_cap_fflow = nil
1657
+ cool_cap_fflow = @standards_data['curves'].select { |curve| curve['name'] == unitary_cop['cool_cap_fflow'] } if unitary_cop['cool_cap_fflow']
1658
+ cool_eir_ft = nil
1659
+ cool_eir_ft = @standards_data['curves'].select { |curve| curve['name'] == unitary_cop['cool_eir_ft'] } if unitary_cop['cool_eir_ft']
1660
+ cool_eir_fflow = nil
1661
+ cool_eir_fflow = @standards_data['curves'].select { |curve| curve['name'] == unitary_cop['cool_eir_fflow'] } if unitary_cop['cool_eir_fflow']
1662
+ cool_plf_fplr = nil
1663
+ cool_plf_fplr = @standards_data['curves'].select { |curve| curve['name'] == unitary_cop['cool_plf_fplr'] } if unitary_cop['cool_plf_fplr']
1664
+ if coil_type == "SingleSpeed"
1665
+ coil.setRatedCOP(cop) if cop
1666
+ coil.setTotalCoolingCapacityFunctionOfTemperatureCurve(cool_cap_ft) if cool_cap_ft
1667
+ coil.setTotalCoolingCapacityFunctionOfFlowFractionCurve(cool_cap_fflow) if cool_cap_fflow
1668
+ coil.setEnergyInputRatioFunctionOfTemperatureCurve(cool_eir_ft) if cool_eir_ft
1669
+ coil.setEnergyInputRatioFunctionOfFlowFractionCurve(cool_eir_fflow) if cool_eir_fflow
1670
+ coil.setPartLoadFractionCorrelationCurve(cool_plf_fplr) if cool_plf_fplr
1671
+ elsif coil_type == "MultiSpeed"
1672
+ coil.stages.sort.each do |stage|
1673
+ stage.setGrossRatedCoolingCOP(cop) if cop
1674
+ stage.setTotalCoolingCapacityFunctionofTemperatureCurve(cool_cap_ft) if cool_cap_ft
1675
+ stage.setTotalCoolingCapacityFunctionofFlowFractionCurve(cool_cap_fflow) if cool_cap_fflow
1676
+ stage.setEnergyInputRatioFunctionofTemperatureCurve(cool_eir_ft) if cool_eir_ft
1677
+ stage.setEnergyInputRatioFunctionofFlowFractionCurve(cool_eir_fflow) if cool_eir_fflow
1678
+ stage.setPartLoadFractionCorrelationCurve(cool_plf_fplr) if cool_plf_fplr
1679
+ end
1680
+ end
1681
+ coil.setName("CoilCoolingDXSingleSpeed_dx-adv") if (cop && coil_type == "SingleSpeed")
1682
+ coil.setName("CoilCoolingDXMultiSpeed_dx-adv") if (cop && coil_type == "MultiSpeed")
1683
+ end
1684
+ end
1685
+ end
1686
+
1687
+ # ============================================================================================================================
1688
+ # Despite the name, this method does not actually remove any air loops. All air loops, hot water loops, cooling and
1689
+ # any existing baseboard heaters should already be gone. The name is an artifact of the way ECM methods are named and
1690
+ # used. With everything gone, this method adds a hot water loop (if required) and baseboard heating back in to all
1691
+ # zones requiring heating. Originally, code was included in the 'apply_systems' method which would prevent the air
1692
+ # loops and other stuff from being created if someone did not want them. But others felt that that was not a clear
1693
+ # way of doing things and did not feel the performance penalty of creating objects, then removing them, then creating
1694
+ # them again was significant.
1695
+ def add_ecm_remove_airloops_add_zone_baseboards(model:,system_zones_map:, system_doas_flags: nil, zone_clg_eqpt_type: nil, standard:, primary_heating_fuel:)
1696
+ # Set the primary fuel set to default to to specific fuel type.
1697
+ standards_info = standard.standards_data
1698
+
1699
+ if primary_heating_fuel == 'DefaultFuel'
1700
+ epw = BTAP::Environment::WeatherFile.new(model.weatherFile.get.path.get)
1701
+ primary_heating_fuel = standards_info['regional_fuel_use'].detect {|fuel_sources| fuel_sources['state_province_regions'].include?(epw.state_province_region)}['fueltype_set']
1702
+ end
1703
+ # Get fuelset.
1704
+ system_fuel_defaults = standards_info['fuel_type_sets'].detect {|fuel_type_set| fuel_type_set['name'] == primary_heating_fuel}
1705
+ raise("fuel_type_sets named #{primary_heating_fuel} not found in fuel_type_sets table.") if system_fuel_defaults.nil?
1706
+
1707
+
1708
+ # Assign fuel sources.
1709
+ boiler_fueltype = system_fuel_defaults['boiler_fueltype']
1710
+ baseboard_type = system_fuel_defaults['baseboard_type']
1711
+ mau_heating_coil_type = "none"
1712
+
1713
+ # Create the hot water loop if necessary.
1714
+ hw_loop = standard.create_hw_loop_if_required(baseboard_type,
1715
+ boiler_fueltype,
1716
+ mau_heating_coil_type,
1717
+ model)
1718
+
1719
+ # Add baseboard heaters to each heated zone.
1720
+ system_zones_map.sort.each do |sname,zones|
1721
+ zones.each do |zone|
1722
+ standard.add_zone_baseboards(baseboard_type: baseboard_type,
1723
+ hw_loop: hw_loop,
1724
+ model: model,
1725
+ zone: zone)
1726
+ end
1727
+ end
1728
+ end
1729
+ end