honeybee-openstudio 2.22.2 → 2.23.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (34) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile +1 -1
  3. data/honeybee-openstudio.gemspec +4 -4
  4. data/lib/from_openstudio/construction/air.rb +2 -2
  5. data/lib/from_openstudio/construction/opaque.rb +2 -2
  6. data/lib/from_openstudio/construction/shade.rb +2 -2
  7. data/lib/from_openstudio/construction/window.rb +2 -2
  8. data/lib/from_openstudio/construction_set.rb +14 -14
  9. data/lib/from_openstudio/geometry/aperture.rb +1 -1
  10. data/lib/from_openstudio/geometry/door.rb +1 -1
  11. data/lib/from_openstudio/geometry/face.rb +1 -1
  12. data/lib/from_openstudio/geometry/room.rb +1 -1
  13. data/lib/from_openstudio/geometry/shade.rb +1 -1
  14. data/lib/from_openstudio/material/opaque.rb +1 -1
  15. data/lib/from_openstudio/material/opaque_no_mass.rb +1 -1
  16. data/lib/from_openstudio/material/window_blind.rb +1 -1
  17. data/lib/from_openstudio/material/window_gas.rb +1 -1
  18. data/lib/from_openstudio/material/window_gas_custom.rb +1 -1
  19. data/lib/from_openstudio/material/window_gas_mixture.rb +1 -1
  20. data/lib/from_openstudio/material/window_glazing.rb +1 -1
  21. data/lib/from_openstudio/material/window_simpleglazsys.rb +1 -1
  22. data/lib/from_openstudio/model.rb +25 -0
  23. data/lib/from_openstudio/schedule/ruleset.rb +114 -0
  24. data/lib/from_openstudio/schedule/type_limit.rb +63 -0
  25. data/lib/from_openstudio.rb +5 -1
  26. data/lib/honeybee/_defaults/energy_default.json +8 -2
  27. data/lib/honeybee/model.rb +1 -0
  28. data/lib/honeybee/model_object.rb +11 -3
  29. data/lib/measures/from_honeybee_model_to_gbxml/measure.rb +1 -0
  30. data/lib/to_openstudio/construction/window.rb +18 -9
  31. data/lib/to_openstudio/geometry/face.rb +1 -1
  32. data/lib/to_openstudio/geometry/room.rb +12 -2
  33. data/lib/to_openstudio/ventcool/opening.rb +51 -25
  34. metadata +10 -8
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 5392435198119a686f3699148121914e8bd91ce5664c5b6499b9c992718655ae
4
- data.tar.gz: 41671a1887d378797a955d26d48211476754dcf31f178fa13ba8689a62e50826
3
+ metadata.gz: 8b1713bd43ce02933e6b62917cfd588f51b34474ab42cc964fac0707892ef6cb
4
+ data.tar.gz: 1b63c7e6ef5ef775b1c6312170fc11cb2117685141e6e6c00d39bc14a4dcb7e9
5
5
  SHA512:
6
- metadata.gz: 486f13b92b50320910c4612c91fa6baf1050f618e844253a3462652d969878cbb99dd67c31569eda343467dc29d10d969d88f626c49d814e4fcc96805ab60780
7
- data.tar.gz: e7baa65945989b5c72169530e40529a7ed2a598980ca3176c51c3fed079f75467353d408e605ae5b47e9a9566147b7ce1006346e9e8d4f3740c03f9cef9a7fff
6
+ metadata.gz: b2ce15cb4c8761569e16fae90f1a378a34d4a662abe027458714ed2c11004e84d833dec91ab7795d14d019ada20803a96969ac08c9eb0e8b8f9f725d60911fd5
7
+ data.tar.gz: 2ed1a4870310d697989c9af03079522af38459cba61280b2053e8b2e59cade74318e5ec43380ca85512ec74258d02b2f13305206c2a3a24e97395de428a95266
data/Gemfile CHANGED
@@ -7,7 +7,7 @@ gemspec
7
7
  if File.exist?('../OpenStudio-extension-gem') # local development copy
8
8
  gem 'openstudio-extension', path: '../OpenStudio-extension-gem'
9
9
  else # get it from rubygems.org
10
- gem 'openstudio-extension', '0.4.2'
10
+ gem 'openstudio-extension', '0.4.3'
11
11
  end
12
12
 
13
13
  # coveralls gem is used to generate coverage reports through CI
@@ -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.22.2'
7
+ spec.version = '2.23.0'
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
 
@@ -29,10 +29,10 @@ Gem::Specification.new do |spec|
29
29
  spec.add_development_dependency "json-schema", "~> 2.8.1"
30
30
  spec.add_development_dependency "rake", "~> 13.0"
31
31
  spec.add_development_dependency "rspec", "~> 3.9"
32
- spec.add_development_dependency "rubocop", "~> 0.54.0"
32
+ spec.add_development_dependency "rubocop", "~> 1.15.0"
33
33
  end
34
34
 
35
35
  spec.add_dependency 'json_pure'
