warp-lang 1.0.0b2__py3-none-win_amd64.whl → 1.0.0b6__py3-none-win_amd64.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 warp-lang might be problematic. Click here for more details.

Files changed (271) hide show
  1. docs/conf.py +17 -5
  2. examples/env/env_ant.py +1 -1
  3. examples/env/env_cartpole.py +1 -1
  4. examples/env/env_humanoid.py +1 -1
  5. examples/env/env_usd.py +4 -1
  6. examples/env/environment.py +8 -9
  7. examples/example_dem.py +34 -33
  8. examples/example_diffray.py +364 -337
  9. examples/example_fluid.py +32 -23
  10. examples/example_jacobian_ik.py +97 -93
  11. examples/example_marching_cubes.py +6 -16
  12. examples/example_mesh.py +6 -16
  13. examples/example_mesh_intersect.py +16 -14
  14. examples/example_nvdb.py +14 -16
  15. examples/example_raycast.py +14 -13
  16. examples/example_raymarch.py +16 -23
  17. examples/example_render_opengl.py +19 -10
  18. examples/example_sim_cartpole.py +82 -78
  19. examples/example_sim_cloth.py +45 -48
  20. examples/example_sim_fk_grad.py +51 -44
  21. examples/example_sim_fk_grad_torch.py +47 -40
  22. examples/example_sim_grad_bounce.py +108 -133
  23. examples/example_sim_grad_cloth.py +99 -113
  24. examples/example_sim_granular.py +5 -6
  25. examples/{example_sim_sdf_shape.py → example_sim_granular_collision_sdf.py} +37 -26
  26. examples/example_sim_neo_hookean.py +51 -55
  27. examples/example_sim_particle_chain.py +4 -4
  28. examples/example_sim_quadruped.py +126 -81
  29. examples/example_sim_rigid_chain.py +54 -61
  30. examples/example_sim_rigid_contact.py +66 -70
  31. examples/example_sim_rigid_fem.py +3 -3
  32. examples/example_sim_rigid_force.py +1 -1
  33. examples/example_sim_rigid_gyroscopic.py +3 -4
  34. examples/example_sim_rigid_kinematics.py +28 -39
  35. examples/example_sim_trajopt.py +112 -110
  36. examples/example_sph.py +9 -8
  37. examples/example_wave.py +7 -7
  38. examples/fem/bsr_utils.py +30 -17
  39. examples/fem/example_apic_fluid.py +85 -69
  40. examples/fem/example_convection_diffusion.py +97 -93
  41. examples/fem/example_convection_diffusion_dg.py +142 -149
  42. examples/fem/example_convection_diffusion_dg0.py +141 -136
  43. examples/fem/example_deformed_geometry.py +146 -0
  44. examples/fem/example_diffusion.py +115 -84
  45. examples/fem/example_diffusion_3d.py +116 -86
  46. examples/fem/example_diffusion_mgpu.py +102 -79
  47. examples/fem/example_mixed_elasticity.py +139 -100
  48. examples/fem/example_navier_stokes.py +175 -162
  49. examples/fem/example_stokes.py +143 -111
  50. examples/fem/example_stokes_transfer.py +186 -157
  51. examples/fem/mesh_utils.py +59 -97
  52. examples/fem/plot_utils.py +138 -17
  53. tools/ci/publishing/build_nodes_info.py +54 -0
  54. warp/__init__.py +4 -3
  55. warp/__init__.pyi +1 -0
  56. warp/bin/warp-clang.dll +0 -0
  57. warp/bin/warp.dll +0 -0
  58. warp/build.py +5 -3
  59. warp/build_dll.py +29 -9
  60. warp/builtins.py +836 -492
  61. warp/codegen.py +864 -553
  62. warp/config.py +3 -1
  63. warp/context.py +389 -172
  64. warp/fem/__init__.py +24 -6
  65. warp/fem/cache.py +318 -25
  66. warp/fem/dirichlet.py +7 -3
  67. warp/fem/domain.py +14 -0
  68. warp/fem/field/__init__.py +30 -38
  69. warp/fem/field/field.py +149 -0
  70. warp/fem/field/nodal_field.py +244 -138
  71. warp/fem/field/restriction.py +8 -6
  72. warp/fem/field/test.py +127 -59
  73. warp/fem/field/trial.py +117 -60
  74. warp/fem/geometry/__init__.py +5 -1
  75. warp/fem/geometry/deformed_geometry.py +271 -0
  76. warp/fem/geometry/element.py +24 -1
  77. warp/fem/geometry/geometry.py +86 -14
  78. warp/fem/geometry/grid_2d.py +112 -54
  79. warp/fem/geometry/grid_3d.py +134 -65
  80. warp/fem/geometry/hexmesh.py +953 -0
  81. warp/fem/geometry/partition.py +85 -33
  82. warp/fem/geometry/quadmesh_2d.py +532 -0
  83. warp/fem/geometry/tetmesh.py +451 -115
  84. warp/fem/geometry/trimesh_2d.py +197 -92
  85. warp/fem/integrate.py +534 -268
  86. warp/fem/operator.py +58 -31
  87. warp/fem/polynomial.py +11 -0
  88. warp/fem/quadrature/__init__.py +1 -1
  89. warp/fem/quadrature/pic_quadrature.py +150 -58
  90. warp/fem/quadrature/quadrature.py +209 -57
  91. warp/fem/space/__init__.py +230 -53
  92. warp/fem/space/basis_space.py +489 -0
  93. warp/fem/space/collocated_function_space.py +105 -0
  94. warp/fem/space/dof_mapper.py +49 -2
  95. warp/fem/space/function_space.py +90 -39
  96. warp/fem/space/grid_2d_function_space.py +149 -496
  97. warp/fem/space/grid_3d_function_space.py +173 -538
  98. warp/fem/space/hexmesh_function_space.py +352 -0
  99. warp/fem/space/partition.py +129 -76
  100. warp/fem/space/quadmesh_2d_function_space.py +369 -0
  101. warp/fem/space/restriction.py +46 -34
  102. warp/fem/space/shape/__init__.py +15 -0
  103. warp/fem/space/shape/cube_shape_function.py +738 -0
  104. warp/fem/space/shape/shape_function.py +103 -0
  105. warp/fem/space/shape/square_shape_function.py +611 -0
  106. warp/fem/space/shape/tet_shape_function.py +567 -0
  107. warp/fem/space/shape/triangle_shape_function.py +429 -0
  108. warp/fem/space/tetmesh_function_space.py +132 -1039
  109. warp/fem/space/topology.py +295 -0
  110. warp/fem/space/trimesh_2d_function_space.py +104 -742
  111. warp/fem/types.py +13 -11
  112. warp/fem/utils.py +335 -60
  113. warp/native/array.h +120 -34
  114. warp/native/builtin.h +101 -72
  115. warp/native/bvh.cpp +73 -325
  116. warp/native/bvh.cu +406 -23
  117. warp/native/bvh.h +22 -40
  118. warp/native/clang/clang.cpp +1 -0
  119. warp/native/crt.h +2 -0
  120. warp/native/cuda_util.cpp +8 -3
  121. warp/native/cuda_util.h +1 -0
  122. warp/native/exports.h +1522 -1243
  123. warp/native/intersect.h +19 -4
  124. warp/native/intersect_adj.h +8 -8
  125. warp/native/mat.h +76 -17
  126. warp/native/mesh.cpp +33 -108
  127. warp/native/mesh.cu +114 -18
  128. warp/native/mesh.h +395 -40
  129. warp/native/noise.h +272 -329
  130. warp/native/quat.h +51 -8
  131. warp/native/rand.h +44 -34
  132. warp/native/reduce.cpp +1 -1
  133. warp/native/sparse.cpp +4 -4
  134. warp/native/sparse.cu +163 -155
  135. warp/native/spatial.h +2 -2
  136. warp/native/temp_buffer.h +18 -14
  137. warp/native/vec.h +103 -21
  138. warp/native/warp.cpp +2 -1
  139. warp/native/warp.cu +28 -3
  140. warp/native/warp.h +4 -3
  141. warp/render/render_opengl.py +261 -109
  142. warp/sim/__init__.py +1 -2
  143. warp/sim/articulation.py +385 -185
  144. warp/sim/import_mjcf.py +59 -48
  145. warp/sim/import_urdf.py +15 -15
  146. warp/sim/import_usd.py +174 -102
  147. warp/sim/inertia.py +17 -18
  148. warp/sim/integrator_xpbd.py +4 -3
  149. warp/sim/model.py +330 -250
  150. warp/sim/render.py +1 -1
  151. warp/sparse.py +625 -152
  152. warp/stubs.py +341 -309
  153. warp/tape.py +9 -6
  154. warp/tests/__main__.py +3 -6
  155. warp/tests/assets/curlnoise_golden.npy +0 -0
  156. warp/tests/assets/pnoise_golden.npy +0 -0
  157. warp/tests/{test_class_kernel.py → aux_test_class_kernel.py} +9 -1
  158. warp/tests/aux_test_conditional_unequal_types_kernels.py +21 -0
  159. warp/tests/{test_dependent.py → aux_test_dependent.py} +2 -2
  160. warp/tests/{test_reference.py → aux_test_reference.py} +1 -1
  161. warp/tests/aux_test_unresolved_func.py +14 -0
  162. warp/tests/aux_test_unresolved_symbol.py +14 -0
  163. warp/tests/disabled_kinematics.py +239 -0
  164. warp/tests/run_coverage_serial.py +31 -0
  165. warp/tests/test_adam.py +103 -106
  166. warp/tests/test_arithmetic.py +94 -74
  167. warp/tests/test_array.py +82 -101
  168. warp/tests/test_array_reduce.py +57 -23
  169. warp/tests/test_atomic.py +64 -28
  170. warp/tests/test_bool.py +22 -12
  171. warp/tests/test_builtins_resolution.py +1292 -0
  172. warp/tests/test_bvh.py +18 -18
  173. warp/tests/test_closest_point_edge_edge.py +54 -57
  174. warp/tests/test_codegen.py +165 -134
  175. warp/tests/test_compile_consts.py +28 -20
  176. warp/tests/test_conditional.py +108 -24
  177. warp/tests/test_copy.py +10 -12
  178. warp/tests/test_ctypes.py +112 -88
  179. warp/tests/test_dense.py +21 -14
  180. warp/tests/test_devices.py +98 -0
  181. warp/tests/test_dlpack.py +75 -75
  182. warp/tests/test_examples.py +237 -0
  183. warp/tests/test_fabricarray.py +22 -24
  184. warp/tests/test_fast_math.py +15 -11
  185. warp/tests/test_fem.py +1034 -124
  186. warp/tests/test_fp16.py +23 -16
  187. warp/tests/test_func.py +187 -86
  188. warp/tests/test_generics.py +194 -49
  189. warp/tests/test_grad.py +123 -181
  190. warp/tests/test_grad_customs.py +176 -0
  191. warp/tests/test_hash_grid.py +35 -34
  192. warp/tests/test_import.py +10 -23
  193. warp/tests/test_indexedarray.py +24 -25
  194. warp/tests/test_intersect.py +18 -9
  195. warp/tests/test_large.py +141 -0
  196. warp/tests/test_launch.py +14 -41
  197. warp/tests/test_lerp.py +64 -65
  198. warp/tests/test_lvalue.py +493 -0
  199. warp/tests/test_marching_cubes.py +12 -13
  200. warp/tests/test_mat.py +517 -2898
  201. warp/tests/test_mat_lite.py +115 -0
  202. warp/tests/test_mat_scalar_ops.py +2889 -0
  203. warp/tests/test_math.py +103 -9
  204. warp/tests/test_matmul.py +304 -69
  205. warp/tests/test_matmul_lite.py +410 -0
  206. warp/tests/test_mesh.py +60 -22
  207. warp/tests/test_mesh_query_aabb.py +21 -25
  208. warp/tests/test_mesh_query_point.py +111 -22
  209. warp/tests/test_mesh_query_ray.py +12 -24
  210. warp/tests/test_mlp.py +30 -22
  211. warp/tests/test_model.py +92 -89
  212. warp/tests/test_modules_lite.py +39 -0
  213. warp/tests/test_multigpu.py +88 -114
  214. warp/tests/test_noise.py +12 -11
  215. warp/tests/test_operators.py +16 -20
  216. warp/tests/test_options.py +11 -11
  217. warp/tests/test_pinned.py +17 -18
  218. warp/tests/test_print.py +32 -11
  219. warp/tests/test_quat.py +275 -129
  220. warp/tests/test_rand.py +18 -16
  221. warp/tests/test_reload.py +38 -34
  222. warp/tests/test_rounding.py +50 -43
  223. warp/tests/test_runlength_encode.py +168 -20
  224. warp/tests/test_smoothstep.py +9 -11
  225. warp/tests/test_snippet.py +143 -0
  226. warp/tests/test_sparse.py +261 -63
  227. warp/tests/test_spatial.py +276 -243
  228. warp/tests/test_streams.py +110 -85
  229. warp/tests/test_struct.py +268 -63
  230. warp/tests/test_tape.py +39 -21
  231. warp/tests/test_torch.py +90 -86
  232. warp/tests/test_transient_module.py +10 -12
  233. warp/tests/test_types.py +363 -0
  234. warp/tests/test_utils.py +451 -0
  235. warp/tests/test_vec.py +354 -2050
  236. warp/tests/test_vec_lite.py +73 -0
  237. warp/tests/test_vec_scalar_ops.py +2099 -0
  238. warp/tests/test_volume.py +418 -376
  239. warp/tests/test_volume_write.py +124 -134
  240. warp/tests/unittest_serial.py +35 -0
  241. warp/tests/unittest_suites.py +291 -0
  242. warp/tests/unittest_utils.py +342 -0
  243. warp/tests/{test_misc.py → unused_test_misc.py} +13 -5
  244. warp/tests/{test_debug.py → walkthough_debug.py} +3 -17
  245. warp/thirdparty/appdirs.py +36 -45
  246. warp/thirdparty/unittest_parallel.py +589 -0
  247. warp/types.py +622 -211
  248. warp/utils.py +54 -393
  249. warp_lang-1.0.0b6.dist-info/METADATA +238 -0
  250. warp_lang-1.0.0b6.dist-info/RECORD +409 -0
  251. {warp_lang-1.0.0b2.dist-info → warp_lang-1.0.0b6.dist-info}/WHEEL +1 -1
  252. examples/example_cache_management.py +0 -40
  253. examples/example_multigpu.py +0 -54
  254. examples/example_struct.py +0 -65
  255. examples/fem/example_stokes_transfer_3d.py +0 -210
  256. warp/bin/warp-clang.so +0 -0
  257. warp/bin/warp.so +0 -0
  258. warp/fem/field/discrete_field.py +0 -80
  259. warp/fem/space/nodal_function_space.py +0 -233
  260. warp/tests/test_all.py +0 -223
  261. warp/tests/test_array_scan.py +0 -60
  262. warp/tests/test_base.py +0 -208
  263. warp/tests/test_unresolved_func.py +0 -7
  264. warp/tests/test_unresolved_symbol.py +0 -7
  265. warp_lang-1.0.0b2.dist-info/METADATA +0 -26
  266. warp_lang-1.0.0b2.dist-info/RECORD +0 -380
  267. /warp/tests/{test_compile_consts_dummy.py → aux_test_compile_consts_dummy.py} +0 -0
  268. /warp/tests/{test_reference_reference.py → aux_test_reference_reference.py} +0 -0
  269. /warp/tests/{test_square.py → aux_test_square.py} +0 -0
  270. {warp_lang-1.0.0b2.dist-info → warp_lang-1.0.0b6.dist-info}/LICENSE.md +0 -0
  271. {warp_lang-1.0.0b2.dist-info → warp_lang-1.0.0b6.dist-info}/top_level.txt +0 -0
