vispy 0.15.0__cp313-cp313-macosx_11_0_arm64.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 vispy might be problematic. Click here for more details.

Files changed (521) hide show
  1. vispy/__init__.py +33 -0
  2. vispy/app/__init__.py +15 -0
  3. vispy/app/_default_app.py +76 -0
  4. vispy/app/_detect_eventloop.py +148 -0
  5. vispy/app/application.py +263 -0
  6. vispy/app/backends/__init__.py +52 -0
  7. vispy/app/backends/_egl.py +264 -0
  8. vispy/app/backends/_glfw.py +513 -0
  9. vispy/app/backends/_jupyter_rfb.py +278 -0
  10. vispy/app/backends/_offscreen_util.py +121 -0
  11. vispy/app/backends/_osmesa.py +235 -0
  12. vispy/app/backends/_pyglet.py +451 -0
  13. vispy/app/backends/_pyqt4.py +36 -0
  14. vispy/app/backends/_pyqt5.py +36 -0
  15. vispy/app/backends/_pyqt6.py +40 -0
  16. vispy/app/backends/_pyside.py +37 -0
  17. vispy/app/backends/_pyside2.py +52 -0
  18. vispy/app/backends/_pyside6.py +53 -0
  19. vispy/app/backends/_qt.py +1003 -0
  20. vispy/app/backends/_sdl2.py +444 -0
  21. vispy/app/backends/_template.py +244 -0
  22. vispy/app/backends/_test.py +8 -0
  23. vispy/app/backends/_tk.py +800 -0
  24. vispy/app/backends/_wx.py +476 -0
  25. vispy/app/backends/tests/__init__.py +0 -0
  26. vispy/app/backends/tests/test_offscreen_util.py +52 -0
  27. vispy/app/backends/tests/test_rfb.py +77 -0
  28. vispy/app/base.py +294 -0
  29. vispy/app/canvas.py +828 -0
  30. vispy/app/qt.py +92 -0
  31. vispy/app/tests/__init__.py +0 -0
  32. vispy/app/tests/qt-designer.ui +58 -0
  33. vispy/app/tests/test_app.py +442 -0
  34. vispy/app/tests/test_backends.py +164 -0
  35. vispy/app/tests/test_canvas.py +122 -0
  36. vispy/app/tests/test_context.py +92 -0
  37. vispy/app/tests/test_qt.py +47 -0
  38. vispy/app/tests/test_simultaneous.py +134 -0
  39. vispy/app/timer.py +174 -0
  40. vispy/color/__init__.py +17 -0
  41. vispy/color/_color_dict.py +193 -0
  42. vispy/color/color_array.py +447 -0
  43. vispy/color/color_space.py +181 -0
  44. vispy/color/colormap.py +1213 -0
  45. vispy/color/tests/__init__.py +0 -0
  46. vispy/color/tests/test_color.py +378 -0
  47. vispy/conftest.py +12 -0
  48. vispy/ext/__init__.py +0 -0
  49. vispy/ext/cocoapy.py +1522 -0
  50. vispy/ext/cubehelix.py +138 -0
  51. vispy/ext/egl.py +375 -0
  52. vispy/ext/fontconfig.py +118 -0
  53. vispy/ext/gdi32plus.py +206 -0
  54. vispy/ext/osmesa.py +105 -0
  55. vispy/geometry/__init__.py +23 -0
  56. vispy/geometry/_triangulation_debugger.py +171 -0
  57. vispy/geometry/calculations.py +162 -0
  58. vispy/geometry/curves.py +399 -0
  59. vispy/geometry/generation.py +643 -0
  60. vispy/geometry/isocurve.py +175 -0
  61. vispy/geometry/isosurface.py +465 -0
  62. vispy/geometry/meshdata.py +700 -0
  63. vispy/geometry/normals.py +78 -0
  64. vispy/geometry/parametric.py +56 -0
  65. vispy/geometry/polygon.py +137 -0
  66. vispy/geometry/rect.py +210 -0
  67. vispy/geometry/tests/__init__.py +0 -0
  68. vispy/geometry/tests/test_calculations.py +23 -0
  69. vispy/geometry/tests/test_generation.py +56 -0
  70. vispy/geometry/tests/test_meshdata.py +106 -0
  71. vispy/geometry/tests/test_triangulation.py +594 -0
  72. vispy/geometry/torusknot.py +142 -0
  73. vispy/geometry/triangulation.py +876 -0
  74. vispy/gloo/__init__.py +56 -0
  75. vispy/gloo/buffer.py +505 -0
  76. vispy/gloo/context.py +272 -0
  77. vispy/gloo/framebuffer.py +257 -0
  78. vispy/gloo/gl/__init__.py +234 -0
  79. vispy/gloo/gl/_constants.py +332 -0
  80. vispy/gloo/gl/_es2.py +986 -0
  81. vispy/gloo/gl/_gl2.py +1365 -0
  82. vispy/gloo/gl/_proxy.py +499 -0
  83. vispy/gloo/gl/_pyopengl2.py +362 -0
  84. vispy/gloo/gl/dummy.py +24 -0
  85. vispy/gloo/gl/es2.py +62 -0
  86. vispy/gloo/gl/gl2.py +98 -0
  87. vispy/gloo/gl/glplus.py +168 -0
  88. vispy/gloo/gl/pyopengl2.py +97 -0
  89. vispy/gloo/gl/tests/__init__.py +0 -0
  90. vispy/gloo/gl/tests/test_basics.py +282 -0
  91. vispy/gloo/gl/tests/test_functionality.py +568 -0
  92. vispy/gloo/gl/tests/test_names.py +246 -0
  93. vispy/gloo/gl/tests/test_use.py +71 -0
  94. vispy/gloo/glir.py +1824 -0
  95. vispy/gloo/globject.py +101 -0
  96. vispy/gloo/preprocessor.py +67 -0
  97. vispy/gloo/program.py +543 -0
  98. vispy/gloo/tests/__init__.py +0 -0
  99. vispy/gloo/tests/test_buffer.py +558 -0
  100. vispy/gloo/tests/test_context.py +119 -0
  101. vispy/gloo/tests/test_framebuffer.py +195 -0
  102. vispy/gloo/tests/test_glir.py +307 -0
  103. vispy/gloo/tests/test_globject.py +35 -0
  104. vispy/gloo/tests/test_program.py +302 -0
  105. vispy/gloo/tests/test_texture.py +732 -0
  106. vispy/gloo/tests/test_use_gloo.py +187 -0
  107. vispy/gloo/tests/test_util.py +60 -0
  108. vispy/gloo/tests/test_wrappers.py +261 -0
  109. vispy/gloo/texture.py +1046 -0
  110. vispy/gloo/util.py +129 -0
  111. vispy/gloo/wrappers.py +762 -0
  112. vispy/glsl/__init__.py +42 -0
  113. vispy/glsl/antialias/antialias.glsl +7 -0
  114. vispy/glsl/antialias/cap-butt.glsl +31 -0
  115. vispy/glsl/antialias/cap-round.glsl +29 -0
  116. vispy/glsl/antialias/cap-square.glsl +30 -0
  117. vispy/glsl/antialias/cap-triangle-in.glsl +30 -0
  118. vispy/glsl/antialias/cap-triangle-out.glsl +30 -0
  119. vispy/glsl/antialias/cap.glsl +67 -0
  120. vispy/glsl/antialias/caps.glsl +67 -0
  121. vispy/glsl/antialias/filled.glsl +50 -0
  122. vispy/glsl/antialias/outline.glsl +40 -0
  123. vispy/glsl/antialias/stroke.glsl +43 -0
  124. vispy/glsl/arrowheads/angle.glsl +99 -0
  125. vispy/glsl/arrowheads/arrowheads.frag +60 -0
  126. vispy/glsl/arrowheads/arrowheads.glsl +12 -0
  127. vispy/glsl/arrowheads/arrowheads.vert +83 -0
  128. vispy/glsl/arrowheads/curved.glsl +48 -0
  129. vispy/glsl/arrowheads/inhibitor.glsl +26 -0
  130. vispy/glsl/arrowheads/stealth.glsl +46 -0
  131. vispy/glsl/arrowheads/triangle.glsl +97 -0
  132. vispy/glsl/arrowheads/util.glsl +13 -0
  133. vispy/glsl/arrows/angle-30.glsl +12 -0
  134. vispy/glsl/arrows/angle-60.glsl +12 -0
  135. vispy/glsl/arrows/angle-90.glsl +12 -0
  136. vispy/glsl/arrows/arrow.frag +39 -0
  137. vispy/glsl/arrows/arrow.vert +49 -0
  138. vispy/glsl/arrows/arrows.glsl +17 -0
  139. vispy/glsl/arrows/common.glsl +187 -0
  140. vispy/glsl/arrows/curved.glsl +63 -0
  141. vispy/glsl/arrows/stealth.glsl +50 -0
  142. vispy/glsl/arrows/triangle-30.glsl +12 -0
  143. vispy/glsl/arrows/triangle-60.glsl +12 -0
  144. vispy/glsl/arrows/triangle-90.glsl +12 -0
  145. vispy/glsl/arrows/util.glsl +98 -0
  146. vispy/glsl/build_spatial_filters.py +660 -0
  147. vispy/glsl/collections/agg-fast-path.frag +20 -0
  148. vispy/glsl/collections/agg-fast-path.vert +78 -0
  149. vispy/glsl/collections/agg-glyph.frag +60 -0
  150. vispy/glsl/collections/agg-glyph.vert +33 -0
  151. vispy/glsl/collections/agg-marker.frag +35 -0
  152. vispy/glsl/collections/agg-marker.vert +48 -0
  153. vispy/glsl/collections/agg-path.frag +55 -0
  154. vispy/glsl/collections/agg-path.vert +166 -0
  155. vispy/glsl/collections/agg-point.frag +21 -0
  156. vispy/glsl/collections/agg-point.vert +35 -0
  157. vispy/glsl/collections/agg-segment.frag +32 -0
  158. vispy/glsl/collections/agg-segment.vert +75 -0
  159. vispy/glsl/collections/marker.frag +38 -0
  160. vispy/glsl/collections/marker.vert +48 -0
  161. vispy/glsl/collections/raw-path.frag +15 -0
  162. vispy/glsl/collections/raw-path.vert +24 -0
  163. vispy/glsl/collections/raw-point.frag +14 -0
  164. vispy/glsl/collections/raw-point.vert +31 -0
  165. vispy/glsl/collections/raw-segment.frag +18 -0
  166. vispy/glsl/collections/raw-segment.vert +26 -0
  167. vispy/glsl/collections/raw-triangle.frag +13 -0
  168. vispy/glsl/collections/raw-triangle.vert +26 -0
  169. vispy/glsl/collections/sdf-glyph-ticks.vert +69 -0
  170. vispy/glsl/collections/sdf-glyph.frag +80 -0
  171. vispy/glsl/collections/sdf-glyph.vert +59 -0
  172. vispy/glsl/collections/tick-labels.vert +71 -0
  173. vispy/glsl/colormaps/autumn.glsl +20 -0
  174. vispy/glsl/colormaps/blues.glsl +20 -0
  175. vispy/glsl/colormaps/color-space.glsl +17 -0
  176. vispy/glsl/colormaps/colormaps.glsl +24 -0
  177. vispy/glsl/colormaps/cool.glsl +20 -0
  178. vispy/glsl/colormaps/fire.glsl +21 -0
  179. vispy/glsl/colormaps/gray.glsl +20 -0
  180. vispy/glsl/colormaps/greens.glsl +20 -0
  181. vispy/glsl/colormaps/hot.glsl +22 -0
  182. vispy/glsl/colormaps/ice.glsl +20 -0
  183. vispy/glsl/colormaps/icefire.glsl +23 -0
  184. vispy/glsl/colormaps/parse.py +40 -0
  185. vispy/glsl/colormaps/reds.glsl +20 -0
  186. vispy/glsl/colormaps/spring.glsl +20 -0
  187. vispy/glsl/colormaps/summer.glsl +20 -0
  188. vispy/glsl/colormaps/user.glsl +22 -0
  189. vispy/glsl/colormaps/util.glsl +41 -0
  190. vispy/glsl/colormaps/wheel.glsl +21 -0
  191. vispy/glsl/colormaps/winter.glsl +20 -0
  192. vispy/glsl/lines/agg.frag +320 -0
  193. vispy/glsl/lines/agg.vert +241 -0
  194. vispy/glsl/markers/arrow.glsl +12 -0
  195. vispy/glsl/markers/asterisk.glsl +16 -0
  196. vispy/glsl/markers/chevron.glsl +14 -0
  197. vispy/glsl/markers/clover.glsl +20 -0
  198. vispy/glsl/markers/club.glsl +31 -0
  199. vispy/glsl/markers/cross.glsl +17 -0
  200. vispy/glsl/markers/diamond.glsl +12 -0
  201. vispy/glsl/markers/disc.glsl +9 -0
  202. vispy/glsl/markers/ellipse.glsl +67 -0
  203. vispy/glsl/markers/hbar.glsl +9 -0
  204. vispy/glsl/markers/heart.glsl +15 -0
  205. vispy/glsl/markers/infinity.glsl +15 -0
  206. vispy/glsl/markers/marker-sdf.frag +74 -0
  207. vispy/glsl/markers/marker-sdf.vert +41 -0
  208. vispy/glsl/markers/marker.frag +36 -0
  209. vispy/glsl/markers/marker.vert +46 -0
  210. vispy/glsl/markers/markers.glsl +24 -0
  211. vispy/glsl/markers/pin.glsl +18 -0
  212. vispy/glsl/markers/ring.glsl +11 -0
  213. vispy/glsl/markers/spade.glsl +28 -0
  214. vispy/glsl/markers/square.glsl +10 -0
  215. vispy/glsl/markers/tag.glsl +11 -0
  216. vispy/glsl/markers/triangle.glsl +14 -0
  217. vispy/glsl/markers/vbar.glsl +9 -0
  218. vispy/glsl/math/circle-through-2-points.glsl +30 -0
  219. vispy/glsl/math/constants.glsl +48 -0
  220. vispy/glsl/math/double.glsl +114 -0
  221. vispy/glsl/math/functions.glsl +20 -0
  222. vispy/glsl/math/point-to-line-distance.glsl +31 -0
  223. vispy/glsl/math/point-to-line-projection.glsl +29 -0
  224. vispy/glsl/math/signed-line-distance.glsl +27 -0
  225. vispy/glsl/math/signed-segment-distance.glsl +30 -0
  226. vispy/glsl/misc/regular-grid.frag +244 -0
  227. vispy/glsl/misc/spatial-filters.frag +1407 -0
  228. vispy/glsl/misc/viewport-NDC.glsl +20 -0
  229. vispy/glsl/transforms/azimuthal-equal-area.glsl +32 -0
  230. vispy/glsl/transforms/azimuthal-equidistant.glsl +38 -0
  231. vispy/glsl/transforms/hammer.glsl +44 -0
  232. vispy/glsl/transforms/identity.glsl +6 -0
  233. vispy/glsl/transforms/identity_forward.glsl +23 -0
  234. vispy/glsl/transforms/identity_inverse.glsl +23 -0
  235. vispy/glsl/transforms/linear-scale.glsl +127 -0
  236. vispy/glsl/transforms/log-scale.glsl +126 -0
  237. vispy/glsl/transforms/mercator-transverse-forward.glsl +40 -0
  238. vispy/glsl/transforms/mercator-transverse-inverse.glsl +40 -0
  239. vispy/glsl/transforms/panzoom.glsl +10 -0
  240. vispy/glsl/transforms/polar.glsl +41 -0
  241. vispy/glsl/transforms/position.glsl +44 -0
  242. vispy/glsl/transforms/power-scale.glsl +139 -0
  243. vispy/glsl/transforms/projection.glsl +7 -0
  244. vispy/glsl/transforms/pvm.glsl +13 -0
  245. vispy/glsl/transforms/rotate.glsl +45 -0
  246. vispy/glsl/transforms/trackball.glsl +15 -0
  247. vispy/glsl/transforms/translate.glsl +35 -0
  248. vispy/glsl/transforms/transverse_mercator.glsl +38 -0
  249. vispy/glsl/transforms/viewport-clipping.glsl +14 -0
  250. vispy/glsl/transforms/viewport-transform.glsl +16 -0
  251. vispy/glsl/transforms/viewport.glsl +50 -0
  252. vispy/glsl/transforms/x.glsl +24 -0
  253. vispy/glsl/transforms/y.glsl +19 -0
  254. vispy/glsl/transforms/z.glsl +14 -0
  255. vispy/io/__init__.py +20 -0
  256. vispy/io/_data/spatial-filters.npy +0 -0
  257. vispy/io/datasets.py +94 -0
  258. vispy/io/image.py +231 -0
  259. vispy/io/mesh.py +122 -0
  260. vispy/io/stl.py +167 -0
  261. vispy/io/tests/__init__.py +0 -0
  262. vispy/io/tests/test_image.py +47 -0
  263. vispy/io/tests/test_io.py +121 -0
  264. vispy/io/wavefront.py +350 -0
  265. vispy/plot/__init__.py +36 -0
  266. vispy/plot/fig.py +58 -0
  267. vispy/plot/plotwidget.py +522 -0
  268. vispy/plot/tests/__init__.py +0 -0
  269. vispy/plot/tests/test_plot.py +46 -0
  270. vispy/scene/__init__.py +43 -0
  271. vispy/scene/cameras/__init__.py +27 -0
  272. vispy/scene/cameras/_base.py +38 -0
  273. vispy/scene/cameras/arcball.py +105 -0
  274. vispy/scene/cameras/base_camera.py +551 -0
  275. vispy/scene/cameras/fly.py +474 -0
  276. vispy/scene/cameras/magnify.py +163 -0
  277. vispy/scene/cameras/panzoom.py +311 -0
  278. vispy/scene/cameras/perspective.py +338 -0
  279. vispy/scene/cameras/tests/__init__.py +0 -0
  280. vispy/scene/cameras/tests/test_cameras.py +27 -0
  281. vispy/scene/cameras/tests/test_link.py +53 -0
  282. vispy/scene/cameras/tests/test_perspective.py +122 -0
  283. vispy/scene/cameras/turntable.py +183 -0
  284. vispy/scene/canvas.py +639 -0
  285. vispy/scene/events.py +85 -0
  286. vispy/scene/node.py +644 -0
  287. vispy/scene/subscene.py +20 -0
  288. vispy/scene/tests/__init__.py +0 -0
  289. vispy/scene/tests/test_canvas.py +119 -0
  290. vispy/scene/tests/test_node.py +142 -0
  291. vispy/scene/tests/test_visuals.py +141 -0
  292. vispy/scene/visuals.py +276 -0
  293. vispy/scene/widgets/__init__.py +18 -0
  294. vispy/scene/widgets/anchor.py +25 -0
  295. vispy/scene/widgets/axis.py +88 -0
  296. vispy/scene/widgets/colorbar.py +176 -0
  297. vispy/scene/widgets/console.py +351 -0
  298. vispy/scene/widgets/grid.py +509 -0
  299. vispy/scene/widgets/label.py +50 -0
  300. vispy/scene/widgets/tests/__init__.py +0 -0
  301. vispy/scene/widgets/tests/test_colorbar.py +47 -0
  302. vispy/scene/widgets/viewbox.py +199 -0
  303. vispy/scene/widgets/widget.py +478 -0
  304. vispy/testing/__init__.py +51 -0
  305. vispy/testing/_runners.py +448 -0
  306. vispy/testing/_testing.py +416 -0
  307. vispy/testing/image_tester.py +494 -0
  308. vispy/testing/rendered_array_tester.py +85 -0
  309. vispy/testing/tests/__init__.py +0 -0
  310. vispy/testing/tests/test_testing.py +20 -0
  311. vispy/util/__init__.py +32 -0
  312. vispy/util/bunch.py +15 -0
  313. vispy/util/check_environment.py +57 -0
  314. vispy/util/config.py +490 -0
  315. vispy/util/dpi/__init__.py +19 -0
  316. vispy/util/dpi/_linux.py +69 -0
  317. vispy/util/dpi/_quartz.py +26 -0
  318. vispy/util/dpi/_win32.py +34 -0
  319. vispy/util/dpi/tests/__init__.py +0 -0
  320. vispy/util/dpi/tests/test_dpi.py +16 -0
  321. vispy/util/eq.py +41 -0
  322. vispy/util/event.py +774 -0
  323. vispy/util/fetching.py +276 -0
  324. vispy/util/filter.py +44 -0
  325. vispy/util/fonts/__init__.py +14 -0
  326. vispy/util/fonts/_freetype.py +73 -0
  327. vispy/util/fonts/_quartz.py +192 -0
  328. vispy/util/fonts/_triage.py +36 -0
  329. vispy/util/fonts/_vispy_fonts.py +20 -0
  330. vispy/util/fonts/_win32.py +105 -0
  331. vispy/util/fonts/data/OpenSans-Bold.ttf +0 -0
  332. vispy/util/fonts/data/OpenSans-BoldItalic.ttf +0 -0
  333. vispy/util/fonts/data/OpenSans-Italic.ttf +0 -0
  334. vispy/util/fonts/data/OpenSans-Regular.ttf +0 -0
  335. vispy/util/fonts/tests/__init__.py +0 -0
  336. vispy/util/fonts/tests/test_font.py +45 -0
  337. vispy/util/fourier.py +69 -0
  338. vispy/util/frozen.py +25 -0
  339. vispy/util/gallery_scraper.py +268 -0
  340. vispy/util/keys.py +91 -0
  341. vispy/util/logs.py +358 -0
  342. vispy/util/osmesa_gl.py +17 -0
  343. vispy/util/profiler.py +135 -0
  344. vispy/util/ptime.py +16 -0
  345. vispy/util/quaternion.py +229 -0
  346. vispy/util/svg/__init__.py +18 -0
  347. vispy/util/svg/base.py +20 -0
  348. vispy/util/svg/color.py +219 -0
  349. vispy/util/svg/element.py +51 -0
  350. vispy/util/svg/geometry.py +478 -0
  351. vispy/util/svg/group.py +66 -0
  352. vispy/util/svg/length.py +81 -0
  353. vispy/util/svg/number.py +25 -0
  354. vispy/util/svg/path.py +332 -0
  355. vispy/util/svg/shapes.py +57 -0
  356. vispy/util/svg/style.py +59 -0
  357. vispy/util/svg/svg.py +40 -0
  358. vispy/util/svg/transform.py +223 -0
  359. vispy/util/svg/transformable.py +28 -0
  360. vispy/util/svg/viewport.py +73 -0
  361. vispy/util/tests/__init__.py +0 -0
  362. vispy/util/tests/test_config.py +58 -0
  363. vispy/util/tests/test_docstring_parameters.py +123 -0
  364. vispy/util/tests/test_emitter_group.py +262 -0
  365. vispy/util/tests/test_event_emitter.py +743 -0
  366. vispy/util/tests/test_fourier.py +35 -0
  367. vispy/util/tests/test_gallery_scraper.py +112 -0
  368. vispy/util/tests/test_import.py +127 -0
  369. vispy/util/tests/test_key.py +22 -0
  370. vispy/util/tests/test_logging.py +45 -0
  371. vispy/util/tests/test_run.py +14 -0
  372. vispy/util/tests/test_transforms.py +42 -0
  373. vispy/util/tests/test_vispy.py +48 -0
  374. vispy/util/transforms.py +201 -0
  375. vispy/util/wrappers.py +155 -0
  376. vispy/version.py +21 -0
  377. vispy/visuals/__init__.py +50 -0
  378. vispy/visuals/_scalable_textures.py +487 -0
  379. vispy/visuals/axis.py +678 -0
  380. vispy/visuals/border.py +208 -0
  381. vispy/visuals/box.py +79 -0
  382. vispy/visuals/collections/__init__.py +30 -0
  383. vispy/visuals/collections/agg_fast_path_collection.py +219 -0
  384. vispy/visuals/collections/agg_path_collection.py +197 -0
  385. vispy/visuals/collections/agg_point_collection.py +52 -0
  386. vispy/visuals/collections/agg_segment_collection.py +142 -0
  387. vispy/visuals/collections/array_list.py +401 -0
  388. vispy/visuals/collections/base_collection.py +482 -0
  389. vispy/visuals/collections/collection.py +253 -0
  390. vispy/visuals/collections/path_collection.py +23 -0
  391. vispy/visuals/collections/point_collection.py +19 -0
  392. vispy/visuals/collections/polygon_collection.py +25 -0
  393. vispy/visuals/collections/raw_path_collection.py +119 -0
  394. vispy/visuals/collections/raw_point_collection.py +113 -0
  395. vispy/visuals/collections/raw_polygon_collection.py +77 -0
  396. vispy/visuals/collections/raw_segment_collection.py +112 -0
  397. vispy/visuals/collections/raw_triangle_collection.py +78 -0
  398. vispy/visuals/collections/segment_collection.py +19 -0
  399. vispy/visuals/collections/triangle_collection.py +16 -0
  400. vispy/visuals/collections/util.py +168 -0
  401. vispy/visuals/colorbar.py +699 -0
  402. vispy/visuals/cube.py +41 -0
  403. vispy/visuals/ellipse.py +162 -0
  404. vispy/visuals/filters/__init__.py +10 -0
  405. vispy/visuals/filters/base_filter.py +242 -0
  406. vispy/visuals/filters/clipper.py +60 -0
  407. vispy/visuals/filters/clipping_planes.py +122 -0
  408. vispy/visuals/filters/color.py +181 -0
  409. vispy/visuals/filters/markers.py +28 -0
  410. vispy/visuals/filters/mesh.py +801 -0
  411. vispy/visuals/filters/picking.py +60 -0
  412. vispy/visuals/filters/tests/__init__.py +3 -0
  413. vispy/visuals/filters/tests/test_primitive_picking_filters.py +70 -0
  414. vispy/visuals/filters/tests/test_wireframe_filter.py +16 -0
  415. vispy/visuals/glsl/__init__.py +1 -0
  416. vispy/visuals/glsl/antialiasing.py +133 -0
  417. vispy/visuals/glsl/color.py +63 -0
  418. vispy/visuals/graphs/__init__.py +1 -0
  419. vispy/visuals/graphs/graph.py +240 -0
  420. vispy/visuals/graphs/layouts/__init__.py +55 -0
  421. vispy/visuals/graphs/layouts/circular.py +49 -0
  422. vispy/visuals/graphs/layouts/force_directed.py +211 -0
  423. vispy/visuals/graphs/layouts/networkx_layout.py +87 -0
  424. vispy/visuals/graphs/layouts/random.py +52 -0
  425. vispy/visuals/graphs/tests/__init__.py +1 -0
  426. vispy/visuals/graphs/tests/test_layouts.py +139 -0
  427. vispy/visuals/graphs/tests/test_networkx_layout.py +47 -0
  428. vispy/visuals/graphs/util.py +120 -0
  429. vispy/visuals/gridlines.py +161 -0
  430. vispy/visuals/gridmesh.py +98 -0
  431. vispy/visuals/histogram.py +58 -0
  432. vispy/visuals/image.py +701 -0
  433. vispy/visuals/image_complex.py +130 -0
  434. vispy/visuals/infinite_line.py +199 -0
  435. vispy/visuals/instanced_mesh.py +152 -0
  436. vispy/visuals/isocurve.py +213 -0
  437. vispy/visuals/isoline.py +241 -0
  438. vispy/visuals/isosurface.py +113 -0
  439. vispy/visuals/line/__init__.py +6 -0
  440. vispy/visuals/line/arrow.py +289 -0
  441. vispy/visuals/line/dash_atlas.py +90 -0
  442. vispy/visuals/line/line.py +545 -0
  443. vispy/visuals/line_plot.py +135 -0
  444. vispy/visuals/linear_region.py +199 -0
  445. vispy/visuals/markers.py +819 -0
  446. vispy/visuals/mesh.py +373 -0
  447. vispy/visuals/mesh_normals.py +159 -0
  448. vispy/visuals/plane.py +54 -0
  449. vispy/visuals/polygon.py +145 -0
  450. vispy/visuals/rectangle.py +196 -0
  451. vispy/visuals/regular_polygon.py +56 -0
  452. vispy/visuals/scrolling_lines.py +197 -0
  453. vispy/visuals/shaders/__init__.py +17 -0
  454. vispy/visuals/shaders/compiler.py +206 -0
  455. vispy/visuals/shaders/expression.py +99 -0
  456. vispy/visuals/shaders/function.py +788 -0
  457. vispy/visuals/shaders/multiprogram.py +145 -0
  458. vispy/visuals/shaders/parsing.py +140 -0
  459. vispy/visuals/shaders/program.py +161 -0
  460. vispy/visuals/shaders/shader_object.py +162 -0
  461. vispy/visuals/shaders/tests/__init__.py +0 -0
  462. vispy/visuals/shaders/tests/test_function.py +486 -0
  463. vispy/visuals/shaders/tests/test_multiprogram.py +78 -0
  464. vispy/visuals/shaders/tests/test_parsing.py +57 -0
  465. vispy/visuals/shaders/variable.py +272 -0
  466. vispy/visuals/spectrogram.py +169 -0
  467. vispy/visuals/sphere.py +80 -0
  468. vispy/visuals/surface_plot.py +192 -0
  469. vispy/visuals/tests/__init__.py +0 -0
  470. vispy/visuals/tests/test_arrows.py +109 -0
  471. vispy/visuals/tests/test_axis.py +120 -0
  472. vispy/visuals/tests/test_collections.py +15 -0
  473. vispy/visuals/tests/test_colorbar.py +179 -0
  474. vispy/visuals/tests/test_colormap.py +97 -0
  475. vispy/visuals/tests/test_ellipse.py +122 -0
  476. vispy/visuals/tests/test_gridlines.py +30 -0
  477. vispy/visuals/tests/test_histogram.py +24 -0
  478. vispy/visuals/tests/test_image.py +392 -0
  479. vispy/visuals/tests/test_image_complex.py +36 -0
  480. vispy/visuals/tests/test_infinite_line.py +53 -0
  481. vispy/visuals/tests/test_instanced_mesh.py +50 -0
  482. vispy/visuals/tests/test_isosurface.py +22 -0
  483. vispy/visuals/tests/test_linear_region.py +152 -0
  484. vispy/visuals/tests/test_markers.py +54 -0
  485. vispy/visuals/tests/test_mesh.py +261 -0
  486. vispy/visuals/tests/test_mesh_normals.py +218 -0
  487. vispy/visuals/tests/test_polygon.py +112 -0
  488. vispy/visuals/tests/test_rectangle.py +163 -0
  489. vispy/visuals/tests/test_regular_polygon.py +111 -0
  490. vispy/visuals/tests/test_scalable_textures.py +196 -0
  491. vispy/visuals/tests/test_sdf.py +73 -0
  492. vispy/visuals/tests/test_spectrogram.py +42 -0
  493. vispy/visuals/tests/test_surface_plot.py +57 -0
  494. vispy/visuals/tests/test_text.py +95 -0
  495. vispy/visuals/tests/test_volume.py +542 -0
  496. vispy/visuals/tests/test_windbarb.py +33 -0
  497. vispy/visuals/text/__init__.py +7 -0
  498. vispy/visuals/text/_sdf_cpu.cpython-313-darwin.so +0 -0
  499. vispy/visuals/text/_sdf_cpu.pyx +112 -0
  500. vispy/visuals/text/_sdf_gpu.py +316 -0
  501. vispy/visuals/text/text.py +675 -0
  502. vispy/visuals/transforms/__init__.py +34 -0
  503. vispy/visuals/transforms/_util.py +191 -0
  504. vispy/visuals/transforms/base_transform.py +233 -0
  505. vispy/visuals/transforms/chain.py +300 -0
  506. vispy/visuals/transforms/interactive.py +98 -0
  507. vispy/visuals/transforms/linear.py +564 -0
  508. vispy/visuals/transforms/nonlinear.py +398 -0
  509. vispy/visuals/transforms/tests/__init__.py +0 -0
  510. vispy/visuals/transforms/tests/test_transforms.py +243 -0
  511. vispy/visuals/transforms/transform_system.py +339 -0
  512. vispy/visuals/tube.py +173 -0
  513. vispy/visuals/visual.py +923 -0
  514. vispy/visuals/volume.py +1366 -0
  515. vispy/visuals/windbarb.py +291 -0
  516. vispy/visuals/xyz_axis.py +34 -0
  517. vispy-0.15.0.dist-info/METADATA +243 -0
  518. vispy-0.15.0.dist-info/RECORD +521 -0
  519. vispy-0.15.0.dist-info/WHEEL +6 -0
  520. vispy-0.15.0.dist-info/licenses/LICENSE.txt +36 -0
  521. vispy-0.15.0.dist-info/top_level.txt +1 -0