36
- spec.add_dependency 'openstudio-extension', '0.4.2'
37
- spec.add_dependency 'openstudio-standards', '~> 0.2.13'
36
+ spec.add_dependency 'openstudio-extension', '0.4.3'
37
+ spec.add_dependency 'openstudio-standards', '~> 0.2.14'
38
38
  end
@@ -40,11 +40,11 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'AirBoundaryConstructionAbridged'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = construction.nameString
43
+ hash[:identifier] = clean_name(construction.nameString)
44
44
  # check if boost optional object is empty
45
45
  unless construction.simpleMixingSchedule.empty?
46
46
  schedule = construction.simpleMixingSchedule.get
47
- hash[:air_mixing_schedule] = schedule.nameString
47
+ hash[:air_mixing_schedule] = clean_name(schedule.nameString)
48
48
  end
49
49
  #TODO: Add air_mixing_per_area
50
50
 
@@ -40,12 +40,12 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'OpaqueConstructionAbridged'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = construction.nameString
43
+ hash[:identifier] = clean_name(construction.nameString)
44
44
  hash[:materials] = []
45
45
  # get construction layers
46
46
  layers = construction.layers
47
47
  layers.each do |layer|
48
- name = layer.nameString
48
+ name = clean_name(layer.nameString)
49
49
  hash[:materials] << name
50
50
  end
51
51
 
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'ShadeConstruction'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = construction.nameString
43
+ hash[:identifier] = clean_name(construction.nameString)
44
44
  # get outermost construction layers
45
45
  layer = construction.layers[0]
46
46
  if layer.to_StandardGlazing.is_initialized
@@ -61,7 +61,7 @@ module Honeybee
61
61
  hash[:solar_reflectance] = layer.solarReflectance.get
62
62
  end
63
63
  unless layer.visibleReflectance.empty?
64
- hash[:visible_reflectance] = layer.visibleReflectance
64
+ hash[:visible_reflectance] = layer.visibleReflectance.get
65
65
  end
66
66
  elsif layer.to_MasslessOpaqueMaterial.is_initialized
67
67
  layer = layer.to_MasslessOpaqueMaterial.get
@@ -40,12 +40,12 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'WindowConstructionAbridged'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = construction.nameString
43
+ hash[:identifier] = clean_name(construction.nameString)
44
44
  hash[:materials] = []
45
45
  # get construction layers
46
46
  layers = construction.layers
47
47
  layers.each do |layer|
48
- name = layer.nameString
48
+ name = clean_name(layer.nameString)
49
49
  hash[:materials] << name
50
50
  end
51
51
 
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'ConstructionSetAbridged'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = construction_set.nameString
43
+ hash[:identifier] = clean_name(construction_set.nameString)
44
44
  hash[:wall_set] = {}
45
45
  hash[:floor_set] = {}
46
46
  hash[:aperture_set] = {}
@@ -53,17 +53,17 @@ module Honeybee
53
53
  # get interior wall construction
54
54
  unless int_surf_construction.wallConstruction.empty?
55
55
  int_wall_const = int_surf_construction.wallConstruction.get
56
- hash[:wall_set][:interior_construction] = int_wall_const.nameString
56
+ hash[:wall_set][:interior_construction] = clean_name(int_wall_const.nameString)
57
57
  end
58
58
  # get interior floor construction
59
59
  unless int_surf_construction.floorConstruction.empty?
60
60
  int_floor_const = int_surf_construction.floorConstruction.get
61
- hash[:floor_set][:interior_construction] = int_floor_const.nameString
61
+ hash[:floor_set][:interior_construction] = clean_name(int_floor_const.nameString)
62
62
  end
63
63
  # get interior roofceiling construction
64
64
  unless int_surf_construction.roofCeilingConstruction.empty?
65
65
  int_roof_const = int_surf_construction.roofCeilingConstruction.get
66
- hash[:roof_ceiling_set][:interior_construction] = int_roof_const.nameString
66
+ hash[:roof_ceiling_set][:interior_construction] = clean_name(int_roof_const.nameString)
67
67
  end
68
68
  end
69
69
 
@@ -72,17 +72,17 @@ module Honeybee
72
72
  int_subsurf_const = construction_set.defaultInteriorSubSurfaceConstructions.get
73
73
  unless int_subsurf_const.fixedWindowConstruction.empty?
74
74
  int_wind_const = int_subsurf_const.fixedWindowConstruction.get
75
- hash[:aperture_set][:window_construction] = int_wind_const.nameString
75
+ hash[:aperture_set][:window_construction] = clean_name(int_wind_const.nameString)
76
76
  end
77
77
  # get interior door construction
78
78
  unless int_subsurf_const.doorConstruction.empty?
79
79
  int_door_const = int_subsurf_const.doorConstruction.get
80
- hash[:door_set][:interior_construction] = int_door_const.nameString
80
+ hash[:door_set][:interior_construction] = clean_name(int_door_const.nameString)
81
81
  end
82
82
  # get interior glass door construction
83
83
  unless int_subsurf_const.glassDoorConstruction.empty?
84
84
  int_glass_door_const = int_subsurf_const.glassDoorConstruction.get
