ansys-pyensight-core 0.9.9__tar.gz → 0.9.11__tar.gz

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.

Files changed (37) hide show
  1. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/PKG-INFO +7 -6
  2. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/pyproject.toml +5 -5
  3. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/dockerlauncher.py +2 -1
  4. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/locallauncher.py +13 -1
  5. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/session.py +14 -11
  6. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/omniverse_dsg_server.py +50 -32
  7. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/LICENSE +0 -0
  8. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/README.rst +0 -0
  9. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/__init__.py +0 -0
  10. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/common.py +0 -0
  11. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/deep_pixel_view.html +0 -0
  12. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/dvs.py +0 -0
  13. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/enscontext.py +0 -0
  14. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/enshell_grpc.py +0 -0
  15. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/ensight_grpc.py +0 -0
  16. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/ensobj.py +0 -0
  17. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/launch_ensight.py +0 -0
  18. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/launcher.py +0 -0
  19. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/libuserd.py +0 -0
  20. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/listobj.py +0 -0
  21. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/py.typed +0 -0
  22. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/renderable.py +0 -0
  23. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/sgeo_poll.html +0 -0
  24. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/__init__.py +0 -0
  25. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/adr.py +0 -0
  26. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/dsg_server.py +0 -0
  27. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/export.py +0 -0
  28. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/omniverse.py +0 -0
  29. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/omniverse_cli.py +0 -0
  30. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/omniverse_glb_server.py +0 -0
  31. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/parts.py +0 -0
  32. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/query.py +0 -0
  33. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/readers.py +0 -0
  34. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/resources/Materials/000_sky.exr +0 -0
  35. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/support.py +0 -0
  36. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/variables.py +0 -0
  37. {ansys_pyensight_core-0.9.9 → ansys_pyensight_core-0.9.11}/src/ansys/pyensight/core/utils/views.py +0 -0
@@ -1,6 +1,6 @@
1
- Metadata-Version: 2.3
1
+ Metadata-Version: 2.4
2
2
  Name: ansys-pyensight-core
3
- Version: 0.9.9
3
+ Version: 0.9.11
4
4
  Summary: A python wrapper for Ansys EnSight
5
5
  Author-email: "ANSYS, Inc." <pyansys.core@ansys.com>
6
6
  Maintainer-email: "ANSYS, Inc." <pyansys.core@ansys.com>
@@ -15,8 +15,9 @@ Classifier: Programming Language :: Python :: 3.9
15
15
  Classifier: Programming Language :: Python :: 3.10
16
16
  Classifier: Programming Language :: Python :: 3.11
17
17
  Classifier: Programming Language :: Python :: 3.12
18
+ License-File: LICENSE
18
19
  Requires-Dist: importlib-metadata>=4.0; python_version<='3.8'
19
- Requires-Dist: ansys-api-pyensight==0.4.6
20
+ Requires-Dist: ansys-api-pyensight==0.4.7
20
21
  Requires-Dist: requests>=2.28.2
21
22
  Requires-Dist: docker>=6.1.0
22
23
  Requires-Dist: urllib3<3.0.0
@@ -32,7 +33,7 @@ Requires-Dist: bump2version>=1.0.1 ; extra == "dev"
32
33
  Requires-Dist: ipdb>=0.9.4 ; extra == "dev"
33
34
  Requires-Dist: dill>=0.3.5.1 ; extra == "dev"
34
35
  Requires-Dist: pre-commit>=3.3.3 ; extra == "dev"
35
- Requires-Dist: Sphinx==8.0.2 ; extra == "doc"
36
+ Requires-Dist: Sphinx==8.1.3 ; extra == "doc"
36
37
  Requires-Dist: numpydoc==1.8.0 ; extra == "doc"
37
38
  Requires-Dist: ansys-sphinx-theme==1.1.1 ; extra == "doc"
38
39
  Requires-Dist: sphinx-copybutton==0.5.2 ; extra == "doc"
