honeybee-openstudio 2.31.6 → 2.31.9

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 5b0a5a024724a6609081dcf05e2895f984636ed874dc2d0561fc99118ee5e776
4
- data.tar.gz: fab2f18b5ab801debe5c5e673f68943897e938f6a9010c7bec5661b16c622f22
3
+ metadata.gz: f9cfa9e82e9efaedde24e6ccfe30c4d7fe6cbd4259a81d36de9b8a9936b8259b
4
+ data.tar.gz: 6c47a045cf0684fdc33521ca96b6bd1fe3f27a52658fe774a6f76165ab3c87b0
5
5
  SHA512:
6
- metadata.gz: 52dd3f3163f2e2099fb58b1318b962b14224be9151929b7ad7dd5059982c8c8564fb4bbc885a556253b60b420d94bfb4bd1723385e3c48ff1079c75fa8c9532c
7
- data.tar.gz: 18a8f4fb2f6f68f637f6969af5478ef22a96fe7c3328429833bec6b24739f57022e90920f5f17358ea2b84042c91d931b26eb7d43b653f81d2b28322a1052789
6
+ metadata.gz: ceefaa71ad6fe18240c21b2738ddf5741fc9620dcf63088c67511a0fedb132f1ea063879527183624f88a196826f7a58bef62ac9211e605f815264ae3add17c4
7
+ data.tar.gz: 4b6e648afaa694daa0e2246f4f5f6cf6c5dadb714e4b4fa7681919447fa24a37cb9bba9e6edbbb77a216e04005a0d23b5da7c8f38df07c60ad2ed2543767ad7d
@@ -4,7 +4,7 @@ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
4
 
5
5
  Gem::Specification.new do |spec|
6
6
  spec.name = 'honeybee-openstudio'
7
- spec.version = '2.31.6'
7
+ spec.version = '2.31.9'
8
8
  spec.authors = ['Tanushree Charan', 'Dan Macumber', 'Chris Mackey', 'Mostapha Sadeghipour Roudsari']
9
9
  spec.email = ['tanushree.charan@nrel.gov', 'chris@ladybug.tools']
10
10
 
@@ -9,7 +9,7 @@ if allow_local && File.exist?('../openstudio-common-measures-gem')
9
9
  elsif allow_local
10
10
  gem 'openstudio-common-measures', github: 'NREL/openstudio-common-measures-gem', branch: 'develop'
11
11
  else
12
- gem 'openstudio-common-measures', '~> 0.5.0'
12
+ gem 'openstudio-common-measures', '~> 0.6.0'
13
13
  end
14
14
 
15
15
  if allow_local && File.exist?('../openstudio-model-articulation-gem')
@@ -17,7 +17,7 @@ if allow_local && File.exist?('../openstudio-model-articulation-gem')
17
17
  elsif allow_local
18
18
  gem 'openstudio-model-articulation', github: 'NREL/openstudio-model-articulation-gem', branch: 'develop'
19
19
  else
20
- gem 'openstudio-model-articulation', '0.5.0'
20
+ gem 'openstudio-model-articulation', '0.6.1'
21
21
  end
22
22
 
23
23
  if allow_local && File.exist?('../urbanopt-geojson-gem')
@@ -25,7 +25,7 @@ if allow_local && File.exist?('../urbanopt-geojson-gem')
25
25
  elsif allow_local
26
26
  gem 'urbanopt-geojson', github: 'URBANopt/urbanopt-geojson-gem', branch: 'develop'
27
27
  else
28
- gem 'urbanopt-geojson', '~> 0.7.0'
28
+ gem 'urbanopt-geojson', '~> 0.8.0'
29
29
  end
30
30
 
31
31
  if allow_local && File.exist?('../urbanopt-reporting-gem')
@@ -33,8 +33,8 @@ if allow_local && File.exist?('../urbanopt-reporting-gem')
33
33
  elsif allow_local
34
34
  gem 'urbanopt-reporting', github: 'URBANopt/urbanopt-reporting-gem', branch: 'develop'
35
35
  else
36
- gem 'urbanopt-reporting', '~> 0.5.0'
36
+ gem 'urbanopt-reporting', '~> 0.6.0'
37
37
  end
38
38
 
39
39
  # include the honeybee-openstudio-gem
40
- gem 'honeybee-openstudio', '2.28.4'
40
+ gem 'honeybee-openstudio', '2.31.7'
@@ -201,6 +201,17 @@ module Honeybee
201
201
  thermal_zone = space.thermalZone
202
202
  unless thermal_zone.empty?
203
203
  thermal_zone = space.thermalZone.get
204
+ # Create ideal_air_system if present
205
+ unless thermal_zone.equipment.nil?
206
+ thermal_zone.equipment.each do |equipment|
207
+ if equipment.to_ZoneHVACIdealLoadsAirSystem.is_initialized
208
+ ideal_air_hash = Honeybee::IdealAirSystemAbridged.from_hvac(
209
+ equipment.to_ZoneHVACIdealLoadsAirSystem.get)
210
+ $hvacs << ideal_air_hash
211
+ hash[:hvac] = ideal_air_hash[:identifier]
212
+ end
213
+ end
214
+ end
204
215
  unless thermal_zone.thermostatSetpointDualSetpoint.empty?
205
216
  hash[:setpoint] = {}
206
217
  hash[:setpoint][:type] = 'SetpointAbridged'