85
- hash[:door_set][:interior_glass_construction] = int_glass_door_const.nameString
85
+ hash[:door_set][:interior_glass_construction] = clean_name(int_glass_door_const.nameString)
86
86
  end
87
87
  end
88
88
 
@@ -92,17 +92,17 @@ module Honeybee
92
92
  # get exterior wall construction
93
93
  unless ext_surf_const.wallConstruction.empty?
94
94
  ext_wall_const = ext_surf_const.wallConstruction.get
95
- hash[:wall_set][:exterior_construction] = ext_wall_const.nameString
95
+ hash[:wall_set][:exterior_construction] = clean_name(ext_wall_const.nameString)
96
96
  end
97
97
  # get exterior floor construction
98
98
  unless ext_surf_const.floorConstruction.empty?
99
99
  ext_floor_const = ext_surf_const.floorConstruction.get
100
- hash[:floor_set][:exterior_construction] = ext_floor_const.nameString
100
+ hash[:floor_set][:exterior_construction] = clean_name(ext_floor_const.nameString)
101
101
  end
102
102
  # get exterior roofceiling construction
103
103
  unless ext_surf_const.roofCeilingConstruction.empty?
104
104
  ext_roof_const = ext_surf_const.roofCeilingConstruction.get
105
- hash[:roof_ceiling_set][:exterior_construction] = ext_roof_const.nameString
105
+ hash[:roof_ceiling_set][:exterior_construction] = clean_name(ext_roof_const.nameString)
106
106
  end
107
107
  end
108
108
 
@@ -112,22 +112,22 @@ module Honeybee
112
112
  # get exterior operable window construction
113
113
  unless ext_subsurf_const.operableWindowConstruction.empty?
114
114
  ext_wind_const = ext_subsurf_const.operableWindowConstruction.get
115
- hash[:aperture_set][:operable_construction] = ext_wind_const.nameString
115
+ hash[:aperture_set][:operable_construction] = clean_name(ext_wind_const.nameString)
116
116
  end
117
117
  # get exterior skylight construction
118
118
  unless ext_subsurf_const.skylightConstruction.empty?
119
119
  ext_skylight_const = ext_subsurf_const.skylightConstruction.get
120
- hash[:aperture_set][:skylight_construction] = ext_skylight_const.nameString
120
+ hash[:aperture_set][:skylight_construction] = clean_name(ext_skylight_const.nameString)
121
121
  end
122
122
  # get exterior door construction
123
123
  unless ext_subsurf_const.doorConstruction.empty?
124
124
  ext_door_const = ext_subsurf_const.doorConstruction.get
125
- hash[:door_set][:exterior_construction] = ext_door_const.nameString
125
+ hash[:door_set][:exterior_construction] = clean_name(ext_door_const.nameString)
126
126
  end
127
127
  # get exterior overhead door construction
128
128
  unless ext_subsurf_const.overheadDoorConstruction.empty?
129
129
  ext_ovhd_door_const = ext_subsurf_const.overheadDoorConstruction.get
130
- hash[:door_set][:overhead_construction] = ext_ovhd_door_const.nameString
130
+ hash[:door_set][:overhead_construction] = clean_name(ext_ovhd_door_const.nameString)
131
131
  end
132
132
  end
133
133
 
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'Aperture'
42
42
  hash[:identifier] = clean_identifier(sub_surface.nameString)
43
- hash[:display_name] = clean_display_name(sub_surface.nameString)
43
+ hash[:display_name] = clean_name(sub_surface.nameString)
44
44
  hash[:user_data] = {handle: sub_surface.handle.to_s}
45
45
  hash[:properties] = properties_from_sub_surface(sub_surface)
46
46
  hash[:geometry] = geometry_from_sub_surface(sub_surface, site_transformation)
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'Door'
42
42
  hash[:identifier] = clean_identifier(sub_surface.nameString)
43
- hash[:display_name] = clean_display_name(sub_surface.nameString)
43
+ hash[:display_name] = clean_name(sub_surface.nameString)
44
44
  hash[:user_data] = {handle: sub_surface.handle.to_s}
45
45
  hash[:properties] = properties_from_sub_surface(sub_surface)
46
46
  hash[:geometry] = geometry_from_sub_surface(sub_surface, site_transformation)
@@ -38,7 +38,7 @@ module Honeybee
38
38
  hash = {}
39
39
  hash[:type] = 'Face'
40
40
  hash[:identifier] = clean_identifier(surface.nameString)
41
- hash[:display_name] = clean_display_name(surface.nameString)
41
+ hash[:display_name] = clean_name(surface.nameString)
42
42
  hash[:user_data] = {handle: surface.handle.to_s}
43
43
  hash[:properties] = properties_from_surface(surface)
44
44
  hash[:geometry] = geometry_from_surface(surface, site_transformation)
@@ -38,7 +38,7 @@ module Honeybee
38
38
  hash = {}
39
39
  hash[:type] = 'Room'
40
40
  hash[:identifier] = clean_identifier(space.nameString)