examples/example_nvdb.py CHANGED
@@ -15,10 +15,11 @@
15
15
  #
16
16
  ###########################################################################
17
17
 
18
- import os
19
18
  import math
19
+ import os
20
20
 
21
21
  import numpy as np
22
+
22
23
  import warp as wp
23
24
  import warp.render
24
25
 
@@ -49,7 +50,6 @@ def simulate(
49
50
  positions: wp.array(dtype=wp.vec3),
50
51
  velocities: wp.array(dtype=wp.vec3),
51
52
  volume: wp.uint64,
52
- restitution: float,
53
53
  margin: float,
54
54
  dt: float,
55
55
  ):
@@ -62,12 +62,12 @@ def simulate(
62
62
  xpred = x + v * dt
63
63
  xpred_local = wp.volume_world_to_index(volume, xpred)
64
64
 
65
- #d = wp.volume_sample_f(volume, xpred_local, wp.Volume.LINEAR)
65
+ # d = wp.volume_sample_f(volume, xpred_local, wp.Volume.LINEAR)
66
66
  n = wp.vec3()
67
67
  d = wp.volume_sample_grad_f(volume, xpred_local, wp.Volume.LINEAR, n)
68
68
 
69
69
  if d < margin:
70
- #n = volume_grad(volume, xpred)
70
+ # n = volume_grad(volume, xpred)
71
71
  n = wp.normalize(n)
72
72
  err = d - margin
73
73
 
@@ -91,14 +91,14 @@ class Example:
91
91
  self.num_particles = 10000
92
92
 
93
93
  self.sim_steps = 1000
94
- self.sim_dt = 1.0 / 60.0
94
+ frame_dt = 1.0 / 60.0
95
95
  self.sim_substeps = 3
96
+ self.sim_dt = frame_dt / self.sim_substeps
96
97
 
97
98
  self.sim_time = 0.0
98
99
  self.sim_timers = {}
99
100
  self.sim_render = True
100
101
 
101
- self.sim_restitution = 0.0
102
102
  self.sim_margin = 15.0
103
103
 
104
104
  self.renderer = wp.render.UsdRenderer(stage, up_axis="z")
@@ -116,9 +116,11 @@ class Example:
116
116
  # create Volume object
117
117
  self.volume = wp.Volume.load_from_nvdb(file)
118
118
 
119
+ file.close()
120
+
119
121
  def update(self):
120
122
  with wp.ScopedTimer("simulate", detailed=False, dict=self.sim_timers):
121
- for s in range(self.sim_substeps):
123
+ for _ in range(self.sim_substeps):
122
124
  wp.launch(
123
125
  kernel=simulate,
124
126
  dim=self.num_particles,
@@ -126,13 +128,11 @@ class Example:
126
128
  self.positions,
127
129
  self.velocities,
128
130
  self.volume.id,
129
- self.sim_restitution,
130
131
  self.sim_margin,
131
- self.sim_dt / float(self.sim_substeps),
132
+ self.sim_dt,
132
133
  ],
133
134
  )