@@ -0,0 +1,75 @@
1
+ # *******************************************************************************
2
+ # 4ju0 d/zf OpenStudio Gem, Copyright (c) 2020, Alliance for Sustainable
3
+ # Energy, LLC, Ladybug Tools LLC and other contributors. All rights reserved.
4
+ #
5
+ # Redistribution and use in source and binary forms, with or without
6
+ # modification, are permitted provided that the following conditions are met:
7
+ #
8
+ # (1) Redistributions of source code must retain the above copyright notice,
9
+ # this list of conditions and the following disclaimer.
10
+ #
11
+ # (2) Redistributions in binary form must reproduce the above copyright notice,
12
+ # this list of conditions and the following disclaimer in the documentation
13
+ # and/or other materials provided with the distribution.
14
+ #
15
+ # (3) Neither the name of the copyright holder nor the names of any contributors
16
+ # may be used to endorse or promote products derived from this software without
17
+ # specific prior written permission from the respective party.
18
+ #
19
+ # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER(S) AND ANY CONTRIBUTORS
20
+ # "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
21
+ # THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22
+ # ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER(S), ANY CONTRIBUTORS, THE
23
+ # UNITED STATES GOVERNMENT, OR THE UNITED STATES DEPARTMENT OF ENERGY, NOR ANY OF
24
+ # THEIR EMPLOYEES, BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
25
+ # EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT
26
+ # OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
27
+ # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
28
+ # STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
29
+ # OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30
+ # *******************************************************************************
31
+
32
+ require 'honeybee/hvac/ideal_air'
33
+ require 'to_openstudio/model_object'
34
+
35
+ module Honeybee
36
+ class IdealAirSystemAbridged
37
+
38
+ def self.from_hvac(hvac)
39
+ # create an empty hash
40
+ hash = {}
41
+ hash[:type] = 'IdealAirSystemAbridged'
42
+ hash[:identifier] = clean_name(hvac.nameString)
43
+ unless hvac.displayName.empty?
44
+ hash[:display_name] = (hvac.displayName.get).force_encoding("UTF-8")
45
+ end
46
+ hash[:economizer_type] = hvac.outdoorAirEconomizerType
47
+ if hvac.demandControlledVentilationType.downcase == 'none'
48
+ hash[:demand_controlled_ventilation] = false
49
+ else
50
+ hash[:demand_controlled_ventilation] = true
51
+ end
52
+ hash[:sensible_heat_recovery] = hvac.sensibleHeatRecoveryEffectiveness
53
+ hash[:latent_heat_recovery] = hvac.latentHeatRecoveryEffectiveness
54
+ hash[:heating_air_temperature] = hvac.maximumHeatingSupplyAirTemperature
55
+ hash[:cooling_air_temperature] = hvac.minimumCoolingSupplyAirTemperature
56
+ if hvac.heatingLimit == 'NoLimit'
57
+ hash[:heating_limit] = hvac.heatingLimit
58
+ end
59
+ if hvac.coolingLimit == 'NoLimit'
60
+ hash[:cooling_limit] = hvac.coolingLimit
61
+ end
62
+ unless hvac.heatingAvailabilitySchedule.empty?
63
+ schedule = hvac.heatingAvailabilitySchedule.get
64
+ hash[:heating_availability] = schedule.nameString
65
+ end
66
+ unless hvac.coolingAvailabilitySchedule.empty?
67
+ schedule = hvac.coolingAvailabilitySchedule.get
68
+ hash[:coolingAvailabilitySchedule]
69
+ end
70
+
71
+ hash
72
+ end
73
+
74
+ end #IdealAirSystemAbridged
75
+ end #Honeybee
@@ -61,4 +61,4 @@ module Honeybee
61
61
 
62
62
 
63
63
  end #ElectricEquipmentAbridged
64
- end #Honeybee
64
+ end #Honeybee
@@ -51,6 +51,7 @@ module Honeybee
51
51
  $opaque_constructions = {}
52
52
  $window_constructions = {}
53
53
  $shade_constructions = {}
54
+ $hvacs = []
54
55
 
55
56
  hash[:properties] = properties_from_model(openstudio_model)
56
57
 
@@ -126,6 +127,7 @@ module Honeybee
126
127
  hash[:schedule_type_limits] = schedtypelimits_from_model(openstudio_model)
127
128
  hash[:schedules] = schedules_from_model(openstudio_model)
128
129
  hash[:program_types] = programtype_from_model(openstudio_model)
130
+ hash[:hvacs] = $hvacs
129
131
 
130
132
  hash
131
133
  end
@@ -81,6 +81,15 @@ module Honeybee
81
81
  hash[:day_schedules] << ScheduleRulesetAbridged.from_day_schedule(schedule_day)
82
82
  end
83
83
 
84
+ # remove the bogus default day schedule that OpenStudio adds upon import from IDF
85
+ if hash[:default_day_schedule].start_with?('Schedule Day ')
86
+ if hash[:day_schedules][0][:values] == [0] && hash[:schedule_rules].length() > 0
87
+ hash[:default_day_schedule] = hash[:schedule_rules][0][:schedule_day]
88
+ hash[:schedule_rules].pop(0)
89
+ hash[:day_schedules].pop(0)
90
+ end
91
+ end
92
+
84
93
  # assing any schedule type limits if they exist
85
94
  unless schedule_ruleset.scheduleTypeLimits.empty?
86
95
  typ_lim = schedule_ruleset.scheduleTypeLimits.get
@@ -44,6 +44,9 @@ require 'from_openstudio/geometry/face'
44
44
  require 'from_openstudio/geometry/room'
45
45
  require 'from_openstudio/geometry/shade'
46
46
 
47
+ # extend the hvac objects
48
+ require 'from_openstudio/hvac/ideal_air'
49
+
47
50
  # extend the construction objects
48
51
  require 'from_openstudio/construction/opaque'
49
52
  require 'from_openstudio/construction/window'
@@ -118,7 +118,7 @@ module Honeybee
118
118
  end
119
119
 
120
120
  # assign the construction if it exists
121
- if @hash[:properties][:energy][:construction]
121
+ if @hash[:properties].key?(:energy) && @hash[:properties][:energy][:construction]
122
122
  construction_identifier = @hash[:properties][:energy][:construction]
123
123
  construction = openstudio_model.getConstructionByName(construction_identifier)
124
124
  if !construction.empty?
@@ -182,7 +182,7 @@ module Honeybee
182
182
 
183
183
  # get the approriate construction id
184
184
  construction_id = nil
185
- if @hash[:properties][:energy][:construction]
185
+ if @hash[:properties].key?(:energy) && @hash[:properties][:energy][:construction]
186
186
  construction_id = @hash[:properties][:energy][:construction]
187
187
  else
188
188
  construction_id = 'Generic Double Pane'
@@ -118,7 +118,7 @@ module Honeybee
118
118
  end
119
119
 
120
120
  # assign the construction if it exists
121
- if @hash[:properties][:energy][:construction]
121
+ if @hash[:properties].key?(:energy) && @hash[:properties][:energy][:construction]
122
122
  construction_identifier = @hash[:properties][:energy][:construction]
123
123
  construction = openstudio_model.getConstructionByName(construction_identifier)
124
124
  if !construction.empty?
@@ -176,7 +176,7 @@ module Honeybee
176
176
 
177
177
  # get the approriate construction id
178
178
  construction_id = nil
179
- if @hash[:properties][:energy][:construction]
179
+ if @hash[:properties].key?(:energy) && @hash[:properties][:energy][:construction]
180
180
  construction_id = @hash[:properties][:energy][:construction]
181
181
  elsif @hash[:is_glass] == true
182
182
  construction_id = 'Generic Double Pane'
@@ -64,39 +64,41 @@ module Honeybee
64
64
  end
