cellpy 2.1.2a3__tar.gz → 2.1.2a4__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.
- cellpy-2.1.2a4/.issueflows/03-solved-issues/issue862_original.md +45 -0
- cellpy-2.1.2a4/.issueflows/03-solved-issues/issue862_plan.md +90 -0
- cellpy-2.1.2a4/.issueflows/03-solved-issues/issue862_status.md +28 -0
- cellpy-2.1.2a4/.issueflows/03-solved-issues/issue863_original.md +35 -0
- cellpy-2.1.2a4/.issueflows/03-solved-issues/issue863_plan.md +103 -0
- cellpy-2.1.2a4/.issueflows/03-solved-issues/issue863_status.md +33 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/test-registry.md +8 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/HISTORY.md +2 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/PKG-INFO +1 -1
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/collect/__init__.py +4 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/collect/collection.py +2 -2
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/collect/collector.py +8 -0
- cellpy-2.1.2a4/cellpy/collect/dva.py +95 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/collect/options.py +10 -1
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/ica.py +30 -55
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/backends/mpl.py +13 -4
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/backends/plotly.py +12 -4
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/collected.py +77 -1
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/config_declarations.py +8 -8
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.aliases +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/commands/build.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/commands/create-original-issue-file.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/rules/cellpy-core-migration.mdc +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/rules/cellpy-workspace.mdc +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/rules/graphify.mdc +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/rules/issueflow-rules.mdc +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/rules/kiss.mdc +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/rules/this-project.mdc +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/caveman/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/gh-ci/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/grill-me/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-archive/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-auto/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-build/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-cleanup/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-close/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-comments/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-cycle/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-doctor/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-epic/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-fix/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-graphify/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-history-update/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-init/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-issue/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-pause/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-pick/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-plan/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-review/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-status/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-version-bump/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/iflow-yolo/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.cursor/skills/issueflow-build/SKILL.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.dockerignore +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.editorconfig +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.env_example +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.gitattributes +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.gitignore +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/00-tools/.gitkeep +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/00-tools/README.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/00-tools/migrate_prms_calls.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/00-tools/scan_hardcoded_headers.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/00-tools/scan_member_usage.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/01-current-issues/.gitkeep +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/02-partly-solved-issues/.gitkeep +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/.gitkeep +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/2026-07-09_archived_issues.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/2026-07-31_archived_issues.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/cycle_status_2026-07-31.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/cycle_status_2026-08-08.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/cycle_status_2026-08-09.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue459_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue786_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue786_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue786_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue799_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue799_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue799_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue800_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue800_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue800_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue801_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue801_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue801_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue802_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue802_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue802_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue804_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue804_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue804_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue809_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue809_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue809_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue816_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue816_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue816_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue817_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue817_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue817_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue818_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue818_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue818_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue819_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue819_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue819_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue820_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue820_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue820_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue821_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue821_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue821_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue822_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue822_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue822_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue825_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue825_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue825_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue837_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue837_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue837_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue839_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue839_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue839_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue845_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue845_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue845_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue846_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue846_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue846_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue849_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue849_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue849_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue850_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue850_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue850_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue851_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue851_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue851_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue853_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue853_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue853_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue855_original.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue855_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/03-solved-issues/issue855_status.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/.gitkeep +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/atomic-file-writes.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/batch-load-orchestrator.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/bdf-export.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/build-and-versioning.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/cellpy-v2-architecture.excalidraw +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/cellpy-v2-branching.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/cellpy-v2-epic.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/cellpy-workspace-repos.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/cellpycell-di-restructuring.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/ci-tiers.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/cli-api-echo-binder.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/cli-light-startup.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/docs-on-master.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/essential-tests.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/filters-and-plot-filtering.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/harmonized-raw-default.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/marimo-docs.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/otherpath-upath.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/plotting-backends.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/plotting-batch-summary.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/plotting-collected.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/plotting-cycle-legend.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/plotting-prepare.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/plotting-registry.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/release-procedure.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/testing-and-coverage.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/this-project.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/04-designs-and-guides/v2-cellpycore-pin-gate.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/05-epics/.gitkeep +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/05-epics/epic567_plan.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.issueflows/config.toml +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/.readthedocs.yaml +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/AGENTS.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/AUTHORS.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/CODE_OF_CONDUCT.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/CONTRIBUTING.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/DEPRECATIONS.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/LICENSE.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/README.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_developers_guide/dev_cellpy_data_structure.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_developers_guide/dev_cellpy_folder_structure.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_developers_guide/dev_cellpy_packaging_pypi.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_developers_guide/dev_cellpy_setup.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_developers_guide/dev_conda_package.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_developers_guide/dev_docs.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_developers_guide/dev_loaders_and_instruments.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_developers_guide/dev_various.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_developers_guide/index.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/basic_interactions/01_getting_started_tutorial.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/basic_interactions/02_read_cell_data.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/basic_interactions/03_more_about_get.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/basic_interactions/04_other_interactions.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/basic_interactions/05_configuring.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/basic_interactions/06_pandas.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/basic_interactions/07_data_mining.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/basic_interactions/08_the_cellpy_cmd.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/basics.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/examples.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/index.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/loaders/01_arbin.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/loaders/02_maccor.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/loaders/03_PEC.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/loaders/04_Neware.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/loaders/05_biologics.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/loaders/06_custom.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/loaders.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/notebooks/images/templates_jupyterlab_001.png +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/notebooks/images/templates_jupyterlab_002.png +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/notebooks/tutorial_get_cap.ipynb +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/notebooks/tutorial_simple_plot.ipynb +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/notebooks/tutorial_templates.ipynb +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/notebooks/tutorial_xxx-checkpoint.ipynb +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/notebooks.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/tips_and_tricks.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/utils/batch.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/utils/collectors.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/utils/custom_file_loaders.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/utils/easyplot.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/utils/figures/tutorials_utils_plotting_fig1.png +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/utils/figures/tutorials_utils_plotting_fig2.png +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/utils/ica.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/utils/plotting.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/utils/templates.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/utils/tut_ocv_rlx.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_examples_and_tutorials/utils.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_main_description/formats.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_main_description/index.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_main_description/installation.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/_main_description/usage.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/_old_docs/index.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/benchmarks/README.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/benchmarks/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/benchmarks/baselines/v1x_ubuntu_py313.json +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/benchmarks/check_baseline.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/benchmarks/conftest.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/benchmarks/paths.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/benchmarks/test_performance.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/_deprecation.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/_version.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/_dbengine.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/aggregate.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/db.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/facade.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/journal.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/layout.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/outputs.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/policy.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/qc.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/result.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/runner.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/batch/store.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/cli.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/cli_api.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/collect/_summary_ops.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/collect/cells.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/collect/curves.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/collect/ica.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/collect/summary.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/config/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/config/credentials.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/config/legacy.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/config/loader.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/config/migrate.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/config/models.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/config/reference.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/config/session.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/config/sources.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/config/types.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/exceptions.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/exporters/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/exporters/bdf.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/exporters/tabular.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/filters/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/filters/cycles.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/filters/summary.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/internals/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/internals/connections.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/internals/otherpath.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/apipkg/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/apipkg/_alias_module.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/apipkg/_importing.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/apipkg/_module.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/apipkg/_syncronized.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/apipkg/_version.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/apipkg/py.typed +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/local_fastnda/LICENSE +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/local_fastnda/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/local_fastnda/btsda.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/local_fastnda/cli.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/local_fastnda/dicts.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/local_fastnda/formats.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/local_fastnda/main.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/local_fastnda/nda.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/local_fastnda/ndax.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/local_fastnda/utils.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/libs/local_fastnda/version.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/log.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/logging.json +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/parameters/.cellpy_prms_default.conf +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/parameters/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/parameters/cell_schema.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/parameters/internal_settings.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/parameters/legacy/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/parameters/legacy/update_headers.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/parameters/prmreader.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/parameters/prms.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/backends/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/backends/base.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/batch_summary.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/context.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/cycle_legend.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/figures.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/headers.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/labels.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/prepare/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/prepare/curves.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/prepare/ica.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/prepare/raw.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/prepare/steps.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/prepare/summary.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/registry.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/spec.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/plotting/theme.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/capacity_curves.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/atomic.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/dtype.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/fids.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/format.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/keys.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/legacy_read.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/meta.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/meta_archive.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/read.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/selectors.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/translate.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/v9.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellpy_file/write.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/cellreader.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/data_structures.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/dbreader.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/do.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/filefinder.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/SQL Table IDs.txt +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/_aux_map.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/arbin_res.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/arbin_sql.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/arbin_sql_7.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/arbin_sql_config.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/arbin_sql_csv.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/arbin_sql_h5.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/arbin_sql_xlsx.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/base.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/batmo_bdf.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/biologics_mpr.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/configurations/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/configurations/batmo_bdf_bdf.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/configurations/maccor_txt_one.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/configurations/maccor_txt_three.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/configurations/maccor_txt_two.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/configurations/maccor_txt_zero.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/configurations/neware_txt_one.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/configurations/neware_txt_two.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/configurations/neware_txt_zero.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/contract.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/custom.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/declarations.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/ext_nda_reader.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/harmonize.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/hooks.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/loader_specific_modules/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/loader_specific_modules/biologic_file_format.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/local_instrument.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/maccor_txt.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/maccor_txt_native.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/neware_nda.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/neware_txt.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/neware_xlsx.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/pec_csv.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/processors/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/processors/post_processors.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/processors/pre_processors.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/registry.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/instruments/testing.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/journal_layer.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/json_dbreader.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/merger.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/meta_resolver.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/native_core.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/provenance.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/slicing.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/sql_dbreader.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/readers/test_meta.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/units.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/utils/__init__.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/utils/batch.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/utils/collectors.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/utils/diagnostics.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/utils/example_data.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/utils/helpers.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/utils/ica.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/utils/live.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/utils/ocv_rlx.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/utils/plotutils.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/utils/processor.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/cellpy/utils/template_registry.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/backfill_notebook_plotly_pngs.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/conda-recipes/README.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/conda-recipes/cellpy/meta.yaml +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/conda-recipes/cellpycore/meta.yaml +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/make_bad_fixtures.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/plot_preview_common.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/preview_curve_plots.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/preview_ica_plots.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/preview_plots.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/preview_summary_plots.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/regenerate_goldens.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/render_example_notebooks.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/snapshot_cli_surface.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/dev/snapshot_figure_specs.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/docker/Dockerfile.build-test +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/docker/sftp-test/README.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/docker/sftp-test/compose.yml +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/docker/sftp-test/data/hello.txt +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/docker/sftp-test/data/nested/sample.txt +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/environment.yml +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/environment_dev.yml +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/github_actions_environment.yml +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/noxfile.py +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/paper/.github/workflows/draft-pdf.yml +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/paper/.gitignore +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/paper/Figures/Cellpy-Utils.jpg +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/paper/Figures/CellpyCell.jpg +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/paper/Figures/CellpyData.jpg +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/paper/paper.bib +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/paper/paper.md +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/pyproject.toml +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/scripts/build_test.sh +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/scripts/dev_sync.sh +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/uv.lock +0 -0
- {cellpy-2.1.2a3 → cellpy-2.1.2a4}/zensical.toml +0 -0
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
# Issue #862: dva_plot(direction='both') does not distinguish the half-cycles visually (ica_plotter does)
|
|
2
|
+
|
|
3
|
+
Source: https://github.com/jepegit/cellpy/issues/862
|
|
4
|
+
|
|
5
|
+
## Original issue text
|
|
6
|
+
|
|
7
|
+
**cellpy version:** 2.1.2a3
|
|
8
|
+
|
|
9
|
+
## Summary
|
|
10
|
+
|
|
11
|
+
`ica_plotter` gained a visual distinction for `direction="both"` in #821 — the charge lobe is dashed (`line_dash`), so the two half-cycles are separable at a glance. `dva_plot(direction="both")` overlays both half-cycles too, but draws them **identically**: same colour, same trace name, no dash.
|
|
12
|
+
|
|
13
|
+
Only the hover tells them apart. On a static export (PNG/SVG/PDF for a report) that information is gone entirely.
|
|
14
|
+
|
|
15
|
+
## Reproduction
|
|
16
|
+
|
|
17
|
+
```python
|
|
18
|
+
import json, plotly.io as pio
|
|
19
|
+
from cellpy.utils.plotutils import dva_plot
|
|
20
|
+
from cellpy.utils import example_data
|
|
21
|
+
|
|
22
|
+
cell = example_data.cellpy_file()
|
|
23
|
+
fig = json.loads(pio.to_json(dva_plot(cell, cycles=[1], direction="both", backend="plotly")))
|
|
24
|
+
for t in fig["data"]:
|
|
25
|
+
print(t["name"], t["line"], t.get("showlegend"))
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
```
|
|
29
|
+
1 {'color': 'rgb(68, 1, 84)', 'width': 1.5} True
|
|
30
|
+
1 {'color': 'rgb(68, 1, 84)', 'width': 1.5} False
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
Both traces: same `name`, same `legendgroup`, same colour, `dash` unset. Compare `ica_plotter(..., direction="both")`, which yields `1, charge` / `1, discharge` with `dash='dot'` on one of them.
|
|
34
|
+
|
|
35
|
+
The hover *is* correct — `customdata[1]` carries `charge`/`discharge` and the template shows it — so this is purely about the visual encoding.
|
|
36
|
+
|
|
37
|
+
## Why it matters for apps
|
|
38
|
+
|
|
39
|
+
We're adding a DVA view to [cellpy-simple-gui](https://github.com/cellpy/cellpy-simple-gui) next to the existing ICA view. Same "Both" control, same user expectation, but two different behaviours: ICA is readable, DVA looks like a single doubled-back curve. We'll dash the discharge half app-side for now, which is exactly the kind of divergence #821 removed for ICA.
|
|
40
|
+
|
|
41
|
+
## Suggested fix
|
|
42
|
+
|
|
43
|
+
Apply the #821 treatment in `dva_plot`: `line_dash` per direction (and ideally `"<cycle>, charge"` / `"<cycle>, discharge"` names, matching `ica_plotter`), so the two families stay consistent with each other.
|
|
44
|
+
|
|
45
|
+
Happy to send a PR if you'd like.
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
# Plan — Issue #862: dva_plot(direction='both') does not distinguish half-cycles visually
|
|
2
|
+
|
|
3
|
+
## Goal
|
|
4
|
+
|
|
5
|
+
Make charge vs discharge half-cycles visually distinguishable (not just via hover) when `direction="both"` in `dva_plot` — and, since it's the same code path, in `ica_plot` too.
|
|
6
|
+
|
|
7
|
+
## Investigation note (corrects the issue's framing)
|
|
8
|
+
|
|
9
|
+
`ica_plot` and `dva_plot` (`cellpy/utils/plotutils.py`) both route through the same shared
|
|
10
|
+
`prepare` (`cellpy/plotting/prepare/ica.py`) → `_render_ica_dva` renderer (one method per
|
|
11
|
+
backend: [`PlotlyBackend._render_ica_dva`](cellpy/plotting/backends/plotly.py) and
|
|
12
|
+
[`MatplotlibBackend._render_ica_dva`](cellpy/plotting/backends/mpl.py)). Reproduced with the
|
|
13
|
+
example cell: **`ica_plot(direction="both")` currently has the identical bug** — both docstrings
|
|
14
|
+
say outright "Line style is shared across charge and discharge." The issue's comparison is to
|
|
15
|
+
`cellpy.plotting.collected.ica_plotter` (the separate `Collection.plot` family-kind path fixed
|
|
16
|
+
in #821, `line_dash=direction_col` via `px.line`), not to `plotutils.ica_plot`.
|
|
17
|
+
|
|
18
|
+
Net effect: this is a **one-shared-fix** — patching `_render_ica_dva` fixes both `ica_plot` and
|
|
19
|
+
`dva_plot` at once, and they stay consistent with each other by construction (no per-kind
|
|
20
|
+
special-casing needed).
|
|
21
|
+
|
|
22
|
+
## Constraints
|
|
23
|
+
|
|
24
|
+
- Keep the fix minimal: line style only (dash), not a legend/trace-naming overhaul. The issue's
|
|
25
|
+
"ideally `<cycle>, charge` / `<cycle>, discharge` names" is explicitly a nice-to-have
|
|
26
|
+
("ideally"), and both backends currently key their legend/colorbar by **cycle** (color), grouped
|
|
27
|
+
across directions — renaming would double legend entries per cycle. Out of scope here.
|
|
28
|
+
- Match the #821 convention already established in `collected.py` for consistency across the
|
|
29
|
+
codebase: charge = solid, discharge = dotted (`px.line`'s default dash sequence gives the first
|
|
30
|
+
category `"solid"`, second `"dot"`, and `"charge"` < `"discharge"` alphabetically).
|
|
31
|
+
- Both backends (plotly + matplotlib) must get the fix — the issue only mentions plotly exports,
|
|
32
|
+
but the mpl backend has the identical "shared line style" bug and docstring.
|
|
33
|
+
- Do not change trace/line count, names, or hover content — `tests/data/figure_specs.json`
|
|
34
|
+
(structural snapshot, #567) does not record line style, so no golden-file update is needed as
|
|
35
|
+
long as trace count/names/axes are untouched.
|
|
36
|
+
|
|
37
|
+
### Prior art
|
|
38
|
+
|
|
39
|
+
- `cellpy/plotting/collected.py::sequence_plotter` (#821 fix, lines ~573-580): sets
|
|
40
|
+
`plotly_arguments["line_dash"] = direction_col` when `direction == "both"`, for the *separate*
|
|
41
|
+
`Collection.plot(family_kind="ica")` path. Same convention (dash keyed by the `direction`
|
|
42
|
+
column values `"charge"` / `"discharge"` from `cellpy.ica.CHARGE` / `cellpy.ica.DISCHARGE`) is
|
|
43
|
+
reused here, but applied manually (since `_render_ica_dva` builds `go.Scatter` traces directly,
|
|
44
|
+
not through `px.line`).
|
|
45
|
+
- `tests/test_collected_ica_direction.py::test_ica_line_direction_both_overlays_without_coerce` —
|
|
46
|
+
existing pattern for asserting `{tr.line.dash for tr in fig.data}` has ≥2 distinct values;
|
|
47
|
+
mirror this style for the new plotutils-level test.
|
|
48
|
+
|
|
49
|
+
## Approach
|
|
50
|
+
|
|
51
|
+
1. **Plotly backend** (`cellpy/plotting/backends/plotly.py::PlotlyBackend._render_ica_dva`):
|
|
52
|
+
in the `for (cycle, direction), group in frame.groupby(group_cols, ...)` loop, compute
|
|
53
|
+
`dash = "dot" if direction == DISCHARGE else "solid"` and pass `dash=dash` into the existing
|
|
54
|
+
`line=dict(color=color, width=1.5)` dict. Import `CHARGE, DISCHARGE` from `cellpy.ica`
|
|
55
|
+
(`ICA_COLS` is already imported there).
|
|
56
|
+
2. **Matplotlib backend** (`cellpy/plotting/backends/mpl.py::MatplotlibBackend._render_ica_dva`):
|
|
57
|
+
in the `for (cycle, _direction), group in frame.groupby(...)` loop, rename `_direction` to
|
|
58
|
+
`direction`, compute `linestyle = ":" if direction == DISCHARGE else "-"`, pass
|
|
59
|
+
`linestyle=linestyle` to `ax.plot(...)`.
|
|
60
|
+
3. **Docstrings** — update both `_render_ica_dva` docstrings' "Line style is shared across charge
|
|
61
|
+
and discharge" line to describe the new dash/linestyle behaviour.
|
|
62
|
+
4. **Tests** — add to `tests/test_ica_plot_prepare.py`:
|
|
63
|
+
- `test_ica_plot_both_direction_dash_differs` (and `dva_plot` equivalent, or parametrized over
|
|
64
|
+
both) for the plotly backend: call `ica_plot`/`dva_plot(direction="both", backend="plotly")`,
|
|
65
|
+
assert `{tr.line.dash for tr in fig.data}` has at least 2 distinct values.
|
|
66
|
+
- matplotlib equivalent: assert `{line.get_linestyle() for line in fig.get_axes()[0].get_lines()}`
|
|
67
|
+
has at least 2 distinct values for `direction="both"`.
|
|
68
|
+
- A `direction="charge"` (single-direction) sanity check that dash stays `"solid"`/`"-"` for
|
|
69
|
+
both kinds, guarding against a future regression that always-dashes regardless of direction.
|
|
70
|
+
|
|
71
|
+
## Files to touch
|
|
72
|
+
|
|
73
|
+
- `cellpy/plotting/backends/plotly.py` — `PlotlyBackend._render_ica_dva`: add per-direction dash.
|
|
74
|
+
- `cellpy/plotting/backends/mpl.py` — `MatplotlibBackend._render_ica_dva`: add per-direction linestyle.
|
|
75
|
+
- `tests/test_ica_plot_prepare.py` — new direction/dash tests.
|
|
76
|
+
- `HISTORY.md` (at `/iflow-close`, per project convention) — patch-level fix note.
|
|
77
|
+
|
|
78
|
+
## Test strategy
|
|
79
|
+
|
|
80
|
+
- `uv run pytest tests/test_ica_plot_prepare.py -m essential` for the fast path; then the
|
|
81
|
+
documented merge gate `uv run pytest -m essential` (per `AGENTS.md`).
|
|
82
|
+
- Plotting tests run fine outside `MPLBACKEND=Agg` requirement here since this repo's local dev
|
|
83
|
+
loop uses conda per project rules — will run via the activated `cellpy_dev_313` env (or `uv run`
|
|
84
|
+
if conda isn't needed locally); confirm whichever is available in the close step actually runs.
|
|
85
|
+
- Manually re-run the issue's repro snippet for both `ica_plot` and `dva_plot` to confirm dash
|
|
86
|
+
values differ and match before/after.
|
|
87
|
+
|
|
88
|
+
## Open questions
|
|
89
|
+
|
|
90
|
+
None — scope, convention (match #821), and file list are all resolved from the codebase itself.
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
# Status — Issue #862
|
|
2
|
+
|
|
3
|
+
- [x] Done
|
|
4
|
+
|
|
5
|
+
## What's done
|
|
6
|
+
|
|
7
|
+
- Investigated and confirmed `ica_plot` and `dva_plot` share the same `_render_ica_dva`
|
|
8
|
+
renderer (plotly + mpl) and both currently lacked dash distinction for `direction="both"`
|
|
9
|
+
(the issue's "ica_plotter already does this" comparison was to the separate
|
|
10
|
+
`cellpy.plotting.collected.ica_plotter`, fixed in #821 — a different code path).
|
|
11
|
+
- Plan written (`issue862_plan.md`), accepted.
|
|
12
|
+
- `PlotlyBackend._render_ica_dva` (`cellpy/plotting/backends/plotly.py`): dash keyed by
|
|
13
|
+
direction (`charge` solid, `discharge` dotted) whenever both directions are overlaid in the
|
|
14
|
+
frame; single-direction plots stay solid.
|
|
15
|
+
- `MatplotlibBackend._render_ica_dva` (`cellpy/plotting/backends/mpl.py`): same behaviour via
|
|
16
|
+
`linestyle` (`"-"` / `":"`).
|
|
17
|
+
- Docstrings updated on both renderers.
|
|
18
|
+
- New tests in `tests/test_ica_plot_prepare.py`: dash/linestyle differ for `direction="both"`
|
|
19
|
+
(both `ica_plot` and `dva_plot`, both backends), and stays solid for a single direction.
|
|
20
|
+
- `uv run pytest tests/test_ica_plot_prepare.py`, related plotting tests (49 passed), and the
|
|
21
|
+
full `uv run pytest -m essential` merge gate (698 passed, 1 skipped, 2 xfailed, 1 xpassed, no
|
|
22
|
+
regressions) all green with `MPLBACKEND=Agg`.
|
|
23
|
+
- `black --diff` / `flake8` on touched files: only pre-existing, unrelated findings (line-length
|
|
24
|
+
config mismatch); no new issues from this change.
|
|
25
|
+
|
|
26
|
+
## Remaining work
|
|
27
|
+
|
|
28
|
+
None.
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
# Issue #863: No collect_dva: DVA is single-cell only, unlike summaries/cycles/ICA
|
|
2
|
+
|
|
3
|
+
Source: https://github.com/jepegit/cellpy/issues/863
|
|
4
|
+
|
|
5
|
+
## Original issue text
|
|
6
|
+
|
|
7
|
+
**cellpy version:** 2.1.2a3
|
|
8
|
+
|
|
9
|
+
## Summary
|
|
10
|
+
|
|
11
|
+
`cellpy.collect` exposes `collect_summaries`, `collect_cycles` and `collect_ica`, each returning a `Collection` that spans a batch of cells and plots through the collected path. **DVA has no equivalent** — `dva_plot(cell, ...)` takes a single cell, so differential voltage is the one analysis family that cannot be compared across cells.
|
|
12
|
+
|
|
13
|
+
```python
|
|
14
|
+
>>> import cellpy.collect as C
|
|
15
|
+
>>> [hasattr(C, f"collect_{k}") for k in ("summaries", "cycles", "ica", "dva")]
|
|
16
|
+
[True, True, True, False]
|
|
17
|
+
```
|
|
18
|
+
|
|
19
|
+
The `dva` plot family *is* registered (`registry.get("dva")` → `extras={'entry_point': 'dva_plot', 'kind': 'dva'}`), which makes the gap easy to trip over: the family shows up in the registry alongside `ica`, but there is no collector behind it.
|
|
20
|
+
|
|
21
|
+
## Why it matters for apps
|
|
22
|
+
|
|
23
|
+
We just added a DVA view to [cellpy-simple-gui](https://github.com/cellpy/cellpy-simple-gui) next to the existing ICA view. ICA gets the full collected treatment — multiple cells, grouping, group-averaging, the whole `Collection` API. DVA had to be wired as a one-cell-at-a-time special case straight onto `dva_plot`, which means:
|
|
24
|
+
|
|
25
|
+
- no multi-cell DVA comparison, though that is exactly what you want when screening electrode formulations;
|
|
26
|
+
- a second code path in the app, with its own export (`dva_plot(return_data=True)` returns pandas, while collections are polars);
|
|
27
|
+
- the two sibling views behave differently for no reason the user can see.
|
|
28
|
+
|
|
29
|
+
`ica.dvdq` already produces the tidy per-cell frame (`cycle`, `direction`, `capacity`, `voltage`, `dvdq`), so the missing piece looks like the collector wrapper rather than the analysis.
|
|
30
|
+
|
|
31
|
+
## Wish
|
|
32
|
+
|
|
33
|
+
A `collect_dva(batch, options=IcaOptions(...))` returning a `Collection` the same way `collect_ica` does — same `Collection.plot()` entry, same grouping/spread behaviour, same polars frame for export. That would let apps treat ICA and DVA as the two halves of one feature instead of two unrelated ones.
|
|
34
|
+
|
|
35
|
+
Happy to help if useful.
|
|
@@ -0,0 +1,103 @@
|
|
|
1
|
+
# Plan — Issue #863: No collect_dva (DVA is single-cell only)
|
|
2
|
+
|
|
3
|
+
## Goal
|
|
4
|
+
|
|
5
|
+
Add `cellpy.collect.collect_dva(batch, options=IcaOptions(...))` returning a `Collection`,
|
|
6
|
+
mirroring `collect_ica`, so DVA gets the same multi-cell `Collection.plot()` / grouping /
|
|
7
|
+
save / export treatment as summaries/cycles/ICA.
|
|
8
|
+
|
|
9
|
+
## Constraints
|
|
10
|
+
|
|
11
|
+
- Reuse the existing `cellpy.collect.options.IcaOptions` dataclass for both ICA and DVA (per
|
|
12
|
+
the issue's own proposed signature) rather than inventing a `DvaOptions` — add the one field
|
|
13
|
+
DVA actually needs (`capacity_resolution`) instead of a parallel dataclass.
|
|
14
|
+
- Match `collect_ica`'s per-cell cycle-isolation behaviour exactly (cycles resolved from the
|
|
15
|
+
*originally requested* set every iteration — the legacy cross-cell narrowing bug,
|
|
16
|
+
collectors.py:1691 — must not regress for DVA either).
|
|
17
|
+
- `Collection.plot()` must work out of the box for a DVA collection (`kind="dva"`) — currently
|
|
18
|
+
`Collection._FAMILY` has no `"dva"` entry (falls back to `"cycles"`, wrong columns) and
|
|
19
|
+
`render_collected` has no `family_kind == "dva"` branch (falls through to raw
|
|
20
|
+
`sequence_plotter` without ICA/DVA column defaults). Both must be wired, or `collect_dva(...).plot()`
|
|
21
|
+
breaks immediately — this is the same gap the issue calls out for the *plot family registry*
|
|
22
|
+
(`registry.get("dva")` already exists) vs the *collector*.
|
|
23
|
+
- Correct resolution knob: `cellpy.ica.dqdv` differentiates along **voltage** (needs `voltage_resolution`
|
|
24
|
+
for the q(V) interpolation); `cellpy.ica.dvdq` differentiates along **capacity** (needs
|
|
25
|
+
`capacity_resolution` for the V(q) interpolation, per `cellpy.ica.IcaOptions` docstring +
|
|
26
|
+
`dvdq`'s own docstring: "differentiates the smoothed V(q) curve"). `collect_ica` forwards
|
|
27
|
+
`voltage_resolution`; `collect_dva` must forward `capacity_resolution`, not `voltage_resolution`.
|
|
28
|
+
- Follow the existing one-file-per-collect-family convention (`cells.py`, `curves.py`, `ica.py`,
|
|
29
|
+
`summary.py`) — new `cellpy/collect/dva.py`, not a growing `ica.py`.
|
|
30
|
+
- Keep the legacy `BatchCollector` convenience-wrapper parity too (`ica_collector` exists
|
|
31
|
+
alongside `collect_ica`) — add `dva_collector` for symmetry; it is a 5-line wrapper.
|
|
32
|
+
|
|
33
|
+
### Prior art
|
|
34
|
+
|
|
35
|
+
- `cellpy/collect/ica.py::collect_ica` — the function to mirror almost line-for-line: per-cell
|
|
36
|
+
`iter_cells` loop, per-cell cycle isolation via the *originally requested* tuple, `_as_polars`
|
|
37
|
+
conversion, `pl.concat(..., how="diagonal_relaxed")`, `opts.transforms` post-hooks,
|
|
38
|
+
`CollectionMeta(kind=..., options={...}, cells_included=...)`.
|
|
39
|
+
- `cellpy/plotting/collected.py::ica_plotter` (wraps `_cycles_plotter` with
|
|
40
|
+
`x="voltage", y="dqdv", z="cycle", g="cell"`) — mirror as `dva_plotter` with
|
|
41
|
+
`x="capacity", y="dvdq"` (labels/units swapped: "Capacity"/"mAh/g" and "dV/dQ"/"V/(mAh/g)").
|
|
42
|
+
`_cycles_plotter` / `sequence_plotter` are already column-name-generic — no changes needed there.
|
|
43
|
+
- `cellpy/collect/collection.py::Collection._FAMILY` and
|
|
44
|
+
`cellpy/plotting/collected.py::render_collected` — both need a `"dva"` branch/entry (see
|
|
45
|
+
Constraints above).
|
|
46
|
+
- `cellpy/collect/collector.py::ica_collector` — mirror as `dva_collector`.
|
|
47
|
+
- `tests/test_collectors.py::test_ica_collector_uses_the_specced_frame` /
|
|
48
|
+
`test_ica_collector_film_mode` / `test_ica_collector_fig_pr_cycle` — mirror for DVA in a new
|
|
49
|
+
`tests/test_collect_dva.py` (or add alongside in `test_collectors.py`; matches existing
|
|
50
|
+
`populated_batch` fixture reuse pattern).
|
|
51
|
+
|
|
52
|
+
## Approach
|
|
53
|
+
|
|
54
|
+
1. `cellpy/collect/options.py::IcaOptions` — add `capacity_resolution: float | None = None`
|
|
55
|
+
field (alongside existing `cycles`, `voltage_resolution`, `transforms`).
|
|
56
|
+
2. New `cellpy/collect/dva.py::collect_dva(batch, options=None, **overrides) -> Collection`:
|
|
57
|
+
copy `collect_ica`'s structure, swap `ica.dqdv` → `ica.dvdq`, forward
|
|
58
|
+
`opts.capacity_resolution` (not `voltage_resolution`) into the per-cell call, `kind="dva"`,
|
|
59
|
+
`name=f"{batch.journal.name or 'batch'}_dva"`, `meta.options={"cycles": ..., "capacity_resolution": ...}`.
|
|
60
|
+
3. `cellpy/collect/collector.py` — add `dva_collector(batch, options=None, *, autorun=True, **overrides)`
|
|
61
|
+
convenience wrapper bound to `collect_dva` (mirrors `ica_collector`).
|
|
62
|
+
4. `cellpy/collect/__init__.py` — import/export `collect_dva`, `dva_collector`.
|
|
63
|
+
5. `cellpy/collect/collection.py::Collection._FAMILY` — add `"dva": "dva"`.
|
|
64
|
+
6. `cellpy/plotting/collected.py`:
|
|
65
|
+
- Add `dva_plotter(collected_curves, cycles_to_plot=None, backend="plotly", method="fig_pr_cell", direction="charge", **kwargs)`
|
|
66
|
+
mirroring `ica_plotter`, calling `_cycles_plotter(..., x="capacity", y="dvdq", z="cycle", g="cell", x_label="Capacity", x_unit="mAh/g", y_label="dV/dQ", y_unit="V/(mAh/g)", default_title="Differential Voltage Analysis Plots", ...)`.
|
|
67
|
+
- `render_collected`: add `if family_kind == "dva": return dva_plotter(frame, backend=backend, method=method, **opts)`.
|
|
68
|
+
- Update `collected_plot`'s docstring `family_kind` line to list `"dva"` too.
|
|
69
|
+
7. **Tests** — new `tests/test_collect_dva.py` (reusing `populated_batch` from `tests/test_batch.py`,
|
|
70
|
+
same `pytest.importorskip("plotly")` guard as `test_collectors.py`):
|
|
71
|
+
- `collect_dva` produces the specced frame (`cycle`, `direction`, `capacity`, `voltage`, `dvdq`)
|
|
72
|
+
and `.plot()` renders a non-empty figure.
|
|
73
|
+
- `dva_collector` convenience wrapper runs end to end (mirrors `test_ica_collector_uses_the_specced_frame`).
|
|
74
|
+
- `capacity_resolution` reaches `ica.dvdq` (monkeypatch spy, mirrors
|
|
75
|
+
`test_collect_cycles_forwards_mode_and_method`), and that `voltage_resolution` is
|
|
76
|
+
**not** what gets forwarded (guards the resolution-knob mixup called out above).
|
|
77
|
+
- `Collection(kind="dva").plot()` picks the `dva` family (not the `cycles` fallback) —
|
|
78
|
+
regression guard for the `_FAMILY` wiring.
|
|
79
|
+
|
|
80
|
+
## Files to touch
|
|
81
|
+
|
|
82
|
+
- `cellpy/collect/options.py` — add `capacity_resolution` to `IcaOptions`.
|
|
83
|
+
- `cellpy/collect/dva.py` — new, `collect_dva`.
|
|
84
|
+
- `cellpy/collect/collector.py` — add `dva_collector`.
|
|
85
|
+
- `cellpy/collect/__init__.py` — export both.
|
|
86
|
+
- `cellpy/collect/collection.py` — `_FAMILY` entry.
|
|
87
|
+
- `cellpy/plotting/collected.py` — `dva_plotter` + `render_collected` branch + docstring.
|
|
88
|
+
- `tests/test_collect_dva.py` — new.
|
|
89
|
+
- `HISTORY.md` (at `/iflow-close`).
|
|
90
|
+
|
|
91
|
+
## Test strategy
|
|
92
|
+
|
|
93
|
+
- `uv run pytest tests/test_collect_dva.py tests/test_collectors.py -v` (needs plotting extras;
|
|
94
|
+
both files already guard with `pytest.importorskip("plotly")`).
|
|
95
|
+
- `MPLBACKEND=Agg uv run pytest -m essential` merge gate.
|
|
96
|
+
- Mark new tests `@pytest.mark.essential` matching the existing collector test conventions (none
|
|
97
|
+
of `test_collectors.py`'s existing tests carry the marker today — check current state at build
|
|
98
|
+
time and follow whatever the file does, per the essential-tests-review step in `/iflow-close`).
|
|
99
|
+
|
|
100
|
+
## Open questions
|
|
101
|
+
|
|
102
|
+
None — the API shape, options reuse, and the two wiring gaps (`_FAMILY`, `render_collected`)
|
|
103
|
+
were all resolved by reading the existing ICA collector/plotter pair end to end.
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
# Status — Issue #863
|
|
2
|
+
|
|
3
|
+
- [x] Done
|
|
4
|
+
|
|
5
|
+
## What's done
|
|
6
|
+
|
|
7
|
+
- Investigated `collect_ica` / `ica_plotter` / `Collection._FAMILY` / `render_collected` end to
|
|
8
|
+
end to establish the mirror pattern for DVA.
|
|
9
|
+
- Identified the resolution-knob subtlety: `dqdv` uses `voltage_resolution`, `dvdq` uses
|
|
10
|
+
`capacity_resolution`.
|
|
11
|
+
- Plan written (`issue863_plan.md`), accepted.
|
|
12
|
+
- `cellpy/collect/options.py::IcaOptions` — added `capacity_resolution` field (shared by ICA
|
|
13
|
+
and DVA, each forwarding only its own knob).
|
|
14
|
+
- New `cellpy/collect/dva.py::collect_dva` — mirrors `collect_ica`, per-cell cycle isolation,
|
|
15
|
+
`kind="dva"`, forwards `capacity_resolution` to `ica.dvdq`.
|
|
16
|
+
- `cellpy/collect/collector.py::dva_collector` convenience wrapper.
|
|
17
|
+
- Exported `collect_dva` / `dva_collector` from `cellpy/collect/__init__.py`.
|
|
18
|
+
- `cellpy/collect/collection.py::Collection._FAMILY["dva"] = "dva"`.
|
|
19
|
+
- `cellpy/plotting/collected.py`: new `dva_plotter` (mirrors `ica_plotter`, x=capacity/y=dvdq),
|
|
20
|
+
wired into `render_collected`'s `family_kind == "dva"` branch, docstring updated.
|
|
21
|
+
- New `tests/test_collect_dva.py` (5 tests): specced frame, `Collection.kind`, resolution-knob
|
|
22
|
+
regression guard (`capacity_resolution` reaches `dvdq`, not `voltage_resolution`), `_FAMILY`
|
|
23
|
+
wiring regression guard, `fig_pr_cycle` layout.
|
|
24
|
+
- `uv run pytest tests/test_collect_dva.py` (5 passed), related collect/ICA/plotting tests
|
|
25
|
+
(70 passed), and the full `uv run pytest -m essential` merge gate (703 passed, 1 skipped,
|
|
26
|
+
2 xfailed, 1 xpassed — no regressions) all green with `MPLBACKEND=Agg`.
|
|
27
|
+
- `black --diff` / `flake8` on touched/new files: only pre-existing, unrelated findings
|
|
28
|
+
(line-length config mismatch; fixture-shadowing F811 identical to `test_collectors.py`;
|
|
29
|
+
pre-existing unused `field` import in `options.py`); nothing new from this change.
|
|
30
|
+
|
|
31
|
+
## Remaining work
|
|
32
|
+
|
|
33
|
+
None.
|
|
@@ -47,6 +47,14 @@ current issue**. `/iflow-doctor` may audit the whole suite against this table.
|
|
|
47
47
|
| tests/test_cli_light_import.py::test_setup_deps_probes_optional_modules | yes | yes | cli_api.setup_config --deps | #839 | opt-in optional probe |
|
|
48
48
|
| tests/test_cellpy_file_v9.py::test_failed_resave_keeps_the_old_file | yes | yes | cellpy_file.atomic.atomic_write / v9.save / CellpyCell.save | #845 | data-loss guard: interrupted re-save must not destroy the old file |
|
|
49
49
|
| tests/test_cellpy_file_v9.py::test_failed_first_save_leaves_no_file | yes | yes | cellpy_file.atomic.atomic_write / v9.save | #845 | no half-written archive on a fresh path |
|
|
50
|
+
| tests/test_ica_plot_prepare.py::test_ica_dva_plotly_both_direction_dash_differs | yes | yes | plotting.backends.plotly._render_ica_dva | #862 | charge solid / discharge dot |
|
|
51
|
+
| tests/test_ica_plot_prepare.py::test_ica_dva_plotly_single_direction_stays_solid | yes | yes | plotting.backends.plotly._render_ica_dva | #862 | single direction stays solid |
|
|
52
|
+
| tests/test_ica_plot_prepare.py::test_ica_dva_matplotlib_both_direction_linestyle_differs | yes | yes | plotting.backends.mpl._render_ica_dva | #862 | "-" / ":" linestyle |
|
|
53
|
+
| tests/test_collect_dva.py::test_dva_collector_uses_the_specced_frame | yes | yes | collect.dva.collect_dva | #863 | specced frame cols |
|
|
54
|
+
| tests/test_collect_dva.py::test_collect_dva_returns_a_dva_collection | yes | yes | collect.dva.collect_dva | #863 | kind="dva" |
|
|
55
|
+
| tests/test_collect_dva.py::test_collect_dva_forwards_capacity_resolution_not_voltage_resolution | yes | yes | collect.dva.collect_dva / ica.dvdq | #863 | resolution-knob guard |
|
|
56
|
+
| tests/test_collect_dva.py::test_dva_collection_plot_uses_the_dva_family_not_cycles | yes | yes | collect.collection.Collection._FAMILY | #863 | family wiring guard |
|
|
57
|
+
| tests/test_collect_dva.py::test_dva_collector_fig_pr_cycle | yes | yes | plotting.collected.dva_plotter | #863 | per-cycle layout |
|
|
50
58
|
| tests/test_cellpy_file_v9.py::test_incomplete_archive_is_rejected_before_replace | yes | yes | v9._verify_members | #845 | missing zip member never replaces a good file |
|
|
51
59
|
| tests/test_cellpy_file_v9.py::test_failed_hdf5_resave_keeps_the_old_file | no | no | cellpy_file.write.save (v8/HDF5) | #845 | same guard for the legacy writer; unmarked to keep Tier 1 fast |
|
|
52
60
|
| tests/test_config.py::test_active_config_file_prefers_toml | yes | yes | config.loader.active_config_file | #851 | "which config am I using" must stay honest |
|
|
@@ -17,6 +17,8 @@
|
|
|
17
17
|
- Pretty-print cycles collector facet strips (Cycle N / cell label, not cycle_num=). (#820)
|
|
18
18
|
- Honour share_y / match_axes on collected summary spread_plot. (#817)
|
|
19
19
|
- ICA plotter: honour direction for line layouts; support direction='both'. (#821)
|
|
20
|
+
- ``ica_plot`` / ``dva_plot``: dash discharge (dotted) vs charge (solid) when ``direction='both'`` so the two half-cycles stay distinguishable on a static export. (#862)
|
|
21
|
+
- ``cellpy.collect.collect_dva``: multi-cell DVA collection (mirrors ``collect_ica``), returning a ``Collection`` with the same ``Collection.plot()`` / grouping / save entry points; ``dva_collector`` convenience wrapper. (#863)
|
|
20
22
|
|
|
21
23
|
## [2.1.1.post6] - 2026-08-02
|
|
22
24
|
|
|
@@ -22,12 +22,14 @@ from cellpy.collect.collection import Collection, CollectionMeta, load_collectio
|
|
|
22
22
|
from cellpy.collect.collector import (
|
|
23
23
|
BatchCollector,
|
|
24
24
|
cycles_collector,
|
|
25
|
+
dva_collector,
|
|
25
26
|
ica_collector,
|
|
26
27
|
normalize_column,
|
|
27
28
|
standard_gravimetric,
|
|
28
29
|
summary_collector,
|
|
29
30
|
)
|
|
30
31
|
from cellpy.collect.curves import collect_cycles
|
|
32
|
+
from cellpy.collect.dva import collect_dva
|
|
31
33
|
from cellpy.collect.ica import collect_ica
|
|
32
34
|
from cellpy.collect.options import (
|
|
33
35
|
CurveOptions,
|
|
@@ -44,6 +46,7 @@ __all__ = [
|
|
|
44
46
|
"collect_summaries",
|
|
45
47
|
"collect_cycles",
|
|
46
48
|
"collect_ica",
|
|
49
|
+
"collect_dva",
|
|
47
50
|
"from_cells",
|
|
48
51
|
"iter_cells",
|
|
49
52
|
"CellItem",
|
|
@@ -55,6 +58,7 @@ __all__ = [
|
|
|
55
58
|
"summary_collector",
|
|
56
59
|
"cycles_collector",
|
|
57
60
|
"ica_collector",
|
|
61
|
+
"dva_collector",
|
|
58
62
|
"standard_gravimetric",
|
|
59
63
|
"normalize_column",
|
|
60
64
|
]
|
|
@@ -56,8 +56,8 @@ class Collection:
|
|
|
56
56
|
name: str
|
|
57
57
|
meta: CollectionMeta
|
|
58
58
|
|
|
59
|
-
#: collection kind -> ``collected_plot`` family (#657).
|
|
60
|
-
_FAMILY = {"summary": "summary", "cycles": "cycles", "ica": "ica"}
|
|
59
|
+
#: collection kind -> ``collected_plot`` family (#657, #863).
|
|
60
|
+
_FAMILY = {"summary": "summary", "cycles": "cycles", "ica": "ica", "dva": "dva"}
|
|
61
61
|
|
|
62
62
|
@property
|
|
63
63
|
def is_grouped(self) -> bool:
|
|
@@ -18,6 +18,7 @@ from typing import Any, Callable
|
|
|
18
18
|
import polars as pl
|
|
19
19
|
|
|
20
20
|
from cellpy.collect.curves import collect_cycles
|
|
21
|
+
from cellpy.collect.dva import collect_dva
|
|
21
22
|
from cellpy.collect.ica import collect_ica
|
|
22
23
|
from cellpy.collect.options import CurveOptions, IcaOptions, SummaryOptions
|
|
23
24
|
from cellpy.collect.summary import collect_summaries
|
|
@@ -117,6 +118,13 @@ def ica_collector(
|
|
|
117
118
|
return BatchCollector(batch, collect_ica, options, autorun=autorun, **overrides)
|
|
118
119
|
|
|
119
120
|
|
|
121
|
+
def dva_collector(
|
|
122
|
+
batch: Any, options: IcaOptions | None = None, *, autorun: bool = True, **overrides
|
|
123
|
+
) -> BatchCollector:
|
|
124
|
+
"""Convenience :class:`BatchCollector` bound to :func:`collect_dva`."""
|
|
125
|
+
return BatchCollector(batch, collect_dva, options, autorun=autorun, **overrides)
|
|
126
|
+
|
|
127
|
+
|
|
120
128
|
def normalize_column(
|
|
121
129
|
column: str, norm_factor: float, out: str | None = None
|
|
122
130
|
) -> Callable[[pl.DataFrame], pl.DataFrame]:
|
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
"""dV/dQ (DVA) collection.
|
|
2
|
+
|
|
3
|
+
Per-cell dV/dQ curves via :func:`cellpy.ica.dvdq`, concatenated into one tidy
|
|
4
|
+
frame with ``cell`` / ``group`` / ``sub_group`` keys. Mirrors
|
|
5
|
+
:func:`cellpy.collect.ica.collect_ica` -- including the per-cell cycle
|
|
6
|
+
isolation that fixes the legacy cross-cell narrowing bug (collectors.py:1691)
|
|
7
|
+
-- but emits the specced DVA frame: ``cycle, direction, capacity, voltage,
|
|
8
|
+
dvdq`` (#863).
|
|
9
|
+
"""
|
|
10
|
+
|
|
11
|
+
from __future__ import annotations
|
|
12
|
+
|
|
13
|
+
from typing import Any
|
|
14
|
+
|
|
15
|
+
import polars as pl
|
|
16
|
+
|
|
17
|
+
from cellpy.collect.cells import iter_cells
|
|
18
|
+
from cellpy.collect.collection import Collection, CollectionMeta
|
|
19
|
+
from cellpy.collect.options import IcaOptions
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
def _as_polars(frame: Any) -> pl.DataFrame | None:
|
|
23
|
+
if frame is None:
|
|
24
|
+
return None
|
|
25
|
+
if isinstance(frame, pl.DataFrame):
|
|
26
|
+
return frame
|
|
27
|
+
try:
|
|
28
|
+
return pl.from_pandas(frame)
|
|
29
|
+
except (TypeError, ValueError):
|
|
30
|
+
return None
|
|
31
|
+
|
|
32
|
+
|
|
33
|
+
def collect_dva(
|
|
34
|
+
batch: Any, options: IcaOptions | None = None, **overrides
|
|
35
|
+
) -> Collection:
|
|
36
|
+
"""Collect dV/dQ (differential voltage) curves per cell into one Collection.
|
|
37
|
+
|
|
38
|
+
Cycle selection is derived per cell from the *originally requested* cycles
|
|
39
|
+
every iteration, so a cell missing a cycle never narrows the request for
|
|
40
|
+
the cells after it (mirrors :func:`cellpy.collect.collect_ica`).
|
|
41
|
+
"""
|
|
42
|
+
from cellpy.utils import ica
|
|
43
|
+
|
|
44
|
+
opts = options or IcaOptions()
|
|
45
|
+
if overrides:
|
|
46
|
+
opts = opts.replace(**overrides)
|
|
47
|
+
requested = tuple(opts.cycles) if opts.cycles is not None else None
|
|
48
|
+
|
|
49
|
+
# dV/dQ differentiates along capacity (V(q) interpolation), unlike
|
|
50
|
+
# dQ/dV's voltage_resolution (q(V) interpolation).
|
|
51
|
+
dvdq_kwargs: dict[str, Any] = {}
|
|
52
|
+
if opts.capacity_resolution is not None:
|
|
53
|
+
dvdq_kwargs["capacity_resolution"] = opts.capacity_resolution
|
|
54
|
+
|
|
55
|
+
frames: list[pl.DataFrame] = []
|
|
56
|
+
for item in iter_cells(batch):
|
|
57
|
+
cell = item.cell
|
|
58
|
+
if requested is None:
|
|
59
|
+
cycles = None
|
|
60
|
+
else:
|
|
61
|
+
available = set(cell.get_cycle_numbers())
|
|
62
|
+
cycles = [c for c in requested if c in available]
|
|
63
|
+
if not cycles:
|
|
64
|
+
continue
|
|
65
|
+
|
|
66
|
+
curve = _as_polars(ica.dvdq(cell, cycles=cycles, **dvdq_kwargs))
|
|
67
|
+
if curve is None or curve.height == 0:
|
|
68
|
+
continue
|
|
69
|
+
frames.append(
|
|
70
|
+
curve.with_columns(
|
|
71
|
+
pl.lit(item.label).alias("cell"),
|
|
72
|
+
pl.lit(item.group).alias("group"),
|
|
73
|
+
pl.lit(item.sub_group).alias("sub_group"),
|
|
74
|
+
)
|
|
75
|
+
)
|
|
76
|
+
|
|
77
|
+
data = pl.concat(frames, how="diagonal_relaxed") if frames else pl.DataFrame()
|
|
78
|
+
for transform in opts.transforms:
|
|
79
|
+
data = transform(data)
|
|
80
|
+
|
|
81
|
+
meta = CollectionMeta(
|
|
82
|
+
kind="dva",
|
|
83
|
+
batch_name=batch.journal.name,
|
|
84
|
+
options={
|
|
85
|
+
"cycles": list(requested) if requested else None,
|
|
86
|
+
"capacity_resolution": opts.capacity_resolution,
|
|
87
|
+
},
|
|
88
|
+
cells_included=list(batch.cells),
|
|
89
|
+
)
|
|
90
|
+
return Collection(
|
|
91
|
+
data=data,
|
|
92
|
+
kind="dva",
|
|
93
|
+
name=f"{batch.journal.name or 'batch'}_dva",
|
|
94
|
+
meta=meta,
|
|
95
|
+
)
|
|
@@ -97,10 +97,19 @@ class CurveOptions:
|
|
|
97
97
|
|
|
98
98
|
@dataclass(frozen=True)
|
|
99
99
|
class IcaOptions:
|
|
100
|
-
"""Options for dQ/dV (ICA) collection.
|
|
100
|
+
"""Options for dQ/dV (ICA) and dV/dQ (DVA) collection.
|
|
101
|
+
|
|
102
|
+
Shared by :func:`cellpy.collect.collect_ica` and
|
|
103
|
+
:func:`cellpy.collect.collect_dva` -- each forwards only the resolution
|
|
104
|
+
knob its own transform actually uses: ``dqdv`` differentiates along
|
|
105
|
+
voltage (needs ``voltage_resolution`` for the q(V) interpolation);
|
|
106
|
+
``dvdq`` differentiates along capacity (needs ``capacity_resolution`` for
|
|
107
|
+
the V(q) interpolation).
|
|
108
|
+
"""
|
|
101
109
|
|
|
102
110
|
cycles: tuple[int, ...] | None = None
|
|
103
111
|
voltage_resolution: float | None = None
|
|
112
|
+
capacity_resolution: float | None = None
|
|
104
113
|
transforms: tuple[Transform, ...] = ()
|
|
105
114
|
|
|
106
115
|
def replace(self, **changes) -> "IcaOptions":
|