setiastrosuitepro 1.6.7__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of setiastrosuitepro might be problematic. Click here for more details.

Files changed (394) hide show
  1. setiastro/__init__.py +2 -0
  2. setiastro/data/SASP_data.fits +0 -0
  3. setiastro/data/catalogs/List_of_Galaxies_with_Distances_Gly.csv +488 -0
  4. setiastro/data/catalogs/astrobin_filters.csv +890 -0
  5. setiastro/data/catalogs/astrobin_filters_page1_local.csv +51 -0
  6. setiastro/data/catalogs/cali2.csv +63 -0
  7. setiastro/data/catalogs/cali2color.csv +65 -0
  8. setiastro/data/catalogs/celestial_catalog - original.csv +16471 -0
  9. setiastro/data/catalogs/celestial_catalog.csv +24031 -0
  10. setiastro/data/catalogs/detected_stars.csv +24784 -0
  11. setiastro/data/catalogs/fits_header_data.csv +46 -0
  12. setiastro/data/catalogs/test.csv +8 -0
  13. setiastro/data/catalogs/updated_celestial_catalog.csv +16471 -0
  14. setiastro/images/Astro_Spikes.png +0 -0
  15. setiastro/images/Background_startup.jpg +0 -0
  16. setiastro/images/HRDiagram.png +0 -0
  17. setiastro/images/LExtract.png +0 -0
  18. setiastro/images/LInsert.png +0 -0
  19. setiastro/images/Oxygenation-atm-2.svg.png +0 -0
  20. setiastro/images/RGB080604.png +0 -0
  21. setiastro/images/abeicon.png +0 -0
  22. setiastro/images/aberration.png +0 -0
  23. setiastro/images/acv_icon.png +0 -0
  24. setiastro/images/andromedatry.png +0 -0
  25. setiastro/images/andromedatry_satellited.png +0 -0
  26. setiastro/images/annotated.png +0 -0
  27. setiastro/images/aperture.png +0 -0
  28. setiastro/images/astrosuite.ico +0 -0
  29. setiastro/images/astrosuite.png +0 -0
  30. setiastro/images/astrosuitepro.icns +0 -0
  31. setiastro/images/astrosuitepro.ico +0 -0
  32. setiastro/images/astrosuitepro.png +0 -0
  33. setiastro/images/background.png +0 -0
  34. setiastro/images/background2.png +0 -0
  35. setiastro/images/benchmark.png +0 -0
  36. setiastro/images/big_moon_stabilizer_timeline.png +0 -0
  37. setiastro/images/big_moon_stabilizer_timeline_clean.png +0 -0
  38. setiastro/images/blaster.png +0 -0
  39. setiastro/images/blink.png +0 -0
  40. setiastro/images/clahe.png +0 -0
  41. setiastro/images/collage.png +0 -0
  42. setiastro/images/colorwheel.png +0 -0
  43. setiastro/images/contsub.png +0 -0
  44. setiastro/images/convo.png +0 -0
  45. setiastro/images/copyslot.png +0 -0
  46. setiastro/images/cosmic.png +0 -0
  47. setiastro/images/cosmicsat.png +0 -0
  48. setiastro/images/crop1.png +0 -0
  49. setiastro/images/cropicon.png +0 -0
  50. setiastro/images/curves.png +0 -0
  51. setiastro/images/cvs.png +0 -0
  52. setiastro/images/debayer.png +0 -0
  53. setiastro/images/denoise_cnn_custom.png +0 -0
  54. setiastro/images/denoise_cnn_graph.png +0 -0
  55. setiastro/images/disk.png +0 -0
  56. setiastro/images/dse.png +0 -0
  57. setiastro/images/exoicon.png +0 -0
  58. setiastro/images/eye.png +0 -0
  59. setiastro/images/first_quarter.png +0 -0
  60. setiastro/images/fliphorizontal.png +0 -0
  61. setiastro/images/flipvertical.png +0 -0
  62. setiastro/images/font.png +0 -0
  63. setiastro/images/freqsep.png +0 -0
  64. setiastro/images/full_moon.png +0 -0
  65. setiastro/images/functionbundle.png +0 -0
  66. setiastro/images/graxpert.png +0 -0
  67. setiastro/images/green.png +0 -0
  68. setiastro/images/gridicon.png +0 -0
  69. setiastro/images/halo.png +0 -0
  70. setiastro/images/hdr.png +0 -0
  71. setiastro/images/histogram.png +0 -0
  72. setiastro/images/hubble.png +0 -0
  73. setiastro/images/imagecombine.png +0 -0
  74. setiastro/images/invert.png +0 -0
  75. setiastro/images/isophote.png +0 -0
  76. setiastro/images/isophote_demo_figure.png +0 -0
  77. setiastro/images/isophote_demo_image.png +0 -0
  78. setiastro/images/isophote_demo_model.png +0 -0
  79. setiastro/images/isophote_demo_residual.png +0 -0
  80. setiastro/images/jwstpupil.png +0 -0
  81. setiastro/images/last_quarter.png +0 -0
  82. setiastro/images/linearfit.png +0 -0
  83. setiastro/images/livestacking.png +0 -0
  84. setiastro/images/mask.png +0 -0
  85. setiastro/images/maskapply.png +0 -0
  86. setiastro/images/maskcreate.png +0 -0
  87. setiastro/images/maskremove.png +0 -0
  88. setiastro/images/morpho.png +0 -0
  89. setiastro/images/mosaic.png +0 -0
  90. setiastro/images/multiscale_decomp.png +0 -0
  91. setiastro/images/nbtorgb.png +0 -0
  92. setiastro/images/neutral.png +0 -0
  93. setiastro/images/new_moon.png +0 -0
  94. setiastro/images/nuke.png +0 -0
  95. setiastro/images/openfile.png +0 -0
  96. setiastro/images/pedestal.png +0 -0
  97. setiastro/images/pen.png +0 -0
  98. setiastro/images/pixelmath.png +0 -0
  99. setiastro/images/platesolve.png +0 -0
  100. setiastro/images/ppp.png +0 -0
  101. setiastro/images/pro.png +0 -0
  102. setiastro/images/project.png +0 -0
  103. setiastro/images/psf.png +0 -0
  104. setiastro/images/redo.png +0 -0
  105. setiastro/images/redoicon.png +0 -0
  106. setiastro/images/rescale.png +0 -0
  107. setiastro/images/rgbalign.png +0 -0
  108. setiastro/images/rgbcombo.png +0 -0
  109. setiastro/images/rgbextract.png +0 -0
  110. setiastro/images/rotate180.png +0 -0
  111. setiastro/images/rotatearbitrary.png +0 -0
  112. setiastro/images/rotateclockwise.png +0 -0
  113. setiastro/images/rotatecounterclockwise.png +0 -0
  114. setiastro/images/satellite.png +0 -0
  115. setiastro/images/script.png +0 -0
  116. setiastro/images/selectivecolor.png +0 -0
  117. setiastro/images/simbad.png +0 -0
  118. setiastro/images/slot0.png +0 -0
  119. setiastro/images/slot1.png +0 -0
  120. setiastro/images/slot2.png +0 -0
  121. setiastro/images/slot3.png +0 -0
  122. setiastro/images/slot4.png +0 -0
  123. setiastro/images/slot5.png +0 -0
  124. setiastro/images/slot6.png +0 -0
  125. setiastro/images/slot7.png +0 -0
  126. setiastro/images/slot8.png +0 -0
  127. setiastro/images/slot9.png +0 -0
  128. setiastro/images/spcc.png +0 -0
  129. setiastro/images/spin_precession_vs_lunar_distance.png +0 -0
  130. setiastro/images/spinner.gif +0 -0
  131. setiastro/images/stacking.png +0 -0
  132. setiastro/images/staradd.png +0 -0
  133. setiastro/images/staralign.png +0 -0
  134. setiastro/images/starnet.png +0 -0
  135. setiastro/images/starregistration.png +0 -0
  136. setiastro/images/starspike.png +0 -0
  137. setiastro/images/starstretch.png +0 -0
  138. setiastro/images/statstretch.png +0 -0
  139. setiastro/images/supernova.png +0 -0
  140. setiastro/images/uhs.png +0 -0
  141. setiastro/images/undoicon.png +0 -0
  142. setiastro/images/upscale.png +0 -0
  143. setiastro/images/viewbundle.png +0 -0
  144. setiastro/images/waning_crescent_1.png +0 -0
  145. setiastro/images/waning_crescent_2.png +0 -0
  146. setiastro/images/waning_crescent_3.png +0 -0
  147. setiastro/images/waning_crescent_4.png +0 -0
  148. setiastro/images/waning_crescent_5.png +0 -0
  149. setiastro/images/waning_gibbous_1.png +0 -0
  150. setiastro/images/waning_gibbous_2.png +0 -0
  151. setiastro/images/waning_gibbous_3.png +0 -0
  152. setiastro/images/waning_gibbous_4.png +0 -0
  153. setiastro/images/waning_gibbous_5.png +0 -0
  154. setiastro/images/waxing_crescent_1.png +0 -0
  155. setiastro/images/waxing_crescent_2.png +0 -0
  156. setiastro/images/waxing_crescent_3.png +0 -0
  157. setiastro/images/waxing_crescent_4.png +0 -0
  158. setiastro/images/waxing_crescent_5.png +0 -0
  159. setiastro/images/waxing_gibbous_1.png +0 -0
  160. setiastro/images/waxing_gibbous_2.png +0 -0
  161. setiastro/images/waxing_gibbous_3.png +0 -0
  162. setiastro/images/waxing_gibbous_4.png +0 -0
  163. setiastro/images/waxing_gibbous_5.png +0 -0
  164. setiastro/images/whitebalance.png +0 -0
  165. setiastro/images/wimi_icon_256x256.png +0 -0
  166. setiastro/images/wimilogo.png +0 -0
  167. setiastro/images/wims.png +0 -0
  168. setiastro/images/wrench_icon.png +0 -0
  169. setiastro/images/xisfliberator.png +0 -0
  170. setiastro/qml/ResourceMonitor.qml +128 -0
  171. setiastro/saspro/__init__.py +20 -0
  172. setiastro/saspro/__main__.py +964 -0
  173. setiastro/saspro/_generated/__init__.py +7 -0
  174. setiastro/saspro/_generated/build_info.py +3 -0
  175. setiastro/saspro/abe.py +1379 -0
  176. setiastro/saspro/abe_preset.py +196 -0
  177. setiastro/saspro/aberration_ai.py +910 -0
  178. setiastro/saspro/aberration_ai_preset.py +224 -0
  179. setiastro/saspro/accel_installer.py +218 -0
  180. setiastro/saspro/accel_workers.py +30 -0
  181. setiastro/saspro/acv_exporter.py +379 -0
  182. setiastro/saspro/add_stars.py +627 -0
  183. setiastro/saspro/astrobin_exporter.py +1010 -0
  184. setiastro/saspro/astrospike.py +153 -0
  185. setiastro/saspro/astrospike_python.py +1841 -0
  186. setiastro/saspro/autostretch.py +198 -0
  187. setiastro/saspro/backgroundneutral.py +639 -0
  188. setiastro/saspro/batch_convert.py +328 -0
  189. setiastro/saspro/batch_renamer.py +522 -0
  190. setiastro/saspro/blemish_blaster.py +494 -0
  191. setiastro/saspro/blink_comparator_pro.py +3149 -0
  192. setiastro/saspro/bundles.py +61 -0
  193. setiastro/saspro/bundles_dock.py +114 -0
  194. setiastro/saspro/cheat_sheet.py +213 -0
  195. setiastro/saspro/clahe.py +371 -0
  196. setiastro/saspro/comet_stacking.py +1442 -0
  197. setiastro/saspro/common_tr.py +107 -0
  198. setiastro/saspro/config.py +38 -0
  199. setiastro/saspro/config_bootstrap.py +40 -0
  200. setiastro/saspro/config_manager.py +316 -0
  201. setiastro/saspro/continuum_subtract.py +1620 -0
  202. setiastro/saspro/convo.py +1403 -0
  203. setiastro/saspro/convo_preset.py +414 -0
  204. setiastro/saspro/copyastro.py +190 -0
  205. setiastro/saspro/cosmicclarity.py +1593 -0
  206. setiastro/saspro/cosmicclarity_preset.py +407 -0
  207. setiastro/saspro/crop_dialog_pro.py +1005 -0
  208. setiastro/saspro/crop_preset.py +189 -0
  209. setiastro/saspro/curve_editor_pro.py +2608 -0
  210. setiastro/saspro/curves_preset.py +375 -0
  211. setiastro/saspro/debayer.py +673 -0
  212. setiastro/saspro/debug_utils.py +29 -0
  213. setiastro/saspro/dnd_mime.py +35 -0
  214. setiastro/saspro/doc_manager.py +2727 -0
  215. setiastro/saspro/exoplanet_detector.py +2258 -0
  216. setiastro/saspro/file_utils.py +284 -0
  217. setiastro/saspro/fitsmodifier.py +748 -0
  218. setiastro/saspro/fix_bom.py +32 -0
  219. setiastro/saspro/free_torch_memory.py +48 -0
  220. setiastro/saspro/frequency_separation.py +1352 -0
  221. setiastro/saspro/function_bundle.py +1596 -0
  222. setiastro/saspro/generate_translations.py +3092 -0
  223. setiastro/saspro/ghs_dialog_pro.py +728 -0
  224. setiastro/saspro/ghs_preset.py +284 -0
  225. setiastro/saspro/graxpert.py +638 -0
  226. setiastro/saspro/graxpert_preset.py +287 -0
  227. setiastro/saspro/gui/__init__.py +0 -0
  228. setiastro/saspro/gui/main_window.py +8928 -0
  229. setiastro/saspro/gui/mixins/__init__.py +33 -0
  230. setiastro/saspro/gui/mixins/dock_mixin.py +375 -0
  231. setiastro/saspro/gui/mixins/file_mixin.py +450 -0
  232. setiastro/saspro/gui/mixins/geometry_mixin.py +503 -0
  233. setiastro/saspro/gui/mixins/header_mixin.py +441 -0
  234. setiastro/saspro/gui/mixins/mask_mixin.py +421 -0
  235. setiastro/saspro/gui/mixins/menu_mixin.py +391 -0
  236. setiastro/saspro/gui/mixins/theme_mixin.py +367 -0
  237. setiastro/saspro/gui/mixins/toolbar_mixin.py +1824 -0
  238. setiastro/saspro/gui/mixins/update_mixin.py +323 -0
  239. setiastro/saspro/gui/mixins/view_mixin.py +477 -0
  240. setiastro/saspro/gui/statistics_dialog.py +47 -0
  241. setiastro/saspro/halobgon.py +492 -0
  242. setiastro/saspro/header_viewer.py +448 -0
  243. setiastro/saspro/headless_utils.py +88 -0
  244. setiastro/saspro/histogram.py +760 -0
  245. setiastro/saspro/history_explorer.py +941 -0
  246. setiastro/saspro/i18n.py +168 -0
  247. setiastro/saspro/image_combine.py +421 -0
  248. setiastro/saspro/image_peeker_pro.py +1608 -0
  249. setiastro/saspro/imageops/__init__.py +37 -0
  250. setiastro/saspro/imageops/mdi_snap.py +292 -0
  251. setiastro/saspro/imageops/scnr.py +36 -0
  252. setiastro/saspro/imageops/starbasedwhitebalance.py +210 -0
  253. setiastro/saspro/imageops/stretch.py +236 -0
  254. setiastro/saspro/isophote.py +1186 -0
  255. setiastro/saspro/layers.py +208 -0
  256. setiastro/saspro/layers_dock.py +714 -0
  257. setiastro/saspro/lazy_imports.py +193 -0
  258. setiastro/saspro/legacy/__init__.py +2 -0
  259. setiastro/saspro/legacy/image_manager.py +2360 -0
  260. setiastro/saspro/legacy/numba_utils.py +3676 -0
  261. setiastro/saspro/legacy/xisf.py +1213 -0
  262. setiastro/saspro/linear_fit.py +537 -0
  263. setiastro/saspro/live_stacking.py +1854 -0
  264. setiastro/saspro/log_bus.py +5 -0
  265. setiastro/saspro/logging_config.py +460 -0
  266. setiastro/saspro/luminancerecombine.py +510 -0
  267. setiastro/saspro/main_helpers.py +201 -0
  268. setiastro/saspro/mask_creation.py +1090 -0
  269. setiastro/saspro/masks_core.py +56 -0
  270. setiastro/saspro/mdi_widgets.py +353 -0
  271. setiastro/saspro/memory_utils.py +666 -0
  272. setiastro/saspro/metadata_patcher.py +75 -0
  273. setiastro/saspro/mfdeconv.py +3909 -0
  274. setiastro/saspro/mfdeconv_earlystop.py +71 -0
  275. setiastro/saspro/mfdeconvcudnn.py +3312 -0
  276. setiastro/saspro/mfdeconvsport.py +2459 -0
  277. setiastro/saspro/minorbodycatalog.py +567 -0
  278. setiastro/saspro/morphology.py +411 -0
  279. setiastro/saspro/multiscale_decomp.py +1751 -0
  280. setiastro/saspro/nbtorgb_stars.py +541 -0
  281. setiastro/saspro/numba_utils.py +3145 -0
  282. setiastro/saspro/numba_warmup.py +141 -0
  283. setiastro/saspro/ops/__init__.py +9 -0
  284. setiastro/saspro/ops/command_help_dialog.py +623 -0
  285. setiastro/saspro/ops/command_runner.py +217 -0
  286. setiastro/saspro/ops/commands.py +1594 -0
  287. setiastro/saspro/ops/script_editor.py +1105 -0
  288. setiastro/saspro/ops/scripts.py +1476 -0
  289. setiastro/saspro/ops/settings.py +637 -0
  290. setiastro/saspro/parallel_utils.py +554 -0
  291. setiastro/saspro/pedestal.py +121 -0
  292. setiastro/saspro/perfect_palette_picker.py +1105 -0
  293. setiastro/saspro/pipeline.py +110 -0
  294. setiastro/saspro/pixelmath.py +1604 -0
  295. setiastro/saspro/plate_solver.py +2480 -0
  296. setiastro/saspro/project_io.py +797 -0
  297. setiastro/saspro/psf_utils.py +136 -0
  298. setiastro/saspro/psf_viewer.py +631 -0
  299. setiastro/saspro/pyi_rthook_astroquery.py +95 -0
  300. setiastro/saspro/remove_green.py +331 -0
  301. setiastro/saspro/remove_stars.py +1599 -0
  302. setiastro/saspro/remove_stars_preset.py +446 -0
  303. setiastro/saspro/resources.py +570 -0
  304. setiastro/saspro/rgb_combination.py +208 -0
  305. setiastro/saspro/rgb_extract.py +19 -0
  306. setiastro/saspro/rgbalign.py +727 -0
  307. setiastro/saspro/runtime_imports.py +7 -0
  308. setiastro/saspro/runtime_torch.py +754 -0
  309. setiastro/saspro/save_options.py +73 -0
  310. setiastro/saspro/selective_color.py +1614 -0
  311. setiastro/saspro/sfcc.py +1530 -0
  312. setiastro/saspro/shortcuts.py +3125 -0
  313. setiastro/saspro/signature_insert.py +1106 -0
  314. setiastro/saspro/stacking_suite.py +19069 -0
  315. setiastro/saspro/star_alignment.py +7383 -0
  316. setiastro/saspro/star_alignment_preset.py +329 -0
  317. setiastro/saspro/star_metrics.py +49 -0
  318. setiastro/saspro/star_spikes.py +769 -0
  319. setiastro/saspro/star_stretch.py +542 -0
  320. setiastro/saspro/stat_stretch.py +554 -0
  321. setiastro/saspro/status_log_dock.py +78 -0
  322. setiastro/saspro/subwindow.py +3523 -0
  323. setiastro/saspro/supernovaasteroidhunter.py +1719 -0
  324. setiastro/saspro/swap_manager.py +134 -0
  325. setiastro/saspro/torch_backend.py +89 -0
  326. setiastro/saspro/torch_rejection.py +434 -0
  327. setiastro/saspro/translations/all_source_strings.json +4726 -0
  328. setiastro/saspro/translations/ar_translations.py +4096 -0
  329. setiastro/saspro/translations/de_translations.py +3728 -0
  330. setiastro/saspro/translations/es_translations.py +4169 -0
  331. setiastro/saspro/translations/fr_translations.py +4090 -0
  332. setiastro/saspro/translations/hi_translations.py +3803 -0
  333. setiastro/saspro/translations/integrate_translations.py +271 -0
  334. setiastro/saspro/translations/it_translations.py +4728 -0
  335. setiastro/saspro/translations/ja_translations.py +3834 -0
  336. setiastro/saspro/translations/pt_translations.py +3847 -0
  337. setiastro/saspro/translations/ru_translations.py +3082 -0
  338. setiastro/saspro/translations/saspro_ar.qm +0 -0
  339. setiastro/saspro/translations/saspro_ar.ts +16019 -0
  340. setiastro/saspro/translations/saspro_de.qm +0 -0
  341. setiastro/saspro/translations/saspro_de.ts +14548 -0
  342. setiastro/saspro/translations/saspro_es.qm +0 -0
  343. setiastro/saspro/translations/saspro_es.ts +16202 -0
  344. setiastro/saspro/translations/saspro_fr.qm +0 -0
  345. setiastro/saspro/translations/saspro_fr.ts +15870 -0
  346. setiastro/saspro/translations/saspro_hi.qm +0 -0
  347. setiastro/saspro/translations/saspro_hi.ts +14855 -0
  348. setiastro/saspro/translations/saspro_it.qm +0 -0
  349. setiastro/saspro/translations/saspro_it.ts +19046 -0
  350. setiastro/saspro/translations/saspro_ja.qm +0 -0
  351. setiastro/saspro/translations/saspro_ja.ts +14980 -0
  352. setiastro/saspro/translations/saspro_pt.qm +0 -0
  353. setiastro/saspro/translations/saspro_pt.ts +15024 -0
  354. setiastro/saspro/translations/saspro_ru.qm +0 -0
  355. setiastro/saspro/translations/saspro_ru.ts +11835 -0
  356. setiastro/saspro/translations/saspro_sw.qm +0 -0
  357. setiastro/saspro/translations/saspro_sw.ts +15237 -0
  358. setiastro/saspro/translations/saspro_uk.qm +0 -0
  359. setiastro/saspro/translations/saspro_uk.ts +15248 -0
  360. setiastro/saspro/translations/saspro_zh.qm +0 -0
  361. setiastro/saspro/translations/saspro_zh.ts +15289 -0
  362. setiastro/saspro/translations/sw_translations.py +3897 -0
  363. setiastro/saspro/translations/uk_translations.py +3929 -0
  364. setiastro/saspro/translations/zh_translations.py +3910 -0
  365. setiastro/saspro/versioning.py +77 -0
  366. setiastro/saspro/view_bundle.py +1558 -0
  367. setiastro/saspro/wavescale_hdr.py +648 -0
  368. setiastro/saspro/wavescale_hdr_preset.py +101 -0
  369. setiastro/saspro/wavescalede.py +683 -0
  370. setiastro/saspro/wavescalede_preset.py +230 -0
  371. setiastro/saspro/wcs_update.py +374 -0
  372. setiastro/saspro/whitebalance.py +540 -0
  373. setiastro/saspro/widgets/__init__.py +48 -0
  374. setiastro/saspro/widgets/common_utilities.py +306 -0
  375. setiastro/saspro/widgets/graphics_views.py +122 -0
  376. setiastro/saspro/widgets/image_utils.py +518 -0
  377. setiastro/saspro/widgets/minigame/game.js +991 -0
  378. setiastro/saspro/widgets/minigame/index.html +53 -0
  379. setiastro/saspro/widgets/minigame/style.css +241 -0
  380. setiastro/saspro/widgets/preview_dialogs.py +280 -0
  381. setiastro/saspro/widgets/resource_monitor.py +313 -0
  382. setiastro/saspro/widgets/spinboxes.py +290 -0
  383. setiastro/saspro/widgets/themed_buttons.py +13 -0
  384. setiastro/saspro/widgets/wavelet_utils.py +331 -0
  385. setiastro/saspro/wimi.py +7367 -0
  386. setiastro/saspro/wims.py +588 -0
  387. setiastro/saspro/window_shelf.py +185 -0
  388. setiastro/saspro/xisf.py +1213 -0
  389. setiastrosuitepro-1.6.7.dist-info/METADATA +279 -0
  390. setiastrosuitepro-1.6.7.dist-info/RECORD +394 -0
  391. setiastrosuitepro-1.6.7.dist-info/WHEEL +4 -0
  392. setiastrosuitepro-1.6.7.dist-info/entry_points.txt +6 -0
  393. setiastrosuitepro-1.6.7.dist-info/licenses/LICENSE +674 -0
  394. setiastrosuitepro-1.6.7.dist-info/licenses/license.txt +2580 -0