65
65
  os_surface.setSurfaceType(@hash[:face_type])
66
66
 
67
- # assign the construction if it is present
68
- if @hash[:properties][:energy][:construction]
69
- construction_identifier = @hash[:properties][:energy][:construction]
70
- construction = openstudio_model.getConstructionByName(construction_identifier)
71
- unless construction.empty?
72
- os_construction = construction.get
73
- os_surface.setConstruction(os_construction)
67
+ if @hash[:properties].key?(:energy)
68
+ # assign the construction if it is present
69
+ if @hash[:properties][:energy][:construction]
70
+ construction_identifier = @hash[:properties][:energy][:construction]
71
+ construction = openstudio_model.getConstructionByName(construction_identifier)
72
+ unless construction.empty?
73
+ os_construction = construction.get
74
+ os_surface.setConstruction(os_construction)
75
+ end
74
76
  end
75
- end
76
-
77
- # assign the AFN crack if it's specified and we are not using simple infiltration
78
- if !$use_simple_vent && @hash[:properties][:energy][:vent_crack]
79
- unless $interior_afn_srf_hash[@hash[:identifier]] # interior crack that's been accounted for
80
- vent_crack = @hash[:properties][:energy][:vent_crack]
81
- # create the crack object for using default values
82
- flow_exponent = crack_defaults[:flow_exponent][:default].to_f
83
- os_crack = OpenStudio::Model::AirflowNetworkCrack.new(
84
- openstudio_model, vent_crack[:flow_coefficient], flow_exponent,
85
- $afn_reference_crack)
86
77
 
87
- # assign the flow exponent if it's specified
88
- if vent_crack[:flow_exponent]
89
- os_crack.setAirMassFlowExponent(vent_crack[:flow_exponent])
90
- end
78
+ # assign the AFN crack if it's specified and we are not using simple infiltration
79
+ if !$use_simple_vent && @hash[:properties][:energy][:vent_crack]
80
+ unless $interior_afn_srf_hash[@hash[:identifier]] # interior crack that's been accounted for
81
+ vent_crack = @hash[:properties][:energy][:vent_crack]
82
+ # create the crack object for using default values
83
+ flow_exponent = crack_defaults[:flow_exponent][:default].to_f
84
+ os_crack = OpenStudio::Model::AirflowNetworkCrack.new(
85
+ openstudio_model, vent_crack[:flow_coefficient], flow_exponent,
86
+ $afn_reference_crack)
87
+
88
+ # assign the flow exponent if it's specified
89
+ if vent_crack[:flow_exponent]
90
+ os_crack.setAirMassFlowExponent(vent_crack[:flow_exponent])
91
+ end
91
92
 
92
- # if it's a Surface boundary condition ensure the neighbor is not written as a duplicate
93
- if @hash[:boundary_condition][:type] == 'Surface'
94
- $interior_afn_srf_hash[@hash[:boundary_condition][:boundary_condition_objects][0]] = true
95
- end
93
+ # if it's a Surface boundary condition ensure the neighbor is not written as a duplicate
94
+ if @hash[:boundary_condition][:type] == 'Surface'
95
+ $interior_afn_srf_hash[@hash[:boundary_condition][:boundary_condition_objects][0]] = true
96
+ end
96
97
 
97
- # create the AirflowNetworkSurface
98
- os_afn_srf = os_surface.getAirflowNetworkSurface(os_crack)
98
+ # create the AirflowNetworkSurface
99
+ os_afn_srf = os_surface.getAirflowNetworkSurface(os_crack)
99
100
 
101
+ end
100
102
  end
101
103
  end
102
104
 
@@ -206,7 +208,7 @@ module Honeybee
206
208
 
207
209
  # get the approriate construction id
208
210
  construction_id = nil
209
- if @hash[:properties][:energy][:construction]
211
+ if @hash[:properties].key?(:energy) && @hash[:properties][:energy][:construction]
210
212
  construction_id = @hash[:properties][:energy][:construction]
211
213
  elsif @hash[:face_type] == 'Wall'
212
214
  construction_id = 'Generic Exterior Wall'
@@ -84,26 +84,6 @@ module Honeybee
84
84
  os_thermal_zone.setDisplayName(@hash[:display_name])
85
85
  end
86
86
 
87
- # assign the programtype
88
- if @hash[:properties][:energy][:program_type]
89
- space_type = openstudio_model.getSpaceTypeByName(@hash[:properties][:energy][:program_type])
90
- unless space_type.empty?
91
- space_type_object = space_type.get
92
- os_space.setSpaceType(space_type_object)
93
- end
94
- end
95
-
96
- # assign the constructionset
97
- if @hash[:properties][:energy][:construction_set]
98
- construction_set_identifier = @hash[:properties][:energy][:construction_set]
99
- # gets default construction set assigned to room from openstudio_model
100
- construction_set = openstudio_model.getDefaultConstructionSetByName(construction_set_identifier)
101
- unless construction_set.empty?
102
- default_construction_set = construction_set.get
103
- os_space.setDefaultConstructionSet(default_construction_set)
104
- end
105
- end
106
-
107
87
  # assign the multiplier
108
88
  if @hash[:multiplier] and @hash[:multiplier] != 1
109
89
  os_thermal_zone.setMultiplier(@hash[:multiplier])
@@ -142,6 +122,28 @@ module Honeybee
142
122
  end
143
123
  os_space.setBuildingStory(story)
144
124
 
125
+ if @hash[:properties].key?(:energy)
126
+ # assign the programtype
127
+ if @hash[:properties][:energy][:program_type]
128
+ space_type = openstudio_model.getSpaceTypeByName(@hash[:properties][:energy][:program_type])
129
+ unless space_type.empty?
130
+ space_type_object = space_type.get
131
+ os_space.setSpaceType(space_type_object)
132
+ end
133
+ end
134
+
135
+ # assign the constructionset
136
+ if @hash[:properties][:energy][:construction_set]
137
+ construction_set_identifier = @hash[:properties][:energy][:construction_set]
138
+ # gets default construction set assigned to room from openstudio_model
139
+ construction_set = openstudio_model.getDefaultConstructionSetByName(construction_set_identifier)
140
+ unless construction_set.empty?
141
+ default_construction_set = construction_set.get
142
+ os_space.setDefaultConstructionSet(default_construction_set)
143
+ end
144
+ end
145
+ end
146
+
145
147
  # keep track of all window ventilation objects
146
148
  window_vent = {}
147
149
 
@@ -162,9 +164,11 @@ module Honeybee
162
164
  # assign aperture-level shades if they exist
163
165
  if face[:apertures]