41
- hash[:display_name] = clean_display_name(space.nameString)
41
+ hash[:display_name] = clean_name(space.nameString)
42
42
  hash[:user_data] = {space: space.handle.to_s}
43
43
  hash[:properties] = properties_from_space(space)
44
44
 
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'Shade'
42
42
  hash[:identifier] = clean_identifier(shading_surface.nameString)
43
- hash[:display_name] = clean_display_name(shading_surface.nameString)
43
+ hash[:display_name] = clean_name(shading_surface.nameString)
44
44
  hash[:user_data] = {handle: shading_surface.handle.to_s}
45
45
  hash[:properties] = properties_from_shading_surface(shading_surface)
46
46
  hash[:geometry] = geometry_from_shading_surface(shading_surface, site_transformation)
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'EnergyMaterial'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = material.nameString
43
+ hash[:identifier] = clean_name(material.nameString)
44
44
  hash[:thickness] = material.thickness
45
45
  hash[:conductivity] = material.conductivity
46
46
  hash[:density] = material.density
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'EnergyMaterialNoMass'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = material.nameString
43
+ hash[:identifier] = clean_name(material.nameString)
44
44
  hash[:r_value] = material.thermalResistance
45
45
 
46
46
  if material.to_MasslessOpaqueMaterial.is_initialized
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'EnergyWindowMaterialBlind'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = material.nameString
43
+ hash[:identifier] = clean_name(material.nameString)
44
44
  hash[:slat_orientation] = material.slatOrientation
45
45
  hash[:slat_width] = material.slatWidth
46
46
  hash[:slat_separation] = material.slatSeparation
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'EnergyWindowMaterialGas'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = material.nameString
43
+ hash[:identifier] = clean_name(material.nameString)
44
44
  hash[:thickness] = material.thickness
45
45
  hash[:gas_type] = material.gasType
46
46
 
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'EnergyWindowMaterialGasCustom'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = material.nameString
43
+ hash[:identifier] = clean_name(material.nameString)
44
44
  hash[:thickness] = material.thickness
45
45
  # check if boost optional object is empty
46
46
  unless material.customConductivityCoefficientA.empty?
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'EnergyWindowMaterialGasMixture'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = material.nameString
43
+ hash[:identifier] = clean_name(material.nameString)
44
44
  hash[:thickness] = material.thickness
45
45
  hash[:gas_types] = []
46
46
  hash[:gas_fractions] = []
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'EnergyWindowMaterialGlazing'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = material.nameString
43
+ hash[:identifier] = clean_name(material.nameString)
44
44
  hash[:thickness] = material.thickness
45
45
  hash[:solar_transmittance] = material.solarTransmittance
46
46
  # check if boost optional object is empty
@@ -40,7 +40,7 @@ module Honeybee
40
40
  hash = {}
41
41
  hash[:type] = 'EnergyWindowMaterialSimpleGlazSys'
42
42
  # set hash values from OpenStudio Object
43
- hash[:identifier] = material.nameString
43
+ hash[:identifier] = clean_name(material.nameString)
44
44
  hash[:u_factor] = material.uFactor
45
45
  hash[:shgc] = material.solarHeatGainCoefficient
46
46
  # check if boost optional object is empty
@@ -46,6 +46,8 @@ require 'from_openstudio/construction/opaque'
46
46
  require 'from_openstudio/construction/window'
47
47
  require 'from_openstudio/construction/shade'
48
48
  require 'from_openstudio/construction_set'
49
+ require 'from_openstudio/schedule/type_limit'
50
+ require 'from_openstudio/schedule/ruleset'
49
51
 
50
52
  require 'openstudio'
51
53
 
@@ -131,6 +133,10 @@ module Honeybee
131
133
  hash[:materials] = materials_from_model(openstudio_model)
132
134
  hash[:construction_sets] = []
133
135
  hash[:construction_sets] = constructionsets_from_model(openstudio_model)
136
+ hash[:schedule_type_limits] = []
137
+ hash[:schedule_type_limits] = schedtypelimits_from_model(openstudio_model)
138
+ hash[:schedules] = []
139
+ hash[:schedules] = scheduleruleset_from_model(openstudio_model)
134
140
 
135
141
  hash
136
142
  end
@@ -266,5 +272,24 @@ module Honeybee
266
272
  result
267
273
  end
268
274
 
275
+ # Create HB Schedule Type Limits from OpenStudio Schedule Type Limits
276
+ def self.schedtypelimits_from_model(openstudio_model)
277
+ result = []
278
+ openstudio_model.getScheduleTypeLimitss.each do |sch_typ_lim|
279
+ result << ScheduleTypeLimit.from_schedule_type_limit(sch_typ_lim)
280
+ end
281
+
282
+ result
283
+ end
284
+
285
+ # Create HB Schedule Ruleset from OpenStudio Ruleset
286
+ def self.scheduleruleset_from_model(openstudio_model)
287
+ result = []
288
+ openstudio_model.getScheduleRulesets.each do |sch_ruleset|
289
+ result << ScheduleRulesetAbridged.from_schedule_ruleset(sch_ruleset)
290
+ end
291
+ result
292
+ end
293
+
269
294
  end # Model