@@ -47,11 +48,11 @@ Requires-Dist: coverage-badge==1.1.2 ; extra == "doc"
47
48
  Requires-Dist: sphinxcontrib-video==0.2.1 ; extra == "doc"
48
49
  Requires-Dist: usd-core>=24.8 ; extra == "doc"
49
50
  Requires-Dist: pygltflib>=1.16.2 ; extra == "doc"
50
- Requires-Dist: pytest==8.3.2 ; extra == "tests"
51
+ Requires-Dist: pytest==8.3.5 ; extra == "tests"
51
52
  Requires-Dist: pytest-cov==5.0.0 ; extra == "tests"
52
53
  Requires-Dist: dill>=0.3.5.1 ; extra == "tests"
53
54
  Requires-Dist: pytest-mock==3.10.0 ; extra == "tests"
54
- Requires-Dist: urllib3==2.2.2 ; extra == "tests"
55
+ Requires-Dist: urllib3==2.3.0 ; extra == "tests"
55
56
  Requires-Dist: requests>=2.28.2 ; extra == "tests"
56
57
  Requires-Dist: docker>=6.1.0 ; extra == "tests"
57
58
  Requires-Dist: pytest-xdist==3.6.1 ; extra == "tests"
@@ -6,7 +6,7 @@ build-backend = "flit_core.buildapi"
6
6
 
7
7
  [project]
8
8
  name = "ansys-pyensight-core"
9
- version = "0.9.9"
9
+ version = "0.9.11"
10
10
  description = "A python wrapper for Ansys EnSight"
11
11
  readme = "README.rst"
12
12
  requires-python = ">=3.9,<4"