@@ -0,0 +1,375 @@
1
+ # pro/curves_preset.py
2
+ from __future__ import annotations
3
+ from typing import List, Tuple, Dict
4
+ import numpy as np
5
+ import json
6
+ from PyQt6.QtCore import QSettings
7
+ # optional PCHIP (same as editor)
8
+ try:
9
+ from scipy.interpolate import PchipInterpolator as _PCHIP
10
+ _HAS_PCHIP = True
11
+ except Exception:
12
+ _HAS_PCHIP = False
13
+
14
+
15
+
16
+ # ---------------------- preset schema ----------------------
17
+ # {
18
+ # "mode": "K (Brightness)" | "R" | "G" | "B" | "L*" | "a*" | "b*" | "Chroma" | "Saturation" | aliases ("rgb","k","lum"…),
19
+ # "shape": "linear" | "s_mild" | "s_med" | "s_strong" | "lift_shadows" | "crush_shadows"
20
+ # | "fade_blacks" | "rolloff_highlights" | "flatten" | "custom",
21
+ # "amount": 0..1 (intensity, ignored for custom),
22
+ # "points_norm": [[x,y], ...] # optional when shape="custom" (normalized 0..1 domain/range)
23
+ # }
24
+ #
25
+ # Default if missing: mode="K (Brightness)", shape="linear", amount=0.5
26
+
27
+ # ---------------------- shape library (normalized) ----------------------
28
+ def _shape_points_norm(shape: str, amount: float) -> List[Tuple[float, float]]:
29
+ a = float(max(0.0, min(1.0, amount)))
30
+ s = shape.lower()
31
+
32
+ # identity
33
+ if s in ("linear", "none", "id"):
34
+ return [(0.0, 0.0), (1.0, 1.0)]
35
+
36
+ # simple parametric S-curves (mid anchored)
37
+ if s in ("s", "s_mild", "s-curve-mild"):
38
+ k = 0.15 * a
39
+ return [(0.0, 0.0), (0.25, max(0.0, 0.25 - k)), (0.5, 0.5), (0.75, min(1.0, 0.75 + k)), (1.0, 1.0)]
40
+ if s in ("s_med", "s-curve-med", "s-curve"):
41
+ k = 0.25 * a
42
+ return [(0.0, 0.0), (0.25, max(0.0, 0.25 - k)), (0.5, 0.5), (0.75, min(1.0, 0.75 + k)), (1.0, 1.0)]
43
+ if s in ("s_strong", "s-curve-strong"):
44
+ k = 0.36 * a
45
+ return [(0.0, 0.0), (0.25, max(0.0, 0.25 - k)), (0.5, 0.5), (0.75, min(1.0, 0.75 + k)), (1.0, 1.0)]
46
+
47
+ # lift/crush shadows, fade blacks, highlight roll-off, flatten
48
+ if s == "lift_shadows":
49
+ k = 0.35 * a
50
+ return [(0.0, k), (0.3, k + 0.25*a), (1.0, 1.0)]
51
+ if s == "crush_shadows":
52
+ k = 0.35 * a
53
+ return [(0.0, 0.0), (0.3, max(0.0, 0.3 - k)), (1.0, 1.0)]
54
+ if s == "fade_blacks":
55
+ k = 0.25 * a
56
+ return [(0.0, k), (0.2, k*0.8), (0.6, 0.6 + 0.15*a), (1.0, 1.0)]
57
+ if s == "rolloff_highlights":
58
+ k = 0.35 * a
59
+ return [(0.0, 0.0), (0.6, 0.6 + 0.15*a), (1.0, 1.0 - k)]
60
+ if s == "flatten":
61
+ k = 0.40 * a
62
+ return [(0.0, 0.0 + 0.25*k), (0.25, 0.35), (0.5, 0.5), (0.75, 0.65), (1.0, 1.0 - 0.25*k)]
63
+
64
+ # default
65
+ return [(0.0, 0.0), (1.0, 1.0)]
66
+
67
+ def _norm_mode(m: str | None) -> str:
68
+ m = (m or "K (Brightness)").strip().lower()
69
+ alias = {
70
+ "k": "K (Brightness)",
71
+ "brightness": "K (Brightness)",
72
+ "rgb": "K (Brightness)",
73
+ "lum": "L*",
74
+ "l": "L*",
75
+ "lab_l": "L*",
76
+ "lab_a": "a*",
77
+ "lab_b": "b*",
78
+ "chroma": "Chroma",
79
+ "sat": "Saturation",
80
+ "s": "Saturation",
81
+ "r": "R", "g": "G", "b": "B",
82
+ }
83
+ # already proper label?
84
+ proper = {"k (brightness)":"K (Brightness)","r":"R","g":"G","b":"B",
85
+ "l*":"L*","a*":"a*","b*":"b*","chroma":"Chroma","saturation":"Saturation"}
86
+ if m in proper: return proper[m]
87
+ return alias.get(m, "K (Brightness)")
88
+
89
+ def _points_norm_to_scene(points_norm: List[Tuple[float, float]]) -> List[Tuple[float, float]]:
90
+ """
91
+ normalized (x:[0..1], y:[0..1] up-is-positive) -> scene coords (x:[0..360], y:[0..360] down-is-positive)
92
+ """
93
+ pts = []
94
+ for x, y in points_norm:
95
+ x = float(max(0.0, min(1.0, x)))
96
+ y = float(max(0.0, min(1.0, y)))
97
+ xs = 360.0 * x
98
+ ys = 360.0 * (1.0 - y) # invert Y for scene
99
+ pts.append((xs, ys))
100
+ # ensure endpoints exist
101
+ if not any(abs(px - 0.0) < 1e-6 for px, _ in pts): pts.append((0.0, 360.0))
102
+ if not any(abs(px - 360.0) < 1e-6 for px, _ in pts): pts.append((360.0, 0.0))
103
+ # x strictly increasing
104
+ pts = sorted(pts, key=lambda t: t[0])
105
+ out = []
106
+ lastx = -1e9
107
+ for x, y in pts:
108
+ if x <= lastx: x = lastx + 1e-3
109
+ out.append((min(360.0, max(0.0, x)), min(360.0, max(0.0, y))))
110
+ lastx = out[-1][0]
111
+ return out
112
+
113
+ def build_curve_lut(curve_func, size=65536):
114
+ """Map v∈[0..1] → y∈[0..1] using a curve defined on x∈[0..360] (scene coords)."""
115
+ x = np.linspace(0.0, 360.0, size, dtype=np.float32)
116
+ y = 360.0 - curve_func(x)
117
+ y = (y / 360.0).clip(0.0, 1.0).astype(np.float32)
118
+ return y
119
+
120
+ def _interpolator_from_scene_points(points_scene: List[Tuple[float, float]]):
121
+ xs = np.array([p[0] for p in points_scene], dtype=np.float64)
122
+ ys = np.array([p[1] for p in points_scene], dtype=np.float64)
123
+ if _HAS_PCHIP and xs.size >= 2:
124
+ return _PCHIP(xs, ys)
125
+ # fallback
126
+ def _lin(x):
127
+ return np.interp(x, xs, ys)
128
+ return _lin
129
+
130
+ def _lut_from_preset(preset: Dict) -> tuple[np.ndarray, str]:
131
+ """
132
+ Build LUT from any compatible preset / last-action dict.
133
+ """
134
+ pts_scene = _scene_points_from_preset(preset or {})
135
+ fn = _interpolator_from_scene_points(pts_scene)
136
+ lut01 = build_curve_lut(fn, size=65536)
137
+ mode = _norm_mode((preset or {}).get("mode"))
138
+ return lut01, mode
139
+
140
+ def _unwrap_preset_dict(preset: Dict) -> Dict:
141
+ """
142
+ Accept a variety of containers and peel down to the actual curve data.
143
+
144
+ Examples we handle:
145
+ {"step_name":"Curves","mode":..., "preset":{...}}
146
+ {"curves": {...}}
147
+ {"state": {...}} # if state contains curve points
148
+ """
149
+ p = dict(preset or {})
150
+
151
+ # Case 1: full metadata from doc.apply_edit: {"step_name":"Curves", "mode":..., "preset": {...}}
152
+ inner = p.get("preset")
153
+ if isinstance(inner, dict) and ("points_norm" in inner or "handles" in inner
154
+ or "points_scene" in inner or "scene_points" in inner):
155
+ return inner
156
+
157
+ # Case 2: payloads like {"curves": {...}}
158
+ inner = p.get("curves")
159
+ if isinstance(inner, dict) and ("points_norm" in inner or "handles" in inner
160
+ or "points_scene" in inner or "scene_points" in inner):
161
+ return inner
162
+
163
+ # Case 3: {"state": {...}} (if you stored the curve state under that key)
164
+ inner = p.get("state")
165
+ if isinstance(inner, dict) and ("points_norm" in inner or "handles" in inner
166
+ or "points_scene" in inner or "scene_points" in inner):
167
+ return inner
168
+
169
+ # Otherwise assume p already *is* the preset
170
+ return p
171
+
172
+
173
+ _SETTINGS_KEY = "curves/custom_presets_v1"
174
+
175
+ def _settings() -> QSettings | None:
176
+ try:
177
+ return QSettings()
178
+ except Exception:
179
+ return None
180
+
181
+ def list_custom_presets() -> list[dict]:
182
+ """Return a list of dicts: {"name", "mode", "shape":"custom", "points_norm":[[x,y],...]}"""
183
+ s = _settings()
184
+ if not s:
185
+ return []
186
+ raw = s.value(_SETTINGS_KEY, "", type=str) or ""
187
+ try:
188
+ lst = json.loads(raw)
189
+ if isinstance(lst, list):
190
+ return [p for p in lst if isinstance(p, dict)]
191
+ except Exception:
192
+ pass
193
+ return []
194
+
195
+ def save_custom_preset(name: str, mode: str, points_norm: list[tuple[float,float]]) -> bool:
196
+ """Create/overwrite by name."""
197
+ s = _settings()
198
+ if not s:
199
+ return False
200
+ name = (name or "").strip()
201
+ if not name:
202
+ return False
203
+ preset = {
204
+ "name": name,
205
+ "mode": _norm_mode(mode),
206
+ "shape": "custom",
207
+ "amount": 1.0,
208
+ "points_norm": [(float(x), float(y)) for (x, y) in points_norm],
209
+ }
210
+ lst = list_custom_presets()
211
+ lst = [p for p in lst if (p.get("name","").lower() != name.lower())]
212
+ lst.append(preset)
213
+ s.setValue(_SETTINGS_KEY, json.dumps(lst))
214
+ s.sync()
215
+ return True
216
+
217
+ def delete_custom_preset(name: str) -> bool:
218
+ s = _settings()
219
+ if not s:
220
+ return False
221
+ lst = list_custom_presets()
222
+ lst = [p for p in lst if (p.get("name","").lower() != (name or "").strip().lower())]
223
+ s.setValue(_SETTINGS_KEY, json.dumps(lst))
224
+ s.sync()
225
+ return True
226
+
227
+
228
+ # ---------------------- headless apply ----------------------
229
+ def apply_curves_via_preset(main_window, doc, preset: Dict):
230
+ import numpy as _np
231
+ from setiastro.saspro.curves_preset import _lut_from_preset, _unwrap_preset_dict # self
232
+ # lazy import to avoid cycle
233
+ from setiastro.saspro.curve_editor_pro import _apply_mode_any
234
+
235
+ img = getattr(doc, "image", None)
236
+ if img is None:
237
+ return
238
+
239
+ # Accept full last-action dicts and unwrap down to the actual curve definition
240
+ core_preset = _unwrap_preset_dict(preset or {})
241
+
242
+ arr = _np.asarray(img)
243
+ if arr.dtype.kind in "ui":
244
+ arr01 = arr.astype(_np.float32) / _np.iinfo(arr.dtype).max
245
+ elif arr.dtype.kind == "f":
246
+ mx = float(arr.max()) if arr.size else 1.0
247
+ arr01 = (arr / (mx if mx > 1.0 else 1.0)).astype(_np.float32)
248
+ else:
249
+ arr01 = arr.astype(_np.float32)
250
+
251
+ lut01, mode = _lut_from_preset(core_preset)
252
+ out01 = _apply_mode_any(arr01, mode, lut01)
253
+
254
+ meta = {
255
+ "step_name": "Curves",
256
+ "mode": mode,
257
+ "preset": dict(core_preset), # store the normalized core preset
258
+ }
259
+ doc.apply_edit(out01, metadata=meta, step_name="Curves")
260
+
261
+
262
+ # ---------------------- open UI with preset ----------------------
263
+ # ---------------------- open UI with preset ----------------------
264
+ def open_curves_with_preset(main_window, preset: Dict | None = None):
265
+ # lazy import UI to avoid cycle
266
+ from setiastro.saspro.curve_editor_pro import CurvesDialogPro
267
+
268
+ dm = getattr(main_window, "doc_manager", getattr(main_window, "docman", None))
269
+ if dm is None:
270
+ return
271
+ doc = dm.get_active_document() if hasattr(dm, "get_active_document") else getattr(dm, "active_document", None)
272
+ if doc is None:
273
+ return
274
+
275
+ dlg = CurvesDialogPro(main_window, doc)
276
+
277
+ # Peel down any wrapper (metadata / last-action container) to the actual curve definition
278
+ core_preset = _unwrap_preset_dict(preset or {})
279
+
280
+ # set mode radio from the *core* preset
281
+ want = _norm_mode(core_preset.get("mode"))
282
+ for b in dlg.mode_group.buttons():
283
+ if b.text().lower() == want.lower():
284
+ b.setChecked(True)
285
+ break
286
+
287
+ # Seed control handles from the same logic used by LUT building
288
+ pts_scene = _scene_points_from_preset(core_preset)
289
+
290
+ # remove exact endpoints if present; editor expects control handles only
291
+ filt = [(x, y) for (x, y) in pts_scene if x > 0.0 + 1e-6 and x < 360.0 - 1e-6]
292
+ dlg.editor.setControlHandles(filt)
293
+
294
+ dlg.show()
295
+ dlg.raise_()
296
+ dlg.activateWindow()
297
+
298
+
299
+ def _sanitize_scene_points(points_scene: List[Tuple[float, float]]) -> List[Tuple[float, float]]:
300
+ """
301
+ Take scene-space points (x,y in [0..360]) and:
302
+ - clamp to [0..360]
303
+ - ensure endpoints at x=0 and x=360 exist
304
+ - enforce strictly increasing x
305
+ """
306
+ pts = []
307
+ for x, y in points_scene:
308
+ xs = float(x)
309
+ ys = float(y)
310
+ xs = min(360.0, max(0.0, xs))
311
+ ys = min(360.0, max(0.0, ys))
312
+ pts.append((xs, ys))
313
+
314
+ # ensure endpoints exist
315
+ if not any(abs(px - 0.0) < 1e-6 for px, _ in pts):
316
+ pts.append((0.0, 360.0))
317
+ if not any(abs(px - 360.0) < 1e-6 for px, _ in pts):
318
+ pts.append((360.0, 0.0))
319
+
320
+ # x strictly increasing
321
+ pts = sorted(pts, key=lambda t: t[0])
322
+ out: List[Tuple[float, float]] = []
323
+ lastx = -1e9
324
+ for x, y in pts:
325
+ if x <= lastx:
326
+ x = lastx + 1e-3
327
+ out.append((min(360.0, max(0.0, x)), min(360.0, max(0.0, y))))
328
+ lastx = out[-1][0]
329
+ return out
330
+
331
+
332
+ def _scene_points_from_preset(preset: Dict) -> List[Tuple[float, float]]:
333
+ """
334
+ Accepts any of:
335
+ - preset["points_scene"] / preset["scene_points"]
336
+ → list of [x,y] or {"x":..,"y":..} in scene coords
337
+ - preset["handles"] / preset["control_points"]
338
+ → same as above, in scene coords (what the editor stores)
339
+ - preset["points_norm"]
340
+ → normalized [0..1] points
341
+ - otherwise falls back to shape/amount library
342
+ Returns a sanitized list of scene-space points.
343
+ """
344
+ p = preset or {}
345
+
346
+ # 1) explicit scene coords from several possible keys
347
+ for key in ("points_scene", "scene_points", "handles", "control_points"):
348
+ raw = p.get(key)
349
+ if isinstance(raw, (list, tuple)) and len(raw) >= 2:
350
+ pts: List[Tuple[float, float]] = []
351
+ for entry in raw:
352
+ if isinstance(entry, (list, tuple)) and len(entry) >= 2:
353
+ x, y = entry[0], entry[1]
354
+ elif isinstance(entry, dict):
355
+ x, y = entry.get("x"), entry.get("y")
356
+ else:
357
+ continue
358
+ if x is None or y is None:
359
+ continue
360
+ pts.append((float(x), float(y)))
361
+ if pts:
362
+ return _sanitize_scene_points(pts)
363
+
364
+ # 2) normalized points (what we already support)
365
+ shape = str(p.get("shape", "linear"))
366
+ amount = float(p.get("amount", 0.5))
367
+ ptsN = p.get("points_norm")
368
+
369
+ if isinstance(ptsN, (list, tuple)) and len(ptsN) >= 2:
370
+ pts_norm = [(float(x), float(y)) for (x, y) in ptsN]
371
+ else:
372
+ pts_norm = _shape_points_norm(shape, amount)
373
+
374
+ return _points_norm_to_scene(pts_norm)
375
+