164
166
  face[:apertures].each do |aperture|
165
- if aperture[:properties][:energy][:vent_opening]
166
- window_vent[aperture[:identifier]] = \
167
- [aperture[:properties][:energy][:vent_opening], aperture[:boundary_condition][:type]]
167
+ if aperture[:properties].key?(:energy)
168
+ if aperture[:properties][:energy][:vent_opening]
169
+ window_vent[aperture[:identifier]] = \
170
+ [aperture[:properties][:energy][:vent_opening], aperture[:boundary_condition][:type]]
171
+ end
168
172
  end
169
173
  if aperture[:outdoor_shades]
170
174
  unless os_shd_group
@@ -180,9 +184,11 @@ module Honeybee
180
184
  # assign door-level shades if they exist
181
185
  if face[:doors]
182
186
  face[:doors].each do |door|
183
- if door[:properties][:energy][:vent_opening]
184
- window_vent[door[:identifier]] = \
185
- [door[:properties][:energy][:vent_opening], door[:boundary_condition][:type]]
187
+ if door[:properties].key?(:energy)
188
+ if door[:properties][:energy][:vent_opening]
189
+ window_vent[door[:identifier]] = \
190
+ [door[:properties][:energy][:vent_opening], door[:boundary_condition][:type]]
191
+ end
186
192
  end
187
193
  if door[:outdoor_shades]
188
194
  unless os_shd_group
@@ -196,7 +202,7 @@ module Honeybee
196
202
  end
197
203
 
198
204
  # assign interior constructions for adiabatic Faces
199
- if !face[:properties][:energy][:construction]
205
+ if face[:properties].key?(:energy) && !face[:properties][:energy][:construction]
200
206
  if face[:boundary_condition][:type] == 'Adiabatic'
201
207
  # assign default interior construction for Adiabatic Faces
202
208
  if face[:face_type] != 'Wall'
@@ -212,7 +218,7 @@ module Honeybee
212
218
  if face[:face_type] == 'AirBoundary'
213
219
  # assign default air boundary construction for AirBoundary face types
214
220
  air_construction = closest_air_construction(openstudio_model, os_space)
215
- if !face[:properties][:energy][:construction]
221
+ if face[:properties].key?(:energy) && !face[:properties][:energy][:construction]
216
222
  unless air_construction.nil?
217
223
  os_surface.setConstruction(air_construction)
218
224
  end
@@ -256,164 +262,166 @@ module Honeybee
256
262
  end
257
263
 
258
264
  #check whether there are any load objects on the room overriding the programtype
259
- if @hash[:properties][:energy][:people]
260
- unique_program = get_unique_space_type(openstudio_model, os_space)
261
- unique_program_ppl = unique_program.people
262
- unless unique_program_ppl.empty? # remove the previous load definition
263
- unique_program_ppl[0].remove()
265
+ if @hash[:properties].key?(:energy)
266
+ if @hash[:properties][:energy][:people]
267
+ unique_program = get_unique_space_type(openstudio_model, os_space)
268
+ unique_program_ppl = unique_program.people
269
+ unless unique_program_ppl.empty? # remove the previous load definition
270
+ unique_program_ppl[0].remove()
271
+ end
272
+ custom_people = PeopleAbridged.new(@hash[:properties][:energy][:people])
273
+ os_custom_people = custom_people.to_openstudio(openstudio_model)
274
+ os_custom_people.setSpaceType(unique_program) # assign the new load definition
264
275
  end
265
- custom_people = PeopleAbridged.new(@hash[:properties][:energy][:people])
266
- os_custom_people = custom_people.to_openstudio(openstudio_model)
267
- os_custom_people.setSpaceType(unique_program) # assign the new load definition
268
- end
269
276
 
270
- # assign lighting if it exists
271
- if @hash[:properties][:energy][:lighting]
272
- unique_program = get_unique_space_type(openstudio_model, os_space)
273
- unique_program_lght = unique_program.lights
274
- unless unique_program_lght.empty? # remove the previous load definition
275
- unique_program_lght[0].remove()
277
+ # assign lighting if it exists
278
+ if @hash[:properties][:energy][:lighting]
279
+ unique_program = get_unique_space_type(openstudio_model, os_space)
280
+ unique_program_lght = unique_program.lights
281
+ unless unique_program_lght.empty? # remove the previous load definition
282
+ unique_program_lght[0].remove()
283
+ end
284
+ custom_lighting = LightingAbridged.new(@hash[:properties][:energy][:lighting])
285
+ os_custom_lighting = custom_lighting.to_openstudio(openstudio_model)
286
+ os_custom_lighting.setSpaceType(unique_program) # assign the new load definition
276
287
  end
277
- custom_lighting = LightingAbridged.new(@hash[:properties][:energy][:lighting])
278
- os_custom_lighting = custom_lighting.to_openstudio(openstudio_model)
279
- os_custom_lighting.setSpaceType(unique_program) # assign the new load definition
280
- end
281
288
 
282
- # assign electric equipment if it exists
283
- if @hash[:properties][:energy][:electric_equipment]
284
- unique_program = get_unique_space_type(openstudio_model, os_space)
285
- unique_program_ele = unique_program.electricEquipment
286
- unless unique_program_ele.empty? # remove the previous load definition
287
- unique_program_ele[0].remove()
289
+ # assign electric equipment if it exists
290
+ if @hash[:properties][:energy][:electric_equipment]
291
+ unique_program = get_unique_space_type(openstudio_model, os_space)
292
+ unique_program_ele = unique_program.electricEquipment
293
+ unless unique_program_ele.empty? # remove the previous load definition
294
+ unique_program_ele[0].remove()
295
+ end
296
+ custom_electric_equipment = ElectricEquipmentAbridged.new(@hash[:properties][:energy][:electric_equipment])
297
+ os_custom_electric_equipment = custom_electric_equipment.to_openstudio(openstudio_model)
298
+ os_custom_electric_equipment.setSpaceType(unique_program) # assign the new load definition
288
299
  end
289
- custom_electric_equipment = ElectricEquipmentAbridged.new(@hash[:properties][:energy][:electric_equipment])
290
- os_custom_electric_equipment = custom_electric_equipment.to_openstudio(openstudio_model)
291
- os_custom_electric_equipment.setSpaceType(unique_program) # assign the new load definition
292
- end
293
300
 