134
-
135
- wp.synchronize_device()
135
+ self.sim_time += self.sim_dt
136
136
 
137
137
  def render(self, is_live=False):
138
138
  with wp.ScopedTimer("render", detailed=False):
@@ -143,16 +143,14 @@ class Example:
143
143
  self.renderer.render_ref(
144
144
  name="collision",
145
145
  path=os.path.join(os.path.dirname(__file__), "assets/rocks.usd"),
146
- pos=(0.0, 0.0, 0.0),
147
- rot=wp.quat_from_axis_angle((1.0, 0.0, 0.0), math.pi),
148
- scale=(1.0, 1.0, 1.0),
146
+ pos=wp.vec3(0.0, 0.0, 0.0),
147
+ rot=wp.quat_from_axis_angle(wp.vec3(1.0, 0.0, 0.0), math.pi),
148
+ scale=wp.vec3(1.0, 1.0, 1.0),
149
149
  )
150
150
  self.renderer.render_points(name="points", points=self.positions.numpy(), radius=self.sim_margin)
151
151
 
152
152
  self.renderer.end_frame()
153
153
 
154
- self.sim_time += self.sim_dt
155
-
156
154
 
157
155
  if __name__ == "__main__":
158
156
  stage_path = os.path.join(os.path.dirname(__file__), "outputs/example_nvdb.usd")
