ansys-pyensight-core 0.8.11__py3-none-any.whl → 0.8.12__py3-none-any.whl
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.
Potentially problematic release.
This version of ansys-pyensight-core might be problematic. Click here for more details.
- ansys/pyensight/core/deep_pixel_view.html +10 -10
- ansys/pyensight/core/libuserd.py +45 -37
- ansys/pyensight/core/locallauncher.py +2 -0
- ansys/pyensight/core/renderable.py +12 -3
- ansys/pyensight/core/utils/dsg_server.py +27 -5
- ansys/pyensight/core/utils/omniverse_cli.py +33 -24
- ansys/pyensight/core/utils/omniverse_dsg_server.py +3 -1
- ansys/pyensight/core/utils/omniverse_glb_server.py +493 -147
- ansys/pyensight/core/utils/parts.py +1 -1
- ansys/pyensight/core/utils/variables.py +1 -1
- {ansys_pyensight_core-0.8.11.dist-info → ansys_pyensight_core-0.8.12.dist-info}/METADATA +10 -8
- {ansys_pyensight_core-0.8.11.dist-info → ansys_pyensight_core-0.8.12.dist-info}/RECORD +14 -14
- {ansys_pyensight_core-0.8.11.dist-info → ansys_pyensight_core-0.8.12.dist-info}/LICENSE +0 -0
- {ansys_pyensight_core-0.8.11.dist-info → ansys_pyensight_core-0.8.12.dist-info}/WHEEL +0 -0
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
<head>
|
|
4
4
|
<link rel="stylesheet" type="text/css" href="/bootstrap.min.cssOPTIONAL_QUERY"/>
|
|
5
5
|
|
|
6
|
-
<script src='/
|
|
6
|
+
<script src='/jqueryJQUERY_VERSION.min.jsOPTIONAL_QUERY'></script>
|
|
7
7
|
<script src='/geotiff.jsOPTIONAL_QUERY'></script>
|
|
8
8
|
<script src='/geotiff_nexus.jsOPTIONAL_QUERY'></script>
|
|
9
9
|
<script src="/bootstrap.min.jsOPTIONAL_QUERY"></script>
|
|
@@ -76,15 +76,15 @@
|
|
|
76
76
|
<div style="margin: 0 auto; display:flex; justify-content:center;">
|
|
77
77
|
<!-- tooltip parent for img --->
|
|
78
78
|
<div id="probe_display_ITEMID"
|
|
79
|
-
data-
|
|
80
|
-
data-
|
|
81
|
-
data-
|
|
82
|
-
data-
|
|
83
|
-
data-
|
|
84
|
-
data-
|
|
85
|
-
data-
|
|
86
|
-
data-
|
|
87
|
-
data-
|
|
79
|
+
data-BS_PREFIXtoggle="tooltip"
|
|
80
|
+
data-BS_PREFIXplacement="bottom"
|
|
81
|
+
data-BS_PREFIXfallbackPlacement="['top', 'right']"
|
|
82
|
+
data-BS_PREFIXhtml="true"
|
|
83
|
+
data-BS_PREFIXcontainer="body"
|
|
84
|
+
data-BS_PREFIXboundary="viewport"
|
|
85
|
+
data-BS_PREFIXanimation="false"
|
|
86
|
+
data-BS_PREFIXtrigger="manual"
|
|
87
|
+
data-BS_PREFIXtitle='<span class="f-1r">
|
|
88
88
|
<span>X, Y : <span id="probe_xy_ITEMID">0, 0</span></span>
|
|
89
89
|
<br>
|
|
90
90
|
<span id="probe_result_ITEMID"></span>
|
ansys/pyensight/core/libuserd.py
CHANGED
|
@@ -63,6 +63,22 @@ warnings.warn(
|
|
|
63
63
|
)
|
|
64
64
|
|
|
65
65
|
|
|
66
|
+
def _build_enum(name: str, pb_enum: Any, flag: bool = False) -> Union[enum.IntEnum, enum.IntFlag]:
|
|
67
|
+
values = {}
|
|
68
|
+
for v in pb_enum:
|
|
69
|
+
values[v[0]] = v[1]
|
|
70
|
+
if flag:
|
|
71
|
+
return enum.IntFlag(name, values)
|
|
72
|
+
return enum.IntEnum(name, values)
|
|
73
|
+
|
|
74
|
+
|
|
75
|
+
ErrorCodes = _build_enum("ErrorCodes", libuserd_pb2.ErrorCodes.items())
|
|
76
|
+
ElementType = _build_enum("ElementType", libuserd_pb2.ElementType.items())
|
|
77
|
+
VariableLocation = _build_enum("VariableLocation", libuserd_pb2.VariableLocation.items())
|
|
78
|
+
VariableType = _build_enum("VariableType", libuserd_pb2.VariableType.items())
|
|
79
|
+
PartHints = _build_enum("PartHints", libuserd_pb2.PartHints.items(), flag=True)
|
|
80
|
+
|
|
81
|
+
|
|
66
82
|
class LibUserdError(Exception):
|
|
67
83
|
"""
|
|
68
84
|
This class is an exception object raised from the libuserd
|
|
@@ -179,9 +195,9 @@ class Variable(object):
|
|
|
179
195
|
The unit label of this variable, "Pa" for example.
|
|
180
196
|
unitDims : str
|
|
181
197
|
The dimensions of this variable, "L/S" for distance per second.
|
|
182
|
-
location : "
|
|
198
|
+
location : "VariableLocation"
|
|
183
199
|
The location of this variable.
|
|
184
|
-
type : "
|
|
200
|
+
type : "VariableType"
|
|
185
201
|
The type of this variable.
|
|
186
202
|
timeVarying : bool
|
|
187
203
|
True if the variable is time-varying.
|
|
@@ -200,8 +216,8 @@ class Variable(object):
|
|
|
200
216
|
self.name = pb.name
|
|
201
217
|
self.unitLabel = pb.unitLabel
|
|
202
218
|
self.unitDims = pb.unitDims
|
|
203
|
-
self.location =
|
|
204
|
-
self.type =
|
|
219
|
+
self.location = VariableLocation(pb.varLocation) # type: ignore
|
|
220
|
+
self.type = VariableType(pb.type) # type: ignore
|
|
205
221
|
self.timeVarying = pb.timeVarying
|
|
206
222
|
self.isComplex = pb.isComplex
|
|
207
223
|
self.interleaveFlag = pb.interleaveFlag
|
|
@@ -240,7 +256,7 @@ class Part(object):
|
|
|
240
256
|
reader_id : int
|
|
241
257
|
The id of the Reader this part is associated with.
|
|
242
258
|
hints : int
|
|
243
|
-
See: `
|
|
259
|
+
See: `PartHints`.
|
|
244
260
|
reader_api_version : float
|
|
245
261
|
The API version number of the USERD reader this part was read with.
|
|
246
262
|
metadata : Dict[str, str]
|
|
@@ -315,7 +331,7 @@ class Part(object):
|
|
|
315
331
|
>>> part = reader.parts()[0]
|
|
316
332
|
>>> elements = part.elements()
|
|
317
333
|
>>> for etype, count in elements.items():
|
|
318
|
-
... print(
|
|
334
|
+
... print(libuserd.ElementType(etype).name, count)
|
|
319
335
|
|
|
320
336
|
"""
|
|
321
337
|
self._userd.connect_check()
|
|
@@ -350,14 +366,14 @@ class Part(object):
|
|
|
350
366
|
--------
|
|
351
367
|
|
|
352
368
|
>>> part = reader.parts()[0]
|
|
353
|
-
>>> conn = part.element_conn(
|
|
354
|
-
>>> nodes_per_elem = libuserd_instance.nodes_per_element(
|
|
369
|
+
>>> conn = part.element_conn(libuserd.ElementType.HEX08)
|
|
370
|
+
>>> nodes_per_elem = libuserd_instance.nodes_per_element(libuserd.ElementType.HEX08)
|
|
355
371
|
>>> conn.shape = (len(conn)//nodes_per_elem, nodes_per_elem)
|
|
356
372
|
>>> for element in conn:
|
|
357
373
|
... print(element)
|
|
358
374
|
|
|
359
375
|
"""
|
|
360
|
-
if elem_type >=
|
|
376
|
+
if elem_type >= ElementType.NSIDED: # type: ignore
|
|
361
377
|
raise RuntimeError(f"Element type {elem_type} is not valid for this call")
|
|
362
378
|
pb = libuserd_pb2.Part_element_connRequest()
|
|
363
379
|
pb.part_id = self.id
|
|
@@ -375,7 +391,7 @@ class Part(object):
|
|
|
375
391
|
error = self._userd.libuserd_exception(e)
|
|
376
392
|
# if we get an "UNKNOWN" error, then return an empty array
|
|
377
393
|
if isinstance(error, LibUserdError):
|
|
378
|
-
if error.code ==
|
|
394
|
+
if error.code == ErrorCodes.UNKNOWN: # type: ignore
|
|
379
395
|
return numpy.empty(0, dtype=numpy.uint32)
|
|
380
396
|
raise error
|
|
381
397
|
return conn
|
|
@@ -1147,27 +1163,12 @@ class LibUserd(object):
|
|
|
1147
1163
|
raise RuntimeError(f"Unable to start the gRPC server ({str(self.server_pathname)})")
|
|
1148
1164
|
|
|
1149
1165
|
def _build_enums(self) -> None:
|
|
1150
|
-
|
|
1151
|
-
|
|
1152
|
-
|
|
1153
|
-
|
|
1154
|
-
self.
|
|
1155
|
-
|
|
1156
|
-
for v in libuserd_pb2.ElementType.items():
|
|
1157
|
-
values[v[0]] = v[1]
|
|
1158
|
-
self.ElementType = enum.IntEnum("ElementType", values) # type: ignore
|
|
1159
|
-
values = {}
|
|
1160
|
-
for v in libuserd_pb2.VariableLocation.items():
|
|
1161
|
-
values[v[0]] = v[1]
|
|
1162
|
-
self.VariableLocation = enum.IntEnum("VariableLocation", values) # type: ignore
|
|
1163
|
-
values = {}
|
|
1164
|
-
for v in libuserd_pb2.VariableType.items():
|
|
1165
|
-
values[v[0]] = v[1]
|
|
1166
|
-
self.VariableType = enum.IntEnum("VariableType", values) # type: ignore
|
|
1167
|
-
values = {}
|
|
1168
|
-
for v in libuserd_pb2.PartHints.items():
|
|
1169
|
-
values[v[0]] = v[1]
|
|
1170
|
-
self.PartHints = enum.IntEnum("PartHints", values) # type: ignore
|
|
1166
|
+
# retained for backward compatibility
|
|
1167
|
+
self.ErrorCodes = ErrorCodes
|
|
1168
|
+
self.ElementType = ElementType
|
|
1169
|
+
self.VariableLocation = VariableLocation
|
|
1170
|
+
self.VariableType = VariableType
|
|
1171
|
+
self.PartHints = PartHints
|
|
1171
1172
|
|
|
1172
1173
|
def _pull_docker_image(self) -> None:
|
|
1173
1174
|
"""Pull the docker image if not available"""
|
|
@@ -1329,6 +1330,13 @@ class LibUserd(object):
|
|
|
1329
1330
|
# ways, we'll add that one too, just in case.
|
|
1330
1331
|
dirs_to_check.append(os.path.join(env_inst, "CEI"))
|
|
1331
1332
|
|
|
1333
|
+
try:
|
|
1334
|
+
import enve
|
|
1335
|
+
|
|
1336
|
+
dirs_to_check.append(enve.home())
|
|
1337
|
+
except ModuleNotFoundError:
|
|
1338
|
+
pass
|
|
1339
|
+
|
|
1332
1340
|
if "CEI_HOME" in os.environ:
|
|
1333
1341
|
env_inst = os.environ["CEI_HOME"]
|
|
1334
1342
|
dirs_to_check.append(env_inst)
|
|
@@ -1577,7 +1585,7 @@ class LibUserd(object):
|
|
|
1577
1585
|
Parameters
|
|
1578
1586
|
----------
|
|
1579
1587
|
element_type
|
|
1580
|
-
The element type:
|
|
1588
|
+
The element type: ElementType enum value
|
|
1581
1589
|
|
|
1582
1590
|
Returns
|
|
1583
1591
|
-------
|
|
@@ -1602,7 +1610,7 @@ class LibUserd(object):
|
|
|
1602
1610
|
Parameters
|
|
1603
1611
|
----------
|
|
1604
1612
|
element_type
|
|
1605
|
-
The element type:
|
|
1613
|
+
The element type: ElementType enum value
|
|
1606
1614
|
|
|
1607
1615
|
Returns
|
|
1608
1616
|
-------
|
|
@@ -1625,7 +1633,7 @@ class LibUserd(object):
|
|
|
1625
1633
|
Parameters
|
|
1626
1634
|
----------
|
|
1627
1635
|
element_type
|
|
1628
|
-
The element type:
|
|
1636
|
+
The element type: ElementType enum value
|
|
1629
1637
|
|
|
1630
1638
|
Returns
|
|
1631
1639
|
-------
|
|
@@ -1648,7 +1656,7 @@ class LibUserd(object):
|
|
|
1648
1656
|
Parameters
|
|
1649
1657
|
----------
|
|
1650
1658
|
element_type
|
|
1651
|
-
The element type:
|
|
1659
|
+
The element type: ElementType enum value
|
|
1652
1660
|
|
|
1653
1661
|
Returns
|
|
1654
1662
|
-------
|
|
@@ -1671,7 +1679,7 @@ class LibUserd(object):
|
|
|
1671
1679
|
Parameters
|
|
1672
1680
|
----------
|
|
1673
1681
|
element_type
|
|
1674
|
-
The element type:
|
|
1682
|
+
The element type: ElementType enum value
|
|
1675
1683
|
|
|
1676
1684
|
Returns
|
|
1677
1685
|
-------
|
|
@@ -1693,7 +1701,7 @@ class LibUserd(object):
|
|
|
1693
1701
|
Part.element_conn() method. This function returns the number of those elements
|
|
1694
1702
|
and may be useful in common element type handling code.
|
|
1695
1703
|
|
|
1696
|
-
Note: The value is effectively int(
|
|
1704
|
+
Note: The value is effectively int(ElementType.NSIDED).
|
|
1697
1705
|
|
|
1698
1706
|
Returns
|
|
1699
1707
|
-------
|
|
@@ -389,10 +389,17 @@ class RenderableDeepPixel(Renderable):
|
|
|
389
389
|
for script in ["geotiff.js", "geotiff_nexus.js", "bootstrap.min.js"]:
|
|
390
390
|
name = base_name + f"'{script}')"
|
|
391
391
|
cmd += f'shutil.copy({name}, r"""{self._session.launcher.session_directory}""")\n'
|
|
392
|
+
name = "os.path.join(enve.home(), f'nexus{ceiversion.nexus_suffix}', 'django', "
|
|
393
|
+
name += "'website', 'static', 'website', 'content', 'bootstrap.min.css')"
|
|
394
|
+
cmd += f'shutil.copy({name}, r"""{self._session.launcher.session_directory}""")\n'
|
|
395
|
+
self._session.cmd(cmd, do_eval=False)
|
|
396
|
+
# With Bootstrap 5 (2025 R1), class names have '-bs-' in them, e.g. 'data-bs-toggle' vs 'data-toggle'
|
|
397
|
+
bs_prefix = "bs-"
|
|
398
|
+
jquery_version = ""
|
|
392
399
|
if int(self._session._cei_suffix) < 251:
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
400
|
+
bs_prefix = ""
|
|
401
|
+
jquery_version = "-3.4.1"
|
|
402
|
+
jquery = f"jquery{jquery_version}.min.js"
|
|
396
403
|
cmd = "import shutil, enve, ceiversion, os.path\n"
|
|
397
404
|
name = base_name + f"'{jquery}')"
|
|
398
405
|
cmd += "try:"
|
|
@@ -409,6 +416,8 @@ class RenderableDeepPixel(Renderable):
|
|
|
409
416
|
html = html.replace("TIFF_URL", tiff_url)
|
|
410
417
|
html = html.replace("ITEMID", self._guid)
|
|
411
418
|
html = html.replace("OPTIONAL_QUERY", optional_query)
|
|
419
|
+
html = html.replace("JQUERY_VERSION", jquery_version)
|
|
420
|
+
html = html.replace("BS_PREFIX", bs_prefix)
|
|
412
421
|
# refresh the remote HTML
|
|
413
422
|
self._save_remote_html_page(html)
|
|
414
423
|
super().update()
|
|
@@ -101,6 +101,12 @@ class Part(object):
|
|
|
101
101
|
self.tcoords[
|
|
102
102
|
cmd.chunk_offset : cmd.chunk_offset + len(cmd.flt_array)
|
|
103
103
|
] = cmd.flt_array
|
|
104
|
+
|
|
105
|
+
# Add the variable hash to the Part's hash, to pick up palette changes
|
|
106
|
+
var_cmd = self.session.variables.get(cmd.variable_id, None)
|
|
107
|
+
if var_cmd is not None:
|
|
108
|
+
self.hash.update(var_cmd.hash.encode("utf-8"))
|
|
109
|
+
|
|
104
110
|
if self.cmd.node_size_variableid == cmd.variable_id: # type: ignore
|
|
105
111
|
# Receive the node size var values
|
|
106
112
|
if self.node_sizes.size != cmd.total_array_size:
|
|
@@ -618,6 +624,15 @@ class DSGSession(object):
|
|
|
618
624
|
"""
|
|
619
625
|
logging.warning(s)
|
|
620
626
|
|
|
627
|
+
@staticmethod
|
|
628
|
+
def error(s: str) -> None:
|
|
629
|
+
"""Issue an error to the logging system
|
|
630
|
+
|
|
631
|
+
The logging message is mapped to "error" and cannot be blocked via verbosity
|
|
632
|
+
checks.
|
|
633
|
+
"""
|
|
634
|
+
logging.error(s)
|
|
635
|
+
|
|
621
636
|
def start(self) -> int:
|
|
622
637
|
"""Start a gRPC connection to an EnSight instance
|
|
623
638
|
|
|
@@ -741,6 +756,13 @@ class DSGSession(object):
|
|
|
741
756
|
except queue.Empty:
|
|
742
757
|
return None
|
|
743
758
|
|
|
759
|
+
def _reset(self):
|
|
760
|
+
self._variables = {}
|
|
761
|
+
self._groups = {}
|
|
762
|
+
self._part = Part(self)
|
|
763
|
+
self._scene_bounds = None
|
|
764
|
+
self._mesh_block_count = 0 # reset when a new group shows up
|
|
765
|
+
|
|
744
766
|
def handle_one_update(self) -> None:
|
|
745
767
|
"""Monitor the DSG stream and handle a single update operation
|
|
746
768
|
|
|
@@ -759,11 +781,7 @@ class DSGSession(object):
|
|
|
759
781
|
cmd = self._get_next_message()
|
|
760
782
|
|
|
761
783
|
# Start anew
|
|
762
|
-
self.
|
|
763
|
-
self._groups = {}
|
|
764
|
-
self._part = Part(self)
|
|
765
|
-
self._scene_bounds = None
|
|
766
|
-
self._mesh_block_count = 0 # reset when a new group shows up
|
|
784
|
+
self._reset()
|
|
767
785
|
self._callback_handler.begin_update()
|
|
768
786
|
|
|
769
787
|
# Update our status
|
|
@@ -839,7 +857,11 @@ class DSGSession(object):
|
|
|
839
857
|
try:
|
|
840
858
|
self._callback_handler.finalize_part(self.part)
|
|
841
859
|
except Exception as e:
|
|
860
|
+
import traceback
|
|
861
|
+
|
|
842
862
|
self.warn(f"Error encountered while finalizing part geometry: {str(e)}")
|
|
863
|
+
traceback_str = "".join(traceback.format_tb(e.__traceback__))
|
|
864
|
+
logging.debug(f"Traceback: {traceback_str}")
|
|
843
865
|
self._mesh_block_count += 1
|
|
844
866
|
|
|
845
867
|
def _handle_part(self, part_cmd: Any) -> None:
|
|
@@ -276,17 +276,16 @@ class OmniverseGeometryServer(object):
|
|
|
276
276
|
update_handler = ov_dsg_server.OmniverseUpdateHandler(omni_link)
|
|
277
277
|
|
|
278
278
|
# Link it to the GLB file monitoring service
|
|
279
|
-
glb_link = ov_glb_server.GLBSession(
|
|
280
|
-
verbose=1,
|
|
281
|
-
handler=update_handler,
|
|
282
|
-
)
|
|
279
|
+
glb_link = ov_glb_server.GLBSession(verbose=1, handler=update_handler, vrmode=self.vrmode)
|
|
283
280
|
if single_file_upload:
|
|
284
281
|
start_time = time.time()
|
|
285
282
|
logging.info(f"Uploading file: {the_dir}.")
|
|
286
283
|
try:
|
|
284
|
+
glb_link.start_uploads([0.0, 0.0])
|
|
287
285
|
glb_link.upload_file(the_dir)
|
|
286
|
+
glb_link.end_uploads()
|
|
288
287
|
except Exception as error:
|
|
289
|
-
logging.
|
|
288
|
+
logging.error(f"Unable to upload file: {the_dir}: {error}")
|
|
290
289
|
logging.info(f"Uploaded in {(time.time() - start_time):.2f}")
|
|
291
290
|
else:
|
|
292
291
|
logging.info(f"Starting file monitoring for {the_dir}.")
|
|
@@ -297,7 +296,7 @@ class OmniverseGeometryServer(object):
|
|
|
297
296
|
while not os.path.exists(stop_file):
|
|
298
297
|
loop_time = time.time()
|
|
299
298
|
files_to_remove = []
|
|
300
|
-
for filename in glob.glob(os.path.join(the_dir, "
|
|
299
|
+
for filename in glob.glob(os.path.join(the_dir, "*.upload")):
|
|
301
300
|
# reset to the launch URI/directory
|
|
302
301
|
omni_link.destination = orig_destination
|
|
303
302
|
# Keep track of the files and time values
|
|
@@ -317,7 +316,7 @@ class OmniverseGeometryServer(object):
|
|
|
317
316
|
with open(filename, "r") as fp:
|
|
318
317
|
glb_info = json.load(fp)
|
|
319
318
|
except Exception:
|
|
320
|
-
logging.
|
|
319
|
+
logging.error(f"Unable to read file: {filename}")
|
|
321
320
|
continue
|
|
322
321
|
# if specified, set the URI/directory target
|
|
323
322
|
omni_link.destination = glb_info.get("destination", orig_destination)
|
|
@@ -326,28 +325,35 @@ class OmniverseGeometryServer(object):
|
|
|
326
325
|
files_to_remove.extend(the_files)
|
|
327
326
|
# Times not used for now, but parse them anyway
|
|
328
327
|
the_times = glb_info.get("times", [0.0] * len(the_files))
|
|
328
|
+
file_timestamps.extend(the_times)
|
|
329
329
|
# Validate a few things
|
|
330
330
|
if len(the_files) != len(the_times):
|
|
331
|
-
logging.
|
|
331
|
+
logging.error(
|
|
332
332
|
f"Number of times and files are not the same in: {filename}"
|
|
333
333
|
)
|
|
334
334
|
continue
|
|
335
|
-
if len(set(the_times)) != 1:
|
|
336
|
-
logging.warning("Time values not currently supported.")
|
|
337
|
-
if len(the_files) > 1:
|
|
338
|
-
logging.warning("Multiple glb files not currently fully supported.")
|
|
339
335
|
files_to_process.extend(the_files)
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
336
|
+
# manage time
|
|
337
|
+
timeline = sorted(set(file_timestamps))
|
|
338
|
+
if len(timeline) != 1:
|
|
339
|
+
logging.warning("Time values not currently supported.")
|
|
340
|
+
if len(files_to_process) > 1:
|
|
341
|
+
logging.warning("Multiple glb files not currently fully supported.")
|
|
342
|
+
# Upload the files
|
|
343
|
+
glb_link.start_uploads([timeline[0], timeline[-1]])
|
|
344
|
+
for glb_file, timestamp in zip(files_to_process, file_timestamps):
|
|
345
|
+
start_time = time.time()
|
|
346
|
+
logging.info(f"Uploading file: {glb_file} to {omni_link.destination}.")
|
|
347
|
+
try:
|
|
348
|
+
time_idx = timeline.index(timestamp) + 1
|
|
349
|
+
if time_idx == len(timeline):
|
|
350
|
+
time_idx -= 1
|
|
351
|
+
limits = [timestamp, timeline[time_idx]]
|
|
352
|
+
glb_link.upload_file(glb_file, timeline=limits)
|
|
353
|
+
except Exception as error:
|
|
354
|
+
logging.error(f"Unable to upload file: {glb_file}: {error}")
|
|
355
|
+
logging.info(f"Uploaded in {(time.time() - start_time):.2f}s")
|
|
356
|
+
glb_link.end_uploads()
|
|
351
357
|
for filename in files_to_remove:
|
|
352
358
|
try:
|
|
353
359
|
# Only delete the file if it is in the_dir_path
|
|
@@ -361,7 +367,10 @@ class OmniverseGeometryServer(object):
|
|
|
361
367
|
except Exception as error:
|
|
362
368
|
logging.error(f"Error encountered while monitoring: {error}")
|
|
363
369
|
logging.info("Stopping file monitoring.")
|
|
364
|
-
|
|
370
|
+
try:
|
|
371
|
+
os.remove(stop_file)
|
|
372
|
+
except IOError:
|
|
373
|
+
logging.error("Unable to remove 'shutdown' file.")
|
|
365
374
|
|
|
366
375
|
omni_link.shutdown()
|
|
367
376
|
|
|
@@ -401,12 +401,14 @@ class OmniverseWrapper(object):
|
|
|
401
401
|
self, stage, mesh, root_name, diffuse=[1.0, 1.0, 1.0, 1.0], variable=None
|
|
402
402
|
):
|
|
403
403
|
# https://graphics.pixar.com/usd/release/spec_usdpreviewsurface.html
|
|
404
|
+
# Use ior==1.0 to be more like EnSight - rays of light do not bend when passing through transparent objs
|
|
404
405
|
material = UsdShade.Material.Define(stage, root_name + "/Material")
|
|
405
406
|
pbrShader = UsdShade.Shader.Define(stage, root_name + "/Material/PBRShader")
|
|
406
407
|
pbrShader.CreateIdAttr("UsdPreviewSurface")
|
|
407
408
|
pbrShader.CreateInput("roughness", Sdf.ValueTypeNames.Float).Set(1.0)
|
|
408
409
|
pbrShader.CreateInput("metallic", Sdf.ValueTypeNames.Float).Set(0.0)
|
|
409
410
|
pbrShader.CreateInput("opacity", Sdf.ValueTypeNames.Float).Set(diffuse[3])
|
|
411
|
+
pbrShader.CreateInput("ior", Sdf.ValueTypeNames.Float).Set(1.0)
|
|
410
412
|
pbrShader.CreateInput("useSpecularWorkflow", Sdf.ValueTypeNames.Int).Set(1)
|
|
411
413
|
if variable:
|
|
412
414
|
stReader = UsdShade.Shader.Define(stage, root_name + "/Material/stReader")
|
|
@@ -416,7 +418,7 @@ class OmniverseWrapper(object):
|
|
|
416
418
|
)
|
|
417
419
|
diffuseTextureSampler.CreateIdAttr("UsdUVTexture")
|
|
418
420
|
name = self.clean_name(variable.name)
|
|
419
|
-
filename =
|
|
421
|
+
filename = f"./Textures/palette_{name}.png"
|
|
420
422
|
diffuseTextureSampler.CreateInput("file", Sdf.ValueTypeNames.Asset).Set(filename)
|
|
421
423
|
diffuseTextureSampler.CreateInput("st", Sdf.ValueTypeNames.Float2).ConnectToSource(
|
|
422
424
|
stReader.ConnectableAPI(), "result"
|