294
- # assign gas equipment if it exists
295
- if @hash[:properties][:energy][:gas_equipment]
296
- unique_program = get_unique_space_type(openstudio_model, os_space)
297
- unique_program_gas = unique_program.gasEquipment
298
- unless unique_program_gas.empty? # remove the previous load definition
299
- unique_program_gas[0].remove()
301
+ # assign gas equipment if it exists
302
+ if @hash[:properties][:energy][:gas_equipment]
303
+ unique_program = get_unique_space_type(openstudio_model, os_space)
304
+ unique_program_gas = unique_program.gasEquipment
305
+ unless unique_program_gas.empty? # remove the previous load definition
306
+ unique_program_gas[0].remove()
307
+ end
308
+ custom_gas_equipment = GasEquipmentAbridged.new(@hash[:properties][:energy][:gas_equipment])
309
+ os_custom_gas_equipment = custom_gas_equipment.to_openstudio(openstudio_model)
310
+ os_custom_gas_equipment.setSpaceType(unique_program) # assign the new load definition
300
311
  end
301
- custom_gas_equipment = GasEquipmentAbridged.new(@hash[:properties][:energy][:gas_equipment])
302
- os_custom_gas_equipment = custom_gas_equipment.to_openstudio(openstudio_model)
303
- os_custom_gas_equipment.setSpaceType(unique_program) # assign the new load definition
304
- end
305
312
 
306
- # assign service hot water if it exists
307
- if @hash[:properties][:energy][:service_hot_water]
308
- shw_space = ServiceHotWaterAbridged.new(@hash[:properties][:energy][:service_hot_water])
309
- os_shw_space = shw_space.to_openstudio(
310
- openstudio_model, os_space, @hash[:properties][:energy][:shw])
311
- $shw_for_plant = shw_space
312
- end
313
+ # assign service hot water if it exists
314
+ if @hash[:properties][:energy][:service_hot_water]
315
+ shw_space = ServiceHotWaterAbridged.new(@hash[:properties][:energy][:service_hot_water])
316
+ os_shw_space = shw_space.to_openstudio(
317
+ openstudio_model, os_space, @hash[:properties][:energy][:shw])
318
+ $shw_for_plant = shw_space
319
+ end
313
320
 
314
- # assign infiltration if it exists
315
- if @hash[:properties][:energy][:infiltration] && $use_simple_vent # only use infiltration with simple ventilation
316
- unique_program = get_unique_space_type(openstudio_model, os_space)
317
- unique_program_inf = unique_program.spaceInfiltrationDesignFlowRates
318
- unless unique_program_inf.empty? # remove the previous load definition
319
- unique_program_inf[0].remove()
321
+ # assign infiltration if it exists
322
+ if @hash[:properties][:energy][:infiltration] && $use_simple_vent # only use infiltration with simple ventilation
323
+ unique_program = get_unique_space_type(openstudio_model, os_space)
324
+ unique_program_inf = unique_program.spaceInfiltrationDesignFlowRates
325
+ unless unique_program_inf.empty? # remove the previous load definition
326
+ unique_program_inf[0].remove()
327
+ end
328
+ custom_infiltration = InfiltrationAbridged.new(@hash[:properties][:energy][:infiltration])
329
+ os_custom_infiltration = custom_infiltration.to_openstudio(openstudio_model)
330
+ os_custom_infiltration.setSpaceType(unique_program) # assign the new load definition
320
331
  end
321
- custom_infiltration = InfiltrationAbridged.new(@hash[:properties][:energy][:infiltration])
322
- os_custom_infiltration = custom_infiltration.to_openstudio(openstudio_model)
323
- os_custom_infiltration.setSpaceType(unique_program) # assign the new load definition
324
- end
325
332
 
326
- # assign ventilation if it exists
327
- if @hash[:properties][:energy][:ventilation]
328
- unique_program = get_unique_space_type(openstudio_model, os_space)
329
- unique_program.resetDesignSpecificationOutdoorAir()
330
- custom_ventilation = VentilationAbridged.new(@hash[:properties][:energy][:ventilation])
331
- os_custom_ventilation = custom_ventilation.to_openstudio(openstudio_model)
332
- unique_program.setDesignSpecificationOutdoorAir(os_custom_ventilation)
333
- end
333
+ # assign ventilation if it exists
334
+ if @hash[:properties][:energy][:ventilation]
335
+ unique_program = get_unique_space_type(openstudio_model, os_space)
336
+ unique_program.resetDesignSpecificationOutdoorAir()
337
+ custom_ventilation = VentilationAbridged.new(@hash[:properties][:energy][:ventilation])
338
+ os_custom_ventilation = custom_ventilation.to_openstudio(openstudio_model)
339
+ unique_program.setDesignSpecificationOutdoorAir(os_custom_ventilation)
340
+ end
334
341
 
335
- # assign setpoint if it exists
336
- if @hash[:properties][:energy][:setpoint]
337
- # thermostat object is created because heating and cooling schedule are required
338
- setpoint_thermostat_space = SetpointThermostat.new(@hash[:properties][:energy][:setpoint])
339
- os_setpoint_thermostat_space = setpoint_thermostat_space.to_openstudio(openstudio_model)
340
- #set thermostat to thermal zone
341
- os_thermal_zone.setThermostatSetpointDualSetpoint(os_setpoint_thermostat_space)
342
- # humidistat object is created if humidifying or dehumidifying schedule is specified
343
- if @hash[:properties][:energy][:setpoint][:humidifying_schedule] or @hash[:properties][:energy][:setpoint][:dehumidifying_schedule]
344
- setpoint_humidistat_space = SetpointHumidistat.new(@hash[:properties][:energy][:setpoint])
345
- os_setpoint_humidistat_space = setpoint_humidistat_space.to_openstudio(openstudio_model)
346
- os_thermal_zone.setZoneControlHumidistat(os_setpoint_humidistat_space)
342
+ # assign setpoint if it exists
343
+ if @hash[:properties][:energy][:setpoint]
344
+ # thermostat object is created because heating and cooling schedule are required
345
+ setpoint_thermostat_space = SetpointThermostat.new(@hash[:properties][:energy][:setpoint])
346
+ os_setpoint_thermostat_space = setpoint_thermostat_space.to_openstudio(openstudio_model)
347
+ #set thermostat to thermal zone
348
+ os_thermal_zone.setThermostatSetpointDualSetpoint(os_setpoint_thermostat_space)
349
+ # humidistat object is created if humidifying or dehumidifying schedule is specified
350
+ if @hash[:properties][:energy][:setpoint][:humidifying_schedule] or @hash[:properties][:energy][:setpoint][:dehumidifying_schedule]
351
+ setpoint_humidistat_space = SetpointHumidistat.new(@hash[:properties][:energy][:setpoint])
352
+ os_setpoint_humidistat_space = setpoint_humidistat_space.to_openstudio(openstudio_model)
353
+ os_thermal_zone.setZoneControlHumidistat(os_setpoint_humidistat_space)
354
+ end
347
355
  end