270
295
  end # Honeybee
@@ -0,0 +1,114 @@
1
+ # *******************************************************************************
2
+ # Honeybee 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/schedule/ruleset'
33
+ require 'from_openstudio/model_object'
34
+
35
+ module Honeybee
36
+ class ScheduleRulesetAbridged < ModelObject
37
+
38
+ def self.from_schedule_ruleset(schedule_ruleset)
39
+ # create an empty hash
40
+ hash = {}
41
+ hash[:type] = 'ScheduleRulesetAbridged'
42
+ # set hash values from OpenStudio Object
43
+ hash[:identifier] = schedule_ruleset.nameString
44
+ # check if boost optional object is empty
45
+ hash[:default_day_schedule] = schedule_ruleset.defaultDaySchedule.nameString
46
+ hash[:summer_designday_schedule] = schedule_ruleset.summerDesignDaySchedule.nameString
47
+ hash[:winter_designday_schedule] = schedule_ruleset.winterDesignDaySchedule.nameString
48
+ hash[:holiday_schedule] = schedule_ruleset.holidaySchedule.nameString
49
+
50
+ schedule_days = [schedule_ruleset.defaultDaySchedule, schedule_ruleset.summerDesignDaySchedule, schedule_ruleset.winterDesignDaySchedule, schedule_ruleset.holidaySchedule]
51
+ hash[:day_schedules] = []
52
+ schedule_days.each do |schedule_day|
53
+ hash[:day_schedules] << ScheduleRulesetAbridged.from_day_schedule(schedule_day)
54
+ end
55
+
56
+ hash[:schedule_rules] = []
57
+ schedule_ruleset.scheduleRules.each do |schedule_rule|
58
+ hash[:schedule_rules] << ScheduleRulesetAbridged.from_schedule_rule(schedule_rule)
59
+ end
60
+
61
+ hash
62
+ end
63
+
64
+ def self.from_day_schedule(day_schedule)
65
+ hash = {}
66
+ hash[:type] = 'ScheduleDay'
67
+ hash[:identifier] = day_schedule.nameString
68
+ hash[:interpolate] = day_schedule.interpolatetoTimestep
69
+ hash[:values] = day_schedule.values
70
+ time_until = [[0,0]]
71
+ day_schedule.times.each do |time|
72
+ time_until << [time.hours, time.minutes]
73
+ end
74
+ time_until.delete_at(-1)
75
+ hash[:times] = time_until
76
+
77
+ hash
78
+ end
79
+
80
+ def self.from_schedule_rule(schedule_rule)
81
+ hash = {}
82
+ hash[:type] = 'ScheduleRuleAbridged'
83
+ hash[:schedule_day] = schedule_rule.daySchedule.nameString
84
+ hash[:apply_sunday] = schedule_rule.applySunday
85
+ hash[:apply_monday] = schedule_rule.applyMonday
86
+ hash[:apply_tuesday] = schedule_rule.applyTuesday
87
+ hash[:apply_wednesday] = schedule_rule.applyWednesday
88
+ hash[:apply_thursday] = schedule_rule.applyThursday
89
+ hash[:apply_friday] = schedule_rule.applyFriday
90
+ hash[:apply_saturday] = schedule_rule.applySaturday
91
+
92
+ #boost optional
93
+ unless schedule_rule.startDate.empty?
94
+ start_date = schedule_rule.startDate.get
95
+ hash[:start_date] = [(start_date.monthOfYear).value, start_date.dayOfMonth]
96
+ if start_date.isLeapYear
97
+ hash[:start_date] << 1
98
+ end
99
+ end
100
+
101
+ #boost optional
102
+ unless schedule_rule.endDate.empty?
103
+ end_date = schedule_rule.endDate.get
104
+ hash[:end_date] = [(end_date.monthOfYear).value, end_date.dayOfMonth]
105
+ if start_date.isLeapYear
106
+ hash[:end_date] << 1
107
+ end
108
+ end
109
+
110
+ hash
111
+ end
112
+
113
+ end # ScheduleRulesetAbridged
114
+ end # Honeybee
@@ -0,0 +1,63 @@
1
+ # *******************************************************************************
2
+ # Honeybee 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/schedule/type_limit'
33
+ require 'to_openstudio/model_object'
34
+
35
+ module Honeybee
36
+ class ScheduleTypeLimit < ModelObject
37
+
38
+ def self.from_schedule_type_limit(schedule_type_limit)
39
+ # create an empty hash
40
+ hash = {}
41
+ hash[:type] = 'ScheduleTypeLimit'
42
+ # set hash values from OpenStudio Object
43
+ hash[:identifier] = schedule_type_limit.nameString
44
+ # check if boost optional object is empty
45
+ unless schedule_type_limit.lowerLimitValue.empty?
46
+ hash[:lower_limit] = schedule_type_limit.lowerLimitValue.get
47
+ end
48
+ # check if boost optional object is empty
49
+ unless schedule_type_limit.upperLimitValue.empty?
50
+ hash[:upper_limit] = schedule_type_limit.upperLimitValue.get
51
+ end
52
+ # check if boost optional object is empty
53
+ unless schedule_type_limit.numericType.empty?
54
+ numeric_type = schedule_type_limit.numericType.get
55
+ hash[:numeric_type] = numeric_type.titleize
56
+ end
57
+ hash[:unit_type] = schedule_type_limit.unitType
58
+
59
+ hash
60
+ end
61
+
62
+ end # ScheduleTypeLimit
63
+ end # Honeybee
@@ -63,4 +63,8 @@ require 'from_openstudio/material/window_simpleglazsys'
63
63
  # extend the simulation objects