@@ -27,7 +27,7 @@ classifiers = [
27
27
 
28
28
  dependencies = [
29
29
  "importlib-metadata>=4.0; python_version<='3.8'",
30
- "ansys-api-pyensight==0.4.6",
30
+ "ansys-api-pyensight==0.4.7",
31
31
  "requests>=2.28.2",
32
32
  "docker>=6.1.0",
33
33
  "urllib3<3.0.0",
@@ -49,18 +49,18 @@ dev = [
49
49
  "pre-commit>=3.3.3",
50
50
  ]
51
51
  tests = [
52
- "pytest==8.3.2",
52
+ "pytest==8.3.5",
53
53
  "pytest-cov==5.0.0",
54
54
  "dill>=0.3.5.1",
55
55
  "pytest-mock==3.10.0",
56
- "urllib3==2.2.2",
56
+ "urllib3==2.3.0",
57
57
  "requests>=2.28.2",
58
58
  "docker>=6.1.0",
59
59
  "pytest-xdist==3.6.1",
60
60
  "pytest-rerunfailures~=14.0",
61
61
  ]
62
62
  doc = [
63
- "Sphinx==8.0.2",
63
+ "Sphinx==8.1.3",
64
64
  "numpydoc==1.8.0",
65
65
  "ansys-sphinx-theme==1.1.1",
66
66
  "sphinx-copybutton==0.5.2",
@@ -403,6 +403,7 @@ class DockerLauncher(Launcher):
403
403
  cmd += f" --ensight-ws-port {ws_port}"
404
404
  cmd += f" --ensight-session-directory {self._session_directory}"
405
405
  cmd += f" --ensight-secret-key {self._secret_key}"
406
+ cmd += "--main-show-gui 'False'"
406
407
  logging.debug(f"Starting WebUI: {cmd}\n")
407
408
  ret = self._enshell.start_other(cmd, extra_env=container_env_str)
408
409
  if ret[0] != 0: # pragma: no cover
@@ -619,7 +620,7 @@ class DockerLauncher(Launcher):
619
620
  pass
620
621
  try:
621
622
  logging.debug("Removing the Docker Container.\n")
622
- self._container.remove()
623
+ self._container.remove(force=True)
623
624
  except Exception:
624
625
  pass
625
626
  self._container = None
@@ -107,9 +107,20 @@ class LocalLauncher(Launcher):
107
107
  cmd += [webui_script]
108
108
  version = re.findall(r"nexus(\d+)", webui_script)[0]
109
109
  path_to_webui = self._install_path
110
- path_to_webui = os.path.join(
110
+ # Dev environment
111
+ path_to_webui_internal = os.path.join(
111
112
  path_to_webui, f"nexus{version}", f"ansys{version}", "ensight", "WebUI", "web", "ui"
112
113
  )
114
+ # Ansys environment
115
+ paths_to_webui_ansys = [
116
+ os.path.join(os.path.dirname(path_to_webui), "simcfd", "web", "ui"),
117
+ os.path.join(os.path.dirname(path_to_webui), "fluidsone", "web", "ui"),
118
+ ]
119
+ path_to_webui = path_to_webui_internal
120
+ for path in paths_to_webui_ansys:
121
+ if os.path.exists(path):
122
+ path_to_webui = path
123
+ break
113
124
  cmd += ["--server-listen-port", str(self._ports[5])]
114
125
  cmd += ["--server-web-roots", path_to_webui]
115
126
  cmd += ["--ensight-grpc-port", str(self._ports[0])]
@@ -117,6 +128,7 @@ class LocalLauncher(Launcher):
117
128
  cmd += ["--ensight-ws-port", str(self._ports[3])]
118
129
  cmd += ["--ensight-session-directory", self._session_directory]
119
130
  cmd += ["--ensight-secret-key", self._secret_key]
131
+ cmd += ["--main-show-gui", "'False'"]
120
132
  if "PYENSIGHT_DEBUG" in os.environ:
121
133
  try:
122
134
  if int(os.environ["PYENSIGHT_DEBUG"]) > 0:
@@ -213,6 +213,7 @@ class Session:
213
213
  # Because this session can have allocated significant external resources
214
214
  # we very much want a chance to close it up cleanly. It is legal to
215
215
  # call close() twice on this class if needed.
216
+ self._already_closed = False
216
217
  atexit.register(self.close)
217
218
 
218
219
  # Speed up subtype lookups:
@@ -1050,17 +1051,19 @@ class Session:
1050
1051
  Close the current session and its gRPC connection.
1051
1052
  """
1052
1053
  # if version 242 or higher, free any objects we have cached there
1053
- if self.cei_suffix >= "242":
1054
- try:
1055
- self._release_remote_objects()
1056
- except RuntimeError: # pragma: no cover
1057
- # handle some intermediate EnSight builds.
1058
- pass
1059
- if self._launcher and self._halt_ensight_on_close:
1060
- self._launcher.close(self)
1061
- else:
1062
- # lightweight shtudown, just close the gRC connection
1063
- self._grpc.shutdown(stop_ensight=False)
1054
+ if not self._already_closed:
1055
+ if self.cei_suffix >= "242":
1056
+ try:
1057
+ self._release_remote_objects()
1058
+ except RuntimeError: # pragma: no cover
1059
+ # handle some intermediate EnSight builds.
1060
+ pass
1061
+ if self._launcher and self._halt_ensight_on_close:
1062
+ self._launcher.close(self)
1063
+ else:
1064
+ # lightweight shtudown, just close the gRC connection
1065
+ self._grpc.shutdown(stop_ensight=False)
1066
+ self._already_closed = True
1064
1067
  self._launcher = None
1065
1068
 
1066
1069
  def _build_utils_interface(self) -> None:
@@ -49,12 +49,14 @@ class OmniverseWrapper(object):
49
49
  self._stage = None
50
50
  self._destinationPath: str = ""
51
51
  self._old_stages: list = []
52
- self._stagename = "dsg_scene.usd"
52
+ self._stagename: str = "dsg_scene.usd"
53
53
  self._live_edit: bool = live_edit
54
54
  if self._live_edit:
55
55
  self._stagename = "dsg_scene.live"
56
56
  # USD time slider will have 120 tick marks per second of animation time
57
- self._time_codes_per_second = 120.0
57
+ self._time_codes_per_second: float = 120.0
58
+ # Omniverse content currently only scales correctly for scenes in cm. DJB, Feb 2025
59
+ self._units_per_meter: float = 100.0
58
60
 
59
61
  if destination:
60
62
  self.destination = destination
@@ -149,8 +151,7 @@ class OmniverseWrapper(object):
149
151
  # record the stage in the "_old_stages" list.
150
152
  self._old_stages.append(self.stage_url())
151
153
  UsdGeom.SetStageUpAxis(self._stage, UsdGeom.Tokens.y)
152
- # in M
153
- UsdGeom.SetStageMetersPerUnit(self._stage, 1.0)
154
+ UsdGeom.SetStageMetersPerUnit(self._stage, 1.0 / self._units_per_meter)
154
155
  logging.info(f"Created stage: {self.stage_url()}")
155
156
 
156
157
  def save_stage(self, comment: str = "") -> None:
@@ -288,6 +289,8 @@ class OmniverseWrapper(object):
288
289
 
289
290
  if not os.path.exists(part_stage_url):
290
291
  part_stage = Usd.Stage.CreateNew(part_stage_url)
292
+ UsdGeom.SetStageUpAxis(part_stage, UsdGeom.Tokens.y)
293
+ UsdGeom.SetStageMetersPerUnit(part_stage, 1.0 / self._units_per_meter)
291
294
  self._old_stages.append(part_stage_url)
292
295
  xform = UsdGeom.Xform.Define(part_stage, "/" + partname)
293
296
  mesh = UsdGeom.Mesh.Define(part_stage, "/" + partname + "/Mesh")
@@ -362,6 +365,7 @@ class OmniverseWrapper(object):
362
365
  parent_prim,
363
366
  verts,
364
367
  tcoords,
368
+ width,
365
369
  matrix=[1.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0],
366
370
  diffuse=[1.0, 1.0, 1.0, 1.0],
367
371
  variable=None,
@@ -369,20 +373,6 @@ class OmniverseWrapper(object):
369
373
  first_timestep=False,
370
374
  mat_info={},
371
375
  ):
372
- # TODO: GLB extension maps to DSG PART attribute map
373
- width = self.line_width
374
- wireframe = width == 0.0
375
- if width < 0.0:
376
- tmp = verts.reshape(-1, 3)
377
- mins = numpy.min(tmp, axis=0)
378
- maxs = numpy.max(tmp, axis=0)
379
- dx = maxs[0] - mins[0]
380
- dy = maxs[1] - mins[1]
381
- dz = maxs[2] - mins[2]
382
- diagonal = math.sqrt(dx * dx + dy * dy + dz * dz)
383
- width = diagonal * math.fabs(width)
384
- self.line_width = width
385
-
386
376
  # include the line width in the hash
387
377
  part_hash.update(str(self.line_width).encode("utf-8"))
388
378
 
@@ -397,6 +387,8 @@ class OmniverseWrapper(object):
397
387
 
398
388
  if not os.path.exists(part_stage_url):
399
389
  part_stage = Usd.Stage.CreateNew(part_stage_url)
390
+ UsdGeom.SetStageUpAxis(part_stage, UsdGeom.Tokens.y)
391
+ UsdGeom.SetStageMetersPerUnit(part_stage, 1.0 / self._units_per_meter)
400
392
  self._old_stages.append(part_stage_url)
401
393
  xform = UsdGeom.Xform.Define(part_stage, "/" + partname)
402
394
  lines = UsdGeom.BasisCurves.Define(part_stage, "/" + partname + "/Lines")
@@ -415,6 +407,7 @@ class OmniverseWrapper(object):
415
407
  endCaps.Set(2) # Rounded = 2
416
408
 
417
409
  prim = lines.GetPrim()
410
+ wireframe = width == 0.0
418
411
  prim.CreateAttribute(
419
412
  "omni:scene:visualization:drawWireframe", Sdf.ValueTypeNames.Bool
420
413
  ).Set(wireframe)
@@ -479,6 +472,8 @@ class OmniverseWrapper(object):
479
472
 
480
473
  if not os.path.exists(part_stage_url):
481
474
  part_stage = Usd.Stage.CreateNew(part_stage_url)
475
+ UsdGeom.SetStageUpAxis(part_stage, UsdGeom.Tokens.y)
476
+ UsdGeom.SetStageMetersPerUnit(part_stage, 1.0 / self._units_per_meter)
482
477
  self._old_stages.append(part_stage_url)
483
478
  xform = UsdGeom.Xform.Define(part_stage, "/" + partname)
484
479
 
@@ -639,8 +634,8 @@ class OmniverseWrapper(object):
639
634
  cam = geom_cam.GetCamera()
640
635
  # LOL, not sure why is might be correct, but so far it seems to work???
641
636
  cam.focalLength = camera.fieldofview
642
- dist = (target_pos - cam_pos).GetLength()
643
- cam.clippingRange = Gf.Range1f(0.1 * dist, 10.0 * dist)
637
+ dist = (target_pos - cam_pos).GetLength() * self._units_per_meter
638
+ cam.clippingRange = Gf.Range1f(0.1 * dist, 1000.0 * dist)
644
639
  look_at = Gf.Matrix4d()
645
640
  look_at.SetLookAt(cam_pos, target_pos, up_vec)
646
641
  trans_row = look_at.GetRow(3)
@@ -724,7 +719,6 @@ class OmniverseUpdateHandler(UpdateHandler):
724
719
  self._group_prims: Dict[int, Any] = dict()
725
720
  self._root_prim = None
726
721
  self._sent_textures = False
727
- self._updated_camera = False
728
722
 
729
723
  def add_group(self, id: int, view: bool = False) -> None:
730
724
  super().add_group(id, view)
@@ -745,7 +739,7 @@ class OmniverseUpdateHandler(UpdateHandler):
745
739
  matrix = group.matrix4x4
746
740
  # Is this a "case" group (it will contain part of the camera view in the matrix)
747
741
  if obj_type == "ENS_CASE":
748
- if (not self.session.vrmode) and (not self._updated_camera):
742
+ if not self.session.vrmode:
749
743
  # if in camera mode, we need to update the camera matrix so we can
750
744
  # use the identity matrix on this group. The camera should have been
751
745
  # created in the "view" handler
@@ -757,7 +751,8 @@ class OmniverseUpdateHandler(UpdateHandler):
757
751
  c = cam.transform
758
752
  m = Gf.Matrix4d(*matrix).GetTranspose()
759
753
  # move the model transform to the camera transform
760
- cam.transform = c * m.GetInverse()
754
+ sc = Gf.Matrix4d(self._omni._units_per_meter)
755
+ cam.transform = c * m.GetInverse() * sc
761
756
  # set the updated camera
762
757
  geom_cam.SetFromCamera(cam)
763
758
  # apply the inverse cam transform to move the center of interest
@@ -771,8 +766,8 @@ class OmniverseUpdateHandler(UpdateHandler):
771
766
  )
772
767
  coi_attr.Set(
773
768
  Gf.Vec3d(
774
- coi_cam[0] / coi_cam[3],
775
- coi_cam[1] / coi_cam[3],
769
+ 0,
770
+ 0,
776
771
  coi_cam[2] / coi_cam[3],
777
772
  )
778
773
  )
@@ -780,9 +775,6 @@ class OmniverseUpdateHandler(UpdateHandler):
780
775
  self._omni._stage.GetRootLayer().customLayerData = { # type: ignore
781
776
  "cameraSettings": {"boundCamera": "/Root/Cam"}
782
777
  }
783
-
784
- # We only want to do this once
785
- self._updated_camera = True
786
778
  matrix = [
787
779
  1.0,
788
780
  0.0,
@@ -852,6 +844,7 @@ class OmniverseUpdateHandler(UpdateHandler):
852
844
  if part.cmd.render == part.cmd.CONNECTIVITY:
853
845
  has_triangles = False
854
846
  command, verts, conn, normals, tcoords, var_cmd = part.nodal_surface_rep()
847
+ verts = numpy.multiply(verts, self._omni._units_per_meter)
855
848
  if command is not None:
856
849
  has_triangles = True
857
850
  # Generate the mesh block
@@ -872,6 +865,7 @@ class OmniverseUpdateHandler(UpdateHandler):
872
865
  mat_info=mat_info,
873
866
  )
874
867
  command, verts, tcoords, var_cmd = part.line_rep()
868
+ verts = numpy.multiply(verts, self._omni._units_per_meter)
875
869
  if command is not None:
876
870
  # If there are no triangle (ideally if these are not hidden line
877
871
  # edges), then use the base color for the part. If there are
@@ -885,9 +879,30 @@ class OmniverseUpdateHandler(UpdateHandler):
885
879
  part.cmd.line_color[2] * part.cmd.diffuse,
886
880
  part.cmd.line_color[3],
887
881
  ]
888
- # TODO: texture coordinates on lines are current invalid in OV
882
+ # TODO: texture coordinates on lines are currently invalid in Omniverse
889
883
  var_cmd = None
890
884
  tcoords = None
885
+ # line info can come from self or our parent group
886
+ width = self._omni.line_width
887
+ # Allow the group to override
888
+ group = self.session.find_group_pb(part.cmd.parent_id)
889
+ if group:
890
+ try:
891
+ width = float(group.attributes.get("ANSYS_linewidth", str(width)))
892
+ except ValueError:
893
+ pass
894
+ if width < 0.0:
895
+ tmp = verts.reshape(-1, 3)
896
+ mins = numpy.min(tmp, axis=0)
897
+ maxs = numpy.max(tmp, axis=0)
898
+ dx = maxs[0] - mins[0]
899
+ dy = maxs[1] - mins[1]
900
+ dz = maxs[2] - mins[2]
901
+ diagonal = math.sqrt(dx * dx + dy * dy + dz * dz)
902
+ width = diagonal * math.fabs(width) / self._omni._units_per_meter
903
+ if self._omni.line_width < 0.0:
904
+ self._omni.line_width = width
905
+ width = width * self._omni._units_per_meter
891
906
  # Generate the lines
892
907
  _ = self._omni.create_dsg_lines(
893
908
  name,
@@ -896,6 +911,7 @@ class OmniverseUpdateHandler(UpdateHandler):
896
911
  parent_prim,
897
912
  verts,
898
913
  tcoords,
914
+ width,
899
915
  matrix=matrix,
900
916
  diffuse=line_color,
901
917
  variable=var_cmd,
@@ -905,6 +921,10 @@ class OmniverseUpdateHandler(UpdateHandler):
905
921
 
906
922
  elif part.cmd.render == part.cmd.NODES:
907
923
  command, verts, sizes, colors, var_cmd = part.point_rep()
924
+ verts = numpy.multiply(verts, self._omni._units_per_meter)
925
+
926
+ if sizes is not None:
927
+ sizes = numpy.multiply(sizes, self._omni._units_per_meter)
908
928
  if command is not None:
909
929
  _ = self._omni.create_dsg_points(
910
930
  name,
@@ -915,7 +935,7 @@ class OmniverseUpdateHandler(UpdateHandler):
915
935
  sizes,
916
936
  colors,
917
937
  matrix=matrix,
918
- default_size=part.cmd.node_size_default,
938
+ default_size=part.cmd.node_size_default * self._omni._units_per_meter,
919
939
  default_color=color,
920
940
  timeline=self.session.cur_timeline,
921
941
  first_timestep=(self.session.cur_timeline[0] == self.session.time_limits[0]),
@@ -942,8 +962,6 @@ class OmniverseUpdateHandler(UpdateHandler):
942
962
  # Upload a material to the Omniverse server
943
963
  self._omni.uploadMaterial()
944
964
  self._sent_textures = False
945
- # We want to update the camera a single time within this update
946
- self._updated_camera = False
947
965
 
948
966
  def end_update(self) -> None:
949
967
  super().end_update()