348
- end
349
356
 
350
- # assign daylight control if it exists
351
- if @hash[:properties][:energy][:daylighting_control]
352
- dl_control = DaylightingControl.new(@hash[:properties][:energy][:daylighting_control])
353
- os_dl_control = dl_control.to_openstudio(openstudio_model, os_thermal_zone, os_space)
354
- end
357
+ # assign daylight control if it exists
358
+ if @hash[:properties][:energy][:daylighting_control]
359
+ dl_control = DaylightingControl.new(@hash[:properties][:energy][:daylighting_control])
360
+ os_dl_control = dl_control.to_openstudio(openstudio_model, os_thermal_zone, os_space)
361
+ end
355
362
 
356
- # assign window ventilation objects if they exist
357
- if $use_simple_vent && !window_vent.empty? # write simple WindAndStack ventilation
358
- window_vent.each do |sub_f_id, open_prop|
359
- opening = open_prop[0]
360
- bc = open_prop[1]
361
- if bc == 'Outdoors'
363
+ # assign window ventilation objects if they exist
364
+ if $use_simple_vent && !window_vent.empty? # write simple WindAndStack ventilation
365
+ window_vent.each do |sub_f_id, open_prop|
366
+ opening = open_prop[0]
367
+ bc = open_prop[1]
368
+ if bc == 'Outdoors'
369
+ opt_sub_f = openstudio_model.getSubSurfaceByName(sub_f_id)
370
+ unless opt_sub_f.empty?
371
+ sub_f = opt_sub_f.get
372
+ vent_open = VentilationOpening.new(opening)
373
+ os_vent_open = vent_open.to_openstudio(
374
+ openstudio_model, sub_f, @hash[:properties][:energy][:window_vent_control])
375
+ os_vent_open.addToThermalZone(os_thermal_zone)
376
+ end
377
+ end
378
+ end
379
+ elsif !$use_simple_vent # we're using the AFN!
380
+ # write an AirflowNetworkZone object in for the Room
381
+ os_afn_room_node = os_thermal_zone.getAirflowNetworkZone
382
+ os_afn_room_node.setVentilationControlMode('NoVent')
383
+ # write the opening objects for each Aperture / Door
384
+ operable_subfs = [] # collect the sub-face objects for the EMS
385
+ opening_factors = [] # collect the maximum opening factors for the EMS
386
+ window_vent.each do |sub_f_id, open_prop|
387
+ opening = open_prop[0]
362
388
  opt_sub_f = openstudio_model.getSubSurfaceByName(sub_f_id)
363
389
  unless opt_sub_f.empty?
364
390
  sub_f = opt_sub_f.get
365
- vent_open = VentilationOpening.new(opening)
366
- os_vent_open = vent_open.to_openstudio(
367
- openstudio_model, sub_f, @hash[:properties][:energy][:window_vent_control])
368
- os_vent_open.addToThermalZone(os_thermal_zone)
369
- end
370
- end
371
- end
372
- elsif !$use_simple_vent # we're using the AFN!
373
- # write an AirflowNetworkZone object in for the Room
374
- os_afn_room_node = os_thermal_zone.getAirflowNetworkZone
375
- os_afn_room_node.setVentilationControlMode('NoVent')
376
- # write the opening objects for each Aperture / Door
377
- operable_subfs = [] # collect the sub-face objects for the EMS
378
- opening_factors = [] # collect the maximum opening factors for the EMS
379
- window_vent.each do |sub_f_id, open_prop|
380
- opening = open_prop[0]
381
- opt_sub_f = openstudio_model.getSubSurfaceByName(sub_f_id)
382
- unless opt_sub_f.empty?
383
- sub_f = opt_sub_f.get
384
- if sub_f.adjacentSubSurface.empty? # not an interior window that's already in the AFN
385
- vent_open = VentilationOpening.new(opening)
386
- open_fac = vent_open.to_openstudio_afn(openstudio_model, sub_f)
387
- unless open_fac.nil? # nil is used for horizontal exterior skylights
388
- operable_subfs << sub_f
389
- opening_factors << open_fac
391
+ if sub_f.adjacentSubSurface.empty? # not an interior window that's already in the AFN
392
+ vent_open = VentilationOpening.new(opening)
393
+ open_fac = vent_open.to_openstudio_afn(openstudio_model, sub_f)
394
+ unless open_fac.nil? # nil is used for horizontal exterior skylights
395
+ operable_subfs << sub_f
396
+ opening_factors << open_fac
397
+ end
390
398
  end
391
399
  end
392
400
  end
401
+ # add the control startegy of the ventilation openings using the EMS
402
+ if @hash[:properties][:energy][:window_vent_control]
403
+ vent_control = VentilationControlAbridged.new(@hash[:properties][:energy][:window_vent_control])
404
+ vent_control.to_openstudio(
405
+ openstudio_model, os_thermal_zone, operable_subfs, opening_factors)
406
+ end
393
407
  end
394
- # add the control startegy of the ventilation openings using the EMS
395
- if @hash[:properties][:energy][:window_vent_control]
396
- vent_control = VentilationControlAbridged.new(@hash[:properties][:energy][:window_vent_control])
397
- vent_control.to_openstudio(
398
- openstudio_model, os_thermal_zone, operable_subfs, opening_factors)
399
- end
400
- end
401
408
 
402
- # assign any internal masses if specified
403
- if @hash[:properties][:energy][:internal_masses]
404
- @hash[:properties][:energy][:internal_masses].each do |int_mass|
405
- hb_int_mass = InternalMassAbridged.new(int_mass)
406
- os_int_mass = hb_int_mass.to_openstudio(openstudio_model, os_space)
407
- os_int_mass.setSpace(os_space)
409
+ # assign any internal masses if specified
410
+ if @hash[:properties][:energy][:internal_masses]
411
+ @hash[:properties][:energy][:internal_masses].each do |int_mass|
412
+ hb_int_mass = InternalMassAbridged.new(int_mass)
413
+ os_int_mass = hb_int_mass.to_openstudio(openstudio_model, os_space)
414
+ os_int_mass.setSpace(os_space)
415
+ end
408
416
  end
409
- end
410
417
 