64
64
  require 'from_openstudio/simulation/design_day'
65
65
  require 'from_openstudio/simulation/parameter_model'
66
- require 'from_openstudio/simulation/simulation_output'
66
+ require 'from_openstudio/simulation/simulation_output'
67
+
68
+ # extend the schedule objects
69
+ require 'from_openstudio/schedule/type_limit'
70
+ require 'from_openstudio/schedule/ruleset'
@@ -54,7 +54,10 @@
54
54
  "identifier": "Generic Single Pane",
55
55
  "materials": [
56
56
  "Generic Clear Glass"
57
- ]
57
+ ],
58
+ "u_factor": 5.731373,
59
+ "shgc": 0.824407,
60
+ "vt": 0.88
58
61
  },
59
62
  {
60
63
  "type": "ShadeConstruction",
@@ -170,7 +173,10 @@
170
173
  "Generic Low-e Glass",
171
174
  "Generic Window Air Gap",
172
175
  "Generic Clear Glass"
173
- ]
176
+ ],
177
+ "u_factor": 1.687787,
178
+ "shgc": 0.43651,
179
+ "vt": 0.635473
174
180
  },
175
181
  {
176
182
  "type": "OpaqueConstructionAbridged",
@@ -51,6 +51,7 @@ module Honeybee
51
51
  @@extension ||= Extension.new
52
52
  @@schema ||= @@extension.schema
53
53
  @@standards ||= @@extension.standards
54
+ $simple_window_cons = false
54
55
 
55
56
  @hash = hash
56
57
  @type = @hash[:type]
@@ -36,6 +36,13 @@ module Honeybee
36
36
 
37
37
  attr_reader :errors, :warnings
38
38
 
39
+ @@encoding_options = {
40
+ :invalid => :replace, # Replace invalid byte sequences
41
+ :undef => :replace, # Replace anything not defined in ASCII
42
+ :replace => '', # Use a blank for those replacements
43
+ :universal_newline => true # Always break lines with \n
44
+ }
45
+
39
46
  def method_missing(sym, *args)
40
47
  name = sym.to_s
41
48
  aname = name.sub('=', '')
@@ -99,13 +106,14 @@ module Honeybee
99
106
  end
100
107
 
101
108
  # remove illegal characters in identifier
102
- def self.clean_display_name(str)
103
- str.gsub(/[^[:ascii:]]/, '')
109
+ def self.clean_name(str)
110
+ ascii = str.encode(Encoding.find('ASCII'), @@encoding_options)
104
111
  end
105
112
 
106
113
  # remove illegal characters in identifier
107
114
  def self.clean_identifier(str)
108
- str.gsub(/[^.A-Za-z0-9_-]/, '_').gsub(' ', '_')
115
+ encode_str = str.encode(Encoding.find('ASCII'), @@encoding_options)
116
+ encode_str.gsub(/[^.A-Za-z0-9_-]/, '_').gsub(' ', '_')
109
117
  end
110
118
 
111
119
 
@@ -86,6 +86,7 @@ class FromHoneybeeModelToGbxml < OpenStudio::Measure::ModelMeasure
86
86
  return false
87
87
  end
88
88
  honeybee_model = Honeybee::Model.read_from_disk(model_json)
89
+ $simple_window_cons = true
89
90
  STDOUT.flush
90
91
  os_model = honeybee_model.to_openstudio_model(model)
91
92
  STDOUT.flush
@@ -50,16 +50,25 @@ module Honeybee
50
50
  # create material vector
51
51
  os_materials = OpenStudio::Model::MaterialVector.new
52
52
  # loop through each layer and add to material vector
53
- if @hash.key?(:layers)
54
- mat_key = :layers
53
+ if $simple_window_cons && @hash[:u_factor]
54
+ os_simple_glazing = OpenStudio::Model::SimpleGlazing.new(openstudio_model)
55
+ os_simple_glazing.setName(@hash[:identifier] + '_SimpleGlazSys')
56
+ os_simple_glazing.setUFactor(@hash[:u_factor])
57
+ os_simple_glazing.setSolarHeatGainCoefficient(@hash[:shgc])
58
+ os_simple_glazing.setVisibleTransmittance(@hash[:vt])
59
+ os_materials << os_simple_glazing
55
60
  else
56
- mat_key = :materials
57
- end
58
- @hash[mat_key].each do |material_identifier|
59
- material = openstudio_model.getMaterialByName(material_identifier)
60
- unless material.empty?
61
- os_material = material.get
62
- os_materials << os_material
61
+ if @hash.key?(:layers)
62
+ mat_key = :layers
63
+ else
64
+ mat_key = :materials
65
+ end
66
+ @hash[mat_key].each do |material_identifier|
67
+ material = openstudio_model.getMaterialByName(material_identifier)
68
+ unless material.empty?
69
+ os_material = material.get
70
+ os_materials << os_material
71
+ end
63
72
  end
64
73
  end
65
74
  os_construction.setLayers(os_materials)
@@ -77,7 +77,7 @@ module Honeybee
77
77
 
78
78
  # assign the flow exponent if it's specified
79
79
  if vent_crack[:flow_exponent]
80
- os_crack. setAirMassFlowExponent(vent_crack[:flow_exponent])
80
+ os_crack.setAirMassFlowExponent(vent_crack[:flow_exponent])
81
81
  end
82
82
 
83
83
  # if it's a Surface boundary condition ensure the neighbor is not written as a duplicate
@@ -105,6 +105,14 @@ module Honeybee
105
105
  os_thermal_zone.setMultiplier(@hash[:multiplier])
106
106
  end
107
107
 
108
+ # assign the geometry properties if they exist
109
+ if @hash[:ceiling_height]
110
+ os_thermal_zone.setCeilingHeight(@hash[:ceiling_height])
111
+ end
112
+ if @hash[:volume]
113
+ os_thermal_zone.setVolume(@hash[:volume])
114
+ end
115
+
108
116
  # assign the story
109
117
  if @hash[:story] # the users has specified the name of the story
110
118
  story = openstudio_model.getBuildingStoryByName(@hash[:story])
@@ -349,8 +357,10 @@ module Honeybee
349
357
  if sub_f.adjacentSubSurface.empty? # not an interior window that's already in the AFN
350
358
  vent_open = VentilationOpening.new(opening)
351
359
  open_fac = vent_open.to_openstudio_afn(openstudio_model, sub_f)
352
- operable_subfs << sub_f
353
- opening_factors << open_fac
360
+ unless open_fac.nil? # nil is used for horizontal exterior skylights
361
+ operable_subfs << sub_f
362
+ opening_factors << open_fac
363
+ end
354
364
  end
355
365
  end
356
366
  end
@@ -128,43 +128,69 @@ module Honeybee
128
128
  end
129
129
 
130
130
  def to_openstudio_afn(openstudio_model, parent)
131
- # process the flow_coefficient_closed and set it to a very small number if it's 0
131
+ # get the tilt and BC of the parent so that we can use the correct AFN object
132
+ srf_tilt = parent.tilt.to_f * (180 / Math::PI)
133
+ srf_bc = parent.outsideBoundaryCondition.to_s
134
+
135
+ # process the flow_coefficient_closed and flow exponent
132
136
  if @hash[:flow_coefficient_closed] and @hash[:flow_coefficient_closed] != 0
133
137
  flow_coefficient = @hash[:flow_coefficient_closed]
134
138
  else
135
139
  flow_coefficient = 1.0e-09 # set it to a very small number
136
140
  end
137
-
138
- # create the simple opening object for the Aperture or Door using default values
139
141
  flow_exponent = defaults[:flow_exponent_closed][:default].to_f
140
- two_way_thresh = defaults[:two_way_threshold][:default].to_f
141
- discharge_coeff = defaults[:discharge_coefficient][:default].to_f
142
- os_opening = OpenStudio::Model::AirflowNetworkSimpleOpening.new(
143
- openstudio_model, flow_coefficient, flow_exponent, two_way_thresh, discharge_coeff)
144
-
145
- # assign the flow exponent when the opening is closed
146
- if @hash[:flow_exponent_closed]
147
- os_opening.setAirMassFlowExponentWhenOpeningisClosed(@hash[:flow_exponent_closed])
148
- end
149
- # assign the minimum difference for two-way flow
150
- if @hash[:two_way_threshold]
151
- os_opening.setMinimumDensityDifferenceforTwoWayFlow(@hash[:two_way_threshold])
152
- end
153
- # assign the discharge coefficient
154
- if @hash[:discharge_coefficient]
155
- os_opening.setDischargeCoefficient(@hash[:discharge_coefficient])
156
- end
157
-
158
- # create the AirflowNetworkSurface
159
- os_afn_srf = parent.getAirflowNetworkSurface(os_opening)
160
142
 
161
- # assign the opening area
143
+ # process the opening area
162
144
  if @hash[:fraction_area_operable]
163
145
  open_fac = @hash[:fraction_area_operable]
164
146
  else
165
147
  open_fac = defaults[:fraction_area_operable][:default]
166
148
  end
167
- os_afn_srf.setWindowDoorOpeningFactorOrCrackFactor(open_fac)
149
+
150
+ # create an opening obj
151
+ if srf_tilt < 10 || srf_tilt > 170
152
+ if srf_bc == 'Outdoors'
153
+ # create a crack object to represent an exterior in-operable horizontal skylight
154
+ open_fac = nil
155
+ os_opening = OpenStudio::Model::AirflowNetworkCrack.new(
156
+ openstudio_model, flow_coefficient, flow_exponent, $afn_reference_crack)
157
+ else
158
+ # create a HorizontalOpening object to represent the interior horizontal window
159
+ discharge_coeff = defaults[:discharge_coefficient][:default].to_f
160
+ if srf_tilt < 10
161
+ slope_ang = 90 - srf_tilt
162
+ else
163
+ slope_ang = 90 - (180 - srf_tilt)
164
+ end
165
+ os_opening = OpenStudio::Model::AirflowNetworkHorizontalOpening .new(
166
+ openstudio_model, flow_coefficient, flow_exponent, slope_ang, discharge_coeff)
167
+ end
168
+ else
169
+ # create the simple opening object for the Aperture or Door using default values
170
+ two_way_thresh = defaults[:two_way_threshold][:default].to_f
171
+ discharge_coeff = defaults[:discharge_coefficient][:default].to_f
172
+ os_opening = OpenStudio::Model::AirflowNetworkSimpleOpening.new(
173
+ openstudio_model, flow_coefficient, flow_exponent, two_way_thresh, discharge_coeff)
174
+
175
+ # assign the flow exponent when the opening is closed
176
+ if @hash[:flow_exponent_closed]
177
+ os_opening.setAirMassFlowExponentWhenOpeningisClosed(@hash[:flow_exponent_closed])
178
+ end
179
+ # assign the minimum difference for two-way flow
180
+ if @hash[:two_way_threshold]
181
+ os_opening.setMinimumDensityDifferenceforTwoWayFlow(@hash[:two_way_threshold])
182
+ end
183
+ # assign the discharge coefficient
184
+ if @hash[:discharge_coefficient]
185
+ os_opening.setDischargeCoefficient(@hash[:discharge_coefficient])
186
+ end
187
+ end
188
+
189
+ # create the AirflowNetworkSurface and assign the opening factor
190
+ os_afn_srf = parent.getAirflowNetworkSurface(os_opening)
191
+ unless open_fac.nil?
192
+ os_afn_srf.setWindowDoorOpeningFactorOrCrackFactor(open_fac)
193
+ end
168
194
 
169
195
  open_fac
170
196
  end
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.22.2
4
+ version: 2.23.0
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: 2021-08-20 00:00:00.000000000 Z
14
+ date: 2021-09-15 00:00:00.000000000 Z
15
15
  dependencies:
16
16
  - !ruby/object:Gem::Dependency
17
17
  name: bundler
@@ -89,14 +89,14 @@ dependencies:
89
89
  requirements:
90
90
  - - "~>"
91
91
  - !ruby/object:Gem::Version
92
- version: 0.54.0
92
+ version: 1.15.0
93
93
  type: :development
94
94
  prerelease: false
95
95
  version_requirements: !ruby/object:Gem::Requirement
96
96
  requirements:
97
97
  - - "~>"
98
98
  - !ruby/object:Gem::Version
99
- version: 0.54.0
99
+ version: 1.15.0
100
100
  - !ruby/object:Gem::Dependency
101
101
  name: json_pure
102
102
  requirement: !ruby/object:Gem::Requirement
@@ -117,28 +117,28 @@ dependencies:
117
117
  requirements:
118
118
  - - '='
119
119
  - !ruby/object:Gem::Version
120
- version: 0.4.2
120
+ version: 0.4.3
121
121
  type: :runtime
122
122
  prerelease: false
123
123
  version_requirements: !ruby/object:Gem::Requirement
124
124
  requirements:
125
125
  - - '='
126
126
  - !ruby/object:Gem::Version
127
- version: 0.4.2
127
+ version: 0.4.3
128
128
  - !ruby/object:Gem::Dependency
129
129
  name: openstudio-standards
130
130
  requirement: !ruby/object:Gem::Requirement
131
131
  requirements:
132
132
  - - "~>"
133
133
  - !ruby/object:Gem::Version
134
- version: 0.2.13
134
+ version: 0.2.14
135
135
  type: :runtime
136
136
  prerelease: false
137
137
  version_requirements: !ruby/object:Gem::Requirement
138
138
  requirements:
139
139
  - - "~>"
140
140
  - !ruby/object:Gem::Version
141
- version: 0.2.13
141
+ version: 0.2.14
142
142
  description: Library and measures for translating between Honeybee JSON schema and
143
143
  OpenStudio Model schema (OSM).
144
144
  email:
@@ -187,6 +187,8 @@ files:
187
187
  - lib/from_openstudio/material/window_simpleglazsys.rb
188
188
  - lib/from_openstudio/model.rb
189
189
  - lib/from_openstudio/model_object.rb
190
+ - lib/from_openstudio/schedule/ruleset.rb
191
+ - lib/from_openstudio/schedule/type_limit.rb
190
192
  - lib/from_openstudio/simulation/design_day.rb
191
193
  - lib/from_openstudio/simulation/parameter_model.rb
192
194
  - lib/from_openstudio/simulation/simulation_output.rb