@@ -13,13 +13,12 @@
13
13
  #
14
14
  ##############################################################################
15
15
 
16
- import matplotlib.pyplot as plt
17
- from pxr import Usd, UsdGeom
16
+ import os
18
17
 
19
- import warp as wp
20
18
  import numpy as np
19
+ from pxr import Usd, UsdGeom
21
20
 
22
- import os
21
+ import warp as wp
23
22
 
24
23
  wp.init()
25
24
 
@@ -54,7 +53,7 @@ def draw(mesh: wp.uint64, cam_pos: wp.vec3, width: int, height: int, pixels: wp.
54
53
 
55
54
 
56
55
  class Example:
57
- def __init__(self):
56
+ def __init__(self, **kwargs):
58
57
  self.width = 1024
59
58
  self.height = 1024
60
59
  self.cam_pos = (0.0, 1.0, 2.0)
@@ -75,7 +74,7 @@ class Example:
75
74
  def update(self):
76
75
  pass
77
76
 
78
- def render(self, is_live=False):
77
+ def render(self):
79
78
  with wp.ScopedTimer("render"):
80
79
  wp.launch(
81
80
  kernel=draw,
@@ -83,14 +82,16 @@ class Example:
83
82
  inputs=[self.mesh.id, self.cam_pos, self.width, self.height, self.pixels],
84
83
  )
85
84
 
86
- wp.synchronize_device()
87
-
88
- plt.imshow(
89
- self.pixels.numpy().reshape((self.height, self.width, 3)), origin="lower", interpolation="antialiased"
90
- )
91
- plt.show()
92
-
93
85
 
94
86
  if __name__ == "__main__":
87
+ import matplotlib.pyplot as plt
88
+
95
89
  example = Example()
96
90
  example.render()
91
+
92
+ wp.synchronize_device()
93
+
94
+ plt.imshow(
95
+ example.pixels.numpy().reshape((example.height, example.width, 3)), origin="lower", interpolation="antialiased"
96
+ )
97
+ plt.show()
@@ -15,20 +15,16 @@
15
15
  ###########################################################################
16
16
 
17
17
 
18
- import matplotlib.pyplot as plt
19
-
20
18
  import warp as wp
21
19
 
22
20
  wp.init()
23
21
 
24
22
 
25
- # signed sphere
26
23
  @wp.func
27
24
  def sdf_sphere(p: wp.vec3, r: float):
28
25
  return wp.length(p) - r
29
26
 
30
27
 
31
- # signed box
32
28
  @wp.func
33
29
  def sdf_box(upper: wp.vec3, p: wp.vec3):
34
30
  qx = wp.abs(p[0]) - upper[0]
@@ -45,19 +41,16 @@ def sdf_plane(p: wp.vec3, plane: wp.vec4):
45
41
  return plane[0] * p[0] + plane[1] * p[1] + plane[2] * p[2] + plane[3]
46
42
 
47
43
 
48
- # union
49
44
  @wp.func
50
45
  def op_union(d1: float, d2: float):
51
46
  return wp.min(d1, d2)
52
47
 
53
48
 
54
- # subtraction
55
49
  @wp.func
56
50
  def op_subtract(d1: float, d2: float):
57
51
  return wp.max(-d1, d2)
58
52
 
59
53
 
60
- # intersection
61
54
  @wp.func
62
55
  def op_intersect(d1: float, d2: float):
63
56
  return wp.max(d1, d2)
@@ -66,12 +59,9 @@ def op_intersect(d1: float, d2: float):
66
59
  # simple scene
67
60
  @wp.func
68
61
  def sdf(p: wp.vec3):
69
- # intersection of two spheres
70
- sphere_1 = wp.vec3(0.0, 0.0, 0.0)
71
- sphere_2 = wp.vec3(0.0, 0.75, 0.0)
62
+ sphere_1 = wp.vec3(0.0, 0.75, 0.0)
72
63
 
73
- d = op_subtract(sdf_sphere(p - sphere_2, 0.75), sdf_box(wp.vec3(1.0, 0.5, 0.5), p))
74
- # sdf_sphere(p + sphere_1, 1.0))
64
+ d = op_subtract(sdf_sphere(p - sphere_1, 0.75), sdf_box(wp.vec3(1.0, 0.5, 0.5), p))
75
65
 
76
66
  # ground plane
77
67
  d = op_union(d, sdf_plane(p, wp.vec4(0.0, 1.0, 0.0, 1.0)))
@@ -96,7 +86,7 @@ def shadow(ro: wp.vec3, rd: wp.vec3):
96
86
  t = float(0.0)
97
87
  s = float(1.0)
98
88
 
99
- for i in range(64):
89
+ for _ in range(64):
100
90
  d = sdf(ro + t * rd)
101
91
  t = t + wp.clamp(d, 0.0001, 2.0)
102
92
 
@@ -127,7 +117,7 @@ def draw(cam_pos: wp.vec3, cam_rot: wp.quat, width: int, height: int, pixels: wp
127
117
  t = float(0.0)
128
118
 
129
119
  # ray march
130
- for i in range(128):
120
+ for _ in range(128):
131
121
  d = sdf(ro + rd * t)
132
122
  t = t + d
133
123
 
@@ -156,7 +146,7 @@ def draw(cam_pos: wp.vec3, cam_rot: wp.quat, width: int, height: int, pixels: wp
156
146
 
157
147
 
158
148
  class Example:
159
- def __init__(self):
149
+ def __init__(self, **kwargs):
160
150
  self.width = 2048
161
151
  self.height = 1024
162
152
  self.cam_pos = (-1.25, 1.0, 2.0)
@@ -164,7 +154,10 @@ class Example:
164
154
 
165
155
  self.pixels = wp.zeros(self.width * self.height, dtype=wp.vec3)
166
156
 
167
- def render(self, is_live=False):
157
+ def update(self):
158
+ pass
159
+
160
+ def render(self):
168
161
  with wp.ScopedTimer("render"):
169
162
  wp.launch(
170
163
  kernel=draw,
@@ -172,14 +165,14 @@ class Example:
172
165
  inputs=[self.cam_pos, self.cam_rot, self.width, self.height, self.pixels],
173
166
  )
174
167
 
175
- wp.synchronize_device()
176
-
177
- plt.imshow(
178
- self.pixels.numpy().reshape((self.height, self.width, 3)), origin="lower", interpolation="antialiased"
179
- )
180
- plt.show()
181
-
182
168
 
183
169
  if __name__ == "__main__":
170
+ import matplotlib.pyplot as plt
171
+
184
172
  example = Example()
185
173
  example.render()
174
+
175
+ plt.imshow(
176
+ example.pixels.numpy().reshape((example.height, example.width, 3)), origin="lower", interpolation="antialiased"
177
+ )
178
+ plt.show()
@@ -27,6 +27,8 @@ split_up_tiles = True
27
27
  custom_tile_arrangement = False
28
28
  # whether to display the pixels in a matplotlib figure
29
29
  show_plot = True
30
+ # whether to render depth image to a Warp array
31
+ render_mode = "depth"
30
32
 
31
33
  renderer = wp.render.OpenGLRenderer(vsync=False)
32
34
  instance_ids = []
@@ -51,11 +53,12 @@ if num_tiles > 1:
51
53
 
52
54
  renderer.render_ground()
53
55
 
56
+ channels = 1 if render_mode == "depth" else 3
54
57
  if show_plot:
55
58
  import matplotlib.pyplot as plt
56
59
 
57
60
  if split_up_tiles:
58
- pixels = wp.zeros((num_tiles, renderer.tile_height, renderer.tile_width, 3), dtype=wp.float32)
61
+ pixels = wp.zeros((num_tiles, renderer.tile_height, renderer.tile_width, channels), dtype=wp.float32)
59
62
  ncols = int(np.ceil(np.sqrt(num_tiles)))
60
63
  nrows = int(np.ceil(num_tiles / float(ncols)))
61
64
  img_plots = []
@@ -70,17 +73,23 @@ if show_plot:
70
73
  sharey=True,
71
74
  num=1,
72
75
  )
73
- tile_temp = np.zeros((renderer.tile_height, renderer.tile_width, 3), dtype=np.float32)
76
+ tile_temp = np.zeros((renderer.tile_height, renderer.tile_width, channels), dtype=np.float32)
74
77
  for dim in range(ncols * nrows):
75
78
  ax = axes[dim // ncols, dim % ncols]
76
79
  if dim >= num_tiles:
77
80
  ax.axis("off")
78
81
  continue
79
- img_plots.append(ax.imshow(tile_temp))
82
+ if render_mode == "depth":
83
+ img_plots.append(ax.imshow(tile_temp, vmin=renderer.camera_near_plane, vmax=renderer.camera_far_plane))
84
+ else:
85
+ img_plots.append(ax.imshow(tile_temp))
80
86
  else:
81
87
  fig = plt.figure(1)
82
- pixels = wp.zeros((renderer.screen_height, renderer.screen_width, 3), dtype=wp.float32)
83
- img_plot = plt.imshow(pixels.numpy())
88
+ pixels = wp.zeros((renderer.screen_height, renderer.screen_width, channels), dtype=wp.float32)
89
+ if render_mode == "depth":
90
+ img_plot = plt.imshow(pixels.numpy(), vmin=renderer.camera_near_plane, vmax=renderer.camera_far_plane)
91
+ else:
92
+ img_plot = plt.imshow(pixels.numpy())
84
93
 
85
94
  plt.ion()
86
95
  plt.show()
@@ -95,14 +104,14 @@ while renderer.is_running():
95
104
  renderer.render_cylinder(
96
105
  "cylinder",
97
106
  [3.2, 1.0, np.sin(time + 0.5)],
98
- np.array(wp.quat_from_axis_angle((1.0, 0.0, 0.0), np.sin(time + 0.5))),
107
+ np.array(wp.quat_from_axis_angle(wp.vec3(1.0, 0.0, 0.0), wp.sin(time + 0.5))),
99
108
  radius=0.5,
100
109
  half_height=0.8,
101
110
  )
102
111
  renderer.render_cone(
103
112
  "cone",
104
113
  [-1.2, 1.0, 0.0],
105
- np.array(wp.quat_from_axis_angle((0.707, 0.707, 0.0), time)),
114
+ np.array(wp.quat_from_axis_angle(wp.vec3(0.707, 0.707, 0.0), time)),
106
115
  radius=0.5,
107
116
  half_height=0.8,
108
117
  )
@@ -110,15 +119,15 @@ while renderer.is_running():
110
119
 
111
120
  if show_plot and plt.fignum_exists(1):
112
121
  if split_up_tiles:
113
- pixel_shape = (num_tiles, renderer.tile_height, renderer.tile_width, 3)
122
+ pixel_shape = (num_tiles, renderer.tile_height, renderer.tile_width, channels)
114
123
  else:
115
- pixel_shape = (renderer.screen_height, renderer.screen_width, 3)
124
+ pixel_shape = (renderer.screen_height, renderer.screen_width, channels)
116
125
 
117
126
  if pixel_shape != pixels.shape:
118
127
  # make sure we resize the pixels array to the right dimensions if the user resizes the window
119
128
  pixels = wp.zeros(pixel_shape, dtype=wp.float32)
120
129
 
121
- renderer.get_pixels(pixels, split_up_tiles=split_up_tiles)
130
+ renderer.get_pixels(pixels, split_up_tiles=split_up_tiles, mode=render_mode)
122
131
 
123
132
  if split_up_tiles:
124
133
  pixels_np = pixels.numpy()
@@ -14,8 +14,8 @@
14
14
  #
15
15
  ###########################################################################
16
16
 
17
- import os
18
17
  import math
18
+ import os
19
19
 
20
20
  import numpy as np
21
21
 
@@ -27,22 +27,11 @@ wp.init()
27
27
 
28
28
 
29
29
  class Example:
30
- frame_dt = 1.0 / 60.0
31
-
32
- episode_duration = 20.0 # seconds
33
- episode_frames = int(episode_duration / frame_dt)
34
-
35
- sim_substeps = 10
36
- sim_dt = frame_dt / sim_substeps
37
- sim_steps = int(episode_duration / sim_dt)
30
+ def __init__(self, stage=None, num_envs=1, enable_rendering=True, print_timers=True):
31
+ self.device = wp.get_device()
38
32
 
39
- sim_time = 0.0
40
-
41
- def __init__(self, stage=None, render=True, num_envs=1):
42
33
  builder = wp.sim.ModelBuilder()
43
34
 
44
- self.enable_rendering = render
45
-
46
35
  self.num_envs = num_envs
47
36
 
48
37
  articulation_builder = wp.sim.ModelBuilder()
@@ -50,7 +39,7 @@ class Example:
50
39
  wp.sim.parse_urdf(
51
40
  os.path.join(os.path.dirname(__file__), "assets/cartpole.urdf"),
52
41
  articulation_builder,
53
- xform=wp.transform(np.zeros(3), wp.quat_from_axis_angle((1.0, 0.0, 0.0), -math.pi * 0.5)),
42
+ xform=wp.transform(wp.vec3(), wp.quat_from_axis_angle(wp.vec3(1.0, 0.0, 0.0), -math.pi * 0.5)),
54
43
  floating=False,
55
44
  density=100,
56
45
  armature=0.1,
@@ -67,6 +56,15 @@ class Example:
67
56
 
68
57
  builder = wp.sim.ModelBuilder()
69
58
 
59
+ self.sim_time = 0.0
60
+ self.frame_dt = 1.0 / 60.0
61
+
62
+ episode_duration = 20.0 # seconds
63
+ self.episode_frames = int(episode_duration / self.frame_dt)
64
+
65
+ self.sim_substeps = 10
66
+ self.sim_dt = self.frame_dt / self.sim_substeps
67
+
70
68
  for i in range(num_envs):
71
69
  builder.add_builder(
72
70
  articulation_builder, xform=wp.transform(np.array((i * 2.0, 4.0, 0.0)), wp.quat_identity())
@@ -86,57 +84,62 @@ class Example:
86
84
 
87
85
  self.integrator = wp.sim.SemiImplicitIntegrator()
88
86
 
89
- # -----------------------
90
- # set up Usd renderer
87
+ self.enable_rendering = enable_rendering
91
88
  self.renderer = None
92
- if render:
93
- self.renderer = wp.sim.render.SimRenderer(self.model, stage, scaling=15.0)
94
-
95
- def update(self):
96
- for _ in range(self.sim_substeps):
97
- self.state.clear_forces()
98
- self.state = self.integrator.simulate(self.model, self.state, self.state, self.sim_dt)
99
-
100
- def render(self, is_live=False):
101
- time = 0.0 if is_live else self.sim_time
102
-
103
- self.renderer.begin_frame(time)
104
- self.renderer.render(self.state)
105
- self.renderer.end_frame()
89
+ if self.enable_rendering:
90
+ self.renderer = wp.sim.render.SimRenderer(path=stage, model=self.model, scaling=15.0)
106
91
 
107
- def run(self, render=True):
108
- # ---------------
109
- # run simulation
92
+ self.print_timers = print_timers
110
93
 
111
- self.sim_time = 0.0
112
94
  self.state = self.model.state()
113
95
 
114
96
  wp.sim.eval_fk(self.model, self.model.joint_q, self.model.joint_qd, None, self.state)
115
97
 
116
- profiler = {}
98
+ self.use_graph = wp.get_device().is_cuda
99
+ self.graph = None
117
100
 
118
- # create update graph
119
- wp.capture_begin()
101
+ if self.use_graph:
102
+ # create update graph
103
+ wp.capture_begin(self.device)
104
+ try:
105
+ self.update()
106
+ finally:
107
+ self.graph = wp.capture_end(self.device)
120
108
 
121
- # simulate
122
- self.update()
109
+ def update(self):
110
+ with wp.ScopedTimer("simulate", active=True, print=self.print_timers):
111
+ if not self.use_graph or self.graph is None:
112
+ for _ in range(self.sim_substeps):
113
+ self.state.clear_forces()
114
+ self.state = self.integrator.simulate(self.model, self.state, self.state, self.sim_dt)
115
+ else:
116
+ wp.capture_launch(self.graph)
117
+
118
+ if not wp.get_device().is_capturing:
119
+ self.sim_time += self.frame_dt
123
120
 
124
- graph = wp.capture_end()
121
+ def render(self, is_live=False):
122
+ if self.enable_rendering:
123
+ with wp.ScopedTimer("render", active=True, print=self.print_timers):
124
+ time = 0.0 if is_live else self.sim_time
125
125
 
126
- # simulate
127
- with wp.ScopedTimer("simulate", detailed=False, print=False, active=True, dict=profiler):
128
- for f in range(0, self.episode_frames):
129
- with wp.ScopedTimer("simulate", active=True):
130
- wp.capture_launch(graph)
131
- self.sim_time += self.frame_dt
126
+ self.renderer.begin_frame(time)
127
+ self.renderer.render(self.state)
128
+ self.renderer.end_frame()
129
+
130
+ def run(self):
131
+ profiler = {}
132
132
 
133
- if self.enable_rendering:
134
- with wp.ScopedTimer("render", active=True):
135
- self.render()
136
- self.renderer.save()
133
+ with wp.ScopedTimer("simulate", detailed=False, print=False, active=True, dict=profiler):
134
+ for _ in range(self.episode_frames):
135
+ self.update()
136
+ self.render()
137
137
 
138
138
  wp.synchronize()
139
139
 
140
+ if self.enable_rendering:
141
+ self.renderer.save()
142
+
140
143
  avg_time = np.array(profiler["simulate"]).mean() / self.episode_frames
141
144
  avg_steps_second = 1000.0 * float(self.num_envs) / avg_time
142
145
 
@@ -145,38 +148,39 @@ class Example:
145
148
  return 1000.0 * float(self.num_envs) / avg_time
146
149
 
147
150
 
148
- profile = False
151
+ if __name__ == "__main__":
152
+ profile = False
149
153
 
150
- if profile:
151
- env_count = 2
152
- env_times = []
153
- env_size = []
154
+ if profile:
155
+ env_count = 2
156
+ env_times = []
157
+ env_size = []
154
158
 
155
- for i in range(15):
156
- robot = Example(render=False, num_envs=env_count)
157
- steps_per_second = robot.run()
159
+ for i in range(15):
160
+ example = Example(num_envs=env_count, enable_rendering=False, print_timers=False)
161
+ steps_per_second = example.run()
158
162
 
159
- env_size.append(env_count)
160
- env_times.append(steps_per_second)
163
+ env_size.append(env_count)
164
+ env_times.append(steps_per_second)
161
165
 
162
- env_count *= 2
166
+ env_count *= 2
163
167
 
164
- # dump times
165
- for i in range(len(env_times)):
166
- print(f"envs: {env_size[i]} steps/second: {env_times[i]}")
168
+ # dump times
169
+ for i in range(len(env_times)):
170
+ print(f"envs: {env_size[i]} steps/second: {env_times[i]}")
167
171
 
168
- # plot
169
- import matplotlib.pyplot as plt
172
+ # plot
173
+ import matplotlib.pyplot as plt
170
174
 
171
- plt.figure(1)
172
- plt.plot(env_size, env_times)
173
- plt.xscale("log")
174
- plt.xlabel("Number of Envs")
175
- plt.yscale("log")
176
- plt.ylabel("Steps/Second")
177
- plt.show()
175
+ plt.figure(1)
176
+ plt.plot(env_size, env_times)
177
+ plt.xscale("log")
178
+ plt.xlabel("Number of Envs")
179
+ plt.yscale("log")
180
+ plt.ylabel("Steps/Second")
181
+ plt.show()
178
182
 
179
- else:
180
- stage = os.path.join(os.path.dirname(__file__), "outputs/example_sim_cartpole.usd")
181
- robot = Example(stage, render=True, num_envs=10)
182
- robot.run()
183
+ else:
184
+ stage = os.path.join(os.path.dirname(__file__), "outputs/example_sim_cartpole.usd")
185
+ example = Example(stage, num_envs=10)
186
+ example.run()