411
- # assign any process loads if specified
412
- if @hash[:properties][:energy][:process_loads]
413
- @hash[:properties][:energy][:process_loads].each do |p_load|
414
- hb_p_load = ProcessAbridged.new(p_load)
415
- os_p_load = hb_p_load.to_openstudio(openstudio_model)
416
- os_p_load.setSpace(os_space)
418
+ # assign any process loads if specified
419
+ if @hash[:properties][:energy][:process_loads]
420
+ @hash[:properties][:energy][:process_loads].each do |p_load|
421
+ hb_p_load = ProcessAbridged.new(p_load)
422
+ os_p_load = hb_p_load.to_openstudio(openstudio_model)
423
+ os_p_load.setSpace(os_space)
424
+ end
417
425
  end
418
426
  end
419
427
 
@@ -61,23 +61,26 @@ module Honeybee
61
61
  unless @hash[:display_name].nil?
62
62
  os_shading_surface.setDisplayName(@hash[:display_name])
63
63
  end
64
- # assign the construction if it exists
65
- if @hash[:properties][:energy][:construction]
66
- construction_identifier = @hash[:properties][:energy][:construction]
67
- construction = openstudio_model.getConstructionByName(construction_identifier)
68
- unless construction.empty?
69
- os_construction = construction.get
70
- os_shading_surface.setConstruction(os_construction)
64
+
65
+ if @hash[:properties].key?(:energy)
66
+ # assign the construction if it exists
67
+ if @hash[:properties][:energy][:construction]
68
+ construction_identifier = @hash[:properties][:energy][:construction]
69
+ construction = openstudio_model.getConstructionByName(construction_identifier)
70
+ unless construction.empty?
71
+ os_construction = construction.get
72
+ os_shading_surface.setConstruction(os_construction)
73
+ end
71
74
  end
72
- end
73
75
 
74
- # assign the transmittance schedule if it exists
75
- if @hash[:properties][:energy][:transmittance_schedule]
76
- schedule_identifier = @hash[:properties][:energy][:transmittance_schedule]
77
- schedule = openstudio_model.getScheduleByName(schedule_identifier)
78
- unless schedule.empty?
79
- os_schedule = schedule.get
80
- os_shading_surface.setTransmittanceSchedule(os_schedule)
76
+ # assign the transmittance schedule if it exists
77
+ if @hash[:properties][:energy][:transmittance_schedule]
78
+ schedule_identifier = @hash[:properties][:energy][:transmittance_schedule]
79
+ schedule = openstudio_model.getScheduleByName(schedule_identifier)
80
+ unless schedule.empty?
81
+ os_schedule = schedule.get
82
+ os_shading_surface.setTransmittanceSchedule(os_schedule)
83
+ end
81
84
  end
82
85
  end
83
86
 
@@ -109,7 +109,7 @@ module Honeybee
109
109
 
110
110
  # initialize a global variable for whether the AFN is used instead of simple ventilation
111
111
  $use_simple_vent = true
112
- if @hash[:properties][:energy][:ventilation_simulation_control]
112
+ if @hash[:properties].key?(:energy) && @hash[:properties][:energy][:ventilation_simulation_control]
113
113
  vent_sim_control = @hash[:properties][:energy][:ventilation_simulation_control]
114
114
  if vent_sim_control[:vent_control_type] && vent_sim_control[:vent_control_type] != 'SingleZone'
115
115
  $use_simple_vent = false
@@ -129,42 +129,44 @@ module Honeybee
129
129
  $shw_for_plant = nil # track whether a hot water plant is needed
130
130
 
131
131
  # create all of the non-geometric model elements
132
- if log_report # schedules are used by all other objects and come first
133
- puts 'Translating Schedules'
134
- end
135
- if @hash[:properties][:energy][:schedule_type_limits]
136
- create_schedule_type_limits(@hash[:properties][:energy][:schedule_type_limits])
137
- end
138
- if @hash[:properties][:energy][:schedules]
139
- create_schedules(@hash[:properties][:energy][:schedules], false, true)
140
- end
132
+ if @hash[:properties].key?(:energy)
133
+ if log_report # schedules are used by all other objects and come first
134
+ puts 'Translating Schedules'
135
+ end
136
+ if @hash[:properties][:energy][:schedule_type_limits]
137
+ create_schedule_type_limits(@hash[:properties][:energy][:schedule_type_limits])
138
+ end
139
+ if @hash[:properties][:energy][:schedules]
140
+ create_schedules(@hash[:properties][:energy][:schedules], false, true)
141
+ end
141
142
 
142
- if log_report
143
- puts 'Translating Materials'
144
- end
145
- if @hash[:properties][:energy][:materials]
146
- create_materials(@hash[:properties][:energy][:materials])
147
- end
143
+ if log_report
144
+ puts 'Translating Materials'
145
+ end
146
+ if @hash[:properties][:energy][:materials]
147
+ create_materials(@hash[:properties][:energy][:materials])
148
+ end
148
149
 
149
- if log_report
150
- puts 'Translating Constructions'
151
- end
152
- if @hash[:properties][:energy][:constructions]
153
- create_constructions(@hash[:properties][:energy][:constructions])
154
- end
150
+ if log_report
151
+ puts 'Translating Constructions'
152
+ end
153
+ if @hash[:properties][:energy][:constructions]
154
+ create_constructions(@hash[:properties][:energy][:constructions])
155
+ end
155
156
 
156
- if log_report
157
- puts 'Translating ConstructionSets'
158
- end
159
- if @hash[:properties][:energy][:construction_sets]
160
- create_construction_sets(@hash[:properties][:energy][:construction_sets])
161
- end
157
+ if log_report
158
+ puts 'Translating ConstructionSets'
159
+ end
160
+ if @hash[:properties][:energy][:construction_sets]
161
+ create_construction_sets(@hash[:properties][:energy][:construction_sets])
162
+ end
162
163
 
163
- if log_report
164
- puts 'Translating ProgramTypes'
165
- end
166
- if @hash[:properties][:energy][:program_types]
167
- create_program_types(@hash[:properties][:energy][:program_types])
164
+ if log_report
165
+ puts 'Translating ProgramTypes'
166
+ end
167
+ if @hash[:properties][:energy][:program_types]
168
+ create_program_types(@hash[:properties][:energy][:program_types])
169
+ end
168
170
  end
169
171
 
170
172
  # create the default construction set to catch any cases of unassigned constructions
@@ -196,8 +198,10 @@ module Honeybee
196
198
  if log_report
197
199
  puts 'Translating HVAC Systems'
198
200
  end
199
- create_hvacs
200
- create_hot_water_plant
201
+ if @hash[:properties].key?(:energy)
202
+ create_hvacs
203
+ create_hot_water_plant
204
+ end
201
205
 
202
206
  if log_report
203
207
  puts 'Translating Context Shade Geometry'
