seraplot 2.3.73__tar.gz → 2.3.74__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.
Files changed (402) hide show
  1. {seraplot-2.3.73 → seraplot-2.3.74}/Cargo.lock +1 -1
  2. {seraplot-2.3.73 → seraplot-2.3.74}/Cargo.toml +1 -1
  3. {seraplot-2.3.73 → seraplot-2.3.74}/PKG-INFO +1 -1
  4. {seraplot-2.3.73 → seraplot-2.3.74}/pyproject.toml +1 -1
  5. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/commands/charts.rs +87 -20
  6. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/commands/native.rs +96 -177
  7. {seraplot-2.3.73 → seraplot-2.3.74}/.gitignore +0 -0
  8. {seraplot-2.3.73 → seraplot-2.3.74}/05--Diabetes_SeraPlot.ipynb +0 -0
  9. {seraplot-2.3.73 → seraplot-2.3.74}/07--OpenFoodFacts_SeraPlot_Benchmark.ipynb +0 -0
  10. {seraplot-2.3.73 → seraplot-2.3.74}/README.md +0 -0
  11. {seraplot-2.3.73 → seraplot-2.3.74}/TEST_1M_Battle.ipynb +0 -0
  12. {seraplot-2.3.73 → seraplot-2.3.74}/bench_all.py +0 -0
  13. {seraplot-2.3.73 → seraplot-2.3.74}/bench_bigdata.py +0 -0
  14. {seraplot-2.3.73 → seraplot-2.3.74}/bench_full.py +0 -0
  15. {seraplot-2.3.73 → seraplot-2.3.74}/bench_issues.json +0 -0
  16. {seraplot-2.3.73 → seraplot-2.3.74}/bench_knn_sgd.py +0 -0
  17. {seraplot-2.3.73 → seraplot-2.3.74}/bench_perf.py +0 -0
  18. {seraplot-2.3.73 → seraplot-2.3.74}/bench_quick.py +0 -0
  19. {seraplot-2.3.73 → seraplot-2.3.74}/bench_quick2.py +0 -0
  20. {seraplot-2.3.73 → seraplot-2.3.74}/bench_scale.py +0 -0
  21. {seraplot-2.3.73 → seraplot-2.3.74}/bench_seraplot.py +0 -0
  22. {seraplot-2.3.73 → seraplot-2.3.74}/bench_sklearn.py +0 -0
  23. {seraplot-2.3.73 → seraplot-2.3.74}/bench_svc.py +0 -0
  24. {seraplot-2.3.73 → seraplot-2.3.74}/bench_svc2.py +0 -0
  25. {seraplot-2.3.73 → seraplot-2.3.74}/bench_test.py +0 -0
  26. {seraplot-2.3.73 → seraplot-2.3.74}/benchmark_gridsearch.py +0 -0
  27. {seraplot-2.3.73 → seraplot-2.3.74}/benchmark_gridsearch2.py +0 -0
  28. {seraplot-2.3.73 → seraplot-2.3.74}/benchmark_kmeans_heavy.ipynb +0 -0
  29. {seraplot-2.3.73 → seraplot-2.3.74}/benchmark_kmeans_openfoodfacts.ipynb +0 -0
  30. {seraplot-2.3.73 → seraplot-2.3.74}/benchmark_ml.ipynb +0 -0
  31. {seraplot-2.3.73 → seraplot-2.3.74}/benchmark_ml_openfoodfacts.ipynb +0 -0
  32. {seraplot-2.3.73 → seraplot-2.3.74}/benchmark_ml_out.ipynb +0 -0
  33. {seraplot-2.3.73 → seraplot-2.3.74}/gen_bench_slides.py +0 -0
  34. {seraplot-2.3.73 → seraplot-2.3.74}/images/2d/1.png +0 -0
  35. {seraplot-2.3.73 → seraplot-2.3.74}/images/2d/2.png +0 -0
  36. {seraplot-2.3.73 → seraplot-2.3.74}/images/2d/3.png +0 -0
  37. {seraplot-2.3.73 → seraplot-2.3.74}/images/2d/4.png +0 -0
  38. {seraplot-2.3.73 → seraplot-2.3.74}/images/2d/5.png +0 -0
  39. {seraplot-2.3.73 → seraplot-2.3.74}/images/2d/6.png +0 -0
  40. {seraplot-2.3.73 → seraplot-2.3.74}/images/2d/7.png +0 -0
  41. {seraplot-2.3.73 → seraplot-2.3.74}/images/2d/8.png +0 -0
  42. {seraplot-2.3.73 → seraplot-2.3.74}/images/3d/1.png +0 -0
  43. {seraplot-2.3.73 → seraplot-2.3.74}/images/3d/2.png +0 -0
  44. {seraplot-2.3.73 → seraplot-2.3.74}/images/3d/3.png +0 -0
  45. {seraplot-2.3.73 → seraplot-2.3.74}/images/3d/4.png +0 -0
  46. {seraplot-2.3.73 → seraplot-2.3.74}/images/3d/5.png +0 -0
  47. {seraplot-2.3.73 → seraplot-2.3.74}/images/3d/6.png +0 -0
  48. {seraplot-2.3.73 → seraplot-2.3.74}/images/3d/7.png +0 -0
  49. {seraplot-2.3.73 → seraplot-2.3.74}/images/3d/8.png +0 -0
  50. {seraplot-2.3.73 → seraplot-2.3.74}/images/README.md +0 -0
  51. {seraplot-2.3.73 → seraplot-2.3.74}/images/benchmark/1.png +0 -0
  52. {seraplot-2.3.73 → seraplot-2.3.74}/images/benchmark/2.png +0 -0
  53. {seraplot-2.3.73 → seraplot-2.3.74}/images/benchmark/3.png +0 -0
  54. {seraplot-2.3.73 → seraplot-2.3.74}/images/logo.png +0 -0
  55. {seraplot-2.3.73 → seraplot-2.3.74}/kmeans_test.html +0 -0
  56. {seraplot-2.3.73 → seraplot-2.3.74}/python/seraplot/__init__.py +0 -0
  57. {seraplot-2.3.73 → seraplot-2.3.74}/python/seraplot/matplotlib.py +0 -0
  58. {seraplot-2.3.73 → seraplot-2.3.74}/python/seraplot/seraplot.cp311-win_amd64.pyd.old +0 -0
  59. {seraplot-2.3.73 → seraplot-2.3.74}/results_seraplot.json +0 -0
  60. {seraplot-2.3.73 → seraplot-2.3.74}/results_sklearn.json +0 -0
  61. {seraplot-2.3.73 → seraplot-2.3.74}/src/.github/workflows/mdbook.yml +0 -0
  62. {seraplot-2.3.73 → seraplot-2.3.74}/src/README.md +0 -0
  63. {seraplot-2.3.73 → seraplot-2.3.74}/src/asset/SVG World Map with labels.svg +0 -0
  64. {seraplot-2.3.73 → seraplot-2.3.74}/src/asset/logo.png +0 -0
  65. {seraplot-2.3.73 → seraplot-2.3.74}/src/asset/world.svg +0 -0
  66. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/builder_template.rs +0 -0
  67. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/chart_types.rs +0 -0
  68. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/commands/docs.rs +0 -0
  69. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/commands/ml.rs +0 -0
  70. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/commands/mod.rs +0 -0
  71. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/commands/registry.rs +0 -0
  72. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/export_builder.rs +0 -0
  73. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/fast_export_c.rs +0 -0
  74. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/fast_render.rs +0 -0
  75. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/memory_pool.rs +0 -0
  76. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/mod.rs +0 -0
  77. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/registry_macro.rs +0 -0
  78. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/unified_builder.rs +0 -0
  79. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/unified_config.rs +0 -0
  80. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/utils/arena_alloc.rs +0 -0
  81. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/utils/bitset.rs +0 -0
  82. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/utils/compact_state.rs +0 -0
  83. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/utils/data_processor.rs +0 -0
  84. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/utils/image_processor.rs +0 -0
  85. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/utils/lazy_builders.rs +0 -0
  86. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/utils/memory_pool.rs +0 -0
  87. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/utils/mod.rs +0 -0
  88. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/utils/simd_ops.rs +0 -0
  89. {seraplot-2.3.73 → seraplot-2.3.74}/src/bindings/utils/state_export.rs +0 -0
  90. {seraplot-2.3.73 → seraplot-2.3.74}/src/book.toml +0 -0
  91. {seraplot-2.3.73 → seraplot-2.3.74}/src/core/builders.rs +0 -0
  92. {seraplot-2.3.73 → seraplot-2.3.74}/src/core/math.rs +0 -0
  93. {seraplot-2.3.73 → seraplot-2.3.74}/src/core/mod.rs +0 -0
  94. {seraplot-2.3.73 → seraplot-2.3.74}/src/data/conversion.rs +0 -0
  95. {seraplot-2.3.73 → seraplot-2.3.74}/src/data/index.rs +0 -0
  96. {seraplot-2.3.73 → seraplot-2.3.74}/src/data/loader.rs +0 -0
  97. {seraplot-2.3.73 → seraplot-2.3.74}/src/data/mod.rs +0 -0
  98. {seraplot-2.3.73 → seraplot-2.3.74}/src/data/processor.rs +0 -0
  99. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/SUMMARY.md +0 -0
  100. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/api/index.md +0 -0
  101. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/area.md +0 -0
  102. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/bar.md +0 -0
  103. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/boxplot.md +0 -0
  104. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/bubble.md +0 -0
  105. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/bullet.md +0 -0
  106. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/candlestick.md +0 -0
  107. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/donut.md +0 -0
  108. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/dumbbell.md +0 -0
  109. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/funnel.md +0 -0
  110. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/gauge.md +0 -0
  111. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/grid.md +0 -0
  112. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/grouped-bar.md +0 -0
  113. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/hbar.md +0 -0
  114. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/heatmap.md +0 -0
  115. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/histogram-overlay.md +0 -0
  116. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/histogram.md +0 -0
  117. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/index.md +0 -0
  118. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/kde.md +0 -0
  119. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/line.md +0 -0
  120. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/lollipop.md +0 -0
  121. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/multiline.md +0 -0
  122. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/parallel.md +0 -0
  123. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/pie.md +0 -0
  124. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/radar.md +0 -0
  125. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/ridgeline.md +0 -0
  126. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/scatter.md +0 -0
  127. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/slideshow.md +0 -0
  128. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/slope.md +0 -0
  129. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/stacked-bar.md +0 -0
  130. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/sunburst.md +0 -0
  131. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/treemap.md +0 -0
  132. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/violin.md +0 -0
  133. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/waterfall.md +0 -0
  134. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/2d/wordcloud.md +0 -0
  135. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/bar3d.md +0 -0
  136. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/bubble3d.md +0 -0
  137. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/candlestick3d.md +0 -0
  138. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/dumbbell3d.md +0 -0
  139. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/funnel3d.md +0 -0
  140. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/globe3d.md +0 -0
  141. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/heatmap3d.md +0 -0
  142. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/index.md +0 -0
  143. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/kde3d.md +0 -0
  144. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/line3d.md +0 -0
  145. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/lollipop3d.md +0 -0
  146. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/pie3d.md +0 -0
  147. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/radar3d.md +0 -0
  148. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/ridgeline3d.md +0 -0
  149. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/scatter3d.md +0 -0
  150. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/stacked-bar3d.md +0 -0
  151. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/sunburst3d.md +0 -0
  152. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/3d/violin3d.md +0 -0
  153. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/map/bubble-map.md +0 -0
  154. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/map/choropleth.md +0 -0
  155. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/charts/map/index.md +0 -0
  156. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/config/auto-display.md +0 -0
  157. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/config/background.md +0 -0
  158. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/config/hover.md +0 -0
  159. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/config/palette.md +0 -0
  160. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/getting-started/chart-methods.md +0 -0
  161. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/getting-started/chart-object.md +0 -0
  162. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/getting-started/installation.md +0 -0
  163. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/getting-started/quickstart.md +0 -0
  164. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/introduction.md +0 -0
  165. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/adaboost.md +0 -0
  166. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/bayes-index.md +0 -0
  167. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/clustering-index.md +0 -0
  168. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/dbscan-class.md +0 -0
  169. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/dbscan.md +0 -0
  170. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/dbscan3d.md +0 -0
  171. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/decision-tree.md +0 -0
  172. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/decomposition-index.md +0 -0
  173. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/decomposition.md +0 -0
  174. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/elastic-net.md +0 -0
  175. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/evaluation-index.md +0 -0
  176. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/gradient-boosting.md +0 -0
  177. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/grid-search.md +0 -0
  178. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/index.md +0 -0
  179. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/kmeans-class.md +0 -0
  180. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/kmeans.md +0 -0
  181. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/knn.md +0 -0
  182. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/lasso.md +0 -0
  183. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/linear-index.md +0 -0
  184. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/linear-regression.md +0 -0
  185. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/logistic-regression.md +0 -0
  186. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/metrics.md +0 -0
  187. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/naive-bayes.md +0 -0
  188. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/neighbors-index.md +0 -0
  189. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/preprocessing-index.md +0 -0
  190. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/preprocessing.md +0 -0
  191. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/random-forest.md +0 -0
  192. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/ridge.md +0 -0
  193. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/selection-index.md +0 -0
  194. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/sgd.md +0 -0
  195. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/svm-index.md +0 -0
  196. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/svm.md +0 -0
  197. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/train-test-split.md +0 -0
  198. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/ml/tree-index.md +0 -0
  199. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/area.html +0 -0
  200. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/bar.html +0 -0
  201. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/bar3d.html +0 -0
  202. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/bench-matplotlib.html +0 -0
  203. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/bench-plotly.html +0 -0
  204. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/bench-seraplot.html +0 -0
  205. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/boxplot.html +0 -0
  206. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/bubble-map.html +0 -0
  207. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/bubble.html +0 -0
  208. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/bubble3d.html +0 -0
  209. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/bullet.html +0 -0
  210. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/candlestick.html +0 -0
  211. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/candlestick3d.html +0 -0
  212. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/choropleth.html +0 -0
  213. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/dbscan-class.html +0 -0
  214. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/dbscan.html +0 -0
  215. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/dbscan3d.html +0 -0
  216. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/donut.html +0 -0
  217. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/dumbbell.html +0 -0
  218. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/dumbbell3d.html +0 -0
  219. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/funnel.html +0 -0
  220. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/funnel3d.html +0 -0
  221. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/gauge.html +0 -0
  222. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/globe3d.html +0 -0
  223. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/grid.html +0 -0
  224. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/grouped-bar.html +0 -0
  225. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/hbar.html +0 -0
  226. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/heatmap.html +0 -0
  227. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/heatmap3d.html +0 -0
  228. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/histogram-overlay.html +0 -0
  229. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/histogram.html +0 -0
  230. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/kde.html +0 -0
  231. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/kde3d.html +0 -0
  232. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/line.html +0 -0
  233. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/line3d.html +0 -0
  234. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/lollipop.html +0 -0
  235. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/lollipop3d.html +0 -0
  236. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/multiline.html +0 -0
  237. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/parallel.html +0 -0
  238. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/pie.html +0 -0
  239. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/pie3d.html +0 -0
  240. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/radar.html +0 -0
  241. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/radar3d.html +0 -0
  242. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/ridgeline.html +0 -0
  243. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/ridgeline3d.html +0 -0
  244. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/scatter.html +0 -0
  245. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/scatter3d.html +0 -0
  246. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/slideshow.html +0 -0
  247. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/slope.html +0 -0
  248. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/stacked-bar.html +0 -0
  249. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/stacked-bar3d.html +0 -0
  250. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/sunburst.html +0 -0
  251. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/sunburst3d.html +0 -0
  252. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/treemap.html +0 -0
  253. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/violin.html +0 -0
  254. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/violin3d.html +0 -0
  255. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/waterfall.html +0 -0
  256. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/previews/wordcloud.html +0 -0
  257. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/theme/custom.css +0 -0
  258. {seraplot-2.3.73 → seraplot-2.3.74}/src/docs/theme/lang-switcher.js +0 -0
  259. {seraplot-2.3.73 → seraplot-2.3.74}/src/html/assets.rs +0 -0
  260. {seraplot-2.3.73 → seraplot-2.3.74}/src/html/fast_builders.rs +0 -0
  261. {seraplot-2.3.73 → seraplot-2.3.74}/src/html/fast_exporter.rs +0 -0
  262. {seraplot-2.3.73 → seraplot-2.3.74}/src/html/hover.rs +0 -0
  263. {seraplot-2.3.73 → seraplot-2.3.74}/src/html/html_export.rs +0 -0
  264. {seraplot-2.3.73 → seraplot-2.3.74}/src/html/html_template.rs +0 -0
  265. {seraplot-2.3.73 → seraplot-2.3.74}/src/html/js_3d.rs +0 -0
  266. {seraplot-2.3.73 → seraplot-2.3.74}/src/html/mod.rs +0 -0
  267. {seraplot-2.3.73 → seraplot-2.3.74}/src/lib.rs +0 -0
  268. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/cache.rs +0 -0
  269. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/decomposition/mod.rs +0 -0
  270. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/decomposition/pca.rs +0 -0
  271. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/linalg.rs +0 -0
  272. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/linear/elastic_net.rs +0 -0
  273. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/linear/lasso.rs +0 -0
  274. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/linear/logistic.rs +0 -0
  275. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/linear/mod.rs +0 -0
  276. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/linear/ols.rs +0 -0
  277. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/linear/ridge.rs +0 -0
  278. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/linear/sgd.rs +0 -0
  279. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/metrics/classification.rs +0 -0
  280. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/metrics/mod.rs +0 -0
  281. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/metrics/regression.rs +0 -0
  282. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/mod.rs +0 -0
  283. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/model_selection/cross_val.rs +0 -0
  284. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/model_selection/grid_search.rs +0 -0
  285. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/model_selection/mod.rs +0 -0
  286. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/model_selection/split.rs +0 -0
  287. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/naive_bayes/bernoulli.rs +0 -0
  288. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/naive_bayes/gaussian.rs +0 -0
  289. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/naive_bayes/mod.rs +0 -0
  290. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/naive_bayes/multinomial.rs +0 -0
  291. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/neighbors/knn.rs +0 -0
  292. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/neighbors/mod.rs +0 -0
  293. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/preprocessing/encoders.rs +0 -0
  294. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/preprocessing/mod.rs +0 -0
  295. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/preprocessing/scalers.rs +0 -0
  296. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/svm/mod.rs +0 -0
  297. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/svm/svm.rs +0 -0
  298. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/tree/adaboost.rs +0 -0
  299. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/tree/decision_tree.rs +0 -0
  300. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/tree/decision_tree_backup.rs +0 -0
  301. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/tree/gradient_boosting.rs +0 -0
  302. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/tree/mod.rs +0 -0
  303. {seraplot-2.3.73 → seraplot-2.3.74}/src/ml/tree/random_forest.rs +0 -0
  304. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/camera.rs +0 -0
  305. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/canvas.rs +0 -0
  306. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/containers_3d.rs +0 -0
  307. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/controller/chart_controller.rs +0 -0
  308. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/controller/mod.rs +0 -0
  309. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/controller/plot_3d_controller.rs +0 -0
  310. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/default/_3d/bar_3d.rs +0 -0
  311. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/default/_3d/line_3d.rs +0 -0
  312. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/default/_3d/mod.rs +0 -0
  313. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/default/_3d/plot_3d_types.rs +0 -0
  314. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/default/_3d/scatter_3d.rs +0 -0
  315. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/default/bar.rs +0 -0
  316. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/default/chart.rs +0 -0
  317. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/default/kmeans.rs +0 -0
  318. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/default/line.rs +0 -0
  319. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/default/mod.rs +0 -0
  320. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/default/scatter.rs +0 -0
  321. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/default/svg.rs +0 -0
  322. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/generic.rs +0 -0
  323. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/map/_3d/globe.rs +0 -0
  324. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/map/_3d/globe_html.rs +0 -0
  325. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/map/_3d/globe_types.rs +0 -0
  326. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/map/_3d/mod.rs +0 -0
  327. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/map/bubble_map.rs +0 -0
  328. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/map/chart.rs +0 -0
  329. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/map/choropleth.rs +0 -0
  330. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/map/mod.rs +0 -0
  331. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/map/svg_parser.rs +0 -0
  332. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/map/world_data.rs +0 -0
  333. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/mod.rs +0 -0
  334. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/projection.rs +0 -0
  335. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/renderers.rs +0 -0
  336. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/scale_renderer.rs +0 -0
  337. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/seaborn/_3d/mod.rs +0 -0
  338. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/seaborn/_3d/plot_3d_types.rs +0 -0
  339. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/seaborn/chart.rs +0 -0
  340. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/seaborn/mod.rs +0 -0
  341. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/candlestick3d.rs +0 -0
  342. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/dumbbell3d.rs +0 -0
  343. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/funnel3d.rs +0 -0
  344. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/heatmap3d.rs +0 -0
  345. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/kde3d.rs +0 -0
  346. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/lollipop3d.rs +0 -0
  347. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/mod.rs +0 -0
  348. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/pie3d.rs +0 -0
  349. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/plot_3d_types.rs +0 -0
  350. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/radar3d.rs +0 -0
  351. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/ridgeline3d.rs +0 -0
  352. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/stacked_bar3d.rs +0 -0
  353. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/sunburst3d.rs +0 -0
  354. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/_3d/violin3d.rs +0 -0
  355. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/area.rs +0 -0
  356. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/boxplot.rs +0 -0
  357. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/bubble.rs +0 -0
  358. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/bullet.rs +0 -0
  359. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/candlestick.rs +0 -0
  360. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/common.rs +0 -0
  361. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/dumbbell.rs +0 -0
  362. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/funnel.rs +0 -0
  363. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/gauge.rs +0 -0
  364. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/grouped_bar.rs +0 -0
  365. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/heatmap.rs +0 -0
  366. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/histogram.rs +0 -0
  367. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/kde.rs +0 -0
  368. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/lollipop.rs +0 -0
  369. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/mod.rs +0 -0
  370. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/multiline.rs +0 -0
  371. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/parallel.rs +0 -0
  372. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/pie.rs +0 -0
  373. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/radar.rs +0 -0
  374. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/ridgeline.rs +0 -0
  375. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/slope.rs +0 -0
  376. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/sunburst.rs +0 -0
  377. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/treemap.rs +0 -0
  378. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/violin.rs +0 -0
  379. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/waterfall.rs +0 -0
  380. {seraplot-2.3.73 → seraplot-2.3.74}/src/plot/statistical/wordcloud.rs +0 -0
  381. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/cache.rs +0 -0
  382. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/chart.rs +0 -0
  383. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/gui.rs +0 -0
  384. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/hybrid.rs +0 -0
  385. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/manager/button_manager.rs +0 -0
  386. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/manager/mod.rs +0 -0
  387. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/mod.rs +0 -0
  388. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/render/advanced_render.rs +0 -0
  389. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/render/fast_render_gui.rs +0 -0
  390. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/render/mod.rs +0 -0
  391. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/render/pipeline.rs +0 -0
  392. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/render/viewer_3d.rs +0 -0
  393. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/render/wiki_viewer.rs +0 -0
  394. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/utils/image_loader.rs +0 -0
  395. {seraplot-2.3.73 → seraplot-2.3.74}/src/viewer/utils/mod.rs +0 -0
  396. {seraplot-2.3.73 → seraplot-2.3.74}/src/wiki/api.rs +0 -0
  397. {seraplot-2.3.73 → seraplot-2.3.74}/src/wiki/extractor.rs +0 -0
  398. {seraplot-2.3.73 → seraplot-2.3.74}/src/wiki/language.rs +0 -0
  399. {seraplot-2.3.73 → seraplot-2.3.74}/src/wiki/macros.rs +0 -0
  400. {seraplot-2.3.73 → seraplot-2.3.74}/src/wiki/metadata.rs +0 -0
  401. {seraplot-2.3.73 → seraplot-2.3.74}/src/wiki/mod.rs +0 -0
  402. {seraplot-2.3.73 → seraplot-2.3.74}/test_accuracy.py +0 -0