@@ -0,0 +1,28 @@
1
+ # -*- coding: utf-8 -*-
2
+ # -----------------------------------------------------------------------------
3
+ # Copyright (c) 2014, Nicolas P. Rougier. All rights reserved.
4
+ # Distributed under the terms of the new BSD License.
5
+ # -----------------------------------------------------------------------------
6
+ from . element import Element
7
+ from . transform import Transform
8
+
9
+
10
+ class Transformable(Element):
11
+ """Transformable SVG element"""
12
+
13
+ def __init__(self, content=None, parent=None):
14
+ Element.__init__(self, content, parent)
15
+
16
+ if isinstance(content, str):
17
+ self._transform = Transform()
18
+ self._computed_transform = self._transform
19
+ else:
20
+ self._transform = Transform(content.get("transform", None))
21
+ self._computed_transform = self._transform
22
+ if parent:
23
+ self._computed_transform = self._transform + \
24
+ self.parent.transform
25
+
26
+ @property
27
+ def transform(self):
28
+ return self._computed_transform
@@ -0,0 +1,73 @@
1
+ # -*- coding: utf-8 -*-
2
+ # -----------------------------------------------------------------------------
3
+ # Copyright (c) 2014, Nicolas P. Rougier. All rights reserved.
4
+ # Distributed under the terms of the new BSD License.
5
+ # -----------------------------------------------------------------------------
6
+
7
+ from . length import XLength, YLength
8
+
9
+
10
+ class Viewport(object):
11
+
12
+ def __init__(self, content=None, parent=None):
13
+
14
+ self._x = None
15
+ self._computed_x = 0
16
+ if content.get('x'):
17
+ self._x = XLength(content.get('x'), parent)
18
+ self._computed_x = float(self._x)
19
+
20
+ self._y = None
21
+ self._computed_y = 0
22
+ if content.get('y'):
23
+ self._y = XLength(content.get('y'), parent)
24
+ self._computed_y = float(self._y)
25
+
26
+ self._width = None
27
+ self._computed_width = 800
28
+ if content.get('width'):
29
+ self._width = XLength(content.get('width'), parent)
30
+ self._computed_width = float(self._width)
31
+
32
+ self._height = None
33
+ self._computed_height = 800
34
+ if content.get('height'):
35
+ self._height = YLength(content.get('height'), parent)
36
+ self._computed_height = float(self._height)
37
+
38
+ @property
39
+ def x(self):
40
+ return self._computed_x
41
+
42
+ @property
43
+ def y(self):
44
+ return self._computed_y
45
+
46
+ @property
47
+ def width(self):
48
+ return self._computed_width
49
+
50
+ @property
51
+ def height(self):
52
+ return self._computed_height
53
+
54
+ def __repr__(self):
55
+ s = repr((self._x, self._y, self._width, self._height))
56
+ return s
57
+
58
+ @property
59
+ def xml(self):
60
+ return self._xml
61
+
62
+ @property
63
+ def _xml(self, prefix=""):
64
+ s = ""
65
+ if self._x:
66
+ s += 'x="%s" ' % repr(self._x)
67
+ if self._y:
68
+ s += 'y="%s" ' % repr(self._y)
69
+ if self._width:
70
+ s += 'width="%s" ' % repr(self._width)
71
+ if self._height:
72
+ s += 'height="%s" ' % repr(self._height)
73
+ return s
File without changes
@@ -0,0 +1,58 @@
1
+ # -*- coding: utf-8 -*-
2
+ # Copyright (c) Vispy Development Team. All Rights Reserved.
3
+ # Distributed under the (new) BSD License. See LICENSE.txt for more info.
4
+ from os import path as op
5
+ import os
6
+
7
+ from vispy.util import (config, sys_info, _TempDir, set_data_dir, save_config,
8
+ load_data_file)
9
+ from vispy.testing import (assert_in, requires_application, run_tests_if_main,
10
+ assert_raises, assert_equal, assert_true,
11
+ requires_ssl)
12
+ temp_dir = _TempDir()
13
+
14
+
15
+ @requires_application()
16
+ def test_sys_info():
17
+ """Test printing of system information"""
18
+ fname = op.join(temp_dir, 'info.txt')
19
+ sys_info(fname)
20
+ assert_raises(IOError, sys_info, fname) # no overwrite
21
+ with open(fname, 'r') as fid:
22
+ out = ''.join(fid.readlines())
23
+ keys = ['GL version', 'Python', 'Backend', 'pyglet', 'Platform:']
24
+ for key in keys:
25
+ assert_in(key, out)
26
+ print(out)
27
+ assert_true('Info-gathering error' not in out)
28
+
29
+
30
+ @requires_ssl()
31
+ def test_config():
32
+ """Test vispy config methods and file downloading"""
33
+ assert_raises(TypeError, config.update, data_path=dict())
34
+ assert_raises(KeyError, config.update, foo='bar') # bad key
35
+ data_dir = op.join(temp_dir, 'data')
36
+ assert_raises(IOError, set_data_dir, data_dir) # didn't say to create
37
+ orig_val = os.environ.get('_VISPY_CONFIG_TESTING', None)
38
+ os.environ['_VISPY_CONFIG_TESTING'] = 'true'
39
+ try:
40
+ assert_raises(IOError, set_data_dir, data_dir) # doesn't exist yet
41
+ set_data_dir(data_dir, create=True, save=True)
42
+ assert_equal(config['data_path'], data_dir)
43
+ config['data_path'] = data_dir
44
+ print(config) # __repr__
45
+ load_data_file('CONTRIBUTING.txt')
46
+ fid = open(op.join(data_dir, 'test-faked.txt'), 'w')
47
+ fid.close()
48
+ load_data_file('test-faked.txt') # this one shouldn't download
49
+ assert_raises(RuntimeError, load_data_file, 'foo-nonexist.txt')
50
+ save_config()
51
+ finally:
52
+ if orig_val is not None:
53
+ os.environ['_VISPY_CONFIG_TESTING'] = orig_val
54
+ else:
55
+ del os.environ['_VISPY_CONFIG_TESTING']
56
+
57
+
58
+ run_tests_if_main()
@@ -0,0 +1,123 @@
1
+ # TODO inspect for Cython (see sagenb.misc.sageinspect)
2
+
3
+ import re
4
+ import inspect
5
+ import pytest
6
+
7
+ import vispy.scene.cameras.magnify
8
+ from vispy.testing import run_tests_if_main, requires_numpydoc
9
+
10
+
11
+ public_modules = [
12
+ # the list of modules users need to access for all functionality
13
+ 'vispy',
14
+ 'vispy.color',
15
+ 'vispy.geometry',
16
+ 'vispy.gloo',
17
+ 'vispy.io',
18
+ 'vispy.plot',
19
+ 'vispy.scene',
20
+ 'vispy.util',
21
+ 'vispy.visuals',
22
+ ]
23
+
24
+
25
+ def _func_name(func, cls=None):
26
+ """Get the name."""
27
+ parts = []
28
+ if cls is not None:
29
+ module = inspect.getmodule(cls)
30
+ else:
31
+ module = inspect.getmodule(func)
32
+ if module:
33
+ parts.append(module.__name__)
34
+ if cls is not None:
35
+ parts.append(cls.__name__)
36
+ parts.append(func.__name__)
37
+ return '.'.join(parts)
38
+
39
+
40
+ # functions to ignore
41
+ docstring_ignores = [
42
+ 'vispy.scene.visuals', # not parsed properly by this func, copies anyway
43
+ ]
44
+ error_ignores = {
45
+ # These we do not live by:
46
+ 'GL01', # Docstring should start in the line immediately after the quotes
47
+ 'EX01', 'EX02', # examples failed (we test them separately)
48
+ 'ES01', # no extended summary
49
+ 'SA01', # no see also
50
+ 'YD01', # no yields section
51
+ 'SA04', # no description in See Also
52
+ 'PR04', # Parameter "shape (n_channels" has no type
53
+ 'RT02', # The first line of the Returns section should contain only the type, unless multiple values are being returned # noqa
54
+ # XXX should also verify that | is used rather than , to separate params
55
+ # XXX should maybe also restore the parameter-desc-length < 800 char check
56
+ }
57
+ error_ignores_specific = {}
58
+ subclass_name_ignores = (
59
+ (vispy.scene.cameras.magnify.MagnifyCamera, {'MagnifyTransform', 'Magnify1DTransform'}),
60
+ )
61
+
62
+
63
+ def check_parameters_match(func, cls=None):
64
+ """Check docstring, return list of incorrect results."""
65
+ from numpydoc.validate import validate
66
+ name = _func_name(func, cls)
67
+ skip = (not name.startswith('vispy.') or
68
+ any(re.match(d, name) for d in docstring_ignores) or
69
+ 'deprecation_wrapped' in getattr(
70
+ getattr(func, '__code__', None), 'co_name', ''))
71
+ if skip:
72
+ return list()
73
+ if cls is not None:
74
+ for subclass, ignores in subclass_name_ignores:
75
+ if issubclass(cls, subclass) and name.split('.')[-1] in ignores:
76
+ return list()
77
+ incorrect = ['%s : %s : %s' % (name, err[0], err[1])
78
+ for err in validate(name)['errors']
79
+ if err[0] not in error_ignores and
80
+ (name.split('.')[-1], err[0]) not in error_ignores_specific]
81
+ return incorrect
82
+
83
+
84
+ @pytest.mark.xfail
85
+ @requires_numpydoc()
86
+ def test_docstring_parameters():
87
+ """Test module docstring formatting."""
88
+ from numpydoc import docscrape
89
+ incorrect = []
90
+ for name in public_modules:
91
+ # Assert that by default we import all public names with `import vispy`
92
+ # if name not in ('vispy'):
93
+ # extra = name.split('.')[1]
94
+ # assert hasattr(vispy, extra)
95
+ with pytest.warns(None): # traits warnings
96
+ module = __import__(name, globals())
97
+ for submod in name.split('.')[1:]:
98
+ module = getattr(module, submod)
99
+ classes = inspect.getmembers(module, inspect.isclass)
100
+ for cname, cls in classes:
101
+ if cname.startswith('_'):
102
+ continue
103
+ incorrect += check_parameters_match(cls)
104
+ cdoc = docscrape.ClassDoc(cls)
105
+ for method_name in cdoc.methods:
106
+ method = getattr(cls, method_name)
107
+ incorrect += check_parameters_match(method, cls=cls)
108
+ if hasattr(cls, '__call__') and \
109
+ 'of type object' not in str(cls.__call__):
110
+ incorrect += check_parameters_match(cls.__call__, cls)
111
+ functions = inspect.getmembers(module, inspect.isfunction)
112
+ for fname, func in functions:
113
+ if fname.startswith('_'):
114
+ continue
115
+ incorrect += check_parameters_match(func)
116
+ incorrect = sorted(list(set(incorrect)))
117
+ msg = '\n' + '\n'.join(incorrect)
118
+ msg += '\n%d error%s' % (len(incorrect), 's' if len(incorrect) == 1 else '')
119
+ if len(incorrect) > 0:
120
+ raise AssertionError(msg)
121
+
122
+
123
+ run_tests_if_main()
@@ -0,0 +1,262 @@
1
+ # -*- coding: utf-8 -*-
2
+ # Copyright (c) Vispy Development Team. All Rights Reserved.
3
+ # Distributed under the (new) BSD License. See LICENSE.txt for more info.
4
+ import unittest
5
+ import copy
6
+
7
+ from vispy.util.event import Event, EventEmitter, EmitterGroup
8
+ from vispy.util import use_log_level
9
+ from vispy.testing import run_tests_if_main, assert_true, assert_raises
10
+
11
+
12
+ class BasicEvent(Event):
13
+ pass
14
+
15
+
16
+ class TypedEvent(Event):
17
+
18
+ def __init__(self, **kwargs):
19
+ kwargs['type'] = 'typed_event'
20
+ Event.__init__(self, **kwargs)
21
+
22
+
23
+ class TestGroups(unittest.TestCase):
24
+
25
+ def test_group_construction(self):
26
+ """The EmitterGroup basic construction"""
27
+ grp = EmitterGroup(em1=Event,
28
+ em2=BasicEvent,
29
+ em3=TypedEvent)
30
+
31
+ grp.em1.connect(self.record_event)
32
+ grp.em2.connect(self.record_event)
33
+ grp.em3.connect(self.record_event)
34
+ self.result = None
35
+ ev = grp.em1()
36
+ self.assert_result(event=ev, type='em1', event_class=Event)
37
+ ev = grp.em2()
38
+ self.assert_result(event=ev, type='em2', event_class=BasicEvent)
39
+ ev = grp.em3()
40
+ self.assert_result(
41
+ event=ev,
42
+ type='typed_event',
43
+ event_class=TypedEvent)
44
+
45
+ def test_group_add_emitter(self):
46
+ """The EmitterGroup.add"""
47
+ grp = EmitterGroup(em1=Event)
48
+ grp.em1.connect(self.record_event)
49
+ self.result = None
50
+ ev = grp.em1()
51
+ self.assert_result(event=ev, type='em1')
52
+
53
+ grp.add(em2=BasicEvent)
54
+ grp.em2.connect(self.record_event)
55
+ ev = grp.em2()
56
+ self.assert_result(event=ev, type='em2', event_class=BasicEvent)
57
+
58
+ grp.add(em3=TypedEvent)
59
+ grp.em3.connect(self.record_event)
60
+ ev = grp.em3(test_key=2)
61
+ self.assert_result(
62
+ event=ev,
63
+ type='typed_event',
64
+ event_class=TypedEvent,
65
+ test_key=2)
66
+
67
+ try:
68
+ grp.add(em3=Event)
69
+ assert False, "Double-added emitter"
70
+ except ValueError:
71
+ pass
72
+
73
+ try:
74
+ grp.add(add=Event)
75
+ assert False, "Added event with invalid name"
76
+ except ValueError:
77
+ pass
78
+
79
+ def test_group_block(self):
80
+ """EmitterGroup.block_all"""
81
+ grp = EmitterGroup(em1=Event, em2=Event)
82
+
83
+ def cb(ev):
84
+ self.result = 1
85
+ grp.em1.connect(self.record_event)
86
+ grp.em2.connect(self.record_event)
87
+ grp.connect(cb)
88
+
89
+ self.result = None
90
+ grp.block_all()
91
+ try:
92
+ grp.em1()
93
+ grp.em2()
94
+ grp(type='test_event')
95
+ finally:
96
+ grp.unblock_all()
97
+ assert self.result is None
98
+
99
+ def test_group_ignore(self):
100
+ """EmitterGroup.block_all"""
101
+ grp = EmitterGroup(em1=Event)
102
+ grp.em1.connect(self.error_event)
103
+ with use_log_level('warning',
104
+ record=True, print_msg=False) as emit_list:
105
+ grp.em1()
106
+ assert_true(len(emit_list) >= 1)
107
+ grp.ignore_callback_errors = False
108
+ assert_raises(RuntimeError, grp.em1)
109
+ grp.ignore_callback_errors = True
110
+ with use_log_level('warning',
111
+ record=True, print_msg=False) as emit_list:
112
+ grp.em1()
113
+ assert_true(len(emit_list) >= 1)
114
+
115
+ def test_group_disconnect(self):
116
+ """EmitterGroup.disconnect"""
117
+ grp = EmitterGroup(em1=Event)
118
+
119
+ assert len(grp.em1.callbacks) == 0, grp.em1.callbacks
120
+ grp.connect(self.record_event)
121
+ assert len(grp.em1.callbacks) == 1
122
+ grp.add(em2=Event)
123
+ assert len(grp.em2.callbacks) == 1
124
+ grp.disconnect()
125
+ assert len(grp.em1.callbacks) == 0
126
+ assert len(grp.em2.callbacks) == 0
127
+
128
+ def test_group_autoconnect(self):
129
+ """The EmitterGroup auto-connect"""
130
+ class Source:
131
+
132
+ def on_em1(self, ev):
133
+ self.result = 1
134
+
135
+ def em2_event(self, ev):
136
+ self.result = 2
137
+
138
+ def em3_event(self, ev):
139
+ self.result = 3
140
+ src = Source()
141
+ grp = EmitterGroup(source=src, em1=Event, auto_connect=False)
142
+ src.result = None
143
+ grp.em1()
144
+ assert src.result is None
145
+
146
+ grp = EmitterGroup(source=src, em1=Event, auto_connect=True)
147
+ src.result = None
148
+ grp.em1()
149
+ assert src.result == 1
150
+
151
+ grp.auto_connect_format = "%s_event"
152
+ grp.add(em2=Event)
153
+ src.result = None
154
+ grp.em2()
155
+ assert src.result == 2
156
+
157
+ grp.add(em3=Event, auto_connect=False)
158
+ src.result = None
159
+ grp.em3()
160
+ assert src.result is None
161
+
162
+ def test_add_custom_emitter(self):
163
+ class Emitter(EventEmitter):
164
+
165
+ def _prepare_event(self, *args, **kwargs):
166
+ ev = super(Emitter, self)._prepare_event(*args, **kwargs)
167
+ ev.test_key = 1
168
+ return ev
169
+
170
+ class Source:
171
+ pass
172
+ src = Source()
173
+
174
+ grp = EmitterGroup(source=src, em1=Emitter(type='test_event1'))
175
+ grp.em1.connect(self.record_event)
176
+ self.result = None
177
+ ev = grp.em1()
178
+ self.assert_result(
179
+ event=ev,
180
+ test_key=1,
181
+ type='test_event1',
182
+ source=src)
183
+
184
+ grp.add(em2=Emitter(type='test_event2'))
185
+ grp.em2.connect(self.record_event)
186
+ self.result = None
187
+ ev = grp.em2()
188
+ self.assert_result(
189
+ event=ev,
190
+ test_key=1,
191
+ type='test_event2',
192
+ source=src)
193
+
194
+ def test_group_connect(self):
195
+ grp = EmitterGroup(source=self, em1=Event)
196
+ grp.connect(self.record_event)
197
+ self.result = None
198
+ ev = grp.em1(test_key=1)
199
+ self.assert_result(
200
+ event=ev,
201
+ source=self,
202
+ sources=[
203
+ self,
204
+ self],
205
+ test_key=1)
206
+
207
+ def record_event(self, ev, key=None):
208
+ # get a copy of all event attributes because these may change
209
+ # as the event is passed around; we want to know exactly what the event
210
+ # looked like when it reached this callback.
211
+ names = [name for name in dir(ev) if name[0] != '_']
212
+ attrs = {}
213
+ for name in names:
214
+ val = getattr(ev, name)
215
+ if name == 'source':
216
+ attrs[name] = val
217
+ elif name == 'sources':
218
+ attrs[name] = val[:]
219
+ else:
220
+ try:
221
+ attrs[name] = copy.deepcopy(val)
222
+ except Exception:
223
+ try:
224
+ attrs[name] = copy.copy(val)
225
+ except Exception:
226
+ attrs[name] = val
227
+ if key is None:
228
+ self.result = ev, attrs
229
+ else:
230
+ if not hasattr(self, 'result') or self.result is None:
231
+ self.result = {}
232
+ self.result[key] = ev, attrs
233
+
234
+ def error_event(self, ev, key=None):
235
+ raise RuntimeError('Errored')
236
+
237
+ def assert_result(self, key=None, **kwargs):
238
+ assert (hasattr(self, 'result') and self.result is not None), \
239
+ "No event recorded"
240
+
241
+ if key is None:
242
+ event, event_attrs = self.result
243
+ else:
244
+ event, event_attrs = self.result[key]
245
+
246
+ assert isinstance(event, Event), "Emitted object is not Event instance"
247
+
248
+ for name, val in kwargs.items():
249
+ if name == 'event':
250
+ assert event is val, "Event objects do not match"
251
+
252
+ elif name == 'event_class':
253
+ assert isinstance(event, val), \
254
+ "Emitted object is not instance of %s" % val.__name__
255
+
256
+ else:
257
+ attr = event_attrs[name]
258
+ assert (attr == val), "Event.%s != %s (%s)" % (
259
+ name, str(val), str(attr))
260
+
261
+
262
+ run_tests_if_main()