@@ -445,32 +449,34 @@ module Honeybee
445
449
  openstudio_room = room_object.to_openstudio(@openstudio_model)
446
450
 
447
451
  # for rooms with hot water objects definied in the ProgramType, make a new WaterUse:Equipment
448
- if room[:properties][:energy][:program_type] && !room[:properties][:energy][:service_hot_water]
449
- program_type_id = room[:properties][:energy][:program_type]
450
- shw_hash = $programtype_shw_hash[program_type_id]
451
- unless shw_hash.nil?
452
- shw_object = ServiceHotWaterAbridged.new(shw_hash)
453
- openstudio_shw = shw_object.to_openstudio(
454
- @openstudio_model, openstudio_room, room[:properties][:energy][:shw])
455
- $shw_for_plant = shw_object
452
+ if room[:properties].key?(:energy)
453
+ if room[:properties][:energy][:program_type] && !room[:properties][:energy][:service_hot_water]
454
+ program_type_id = room[:properties][:energy][:program_type]
455
+ shw_hash = $programtype_shw_hash[program_type_id]
456
+ unless shw_hash.nil?
457
+ shw_object = ServiceHotWaterAbridged.new(shw_hash)
458
+ openstudio_shw = shw_object.to_openstudio(
459
+ @openstudio_model, openstudio_room, room[:properties][:energy][:shw])
460
+ $shw_for_plant = shw_object
461
+ end
456
462
  end
457
- end
458
463
 
459
- # for rooms with setpoint objects defined in the ProgramType, make a new thermostat
460
- if room[:properties][:energy][:program_type] && !room[:properties][:energy][:setpoint]
461
- thermal_zone = openstudio_room.thermalZone()
462
- unless thermal_zone.empty?
463
- thermal_zone_object = thermal_zone.get
464
- program_type_id = room[:properties][:energy][:program_type]
465
- setpoint_hash = $programtype_setpoint_hash[program_type_id]
466
- unless setpoint_hash.nil? # program type has no setpoint
467
- thermostat_object = SetpointThermostat.new(setpoint_hash)
468
- openstudio_thermostat = thermostat_object.to_openstudio(@openstudio_model)
469
- thermal_zone_object.setThermostatSetpointDualSetpoint(openstudio_thermostat)
470
- if setpoint_hash[:humidifying_schedule] or setpoint_hash[:dehumidifying_schedule]
471
- humidistat_object = SetpointHumidistat.new(setpoint_hash)
472
- openstudio_humidistat = humidistat_object.to_openstudio(@openstudio_model)
473
- thermal_zone_object.setZoneControlHumidistat(openstudio_humidistat)
464
+ # for rooms with setpoint objects defined in the ProgramType, make a new thermostat
465
+ if room[:properties][:energy][:program_type] && !room[:properties][:energy][:setpoint]
466
+ thermal_zone = openstudio_room.thermalZone()
467
+ unless thermal_zone.empty?
468
+ thermal_zone_object = thermal_zone.get
469
+ program_type_id = room[:properties][:energy][:program_type]
470
+ setpoint_hash = $programtype_setpoint_hash[program_type_id]
471
+ unless setpoint_hash.nil? # program type has no setpoint
472
+ thermostat_object = SetpointThermostat.new(setpoint_hash)
473
+ openstudio_thermostat = thermostat_object.to_openstudio(@openstudio_model)
474
+ thermal_zone_object.setThermostatSetpointDualSetpoint(openstudio_thermostat)
475
+ if setpoint_hash[:humidifying_schedule] or setpoint_hash[:dehumidifying_schedule]
476
+ humidistat_object = SetpointHumidistat.new(setpoint_hash)
477
+ openstudio_humidistat = humidistat_object.to_openstudio(@openstudio_model)
478
+ thermal_zone_object.setZoneControlHumidistat(openstudio_humidistat)
479
+ end
474
480
  end
475
481
  end
476
482
  end
@@ -156,14 +156,19 @@ module Honeybee
156
156
  end
157
157
 
158
158
  # use the average of design day temperatures to set the water mains temperature
159
- os_water_mains = @openstudio_model.getSiteWaterMainsTemperature
160
- os_water_mains.setCalculationMethod('Correlation')
161
- if db_temps.length > 0
162
- os_water_mains.setAnnualAverageOutdoorAirTemperature((db_temps.max + db_temps.min) / 2)
163
- else # just use some dummy values so that the simulation does not fail
164
- os_water_mains.setAnnualAverageOutdoorAirTemperature(12)
159
+ os_water_mains = @openstudio_model.getSiteWaterMainsTemperature
160
+ os_version_water_fix = OpenStudio::VersionString.new(3, 4)
161
+ if @openstudio_model.version() >= os_version_water_fix
162
+ os_water_mains.setCalculationMethod('CorrelationFromWeatherFile')
163
+ else
164
+ os_water_mains.setCalculationMethod('Correlation')
165
+ if db_temps.length > 0
166
+ os_water_mains.setAnnualAverageOutdoorAirTemperature((db_temps.max + db_temps.min) / 2)
167
+ else # just use some dummy values so that the simulation does not fail
168
+ os_water_mains.setAnnualAverageOutdoorAirTemperature(12)
169
+ end
170
+ os_water_mains.setMaximumDifferenceInMonthlyAverageOutdoorAirTemperatures(4)
165
171
  end
166
- os_water_mains.setMaximumDifferenceInMonthlyAverageOutdoorAirTemperatures(4)
167
172
 
168
173
  # set the climate zone from design days assuming 0.4% extremes and normal distribution
169
174
  climate_zone_objs = @openstudio_model.getClimateZones
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: honeybee-openstudio
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.31.6
4
+ version: 2.31.9
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tanushree Charan
@@ -11,7 +11,7 @@ authors:
11
11
  autorequire:
12
12
  bindir: exe
13
13
  cert_chain: []
14
- date: 2022-04-29 00:00:00.000000000 Z
14
+ date: 2022-05-26 00:00:00.000000000 Z
15
15
  dependencies:
16
16
  - !ruby/object:Gem::Dependency
17
17
  name: bundler
@@ -177,6 +177,7 @@ files:
177
177
  - lib/from_openstudio/geometry/face.rb
178
178
  - lib/from_openstudio/geometry/room.rb
179
179
  - lib/from_openstudio/geometry/shade.rb
180
+ - lib/from_openstudio/hvac/ideal_air.rb
180
181
  - lib/from_openstudio/load/daylight.rb
181
182
  - lib/from_openstudio/load/electric_equipment.rb
182
183
  - lib/from_openstudio/load/gas_equipment.rb