scitex 2.10.3__py3-none-any.whl → 2.13.0__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.
- scitex/__init__.py +1 -4
- scitex/__main__.py +24 -5
- scitex/__version__.py +1 -1
- scitex/_install_guide.py +14 -2
- scitex/_optional_deps.py +33 -0
- scitex/ai/classification/reporters/_ClassificationReporter.py +1 -1
- scitex/ai/classification/timeseries/_TimeSeriesBlockingSplit.py +2 -2
- scitex/ai/classification/timeseries/_TimeSeriesCalendarSplit.py +2 -2
- scitex/ai/classification/timeseries/_TimeSeriesSlidingWindowSplit.py +2 -2
- scitex/ai/classification/timeseries/_TimeSeriesSlidingWindowSplit_v01-not-using-n_splits.py +2 -2
- scitex/ai/classification/timeseries/_TimeSeriesStratifiedSplit.py +2 -2
- scitex/ai/classification/timeseries/_normalize_timestamp.py +1 -1
- scitex/ai/metrics/_calc_seizure_prediction_metrics.py +1 -1
- scitex/ai/plt/_plot_feature_importance.py +1 -1
- scitex/ai/plt/_plot_learning_curve.py +1 -1
- scitex/ai/plt/_plot_optuna_study.py +1 -1
- scitex/ai/plt/_plot_pre_rec_curve.py +1 -1
- scitex/ai/plt/_plot_roc_curve.py +1 -1
- scitex/ai/plt/_stx_conf_mat.py +1 -1
- scitex/ai/training/_LearningCurveLogger.py +1 -1
- scitex/audio/mcp_server.py +38 -8
- scitex/bridge/_figrecipe.py +1 -1
- scitex/bridge/_helpers.py +1 -1
- scitex/bridge/_plt_vis.py +1 -1
- scitex/bridge/_stats_plt.py +1 -1
- scitex/bridge/_stats_vis.py +2 -2
- scitex/browser/automation/CookieHandler.py +1 -1
- scitex/browser/core/BrowserMixin.py +1 -1
- scitex/browser/core/ChromeProfileManager.py +1 -1
- scitex/browser/debugging/_browser_logger.py +1 -1
- scitex/browser/debugging/_highlight_element.py +1 -1
- scitex/browser/debugging/_show_grid.py +1 -1
- scitex/browser/interaction/click_center.py +1 -1
- scitex/browser/interaction/click_with_fallbacks.py +1 -1
- scitex/browser/interaction/close_popups.py +1 -1
- scitex/browser/interaction/fill_with_fallbacks.py +1 -1
- scitex/browser/pdf/click_download_for_chrome_pdf_viewer.py +1 -1
- scitex/browser/pdf/detect_chrome_pdf_viewer.py +1 -1
- scitex/browser/stealth/HumanBehavior.py +1 -1
- scitex/browser/stealth/StealthManager.py +1 -1
- scitex/{fig → canvas}/__init__.py +84 -96
- scitex/canvas/_mcp_handlers.py +372 -0
- scitex/canvas/_mcp_tool_schemas.py +219 -0
- scitex/{fig → canvas}/backend/_parser.py +1 -1
- scitex/{fig → canvas}/canvas.py +13 -14
- scitex/{fts/_fig/_editor → canvas/editor}/_defaults.py +2 -2
- scitex/{fig → canvas}/editor/edit/__init__.py +11 -14
- scitex/{fig → canvas}/editor/edit/bundle_resolver.py +56 -48
- scitex/{fig → canvas}/editor/edit/editor_launcher.py +79 -26
- scitex/{fts/_fig/_editor/_cui/_panel_loader.py → canvas/editor/edit/panel_loader.py} +8 -8
- scitex/{fts/_fig/_editor/_gui/_flask_editor → canvas/editor/flask_editor}/_bbox.py +2 -1
- scitex/{fts/_fig/_editor/_gui/_flask_editor → canvas/editor/flask_editor}/_core.py +84 -84
- scitex/{fts/_fig/_editor/_gui/_flask_editor → canvas/editor/flask_editor}/_renderer.py +7 -6
- scitex/{fts/_fig/_editor/_gui/_flask_editor → canvas/editor/flask_editor}/static/css/features/canvas.css +2 -2
- scitex/{fig → canvas}/editor/flask_editor/static/css/features/panel-grid.css +1 -1
- scitex/{fig → canvas}/editor/flask_editor/static/js/core/api.js +3 -4
- scitex/{fig → canvas}/editor/flask_editor/static/js/editor/preview.js +5 -5
- scitex/{fig → canvas}/editor/flask_editor/templates/_html.py +3 -3
- scitex/{fig → canvas}/editor/flask_editor/templates/_scripts.py +10 -10
- scitex/{fig → canvas}/editor/flask_editor/templates/_styles.py +3 -3
- scitex/{fig → canvas}/io/__init__.py +32 -38
- scitex/{fig → canvas}/io/_bundle.py +217 -154
- scitex/{fig → canvas}/io/_canvas.py +1 -1
- scitex/{fig → canvas}/io/_data.py +1 -1
- scitex/{fig → canvas}/io/_export.py +1 -1
- scitex/{fig → canvas}/io/_load.py +1 -1
- scitex/{fig → canvas}/io/_panel.py +1 -1
- scitex/{fig → canvas}/io/_save.py +1 -1
- scitex/canvas/mcp_server.py +151 -0
- scitex/{fig → canvas}/model/__init__.py +1 -1
- scitex/{fig → canvas}/model/_annotations.py +1 -1
- scitex/{fig → canvas}/model/_axes.py +1 -1
- scitex/{fig → canvas}/model/_figure.py +1 -1
- scitex/{fig → canvas}/model/_guides.py +1 -1
- scitex/{fig → canvas}/model/_plot.py +1 -1
- scitex/{fig → canvas}/model/_styles.py +1 -1
- scitex/{fig → canvas}/utils/__init__.py +1 -1
- scitex/capture/mcp_server.py +41 -12
- scitex/cli/audio.py +233 -0
- scitex/cli/capture.py +307 -0
- scitex/cli/convert.py +10 -6
- scitex/cli/main.py +27 -4
- scitex/cli/repro.py +233 -0
- scitex/cli/resource.py +240 -0
- scitex/cli/stats.py +325 -0
- scitex/cli/template.py +236 -0
- scitex/cli/tex.py +286 -0
- scitex/cli/web.py +11 -12
- scitex/dev/__init__.py +3 -0
- scitex/dev/_pyproject.py +405 -0
- scitex/dev/plt/__init__.py +2 -2
- scitex/dev/plt/mpl/get_dir_ax.py +1 -1
- scitex/dev/plt/mpl/get_signatures.py +1 -1
- scitex/dev/plt/mpl/get_signatures_details.py +1 -1
- scitex/diagram/README.md +7 -7
- scitex/diagram/_mcp_handlers.py +400 -0
- scitex/diagram/_mcp_tool_schemas.py +157 -0
- scitex/diagram/mcp_server.py +151 -0
- scitex/dsp/_demo_sig.py +51 -5
- scitex/dsp/_mne.py +13 -2
- scitex/dsp/_modulation_index.py +15 -3
- scitex/dsp/_pac.py +23 -5
- scitex/dsp/_psd.py +16 -4
- scitex/dsp/_resample.py +24 -4
- scitex/dsp/_transform.py +16 -3
- scitex/dsp/add_noise.py +15 -1
- scitex/dsp/norm.py +17 -2
- scitex/dsp/reference.py +17 -1
- scitex/dsp/utils/_differential_bandpass_filters.py +20 -2
- scitex/dsp/utils/_zero_pad.py +18 -4
- scitex/dt/_normalize_timestamp.py +1 -1
- scitex/git/_session.py +1 -1
- scitex/io/__init__.py +7 -19
- scitex/io/_load.py +15 -19
- scitex/io/_load_modules/_canvas.py +2 -2
- scitex/io/_load_modules/_con.py +17 -6
- scitex/io/_load_modules/_eeg.py +28 -13
- scitex/io/_load_modules/_optuna.py +21 -63
- scitex/io/_load_modules/_torch.py +11 -3
- scitex/io/_save.py +11 -16
- scitex/io/_save_modules/__init__.py +6 -10
- scitex/io/_save_modules/_canvas.py +3 -3
- scitex/io/_save_modules/_optuna_study_as_csv_and_pngs.py +13 -2
- scitex/io/_save_modules/_plot_bundle.py +112 -0
- scitex/io/_save_modules/{_pltz_stx.py → _plot_scitex.py} +7 -7
- scitex/io/_save_modules/_stx_bundle.py +16 -16
- scitex/io/_save_modules/_torch.py +11 -3
- scitex/io/bundle/README.md +89 -80
- scitex/{fts/_bundle/_FTS.py → io/bundle/_Bundle.py} +197 -95
- scitex/io/bundle/__init__.py +67 -35
- scitex/{fts/_bundle → io/bundle}/_children.py +32 -40
- scitex/io/bundle/_core.py +184 -97
- scitex/{fts/_bundle/_dataclasses/_Node.py → io/bundle/_dataclasses/_Spec.py} +29 -23
- scitex/{fts/_bundle/_dataclasses/_NodeRefs.py → io/bundle/_dataclasses/_SpecRefs.py} +6 -6
- scitex/{fts/_bundle → io/bundle}/_dataclasses/__init__.py +4 -4
- scitex/{fts/_bundle → io/bundle}/_loader.py +19 -19
- scitex/io/bundle/_manifest.py +99 -0
- scitex/{fts/_bundle → io/bundle}/_mpl_helpers.py +119 -28
- scitex/io/bundle/_nested.py +113 -100
- scitex/{fts/_bundle → io/bundle}/_saver.py +13 -14
- scitex/{fts/_bundle → io/bundle}/_storage.py +3 -3
- scitex/io/bundle/_types.py +41 -16
- scitex/{fts/_bundle → io/bundle}/_validation.py +20 -18
- scitex/io/bundle/_zip.py +21 -31
- scitex/{fts/_kinds → io/bundle/kinds}/_plot/_backend/_parser.py +1 -1
- scitex/{fts/_kinds → io/bundle/kinds}/_plot/_models/_Annotations.py +1 -1
- scitex/{fts/_kinds → io/bundle/kinds}/_plot/_models/_Axes.py +1 -1
- scitex/{fts/_kinds → io/bundle/kinds}/_plot/_models/_Figure.py +1 -1
- scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_Guides.py +1 -1
- scitex/{fts/_kinds → io/bundle/kinds}/_plot/_models/_Plot.py +1 -1
- scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_Styles.py +1 -1
- scitex/{fts/_kinds → io/bundle/kinds}/_plot/_utils/_plot_layout.py +1 -1
- scitex/{fts/_kinds → io/bundle/kinds}/_table/_latex/__init__.py +1 -1
- scitex/{fts/_kinds → io/bundle/kinds}/_table/_latex/_editor/_app.py +1 -1
- scitex/{fts/_tables → io/bundle/kinds/_table}/_latex/_export.py +1 -1
- scitex/{fts/_kinds → io/bundle/kinds}/_table/_latex/_figure_exporter.py +1 -1
- scitex/{fts/_kinds → io/bundle/kinds}/_table/_latex/_table_exporter.py +1 -1
- scitex/io/bundle/schemas/__init__.py +30 -0
- scitex/mcp_server.py +159 -0
- scitex/parallel/_run.py +5 -4
- scitex/path/_find.py +60 -83
- scitex/path/_get_module_path.py +23 -21
- scitex/path/_get_spath.py +6 -27
- scitex/path/_getsize.py +23 -9
- scitex/path/_increment_version.py +31 -38
- scitex/path/_mk_spath.py +26 -29
- scitex/path/_path.py +5 -12
- scitex/path/_split.py +27 -15
- scitex/path/_this_path.py +23 -9
- scitex/plt/_mcp_handlers.py +361 -0
- scitex/plt/_mcp_tool_schemas.py +169 -0
- scitex/plt/_subplots/_AxisWrapperMixins/_MatplotlibPlotMixin/__init__.py +2 -1
- scitex/plt/_subplots/_AxisWrapperMixins/__init__.py +2 -2
- scitex/plt/gallery/_generate.py +76 -50
- scitex/plt/io/__init__.py +17 -19
- scitex/plt/io/_bundle.py +99 -52
- scitex/plt/io/_layered_bundle.py +303 -168
- scitex/plt/mcp_server.py +205 -0
- scitex/plt/utils/_csv_column_naming.py +250 -118
- scitex/repro/README_RandomStateManager.md +3 -3
- scitex/repro/_RandomStateManager.py +14 -14
- scitex/repro/_gen_ID.py +1 -1
- scitex/repro/_gen_timestamp.py +1 -1
- scitex/repro/_hash_array.py +4 -4
- scitex/schema/__init__.py +69 -73
- scitex/schema/_canvas.py +1 -1
- scitex/schema/_stats.py +2 -2
- scitex/scholar/__main__.py +24 -2
- scitex/scholar/_mcp_handlers.py +685 -0
- scitex/scholar/_mcp_tool_schemas.py +339 -0
- scitex/scholar/docs/template.py +1 -1
- scitex/scholar/examples/07_storage_integration.py +1 -1
- scitex/scholar/impact_factor/jcr/ImpactFactorJCREngine.py +1 -1
- scitex/scholar/impact_factor/jcr/build_database.py +1 -1
- scitex/scholar/mcp_server.py +315 -0
- scitex/scholar/pdf_download/ScholarPDFDownloader.py +1 -1
- scitex/scholar/pipelines/ScholarPipelineBibTeX.py +1 -1
- scitex/scholar/pipelines/ScholarPipelineParallel.py +1 -1
- scitex/scholar/pipelines/ScholarPipelineSingle.py +1 -1
- scitex/scholar/storage/PaperIO.py +1 -1
- scitex/session/README.md +4 -4
- scitex/session/__init__.py +1 -1
- scitex/session/_decorator.py +9 -9
- scitex/session/_lifecycle.py +5 -5
- scitex/session/template.py +1 -1
- scitex/stats/__init__.py +30 -33
- scitex/stats/__main__.py +281 -0
- scitex/stats/_mcp_handlers.py +1191 -0
- scitex/stats/_mcp_tool_schemas.py +384 -0
- scitex/stats/_schema.py +1 -1
- scitex/stats/correct/_correct_bonferroni.py +1 -1
- scitex/stats/correct/_correct_fdr.py +1 -1
- scitex/stats/correct/_correct_fdr_.py +1 -1
- scitex/stats/correct/_correct_holm.py +1 -1
- scitex/stats/correct/_correct_sidak.py +1 -1
- scitex/stats/effect_sizes/_cliffs_delta.py +1 -1
- scitex/stats/effect_sizes/_cohens_d.py +1 -1
- scitex/stats/effect_sizes/_epsilon_squared.py +1 -1
- scitex/stats/effect_sizes/_eta_squared.py +1 -1
- scitex/stats/effect_sizes/_prob_superiority.py +1 -1
- scitex/stats/io/__init__.py +10 -11
- scitex/stats/io/_bundle.py +16 -16
- scitex/stats/mcp_server.py +405 -0
- scitex/stats/posthoc/_dunnett.py +1 -1
- scitex/stats/posthoc/_games_howell.py +1 -1
- scitex/stats/posthoc/_tukey_hsd.py +1 -1
- scitex/stats/power/_power.py +1 -1
- scitex/stats/utils/_effect_size.py +1 -1
- scitex/stats/utils/_formatters.py +1 -1
- scitex/stats/utils/_power.py +1 -1
- scitex/template/_mcp_handlers.py +259 -0
- scitex/template/_mcp_tool_schemas.py +112 -0
- scitex/template/mcp_server.py +186 -0
- scitex/utils/_verify_scitex_format.py +2 -2
- scitex/utils/template.py +1 -1
- scitex/web/__init__.py +12 -11
- scitex/web/_scraping.py +26 -265
- scitex/web/download_images.py +316 -0
- scitex/writer/Writer.py +1 -1
- scitex/writer/_clone_writer_project.py +1 -1
- scitex/writer/_validate_tree_structures.py +1 -1
- scitex/writer/dataclasses/config/_WriterConfig.py +1 -1
- scitex/writer/dataclasses/contents/_ManuscriptContents.py +1 -1
- scitex/writer/dataclasses/core/_Document.py +1 -1
- scitex/writer/dataclasses/core/_DocumentSection.py +1 -1
- scitex/writer/dataclasses/results/_CompilationResult.py +1 -1
- scitex/writer/dataclasses/results/_LaTeXIssue.py +1 -1
- scitex/writer/utils/.legacy_git_retry.py +7 -5
- scitex/writer/utils/_parse_latex_logs.py +1 -1
- scitex-2.13.0.dist-info/METADATA +1231 -0
- {scitex-2.10.3.dist-info → scitex-2.13.0.dist-info}/RECORD +376 -470
- scitex-2.13.0.dist-info/entry_points.txt +11 -0
- scitex/fig/editor/_defaults.py +0 -300
- scitex/fig/editor/edit/panel_loader.py +0 -232
- scitex/fig/editor/flask_editor/_bbox.py +0 -1299
- scitex/fig/editor/flask_editor/_core.py +0 -1429
- scitex/fig/editor/flask_editor/_renderer.py +0 -813
- scitex/fig/editor/flask_editor/static/css/features/canvas.css +0 -176
- scitex/fts/README.md +0 -262
- scitex/fts/TODO.md +0 -66
- scitex/fts/__init__.py +0 -90
- scitex/fts/_bundle/README_IN_BUNDLE.md +0 -102
- scitex/fts/_bundle/__init__.py +0 -38
- scitex/fts/_bundle/_utils/__init__.py +0 -55
- scitex/fts/_bundle/_utils/_const.py +0 -26
- scitex/fts/_bundle/_utils/_errors.py +0 -73
- scitex/fts/_bundle/_utils/_generate.py +0 -21
- scitex/fts/_bundle/_utils/_types.py +0 -76
- scitex/fts/_bundle/_zipbundle.py +0 -165
- scitex/fts/_fig/__init__.py +0 -22
- scitex/fts/_fig/_backend/_parser.py +0 -188
- scitex/fts/_fig/_editor/__init__.py +0 -14
- scitex/fts/_fig/_editor/_cui/__init__.py +0 -33
- scitex/fts/_fig/_editor/_cui/_backend_detector.py +0 -39
- scitex/fts/_fig/_editor/_cui/_bundle_resolver.py +0 -366
- scitex/fts/_fig/_editor/_cui/_editor_launcher.py +0 -175
- scitex/fts/_fig/_editor/_cui/_manual_handler.py +0 -52
- scitex/fts/_fig/_editor/_cui/_path_resolver.py +0 -66
- scitex/fts/_fig/_editor/_gui/__init__.py +0 -11
- scitex/fts/_fig/_editor/_gui/_flask_editor/__init__.py +0 -20
- scitex/fts/_fig/_editor/_gui/_flask_editor/_plotter.py +0 -664
- scitex/fts/_fig/_editor/_gui/_flask_editor/_utils.py +0 -79
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/base/reset.css +0 -41
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/base/typography.css +0 -16
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/base/variables.css +0 -85
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/components/buttons.css +0 -217
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/components/context-menu.css +0 -93
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/components/dropdown.css +0 -57
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/components/forms.css +0 -112
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/components/modal.css +0 -59
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/components/sections.css +0 -212
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/features/element-inspector.css +0 -190
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/features/loading.css +0 -59
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/features/overlay.css +0 -45
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/features/panel-grid.css +0 -95
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/features/selection.css +0 -101
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/features/statistics.css +0 -138
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/index.css +0 -31
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/layout/container.css +0 -7
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/layout/controls.css +0 -56
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/css/layout/preview.css +0 -78
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/alignment/axis.js +0 -314
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/alignment/basic.js +0 -107
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/alignment/distribute.js +0 -54
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/canvas/canvas.js +0 -172
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/canvas/dragging.js +0 -258
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/canvas/resize.js +0 -48
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/canvas/selection.js +0 -71
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/core/api.js +0 -288
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/core/state.js +0 -143
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/core/utils.js +0 -245
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/dev/element-inspector.js +0 -992
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/editor/bbox.js +0 -339
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/editor/element-drag.js +0 -286
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/editor/overlay.js +0 -371
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/editor/preview.js +0 -293
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/main.js +0 -426
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/shortcuts/context-menu.js +0 -152
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/shortcuts/keyboard.js +0 -265
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/ui/controls.js +0 -184
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/ui/download.js +0 -57
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/ui/help.js +0 -100
- scitex/fts/_fig/_editor/_gui/_flask_editor/static/js/ui/theme.js +0 -34
- scitex/fts/_fig/_editor/_gui/_flask_editor/templates/__init__.py +0 -124
- scitex/fts/_fig/_editor/_gui/_flask_editor/templates/_html.py +0 -851
- scitex/fts/_fig/_editor/_gui/_flask_editor/templates/_scripts.py +0 -4932
- scitex/fts/_fig/_editor/_gui/_flask_editor/templates/_styles.py +0 -1657
- scitex/fts/_fig/_editor/_gui/_flask_editor.py +0 -36
- scitex/fts/_fig/_models/_Annotations.py +0 -115
- scitex/fts/_fig/_models/_Axes.py +0 -152
- scitex/fts/_fig/_models/_Figure.py +0 -138
- scitex/fts/_fig/_models/_Plot.py +0 -123
- scitex/fts/_fig/_utils/_plot_layout.py +0 -397
- scitex/fts/_kinds/_figure/_composite.py +0 -345
- scitex/fts/_kinds/_plot/_backend/__init__.py +0 -53
- scitex/fts/_kinds/_plot/_backend/_export.py +0 -165
- scitex/fts/_kinds/_plot/_backend/_render.py +0 -538
- scitex/fts/_kinds/_plot/_dataclasses/_ChannelEncoding.py +0 -46
- scitex/fts/_kinds/_plot/_dataclasses/_Encoding.py +0 -82
- scitex/fts/_kinds/_plot/_dataclasses/_Theme.py +0 -441
- scitex/fts/_kinds/_plot/_dataclasses/_TraceEncoding.py +0 -52
- scitex/fts/_kinds/_plot/_dataclasses/__init__.py +0 -47
- scitex/fts/_kinds/_plot/_models/_Guides.py +0 -104
- scitex/fts/_kinds/_plot/_models/_Styles.py +0 -245
- scitex/fts/_kinds/_plot/_models/__init__.py +0 -80
- scitex/fts/_kinds/_plot/_models/_plot_types/__init__.py +0 -156
- scitex/fts/_kinds/_plot/_models/_plot_types/_bar.py +0 -43
- scitex/fts/_kinds/_plot/_models/_plot_types/_box.py +0 -38
- scitex/fts/_kinds/_plot/_models/_plot_types/_distribution.py +0 -36
- scitex/fts/_kinds/_plot/_models/_plot_types/_errorbar.py +0 -60
- scitex/fts/_kinds/_plot/_models/_plot_types/_histogram.py +0 -30
- scitex/fts/_kinds/_plot/_models/_plot_types/_image.py +0 -61
- scitex/fts/_kinds/_plot/_models/_plot_types/_line.py +0 -57
- scitex/fts/_kinds/_plot/_models/_plot_types/_scatter.py +0 -30
- scitex/fts/_kinds/_plot/_models/_plot_types/_seaborn.py +0 -121
- scitex/fts/_kinds/_plot/_models/_plot_types/_violin.py +0 -36
- scitex/fts/_kinds/_plot/_utils/__init__.py +0 -129
- scitex/fts/_kinds/_plot/_utils/_auto_layout.py +0 -127
- scitex/fts/_kinds/_plot/_utils/_calc_bounds.py +0 -111
- scitex/fts/_kinds/_plot/_utils/_const_sizes.py +0 -48
- scitex/fts/_kinds/_plot/_utils/_convert_coords.py +0 -77
- scitex/fts/_kinds/_plot/_utils/_get_template.py +0 -178
- scitex/fts/_kinds/_plot/_utils/_normalize.py +0 -73
- scitex/fts/_kinds/_plot/_utils/_validate.py +0 -197
- scitex/fts/_kinds/_table/_latex/_export.py +0 -279
- scitex/fts/_stats/__init__.py +0 -48
- scitex/fts/_stats/_dataclasses/_Stats.py +0 -423
- scitex/fts/_stats/_dataclasses/__init__.py +0 -48
- scitex/fts/_tables/__init__.py +0 -65
- scitex/fts/_tables/_latex/__init__.py +0 -93
- scitex/fts/_tables/_latex/_editor/__init__.py +0 -11
- scitex/fts/_tables/_latex/_editor/_app.py +0 -725
- scitex/fts/_tables/_latex/_figure_exporter.py +0 -153
- scitex/fts/_tables/_latex/_stats_formatter.py +0 -274
- scitex/fts/_tables/_latex/_table_exporter.py +0 -362
- scitex/fts/_tables/_latex/_utils.py +0 -369
- scitex/fts/_tables/_latex/_validator.py +0 -445
- scitex/io/_save_modules/_pltz_bundle.py +0 -356
- scitex-2.10.3.dist-info/METADATA +0 -952
- scitex-2.10.3.dist-info/entry_points.txt +0 -2
- /scitex/{fig → canvas}/README.md +0 -0
- /scitex/{fig → canvas}/backend/__init__.py +0 -0
- /scitex/{fig → canvas}/backend/_export.py +0 -0
- /scitex/{fig → canvas}/backend/_render.py +0 -0
- /scitex/{fig → canvas}/docs/CANVAS_ARCHITECTURE.md +0 -0
- /scitex/{fig → canvas}/editor/__init__.py +0 -0
- /scitex/{fig → canvas}/editor/_dearpygui_editor.py +0 -0
- /scitex/{fig → canvas}/editor/_flask_editor.py +0 -0
- /scitex/{fig → canvas}/editor/_mpl_editor.py +0 -0
- /scitex/{fig → canvas}/editor/_qt_editor.py +0 -0
- /scitex/{fig → canvas}/editor/_tkinter_editor.py +0 -0
- /scitex/{fig → canvas}/editor/edit/backend_detector.py +0 -0
- /scitex/{fig → canvas}/editor/edit/manual_handler.py +0 -0
- /scitex/{fig → canvas}/editor/edit/path_resolver.py +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/__init__.py +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/_plotter.py +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/_utils.py +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/base/reset.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/base/typography.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/base/variables.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/components/buttons.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/components/context-menu.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/components/dropdown.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/components/forms.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/components/modal.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/components/sections.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/features/element-inspector.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/features/loading.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/features/overlay.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/features/selection.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/features/statistics.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/index.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/layout/container.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/layout/controls.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/css/layout/preview.css +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/alignment/axis.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/alignment/basic.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/alignment/distribute.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/canvas/canvas.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/canvas/dragging.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/canvas/resize.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/canvas/selection.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/core/state.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/core/utils.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/dev/element-inspector.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/editor/bbox.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/editor/element-drag.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/editor/overlay.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/main.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/shortcuts/context-menu.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/shortcuts/keyboard.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/ui/controls.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/ui/download.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/ui/help.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/static/js/ui/theme.js +0 -0
- /scitex/{fig → canvas}/editor/flask_editor/templates/__init__.py +0 -0
- /scitex/{fig → canvas}/io/_directory.py +0 -0
- /scitex/{fig → canvas}/model/_plot_types.py +0 -0
- /scitex/{fig → canvas}/utils/_defaults.py +0 -0
- /scitex/{fig → canvas}/utils/_validate.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_conversion/__init__.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_conversion/_bundle2dict.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_conversion/_dict2bundle.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_dataclasses/_Axes.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_dataclasses/_BBox.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_dataclasses/_ColumnDef.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_dataclasses/_DataFormat.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_dataclasses/_DataInfo.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_dataclasses/_DataSource.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_dataclasses/_SizeMM.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_extractors/__init__.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_extractors/_extract_bar.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_extractors/_extract_line.py +0 -0
- /scitex/{fts/_bundle → io/bundle}/_extractors/_extract_scatter.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/__init__.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/_figure/__init__.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_figure}/_composite.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/_plot/__init__.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_backend/__init__.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_backend/_export.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_backend/_render.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_dataclasses/_ChannelEncoding.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_dataclasses/_Encoding.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_dataclasses/_Theme.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_dataclasses/_TraceEncoding.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_dataclasses/__init__.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/__init__.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_plot_types/__init__.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_plot_types/_bar.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_plot_types/_box.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_plot_types/_distribution.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_plot_types/_errorbar.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_plot_types/_histogram.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_plot_types/_image.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_plot_types/_line.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_plot_types/_scatter.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_plot_types/_seaborn.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_models/_plot_types/_violin.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_utils/__init__.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_utils/_auto_layout.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_utils/_calc_bounds.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_utils/_const_sizes.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_utils/_convert_coords.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_utils/_get_template.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_utils/_normalize.py +0 -0
- /scitex/{fts/_fig → io/bundle/kinds/_plot}/_utils/_validate.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/_shape/__init__.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/_stats/__init__.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/_stats/_dataclasses/_Stats.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/_stats/_dataclasses/__init__.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/_table/__init__.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/_table/_latex/_editor/__init__.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/_table/_latex/_stats_formatter.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/_table/_latex/_utils.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/_table/_latex/_validator.py +0 -0
- /scitex/{fts/_kinds → io/bundle/kinds}/_text/__init__.py +0 -0
- /scitex/{fts/_schemas → io/bundle/schemas}/data_info.schema.json +0 -0
- /scitex/{fts/_schemas → io/bundle/schemas}/encoding.schema.json +0 -0
- /scitex/{fts/_schemas → io/bundle/schemas}/node.schema.json +0 -0
- /scitex/{fts/_schemas → io/bundle/schemas}/render_manifest.schema.json +0 -0
- /scitex/{fts/_schemas → io/bundle/schemas}/stats.schema.json +0 -0
- /scitex/{fts/_schemas → io/bundle/schemas}/theme.schema.json +0 -0
- {scitex-2.10.3.dist-info → scitex-2.13.0.dist-info}/WHEEL +0 -0
- {scitex-2.10.3.dist-info → scitex-2.13.0.dist-info}/licenses/LICENSE +0 -0
|
@@ -0,0 +1,219 @@
|
|
|
1
|
+
#!/usr/bin/env python3
|
|
2
|
+
# Timestamp: 2026-01-08
|
|
3
|
+
# File: src/scitex/canvas/_mcp_tool_schemas.py
|
|
4
|
+
# ----------------------------------------
|
|
5
|
+
|
|
6
|
+
"""
|
|
7
|
+
MCP Tool schemas for SciTeX canvas module.
|
|
8
|
+
|
|
9
|
+
Defines tools for multi-panel figure composition:
|
|
10
|
+
- create_canvas: Create paper figure workspace
|
|
11
|
+
- add_panel: Add subplot to canvas
|
|
12
|
+
- list_panels: List panels in canvas
|
|
13
|
+
- export_canvas: Render final figure
|
|
14
|
+
- list_canvases: List available canvases
|
|
15
|
+
"""
|
|
16
|
+
|
|
17
|
+
from __future__ import annotations
|
|
18
|
+
|
|
19
|
+
import mcp.types as types
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
def get_tool_schemas() -> list[types.Tool]:
|
|
23
|
+
"""Return list of available MCP tools for canvas operations."""
|
|
24
|
+
return [
|
|
25
|
+
# Create canvas
|
|
26
|
+
types.Tool(
|
|
27
|
+
name="create_canvas",
|
|
28
|
+
description="Create a new paper figure canvas workspace for multi-panel composition",
|
|
29
|
+
inputSchema={
|
|
30
|
+
"type": "object",
|
|
31
|
+
"properties": {
|
|
32
|
+
"parent_dir": {
|
|
33
|
+
"type": "string",
|
|
34
|
+
"description": "Parent directory for the canvas",
|
|
35
|
+
},
|
|
36
|
+
"canvas_name": {
|
|
37
|
+
"type": "string",
|
|
38
|
+
"description": "Name for the canvas (e.g., 'fig1', 'Figure_2')",
|
|
39
|
+
},
|
|
40
|
+
"width_mm": {
|
|
41
|
+
"type": "number",
|
|
42
|
+
"description": "Canvas width in millimeters (default: 180 for double column)",
|
|
43
|
+
"default": 180,
|
|
44
|
+
},
|
|
45
|
+
"height_mm": {
|
|
46
|
+
"type": "number",
|
|
47
|
+
"description": "Canvas height in millimeters (default: 120)",
|
|
48
|
+
"default": 120,
|
|
49
|
+
},
|
|
50
|
+
},
|
|
51
|
+
"required": ["parent_dir", "canvas_name"],
|
|
52
|
+
},
|
|
53
|
+
),
|
|
54
|
+
# Add panel
|
|
55
|
+
types.Tool(
|
|
56
|
+
name="add_panel",
|
|
57
|
+
description="Add a panel (subplot) to an existing canvas from an image or plot file",
|
|
58
|
+
inputSchema={
|
|
59
|
+
"type": "object",
|
|
60
|
+
"properties": {
|
|
61
|
+
"parent_dir": {
|
|
62
|
+
"type": "string",
|
|
63
|
+
"description": "Parent directory containing the canvas",
|
|
64
|
+
},
|
|
65
|
+
"canvas_name": {
|
|
66
|
+
"type": "string",
|
|
67
|
+
"description": "Canvas name",
|
|
68
|
+
},
|
|
69
|
+
"panel_name": {
|
|
70
|
+
"type": "string",
|
|
71
|
+
"description": "Name for this panel (e.g., 'panel_a', 'timecourse')",
|
|
72
|
+
},
|
|
73
|
+
"source": {
|
|
74
|
+
"type": "string",
|
|
75
|
+
"description": "Path to source file (PNG, JPG, SVG, or SciTeX plot)",
|
|
76
|
+
},
|
|
77
|
+
"x_mm": {
|
|
78
|
+
"type": "number",
|
|
79
|
+
"description": "X position in millimeters from left edge",
|
|
80
|
+
"default": 0,
|
|
81
|
+
},
|
|
82
|
+
"y_mm": {
|
|
83
|
+
"type": "number",
|
|
84
|
+
"description": "Y position in millimeters from top edge",
|
|
85
|
+
"default": 0,
|
|
86
|
+
},
|
|
87
|
+
"width_mm": {
|
|
88
|
+
"type": "number",
|
|
89
|
+
"description": "Panel width in millimeters",
|
|
90
|
+
"default": 50,
|
|
91
|
+
},
|
|
92
|
+
"height_mm": {
|
|
93
|
+
"type": "number",
|
|
94
|
+
"description": "Panel height in millimeters",
|
|
95
|
+
"default": 50,
|
|
96
|
+
},
|
|
97
|
+
"label": {
|
|
98
|
+
"type": "string",
|
|
99
|
+
"description": "Panel label (e.g., 'A', 'B', 'C')",
|
|
100
|
+
},
|
|
101
|
+
},
|
|
102
|
+
"required": ["parent_dir", "canvas_name", "panel_name", "source"],
|
|
103
|
+
},
|
|
104
|
+
),
|
|
105
|
+
# List panels
|
|
106
|
+
types.Tool(
|
|
107
|
+
name="list_panels",
|
|
108
|
+
description="List all panels in a canvas with their properties",
|
|
109
|
+
inputSchema={
|
|
110
|
+
"type": "object",
|
|
111
|
+
"properties": {
|
|
112
|
+
"parent_dir": {
|
|
113
|
+
"type": "string",
|
|
114
|
+
"description": "Parent directory containing the canvas",
|
|
115
|
+
},
|
|
116
|
+
"canvas_name": {
|
|
117
|
+
"type": "string",
|
|
118
|
+
"description": "Canvas name",
|
|
119
|
+
},
|
|
120
|
+
},
|
|
121
|
+
"required": ["parent_dir", "canvas_name"],
|
|
122
|
+
},
|
|
123
|
+
),
|
|
124
|
+
# Remove panel
|
|
125
|
+
types.Tool(
|
|
126
|
+
name="remove_panel",
|
|
127
|
+
description="Remove a panel from a canvas",
|
|
128
|
+
inputSchema={
|
|
129
|
+
"type": "object",
|
|
130
|
+
"properties": {
|
|
131
|
+
"parent_dir": {
|
|
132
|
+
"type": "string",
|
|
133
|
+
"description": "Parent directory containing the canvas",
|
|
134
|
+
},
|
|
135
|
+
"canvas_name": {
|
|
136
|
+
"type": "string",
|
|
137
|
+
"description": "Canvas name",
|
|
138
|
+
},
|
|
139
|
+
"panel_name": {
|
|
140
|
+
"type": "string",
|
|
141
|
+
"description": "Name of the panel to remove",
|
|
142
|
+
},
|
|
143
|
+
},
|
|
144
|
+
"required": ["parent_dir", "canvas_name", "panel_name"],
|
|
145
|
+
},
|
|
146
|
+
),
|
|
147
|
+
# Export canvas
|
|
148
|
+
types.Tool(
|
|
149
|
+
name="export_canvas",
|
|
150
|
+
description="Export/render canvas to PNG, PDF, or SVG format",
|
|
151
|
+
inputSchema={
|
|
152
|
+
"type": "object",
|
|
153
|
+
"properties": {
|
|
154
|
+
"parent_dir": {
|
|
155
|
+
"type": "string",
|
|
156
|
+
"description": "Parent directory containing the canvas",
|
|
157
|
+
},
|
|
158
|
+
"canvas_name": {
|
|
159
|
+
"type": "string",
|
|
160
|
+
"description": "Canvas name",
|
|
161
|
+
},
|
|
162
|
+
"output_path": {
|
|
163
|
+
"type": "string",
|
|
164
|
+
"description": "Output file path (format determined by extension)",
|
|
165
|
+
},
|
|
166
|
+
"format": {
|
|
167
|
+
"type": "string",
|
|
168
|
+
"description": "Output format (auto-detected from path if not specified)",
|
|
169
|
+
"enum": ["png", "pdf", "svg"],
|
|
170
|
+
},
|
|
171
|
+
"dpi": {
|
|
172
|
+
"type": "integer",
|
|
173
|
+
"description": "Output DPI for raster formats (default: 300)",
|
|
174
|
+
"default": 300,
|
|
175
|
+
},
|
|
176
|
+
},
|
|
177
|
+
"required": ["parent_dir", "canvas_name"],
|
|
178
|
+
},
|
|
179
|
+
),
|
|
180
|
+
# List canvases
|
|
181
|
+
types.Tool(
|
|
182
|
+
name="list_canvases",
|
|
183
|
+
description="List all canvases in a directory",
|
|
184
|
+
inputSchema={
|
|
185
|
+
"type": "object",
|
|
186
|
+
"properties": {
|
|
187
|
+
"parent_dir": {
|
|
188
|
+
"type": "string",
|
|
189
|
+
"description": "Directory to search for canvases",
|
|
190
|
+
},
|
|
191
|
+
},
|
|
192
|
+
"required": ["parent_dir"],
|
|
193
|
+
},
|
|
194
|
+
),
|
|
195
|
+
# Canvas exists
|
|
196
|
+
types.Tool(
|
|
197
|
+
name="canvas_exists",
|
|
198
|
+
description="Check if a canvas exists",
|
|
199
|
+
inputSchema={
|
|
200
|
+
"type": "object",
|
|
201
|
+
"properties": {
|
|
202
|
+
"parent_dir": {
|
|
203
|
+
"type": "string",
|
|
204
|
+
"description": "Parent directory",
|
|
205
|
+
},
|
|
206
|
+
"canvas_name": {
|
|
207
|
+
"type": "string",
|
|
208
|
+
"description": "Canvas name to check",
|
|
209
|
+
},
|
|
210
|
+
},
|
|
211
|
+
"required": ["parent_dir", "canvas_name"],
|
|
212
|
+
},
|
|
213
|
+
),
|
|
214
|
+
]
|
|
215
|
+
|
|
216
|
+
|
|
217
|
+
__all__ = ["get_tool_schemas"]
|
|
218
|
+
|
|
219
|
+
# EOF
|
|
@@ -161,7 +161,7 @@ def validate_figure_json(fig_json: Dict[str, Any]) -> bool:
|
|
|
161
161
|
|
|
162
162
|
Examples
|
|
163
163
|
--------
|
|
164
|
-
>>> from scitex.
|
|
164
|
+
>>> from scitex.canvas.backend import validate_figure_json
|
|
165
165
|
>>> fig_json = {"width_mm": 180, "height_mm": 120, "axes": []}
|
|
166
166
|
>>> validate_figure_json(fig_json)
|
|
167
167
|
True
|
scitex/{fig → canvas}/canvas.py
RENAMED
|
@@ -1,16 +1,15 @@
|
|
|
1
1
|
#!/usr/bin/env python3
|
|
2
|
-
# -*- coding: utf-8 -*-
|
|
3
2
|
# Timestamp: 2025-12-08
|
|
4
3
|
# File: ./src/scitex/vis/canvas.py
|
|
5
4
|
"""
|
|
6
|
-
Canvas class for scitex.
|
|
5
|
+
Canvas class for scitex.canvas.
|
|
7
6
|
|
|
8
7
|
Provides object-oriented interface to canvas operations.
|
|
9
8
|
"""
|
|
10
9
|
|
|
11
|
-
from pathlib import Path
|
|
12
|
-
from typing import Dict, Any, Union, List, Optional
|
|
13
10
|
from datetime import datetime
|
|
11
|
+
from pathlib import Path
|
|
12
|
+
from typing import Any, Dict, List, Union
|
|
14
13
|
|
|
15
14
|
|
|
16
15
|
class Canvas:
|
|
@@ -35,8 +34,8 @@ class Canvas:
|
|
|
35
34
|
>>> # Create canvas
|
|
36
35
|
>>> canvas = stx.vis.Canvas("fig1", width_mm=180, height_mm=120)
|
|
37
36
|
>>> # Add panels
|
|
38
|
-
>>> canvas.add_panel("panel_a", "plot.png",
|
|
39
|
-
>>> canvas.add_panel("panel_b", "chart.png",
|
|
37
|
+
>>> canvas.add_panel("panel_a", "plot.png", xy_mm=(10, 10), size_mm=(80, 50), label="A")
|
|
38
|
+
>>> canvas.add_panel("panel_b", "chart.png", xy_mm=(100, 10), size_mm=(80, 50), label="B")
|
|
40
39
|
>>> # Save (auto-exports PNG/PDF/SVG)
|
|
41
40
|
>>> stx.io.save(canvas, "/output/fig1.canvas")
|
|
42
41
|
"""
|
|
@@ -82,8 +81,8 @@ class Canvas:
|
|
|
82
81
|
self,
|
|
83
82
|
panel_name: str,
|
|
84
83
|
source: Union[str, Path],
|
|
85
|
-
|
|
86
|
-
|
|
84
|
+
xy_mm: tuple = (0, 0),
|
|
85
|
+
size_mm: tuple = (50, 50),
|
|
87
86
|
label: str = "",
|
|
88
87
|
**kwargs,
|
|
89
88
|
) -> "Canvas":
|
|
@@ -96,10 +95,10 @@ class Canvas:
|
|
|
96
95
|
Name for the panel
|
|
97
96
|
source : str or Path
|
|
98
97
|
Path to source file (PNG, JPG, SVG)
|
|
99
|
-
|
|
100
|
-
(x_mm, y_mm) position on canvas
|
|
101
|
-
|
|
102
|
-
(width_mm, height_mm) panel size
|
|
98
|
+
xy_mm : tuple
|
|
99
|
+
(x_mm, y_mm) position on canvas in millimeters
|
|
100
|
+
size_mm : tuple
|
|
101
|
+
(width_mm, height_mm) panel size in millimeters
|
|
103
102
|
label : str
|
|
104
103
|
Panel label (A, B, C...)
|
|
105
104
|
**kwargs
|
|
@@ -120,8 +119,8 @@ class Canvas:
|
|
|
120
119
|
panel_entry = {
|
|
121
120
|
"name": panel_name,
|
|
122
121
|
"type": panel_type,
|
|
123
|
-
"position": {"x_mm":
|
|
124
|
-
"size": {"width_mm":
|
|
122
|
+
"position": {"x_mm": xy_mm[0], "y_mm": xy_mm[1]},
|
|
123
|
+
"size": {"width_mm": size_mm[0], "height_mm": size_mm[1]},
|
|
125
124
|
"z_index": len(self._panels),
|
|
126
125
|
"rotation_deg": kwargs.get("rotation_deg", 0),
|
|
127
126
|
"opacity": kwargs.get("opacity", 1.0),
|
|
@@ -197,7 +197,7 @@ def extract_defaults_from_metadata(metadata):
|
|
|
197
197
|
# Extract traces information - check multiple possible locations
|
|
198
198
|
traces = metadata.get("traces", [])
|
|
199
199
|
|
|
200
|
-
# Also check axes[].lines (
|
|
200
|
+
# Also check axes[].lines (plot bundle format)
|
|
201
201
|
if not traces and isinstance(axes, list) and len(axes) > 0:
|
|
202
202
|
ax = axes[0]
|
|
203
203
|
lines = ax.get("lines", [])
|
|
@@ -225,7 +225,7 @@ def extract_defaults_from_metadata(metadata):
|
|
|
225
225
|
# Extract legend information from multiple possible locations
|
|
226
226
|
legend = metadata.get("legend", {})
|
|
227
227
|
|
|
228
|
-
# Also check selectable_regions.axes[0].legend (
|
|
228
|
+
# Also check selectable_regions.axes[0].legend (plot bundle format)
|
|
229
229
|
if not legend:
|
|
230
230
|
selectable = metadata.get("selectable_regions", {})
|
|
231
231
|
sel_axes = selectable.get("axes", [])
|
|
@@ -8,24 +8,21 @@
|
|
|
8
8
|
This module provides the main edit() function and supporting utilities for:
|
|
9
9
|
- Backend detection and selection (flask, dearpygui, qt, tkinter, mpl)
|
|
10
10
|
- Path resolution for figure files (.json, .csv, .png)
|
|
11
|
-
- Bundle resolution for .
|
|
11
|
+
- Bundle resolution for .plot and .figure formats
|
|
12
12
|
- Panel data loading for multi-panel figures
|
|
13
13
|
- Manual override handling (.manual.json)
|
|
14
14
|
"""
|
|
15
15
|
|
|
16
|
-
from .
|
|
17
|
-
from .backend_detector import (
|
|
18
|
-
detect_best_backend,
|
|
19
|
-
print_available_backends,
|
|
20
|
-
)
|
|
21
|
-
from .path_resolver import resolve_figure_paths
|
|
16
|
+
from .backend_detector import detect_best_backend, print_available_backends
|
|
22
17
|
from .bundle_resolver import (
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
18
|
+
resolve_figure_bundle,
|
|
19
|
+
resolve_layered_plot_bundle,
|
|
20
|
+
resolve_plot_bundle,
|
|
26
21
|
)
|
|
27
|
-
from .
|
|
22
|
+
from .editor_launcher import edit
|
|
28
23
|
from .manual_handler import compute_file_hash, save_manual_overrides
|
|
24
|
+
from .panel_loader import load_panel_data
|
|
25
|
+
from .path_resolver import resolve_figure_paths
|
|
29
26
|
|
|
30
27
|
__all__ = [
|
|
31
28
|
# Main entry point
|
|
@@ -36,9 +33,9 @@ __all__ = [
|
|
|
36
33
|
# Path resolution
|
|
37
34
|
"resolve_figure_paths",
|
|
38
35
|
# Bundle resolution
|
|
39
|
-
"
|
|
40
|
-
"
|
|
41
|
-
"
|
|
36
|
+
"resolve_plot_bundle",
|
|
37
|
+
"resolve_figure_bundle",
|
|
38
|
+
"resolve_layered_plot_bundle",
|
|
42
39
|
# Panel loading
|
|
43
40
|
"load_panel_data",
|
|
44
41
|
# Manual overrides
|
|
@@ -3,27 +3,31 @@
|
|
|
3
3
|
# Timestamp: "2025-12-14 (ywatanabe)"
|
|
4
4
|
# File: /home/ywatanabe/proj/scitex-code/src/scitex/fig/editor/edit/bundle_resolver.py
|
|
5
5
|
|
|
6
|
-
"""Bundle path resolution for .
|
|
6
|
+
"""Bundle path resolution for .plot and .figure formats."""
|
|
7
7
|
|
|
8
8
|
import json as json_module
|
|
9
9
|
import tempfile
|
|
10
10
|
import zipfile
|
|
11
11
|
from pathlib import Path
|
|
12
|
-
from typing import
|
|
12
|
+
from typing import Any, Dict, Optional, Tuple
|
|
13
13
|
|
|
14
|
-
__all__ = [
|
|
14
|
+
__all__ = [
|
|
15
|
+
"resolve_plot_bundle",
|
|
16
|
+
"resolve_figure_bundle",
|
|
17
|
+
"resolve_layered_plot_bundle",
|
|
18
|
+
]
|
|
15
19
|
|
|
16
20
|
|
|
17
|
-
def
|
|
21
|
+
def resolve_figure_bundle(path: Path, panel_index: int = 0) -> Tuple:
|
|
18
22
|
"""
|
|
19
|
-
Resolve paths from a .
|
|
23
|
+
Resolve paths from a .figure bundle (multi-panel figure).
|
|
20
24
|
|
|
21
|
-
Uses in-memory zip reading for .
|
|
25
|
+
Uses in-memory zip reading for .plot panels - no disk extraction.
|
|
22
26
|
|
|
23
27
|
Parameters
|
|
24
28
|
----------
|
|
25
29
|
path : Path
|
|
26
|
-
Path to .
|
|
30
|
+
Path to .figure bundle (.figure or .figure)
|
|
27
31
|
panel_index : int, optional
|
|
28
32
|
Index of panel to open (default: 0 for first panel)
|
|
29
33
|
|
|
@@ -33,41 +37,41 @@ def resolve_figz_bundle(path: Path, panel_index: int = 0) -> Tuple:
|
|
|
33
37
|
(json_path, csv_path, png_path, hitmap_path, bundle_spec, panel_info)
|
|
34
38
|
"""
|
|
35
39
|
spath = str(path)
|
|
36
|
-
|
|
40
|
+
figure_is_zip = False
|
|
37
41
|
|
|
38
42
|
# Handle ZIP vs directory for figz
|
|
39
|
-
if spath.endswith(
|
|
40
|
-
|
|
43
|
+
if spath.endswith(".figure") and not spath.endswith(".figure"):
|
|
44
|
+
figure_is_zip = True
|
|
41
45
|
if not path.exists():
|
|
42
|
-
raise FileNotFoundError(f"
|
|
43
|
-
# For
|
|
44
|
-
temp_dir = tempfile.mkdtemp(prefix=
|
|
45
|
-
with zipfile.ZipFile(path,
|
|
46
|
+
raise FileNotFoundError(f"Figure bundle not found: {path}")
|
|
47
|
+
# For figure zip, extract to access nested pltz
|
|
48
|
+
temp_dir = tempfile.mkdtemp(prefix="scitex_edit_figure_")
|
|
49
|
+
with zipfile.ZipFile(path, "r") as zf:
|
|
46
50
|
zf.extractall(temp_dir)
|
|
47
51
|
bundle_dir = Path(temp_dir)
|
|
48
52
|
for item in bundle_dir.iterdir():
|
|
49
|
-
if item.is_dir() and str(item).endswith(
|
|
53
|
+
if item.is_dir() and str(item).endswith(".figure"):
|
|
50
54
|
bundle_dir = item
|
|
51
55
|
break
|
|
52
56
|
else:
|
|
53
57
|
bundle_dir = Path(path)
|
|
54
58
|
if not bundle_dir.exists():
|
|
55
|
-
raise FileNotFoundError(f"
|
|
59
|
+
raise FileNotFoundError(f"Figure bundle directory not found: {bundle_dir}")
|
|
56
60
|
|
|
57
|
-
# Find nested
|
|
61
|
+
# Find nested plot bundles
|
|
58
62
|
panel_paths = []
|
|
59
63
|
panel_is_zip = []
|
|
60
64
|
|
|
61
65
|
for item in sorted(bundle_dir.iterdir(), key=lambda x: x.name):
|
|
62
|
-
if item.is_dir() and str(item).endswith(
|
|
66
|
+
if item.is_dir() and str(item).endswith(".plot"):
|
|
63
67
|
panel_paths.append(str(item))
|
|
64
68
|
panel_is_zip.append(False)
|
|
65
|
-
elif item.is_file() and str(item).endswith(
|
|
69
|
+
elif item.is_file() and str(item).endswith(".plot"):
|
|
66
70
|
panel_paths.append(str(item))
|
|
67
71
|
panel_is_zip.append(True)
|
|
68
72
|
|
|
69
73
|
if not panel_paths:
|
|
70
|
-
raise FileNotFoundError(f"No .
|
|
74
|
+
raise FileNotFoundError(f"No .plot panels found in figure bundle: {bundle_dir}")
|
|
71
75
|
|
|
72
76
|
# Validate panel index
|
|
73
77
|
if panel_index < 0 or panel_index >= len(panel_paths):
|
|
@@ -77,7 +81,7 @@ def resolve_figz_bundle(path: Path, panel_index: int = 0) -> Tuple:
|
|
|
77
81
|
panel_name = Path(selected_panel_path).name
|
|
78
82
|
print(f"Opening panel: {panel_name}")
|
|
79
83
|
if len(panel_paths) > 1:
|
|
80
|
-
print(f" (
|
|
84
|
+
print(f" (Figure contains {len(panel_paths)} panels)")
|
|
81
85
|
|
|
82
86
|
# Build panel info
|
|
83
87
|
panel_names = [Path(p).name for p in panel_paths]
|
|
@@ -86,19 +90,21 @@ def resolve_figz_bundle(path: Path, panel_index: int = 0) -> Tuple:
|
|
|
86
90
|
"panel_paths": panel_paths,
|
|
87
91
|
"panel_is_zip": panel_is_zip,
|
|
88
92
|
"current_index": panel_index,
|
|
89
|
-
"
|
|
90
|
-
"
|
|
91
|
-
"bundle_path":
|
|
93
|
+
"figure_dir": str(bundle_dir),
|
|
94
|
+
"figure_is_zip": figure_is_zip,
|
|
95
|
+
"bundle_path": (
|
|
96
|
+
str(path) if figure_is_zip else None
|
|
97
|
+
), # Original figure zip path for export/download
|
|
92
98
|
}
|
|
93
99
|
|
|
94
100
|
# Resolve the selected panel
|
|
95
|
-
result =
|
|
101
|
+
result = resolve_plot_bundle(Path(selected_panel_path))
|
|
96
102
|
return result + (panel_info,)
|
|
97
103
|
|
|
98
104
|
|
|
99
|
-
def
|
|
105
|
+
def resolve_plot_bundle(path: Path) -> Tuple:
|
|
100
106
|
"""
|
|
101
|
-
Resolve paths from a .
|
|
107
|
+
Resolve paths from a .plot bundle (directory or ZIP).
|
|
102
108
|
|
|
103
109
|
Supports both:
|
|
104
110
|
- Legacy format (single {basename}.json)
|
|
@@ -107,7 +113,7 @@ def resolve_pltz_bundle(path: Path) -> Tuple:
|
|
|
107
113
|
Parameters
|
|
108
114
|
----------
|
|
109
115
|
path : Path
|
|
110
|
-
Path to .
|
|
116
|
+
Path to .plot bundle (.plot or .plot)
|
|
111
117
|
|
|
112
118
|
Returns
|
|
113
119
|
-------
|
|
@@ -117,15 +123,15 @@ def resolve_pltz_bundle(path: Path) -> Tuple:
|
|
|
117
123
|
spath = str(path)
|
|
118
124
|
|
|
119
125
|
# Handle ZIP vs directory
|
|
120
|
-
if spath.endswith(
|
|
126
|
+
if spath.endswith(".plot") and not spath.endswith(".plot"):
|
|
121
127
|
if not path.exists():
|
|
122
128
|
raise FileNotFoundError(f"Bundle not found: {path}")
|
|
123
|
-
temp_dir = tempfile.mkdtemp(prefix=
|
|
124
|
-
with zipfile.ZipFile(path,
|
|
129
|
+
temp_dir = tempfile.mkdtemp(prefix="scitex_edit_")
|
|
130
|
+
with zipfile.ZipFile(path, "r") as zf:
|
|
125
131
|
zf.extractall(temp_dir)
|
|
126
132
|
bundle_dir = Path(temp_dir)
|
|
127
133
|
for item in bundle_dir.iterdir():
|
|
128
|
-
if item.is_dir() and str(item).endswith(
|
|
134
|
+
if item.is_dir() and str(item).endswith(".plot"):
|
|
129
135
|
bundle_dir = item
|
|
130
136
|
break
|
|
131
137
|
else:
|
|
@@ -136,7 +142,7 @@ def resolve_pltz_bundle(path: Path) -> Tuple:
|
|
|
136
142
|
# Check if this is a layered bundle (v2.0)
|
|
137
143
|
spec_path = bundle_dir / "spec.json"
|
|
138
144
|
if spec_path.exists():
|
|
139
|
-
return
|
|
145
|
+
return resolve_layered_plot_bundle(bundle_dir)
|
|
140
146
|
|
|
141
147
|
# === Legacy format ===
|
|
142
148
|
json_path = None
|
|
@@ -148,15 +154,17 @@ def resolve_pltz_bundle(path: Path) -> Tuple:
|
|
|
148
154
|
|
|
149
155
|
for f in bundle_dir.iterdir():
|
|
150
156
|
name = f.name
|
|
151
|
-
if name.endswith(
|
|
157
|
+
if name.endswith(".json") and not name.endswith(".manual.json"):
|
|
152
158
|
json_path = f
|
|
153
|
-
elif name.endswith(
|
|
159
|
+
elif name.endswith(".csv"):
|
|
154
160
|
csv_path = f
|
|
155
|
-
elif name.endswith(
|
|
161
|
+
elif name.endswith("_hitmap.png"):
|
|
156
162
|
hitmap_path = f
|
|
157
|
-
elif name.endswith(
|
|
163
|
+
elif name.endswith(".svg") and "_hitmap" not in name:
|
|
158
164
|
svg_path = f
|
|
159
|
-
elif
|
|
165
|
+
elif (
|
|
166
|
+
name.endswith(".png") and "_hitmap" not in name and "_overview" not in name
|
|
167
|
+
):
|
|
160
168
|
png_path = f
|
|
161
169
|
|
|
162
170
|
# Prefer SVG for display
|
|
@@ -164,7 +172,7 @@ def resolve_pltz_bundle(path: Path) -> Tuple:
|
|
|
164
172
|
png_path = svg_path
|
|
165
173
|
|
|
166
174
|
if json_path and json_path.exists():
|
|
167
|
-
with open(json_path,
|
|
175
|
+
with open(json_path, "r") as f:
|
|
168
176
|
bundle_spec = json_module.load(f)
|
|
169
177
|
|
|
170
178
|
return (
|
|
@@ -176,12 +184,12 @@ def resolve_pltz_bundle(path: Path) -> Tuple:
|
|
|
176
184
|
)
|
|
177
185
|
|
|
178
186
|
|
|
179
|
-
def
|
|
187
|
+
def resolve_layered_plot_bundle(bundle_dir: Path) -> Tuple:
|
|
180
188
|
"""
|
|
181
|
-
Resolve paths from a layered .
|
|
189
|
+
Resolve paths from a layered .plot bundle (v2.0 format).
|
|
182
190
|
|
|
183
191
|
Layered format structure:
|
|
184
|
-
plot.
|
|
192
|
+
plot.plot/
|
|
185
193
|
spec.json # Semantic
|
|
186
194
|
style.json # Appearance
|
|
187
195
|
{basename}.csv # Data
|
|
@@ -191,16 +199,16 @@ def resolve_layered_pltz_bundle(bundle_dir: Path) -> Tuple:
|
|
|
191
199
|
Parameters
|
|
192
200
|
----------
|
|
193
201
|
bundle_dir : Path
|
|
194
|
-
Path to .
|
|
202
|
+
Path to .plot bundle directory.
|
|
195
203
|
|
|
196
204
|
Returns
|
|
197
205
|
-------
|
|
198
206
|
tuple
|
|
199
207
|
(json_path, csv_path, png_path, hitmap_path, bundle_spec)
|
|
200
208
|
"""
|
|
201
|
-
from scitex.plt.io import
|
|
209
|
+
from scitex.plt.io import load_layered_plot_bundle
|
|
202
210
|
|
|
203
|
-
bundle_data =
|
|
211
|
+
bundle_data = load_layered_plot_bundle(bundle_dir)
|
|
204
212
|
spec_path = bundle_dir / "spec.json"
|
|
205
213
|
csv_path = None
|
|
206
214
|
png_path = None
|
|
@@ -216,11 +224,11 @@ def resolve_layered_pltz_bundle(bundle_dir: Path) -> Tuple:
|
|
|
216
224
|
if exports_dir.exists():
|
|
217
225
|
for f in exports_dir.iterdir():
|
|
218
226
|
name = f.name
|
|
219
|
-
if name.endswith(
|
|
227
|
+
if name.endswith("_hitmap.png"):
|
|
220
228
|
hitmap_path = f
|
|
221
|
-
elif name.endswith(
|
|
229
|
+
elif name.endswith(".svg") and "_hitmap" not in name:
|
|
222
230
|
png_path = f
|
|
223
|
-
elif name.endswith(
|
|
231
|
+
elif name.endswith(".png") and "_hitmap" not in name and png_path is None:
|
|
224
232
|
png_path = f
|
|
225
233
|
|
|
226
234
|
bundle_spec = bundle_data.get("merged", {})
|