tbd 3.1.1 → 3.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.github/workflows/pull_request.yml +16 -0
- data/LICENSE.md +1 -1
- data/README.md +3 -7
- data/Rakefile +8 -7
- data/lib/measures/tbd/LICENSE.md +1 -1
- data/lib/measures/tbd/README.md +8 -0
- data/lib/measures/tbd/measure.rb +44 -2
- data/lib/measures/tbd/measure.xml +38 -29
- data/lib/measures/tbd/resources/geo.rb +56 -16
- data/lib/measures/tbd/resources/model.rb +0 -6
- data/lib/measures/tbd/resources/oslog.rb +17 -7
- data/lib/measures/tbd/resources/psi.rb +117 -10
- data/lib/measures/tbd/resources/tbd.rb +1 -1
- data/lib/measures/tbd/resources/ua.rb +36 -69
- data/lib/measures/tbd/resources/utils.rb +86 -28
- data/lib/measures/tbd/resources/version.rb +1 -1
- data/lib/measures/tbd/tests/tbd_tests.rb +117 -87
- data/lib/tbd/geo.rb +56 -16
- data/lib/tbd/psi.rb +117 -10
- data/lib/tbd/ua.rb +36 -69
- data/lib/tbd/version.rb +2 -2
- data/lib/tbd.rb +9 -9
- metadata +3 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 7a5a9002ff406325bc226c157ed29ffc22ccb60ac46b9c6bf29358f04aa9d6a3
|
4
|
+
data.tar.gz: 60b0a52d46be3a91a2119cb5d3875826e7b278ca9ce78a230e9575263dbb4c89
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: df24c1565b802fd84c8f067d78662adf23d5fb2059145b6b22da98b8c06f70b49283ef7f28613e91c1258e3c7b865d17e81df93c2340aec431483597d8ddb847
|
7
|
+
data.tar.gz: 34ea2406564f08b36a54987ab08fd5d2cb24e49bfb02640169278f1138f65f36ac2c9279abb7e8be83e1c2aec4cca639b8735ab13f54f0470fe0a8470977be86
|
@@ -70,3 +70,19 @@ jobs:
|
|
70
70
|
docker exec -t test bundle update
|
71
71
|
docker exec -t test bundle exec rake
|
72
72
|
docker kill test
|
73
|
+
test_351x:
|
74
|
+
runs-on: ubuntu-22.04
|
75
|
+
steps:
|
76
|
+
- name: Check out repository
|
77
|
+
uses: actions/checkout@v2
|
78
|
+
- name: Run Tests
|
79
|
+
run: |
|
80
|
+
echo $(pwd)
|
81
|
+
echo $(ls)
|
82
|
+
docker pull nrel/openstudio:3.5.1
|
83
|
+
docker run --name test --rm -d -t -v $(pwd):/work -w /work nrel/openstudio:3.5.1
|
84
|
+
docker exec -t test pwd
|
85
|
+
docker exec -t test ls
|
86
|
+
docker exec -t test bundle update
|
87
|
+
docker exec -t test bundle exec rake
|
88
|
+
docker kill test
|
data/LICENSE.md
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
MIT License
|
2
2
|
|
3
|
-
Copyright (c) 2020-
|
3
|
+
Copyright (c) 2020-2023 Denis Bourgeois & Dan Macumber
|
4
4
|
|
5
5
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
6
|
of this software and associated documentation files (the "Software"), to deal
|
data/README.md
CHANGED
@@ -32,9 +32,7 @@ TBD is systematically tested against updated OpenStudio versions (since v3.0.0).
|
|
32
32
|
|
33
33
|
### Windows Installation
|
34
34
|
|
35
|
-
|
36
|
-
|
37
|
-
From the command line, check that the ruby installation returns the correct Ruby version:
|
35
|
+
Either install Ruby using the [RubyInstaller](https://rubyinstaller.org/downloads/archives/) for [Ruby 2.7.2 (x64)](https://github.com/oneclick/rubyinstaller2/releases/tag/RubyInstaller-2.7.2-1/rubyinstaller-2.7.2-1-x64.exe), or preferably under [WSL2](https://gist.github.com/brgix/0d968d8f32c41f13300dc6769414df79). Run the following steps if going down the _RubyInstaller_ route. From the command line, check that the ruby installation returns the correct Ruby version:
|
38
36
|
```
|
39
37
|
ruby -v
|
40
38
|
```
|
@@ -57,9 +55,6 @@ Verify your OpenStudio and Ruby configuration:
|
|
57
55
|
ruby -e "require 'openstudio'" -e "puts OpenStudio::Model::Model.new"
|
58
56
|
```
|
59
57
|
|
60
|
-
`git clone` the TBD repo, then run basic tests to ensure the measure operates properly (see end of this README).
|
61
|
-
|
62
|
-
|
63
58
|
### MacOS Installation
|
64
59
|
|
65
60
|
MacOS already comes with Ruby, but likely not the right Ruby version for the desired OpenStudio measure development [environment](https://github.com/NREL/OpenStudio/wiki/OpenStudio-SDK-Version-Compatibility-Matrix). Instructions here show how to install Ruby v2.7.2 alongside MacOS's own Ruby version. Although no longer officially supported, instructions for an OpenStudio v2.9.1 setup is described [here](https://github.com/rd2/tbd/blob/master/v291_MacOS.md).
|
@@ -117,8 +112,9 @@ cd ~/Documents/sandbox340
|
|
117
112
|
ruby -e "require 'openstudio'" -e "puts OpenStudio::Model::Model.new"
|
118
113
|
```
|
119
114
|
|
120
|
-
|
115
|
+
## Clone TBD
|
121
116
|
|
117
|
+
Once done with either the Windows or MacOS setup, install the latest version of _git_ (e.g. through Homebrew), then ```git clone``` the TBD repo, e.g. under "sandbox340". Run the basic tests below to ensure the measure operates as expected.
|
122
118
|
|
123
119
|
## Complete list of test commands
|
124
120
|
|
data/Rakefile
CHANGED
@@ -2,28 +2,29 @@ require "bundler/gem_tasks"
|
|
2
2
|
require "rspec/core/rake_task"
|
3
3
|
|
4
4
|
RSpec::Core::RakeTask.new(:spec) do |t|
|
5
|
-
|
5
|
+
t.rspec_opts = "--exclude-pattern \'spec/**/*suite_spec.rb\'"
|
6
6
|
end
|
7
7
|
|
8
8
|
task default: :spec
|
9
9
|
|
10
10
|
desc "Update Library Files"
|
11
11
|
task :libraries do
|
12
|
-
puts "Updating Library Files"
|
12
|
+
# puts "Updating Library Files"
|
13
13
|
|
14
14
|
require "fileutils"
|
15
15
|
|
16
16
|
libs = ["topolys", "osut", "oslg", "tbd"]
|
17
17
|
files = {}
|
18
|
-
|
18
|
+
|
19
19
|
$:.each do |path|
|
20
20
|
libs.each do |l|
|
21
21
|
next unless path.include?(l)
|
22
|
+
|
22
23
|
files[l] = Dir.glob(File.join(path, "#{l}/*.rb"))
|
23
24
|
files[l].delete_if { |f| f.include?("version.rb") } unless l == "topolys"
|
24
|
-
puts "#{l} lib files:"
|
25
|
-
files[l].each { |lf| puts "... #{lf}" }
|
26
|
-
puts
|
25
|
+
# puts "#{l} lib files:"
|
26
|
+
# files[l].each { |lf| puts "... #{lf}" }
|
27
|
+
# puts
|
27
28
|
end
|
28
29
|
end
|
29
30
|
|
@@ -38,7 +39,7 @@ end
|
|
38
39
|
|
39
40
|
desc "Update Measure"
|
40
41
|
task measure: [:libraries] do
|
41
|
-
puts "Updating Measure"
|
42
|
+
# puts "Updating Measure"
|
42
43
|
|
43
44
|
require "openstudio"
|
44
45
|
require "open3"
|
data/lib/measures/tbd/LICENSE.md
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
MIT License
|
2
2
|
|
3
|
-
Copyright (c) 2020-
|
3
|
+
Copyright (c) 2020-2023 Denis Bourgeois & Dan Macumber
|
4
4
|
|
5
5
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
6
|
of this software and associated documentation files (the "Software"), to deal
|
data/lib/measures/tbd/README.md
CHANGED
@@ -27,6 +27,14 @@ For EnergyPlus simulations, leave CHECKED. For iterative exploration with Apply
|
|
27
27
|
**Required:** false,
|
28
28
|
**Model Dependent:** false
|
29
29
|
|
30
|
+
### Proximity tolerance (m)
|
31
|
+
Proximity tolerance (e.g. 0.100 m) between subsurface edges, e.g. between near-adjacent window jambs.
|
32
|
+
**Name:** sub_tol,
|
33
|
+
**Type:** Double,
|
34
|
+
**Units:** ,
|
35
|
+
**Required:** false,
|
36
|
+
**Model Dependent:** false
|
37
|
+
|
30
38
|
### Load 'tbd.json'
|
31
39
|
Loads existing 'tbd.json' file (under '/files'), may override 'default thermal bridge' set.
|
32
40
|
**Name:** load_tbd_json,
|
data/lib/measures/tbd/measure.rb
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
# MIT License
|
2
2
|
#
|
3
|
-
# Copyright (c) 2020-
|
3
|
+
# Copyright (c) 2020-2023 Denis Bourgeois & Dan Macumber
|
4
4
|
#
|
5
5
|
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
6
|
# of this software and associated documentation files (the "Software"), to deal
|
@@ -48,6 +48,15 @@ class TBDMeasure < OpenStudio::Measure::ModelMeasure
|
|
48
48
|
alter.setDefaultValue(true)
|
49
49
|
args << alter
|
50
50
|
|
51
|
+
arg = "sub_tol"
|
52
|
+
dsc = "Proximity tolerance (e.g. 0.100 m) between subsurface edges, e.g. " \
|
53
|
+
"between near-adjacent window jambs."
|
54
|
+
sub_tol = OpenStudio::Measure::OSArgument.makeDoubleArgument(arg, false)
|
55
|
+
sub_tol.setDisplayName("Proximity tolerance (m)")
|
56
|
+
sub_tol.setDescription(dsc)
|
57
|
+
sub_tol.setDefaultValue(TBD::TOL)
|
58
|
+
args << sub_tol
|
59
|
+
|
51
60
|
arg = "load_tbd_json"
|
52
61
|
dsc = "Loads existing 'tbd.json' file (under '/files'), may override " \
|
53
62
|
"'default thermal bridge' set."
|
@@ -225,6 +234,7 @@ class TBDMeasure < OpenStudio::Measure::ModelMeasure
|
|
225
234
|
|
226
235
|
argh = {}
|
227
236
|
argh[:alter ] = runner.getBoolArgumentValue("alter_model", args)
|
237
|
+
argh[:sub_tol ] = runner.getDoubleArgumentValue("sub_tol", args)
|
228
238
|
argh[:load_tbd ] = runner.getBoolArgumentValue("load_tbd_json", args)
|
229
239
|
argh[:option ] = runner.getStringArgumentValue("option", args)
|
230
240
|
argh[:write_tbd ] = runner.getBoolArgumentValue("write_tbd_json", args)
|
@@ -286,6 +296,38 @@ class TBDMeasure < OpenStudio::Measure::ModelMeasure
|
|
286
296
|
end
|
287
297
|
end
|
288
298
|
|
299
|
+
# Pre-validate ground-facing constructions for KIVA.
|
300
|
+
if argh[:kiva_force] || argh[:gen_kiva]
|
301
|
+
kva = true
|
302
|
+
|
303
|
+
mdl.getSurfaces.each do |s|
|
304
|
+
id = s.nameString
|
305
|
+
construction = s.construction
|
306
|
+
next unless s.isGroundSurface
|
307
|
+
|
308
|
+
if construction.empty?
|
309
|
+
runner.registerError("Invalid construction for KIVA (#{id})")
|
310
|
+
kva = false if kva
|
311
|
+
else
|
312
|
+
construction = construction.get.to_LayeredConstruction
|
313
|
+
|
314
|
+
if construction.empty?
|
315
|
+
runner.registerError("KIVA requires layered constructions (#{id})")
|
316
|
+
kva = false if kva
|
317
|
+
else
|
318
|
+
construction = construction.get
|
319
|
+
|
320
|
+
unless TBD.standardOpaqueLayers?(construction)
|
321
|
+
runner.registerError("KIVA requires standard materials (#{id})")
|
322
|
+
kva = false if kva
|
323
|
+
end
|
324
|
+
end
|
325
|
+
end
|
326
|
+
end
|
327
|
+
|
328
|
+
return false unless kva
|
329
|
+
end
|
330
|
+
|
289
331
|
# Process all ground-facing surfaces as foundation-facing.
|
290
332
|
if argh[:kiva_force]
|
291
333
|
argh[:gen_kiva] = true
|
@@ -313,7 +355,7 @@ class TBDMeasure < OpenStudio::Measure::ModelMeasure
|
|
313
355
|
|
314
356
|
argh[:version ] = model.getVersion.versionIdentifier
|
315
357
|
tbd = TBD.process(model, argh)
|
316
|
-
argh[:io ] = tbd[:io]
|
358
|
+
argh[:io ] = tbd[:io ]
|
317
359
|
argh[:surfaces] = tbd[:surfaces]
|
318
360
|
setpoints = TBD.heatingTemperatureSetpoints?(model)
|
319
361
|
setpoints = TBD.coolingTemperatureSetpoints?(model) || setpoints
|
@@ -3,8 +3,8 @@
|
|
3
3
|
<schema_version>3.0</schema_version>
|
4
4
|
<name>tbd_measure</name>
|
5
5
|
<uid>8890787b-8c25-4dc8-8641-b6be1b6c2357</uid>
|
6
|
-
<version_id>
|
7
|
-
<version_modified>
|
6
|
+
<version_id>2fc42e1d-2010-44ae-9837-6390512c41d4</version_id>
|
7
|
+
<version_modified>20230214T105829Z</version_modified>
|
8
8
|
<xml_checksum>99772807</xml_checksum>
|
9
9
|
<class_name>TBDMeasure</class_name>
|
10
10
|
<display_name>Thermal Bridging and Derating - TBD</display_name>
|
@@ -30,6 +30,15 @@
|
|
30
30
|
</choice>
|
31
31
|
</choices>
|
32
32
|
</argument>
|
33
|
+
<argument>
|
34
|
+
<name>sub_tol</name>
|
35
|
+
<display_name>Proximity tolerance (m)</display_name>
|
36
|
+
<description>Proximity tolerance (e.g. 0.100 m) between subsurface edges, e.g. between near-adjacent window jambs.</description>
|
37
|
+
<type>Double</type>
|
38
|
+
<required>false</required>
|
39
|
+
<model_dependent>false</model_dependent>
|
40
|
+
<default_value>0.01</default_value>
|
41
|
+
</argument>
|
33
42
|
<argument>
|
34
43
|
<name>load_tbd_json</name>
|
35
44
|
<display_name>Load 'tbd.json'</display_name>
|
@@ -373,12 +382,6 @@
|
|
373
382
|
<usage_type>doc</usage_type>
|
374
383
|
<checksum>32D70693</checksum>
|
375
384
|
</file>
|
376
|
-
<file>
|
377
|
-
<filename>LICENSE.md</filename>
|
378
|
-
<filetype>md</filetype>
|
379
|
-
<usage_type>license</usage_type>
|
380
|
-
<checksum>CB393A2B</checksum>
|
381
|
-
</file>
|
382
385
|
<file>
|
383
386
|
<filename>geometry.rb</filename>
|
384
387
|
<filetype>rb</filetype>
|
@@ -386,34 +389,28 @@
|
|
386
389
|
<checksum>D80E9AE6</checksum>
|
387
390
|
</file>
|
388
391
|
<file>
|
389
|
-
<filename>
|
390
|
-
<filetype>
|
391
|
-
<usage_type>
|
392
|
-
<checksum>
|
393
|
-
</file>
|
394
|
-
<file>
|
395
|
-
<filename>version.rb</filename>
|
396
|
-
<filetype>rb</filetype>
|
397
|
-
<usage_type>resource</usage_type>
|
398
|
-
<checksum>05CC939E</checksum>
|
392
|
+
<filename>LICENSE.md</filename>
|
393
|
+
<filetype>md</filetype>
|
394
|
+
<usage_type>license</usage_type>
|
395
|
+
<checksum>A91E64A0</checksum>
|
399
396
|
</file>
|
400
397
|
<file>
|
401
398
|
<filename>oslog.rb</filename>
|
402
399
|
<filetype>rb</filetype>
|
403
400
|
<usage_type>resource</usage_type>
|
404
|
-
<checksum>
|
401
|
+
<checksum>E97617E3</checksum>
|
405
402
|
</file>
|
406
403
|
<file>
|
407
404
|
<filename>tbd.rb</filename>
|
408
405
|
<filetype>rb</filetype>
|
409
406
|
<usage_type>resource</usage_type>
|
410
|
-
<checksum>
|
407
|
+
<checksum>A4E8433C</checksum>
|
411
408
|
</file>
|
412
409
|
<file>
|
413
410
|
<filename>utils.rb</filename>
|
414
411
|
<filetype>rb</filetype>
|
415
412
|
<usage_type>resource</usage_type>
|
416
|
-
<checksum>
|
413
|
+
<checksum>283C976C</checksum>
|
417
414
|
</file>
|
418
415
|
<file>
|
419
416
|
<version>
|
@@ -424,37 +421,49 @@
|
|
424
421
|
<filename>measure.rb</filename>
|
425
422
|
<filetype>rb</filetype>
|
426
423
|
<usage_type>script</usage_type>
|
427
|
-
<checksum>
|
424
|
+
<checksum>44B11139</checksum>
|
428
425
|
</file>
|
429
426
|
<file>
|
430
427
|
<filename>tbd_tests.rb</filename>
|
431
428
|
<filetype>rb</filetype>
|
432
429
|
<usage_type>test</usage_type>
|
433
|
-
<checksum>
|
430
|
+
<checksum>58ED6635</checksum>
|
431
|
+
</file>
|
432
|
+
<file>
|
433
|
+
<filename>geo.rb</filename>
|
434
|
+
<filetype>rb</filetype>
|
435
|
+
<usage_type>resource</usage_type>
|
436
|
+
<checksum>F447D8CE</checksum>
|
434
437
|
</file>
|
435
438
|
<file>
|
436
439
|
<filename>README.md</filename>
|
437
440
|
<filetype>md</filetype>
|
438
441
|
<usage_type>readme</usage_type>
|
439
|
-
<checksum>
|
442
|
+
<checksum>B836C43A</checksum>
|
440
443
|
</file>
|
441
444
|
<file>
|
442
|
-
<filename>
|
445
|
+
<filename>ua.rb</filename>
|
443
446
|
<filetype>rb</filetype>
|
444
447
|
<usage_type>resource</usage_type>
|
445
|
-
<checksum>
|
448
|
+
<checksum>19193778</checksum>
|
446
449
|
</file>
|
447
450
|
<file>
|
448
451
|
<filename>psi.rb</filename>
|
449
452
|
<filetype>rb</filetype>
|
450
453
|
<usage_type>resource</usage_type>
|
451
|
-
<checksum>
|
454
|
+
<checksum>1045EF38</checksum>
|
452
455
|
</file>
|
453
456
|
<file>
|
454
|
-
<filename>
|
457
|
+
<filename>model.rb</filename>
|
458
|
+
<filetype>rb</filetype>
|
459
|
+
<usage_type>resource</usage_type>
|
460
|
+
<checksum>8E9A76C7</checksum>
|
461
|
+
</file>
|
462
|
+
<file>
|
463
|
+
<filename>version.rb</filename>
|
455
464
|
<filetype>rb</filetype>
|
456
465
|
<usage_type>resource</usage_type>
|
457
|
-
<checksum>
|
466
|
+
<checksum>A3BB982A</checksum>
|
458
467
|
</file>
|
459
468
|
</files>
|
460
469
|
</measure>
|
@@ -1,6 +1,6 @@
|
|
1
1
|
# MIT License
|
2
2
|
#
|
3
|
-
# Copyright (c) 2020-
|
3
|
+
# Copyright (c) 2020-2023 Denis Bourgeois & Dan Macumber
|
4
4
|
#
|
5
5
|
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
6
|
# of this software and associated documentation files (the "Software"), to deal
|
@@ -22,24 +22,27 @@
|
|
22
22
|
|
23
23
|
module TBD
|
24
24
|
##
|
25
|
-
# Check for matching Topolys vertex pairs between edges
|
25
|
+
# Check for matching Topolys vertex pairs between edges.
|
26
26
|
#
|
27
27
|
# @param e1 [Hash] first edge
|
28
28
|
# @param e2 [Hash] second edge
|
29
|
+
# @param tol [Float] user-set tolerance (> TOL) in m
|
29
30
|
#
|
30
31
|
# @return [Bool] true if edges share vertex pairs
|
31
32
|
# @return [Bool] false if invalid input
|
32
|
-
def matches?(e1 = {}, e2 = {})
|
33
|
+
def matches?(e1 = {}, e2 = {}, tol = TOL)
|
33
34
|
mth = "TBD::#{__callee__}"
|
34
35
|
cl = Topolys::Point3D
|
35
36
|
a = false
|
36
37
|
|
37
38
|
return mismatch("e1", e1, Hash, mth, DBG, a) unless e1.is_a?(Hash)
|
38
39
|
return mismatch("e2", e2, Hash, mth, DBG, a) unless e2.is_a?(Hash)
|
40
|
+
|
39
41
|
return hashkey("e1", e1, :v0, mth, DBG, a) unless e1.key?(:v0)
|
40
42
|
return hashkey("e1", e1, :v1, mth, DBG, a) unless e1.key?(:v1)
|
41
43
|
return hashkey("e2", e2, :v0, mth, DBG, a) unless e2.key?(:v0)
|
42
44
|
return hashkey("e2", e2, :v1, mth, DBG, a) unless e2.key?(:v1)
|
45
|
+
|
43
46
|
return mismatch("e1 :v0", e1[:v0], cl, mth, DBG, a) unless e1[:v0].is_a?(cl)
|
44
47
|
return mismatch("e1 :v1", e1[:v1], cl, mth, DBG, a) unless e1[:v1].is_a?(cl)
|
45
48
|
return mismatch("e2 :v0", e2[:v0], cl, mth, DBG, a) unless e2[:v0].is_a?(cl)
|
@@ -51,26 +54,29 @@ module TBD
|
|
51
54
|
return zero("e1", mth, DBG, a) if e1_vector.magnitude < TOL
|
52
55
|
return zero("e2", mth, DBG, a) if e2_vector.magnitude < TOL
|
53
56
|
|
57
|
+
return mismatch("e1", e1, Hash, mth, DBG, a) unless tol.is_a?(Numeric)
|
58
|
+
return zero("tol", mth, DBG, a) if tol < TOL
|
59
|
+
|
54
60
|
return true if
|
55
61
|
(
|
56
62
|
(
|
57
|
-
( (e1[:v0].x - e2[:v0].x).abs <
|
58
|
-
(e1[:v0].y - e2[:v0].y).abs <
|
59
|
-
(e1[:v0].z - e2[:v0].z).abs <
|
63
|
+
( (e1[:v0].x - e2[:v0].x).abs < tol &&
|
64
|
+
(e1[:v0].y - e2[:v0].y).abs < tol &&
|
65
|
+
(e1[:v0].z - e2[:v0].z).abs < tol
|
60
66
|
) ||
|
61
|
-
( (e1[:v0].x - e2[:v1].x).abs <
|
62
|
-
(e1[:v0].y - e2[:v1].y).abs <
|
63
|
-
(e1[:v0].z - e2[:v1].z).abs <
|
67
|
+
( (e1[:v0].x - e2[:v1].x).abs < tol &&
|
68
|
+
(e1[:v0].y - e2[:v1].y).abs < tol &&
|
69
|
+
(e1[:v0].z - e2[:v1].z).abs < tol
|
64
70
|
)
|
65
71
|
) &&
|
66
72
|
(
|
67
|
-
( (e1[:v1].x - e2[:v0].x).abs <
|
68
|
-
(e1[:v1].y - e2[:v0].y).abs <
|
69
|
-
(e1[:v1].z - e2[:v0].z).abs <
|
73
|
+
( (e1[:v1].x - e2[:v0].x).abs < tol &&
|
74
|
+
(e1[:v1].y - e2[:v0].y).abs < tol &&
|
75
|
+
(e1[:v1].z - e2[:v0].z).abs < tol
|
70
76
|
) ||
|
71
|
-
( (e1[:v1].x - e2[:v1].x).abs <
|
72
|
-
(e1[:v1].y - e2[:v1].y).abs <
|
73
|
-
(e1[:v1].z - e2[:v1].z).abs <
|
77
|
+
( (e1[:v1].x - e2[:v1].x).abs < tol &&
|
78
|
+
(e1[:v1].y - e2[:v1].y).abs < tol &&
|
79
|
+
(e1[:v1].z - e2[:v1].z).abs < tol
|
74
80
|
)
|
75
81
|
)
|
76
82
|
)
|
@@ -354,6 +360,7 @@ module TBD
|
|
354
360
|
next unless valid
|
355
361
|
vec = s.vertices
|
356
362
|
area = s.grossArea
|
363
|
+
mult = s.multiplier
|
357
364
|
typ = s.subSurfaceType.downcase
|
358
365
|
type = :skylight
|
359
366
|
type = :window if typ.include?("window" )
|
@@ -442,6 +449,7 @@ module TBD
|
|
442
449
|
n: n,
|
443
450
|
gross: s.grossArea,
|
444
451
|
area: area,
|
452
|
+
mult: mult,
|
445
453
|
type: type,
|
446
454
|
u: u,
|
447
455
|
unhinged: unhinged }
|
@@ -478,7 +486,9 @@ module TBD
|
|
478
486
|
end
|
479
487
|
|
480
488
|
subarea = 0
|
481
|
-
|
489
|
+
|
490
|
+
subs.values.each { |sub| subarea += sub[:area] * sub[:mult] }
|
491
|
+
|
482
492
|
surf[:net] = surf[:gross] - subarea
|
483
493
|
|
484
494
|
# Tranform final Point 3D sets, and store.
|
@@ -604,6 +614,36 @@ module TBD
|
|
604
614
|
return mismatch("floors", floors, cl2, mth, DBG, a) unless floors.is_a?(cl2)
|
605
615
|
return mismatch("edges", edges, cl2, mth, DBG, a) unless edges.is_a?(cl2)
|
606
616
|
|
617
|
+
kva = true
|
618
|
+
|
619
|
+
# Pre-validate foundation-facing constructions.
|
620
|
+
model.getSurfaces.each do |s|
|
621
|
+
id = s.nameString
|
622
|
+
construction = s.construction
|
623
|
+
next unless s.outsideBoundaryCondition.downcase == "foundation"
|
624
|
+
|
625
|
+
if construction.empty?
|
626
|
+
log(ERR, "Invalid construction for KIVA (see #{id})")
|
627
|
+
kva = false if kva
|
628
|
+
else
|
629
|
+
construction = construction.get.to_LayeredConstruction
|
630
|
+
|
631
|
+
if construction.empty?
|
632
|
+
log(ERR, "KIVA requires layered constructions (see #{id})")
|
633
|
+
kva = false if kva
|
634
|
+
else
|
635
|
+
construction = construction.get
|
636
|
+
|
637
|
+
unless standardOpaqueLayers?(construction)
|
638
|
+
log(ERR, "KIVA requires standard materials (see #{id})")
|
639
|
+
kva = false if kva
|
640
|
+
end
|
641
|
+
end
|
642
|
+
end
|
643
|
+
end
|
644
|
+
|
645
|
+
return a unless kva
|
646
|
+
|
607
647
|
# Strictly relying on Kiva's total exposed perimeter approach.
|
608
648
|
arg = "TotalExposedPerimeter"
|
609
649
|
kiva = true
|
@@ -1,6 +1,6 @@
|
|
1
1
|
# BSD 3-Clause License
|
2
2
|
#
|
3
|
-
# Copyright (c) 2022, Denis Bourgeois
|
3
|
+
# Copyright (c) 2022-2023, Denis Bourgeois
|
4
4
|
# All rights reserved.
|
5
5
|
#
|
6
6
|
# Redistribution and use in source and binary forms, with or without
|
@@ -127,6 +127,7 @@ module OSlg
|
|
127
127
|
# @return [String] "DEBUG", "INFO", "WARN", "ERROR" or "FATAL"
|
128
128
|
def tag(level)
|
129
129
|
return @@tag[level] if level >= DEBUG && level <= FATAL
|
130
|
+
|
130
131
|
""
|
131
132
|
end
|
132
133
|
|
@@ -138,6 +139,7 @@ module OSlg
|
|
138
139
|
# @return [String] preset OSlg message
|
139
140
|
def msg(status)
|
140
141
|
return @@msg[status] if status >= DEBUG && status <= FATAL
|
142
|
+
|
141
143
|
""
|
142
144
|
end
|
143
145
|
|
@@ -163,6 +165,7 @@ module OSlg
|
|
163
165
|
@@logs << {level: level, message: message}
|
164
166
|
@@status = level if level > @@status
|
165
167
|
end
|
168
|
+
|
166
169
|
@@status
|
167
170
|
end
|
168
171
|
|
@@ -194,10 +197,11 @@ module OSlg
|
|
194
197
|
mth = mth[0...60] + " ..." if mth.length > 60
|
195
198
|
return res if mth.empty?
|
196
199
|
|
197
|
-
msg
|
200
|
+
msg = "Invalid '#{id}' "
|
198
201
|
msg += "arg ##{ord} " if ord > 0
|
199
202
|
msg += "(#{mth})"
|
200
203
|
log(lvl, msg) if lvl >= DEBUG && lvl <= FATAL
|
204
|
+
|
201
205
|
res
|
202
206
|
end
|
203
207
|
|
@@ -232,6 +236,7 @@ module OSlg
|
|
232
236
|
|
233
237
|
msg = "'#{id}' #{obj.class}? expecting #{cl} (#{mth})"
|
234
238
|
log(lvl, msg) if lvl >= DEBUG && lvl <= FATAL
|
239
|
+
|
235
240
|
res
|
236
241
|
end
|
237
242
|
|
@@ -264,8 +269,9 @@ module OSlg
|
|
264
269
|
mth = mth[0...60] + " ..." if mth.length > 60
|
265
270
|
return res if mth.empty?
|
266
271
|
|
267
|
-
msg
|
272
|
+
msg = "Missing '#{key}' key in '#{id}' Hash (#{mth})"
|
268
273
|
log(lvl, msg) if lvl >= DEBUG && lvl <= FATAL
|
274
|
+
|
269
275
|
res
|
270
276
|
end
|
271
277
|
|
@@ -294,8 +300,9 @@ module OSlg
|
|
294
300
|
mth = mth[0...60] + " ..." if mth.length > 60
|
295
301
|
return res if mth.empty?
|
296
302
|
|
297
|
-
msg
|
303
|
+
msg = "Empty '#{id}' (#{mth})"
|
298
304
|
log(lvl, msg) if lvl >= DEBUG && lvl <= FATAL
|
305
|
+
|
299
306
|
res
|
300
307
|
end
|
301
308
|
|
@@ -325,8 +332,9 @@ module OSlg
|
|
325
332
|
mth = mth[0...60] + " ..." if mth.length > 60
|
326
333
|
return res if mth.empty?
|
327
334
|
|
328
|
-
msg
|
335
|
+
msg = "Zero '#{id}' (#{mth})"
|
329
336
|
log(lvl, msg) if lvl >= DEBUG && lvl <= FATAL
|
337
|
+
|
330
338
|
res
|
331
339
|
end
|
332
340
|
|
@@ -355,9 +363,10 @@ module OSlg
|
|
355
363
|
|
356
364
|
mth = mth[0...60] + " ..." if mth.length > 60
|
357
365
|
return res if mth.empty?
|
358
|
-
|
359
|
-
msg
|
366
|
+
|
367
|
+
msg = "Negative '#{id}' (#{mth})"
|
360
368
|
log(lvl, msg) if lvl >= DEBUG && lvl <= FATAL
|
369
|
+
|
361
370
|
res
|
362
371
|
end
|
363
372
|
|
@@ -368,6 +377,7 @@ module OSlg
|
|
368
377
|
def clean!
|
369
378
|
@@status = 0
|
370
379
|
@@logs = []
|
380
|
+
|
371
381
|
@@level
|
372
382
|
end
|
373
383
|
|