@@ -3471,7 +3471,7 @@ checksum = "8a7852d02fc848982e0c167ef163aaff9cd91dc640ba85e263cb1ce46fae51cd"
3471
3471
 
3472
3472
  [[package]]
3473
3473
  name = "seraplot"
3474
- version = "2.3.73"
3474
+ version = "2.3.74"
3475
3475
  dependencies = [
3476
3476
  "base64 0.22.1",
3477
3477
  "criterion",
@@ -1,6 +1,6 @@
1
1
  [package]
2
2
  name = "seraplot"
3
- version = "2.3.73"
3
+ version = "2.3.74"
4
4
  edition = "2021"
5
5
  authors = ["feur25"]
6
6
  description = "Rust data visualization framework - The modern Plotly alternative"
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: seraplot
3
- Version: 2.3.73
3
+ Version: 2.3.74
4
4
  Classifier: Development Status :: 5 - Production/Stable
5
5
  Classifier: Environment :: Win32 (MS Windows)
6
6
  Classifier: Intended Audience :: Developers
@@ -4,7 +4,7 @@ build-backend = "maturin"
4
4
 
5
5
  [project]
6
6
  name = "seraplot"
7
- version = "2.3.73"
7
+ version = "2.3.74"
8
8
  description = "Rust data visualization framework - The modern Plotly alternative"
9
9
  readme = "README.md"
10
10
  readme-content-type = "text/markdown"
@@ -32,7 +32,7 @@ fn get_global_grid() -> bool {
32
32
  }
33
33
 
34
34
  #[derive(Deserialize, Default)]
35
- pub struct CoreOpts {
35
+ pub struct ChartOpts {
36
36
  pub width: Option<i32>,
37
37
  pub height: Option<i32>,
38
38
  pub x_label: Option<String>,
@@ -98,7 +98,7 @@ pub struct CoreOpts {
98
98
  pub descriptions: Option<Vec<Vec<Vec<String>>>>,
99
99
  }
100
100
 
101
- impl CoreOpts {
101
+ impl ChartOpts {
102
102
  pub fn w(&self, default: i32) -> i32 { self.width.unwrap_or(default) }
103
103
  pub fn h(&self, default: i32) -> i32 { self.height.unwrap_or(default) }
104
104
  pub fn xl(&self) -> String { self.x_label.clone().unwrap_or_default() }
@@ -124,7 +124,7 @@ impl CoreOpts {
124
124
  }
125
125
 
126
126
  #[derive(Deserialize, Default)]
127
- pub struct CoreArgs {
127
+ pub struct ChartArgs {
128
128
  pub labels: Option<Vec<String>>,
129
129
  pub values: Option<Vec<f64>>,
130
130
  pub x: Option<Vec<f64>>,
@@ -156,35 +156,35 @@ pub struct CoreArgs {
156
156
  pub data: Option<Vec<Vec<f64>>>,
157
157
  }
158
158
 
159
- pub fn parse_opts(opts: &str) -> CoreOpts {
159
+ pub fn parse_opts(opts: &str) -> ChartOpts {
160
160
  serde_json::from_str(opts).unwrap_or_default()
161
161
  }
162
162
 
163
- pub fn parse_args(args: &str) -> CoreArgs {
163
+ pub fn parse_args(args: &str) -> ChartArgs {
164
164
  serde_json::from_str(args).unwrap_or_default()
165
165
  }
166
166
 
167
- fn parse_all(input: &str) -> (String, CoreArgs, CoreOpts) {
167
+ fn parse_all(input: &str) -> (String, ChartArgs, ChartOpts) {
168
168
  #[derive(Deserialize, Default)]
169
169
  struct All {
170
170
  #[serde(default)]
171
171
  title: String,
172
172
  #[serde(flatten)]
173
- args: CoreArgs,
173
+ args: ChartArgs,
174
174
  #[serde(flatten)]
175
- opts: CoreOpts,
175
+ opts: ChartOpts,
176
176
  }
177
177
  let all: All = serde_json::from_str(input).unwrap_or_default();
178
178
  (all.title, all.args, all.opts)
179
179
  }
180
180
 
181
- pub fn apply(html: String, o: &CoreOpts) -> String {
181
+ pub fn apply(html: String, o: &ChartOpts) -> String {
182
182
  let bg_str = o.bg_str().or_else(get_global_bg);
183
183
  let bg = bg_str.as_deref();
184
184
  crate::html::hover::apply_opts(html, bg, !o.no_x(), !o.no_y())
185
185
  }
186
186
 
187
- pub fn apply_bg3d(html: String, o: &CoreOpts) -> String {
187
+ pub fn apply_bg3d(html: String, o: &ChartOpts) -> String {
188
188
  let bg_str = o.bg_str().or_else(get_global_bg);
189
189
  if let Some(bg) = bg_str.as_deref() {
190
190
  crate::html::hover::apply_bg(html, Some(bg))
@@ -1297,13 +1297,17 @@ pub fn build_slideshow(input: &str) -> String {
1297
1297
  format!("<div style=\"color:#1e293b;font-family:system-ui;font-size:22px;font-weight:700;text-align:center;margin-bottom:16px\">{}</div>", show_title)
1298
1298
  };
1299
1299
  let n = charts.len();
1300
- let json_array = format!("[{}]", charts.iter()
1301
- .map(|s| serde_json::to_string(s).unwrap_or_else(|_| "\"\"".to_string()))
1302
- .collect::<Vec<_>>().join(","));
1300
+ let mut frames_html = String::new();
1301
+ for (i, html) in charts.iter().enumerate() {
1302
+ let esc = html.replace('&', "&amp;").replace('"', "&quot;");
1303
+ let vis = if i == 0 { "" } else { "display:none;" };
1304
+ frames_html.push_str(&format!(
1305
+ "<iframe id=\"sp-s-{i}\" style=\"{vis}width:{width}px;height:{height}px;border:none;border-radius:12px;overflow:hidden;box-shadow:0 2px 12px rgba(0,0,0,.1)\" srcdoc=\"{esc}\"></iframe>"
1306
+ ));
1307
+ }
1303
1308
  format!(
1304
1309
  "<!DOCTYPE html><html><head><meta charset=\"utf-8\"><style>\
1305
1310
  body{{margin:0;padding:24px;background:#f0f2f5;display:flex;flex-direction:column;align-items:center;font-family:system-ui}}\
1306
- .sp-frm{{border-radius:12px;overflow:hidden;box-shadow:0 2px 12px rgba(0,0,0,.1);background:#fff}}\
1307
1311
  .sp-ctrl{{display:flex;gap:10px;margin-top:14px;align-items:center}}\
1308
1312
  .sp-btn{{cursor:pointer;background:#6366f1;color:#fff;border:none;border-radius:8px;padding:7px 20px;font-size:14px;font-weight:600}}\
1309
1313
  .sp-btn:hover{{background:#4f46e5}}\
@@ -1312,20 +1316,19 @@ pub fn build_slideshow(input: &str) -> String {
1312
1316
  .sp-bar{{height:100%;background:#6366f1;border-radius:2px;width:0%}}\
1313
1317
  </style></head><body>\
1314
1318
  {title_html}\
1315
- <div class=\"sp-frm\" id=\"sp-frm\" style=\"width:{width}px;height:{height}px\"></div>\
1319
+ {frames_html}\
1316
1320
  <div class=\"sp-ctrl\">\
1317
1321
  <button class=\"sp-btn\" id=\"sp-p\">&#9664;</button>\
1318
1322
  <div class=\"sp-ctr\" id=\"sp-c\">1 / {n}</div>\
1319
1323
  <button class=\"sp-btn\" id=\"sp-n\">&#9654;</button>\
1320
1324
  </div>\
1321
1325
  <div class=\"sp-prog\"><div class=\"sp-bar\" id=\"sp-b\"></div></div>\
1322
- <script type=\"application/json\" id=\"sp-d\">{json_array}</script>\
1323
1326
  <script>\
1324
- const frames=JSON.parse(document.getElementById('sp-d').textContent);\
1327
+ const slides=document.querySelectorAll('[id^=\"sp-s-\"]');\
1325
1328
  let idx=0,timer;\
1326
- function show(i){{idx=((i%frames.length)+frames.length)%frames.length;\
1327
- document.getElementById('sp-frm').innerHTML=frames[idx];\
1328
- document.getElementById('sp-c').textContent=(idx+1)+' / '+frames.length;\
1329
+ function show(i){{idx=((i%slides.length)+slides.length)%slides.length;\
1330
+ slides.forEach((s,j)=>{{s.style.display=j===idx?'':'none';}});\
1331
+ document.getElementById('sp-c').textContent=(idx+1)+' / '+slides.length;\
1329
1332
  const b=document.getElementById('sp-b');\
1330
1333
  b.style.transition='none';b.style.width='0%';\
1331
1334
  setTimeout(()=>{{b.style.transition='width {ivms}ms linear';b.style.width='100%';}},20);}}\
@@ -1445,4 +1448,68 @@ pub fn themes(_: &str) -> String {
1445
1448
  "[\"dark\",\"light\",\"scientific\",\"apple\",\"notion\",\"minimal\",\"neon\"]".to_string()
1446
1449
  }
1447
1450
 
1451
+ pub struct DbscanState {
1452
+ pub eps: f64,
1453
+ pub min_samples: usize,
1454
+ pub labels: Vec<i32>,
1455
+ pub n_clusters: usize,
1456
+ pub n_noise: usize,
1457
+ }
1458
+
1459
+ impl DbscanState {
1460
+ pub fn new(eps: f64, min_samples: usize) -> Self {
1461
+ Self { eps, min_samples, labels: Vec::new(), n_clusters: 0, n_noise: 0 }
1462
+ }
1463
+ pub fn fit(&mut self, x: &[Vec<f64>]) {
1464
+ let (labels, n_clusters) = crate::plot::default::scatter::dbscan_core_nd(x, self.eps, self.min_samples);
1465
+ self.n_noise = labels.iter().filter(|&&l| l < 0).count();
1466
+ self.labels = labels;
1467
+ self.n_clusters = n_clusters;
1468
+ }
1469
+ }
1470
+
1471
+ pub struct KMeansState {
1472
+ pub k: usize,
1473
+ pub max_iter: usize,
1474
+ pub tol: f64,
1475
+ pub mini_batch: bool,
1476
+ pub batch_size: usize,
1477
+ pub n_init: usize,
1478
+ pub labels: Vec<i32>,
1479
+ pub centroids: Vec<Vec<f64>>,
1480
+ pub inertia: f64,
1481
+ pub n_iter: usize,
1482
+ }
1448
1483
 
1484
+ impl KMeansState {
1485
+ pub fn new(k: usize, max_iter: usize, tol: f64, mini_batch: bool, batch_size: usize, n_init: usize) -> Self {
1486
+ Self { k, max_iter, tol, mini_batch, batch_size, n_init, labels: Vec::new(), centroids: Vec::new(), inertia: 0.0, n_iter: 0 }
1487
+ }
1488
+ pub fn fit_flat(&mut self, flat: &[f64], n: usize, dims: usize) {
1489
+ if self.mini_batch {
1490
+ let (labels, flat_c, inertia) = crate::plot::default::minibatch_kmeans_core_flat(flat, n, dims, self.k, self.max_iter, self.batch_size);
1491
+ self.labels = labels;
1492
+ self.centroids = (0..self.k.min(n)).map(|ki| flat_c[ki*dims..(ki+1)*dims].to_vec()).collect();
1493
+ self.inertia = inertia;
1494
+ } else {
1495
+ let (labels, flat_c, inertia) = crate::plot::default::kmeans_core_flat_ninit(flat, n, dims, self.k, self.max_iter, self.tol, self.n_init);
1496
+ self.labels = labels;
1497
+ self.centroids = (0..self.k.min(n)).map(|ki| flat_c[ki*dims..(ki+1)*dims].to_vec()).collect();
1498
+ self.inertia = inertia;
1499
+ }
1500
+ self.n_iter = self.max_iter;
1501
+ }
1502
+ pub fn predict_flat(&self, flat: &[f64], n: usize, dims: usize) -> Vec<i32> {
1503
+ (0..n).map(|i| {
1504
+ self.centroids.iter().enumerate()
1505
+ .map(|(ki, c)| (ki, crate::plot::default::kmeans::sq_dist_flat(&flat[i*dims..(i+1)*dims], c)))
1506
+ .min_by(|a, b| a.1.partial_cmp(&b.1).unwrap())
1507
+ .map(|(ki, _)| ki as i32).unwrap_or(0)
1508
+ }).collect()
1509
+ }
1510
+ pub fn transform_flat(&self, flat: &[f64], n: usize, dims: usize) -> Vec<Vec<f64>> {
1511
+ (0..n).map(|i| {
1512
+ self.centroids.iter().map(|c| crate::plot::default::kmeans::sq_dist_flat(&flat[i*dims..(i+1)*dims], c).sqrt()).collect()
1513
+ }).collect()
1514
+ }
1515
+ }
@@ -1,4 +1,4 @@
1
- #[cfg(feature = "js")]
1
+ #[cfg(feature = "js")]
2
2
  use wasm_bindgen::prelude::*;
3
3
 
4
4
  #[cfg(feature = "js")]
@@ -55,35 +55,65 @@ fn chart_auto(name: &str, title: &str, n: usize) -> crate::ml::cache::TaskHandle
55
55
  }
56
56
 
57
57
  #[cfg(feature = "python")]
58
- fn kwargs_to_json(kwargs: Option<&pyo3::types::PyDict>) -> String {
59
- fn v(val: &PyAny) -> serde_json::Value {
60
- if val.is_none() { return serde_json::Value::Null; }
61
- if let Ok(b) = val.extract::<bool>() { return serde_json::Value::Bool(b); }
62
- if let Ok(i) = val.extract::<i64>() { return serde_json::json!(i); }
63
- if let Ok(f) = val.extract::<f64>() { return serde_json::json!(f); }
64
- if let Ok(s) = val.extract::<String>() { return serde_json::Value::String(s); }
65
- if let Ok(list) = val.extract::<Vec<Vec<f64>>>() { return serde_json::json!(list); }
66
- if let Ok(list) = val.extract::<Vec<f64>>() { return serde_json::json!(list); }
67
- if let Ok(list) = val.extract::<Vec<String>>() { return serde_json::json!(list); }
68
- if let Ok(list) = val.extract::<Vec<i64>>() { return serde_json::json!(list); }
69
- serde_json::Value::Null
58
+ fn py_any_val(val: &PyAny) -> serde_json::Value {
59
+ if val.is_none() { return serde_json::Value::Null; }
60
+ if let Ok(b) = val.extract::<bool>() { return serde_json::Value::Bool(b); }
61
+ if let Ok(i) = val.extract::<i64>() { return serde_json::json!(i); }
62
+ if let Ok(f) = val.extract::<f64>() { return serde_json::json!(f); }
63
+ if let Ok(s) = val.extract::<String>() { return serde_json::Value::String(s); }
64
+ if let Ok(list) = val.extract::<Vec<Vec<f64>>>() { return serde_json::json!(list); }
65
+ if let Ok(list) = val.extract::<Vec<f64>>() { return serde_json::json!(list); }
66
+ if let Ok(list) = val.extract::<Vec<String>>() { return serde_json::json!(list); }
67
+ if let Ok(list) = val.extract::<Vec<i64>>() { return serde_json::json!(list); }
68
+ serde_json::Value::Null
69
+ }
70
+
71
+ #[cfg(feature = "python")]
72
+ fn py_args_to_json(
73
+ title: &str,
74
+ labels: Option<&pyo3::types::PyAny>,
75
+ values: Option<&pyo3::types::PyAny>,
76
+ kwargs: Option<&pyo3::types::PyDict>,
77
+ ) -> String {
78
+ let mut m = serde_json::Map::new();
79
+ if !title.is_empty() { m.insert("title".into(), serde_json::json!(title)); }
80
+ if let Some(v) = labels {
81
+ let jv = py_any_val(v);
82
+ if jv != serde_json::Value::Null { m.insert("labels".into(), jv); }
83
+ }
84
+ if let Some(v) = values {
85
+ if let Ok(vv) = v.extract::<Vec<Vec<f64>>>() {
86
+ m.insert("series".into(), serde_json::json!(vv));
87
+ } else {
88
+ let jv = py_any_val(v);
89
+ if jv != serde_json::Value::Null { m.insert("values".into(), jv); }
90
+ }
91
+ }
92
+ if let Some(d) = kwargs {
93
+ for (key, val) in d.iter() {
94
+ if let Ok(ks) = key.str() {
95
+ let ks = ks.to_string_lossy().to_string();
96
+ let v = py_any_val(val);
97
+ if v != serde_json::Value::Null { m.insert(ks, v); }
98
+ }
99
+ }
70
100
  }
71
- let Some(d) = kwargs else { return "{}".to_string() };
72
- serde_json::Value::Object(
73
- d.iter()
74
- .filter_map(|(k, val)| Some((k.str().ok()?.to_string_lossy().to_string(), v(val))))
75
- .collect(),
76
- ).to_string()
101
+ serde_json::Value::Object(m).to_string()
77
102
  }
78
103
 
79
104
  #[cfg(feature = "python")]
80
105
  macro_rules! impl_python {
81
106
  ($fn:ident, $_js:literal) => {
82
107
  #[pyfunction]
83
- #[pyo3(signature = (**kwargs))]
84
- pub fn $fn(kwargs: Option<&pyo3::types::PyDict>) -> PyResult<crate::Chart> {
108
+ #[pyo3(signature = (title="", labels=None, values=None, **kwargs))]
109
+ pub fn $fn(
110
+ title: &str,
111
+ labels: Option<&pyo3::types::PyAny>,
112
+ values: Option<&pyo3::types::PyAny>,
113
+ kwargs: Option<&pyo3::types::PyDict>,
114
+ ) -> PyResult<crate::Chart> {
85
115
  Ok(crate::Chart::new_doc(
86
- crate::bindings::commands::charts::$fn(&kwargs_to_json(kwargs)),
116
+ crate::bindings::commands::charts::$fn(&py_args_to_json(title, labels, values, kwargs)),
87
117
  "",
88
118
  ))
89
119
  }
@@ -179,13 +209,7 @@ pub fn bench_pure_rust(n: usize) -> (f64, f64, f64, f64) {
179
209
 
180
210
  #[cfg(feature = "python")]
181
211
  #[pyclass(module = "seraplot", name = "DBSCAN")]
182
- pub struct DbscanModel {
183
- eps: f64,
184
- min_samples: usize,
185
- labels_: Vec<i32>,
186
- n_clusters_: usize,
187
- n_noise_: usize,
188
- }
212
+ pub struct DbscanModel(crate::bindings::commands::charts::DbscanState);
189
213
 
190
214
  #[cfg(feature = "python")]
191
215
  #[pymethods]
@@ -193,19 +217,16 @@ impl DbscanModel {
193
217
  #[new]
194
218
  #[pyo3(signature = (eps=0.5, min_samples=5))]
195
219
  pub fn py_new(eps: f64, min_samples: usize) -> Self {
196
- DbscanModel { eps, min_samples, labels_: Vec::new(), n_clusters_: 0, n_noise_: 0 }
220
+ DbscanModel(crate::bindings::commands::charts::DbscanState::new(eps, min_samples))
197
221
  }
198
222
 
199
223
  #[pyo3(signature = (x))]
200
224
  pub fn fit(&mut self, x: Vec<Vec<f64>>) -> PyResult<()> {
201
225
  let n = x.len();
202
226
  let d = x.first().map_or(0, |r| r.len());
203
- let fp = crate::ml::cache::Fp::new("DBSCAN.fit").f64(self.eps).usize(self.min_samples).usize(n).usize(d).finish();
227
+ let fp = crate::ml::cache::Fp::new("DBSCAN.fit").f64(self.0.eps).usize(self.0.min_samples).usize(n).usize(d).finish();
204
228
  let _h = crate::ml::cache::TaskHandle::auto("DBSCAN.fit", fp);
205
- let (labels, n_clusters) = crate::plot::default::scatter::dbscan_core_nd(&x, self.eps, self.min_samples);
206
- self.n_noise_ = labels.iter().filter(|&&l| l < 0).count();
207
- self.labels_ = labels;
208
- self.n_clusters_ = n_clusters;
229
+ self.0.fit(&x);
209
230
  _h.complete(&crate::ml::cache::PartialState::default());
210
231
  Ok(())
211
232
  }
@@ -213,33 +234,20 @@ impl DbscanModel {
213
234
  #[pyo3(signature = (x))]
214
235
  pub fn fit_predict(&mut self, x: Vec<Vec<f64>>) -> PyResult<Vec<i32>> {
215
236
  self.fit(x)?;
216
- Ok(self.labels_.clone())
237
+ Ok(self.0.labels.clone())
217
238
  }
218
239
 
219
- #[getter]
220
- pub fn labels_(&self) -> Vec<i32> { self.labels_.clone() }
240
+ #[getter] pub fn labels_(&self) -> Vec<i32> { self.0.labels.clone() }
241
+ #[getter] pub fn n_clusters_(&self) -> usize { self.0.n_clusters }
242
+ #[getter] pub fn n_noise_(&self) -> usize { self.0.n_noise }
243
+ #[getter] pub fn eps(&self) -> f64 { self.0.eps }
244
+ #[getter] pub fn min_samples(&self) -> usize { self.0.min_samples }
221
245
 
222
- #[getter]
223
- pub fn n_clusters_(&self) -> usize { self.n_clusters_ }
224
-
225
- #[getter]
226
- pub fn n_noise_(&self) -> usize { self.n_noise_ }
227
-
228
- #[getter]
229
- pub fn eps(&self) -> f64 { self.eps }
230
-
231
- #[getter]
232
- pub fn min_samples(&self) -> usize { self.min_samples }
233
-
234
- fn doc(&self) -> &'static str {
235
- crate::bindings::commands::docs::DOC_DBSCAN_MODEL
236
- }
246
+ fn doc(&self) -> &'static str { crate::bindings::commands::docs::DOC_DBSCAN_MODEL }
237
247
 
238
248
  fn __repr__(&self) -> String {
239
- format!(
240
- "DBSCAN(eps={}, min_samples={}) -> {} clusters, {} noise",
241
- self.eps, self.min_samples, self.n_clusters_, self.n_noise_
242
- )
249
+ format!("DBSCAN(eps={}, min_samples={}) -> {} clusters, {} noise",
250
+ self.0.eps, self.0.min_samples, self.0.n_clusters, self.0.n_noise)
243
251
  }
244
252
  }
245
253
 
@@ -278,18 +286,7 @@ fn extract_flat(x: &PyAny) -> PyResult<(Vec<f64>, usize, usize)> {
278
286
 
279
287
  #[cfg(feature = "python")]
280
288
  #[pyclass(module = "seraplot", name = "KMeans")]
281
- pub struct KMeansModel {
282
- k: usize,
283
- max_iter: usize,
284
- tol: f64,
285
- mini_batch: bool,
286
- batch_size: usize,
287
- n_init: usize,
288
- labels_: Vec<i32>,
289
- centroids_: Vec<Vec<f64>>,
290
- inertia_: f64,
291
- n_iter_: usize,
292
- }
289
+ pub struct KMeansModel(crate::bindings::commands::charts::KMeansState);
293
290
 
294
291
  #[cfg(feature = "python")]
295
292
  #[pymethods]
@@ -297,27 +294,15 @@ impl KMeansModel {
297
294
  #[new]
298
295
  #[pyo3(signature = (k=3, max_iter=300, tol=1e-4, mini_batch=false, batch_size=1000, n_init=10))]
299
296
  pub fn py_new(k: usize, max_iter: usize, tol: f64, mini_batch: bool, batch_size: usize, n_init: usize) -> Self {
300
- KMeansModel { k, max_iter, tol, mini_batch, batch_size, n_init, labels_: Vec::new(), centroids_: Vec::new(), inertia_: 0.0, n_iter_: 0 }
297
+ KMeansModel(crate::bindings::commands::charts::KMeansState::new(k, max_iter, tol, mini_batch, batch_size, n_init))
301
298
  }
302
299
 
303
300
  #[pyo3(signature = (x))]
304
301
  pub fn fit(&mut self, x: &PyAny) -> PyResult<()> {
305
302
  let (flat, n, dims) = extract_flat(x)?;
306
- let fp = crate::ml::cache::Fp::new("KMeans.fit").usize(self.k).usize(self.max_iter).bval(self.mini_batch).data(&flat, n, dims).finish();
303
+ let fp = crate::ml::cache::Fp::new("KMeans.fit").usize(self.0.k).usize(self.0.max_iter).bval(self.0.mini_batch).data(&flat, n, dims).finish();
307
304
  let _h = crate::ml::cache::TaskHandle::auto("KMeans.fit", fp);
308
- if self.mini_batch {
309
- let (labels, flat_c, inertia) = crate::plot::default::minibatch_kmeans_core_flat(&flat, n, dims, self.k, self.max_iter, self.batch_size);
310
- self.labels_ = labels;
311
- self.centroids_ = (0..self.k.min(n)).map(|ki| flat_c[ki*dims..(ki+1)*dims].to_vec()).collect();
312
- self.inertia_ = inertia;
313
- self.n_iter_ = self.max_iter;
314
- } else {
315
- let (labels, flat_c, inertia) = crate::plot::default::kmeans_core_flat_ninit(&flat, n, dims, self.k, self.max_iter, self.tol, self.n_init);
316
- self.labels_ = labels;
317
- self.centroids_ = (0..self.k.min(n)).map(|ki| flat_c[ki*dims..(ki+1)*dims].to_vec()).collect();
318
- self.inertia_ = inertia;
319
- self.n_iter_ = self.max_iter;
320
- }
305
+ self.0.fit_flat(&flat, n, dims);
321
306
  _h.complete(&crate::ml::cache::PartialState::default());
322
307
  Ok(())
323
308
  }
@@ -325,41 +310,33 @@ impl KMeansModel {
325
310
  #[pyo3(signature = (x))]
326
311
  pub fn fit_predict(&mut self, x: &PyAny) -> PyResult<Vec<i32>> {
327
312
  self.fit(x)?;
328
- Ok(self.labels_.clone())
313
+ Ok(self.0.labels.clone())
329
314
  }
330
315
 
331
316
  #[pyo3(signature = (x))]
332
317
  pub fn transform(&self, x: &PyAny) -> PyResult<Vec<Vec<f64>>> {
333
318
  let (flat, n, dims) = extract_flat(x)?;
334
- Ok((0..n).map(|i| {
335
- self.centroids_.iter().map(|c| crate::plot::default::kmeans::sq_dist_flat(&flat[i*dims..(i+1)*dims], c).sqrt()).collect()
336
- }).collect())
319
+ Ok(self.0.transform_flat(&flat, n, dims))
337
320
  }
338
321
 
339
322
  #[pyo3(signature = (x))]
340
323
  pub fn predict(&self, x: &PyAny) -> PyResult<Vec<i32>> {
341
324
  let (flat, n, dims) = extract_flat(x)?;
342
- Ok((0..n).map(|i| {
343
- self.centroids_.iter().enumerate()
344
- .map(|(ki, c)| (ki, crate::plot::default::kmeans::sq_dist_flat(&flat[i*dims..(i+1)*dims], c)))
345
- .min_by(|a, b| a.1.partial_cmp(&b.1).unwrap())
346
- .map(|(ki, _)| ki as i32).unwrap_or(0)
347
- }).collect())
325
+ Ok(self.0.predict_flat(&flat, n, dims))
348
326
  }
349
327
 
350
- #[getter] pub fn labels_(&self) -> Vec<i32> { self.labels_.clone() }
351
- #[getter] pub fn centroids_(&self) -> Vec<Vec<f64>> { self.centroids_.clone() }
352
- #[getter] pub fn inertia_(&self) -> f64 { self.inertia_ }
353
- #[getter] pub fn n_iter_(&self) -> usize { self.n_iter_ }
354
- #[getter] pub fn n_clusters(&self) -> usize { self.centroids_.len() }
355
- #[getter] pub fn k(&self) -> usize { self.k }
328
+ #[getter] pub fn labels_(&self) -> Vec<i32> { self.0.labels.clone() }
329
+ #[getter] pub fn centroids_(&self) -> Vec<Vec<f64>> { self.0.centroids.clone() }
330
+ #[getter] pub fn inertia_(&self) -> f64 { self.0.inertia }
331
+ #[getter] pub fn n_iter_(&self) -> usize { self.0.n_iter }
332
+ #[getter] pub fn n_clusters(&self) -> usize { self.0.centroids.len() }
333
+ #[getter] pub fn k(&self) -> usize { self.0.k }
356
334
 
357
- fn doc(&self) -> &'static str {
358
- crate::bindings::commands::docs::DOC_KMEANS_MODEL
359
- }
335
+ fn doc(&self) -> &'static str { crate::bindings::commands::docs::DOC_KMEANS_MODEL }
360
336
 
361
337
  fn __repr__(&self) -> String {
362
- format!("KMeans(k={}, max_iter={}, n_init={}, mini_batch={}) -> inertia={:.2}", self.k, self.max_iter, self.n_init, self.mini_batch, self.inertia_)
338
+ format!("KMeans(k={}, max_iter={}, n_init={}, mini_batch={}) -> inertia={:.2}",
339
+ self.0.k, self.0.max_iter, self.0.n_init, self.0.mini_batch, self.0.inertia)
363
340
  }
364
341
  }
365
342
 
@@ -374,27 +351,14 @@ pub fn build_grid(
374
351
  cell_height: i32,
375
352
  ) -> Chart {
376
353
  let _h = chart_auto("build_grid", "", 0);
377
- let bg_color = bg
378
- .map(|s| s.to_string())
379
- .or_else(crate::get_global_background)
380
- .unwrap_or_else(|| "#f0f2f5".to_string());
381
- let cols = cols.max(1);
382
- let mut buf = format!(
383
- "<!DOCTYPE html><html><head><meta charset=\"utf-8\"><style>\
384
- *{{box-sizing:border-box}}body{{margin:0;padding:{gap}px;background:{bg_color}}}\
385
- .spg{{display:grid;grid-template-columns:repeat({cols},1fr);gap:{gap}px}}\
386
- .spg-c iframe{{width:100%;height:{cell_height}px;border:none;display:block;\
387
- border-radius:12px;overflow:hidden;box-shadow:0 2px 8px rgba(0,0,0,.07)}}\
388
- </style></head><body><div class=\"spg\">"
389
- );
390
- for c in charts.iter() {
391
- let esc = c.html.replace('&', "&amp;").replace('"', "&quot;");
392
- buf.push_str("<div class=\"spg-c\"><iframe srcdoc=\"");
393
- buf.push_str(&esc);
394
- buf.push_str("\"></iframe></div>");
395
- }
396
- buf.push_str("</div></body></html>");
397
- Chart::new_doc(buf, crate::bindings::commands::docs::DOC_BUILD_GRID)
354
+ let bg_color = bg.map(|s| s.to_string()).or_else(crate::get_global_background).unwrap_or_else(|| "#f0f2f5".to_string());
355
+ let html_strs: Vec<String> = charts.iter().map(|c| c.html.clone()).collect();
356
+ Chart::new_doc(
357
+ crate::bindings::commands::charts::build_grid(
358
+ &serde_json::json!({"charts": html_strs, "cols": cols, "gap": gap, "background": bg_color, "cell_height": cell_height}).to_string()
359
+ ),
360
+ crate::bindings::commands::docs::DOC_BUILD_GRID,
361
+ )
398
362
  }
399
363
 
400
364
  #[cfg(feature = "python")]
@@ -408,58 +372,13 @@ pub fn build_slideshow(
408
372
  height: i32,
409
373
  ) -> Chart {
410
374
  let _h = chart_auto("build_slideshow", "", 0);
411
- if charts.is_empty() { return Chart::new_doc(String::new(), crate::bindings::commands::docs::DOC_BUILD_SLIDESHOW); }
412
- let svgs: Vec<String> = charts.iter().map(|c| {
413
- let h = &c.html;
414
- let start = h.find("<svg").unwrap_or(0);
415
- let end = h.rfind("</svg>").map(|i| i + 6).unwrap_or(h.len());
416
- if start < end { h[start..end].to_string() }
417
- else { "<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"100\" height=\"100\"></svg>".to_string() }
418
- }).collect();
419
- let json_array = format!("[{}]", svgs.iter()
420
- .map(|s| serde_json::to_string(s).unwrap_or_else(|_| "\"\"".to_string()))
421
- .collect::<Vec<_>>().join(","));
422
- let n = charts.len();
423
- let ivms = interval_ms;
424
- let title_html = if title.is_empty() { String::new() } else {
425
- format!("<div style=\"color:#1e293b;font-family:system-ui;font-size:22px;font-weight:700;text-align:center;margin-bottom:16px\">{}</div>", title)
426
- };
427
- Chart::new_doc(format!(
428
- "<!DOCTYPE html><html><head><meta charset=\"utf-8\"><style>\
429
- body{{margin:0;padding:24px;background:#f0f2f5;display:flex;flex-direction:column;align-items:center;font-family:system-ui}}\
430
- .sp-frm{{border-radius:12px;overflow:hidden;box-shadow:0 2px 12px rgba(0,0,0,.1);background:#fff}}\
431
- .sp-frm svg{{width:{width}px;height:{height}px;display:block}}\
432
- .sp-ctrl{{display:flex;gap:10px;margin-top:14px;align-items:center}}\
433
- .sp-btn{{cursor:pointer;background:#6366f1;color:#fff;border:none;border-radius:8px;padding:7px 20px;font-size:14px;font-weight:600}}\
434
- .sp-btn:hover{{background:#4f46e5}}\
435
- .sp-ctr{{color:#64748b;font-size:13px;min-width:64px;text-align:center}}\
436
- .sp-prog{{width:{width}px;height:4px;background:#e2e8f0;border-radius:2px;margin-top:10px;overflow:hidden}}\
437
- .sp-bar{{height:100%;background:#6366f1;border-radius:2px;width:0%}}\
438
- </style></head><body>\
439
- {title_html}\
440
- <div class=\"sp-frm\" id=\"sp-frm\"></div>\
441
- <div class=\"sp-ctrl\">\
442
- <button class=\"sp-btn\" id=\"sp-p\">&#9664;</button>\
443
- <div class=\"sp-ctr\" id=\"sp-c\">1 / {n}</div>\
444
- <button class=\"sp-btn\" id=\"sp-n\">&#9654;</button>\
445
- </div>\
446
- <div class=\"sp-prog\"><div class=\"sp-bar\" id=\"sp-b\"></div></div>\
447
- <script type=\"application/json\" id=\"sp-d\">{json_array}</script>\
448
- <script>\
449
- const frames=JSON.parse(document.getElementById('sp-d').textContent);\
450
- let idx=0,timer;\
451
- function show(i){{idx=((i%frames.length)+frames.length)%frames.length;\
452
- document.getElementById('sp-frm').innerHTML=frames[idx];\
453
- document.getElementById('sp-c').textContent=(idx+1)+' / '+frames.length;\
454
- const b=document.getElementById('sp-b');\
455
- b.style.transition='none';b.style.width='0%';\
456
- setTimeout(()=>{{b.style.transition='width {ivms}ms linear';b.style.width='100%';}},20);}}\
457
- function play(){{clearInterval(timer);timer=setInterval(()=>{{show(idx+1);}},{ivms});}}\
458
- show(0);play();\
459
- document.getElementById('sp-p').onclick=()=>{{clearInterval(timer);show(idx-1);play();}};\
460
- document.getElementById('sp-n').onclick=()=>{{clearInterval(timer);show(idx+1);play();}};\
461
- </script></body></html>"
462
- ), crate::bindings::commands::docs::DOC_BUILD_SLIDESHOW)
375
+ let html_strs: Vec<String> = charts.iter().map(|c| c.html.clone()).collect();
376
+ Chart::new_doc(
377
+ crate::bindings::commands::charts::build_slideshow(
378
+ &serde_json::json!({"charts": html_strs, "interval_ms": interval_ms, "title": title, "width": width, "height": height}).to_string()
379
+ ),
380
+ crate::bindings::commands::docs::DOC_BUILD_SLIDESHOW,
381
+ )
463
382
  }
464
383
 
465
384
  #[cfg(feature = "python")]
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes