matterviz 0.3.7 → 0.4.1
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.
- package/dist/Icon.svelte +7 -4
- package/dist/MillerIndexInput.svelte +1 -1
- package/dist/api/optimade.js +32 -26
- package/dist/app.css +0 -3
- package/dist/brillouin/BrillouinZone.svelte +76 -148
- package/dist/brillouin/BrillouinZone.svelte.d.ts +6 -14
- package/dist/brillouin/BrillouinZoneExportPane.svelte +43 -96
- package/dist/brillouin/BrillouinZoneExportPane.svelte.d.ts +1 -1
- package/dist/brillouin/BrillouinZoneInfoPane.svelte +9 -32
- package/dist/brillouin/BrillouinZoneInfoPane.svelte.d.ts +2 -3
- package/dist/brillouin/BrillouinZoneScene.svelte +97 -205
- package/dist/brillouin/BrillouinZoneScene.svelte.d.ts +4 -23
- package/dist/brillouin/BrillouinZoneTooltip.svelte +16 -25
- package/dist/brillouin/ReciprocalVectors.svelte +39 -0
- package/dist/brillouin/ReciprocalVectors.svelte.d.ts +9 -0
- package/dist/brillouin/compute.d.ts +2 -0
- package/dist/brillouin/compute.js +89 -90
- package/dist/brillouin/geometry.d.ts +8 -0
- package/dist/brillouin/geometry.js +57 -0
- package/dist/brillouin/index.d.ts +2 -0
- package/dist/brillouin/index.js +2 -0
- package/dist/brillouin/types.d.ts +2 -2
- package/dist/chempot-diagram/ChemPotDiagram.svelte +14 -13
- package/dist/chempot-diagram/ChemPotDiagram.svelte.d.ts +1 -1
- package/dist/chempot-diagram/ChemPotDiagram2D.svelte +109 -203
- package/dist/chempot-diagram/ChemPotDiagram2D.svelte.d.ts +4 -1
- package/dist/chempot-diagram/ChemPotDiagram3D.svelte +180 -470
- package/dist/chempot-diagram/ChemPotDiagram3D.svelte.d.ts +7 -1
- package/dist/chempot-diagram/async-compute.svelte.js +3 -1
- package/dist/chempot-diagram/chempot-worker.js +2 -1
- package/dist/chempot-diagram/color.d.ts +3 -6
- package/dist/chempot-diagram/color.js +5 -5
- package/dist/chempot-diagram/compute.d.ts +4 -4
- package/dist/chempot-diagram/compute.js +20 -20
- package/dist/chempot-diagram/controls-state.svelte.d.ts +10 -0
- package/dist/chempot-diagram/controls-state.svelte.js +42 -0
- package/dist/chempot-diagram/export.d.ts +47 -0
- package/dist/chempot-diagram/export.js +133 -0
- package/dist/chempot-diagram/index.d.ts +1 -0
- package/dist/chempot-diagram/index.js +1 -0
- package/dist/chempot-diagram/pointer.d.ts +0 -10
- package/dist/chempot-diagram/pointer.js +4 -4
- package/dist/chempot-diagram/types.d.ts +3 -3
- package/dist/colors/index.js +8 -7
- package/dist/composition/FormulaFilter.svelte +18 -11
- package/dist/composition/PieChart.svelte +11 -10
- package/dist/composition/chem-sys.d.ts +8 -0
- package/dist/composition/chem-sys.js +86 -0
- package/dist/composition/format.js +7 -4
- package/dist/composition/index.d.ts +1 -0
- package/dist/composition/index.js +1 -0
- package/dist/composition/parse.d.ts +0 -1
- package/dist/composition/parse.js +41 -31
- package/dist/controls.d.ts +1 -0
- package/dist/controls.js +0 -1
- package/dist/convex-hull/ConvexHull.svelte +8 -10
- package/dist/convex-hull/ConvexHull.svelte.d.ts +1 -4
- package/dist/convex-hull/ConvexHull2D.svelte +106 -185
- package/dist/convex-hull/ConvexHull2D.svelte.d.ts +1 -1
- package/dist/convex-hull/ConvexHull3D.svelte +179 -683
- package/dist/convex-hull/ConvexHull3D.svelte.d.ts +1 -1
- package/dist/convex-hull/ConvexHull4D.svelte +183 -687
- package/dist/convex-hull/ConvexHull4D.svelte.d.ts +1 -1
- package/dist/convex-hull/ConvexHullChrome.svelte +268 -0
- package/dist/convex-hull/ConvexHullChrome.svelte.d.ts +30 -0
- package/dist/convex-hull/ConvexHullControls.svelte +88 -7
- package/dist/convex-hull/ConvexHullControls.svelte.d.ts +7 -6
- package/dist/convex-hull/ConvexHullInfoPane.svelte +18 -5
- package/dist/convex-hull/ConvexHullInfoPane.svelte.d.ts +6 -5
- package/dist/convex-hull/ConvexHullStats.svelte +36 -175
- package/dist/convex-hull/ConvexHullStats.svelte.d.ts +3 -1
- package/dist/convex-hull/ConvexHullTooltip.svelte +11 -2
- package/dist/convex-hull/ConvexHullTooltip.svelte.d.ts +2 -1
- package/dist/convex-hull/GasPressureControls.svelte +4 -4
- package/dist/convex-hull/TemperatureSlider.svelte +2 -2
- package/dist/convex-hull/barycentric-coords.d.ts +2 -4
- package/dist/convex-hull/barycentric-coords.js +6 -33
- package/dist/convex-hull/canvas-interactions.svelte.d.ts +79 -0
- package/dist/convex-hull/canvas-interactions.svelte.js +278 -0
- package/dist/convex-hull/demo-temperature.d.ts +1 -1
- package/dist/convex-hull/demo-temperature.js +20 -22
- package/dist/convex-hull/gas-thermodynamics.d.ts +2 -2
- package/dist/convex-hull/gas-thermodynamics.js +22 -30
- package/dist/convex-hull/helpers.d.ts +42 -7
- package/dist/convex-hull/helpers.js +171 -78
- package/dist/convex-hull/hull-state.svelte.d.ts +44 -0
- package/dist/convex-hull/hull-state.svelte.js +124 -0
- package/dist/convex-hull/index.d.ts +10 -8
- package/dist/convex-hull/index.js +7 -2
- package/dist/convex-hull/thermodynamics.js +136 -960
- package/dist/convex-hull/types.d.ts +13 -5
- package/dist/convex-hull/types.js +12 -0
- package/dist/coordination/CoordinationBarPlot.svelte +27 -34
- package/dist/coordination/CoordinationBarPlot.svelte.d.ts +1 -1
- package/dist/element/BohrAtom.svelte +2 -1
- package/dist/element/index.d.ts +4 -0
- package/dist/element/index.js +18 -0
- package/dist/feedback/DragOverlay.svelte +3 -1
- package/dist/feedback/DragOverlay.svelte.d.ts +1 -0
- package/dist/feedback/StatusMessage.svelte +13 -3
- package/dist/fermi-surface/FermiSlice.svelte +13 -5
- package/dist/fermi-surface/FermiSurface.svelte +78 -151
- package/dist/fermi-surface/FermiSurface.svelte.d.ts +5 -14
- package/dist/fermi-surface/FermiSurfaceControls.svelte +1 -1
- package/dist/fermi-surface/FermiSurfaceControls.svelte.d.ts +1 -1
- package/dist/fermi-surface/FermiSurfaceScene.svelte +72 -221
- package/dist/fermi-surface/FermiSurfaceScene.svelte.d.ts +3 -23
- package/dist/fermi-surface/FermiSurfaceTooltip.svelte +8 -34
- package/dist/fermi-surface/compute.js +67 -66
- package/dist/fermi-surface/export.js +6 -16
- package/dist/fermi-surface/index.d.ts +0 -1
- package/dist/fermi-surface/index.js +0 -1
- package/dist/fermi-surface/parse.d.ts +1 -1
- package/dist/fermi-surface/parse.js +71 -79
- package/dist/fermi-surface/types.d.ts +3 -2
- package/dist/heatmap-matrix/HeatmapMatrix.svelte +69 -52
- package/dist/heatmap-matrix/HeatmapMatrix.svelte.d.ts +4 -3
- package/dist/heatmap-matrix/HeatmapMatrixControls.svelte +3 -2
- package/dist/heatmap-matrix/HeatmapMatrixControls.svelte.d.ts +5 -5
- package/dist/heatmap-matrix/index.d.ts +3 -2
- package/dist/heatmap-matrix/index.js +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/io/ExportPane.svelte +166 -0
- package/dist/io/ExportPane.svelte.d.ts +17 -0
- package/dist/io/decompress.js +5 -4
- package/dist/io/export.d.ts +9 -5
- package/dist/io/export.js +77 -51
- package/dist/io/fetch.d.ts +2 -1
- package/dist/io/fetch.js +5 -1
- package/dist/io/file-drop.d.ts +8 -1
- package/dist/io/file-drop.js +48 -36
- package/dist/io/index.d.ts +2 -0
- package/dist/io/index.js +10 -0
- package/dist/io/types.d.ts +13 -0
- package/dist/io/url-drop.js +64 -33
- package/dist/isosurface/parse.js +52 -51
- package/dist/isosurface/slice.js +5 -4
- package/dist/isosurface/types.js +1 -1
- package/dist/keyboard.d.ts +3 -0
- package/dist/keyboard.js +23 -0
- package/dist/labels.d.ts +1 -1
- package/dist/labels.js +9 -8
- package/dist/layout/FullscreenButton.svelte +33 -0
- package/dist/layout/FullscreenButton.svelte.d.ts +10 -0
- package/dist/layout/FullscreenToggle.svelte +8 -14
- package/dist/layout/PropertyFilter.svelte +3 -2
- package/dist/layout/SettingsSection.svelte +1 -1
- package/dist/layout/ViewerChrome.svelte +116 -0
- package/dist/layout/ViewerChrome.svelte.d.ts +17 -0
- package/dist/layout/fullscreen.d.ts +4 -0
- package/dist/layout/fullscreen.svelte.d.ts +8 -0
- package/dist/layout/fullscreen.svelte.js +37 -0
- package/dist/layout/index.d.ts +3 -0
- package/dist/layout/index.js +3 -0
- package/dist/layout/json-tree/JsonNode.svelte +1 -1
- package/dist/layout/json-tree/JsonTree.svelte +2 -2
- package/dist/layout/json-tree/utils.js +5 -4
- package/dist/marching-cubes.js +8 -13
- package/dist/math.d.ts +12 -4
- package/dist/math.js +42 -30
- package/dist/overlays/DraggablePane.svelte +4 -4
- package/dist/overlays/index.d.ts +4 -0
- package/dist/periodic-table/PeriodicTable.svelte +27 -15
- package/dist/periodic-table/PropertySelect.svelte +1 -0
- package/dist/phase-diagram/IsobaricBinaryPhaseDiagram.svelte +9 -3
- package/dist/phase-diagram/IsobaricBinaryPhaseDiagram.svelte.d.ts +1 -1
- package/dist/phase-diagram/PhaseDiagramControls.svelte +3 -2
- package/dist/phase-diagram/PhaseDiagramControls.svelte.d.ts +4 -3
- package/dist/phase-diagram/PhaseDiagramEditorPane.svelte +4 -2
- package/dist/phase-diagram/PhaseDiagramEditorPane.svelte.d.ts +2 -3
- package/dist/phase-diagram/PhaseDiagramExportPane.svelte +47 -132
- package/dist/phase-diagram/PhaseDiagramExportPane.svelte.d.ts +3 -4
- package/dist/phase-diagram/PhaseDiagramTooltip.svelte +1 -1
- package/dist/phase-diagram/build-diagram.js +2 -2
- package/dist/phase-diagram/colors.js +1 -1
- package/dist/phase-diagram/parse.d.ts +2 -1
- package/dist/phase-diagram/parse.js +6 -5
- package/dist/phase-diagram/types.d.ts +1 -1
- package/dist/phase-diagram/utils.d.ts +3 -3
- package/dist/phase-diagram/utils.js +8 -12
- package/dist/plot/{BarPlot.svelte → bar/BarPlot.svelte} +246 -841
- package/dist/plot/{BarPlot.svelte.d.ts → bar/BarPlot.svelte.d.ts} +8 -16
- package/dist/plot/{BarPlotControls.svelte → bar/BarPlotControls.svelte} +6 -5
- package/dist/plot/{BarPlotControls.svelte.d.ts → bar/BarPlotControls.svelte.d.ts} +3 -3
- package/dist/plot/{SpacegroupBarPlot.svelte → bar/SpacegroupBarPlot.svelte} +8 -7
- package/dist/plot/{SpacegroupBarPlot.svelte.d.ts → bar/SpacegroupBarPlot.svelte.d.ts} +1 -1
- package/dist/plot/bar/data.d.ts +40 -0
- package/dist/plot/bar/data.js +154 -0
- package/dist/plot/bar/geometry.d.ts +39 -0
- package/dist/plot/bar/geometry.js +60 -0
- package/dist/plot/bar/index.d.ts +3 -0
- package/dist/plot/bar/index.js +3 -0
- package/dist/plot/box/BoxPlot.svelte +1292 -0
- package/dist/plot/box/BoxPlot.svelte.d.ts +95 -0
- package/dist/plot/box/BoxPlotControls.svelte +109 -0
- package/dist/plot/box/BoxPlotControls.svelte.d.ts +19 -0
- package/dist/plot/box/Violin.svelte +14 -0
- package/dist/plot/box/Violin.svelte.d.ts +70 -0
- package/dist/plot/box/box-plot.d.ts +56 -0
- package/dist/plot/box/box-plot.js +129 -0
- package/dist/plot/box/index.d.ts +5 -0
- package/dist/plot/box/index.js +5 -0
- package/dist/plot/box/kde.d.ts +17 -0
- package/dist/plot/box/kde.js +160 -0
- package/dist/plot/box/quantile.d.ts +3 -0
- package/dist/plot/box/quantile.js +53 -0
- package/dist/plot/{auto-place.d.ts → core/auto-place.d.ts} +1 -1
- package/dist/plot/{auto-place.js → core/auto-place.js} +6 -3
- package/dist/plot/core/axis-utils.d.ts +46 -0
- package/dist/plot/core/axis-utils.js +110 -0
- package/dist/plot/{AxisLabel.svelte → core/components/AxisLabel.svelte} +2 -2
- package/dist/plot/{AxisLabel.svelte.d.ts → core/components/AxisLabel.svelte.d.ts} +1 -1
- package/dist/plot/{ColorBar.svelte → core/components/ColorBar.svelte} +41 -38
- package/dist/plot/{ColorBar.svelte.d.ts → core/components/ColorBar.svelte.d.ts} +7 -6
- package/dist/plot/{ColorScaleSelect.svelte → core/components/ColorScaleSelect.svelte} +4 -3
- package/dist/plot/{ColorScaleSelect.svelte.d.ts → core/components/ColorScaleSelect.svelte.d.ts} +2 -2
- package/dist/plot/core/components/ControlPane.svelte +46 -0
- package/dist/plot/core/components/ControlPane.svelte.d.ts +13 -0
- package/dist/plot/{FillArea.svelte → core/components/FillArea.svelte} +17 -6
- package/dist/plot/{FillArea.svelte.d.ts → core/components/FillArea.svelte.d.ts} +1 -1
- package/dist/plot/{InteractiveAxisLabel.svelte → core/components/InteractiveAxisLabel.svelte} +3 -3
- package/dist/plot/{InteractiveAxisLabel.svelte.d.ts → core/components/InteractiveAxisLabel.svelte.d.ts} +2 -2
- package/dist/plot/{Line.svelte → core/components/Line.svelte} +33 -15
- package/dist/plot/{Line.svelte.d.ts → core/components/Line.svelte.d.ts} +3 -2
- package/dist/plot/{PlotAxis.svelte → core/components/PlotAxis.svelte} +9 -6
- package/dist/plot/{PlotAxis.svelte.d.ts → core/components/PlotAxis.svelte.d.ts} +5 -3
- package/dist/plot/{PlotControls.svelte → core/components/PlotControls.svelte} +17 -29
- package/dist/plot/core/components/PlotControls.svelte.d.ts +4 -0
- package/dist/plot/{PlotLegend.svelte → core/components/PlotLegend.svelte} +21 -10
- package/dist/plot/{PlotLegend.svelte.d.ts → core/components/PlotLegend.svelte.d.ts} +3 -2
- package/dist/plot/{PlotTooltip.svelte → core/components/PlotTooltip.svelte} +17 -1
- package/dist/plot/{PlotTooltip.svelte.d.ts → core/components/PlotTooltip.svelte.d.ts} +8 -0
- package/dist/plot/{PortalSelect.svelte → core/components/PortalSelect.svelte} +11 -7
- package/dist/plot/{ReferenceLine.svelte → core/components/ReferenceLine.svelte} +3 -3
- package/dist/plot/{ReferenceLine.svelte.d.ts → core/components/ReferenceLine.svelte.d.ts} +1 -1
- package/dist/plot/{ReferenceLine3D.svelte → core/components/ReferenceLine3D.svelte} +5 -5
- package/dist/plot/{ReferenceLine3D.svelte.d.ts → core/components/ReferenceLine3D.svelte.d.ts} +5 -5
- package/dist/plot/{ReferencePlane.svelte → core/components/ReferencePlane.svelte} +8 -8
- package/dist/plot/{ReferencePlane.svelte.d.ts → core/components/ReferencePlane.svelte.d.ts} +5 -5
- package/dist/plot/{ZeroLines.svelte → core/components/ZeroLines.svelte} +3 -3
- package/dist/plot/{ZeroLines.svelte.d.ts → core/components/ZeroLines.svelte.d.ts} +3 -3
- package/dist/plot/{ZoomRect.svelte → core/components/ZoomRect.svelte} +1 -1
- package/dist/plot/{ZoomRect.svelte.d.ts → core/components/ZoomRect.svelte.d.ts} +1 -1
- package/dist/plot/core/components/index.d.ts +17 -0
- package/dist/plot/core/components/index.js +17 -0
- package/dist/plot/{data-cleaning.d.ts → core/data-cleaning.d.ts} +71 -1
- package/dist/plot/{data-cleaning.js → core/data-cleaning.js} +21 -23
- package/dist/plot/{data-transform.d.ts → core/data-transform.d.ts} +2 -2
- package/dist/plot/{data-transform.js → core/data-transform.js} +3 -3
- package/dist/plot/core/fill-utils.d.ts +34 -0
- package/dist/plot/core/fill-utils.js +391 -0
- package/dist/plot/core/index.d.ts +10 -0
- package/dist/plot/core/index.js +11 -0
- package/dist/plot/core/interactions.d.ts +39 -0
- package/dist/plot/core/interactions.js +209 -0
- package/dist/plot/{layout.d.ts → core/layout.d.ts} +1 -0
- package/dist/plot/{layout.js → core/layout.js} +16 -8
- package/dist/plot/core/pan-zoom.svelte.d.ts +35 -0
- package/dist/plot/core/pan-zoom.svelte.js +221 -0
- package/dist/plot/core/placed-tween.svelte.d.ts +21 -0
- package/dist/plot/core/placed-tween.svelte.js +68 -0
- package/dist/plot/{reference-line.d.ts → core/reference-line.d.ts} +11 -11
- package/dist/plot/{reference-line.js → core/reference-line.js} +29 -42
- package/dist/plot/core/scales.d.ts +40 -0
- package/dist/plot/{scales.js → core/scales.js} +94 -93
- package/dist/plot/core/svg.d.ts +3 -0
- package/dist/plot/core/svg.js +41 -0
- package/dist/plot/{types.d.ts → core/types.d.ts} +36 -85
- package/dist/plot/{types.js → core/types.js} +1 -1
- package/dist/plot/{utils → core/utils}/label-placement.d.ts +3 -3
- package/dist/plot/{utils → core/utils}/label-placement.js +3 -3
- package/dist/plot/core/utils/series-visibility.d.ts +26 -0
- package/dist/plot/{utils → core/utils}/series-visibility.js +29 -2
- package/dist/plot/core/utils.d.ts +12 -0
- package/dist/plot/core/utils.js +27 -0
- package/dist/plot/{Histogram.svelte → histogram/Histogram.svelte} +174 -551
- package/dist/plot/{Histogram.svelte.d.ts → histogram/Histogram.svelte.d.ts} +2 -2
- package/dist/plot/{HistogramControls.svelte → histogram/HistogramControls.svelte} +6 -6
- package/dist/plot/{HistogramControls.svelte.d.ts → histogram/HistogramControls.svelte.d.ts} +4 -4
- package/dist/plot/histogram/index.d.ts +2 -0
- package/dist/plot/histogram/index.js +2 -0
- package/dist/plot/index.d.ts +8 -41
- package/dist/plot/index.js +10 -39
- package/dist/plot/sankey/Sankey.svelte +697 -0
- package/dist/plot/sankey/Sankey.svelte.d.ts +74 -0
- package/dist/plot/sankey/SankeyControls.svelte +98 -0
- package/dist/plot/sankey/SankeyControls.svelte.d.ts +19 -0
- package/dist/plot/sankey/index.d.ts +4 -0
- package/dist/plot/sankey/index.js +3 -0
- package/dist/plot/sankey/sankey-types.d.ts +42 -0
- package/dist/plot/sankey/sankey-types.js +4 -0
- package/dist/plot/sankey/sankey.d.ts +52 -0
- package/dist/plot/sankey/sankey.js +189 -0
- package/dist/plot/{BinnedScatterPlot.svelte → scatter/BinnedScatterPlot.svelte} +64 -64
- package/dist/plot/{BinnedScatterPlot.svelte.d.ts → scatter/BinnedScatterPlot.svelte.d.ts} +6 -6
- package/dist/plot/{ElementScatter.svelte → scatter/ElementScatter.svelte} +6 -6
- package/dist/plot/{ElementScatter.svelte.d.ts → scatter/ElementScatter.svelte.d.ts} +2 -2
- package/dist/plot/{ScatterPlot.svelte → scatter/ScatterPlot.svelte} +297 -1008
- package/dist/plot/{ScatterPlot.svelte.d.ts → scatter/ScatterPlot.svelte.d.ts} +10 -18
- package/dist/plot/{ScatterPlotControls.svelte → scatter/ScatterPlotControls.svelte} +6 -5
- package/dist/plot/{ScatterPlotControls.svelte.d.ts → scatter/ScatterPlotControls.svelte.d.ts} +2 -2
- package/dist/plot/{ScatterPoint.svelte → scatter/ScatterPoint.svelte} +7 -7
- package/dist/plot/{ScatterPoint.svelte.d.ts → scatter/ScatterPoint.svelte.d.ts} +3 -3
- package/dist/plot/{adaptive-density.d.ts → scatter/adaptive-density.d.ts} +14 -4
- package/dist/plot/{adaptive-density.js → scatter/adaptive-density.js} +46 -20
- package/dist/plot/{binned-scatter-types.d.ts → scatter/binned-scatter-types.d.ts} +5 -12
- package/dist/plot/scatter/index.d.ts +7 -0
- package/dist/plot/scatter/index.js +5 -0
- package/dist/plot/scatter/scatter-data.d.ts +19 -0
- package/dist/plot/scatter/scatter-data.js +212 -0
- package/dist/plot/{ScatterPlot3D.svelte → scatter-3d/ScatterPlot3D.svelte} +25 -34
- package/dist/plot/{ScatterPlot3D.svelte.d.ts → scatter-3d/ScatterPlot3D.svelte.d.ts} +9 -17
- package/dist/plot/{ScatterPlot3DControls.svelte → scatter-3d/ScatterPlot3DControls.svelte} +14 -14
- package/dist/plot/{ScatterPlot3DControls.svelte.d.ts → scatter-3d/ScatterPlot3DControls.svelte.d.ts} +6 -6
- package/dist/plot/{ScatterPlot3DScene.svelte → scatter-3d/ScatterPlot3DScene.svelte} +129 -128
- package/dist/plot/{ScatterPlot3DScene.svelte.d.ts → scatter-3d/ScatterPlot3DScene.svelte.d.ts} +6 -15
- package/dist/plot/{Surface3D.svelte → scatter-3d/Surface3D.svelte} +7 -6
- package/dist/plot/{Surface3D.svelte.d.ts → scatter-3d/Surface3D.svelte.d.ts} +5 -4
- package/dist/plot/scatter-3d/index.d.ts +4 -0
- package/dist/plot/scatter-3d/index.js +4 -0
- package/dist/plot/sunburst/Sunburst.svelte +1041 -0
- package/dist/plot/sunburst/Sunburst.svelte.d.ts +97 -0
- package/dist/plot/sunburst/SunburstControls.svelte +200 -0
- package/dist/plot/sunburst/SunburstControls.svelte.d.ts +26 -0
- package/dist/plot/sunburst/index.d.ts +4 -0
- package/dist/plot/sunburst/index.js +4 -0
- package/dist/plot/sunburst/render.d.ts +34 -0
- package/dist/plot/sunburst/render.js +122 -0
- package/dist/plot/sunburst/sunburst.d.ts +62 -0
- package/dist/plot/sunburst/sunburst.js +269 -0
- package/dist/rdf/RdfPlot.svelte +2 -1
- package/dist/rdf/RdfPlot.svelte.d.ts +1 -1
- package/dist/rdf/calc-rdf.js +11 -24
- package/dist/sanitize.js +14 -3
- package/dist/scene/SceneCamera.svelte +62 -0
- package/dist/scene/SceneCamera.svelte.d.ts +19 -0
- package/dist/scene/bind-renderer.svelte.d.ts +2 -0
- package/dist/scene/bind-renderer.svelte.js +14 -0
- package/dist/scene/index.d.ts +4 -0
- package/dist/scene/index.js +5 -0
- package/dist/scene/props.js +52 -0
- package/dist/scene/types.d.ts +26 -0
- package/dist/scene/types.js +1 -0
- package/dist/settings.d.ts +79 -3
- package/dist/settings.js +321 -1
- package/dist/spectral/Bands.svelte +47 -36
- package/dist/spectral/Bands.svelte.d.ts +6 -6
- package/dist/spectral/BandsAndDos.svelte +23 -25
- package/dist/spectral/BrillouinBandsDos.svelte +42 -30
- package/dist/spectral/Dos.svelte +15 -23
- package/dist/spectral/Dos.svelte.d.ts +4 -3
- package/dist/spectral/helpers.d.ts +8 -6
- package/dist/spectral/helpers.js +137 -65
- package/dist/state.svelte.d.ts +0 -7
- package/dist/state.svelte.js +0 -6
- package/dist/structure/Arrow.svelte +2 -4
- package/dist/structure/AtomLegend.svelte +8 -9
- package/dist/structure/AtomLegend.svelte.d.ts +1 -1
- package/dist/structure/CanvasTooltip.svelte +1 -0
- package/dist/structure/CellSelect.svelte +12 -5
- package/dist/structure/CellSelect.svelte.d.ts +2 -1
- package/dist/structure/Cylinder.svelte +12 -8
- package/dist/structure/Cylinder.svelte.d.ts +4 -1
- package/dist/structure/Lattice.svelte +2 -2
- package/dist/structure/Structure.svelte +365 -423
- package/dist/structure/Structure.svelte.d.ts +5 -15
- package/dist/structure/StructureControls.svelte +217 -2
- package/dist/structure/StructureControls.svelte.d.ts +5 -3
- package/dist/structure/StructureExportPane.svelte +54 -156
- package/dist/structure/StructureExportPane.svelte.d.ts +4 -5
- package/dist/structure/StructureInfoPane.svelte +10 -9
- package/dist/structure/StructureInfoPane.svelte.d.ts +5 -5
- package/dist/structure/StructureScene.svelte +376 -208
- package/dist/structure/StructureScene.svelte.d.ts +22 -20
- package/dist/structure/{label-placement.d.ts → atom-label-placement.d.ts} +3 -3
- package/dist/structure/{label-placement.js → atom-label-placement.js} +15 -5
- package/dist/structure/atom-properties.d.ts +1 -1
- package/dist/structure/atom-properties.js +17 -22
- package/dist/structure/bond-order-perception.js +3 -5
- package/dist/structure/bonding.d.ts +4 -0
- package/dist/structure/bonding.js +134 -63
- package/dist/structure/export.d.ts +24 -4
- package/dist/structure/export.js +89 -143
- package/dist/structure/index.d.ts +4 -4
- package/dist/structure/index.js +3 -3
- package/dist/structure/measure.d.ts +3 -2
- package/dist/structure/measure.js +6 -5
- package/dist/structure/parse.d.ts +3 -2
- package/dist/structure/parse.js +419 -438
- package/dist/structure/partial-occupancy.d.ts +0 -1
- package/dist/structure/partial-occupancy.js +1 -1
- package/dist/structure/pbc.d.ts +1 -1
- package/dist/structure/pbc.js +190 -13
- package/dist/structure/polyhedra.d.ts +41 -0
- package/dist/structure/polyhedra.js +602 -0
- package/dist/structure/site.d.ts +4 -0
- package/dist/structure/site.js +1 -0
- package/dist/structure/supercell.js +3 -2
- package/dist/structure/validation.js +5 -6
- package/dist/symmetry/SymmetryElementControls.svelte +69 -0
- package/dist/symmetry/SymmetryElementControls.svelte.d.ts +9 -0
- package/dist/symmetry/SymmetryElements.svelte +354 -0
- package/dist/symmetry/SymmetryElements.svelte.d.ts +24 -0
- package/dist/symmetry/SymmetryStats.svelte +113 -8
- package/dist/symmetry/WyckoffTable.svelte +68 -7
- package/dist/symmetry/WyckoffTable.svelte.d.ts +3 -0
- package/dist/symmetry/cell-transform.js +7 -14
- package/dist/symmetry/index.d.ts +14 -4
- package/dist/symmetry/index.js +291 -72
- package/dist/symmetry/spacegroups.d.ts +12 -1
- package/dist/symmetry/spacegroups.js +63 -14
- package/dist/symmetry/symmetry-elements.d.ts +33 -0
- package/dist/symmetry/symmetry-elements.js +521 -0
- package/dist/symmetry/wyckoff-db.d.ts +9 -0
- package/dist/symmetry/wyckoff-db.js +87 -0
- package/dist/table/HeatmapTable.svelte +66 -25
- package/dist/table/HeatmapTable.svelte.d.ts +1 -1
- package/dist/table/index.d.ts +1 -3
- package/dist/table/index.js +1 -1
- package/dist/theme/index.js +8 -8
- package/dist/tooltip/KCoords.svelte +45 -0
- package/dist/tooltip/KCoords.svelte.d.ts +8 -0
- package/dist/tooltip/index.d.ts +1 -0
- package/dist/tooltip/index.js +1 -0
- package/dist/trajectory/Trajectory.svelte +123 -100
- package/dist/trajectory/Trajectory.svelte.d.ts +11 -22
- package/dist/trajectory/TrajectoryExportPane.svelte +17 -25
- package/dist/trajectory/TrajectoryExportPane.svelte.d.ts +4 -5
- package/dist/trajectory/TrajectoryInfoPane.svelte +5 -3
- package/dist/trajectory/TrajectoryInfoPane.svelte.d.ts +3 -2
- package/dist/trajectory/constants.js +6 -2
- package/dist/trajectory/extract.js +17 -37
- package/dist/trajectory/format-detect.d.ts +1 -1
- package/dist/trajectory/format-detect.js +27 -19
- package/dist/trajectory/frame-reader.d.ts +0 -1
- package/dist/trajectory/frame-reader.js +63 -162
- package/dist/trajectory/helpers.d.ts +10 -2
- package/dist/trajectory/helpers.js +56 -36
- package/dist/trajectory/index.js +1 -1
- package/dist/trajectory/parse/ase.d.ts +9 -1
- package/dist/trajectory/parse/ase.js +47 -32
- package/dist/trajectory/parse/diagnostics.d.ts +3 -0
- package/dist/trajectory/parse/diagnostics.js +14 -0
- package/dist/trajectory/parse/hdf5.js +1 -1
- package/dist/trajectory/parse/index.d.ts +1 -1
- package/dist/trajectory/parse/index.js +65 -105
- package/dist/trajectory/parse/lammps.d.ts +0 -2
- package/dist/trajectory/parse/lammps.js +8 -6
- package/dist/trajectory/parse/pymatgen.d.ts +2 -0
- package/dist/trajectory/parse/pymatgen.js +74 -0
- package/dist/trajectory/parse/vasp.js +38 -18
- package/dist/trajectory/parse/xyz.d.ts +13 -1
- package/dist/trajectory/parse/xyz.js +102 -94
- package/dist/trajectory/plotting.d.ts +1 -2
- package/dist/trajectory/plotting.js +16 -113
- package/dist/utils.d.ts +2 -0
- package/dist/utils.js +7 -5
- package/dist/xrd/XrdPlot.svelte +16 -30
- package/dist/xrd/broadening.d.ts +2 -1
- package/dist/xrd/calc-xrd.js +18 -20
- package/dist/xrd/index.d.ts +2 -2
- package/dist/xrd/parse.js +2 -2
- package/package.json +43 -26
- package/dist/element/data.json +0 -11864
- package/dist/fermi-surface/marching-cubes.d.ts +0 -2
- package/dist/fermi-surface/marching-cubes.js +0 -2
- package/dist/plot/PlotControls.svelte.d.ts +0 -4
- package/dist/plot/axis-utils.d.ts +0 -19
- package/dist/plot/axis-utils.js +0 -78
- package/dist/plot/defaults.d.ts +0 -19
- package/dist/plot/defaults.js +0 -9
- package/dist/plot/fill-utils.d.ts +0 -46
- package/dist/plot/fill-utils.js +0 -322
- package/dist/plot/hover-lock.svelte.d.ts +0 -14
- package/dist/plot/hover-lock.svelte.js +0 -46
- package/dist/plot/interactions.d.ts +0 -12
- package/dist/plot/interactions.js +0 -101
- package/dist/plot/scales.d.ts +0 -48
- package/dist/plot/svg.d.ts +0 -1
- package/dist/plot/svg.js +0 -11
- package/dist/plot/utils/series-visibility.d.ts +0 -15
- package/dist/plot/utils.d.ts +0 -1
- package/dist/plot/utils.js +0 -14
- /package/dist/plot/{PortalSelect.svelte.d.ts → core/components/PortalSelect.svelte.d.ts} +0 -0
- /package/dist/plot/{binned-scatter-types.js → scatter/binned-scatter-types.js} +0 -0
package/dist/io/export.js
CHANGED
|
@@ -1,28 +1,21 @@
|
|
|
1
1
|
import { download } from './fetch';
|
|
2
2
|
import { create_structure_filename } from '../structure/export';
|
|
3
|
+
import { to_error } from '../utils';
|
|
3
4
|
import { Vector2 } from 'three';
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
typeof renderer_obj.setPixelRatio === `function` &&
|
|
11
|
-
typeof renderer_obj.getSize === `function` &&
|
|
12
|
-
typeof renderer_obj.setSize === `function`);
|
|
13
|
-
}
|
|
14
|
-
function get_canvas_renderer(canvas) {
|
|
15
|
-
const renderer_val = canvas[`__renderer`];
|
|
16
|
-
return is_webgl_renderer_like(renderer_val) ? renderer_val : undefined;
|
|
17
|
-
}
|
|
5
|
+
// Maps a Threlte canvas to its WebGLRenderer so PNG export can look up the renderer for a
|
|
6
|
+
// given canvas without mutating the DOM element. Populated by bind_renderer (scene/).
|
|
7
|
+
export const renderer_registry = new WeakMap();
|
|
8
|
+
// PNG DPI -> render scale relative to the 72 DPI baseline, capped at 10x. DPI floors
|
|
9
|
+
// at 1 (non-finite -> 72) so bad inputs can't yield 0x0 canvases or NaN pixel ratios.
|
|
10
|
+
export const dpi_to_scale = (png_dpi) => Math.min(Math.max(1, Number.isFinite(png_dpi) ? png_dpi : 72) / 72, 10);
|
|
18
11
|
// Capture a WebGL canvas as a PNG Blob at the given DPI.
|
|
19
12
|
// Temporarily adjusts renderer pixel ratio for high-res capture, then restores.
|
|
20
13
|
// Returns data directly (no browser download), suitable for programmatic capture
|
|
21
14
|
// in test suites, server-side rendering, or Python widget integration via anywidget.
|
|
22
15
|
// DPI is converted to a resolution multiplier relative to 72 DPI baseline, capped at 10x.
|
|
23
16
|
export function canvas_to_png_blob(canvas, png_dpi = 150, scene = null, camera = null) {
|
|
24
|
-
const resolution_multiplier =
|
|
25
|
-
const renderer =
|
|
17
|
+
const resolution_multiplier = dpi_to_scale(png_dpi);
|
|
18
|
+
const renderer = renderer_registry.get(canvas);
|
|
26
19
|
if (resolution_multiplier <= 1.1 || !renderer) {
|
|
27
20
|
if (renderer && scene && camera)
|
|
28
21
|
renderer.render(scene, camera);
|
|
@@ -36,7 +29,7 @@ export function canvas_to_png_blob(canvas, png_dpi = 150, scene = null, camera =
|
|
|
36
29
|
}, `image/png`);
|
|
37
30
|
}
|
|
38
31
|
catch (error) {
|
|
39
|
-
reject(error);
|
|
32
|
+
reject(to_error(error));
|
|
40
33
|
}
|
|
41
34
|
});
|
|
42
35
|
}
|
|
@@ -63,7 +56,7 @@ export function canvas_to_png_blob(canvas, png_dpi = 150, scene = null, camera =
|
|
|
63
56
|
}
|
|
64
57
|
catch (error) {
|
|
65
58
|
restore();
|
|
66
|
-
reject(error);
|
|
59
|
+
reject(to_error(error));
|
|
67
60
|
}
|
|
68
61
|
});
|
|
69
62
|
}
|
|
@@ -90,34 +83,56 @@ export function export_canvas_as_png(canvas, structure_or_filename, png_dpi = 15
|
|
|
90
83
|
}
|
|
91
84
|
// Helper to ensure font-family is set on SVG root
|
|
92
85
|
function set_svg_font_family(svg) {
|
|
93
|
-
const style = svg.getAttribute(`style`)
|
|
86
|
+
const style = svg.getAttribute(`style`) ?? ``;
|
|
94
87
|
if (!style.includes(`font-family`)) {
|
|
95
88
|
svg.setAttribute(`style`, `${style}${style ? `;` : ``}font-family:sans-serif;`);
|
|
96
89
|
}
|
|
97
90
|
// Also set as attribute for extra robustness
|
|
98
91
|
svg.setAttribute(`font-family`, `sans-serif`);
|
|
99
92
|
}
|
|
100
|
-
//
|
|
101
|
-
//
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
const
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
93
|
+
// Copy the given computed-style props from each live SVG element to its clone counterpart;
|
|
94
|
+
// identical structure lets querySelectorAll(`*`) walk both in lockstep. Writes clone-only.
|
|
95
|
+
function inline_computed_styles(live, clone, properties) {
|
|
96
|
+
const live_els = [live, ...live.querySelectorAll(`*`)];
|
|
97
|
+
const clone_els = [clone, ...clone.querySelectorAll(`*`)];
|
|
98
|
+
for (const [idx, live_el] of live_els.entries()) {
|
|
99
|
+
const computed = getComputedStyle(live_el);
|
|
100
|
+
for (const prop of properties) {
|
|
101
|
+
const val = computed.getPropertyValue(prop);
|
|
102
|
+
if (val)
|
|
103
|
+
clone_els[idx].setAttribute(prop, val);
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
// Clone, inline the given computed-style props, ensure font-family + xmlns, then serialize
|
|
108
|
+
// to a standalone SVG string. Never mutates the live element.
|
|
109
|
+
function serialize_svg_for_export(svg_element, inline_styles = []) {
|
|
110
|
+
const clone = svg_element.cloneNode(true);
|
|
111
|
+
if (inline_styles.length)
|
|
112
|
+
inline_computed_styles(svg_element, clone, inline_styles);
|
|
113
|
+
set_svg_font_family(clone);
|
|
114
|
+
if (!clone.hasAttribute(`xmlns`)) {
|
|
115
|
+
clone.setAttribute(`xmlns`, `http://www.w3.org/2000/svg`);
|
|
109
116
|
}
|
|
110
|
-
|
|
117
|
+
return new XMLSerializer().serializeToString(clone);
|
|
118
|
+
}
|
|
119
|
+
// Wrap serialize_svg_for_export's output as a full SVG document string (XML declaration +
|
|
120
|
+
// DOCTYPE + SVG), suitable for saving to file.
|
|
121
|
+
export function svg_to_svg_string(svg_element,
|
|
122
|
+
// CSS props to inline from computed styles as presentation attributes; a standalone SVG
|
|
123
|
+
// drops page stylesheets (e.g. Svelte component styles), so class-based styling is lost.
|
|
124
|
+
inline_styles = []) {
|
|
125
|
+
const svg_string = serialize_svg_for_export(svg_element, inline_styles);
|
|
111
126
|
return `<?xml version="1.0" encoding="UTF-8"?>\n<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">\n${svg_string}`;
|
|
112
127
|
}
|
|
113
128
|
// Export SVG element as SVG file (triggers browser download)
|
|
114
|
-
export function export_svg_as_svg(svg_element, filename) {
|
|
129
|
+
export function export_svg_as_svg(svg_element, filename, inline_styles = []) {
|
|
115
130
|
if (!svg_element) {
|
|
116
131
|
console.warn(`SVG element not found for export`);
|
|
117
132
|
return;
|
|
118
133
|
}
|
|
119
134
|
try {
|
|
120
|
-
const svg_content = svg_to_svg_string(svg_element);
|
|
135
|
+
const svg_content = svg_to_svg_string(svg_element, inline_styles);
|
|
121
136
|
download(svg_content, filename, `image/svg+xml;charset=utf-8`);
|
|
122
137
|
}
|
|
123
138
|
catch (error) {
|
|
@@ -129,7 +144,7 @@ export function export_svg_as_svg(svg_element, filename) {
|
|
|
129
144
|
// Image element, and returns the resulting PNG Blob. Rejects if viewBox is
|
|
130
145
|
// missing or dimensions are invalid (zero width/height).
|
|
131
146
|
// DPI is converted to a resolution multiplier relative to 72 DPI baseline, capped at 10x.
|
|
132
|
-
export function svg_to_png_blob(svg_element, png_dpi = 150) {
|
|
147
|
+
export function svg_to_png_blob(svg_element, png_dpi = 150, inline_styles = []) {
|
|
133
148
|
const viewBox = svg_element.getAttribute(`viewBox`)?.trim();
|
|
134
149
|
if (!viewBox)
|
|
135
150
|
return Promise.reject(new Error(`SVG viewBox not found for PNG export`));
|
|
@@ -144,18 +159,17 @@ export function svg_to_png_blob(svg_element, png_dpi = 150) {
|
|
|
144
159
|
if (!Number.isFinite(png_dpi) || png_dpi <= 0) {
|
|
145
160
|
return Promise.reject(new Error(`Invalid PNG DPI for export`));
|
|
146
161
|
}
|
|
147
|
-
const resolution_multiplier =
|
|
148
|
-
|
|
149
|
-
const
|
|
162
|
+
const resolution_multiplier = dpi_to_scale(png_dpi);
|
|
163
|
+
// Floor at 1px: small viewBoxes at low DPI round to 0 and make toBlob fail confusingly
|
|
164
|
+
const pixel_width = Math.max(1, Math.round(width * resolution_multiplier));
|
|
165
|
+
const pixel_height = Math.max(1, Math.round(height * resolution_multiplier));
|
|
150
166
|
const canvas = document.createElement(`canvas`);
|
|
151
167
|
const ctx = canvas.getContext(`2d`);
|
|
152
168
|
if (!ctx)
|
|
153
169
|
return Promise.reject(new Error(`Canvas 2D context not available`));
|
|
154
170
|
canvas.width = pixel_width;
|
|
155
171
|
canvas.height = pixel_height;
|
|
156
|
-
const
|
|
157
|
-
set_svg_font_family(cloned_svg);
|
|
158
|
-
const serialized = new XMLSerializer().serializeToString(cloned_svg);
|
|
172
|
+
const serialized = serialize_svg_for_export(svg_element, inline_styles);
|
|
159
173
|
const svg_blob = new Blob([serialized], { type: `image/svg+xml;charset=utf-8` });
|
|
160
174
|
const svg_data_url = URL.createObjectURL(svg_blob);
|
|
161
175
|
return new Promise((resolve, reject) => {
|
|
@@ -172,7 +186,7 @@ export function svg_to_png_blob(svg_element, png_dpi = 150) {
|
|
|
172
186
|
}, `image/png`, 1);
|
|
173
187
|
}
|
|
174
188
|
catch (error) {
|
|
175
|
-
reject(error);
|
|
189
|
+
reject(to_error(error));
|
|
176
190
|
}
|
|
177
191
|
finally {
|
|
178
192
|
URL.revokeObjectURL(svg_data_url);
|
|
@@ -186,15 +200,32 @@ export function svg_to_png_blob(svg_element, png_dpi = 150) {
|
|
|
186
200
|
});
|
|
187
201
|
}
|
|
188
202
|
// Export SVG element as PNG (triggers browser download)
|
|
189
|
-
export function export_svg_as_png(svg_element, filename, png_dpi = 150) {
|
|
203
|
+
export function export_svg_as_png(svg_element, filename, png_dpi = 150, inline_styles = []) {
|
|
190
204
|
if (!svg_element) {
|
|
191
205
|
console.warn(`SVG element not found for PNG export`);
|
|
192
206
|
return;
|
|
193
207
|
}
|
|
194
|
-
svg_to_png_blob(svg_element, png_dpi)
|
|
208
|
+
svg_to_png_blob(svg_element, png_dpi, inline_styles)
|
|
195
209
|
.then((blob) => download(blob, filename, `image/png`))
|
|
196
210
|
.catch((error) => console.error(`Error exporting PNG:`, error));
|
|
197
211
|
}
|
|
212
|
+
// Watch a wrapper element for <canvas> insertion/removal: calls set(bool) immediately
|
|
213
|
+
// and on every DOM mutation. Returns a cleanup that disconnects the observer (or
|
|
214
|
+
// undefined when no wrapper is given). Used by export panes to enable canvas exports.
|
|
215
|
+
export function observe_canvas_presence(wrapper, set) {
|
|
216
|
+
if (!wrapper) {
|
|
217
|
+
set(false);
|
|
218
|
+
return undefined;
|
|
219
|
+
}
|
|
220
|
+
const check = () => set(Boolean(wrapper.querySelector(`canvas`)));
|
|
221
|
+
check();
|
|
222
|
+
const observer = new MutationObserver(check);
|
|
223
|
+
observer.observe(wrapper, { childList: true, subtree: true });
|
|
224
|
+
return () => observer.disconnect();
|
|
225
|
+
}
|
|
226
|
+
// Estimate VP9 video bitrate (bits/s) from pixel count and frame rate.
|
|
227
|
+
// VP9 needs ~0.1 bits per pixel per frame for good quality; clamped to [1, 200] Mbps.
|
|
228
|
+
export const estimate_video_bitrate = (pixel_count, fps) => Math.max(1_000_000, Math.min(pixel_count * fps * 0.1, 200_000_000));
|
|
198
229
|
// Generate FFmpeg command for WebM to MP4 conversion
|
|
199
230
|
export function get_ffmpeg_conversion_command(input_filename) {
|
|
200
231
|
const output = input_filename.replace(/\.webm$/i, `.mp4`);
|
|
@@ -208,7 +239,7 @@ export async function export_trajectory_video(canvas, filename, options = {}) {
|
|
|
208
239
|
typeof MediaRecorder === `undefined` ||
|
|
209
240
|
!MediaRecorder.isTypeSupported(`video/webm;codecs=vp9`))
|
|
210
241
|
throw new Error(`WebM video recording not supported in this browser`);
|
|
211
|
-
const renderer =
|
|
242
|
+
const renderer = renderer_registry.get(canvas);
|
|
212
243
|
// Store original renderer settings if changing resolution
|
|
213
244
|
let orig_pixel_ratio;
|
|
214
245
|
let orig_size;
|
|
@@ -220,13 +251,8 @@ export async function export_trajectory_video(canvas, filename, options = {}) {
|
|
|
220
251
|
renderer.setSize(orig_size.width, orig_size.height, false);
|
|
221
252
|
}
|
|
222
253
|
// Calculate bitrate based on actual video dimensions
|
|
223
|
-
//
|
|
224
|
-
|
|
225
|
-
const pixels_per_frame = canvas.width * canvas.height;
|
|
226
|
-
const bits_per_pixel_per_frame = 0.1; // Good quality for VP9
|
|
227
|
-
// Clamp bitrate to reasonable bounds (1 Mbps min, 200 Mbps max)
|
|
228
|
-
const calculated_bitrate = pixels_per_frame * fps * bits_per_pixel_per_frame;
|
|
229
|
-
const bitrate = Math.max(1_000_000, Math.min(calculated_bitrate, 200_000_000));
|
|
254
|
+
// (canvas dimensions include device pixel ratio and any resolution_multiplier)
|
|
255
|
+
const bitrate = estimate_video_bitrate(canvas.width * canvas.height, fps);
|
|
230
256
|
const stream = canvas.captureStream(0);
|
|
231
257
|
const chunks = [];
|
|
232
258
|
const recorder = new MediaRecorder(stream, {
|
|
@@ -283,7 +309,7 @@ export async function export_trajectory_video(canvas, filename, options = {}) {
|
|
|
283
309
|
resolve();
|
|
284
310
|
}
|
|
285
311
|
catch (error) {
|
|
286
|
-
reject(error);
|
|
312
|
+
reject(to_error(error));
|
|
287
313
|
}
|
|
288
314
|
});
|
|
289
315
|
recorder.addEventListener(`error`, (event) => {
|
|
@@ -309,7 +335,7 @@ export async function export_trajectory_video(canvas, filename, options = {}) {
|
|
|
309
335
|
catch (error) {
|
|
310
336
|
if (!is_resolved) {
|
|
311
337
|
is_resolved = true;
|
|
312
|
-
reject(error);
|
|
338
|
+
reject(to_error(error));
|
|
313
339
|
}
|
|
314
340
|
}
|
|
315
341
|
});
|
package/dist/io/fetch.d.ts
CHANGED
|
@@ -2,4 +2,5 @@ export declare const to_query: (params: Record<string, string | number | undefin
|
|
|
2
2
|
export declare function fetch_zipped<T>(url: string, { unzip }?: {
|
|
3
3
|
unzip?: boolean | undefined;
|
|
4
4
|
}): Promise<T | null>;
|
|
5
|
-
export
|
|
5
|
+
export type DownloadData = string | Blob | ArrayBuffer | ArrayBufferView<ArrayBuffer>;
|
|
6
|
+
export declare function download(data: DownloadData, filename: string, type: string): void;
|
package/dist/io/fetch.js
CHANGED
|
@@ -22,7 +22,11 @@ function default_download(data, filename, type) {
|
|
|
22
22
|
link.style.display = `none`;
|
|
23
23
|
link.href = url;
|
|
24
24
|
link.download = filename;
|
|
25
|
-
document
|
|
25
|
+
// keep the synthetic download click from bubbling to document-level handlers
|
|
26
|
+
// (e.g. DraggablePane's click-outside) that would dismiss an open pane the export
|
|
27
|
+
// button lives in
|
|
28
|
+
link.addEventListener(`click`, (evt) => evt.stopPropagation());
|
|
29
|
+
document.body.append(link);
|
|
26
30
|
link.click();
|
|
27
31
|
link.remove();
|
|
28
32
|
URL.revokeObjectURL(url);
|
package/dist/io/file-drop.d.ts
CHANGED
|
@@ -4,4 +4,11 @@ export interface FileDropOptions {
|
|
|
4
4
|
on_error?: (msg: string) => void;
|
|
5
5
|
set_loading?: (loading: boolean) => void;
|
|
6
6
|
}
|
|
7
|
-
export declare
|
|
7
|
+
export declare const drag_over_handlers: (opts: {
|
|
8
|
+
allow?: () => boolean;
|
|
9
|
+
set_dragover: (over: boolean) => void;
|
|
10
|
+
}) => {
|
|
11
|
+
ondragover: (event: DragEvent) => void;
|
|
12
|
+
ondragleave: () => void;
|
|
13
|
+
};
|
|
14
|
+
export declare const create_file_drop_handler: (opts: FileDropOptions) => ((event: DragEvent) => Promise<void>);
|
package/dist/io/file-drop.js
CHANGED
|
@@ -1,43 +1,55 @@
|
|
|
1
1
|
// Shared file-drop handler composable for drag-and-drop file loading.
|
|
2
2
|
import { decompress_file } from './decompress';
|
|
3
3
|
import { handle_url_drop } from './url-drop';
|
|
4
|
+
import { to_error } from '../utils';
|
|
5
|
+
// Drag-over visual-state handlers for file-drop zones; spread onto the drop target
|
|
6
|
+
// alongside `ondrop` from create_file_drop_handler
|
|
7
|
+
export const drag_over_handlers = (opts) => ({
|
|
8
|
+
// preventDefault on dragover marks the element as a valid drop target; dragleave
|
|
9
|
+
// has no default action to cancel, so it only clears the visual state
|
|
10
|
+
ondragover: (event) => {
|
|
11
|
+
event.preventDefault();
|
|
12
|
+
if (opts.allow && !opts.allow())
|
|
13
|
+
return;
|
|
14
|
+
opts.set_dragover(true);
|
|
15
|
+
},
|
|
16
|
+
ondragleave: () => opts.set_dragover(false),
|
|
17
|
+
});
|
|
4
18
|
// Handles URL drops (from FilePicker), direct file drops with decompression,
|
|
5
19
|
// loading state, and error reporting.
|
|
6
|
-
export
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
20
|
+
export const create_file_drop_handler = (opts) => async (event) => {
|
|
21
|
+
event.preventDefault();
|
|
22
|
+
if (!opts.allow())
|
|
23
|
+
return;
|
|
24
|
+
opts.set_loading?.(true);
|
|
25
|
+
let drop_filename = ``;
|
|
26
|
+
try {
|
|
27
|
+
let url_error;
|
|
28
|
+
const handled = await handle_url_drop(event, opts.on_drop).catch((exc) => {
|
|
29
|
+
url_error = to_error(exc).message;
|
|
30
|
+
return false;
|
|
31
|
+
});
|
|
32
|
+
if (handled)
|
|
33
|
+
return;
|
|
34
|
+
const file = event.dataTransfer?.files[0];
|
|
35
|
+
if (!file) {
|
|
36
|
+
if (url_error)
|
|
37
|
+
opts.on_error?.(`Failed to load from URL: ${url_error}`);
|
|
10
38
|
return;
|
|
11
|
-
opts.set_loading?.(true);
|
|
12
|
-
let drop_filename = ``;
|
|
13
|
-
try {
|
|
14
|
-
let url_error;
|
|
15
|
-
const handled = await handle_url_drop(event, opts.on_drop).catch((exc) => {
|
|
16
|
-
url_error = exc instanceof Error ? exc.message : String(exc);
|
|
17
|
-
return false;
|
|
18
|
-
});
|
|
19
|
-
if (handled)
|
|
20
|
-
return;
|
|
21
|
-
const file = event.dataTransfer?.files[0];
|
|
22
|
-
if (!file) {
|
|
23
|
-
if (url_error)
|
|
24
|
-
opts.on_error?.(`Failed to load from URL: ${url_error}`);
|
|
25
|
-
return;
|
|
26
|
-
}
|
|
27
|
-
drop_filename = file.name;
|
|
28
|
-
const { content, filename } = await decompress_file(file);
|
|
29
|
-
if (content)
|
|
30
|
-
await opts.on_drop(content, filename);
|
|
31
|
-
}
|
|
32
|
-
catch (exc) {
|
|
33
|
-
const detail = exc instanceof Error ? exc.message : String(exc);
|
|
34
|
-
const msg = drop_filename
|
|
35
|
-
? `Failed to load file ${drop_filename}: ${detail}`
|
|
36
|
-
: `Failed to load file: ${detail}`;
|
|
37
|
-
opts.on_error?.(msg);
|
|
38
|
-
}
|
|
39
|
-
finally {
|
|
40
|
-
opts.set_loading?.(false);
|
|
41
39
|
}
|
|
42
|
-
|
|
43
|
-
}
|
|
40
|
+
drop_filename = file.name;
|
|
41
|
+
const { content, filename } = await decompress_file(file);
|
|
42
|
+
if (content)
|
|
43
|
+
await opts.on_drop(content, filename);
|
|
44
|
+
}
|
|
45
|
+
catch (exc) {
|
|
46
|
+
const detail = to_error(exc).message;
|
|
47
|
+
const msg = drop_filename
|
|
48
|
+
? `Failed to load file ${drop_filename}: ${detail}`
|
|
49
|
+
: `Failed to load file: ${detail}`;
|
|
50
|
+
opts.on_error?.(msg);
|
|
51
|
+
}
|
|
52
|
+
finally {
|
|
53
|
+
opts.set_loading?.(false);
|
|
54
|
+
}
|
|
55
|
+
};
|
package/dist/io/index.d.ts
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
export { default as ExportPane } from './ExportPane.svelte';
|
|
1
2
|
export * from './decompress';
|
|
2
3
|
export * from './export';
|
|
3
4
|
export * from './fetch';
|
|
@@ -5,3 +6,4 @@ export * from './file-drop';
|
|
|
5
6
|
export * from './is-binary';
|
|
6
7
|
export type * from './types';
|
|
7
8
|
export * from './url-drop';
|
|
9
|
+
export declare function strip_compression_extensions(filename: string): string;
|
package/dist/io/index.js
CHANGED
|
@@ -1,6 +1,16 @@
|
|
|
1
|
+
import { COMPRESSION_EXTENSIONS_REGEX } from '../constants';
|
|
2
|
+
export { default as ExportPane } from './ExportPane.svelte';
|
|
1
3
|
export * from './decompress';
|
|
2
4
|
export * from './export';
|
|
3
5
|
export * from './fetch';
|
|
4
6
|
export * from './file-drop';
|
|
5
7
|
export * from './is-binary';
|
|
6
8
|
export * from './url-drop';
|
|
9
|
+
// Lowercase a filename and strip all trailing compression extensions (.gz, .zip, ...)
|
|
10
|
+
export function strip_compression_extensions(filename) {
|
|
11
|
+
let base_name = filename.toLowerCase();
|
|
12
|
+
while (COMPRESSION_EXTENSIONS_REGEX.test(base_name)) {
|
|
13
|
+
base_name = base_name.replace(COMPRESSION_EXTENSIONS_REGEX, ``);
|
|
14
|
+
}
|
|
15
|
+
return base_name;
|
|
16
|
+
}
|
package/dist/io/types.d.ts
CHANGED
|
@@ -6,3 +6,16 @@ export interface FileInfo {
|
|
|
6
6
|
category?: string;
|
|
7
7
|
category_icon?: string;
|
|
8
8
|
}
|
|
9
|
+
export interface ExportItem {
|
|
10
|
+
label: string;
|
|
11
|
+
hint?: string;
|
|
12
|
+
disabled?: boolean;
|
|
13
|
+
on_download?: () => void;
|
|
14
|
+
copy_text?: () => string | null;
|
|
15
|
+
show_dpi?: boolean;
|
|
16
|
+
}
|
|
17
|
+
export interface ExportSection {
|
|
18
|
+
title?: string;
|
|
19
|
+
tooltip?: string;
|
|
20
|
+
items: ExportItem[];
|
|
21
|
+
}
|
package/dist/io/url-drop.js
CHANGED
|
@@ -1,7 +1,9 @@
|
|
|
1
1
|
import { load_binary_traj } from '../trajectory/parse';
|
|
2
|
-
|
|
2
|
+
import { decompress_data_binary } from './decompress';
|
|
3
|
+
const BINARY_EXTENSIONS = new Set(`h5 hdf5 traj npz pkl dat gz gzip zip bz2 xz brml raw`.split(` `));
|
|
3
4
|
const TEXT_EXTENSIONS = new Set(`xyz extxyz json cif poscar yaml yml txt md py js ts css html xml`.split(` `));
|
|
4
5
|
const VASP_BASENAME_RE = /^(poscar|xdatcar|contcar)$/i;
|
|
6
|
+
const GZ_EXT_RE = /\.(gz|gzip)$/i;
|
|
5
7
|
// Extract filename from Content-Disposition header, falling back to url_basename.
|
|
6
8
|
function extract_filename(headers, fallback) {
|
|
7
9
|
if (!headers)
|
|
@@ -9,9 +11,13 @@ function extract_filename(headers, fallback) {
|
|
|
9
11
|
const content_disposition_str = headers.get(`content-disposition`);
|
|
10
12
|
if (!content_disposition_str)
|
|
11
13
|
return fallback;
|
|
12
|
-
const star_match = /filename\*=(
|
|
14
|
+
const star_match = /filename\*=([^;]+)/i.exec(content_disposition_str);
|
|
13
15
|
if (star_match?.[1]) {
|
|
14
|
-
|
|
16
|
+
let raw = star_match[1].trim().replaceAll(/^"|"$/g, ``);
|
|
17
|
+
// Strip any RFC 5987 charset'language' prefix; bare values pass through unchanged
|
|
18
|
+
const ext_value_match = /^[\w!#$%&+^`{}~-]+'[\w-]*'(.*)$/.exec(raw);
|
|
19
|
+
if (ext_value_match)
|
|
20
|
+
raw = ext_value_match[1];
|
|
15
21
|
try {
|
|
16
22
|
return decodeURIComponent(raw);
|
|
17
23
|
}
|
|
@@ -20,7 +26,24 @@ function extract_filename(headers, fallback) {
|
|
|
20
26
|
}
|
|
21
27
|
}
|
|
22
28
|
const plain_match = /filename\s*=\s*"?([^";]+)"?/i.exec(content_disposition_str);
|
|
23
|
-
|
|
29
|
+
// truthiness check (not ??) so whitespace-only `filename=` values fall back too
|
|
30
|
+
const name = plain_match?.[1]?.trim();
|
|
31
|
+
if (!name)
|
|
32
|
+
return fallback;
|
|
33
|
+
return name;
|
|
34
|
+
}
|
|
35
|
+
const ext_of = (name) => name.split(`.`).pop()?.toLowerCase() ?? ``;
|
|
36
|
+
// Whether the file inside a .gz/.gzip wrapper is a known binary format that a
|
|
37
|
+
// lossy text decode would corrupt (bytes >= 0x80 → U+FFFD)
|
|
38
|
+
const has_binary_inner_ext = (filename) => BINARY_EXTENSIONS.has(ext_of(filename.replace(GZ_EXT_RE, ``)));
|
|
39
|
+
// Gunzip a fetched payload → [content, filename] with .gz/.gzip stripped; content
|
|
40
|
+
// stays an ArrayBuffer for binary inner formats, decoded string otherwise
|
|
41
|
+
async function decompress_gz_payload(buffer, filename) {
|
|
42
|
+
const decompressed = await decompress_data_binary(buffer, `gzip`);
|
|
43
|
+
const content = has_binary_inner_ext(filename)
|
|
44
|
+
? decompressed
|
|
45
|
+
: new TextDecoder().decode(decompressed);
|
|
46
|
+
return [content, filename.replace(GZ_EXT_RE, ``)];
|
|
24
47
|
}
|
|
25
48
|
// Handle URL-based file drop data by fetching content lazily
|
|
26
49
|
export async function handle_url_drop(drag_event, callback) {
|
|
@@ -40,8 +63,10 @@ export async function handle_url_drop(drag_event, callback) {
|
|
|
40
63
|
return true;
|
|
41
64
|
}
|
|
42
65
|
export async function load_from_url(url, callback) {
|
|
43
|
-
|
|
44
|
-
|
|
66
|
+
// Strip query string/hash before basename/extension detection so pre-signed
|
|
67
|
+
// URLs like traj.h5?X-Amz-Expires=300 still hit the right format path
|
|
68
|
+
const url_basename = url.split(/[?#]/)[0].split(`/`).pop() ?? url;
|
|
69
|
+
const ext = ext_of(url_basename);
|
|
45
70
|
if (BINARY_EXTENSIONS.has(ext)) {
|
|
46
71
|
// Force binary mode for known binary files to handle GitHub Pages content-type issues
|
|
47
72
|
const resp = await fetch(url);
|
|
@@ -51,17 +76,11 @@ export async function load_from_url(url, callback) {
|
|
|
51
76
|
// Handle gzipped files with proper content-encoding detection
|
|
52
77
|
if (ext === `gz` || ext === `gzip`) {
|
|
53
78
|
if (resp.headers.get(`content-encoding`) === `gzip`) {
|
|
54
|
-
// Browser
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
else {
|
|
58
|
-
// Need to decompress manually
|
|
59
|
-
const { decompress_data } = await import(`./decompress`);
|
|
60
|
-
const buffer = await resp.arrayBuffer();
|
|
61
|
-
const content = await decompress_data(buffer, `gzip`);
|
|
62
|
-
// Remove .gz extension when manually decompressing
|
|
63
|
-
return callback(content, filename.replace(/\.gz$/, ``));
|
|
79
|
+
// Browser already decompressed the stored .gz (GitHub Pages-style serving), so
|
|
80
|
+
// the body is the inner file — keep binary inner formats (.h5.gz, ...) binary
|
|
81
|
+
return callback(await (has_binary_inner_ext(filename) ? resp.arrayBuffer() : resp.text()), filename);
|
|
64
82
|
}
|
|
83
|
+
return callback(...(await decompress_gz_payload(await resp.arrayBuffer(), filename)));
|
|
65
84
|
}
|
|
66
85
|
// For H5 files, always load as binary regardless of signature
|
|
67
86
|
// to handle files that have .h5/.hdf5 extensions but may not have the proper HDF5 signature
|
|
@@ -82,40 +101,52 @@ export async function load_from_url(url, callback) {
|
|
|
82
101
|
const buffer = await load_binary_traj(resp, `.traj`);
|
|
83
102
|
return callback(buffer, filename);
|
|
84
103
|
}
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
104
|
+
// Content-Encoding is transparent transport compression: fetch already
|
|
105
|
+
// decompressed the body, so binary formats (npz, pkl, brml, ...) must still
|
|
106
|
+
// be read as ArrayBuffer — .text() would corrupt them via lossy UTF-8 decode
|
|
88
107
|
return callback(await resp.arrayBuffer(), filename);
|
|
89
108
|
}
|
|
90
109
|
// Skip Range requests for known text formats to avoid production server issues
|
|
91
110
|
// Include VASP files that don't have extensions (POSCAR, XDATCAR, CONTCAR)
|
|
92
111
|
const is_known_text = TEXT_EXTENSIONS.has(ext) || VASP_BASENAME_RE.test(url_basename);
|
|
93
|
-
let
|
|
112
|
+
let sniffed_callback_args;
|
|
94
113
|
if (!is_known_text) {
|
|
114
|
+
// Only the Range sniff is guarded (failure → plain text fetch). Once magic bytes
|
|
115
|
+
// commit to a binary format, download/decompress errors must propagate instead of
|
|
116
|
+
// falling through to a text fetch that would parse the binary bytes as garbage.
|
|
117
|
+
let sniffed = null;
|
|
95
118
|
try {
|
|
96
|
-
// Check for magic bytes only for unknown formats
|
|
119
|
+
// Check for magic bytes only for unknown formats (covers extensionless URLs
|
|
120
|
+
// like blob: object URLs whose basenames are UUIDs)
|
|
97
121
|
const head = await fetch(url, { headers: { Range: `bytes=0-15` } });
|
|
98
122
|
if (head.ok) {
|
|
99
123
|
const buf = new Uint8Array(await head.arrayBuffer());
|
|
100
124
|
const is_gzip = buf[0] === 0x1f && buf[1] === 0x8b;
|
|
101
125
|
const is_hdf5 = buf[0] === 0x89 && buf[1] === 0x48 && buf[2] === 0x44 && buf[3] === 0x46;
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
extract_filename(resp.headers, url_basename),
|
|
109
|
-
];
|
|
110
|
-
}
|
|
126
|
+
// ASE .traj files start with the Ulm signature "- of Ulm"
|
|
127
|
+
const is_ase_traj = [0x2d, 0x20, 0x6f, 0x66, 0x20, 0x55, 0x6c, 0x6d].every((byte, idx) => buf[idx] === byte);
|
|
128
|
+
if (is_gzip)
|
|
129
|
+
sniffed = `gzip`;
|
|
130
|
+
else if (is_hdf5 || is_ase_traj)
|
|
131
|
+
sniffed = `binary`;
|
|
111
132
|
}
|
|
112
133
|
}
|
|
113
134
|
catch {
|
|
114
|
-
// Fall through to text fetch if HEAD request fails
|
|
135
|
+
// Fall through to text fetch if the Range HEAD request fails
|
|
136
|
+
}
|
|
137
|
+
if (sniffed) {
|
|
138
|
+
const resp = await fetch(url);
|
|
139
|
+
if (!resp.ok)
|
|
140
|
+
throw new Error(`Fetch failed: ${resp.status}`);
|
|
141
|
+
const filename = extract_filename(resp.headers, url_basename);
|
|
142
|
+
const buffer = await resp.arrayBuffer();
|
|
143
|
+
// Gunzip sniffed gzip — downstream parsers can't handle raw gzip bytes
|
|
144
|
+
sniffed_callback_args =
|
|
145
|
+
sniffed === `gzip` ? await decompress_gz_payload(buffer, filename) : [buffer, filename];
|
|
115
146
|
}
|
|
116
147
|
}
|
|
117
|
-
if (
|
|
118
|
-
return callback(...
|
|
148
|
+
if (sniffed_callback_args)
|
|
149
|
+
return callback(...sniffed_callback_args);
|
|
119
150
|
const resp = await fetch(url);
|
|
120
151
|
if (!resp.ok)
|
|
121
152
|
throw new Error(`Fetch failed: ${resp.status}`);
|