Compare commits
10 Commits
9658839dc7
...
ef72904fb5
| Author | SHA1 | Date | |
|---|---|---|---|
| ef72904fb5 | |||
|
|
e38c5b87ee | ||
|
|
161f7dd8ea | ||
|
|
7ac5b87016 | ||
|
|
a462e80882 | ||
|
|
1df45b1590 | ||
|
|
3fbd8da66f | ||
|
|
7b41673594 | ||
|
|
fd6590d819 | ||
|
|
6da66b5990 |
2
.gitignore
vendored
2
.gitignore
vendored
@@ -1,3 +1,5 @@
|
|||||||
|
.conda-env
|
||||||
|
dispersion_config.toml
|
||||||
pyrightconfig.json
|
pyrightconfig.json
|
||||||
.DS_Store
|
.DS_Store
|
||||||
|
|
||||||
|
|||||||
41
README.md
41
README.md
@@ -1,7 +1,3 @@
|
|||||||
# Crash course on Python installation, with a few small side tracks
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
# Installation
|
# Installation
|
||||||
1. If not already done so, create a virtual environment to contain all the packages required. Python 3.10 is recommended. The command below will create a new environment named 'app-env' with the latest version of Python 3.10.
|
1. If not already done so, create a virtual environment to contain all the packages required. Python 3.10 is recommended. The command below will create a new environment named 'app-env' with the latest version of Python 3.10.
|
||||||
|
|
||||||
@@ -11,6 +7,39 @@ conda create -y -n app-env python=3.10
|
|||||||
|
|
||||||
conda activate app-env
|
conda activate app-env
|
||||||
|
|
||||||
3. The prompt should now read '(app-env)' on the left. The app is not published on Github or anywhere else. The link below points to my own personnal home server (I didn't find any way of getting a direct download link You are now ready to install everything with this command:
|
3. The prompt should now read '(app-env)' on the left. The app is not published on Github or anywhere else. The link below points to the webserver running on the FibNas server. You are now ready to install everything with this command:
|
||||||
|
|
||||||
|
pip install http://130.92.113.172/dispersionapp.zip
|
||||||
|
|
||||||
|
# Usage
|
||||||
|
|
||||||
|
1. Make sure your environment is activated (step 1 above)
|
||||||
|
|
||||||
|
2. call the `dispersionapp` command
|
||||||
|
|
||||||
|
dispersionapp
|
||||||
|
|
||||||
|
2*. this can be also done via calling python first (`-m` tells python to open the specified module)
|
||||||
|
|
||||||
|
python -m dispersionapp
|
||||||
|
|
||||||
|
# Interface
|
||||||
|
|
||||||
|
At the very top is a summary of the configuration as well as a few physical properties derived from the current parameters.
|
||||||
|
|
||||||
|
Below, you will find the parameter list. Each parameter has a couple elements. From left to right :
|
||||||
|
- the name of the paramter
|
||||||
|
- a slider to quickly explore values
|
||||||
|
- arrow buttons to move from one value to the next.
|
||||||
|
- a text box where you can input your desired value. The closest possible value will then be selected. Possible values are hard-coded. I might add an option for custom values later on.
|
||||||
|
|
||||||
|
To navigate the plot:
|
||||||
|
- left-click+drag to move around
|
||||||
|
- right-click+drag to zoom
|
||||||
|
- scroll wheel to zoom
|
||||||
|
- for each of these movement, you can do it while the cursor is hovering over one of the axis. In that case, only that axis is affected.
|
||||||
|
- to go back to a view that fits everything, click on the small "A" at the bottom left. This is not ideal for the dispersion plot because of all the resonances, so you can find another reset button in the parameter list.
|
||||||
|
- to hide/show a line, click on it in the legend. You can also click+drag on the legend to move it around.
|
||||||
|
- click+drag on the purble title bar to move plots around (it's a bit buggy)
|
||||||
|
- double click on the purple title bar (left side or top) to pop out the plot in its own window.
|
||||||
|
|
||||||
pip install https://bao.dedebenui.me/s/f3KgiqMq7giN73i/download
|
|
||||||
|
|||||||
@@ -1,17 +1,19 @@
|
|||||||
[project]
|
[project]
|
||||||
name = "dispersionapp"
|
name = "dispersionapp"
|
||||||
version = "0.1.0"
|
version = "0.2.2"
|
||||||
description = "Model hollow capillary and revolver fiber interactively"
|
description = "Model hollow capillary and revolver fiber interactively"
|
||||||
authors = [{ name = "Benoît Sierro", email = "benoit.sierro@unibe.ch" }]
|
authors = [{ name = "Dedebenui", email = "dedebenui@protonmail.com" }]
|
||||||
|
requires-python = ">=3.13"
|
||||||
|
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"scgenerator @ git+https://github.com/bsierro/scgenerator.git",
|
|
||||||
"click",
|
"click",
|
||||||
"pydantic",
|
"pydantic >= 2",
|
||||||
"tomli",
|
"tomli",
|
||||||
"tomli_w",
|
"tomli_w",
|
||||||
"PySide6 >= 6.4.0",
|
"PySide6 >= 6.4.0",
|
||||||
"pyqtgraph >= 0.13.1",
|
"pyqtgraph >= 0.13.1",
|
||||||
|
"numba>=0.62.1",
|
||||||
|
"scipy>=1.16.3",
|
||||||
]
|
]
|
||||||
|
|
||||||
license = { file = "LICENSE" }
|
license = { file = "LICENSE" }
|
||||||
@@ -25,5 +27,17 @@ classifiers = [
|
|||||||
dispersionapp = "dispersionapp.__main__:main"
|
dispersionapp = "dispersionapp.__main__:main"
|
||||||
|
|
||||||
[build-system]
|
[build-system]
|
||||||
build-backend = "setuptools.build_meta"
|
requires = ["hatchling"]
|
||||||
requires = ["setuptools >= 65.0.0"]
|
build-backend = "hatchling.build"
|
||||||
|
|
||||||
|
[tool.pyright]
|
||||||
|
exclude = [".venv"]
|
||||||
|
venvPath = "."
|
||||||
|
venv = ".venv"
|
||||||
|
typeCheckingMode = "off"
|
||||||
|
|
||||||
|
[dependency-groups]
|
||||||
|
dev = [
|
||||||
|
"matplotlib>=3.10.7",
|
||||||
|
]
|
||||||
|
|
||||||
|
|||||||
@@ -3,7 +3,7 @@ import sys
|
|||||||
|
|
||||||
import click
|
import click
|
||||||
|
|
||||||
from dispersionapp.core import DEFAULT_CONFIG_FILE
|
from dispersionapp.core import DEFAULT_CONFIG_FILE, Config
|
||||||
from dispersionapp.gui import app
|
from dispersionapp.gui import app
|
||||||
|
|
||||||
|
|
||||||
@@ -11,12 +11,17 @@ from dispersionapp.gui import app
|
|||||||
@click.option(
|
@click.option(
|
||||||
"-c",
|
"-c",
|
||||||
"--config",
|
"--config",
|
||||||
|
"config_file",
|
||||||
default=DEFAULT_CONFIG_FILE,
|
default=DEFAULT_CONFIG_FILE,
|
||||||
help="configuration file in TOML format",
|
help="configuration file in TOML format",
|
||||||
type=click.Path(file_okay=True, dir_okay=False, resolve_path=True),
|
type=click.Path(file_okay=True, dir_okay=False, resolve_path=True),
|
||||||
)
|
)
|
||||||
|
@click.option("-g", "--gas", help="Gas. Must be one of ", type=str)
|
||||||
@click.version_option()
|
@click.version_option()
|
||||||
def main(config: os.PathLike):
|
def main(config_file: os.PathLike, gas: str | None = None):
|
||||||
|
config = Config.load(config_file)
|
||||||
|
if gas is not None:
|
||||||
|
config.gas = gas.lower()
|
||||||
app(config)
|
app(config)
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -1,33 +1,39 @@
|
|||||||
from __future__ import annotations
|
from __future__ import annotations
|
||||||
|
import os
|
||||||
|
|
||||||
import sys
|
import sys
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from typing import NamedTuple
|
from typing import Annotated, NamedTuple, Self
|
||||||
|
|
||||||
import numpy as np
|
import numpy as np
|
||||||
import scgenerator as sc
|
|
||||||
import tomli
|
import tomli
|
||||||
import tomli_w
|
import tomli_w
|
||||||
from pydantic import BaseModel, PrivateAttr, ValidationError, confloat, conint
|
from pydantic import BaseModel, PrivateAttr, ValidationError, Field
|
||||||
|
|
||||||
DEFAULT_CONFIG_FILE = "dispersion_config.toml"
|
import dispersionapp.physics.units as units
|
||||||
|
import dispersionapp.physics.materials as materials
|
||||||
|
import dispersionapp.physics.pulse as pulse
|
||||||
|
import dispersionapp.physics.fiber as fiber
|
||||||
|
import dispersionapp.math as math
|
||||||
|
|
||||||
|
DEFAULT_CONFIG_FILE = Path.home() / "dispersion_config.toml"
|
||||||
|
|
||||||
|
|
||||||
class CurrentState(BaseModel):
|
class CurrentState(BaseModel):
|
||||||
core_diameter_um: float
|
core_diameter_um: float
|
||||||
pressure_mbar: float
|
pressure_mbar: float
|
||||||
wall_thickness_um: float
|
wall_thickness_um: float
|
||||||
|
num_resonances: Annotated[int, Field(ge=6, le=40)] = 6
|
||||||
n_tubes: int
|
n_tubes: int
|
||||||
gap_um: float
|
gap_um: float
|
||||||
t_fwhm_fs: float
|
t_fwhm_fs: float
|
||||||
|
|
||||||
|
|
||||||
class Config(BaseModel):
|
class Config(BaseModel):
|
||||||
wl_min: confloat(ge=100, le=1000) = 160
|
wl_min: Annotated[float, Field(ge=100, le=1000)] = 160
|
||||||
wl_max: confloat(ge=500, le=6000) = 1600
|
wl_max: Annotated[float, Field(ge=500, le=6000)] = 1600
|
||||||
wl_pump: confloat(ge=200, le=6000) = 800
|
wl_pump: Annotated[float, Field(ge=200, le=6000)] = 800
|
||||||
rep_rate: confloat(gt=0) = 8e3
|
rep_rate: Annotated[float, Field(gt=0)] = 8e3
|
||||||
num_resonances: conint(ge=6, le=20) = 6
|
|
||||||
gas: str = "argon"
|
gas: str = "argon"
|
||||||
safety_factor: float = 10.0
|
safety_factor: float = 10.0
|
||||||
current_state: CurrentState | None = None
|
current_state: CurrentState | None = None
|
||||||
@@ -35,7 +41,7 @@ class Config(BaseModel):
|
|||||||
_file_name: Path = PrivateAttr()
|
_file_name: Path = PrivateAttr()
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def load(cls, config_file: str | None = None) -> Config:
|
def load(cls, config_file: os.PathLike | None = None) -> Self:
|
||||||
config_file = Path(config_file or DEFAULT_CONFIG_FILE)
|
config_file = Path(config_file or DEFAULT_CONFIG_FILE)
|
||||||
if not config_file.exists():
|
if not config_file.exists():
|
||||||
config_file.touch()
|
config_file.touch()
|
||||||
@@ -45,7 +51,7 @@ class Config(BaseModel):
|
|||||||
try:
|
try:
|
||||||
out = cls(**d)
|
out = cls(**d)
|
||||||
except ValidationError as e:
|
except ValidationError as e:
|
||||||
s = f"invalid input in config file {config_file}:\n{e}"
|
s = f"invalid input in config file {config_file}:\n{e}\ncreating new config"
|
||||||
print(s)
|
print(s)
|
||||||
sys.exit(1)
|
sys.exit(1)
|
||||||
out._file_name = Path(config_file)
|
out._file_name = Path(config_file)
|
||||||
@@ -54,16 +60,24 @@ class Config(BaseModel):
|
|||||||
def save(self):
|
def save(self):
|
||||||
tmp = self._file_name.parent / f"{self._file_name.name}.tmp"
|
tmp = self._file_name.parent / f"{self._file_name.name}.tmp"
|
||||||
with open(tmp, "wb") as file:
|
with open(tmp, "wb") as file:
|
||||||
tomli_w.dump(self.dict(), file)
|
tomli_w.dump(self.model_dump(), file)
|
||||||
tmp.replace(self._file_name)
|
tmp.replace(self._file_name)
|
||||||
|
|
||||||
def update_current(
|
def update_current(
|
||||||
self, core_diameter_um, pressure_mbar, wall_thickness_um, n_tubes, gap_um, t_fwhm_fs
|
self,
|
||||||
|
core_diameter_um: float,
|
||||||
|
pressure_mbar: float,
|
||||||
|
wall_thickness_um: float,
|
||||||
|
num_resonances: int,
|
||||||
|
n_tubes: int,
|
||||||
|
gap_um: float,
|
||||||
|
t_fwhm_fs: float,
|
||||||
):
|
):
|
||||||
self.current_state = CurrentState(
|
self.current_state = CurrentState(
|
||||||
core_diameter_um=core_diameter_um,
|
core_diameter_um=core_diameter_um,
|
||||||
pressure_mbar=pressure_mbar,
|
pressure_mbar=pressure_mbar,
|
||||||
wall_thickness_um=wall_thickness_um,
|
wall_thickness_um=wall_thickness_um,
|
||||||
|
num_resonances=num_resonances,
|
||||||
n_tubes=n_tubes,
|
n_tubes=n_tubes,
|
||||||
gap_um=gap_um,
|
gap_um=gap_um,
|
||||||
t_fwhm_fs=t_fwhm_fs,
|
t_fwhm_fs=t_fwhm_fs,
|
||||||
@@ -80,12 +94,16 @@ class LimitValues(NamedTuple):
|
|||||||
|
|
||||||
def b2(w, n_eff):
|
def b2(w, n_eff):
|
||||||
dw = w[1] - w[0]
|
dw = w[1] - w[0]
|
||||||
beta = sc.fiber.beta(w, n_eff)
|
beta = fiber.beta(w, n_eff)
|
||||||
return sc.math.differentiate_arr(beta, 2, 4, dw)
|
return math.differentiate_arr(beta, 2, 4, dw)
|
||||||
|
|
||||||
|
|
||||||
def N_sf_max(
|
def N_sf_max(
|
||||||
wl: np.ndarray, t0: float, wl_zero_disp: float, gas: sc.materials.Gas, safety: float = 10.0
|
wl: np.ndarray,
|
||||||
|
t0: float,
|
||||||
|
wl_zero_disp: float,
|
||||||
|
gas: materials.Gas,
|
||||||
|
safety: float = 10.0,
|
||||||
) -> np.ndarray:
|
) -> np.ndarray:
|
||||||
"""
|
"""
|
||||||
maximum soliton number according to self focusing
|
maximum soliton number according to self focusing
|
||||||
@@ -97,30 +115,34 @@ def N_sf_max(
|
|||||||
|
|
||||||
|
|
||||||
def N_ion_max(
|
def N_ion_max(
|
||||||
wl: np.ndarray, t0: float, wl_zero_disp: float, gas: sc.materials.Gas, safety: float = 10.0
|
wl: np.ndarray,
|
||||||
|
t0: float,
|
||||||
|
wl_zero_disp: float,
|
||||||
|
gas: materials.Gas,
|
||||||
|
safety: float = 10.0,
|
||||||
) -> np.ndarray:
|
) -> np.ndarray:
|
||||||
"""
|
"""
|
||||||
eq. S16 in Travers2019
|
eq. S16 in Travers2019
|
||||||
"""
|
"""
|
||||||
ind = sc.math.argclosest(wl, wl_zero_disp)
|
ind = math.argclosest(wl, wl_zero_disp)
|
||||||
f = np.gradient(np.gradient(gas.sellmeier.chi(wl), wl), wl)
|
f = np.gradient(np.gradient(gas.sellmeier.chi(wl), wl), wl)
|
||||||
factor = (sc.math.u_nm(1, 1) / sc.units.c) ** 2 * (0.5 * wl / np.pi) ** 3
|
factor = (math.u_nm(1, 1) / units.c) ** 2 * (0.5 * wl / np.pi) ** 3
|
||||||
delta = factor * (f / f[ind] - 1)
|
delta = factor * (f / f[ind] - 1)
|
||||||
denom = safety * np.pi * wl * np.abs(delta) * f[ind]
|
denom = safety * np.pi * wl * np.abs(delta) * f[ind]
|
||||||
return t0 * sc.math.u_nm(1, 1) * np.sqrt(gas.n2() * gas.barrier_suppression / denom)
|
return t0 * math.u_nm(1, 1) * np.sqrt(gas.n2() * gas.barrier_suppression / denom)
|
||||||
|
|
||||||
|
|
||||||
def solition_num(
|
def solition_num(
|
||||||
t0: float, w0: float, beta2: float, n2: float, core_radius: float, peak_power: float
|
t0: float, w0: float, beta2: float, n2: float, core_radius: float, peak_power: float
|
||||||
) -> float:
|
) -> float:
|
||||||
gamma = sc.fiber.gamma_parameter(n2, w0, sc.fiber.A_eff_marcatili(core_radius))
|
gamma = fiber.gamma_parameter(n2, w0, fiber.effective_area_marcatili(core_radius))
|
||||||
ld = sc.pulse.L_D(t0, beta2)
|
ld = pulse.dispersion_length(t0, beta2)
|
||||||
return np.sqrt(gamma * ld * peak_power)
|
return np.sqrt(gamma * ld * peak_power)
|
||||||
|
|
||||||
|
|
||||||
def energy(
|
def energy(
|
||||||
t0: float, w0: float, beta2: float, n2: float, core_radius: float, solition_num: float
|
t0: float, w0: float, beta2: float, n2: float, core_radius: float, solition_num: float
|
||||||
) -> float:
|
) -> float:
|
||||||
gamma = sc.fiber.gamma_parameter(n2, w0, sc.fiber.A_eff_marcatili(core_radius))
|
gamma = fiber.gamma_parameter(n2, w0, fiber.effective_area_marcatili(core_radius))
|
||||||
peak_power = solition_num**2 * abs(beta2) / (t0**2 * gamma)
|
peak_power = solition_num**2 * abs(beta2) / (t0**2 * gamma)
|
||||||
return sc.pulse.P0_to_E0(peak_power, t0, "sech")
|
return pulse.P0_to_E0(peak_power, t0, "sech")
|
||||||
|
|||||||
10
src/dispersionapp/data/README.md
Normal file
10
src/dispersionapp/data/README.md
Normal file
@@ -0,0 +1,10 @@
|
|||||||
|
# `materials.json`
|
||||||
|
Contains material property like Sellmeir coefficients, nonlinear refractive index and Van der Waals constants.
|
||||||
|
|
||||||
|
Sources are embeded in the document and are completed as such:
|
||||||
|
Van der Waals constants : https://en.wikipedia.org/wiki/Van_der_Waals_constants_(data_page)
|
||||||
|
Chi3 : Wahlstrand 2012
|
||||||
|
|
||||||
|
# `raman_response.csv`
|
||||||
|
Raman impulse response recovered from measured gain spectrum. This is used then `raman_type` is set to `"measured"` (Stolen1989).
|
||||||
|
|
||||||
0
src/dispersionapp/data/__init__.py
Normal file
0
src/dispersionapp/data/__init__.py
Normal file
449
src/dispersionapp/data/materials.json
Normal file
449
src/dispersionapp/data/materials.json
Normal file
@@ -0,0 +1,449 @@
|
|||||||
|
{
|
||||||
|
"air":
|
||||||
|
{
|
||||||
|
"a": 0.1358,
|
||||||
|
"atomic_mass": 4.809e-26,
|
||||||
|
"atomic_number": 7.14,
|
||||||
|
"b": 3.64e-5,
|
||||||
|
"kerr":
|
||||||
|
{
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 293.15,
|
||||||
|
"n2": 4e-23,
|
||||||
|
"source": "Nibbering, E., Grillon, G., Franco, M.A., Prade, B., Mysyrowicz, A., 1997. JOSA B 14, 650–660."
|
||||||
|
},
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
57921050000,
|
||||||
|
1679170000
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
2.380185e+14,
|
||||||
|
5.7362e+13
|
||||||
|
],
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 288.15,
|
||||||
|
"kind": 2
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"argon":
|
||||||
|
{
|
||||||
|
"a": 0.1355,
|
||||||
|
"atomic_mass": 6.6338e-26,
|
||||||
|
"atomic_number": 18,
|
||||||
|
"b": 3.201e-5,
|
||||||
|
"ionization_energy": 2.5249661793774e-18,
|
||||||
|
"kerr":
|
||||||
|
{
|
||||||
|
"P0": 30400,
|
||||||
|
"T0": 273.15,
|
||||||
|
"n2": 9.7e-24,
|
||||||
|
"source": "Wahlstrand, J. K., Cheng, Y. H., & Milchberg, H. M. (2012). High field optical nonlinearity and the Kramers-Kronig relations. Physical review letters, 109(11), 113904."
|
||||||
|
},
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
2501410000,
|
||||||
|
500283000,
|
||||||
|
52234300000
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
9.1012e+13,
|
||||||
|
8.7892e+13,
|
||||||
|
2.1402e+14
|
||||||
|
],
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 273.15,
|
||||||
|
"kind": 2,
|
||||||
|
"source": "A. Bideau-Mehu, Y. Guern, R. Abjean, A. Johannin-Gilles. Measurement of refractive indices of neon, argon, krypton and xenon in the 253.7-140.4 nm wavelength range. Dispersion relations and estimated oscillator strengths of the resonance lines. J. Quant. Spectrosc. Rad. Transfer 25, 395-402 (1981)"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"argon_alt":
|
||||||
|
{
|
||||||
|
"a": 0.1355,
|
||||||
|
"atomic_mass": 6.6338e-26,
|
||||||
|
"atomic_number": 18,
|
||||||
|
"b": 3.201e-5,
|
||||||
|
"kerr":
|
||||||
|
{
|
||||||
|
"P0": 30400,
|
||||||
|
"T0": 273.15,
|
||||||
|
"n2": 9.7e-24,
|
||||||
|
"source": "Wahlstrand, J. K., Cheng, Y. H., & Milchberg, H. M. (2012). High field optical nonlinearity and the Kramers-Kronig relations. Physical review letters, 109(11), 113904."
|
||||||
|
},
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
0.0002033229,
|
||||||
|
0.0003445831
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
2.0612e-16,
|
||||||
|
8.066e-15
|
||||||
|
],
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 273.15,
|
||||||
|
"kind": 1,
|
||||||
|
"source": "A. Börzsönyi, Z. Heiner, M. P. Kalashnikov, A. P. Kovács, and K. Osvay, Dispersion measurement of inert gases and gas mixtures at 800 nm, Appl. Opt. 47, 4856-4863 (2008)"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"argon_alt2":
|
||||||
|
{
|
||||||
|
"a": 0.1355,
|
||||||
|
"b": 3.201e-5,
|
||||||
|
"kerr":
|
||||||
|
{
|
||||||
|
"P0": 30400,
|
||||||
|
"T0": 273.15,
|
||||||
|
"n2": 9.7e-24,
|
||||||
|
"source": "Wahlstrand, J. K., Cheng, Y. H., & Milchberg, H. M. (2012). High field optical nonlinearity and the Kramers-Kronig relations. Physical review letters, 109(11), 113904."
|
||||||
|
},
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
0.030182943
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
1.44e+14
|
||||||
|
],
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 273.15,
|
||||||
|
"const": 6.7867e-5,
|
||||||
|
"kind": 2,
|
||||||
|
"source": "E. R. Peck and D. J. Fisher. Dispersion of argon, J. Opt. Soc. Am. 54, 1362-1364 (1964)"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"d-zlaf52la":
|
||||||
|
{
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
-8487502830,
|
||||||
|
3.1753525,
|
||||||
|
3.71301651e-14,
|
||||||
|
-1.09609062e-27,
|
||||||
|
2.4418582e-40,
|
||||||
|
-8.94583294e-54
|
||||||
|
],
|
||||||
|
"C": [],
|
||||||
|
"kind": 3,
|
||||||
|
"reference":
|
||||||
|
[
|
||||||
|
"CDGM Zemax catalog 2017-09 (obtained from http://www.cdgmgd.com)"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"e7":
|
||||||
|
{
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
0,
|
||||||
|
7.2e-15,
|
||||||
|
3e-28
|
||||||
|
],
|
||||||
|
"C": [],
|
||||||
|
"kind": 3,
|
||||||
|
"reference":
|
||||||
|
[
|
||||||
|
"J. Li, C. H. Wen, S. Gauza, R. Lu and S. T. Wu. Refractive indices of liquid crystals for display applications, J. Disp. Technol. 1, 51-61, 2005"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"helium":
|
||||||
|
{
|
||||||
|
"a": 0.00346,
|
||||||
|
"atomic_mass": 6.646477e-27,
|
||||||
|
"atomic_number": 2,
|
||||||
|
"b": 2.38e-5,
|
||||||
|
"ionization_energy": 3.9393356074281e-18,
|
||||||
|
"kerr":
|
||||||
|
{
|
||||||
|
"P0": 30400,
|
||||||
|
"T0": 273.15,
|
||||||
|
"n2": 3.1e-25,
|
||||||
|
"source": "Wahlstrand, J. K., Cheng, Y. H., & Milchberg, H. M. (2012). High field optical nonlinearity and the Kramers-Kronig relations. Physical review letters, 109(11), 113904."
|
||||||
|
},
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
2.16463842e-5,
|
||||||
|
2.10561127e-7,
|
||||||
|
4.7509272e-5
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
-6.80769781e-16,
|
||||||
|
5.13251289e-15,
|
||||||
|
3.18621354e-15
|
||||||
|
],
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 273.15,
|
||||||
|
"kind": 1,
|
||||||
|
"source": "A. Ermolov, K. F. Mak, M. H. Frosz, J. C. Travers, P. St. J. Russell, Supercontinuum generation in the vacuum ultraviolet through dispersive-wave and soliton-plasma interaction in a noble-gas-filled hollow-core photonic crystal fiber, Phys. Rev. A 92, 033821 (2015)"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"helium_alt":
|
||||||
|
{
|
||||||
|
"a": 0.00346,
|
||||||
|
"b": 2.38e-5,
|
||||||
|
"kerr":
|
||||||
|
{
|
||||||
|
"P0": 30400,
|
||||||
|
"T0": 273.15,
|
||||||
|
"n2": 3.1e-25
|
||||||
|
},
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
14755297000
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
4.262974e+14
|
||||||
|
],
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 273.15,
|
||||||
|
"kind": 2,
|
||||||
|
"source": " C. Cuthbertson and M. Cuthbertson. The refraction and dispersion of neon and helium. Proc. R. Soc. London A 135, 40-47 (1936)"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"hydrogen":
|
||||||
|
{
|
||||||
|
"a": 0.02453,
|
||||||
|
"atomic_mass": 1.674e-27,
|
||||||
|
"b": 2.651e-5,
|
||||||
|
"kerr":
|
||||||
|
{
|
||||||
|
"P0": 30400,
|
||||||
|
"T0": 273.15,
|
||||||
|
"n2": 6.36e-24,
|
||||||
|
"source": "Shelton, D. P., & Rice, J. E. (1994). Measurements and calculations of the hyperpolarizabilities of atoms and small molecules in the gas phase. Chemical Reviews, 94(1), 3-29"
|
||||||
|
},
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
0.0148956,
|
||||||
|
0.0049037
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
1.807e-10,
|
||||||
|
9.2e-11
|
||||||
|
],
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 273.15,
|
||||||
|
"kind": 2,
|
||||||
|
"source": "E. R. Peck and S. Hung. Refractivity and dispersion of hydrogen in the visible and near infrared, J. Opt. Soc. Am. 67, 1550-1554 (1977)"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"krypton":
|
||||||
|
{
|
||||||
|
"a": 0.2349,
|
||||||
|
"atomic_mass": 1.3915e-25,
|
||||||
|
"atomic_number": 36,
|
||||||
|
"b": 3.978e-5,
|
||||||
|
"ionization_energy": 2.2429831039374e-18,
|
||||||
|
"kerr":
|
||||||
|
{
|
||||||
|
"P0": 30400,
|
||||||
|
"T0": 273.15,
|
||||||
|
"n2": 2.2e-23,
|
||||||
|
"source": "Wahlstrand, J. K., Cheng, Y. H., & Milchberg, H. M. (2012). High field optical nonlinearity and the Kramers-Kronig relations. Physical review letters, 109(11), 113904."
|
||||||
|
},
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
2536370000,
|
||||||
|
2736490000,
|
||||||
|
62080200000
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
6.54742e+13,
|
||||||
|
7.3698e+13,
|
||||||
|
1.8108e+14
|
||||||
|
],
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 273.15,
|
||||||
|
"kind": 2
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"nbk7":
|
||||||
|
{
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
1.03961212,
|
||||||
|
0.231792344,
|
||||||
|
1.01046945
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
6.00069867e-15,
|
||||||
|
2.00179144e-14,
|
||||||
|
1.03560653e-10
|
||||||
|
],
|
||||||
|
"kind": 1,
|
||||||
|
"reference":
|
||||||
|
[
|
||||||
|
"SCHOTT Zemax catalog 2017-01-20b (obtained from http://www.schott.com)"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"neon":
|
||||||
|
{
|
||||||
|
"a": 0.02135,
|
||||||
|
"atomic_mass": 3.35092e-26,
|
||||||
|
"atomic_number": 10,
|
||||||
|
"b": 1.709e-5,
|
||||||
|
"ionization_energy": 3.45501365359425e-18,
|
||||||
|
"kerr":
|
||||||
|
{
|
||||||
|
"P0": 30400,
|
||||||
|
"T0": 273.15,
|
||||||
|
"n2": 8.7e-25,
|
||||||
|
"source": "Wahlstrand, J. K., Cheng, Y. H., & Milchberg, H. M. (2012). High field optical nonlinearity and the Kramers-Kronig relations. Physical review letters, 109(11), 113904."
|
||||||
|
},
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
1281450000,
|
||||||
|
22048600000
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
1.84661e+14,
|
||||||
|
3.7684e+14
|
||||||
|
],
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 273.15,
|
||||||
|
"kind": 2
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"nitrogen":
|
||||||
|
{
|
||||||
|
"a": 0.137,
|
||||||
|
"atomic_mass": 2.3259e-26,
|
||||||
|
"atomic_number": 7,
|
||||||
|
"b": 1.709e-5,
|
||||||
|
"kerr":
|
||||||
|
{
|
||||||
|
"P0": 30400,
|
||||||
|
"T0": 273.15,
|
||||||
|
"n2": 2.2e-23,
|
||||||
|
"source": "Wahlstrand, J. K., Cheng, Y. H., & Milchberg, H. M. (2012). High field optical nonlinearity and the Kramers-Kronig relations. Physical review letters, 109(11), 113904."
|
||||||
|
},
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
32431570000
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
1.44e+14
|
||||||
|
],
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 273.15,
|
||||||
|
"const": 6.8552e-5,
|
||||||
|
"kind": 2
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"silica":
|
||||||
|
{
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
0.6961663,
|
||||||
|
0.4079426,
|
||||||
|
0.8974794
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
4.67914826e-15,
|
||||||
|
1.35120631e-14,
|
||||||
|
9.79340025e-11
|
||||||
|
],
|
||||||
|
"kind": 1,
|
||||||
|
"reference":
|
||||||
|
[
|
||||||
|
"I. H. Malitson. Interspecimen comparison of the refractive index of fused silica, J. Opt. Soc. Am. 55, 1205-1208 (1965)",
|
||||||
|
"C. Z. Tan. Determination of refractive index of silica glass for infrared wavelengths by IR spectroscopy, J. Non-Cryst. Solids 223, 158-163 (1998)"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"vacuum":
|
||||||
|
{
|
||||||
|
"a": 0,
|
||||||
|
"atomic_mass": 0,
|
||||||
|
"atomic_number": 1,
|
||||||
|
"b": 0,
|
||||||
|
"kerr":
|
||||||
|
{
|
||||||
|
"P0": 30400,
|
||||||
|
"T0": 273.15,
|
||||||
|
"n2": 0,
|
||||||
|
"source": "none"
|
||||||
|
},
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B": [],
|
||||||
|
"C": [],
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 273.15,
|
||||||
|
"kind": 1
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"xenon":
|
||||||
|
{
|
||||||
|
"a": 0.425,
|
||||||
|
"atomic_mass": 2.18017e-25,
|
||||||
|
"atomic_number": 54,
|
||||||
|
"b": 5.105e-5,
|
||||||
|
"ionization_energy": 1.94342415157935e-18,
|
||||||
|
"kerr":
|
||||||
|
{
|
||||||
|
"P0": 30400,
|
||||||
|
"T0": 273.15,
|
||||||
|
"n2": 5.8e-23,
|
||||||
|
"source": "Wahlstrand, J. K., Cheng, Y. H., & Milchberg, H. M. (2012). High field optical nonlinearity and the Kramers-Kronig relations. Physical review letters, 109(11), 113904."
|
||||||
|
},
|
||||||
|
"sellmeier":
|
||||||
|
{
|
||||||
|
"B":
|
||||||
|
[
|
||||||
|
3228690000,
|
||||||
|
3553930000,
|
||||||
|
60676400000
|
||||||
|
],
|
||||||
|
"C":
|
||||||
|
[
|
||||||
|
4.6301e+13,
|
||||||
|
5.9578e+13,
|
||||||
|
1.1274e+14
|
||||||
|
],
|
||||||
|
"P0": 101325,
|
||||||
|
"T0": 273.15,
|
||||||
|
"kind": 2
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
BIN
src/dispersionapp/data/raman_response.npy
Normal file
BIN
src/dispersionapp/data/raman_response.npy
Normal file
Binary file not shown.
@@ -1,43 +1,54 @@
|
|||||||
from __future__ import annotations
|
from __future__ import annotations
|
||||||
|
|
||||||
import os
|
|
||||||
import warnings
|
import warnings
|
||||||
from functools import cache
|
from functools import cache
|
||||||
|
|
||||||
import numpy as np
|
import numpy as np
|
||||||
import scgenerator as sc
|
|
||||||
|
|
||||||
|
import dispersionapp.math as math
|
||||||
|
import dispersionapp.physics.fiber as fiber
|
||||||
|
import dispersionapp.physics.materials as materials
|
||||||
|
import dispersionapp.physics.pulse as pulse
|
||||||
|
import dispersionapp.physics.units as units
|
||||||
from dispersionapp.core import Config, LimitValues, N_ion_max, N_sf_max, b2, energy
|
from dispersionapp.core import Config, LimitValues, N_ion_max, N_sf_max, b2, energy
|
||||||
from dispersionapp.plotapp import PlotApp
|
from dispersionapp.plotapp import PlotApp, QtWidgets
|
||||||
|
|
||||||
|
|
||||||
def app(config_file: os.PathLike | None = None):
|
def app(config: Config):
|
||||||
config = Config.load(config_file)
|
|
||||||
# grid stuff
|
# grid stuff
|
||||||
w = sc.w_from_wl(config.wl_min, config.wl_max, 2048)
|
w = units.w_from_wl(config.wl_min, config.wl_max, 2048)
|
||||||
wl = sc.units.m.inv(w)
|
wl = units.m_rads(w)
|
||||||
wl_ind = sc.math.argclosest(wl, config.wl_pump * 1e-9)
|
wl_ind = math.argclosest(wl, config.wl_pump * 1e-9)
|
||||||
w0 = w[wl_ind]
|
w0: float = w[wl_ind]
|
||||||
|
|
||||||
gas = sc.materials.Gas(config.gas)
|
gas = materials.Gas(config.gas)
|
||||||
|
|
||||||
with PlotApp(
|
with PlotApp(
|
||||||
f"Dispersion design with {config.gas.title()}",
|
f"Dispersion design with {config.gas.title()}",
|
||||||
core_diameter_um=np.linspace(50, 300),
|
core_diameter_um=np.arange(5, 301, dtype=float),
|
||||||
pressure_mbar=np.geomspace(1, 2000),
|
pressure_mbar=np.geomspace(1, 2000),
|
||||||
wall_thickness_um=np.geomspace(0.01, 10),
|
wall_thickness_um=np.geomspace(0.01, 10, 201),
|
||||||
|
num_resonances=np.arange(6, 41),
|
||||||
n_tubes=np.arange(6, 16),
|
n_tubes=np.arange(6, 16),
|
||||||
gap_um=np.linspace(1, 15),
|
gap_um=np.arange(1, 15.5, 0.5),
|
||||||
t_fwhm_fs=np.linspace(10, 200, 96),
|
t_fwhm_fs=np.arange(10, 201, dtype=float),
|
||||||
) as app:
|
) as app:
|
||||||
# initial setup
|
# initial setup
|
||||||
app[0].horizontal_line("reference", 0, color="gray")
|
beta_ax = app["Dispersion plot"]
|
||||||
app[0].set_xlabel("wavelength (nm)")
|
beta_ax.horizontal_line("reference", 0, color="gray")
|
||||||
app[0].set_ylabel("beta2 (fs^2/cm)")
|
beta_ax.set_xlabel("wavelength (nm)")
|
||||||
|
beta_ax.set_ylabel("beta2 (fs^2/cm)")
|
||||||
|
|
||||||
|
n_ax = app["Refractive index (real)"]
|
||||||
|
n_ax.link_x(beta_ax)
|
||||||
|
n_ax.set_xlabel("wavelength (nm)")
|
||||||
|
n_ax.set_ylabel("n")
|
||||||
|
|
||||||
if config.current_state is not None:
|
if config.current_state is not None:
|
||||||
app.params["core_diameter_um"].value = config.current_state.core_diameter_um
|
app.params["core_diameter_um"].value = config.current_state.core_diameter_um
|
||||||
app.params["pressure_mbar"].value = config.current_state.pressure_mbar
|
app.params["pressure_mbar"].value = config.current_state.pressure_mbar
|
||||||
app.params["wall_thickness_um"].value = config.current_state.wall_thickness_um
|
app.params["wall_thickness_um"].value = config.current_state.wall_thickness_um
|
||||||
|
app.params["num_resonances"].value = config.current_state.num_resonances
|
||||||
app.params["n_tubes"].value = config.current_state.n_tubes
|
app.params["n_tubes"].value = config.current_state.n_tubes
|
||||||
app.params["gap_um"].value = config.current_state.gap_um
|
app.params["gap_um"].value = config.current_state.gap_um
|
||||||
app.params["t_fwhm_fs"].value = config.current_state.t_fwhm_fs
|
app.params["t_fwhm_fs"].value = config.current_state.t_fwhm_fs
|
||||||
@@ -45,10 +56,19 @@ def app(config_file: os.PathLike | None = None):
|
|||||||
app.params["core_diameter_um"].value = 100
|
app.params["core_diameter_um"].value = 100
|
||||||
app.params["pressure_mbar"].value = 500
|
app.params["pressure_mbar"].value = 500
|
||||||
app.params["wall_thickness_um"].value = 1
|
app.params["wall_thickness_um"].value = 1
|
||||||
|
app.params["num_resonances"].value = 6
|
||||||
app.params["n_tubes"].value = 7
|
app.params["n_tubes"].value = 7
|
||||||
app.params["gap_um"].value = 5
|
app.params["gap_um"].value = 5
|
||||||
app.params["t_fwhm_fs"].value = 100
|
app.params["t_fwhm_fs"].value = 100
|
||||||
app[0].set_lim(ylim=(-4, 2))
|
|
||||||
|
def reset_view():
|
||||||
|
# reseting beta_ax resets n_ax as well since they're linked
|
||||||
|
beta_ax.set_lim(ylim=(-4, 2))
|
||||||
|
|
||||||
|
reset_button = QtWidgets.QPushButton("Reset axes")
|
||||||
|
reset_button.clicked.connect(reset_view)
|
||||||
|
app.params_layout.addWidget(reset_button)
|
||||||
|
reset_view()
|
||||||
|
|
||||||
app.update(config.update_current)
|
app.update(config.update_current)
|
||||||
|
|
||||||
@@ -59,24 +79,28 @@ def app(config_file: os.PathLike | None = None):
|
|||||||
t_fwhm = 1e-15 * t_fwhm_fs
|
t_fwhm = 1e-15 * t_fwhm_fs
|
||||||
pressure = 1e2 * pressure_mbar
|
pressure = 1e2 * pressure_mbar
|
||||||
core_radius = 0.5e-6 * core_diameter_um
|
core_radius = 0.5e-6 * core_diameter_um
|
||||||
t0 = sc.pulse.fwhm_to_T0_fac["sech"] * t_fwhm
|
t0 = pulse.fwhm_to_T0_fac["sech"] * t_fwhm
|
||||||
|
|
||||||
disp = compute_capillary(core_diameter_um, pressure_mbar)
|
disp = compute_capillary(core_diameter_um, pressure_mbar)
|
||||||
wl_zero_disp = sc.math.all_zeros(wl, disp)
|
wl_zero_disp = math.all_zeros(wl, disp)
|
||||||
if len(wl_zero_disp) == 0:
|
if len(wl_zero_disp) == 0:
|
||||||
return
|
raise ValueError("No zero dispersion found")
|
||||||
wl_zero_disp = wl_zero_disp[0]
|
single_wl_zero_disp: float = wl_zero_disp[0]
|
||||||
|
|
||||||
with warnings.catch_warnings():
|
with warnings.catch_warnings():
|
||||||
warnings.simplefilter("ignore")
|
warnings.simplefilter("ignore")
|
||||||
ion_limit = N_ion_max(wl, t0, wl_zero_disp, gas, config.safety_factor)[wl_ind]
|
ion_limit: float = N_ion_max(
|
||||||
sf_limit = N_sf_max(wl, t0, wl_zero_disp, gas, config.safety_factor)[wl_ind]
|
wl, t0, single_wl_zero_disp, gas, config.safety_factor
|
||||||
|
)[wl_ind]
|
||||||
|
sf_limit: float = N_sf_max(wl, t0, single_wl_zero_disp, gas, config.safety_factor)[
|
||||||
|
wl_ind
|
||||||
|
]
|
||||||
|
|
||||||
beta2 = disp[wl_ind]
|
beta2 = disp[wl_ind]
|
||||||
n2 = gas.n2(pressure=pressure)
|
n2 = gas.n2(pressure=pressure)
|
||||||
|
|
||||||
return LimitValues(
|
return LimitValues(
|
||||||
wl_zero_disp,
|
single_wl_zero_disp,
|
||||||
ion_limit,
|
ion_limit,
|
||||||
sf_limit,
|
sf_limit,
|
||||||
energy(t0, w0, beta2, n2, core_radius, ion_limit),
|
energy(t0, w0, beta2, n2, core_radius, ion_limit),
|
||||||
@@ -84,29 +108,36 @@ def app(config_file: os.PathLike | None = None):
|
|||||||
)
|
)
|
||||||
|
|
||||||
@cache
|
@cache
|
||||||
def compute_vincetti(
|
def compute_n_eff_vincetti(
|
||||||
wall_thickness_um: float,
|
wall_thickness_um: float,
|
||||||
core_diameter_um: float,
|
core_diameter_um: float,
|
||||||
pressure_mbar: float,
|
pressure_mbar: float,
|
||||||
|
num_resonances: int,
|
||||||
n_tubes: int,
|
n_tubes: int,
|
||||||
gap_um: float,
|
gap_um: float,
|
||||||
) -> np.ndarray:
|
):
|
||||||
core_diameter = core_diameter_um * 1e-6
|
core_diameter = core_diameter_um * 1e-6
|
||||||
wall_thickness = wall_thickness_um * 1e-6
|
wall_thickness = wall_thickness_um * 1e-6
|
||||||
gap = gap_um * 1e-6
|
gap = gap_um * 1e-6
|
||||||
pressure = pressure_mbar * 1e2
|
pressure = pressure_mbar * 1e2
|
||||||
|
|
||||||
tr = sc.fiber.tube_radius_from_gap(core_diameter / 2, gap, n_tubes)
|
tr = fiber.tube_radius_from_gap(core_diameter / 2, gap, n_tubes)
|
||||||
n_gas_2 = gas.sellmeier.n_gas_2(wl, None, pressure)
|
n_gas_2 = gas.sellmeier.n_gas_2(wl, None, pressure)
|
||||||
n_eff_vinc = sc.fiber.n_eff_vincetti(
|
return fiber.n_eff_vincetti(
|
||||||
wl,
|
wl, 800e-9, n_gas_2, wall_thickness, tr, gap, n_tubes, n_terms=num_resonances
|
||||||
800e-9,
|
)
|
||||||
n_gas_2,
|
|
||||||
wall_thickness,
|
@cache
|
||||||
tr,
|
def compute_vincetti_beta(
|
||||||
gap,
|
wall_thickness_um: float,
|
||||||
n_tubes,
|
core_diameter_um: float,
|
||||||
n_terms=config.num_resonances,
|
pressure_mbar: float,
|
||||||
|
num_resonances: int,
|
||||||
|
n_tubes: int,
|
||||||
|
gap_um: float,
|
||||||
|
) -> np.ndarray:
|
||||||
|
n_eff_vinc = compute_n_eff_vincetti(
|
||||||
|
wall_thickness_um, core_diameter_um, pressure_mbar, num_resonances, n_tubes, gap_um
|
||||||
)
|
)
|
||||||
return b2(w, n_eff_vinc)
|
return b2(w, n_eff_vinc)
|
||||||
|
|
||||||
@@ -115,42 +146,64 @@ def app(config_file: os.PathLike | None = None):
|
|||||||
pressure = pressure_mbar * 1e2
|
pressure = pressure_mbar * 1e2
|
||||||
core_diameter = core_diameter_um * 1e-6
|
core_diameter = core_diameter_um * 1e-6
|
||||||
n_gas_2 = gas.sellmeier.n_gas_2(wl, None, pressure)
|
n_gas_2 = gas.sellmeier.n_gas_2(wl, None, pressure)
|
||||||
n_eff_cap = sc.fiber.n_eff_marcatili(wl, n_gas_2, core_diameter / 2)
|
n_eff_cap = fiber.n_eff_marcatili(wl, n_gas_2, core_diameter / 2)
|
||||||
return b2(w, n_eff_cap)
|
return b2(w, n_eff_cap)
|
||||||
|
|
||||||
@app.update
|
@app.update
|
||||||
def draw_vincetty(
|
def draw_vincetty_n_eff(
|
||||||
wall_thickness_um: float,
|
wall_thickness_um: float,
|
||||||
core_diameter_um: float,
|
core_diameter_um: float,
|
||||||
pressure_mbar: float,
|
pressure_mbar: float,
|
||||||
|
num_resonances: int,
|
||||||
n_tubes: int,
|
n_tubes: int,
|
||||||
gap_um: float,
|
gap_um: float,
|
||||||
):
|
):
|
||||||
b2 = compute_vincetti(
|
n_eff = compute_n_eff_vincetti(
|
||||||
wall_thickness_um, core_diameter_um, pressure_mbar, n_tubes, gap_um
|
wall_thickness_um, core_diameter_um, pressure_mbar, num_resonances, n_tubes, gap_um
|
||||||
)
|
)
|
||||||
app[0].set_line_data("Vincetti", wl * 1e9, sc.units.beta2_fs_cm_inv(b2))
|
n_ax.set_line_data("Vincetti", wl * 1e9, n_eff)
|
||||||
|
|
||||||
|
@app.update
|
||||||
|
def draw_vincetty_beta(
|
||||||
|
wall_thickness_um: float,
|
||||||
|
core_diameter_um: float,
|
||||||
|
pressure_mbar: float,
|
||||||
|
num_resonances: int,
|
||||||
|
n_tubes: int,
|
||||||
|
gap_um: float,
|
||||||
|
):
|
||||||
|
b2 = compute_vincetti_beta(
|
||||||
|
wall_thickness_um, core_diameter_um, pressure_mbar, num_resonances, n_tubes, gap_um
|
||||||
|
)
|
||||||
|
beta_ax.set_line_data("Vincetti", wl * 1e9, units.beta2_fs_cm_inv(b2))
|
||||||
|
|
||||||
@app.update
|
@app.update
|
||||||
def draw_capillary(core_diameter_um: float, pressure_mbar: float):
|
def draw_capillary(core_diameter_um: float, pressure_mbar: float):
|
||||||
b2 = compute_capillary(core_diameter_um, pressure_mbar)
|
b2 = compute_capillary(core_diameter_um, pressure_mbar)
|
||||||
app[0].set_line_data("Capillary", wl * 1e9, sc.units.beta2_fs_cm_inv(b2))
|
beta_ax.set_line_data("Capillary", wl * 1e9, units.beta2_fs_cm_inv(b2))
|
||||||
|
|
||||||
@app.update
|
@app.update
|
||||||
def draw_energy_limit(core_diameter_um: float, pressure_mbar: float, t_fwhm_fs: float):
|
def draw_energy_limit(core_diameter_um: float, pressure_mbar: float, t_fwhm_fs: float):
|
||||||
lim = compute_max_energy(core_diameter_um, pressure_mbar, t_fwhm_fs)
|
|
||||||
zdw = lim.wl_zero_disp * 1e9
|
|
||||||
app[0].set_line_data("zdw", [zdw, zdw], [-3, 3])
|
|
||||||
|
|
||||||
info_lines = [
|
info_lines = [
|
||||||
f"gas = {config.gas.title()}",
|
f"gas = {config.gas.title()}",
|
||||||
f"rep rate = {config.rep_rate * 1e-3}kHz",
|
f"rep rate = {config.rep_rate * 1e-3}kHz",
|
||||||
f"ZDW = {zdw:.0f}nm",
|
|
||||||
]
|
]
|
||||||
|
|
||||||
|
try:
|
||||||
|
lim = compute_max_energy(core_diameter_um, pressure_mbar, t_fwhm_fs)
|
||||||
|
except ValueError:
|
||||||
|
info_lines.append("No ZDW found")
|
||||||
|
app.info_label.setText("\n".join(info_lines))
|
||||||
|
return
|
||||||
|
|
||||||
|
zdw = lim.wl_zero_disp * 1e9
|
||||||
|
beta_ax.set_line_data("zdw", [zdw, zdw], [-3, 3])
|
||||||
|
|
||||||
|
info_lines.append(f"ZDW = {zdw:.0f}nm")
|
||||||
if lim.ion_lim > lim.sf_lim:
|
if lim.ion_lim > lim.sf_lim:
|
||||||
power = lim.sf_lim * 1e3 * config.rep_rate
|
power = lim.sf_lim * 1e3 * config.rep_rate
|
||||||
info_lines += [
|
info_lines += [
|
||||||
f"max energy = {power:.0f}mW",
|
f"max power = {power:.0f}mW",
|
||||||
f"N = {lim.soliton_sf_limit:.1f}",
|
f"N = {lim.soliton_sf_limit:.1f}",
|
||||||
"limited by self-focusing",
|
"limited by self-focusing",
|
||||||
]
|
]
|
||||||
@@ -161,6 +214,6 @@ def app(config_file: os.PathLike | None = None):
|
|||||||
f"N = {lim.soliton_sf_limit:.1f}",
|
f"N = {lim.soliton_sf_limit:.1f}",
|
||||||
"limited by ionization",
|
"limited by ionization",
|
||||||
]
|
]
|
||||||
app.info_label.setText("\n".join(info_lines))
|
app.info_label.setText(" ".join(info_lines))
|
||||||
|
|
||||||
config.save()
|
config.save()
|
||||||
|
|||||||
432
src/dispersionapp/io.py
Normal file
432
src/dispersionapp/io.py
Normal file
@@ -0,0 +1,432 @@
|
|||||||
|
from __future__ import annotations
|
||||||
|
|
||||||
|
import datetime
|
||||||
|
import importlib.resources
|
||||||
|
import json
|
||||||
|
import os
|
||||||
|
import re
|
||||||
|
from dataclasses import dataclass
|
||||||
|
from functools import cache
|
||||||
|
from io import BytesIO
|
||||||
|
from pathlib import Path
|
||||||
|
from typing import Any, BinaryIO, Protocol, Sequence, overload
|
||||||
|
from zipfile import ZipFile
|
||||||
|
|
||||||
|
import numpy as np
|
||||||
|
|
||||||
|
|
||||||
|
class TimedMessage:
|
||||||
|
def __init__(self, interval: float = 10.0):
|
||||||
|
self.interval = datetime.timedelta(seconds=interval)
|
||||||
|
self.next = datetime.datetime.now()
|
||||||
|
|
||||||
|
def ready(self) -> bool:
|
||||||
|
t = datetime.datetime.now()
|
||||||
|
if self.next <= t:
|
||||||
|
self.next = t + self.interval
|
||||||
|
return True
|
||||||
|
return False
|
||||||
|
|
||||||
|
|
||||||
|
def data_file(path: str) -> Path:
|
||||||
|
"""returns a `Path` object pointing to the desired data file included in `scgenerator`"""
|
||||||
|
return Path(importlib.resources.files("dispersionapp") / "data" / path)
|
||||||
|
|
||||||
|
|
||||||
|
class CustomEncoder(json.JSONEncoder):
|
||||||
|
def default(self, obj):
|
||||||
|
if isinstance(obj, (datetime.date, datetime.datetime)):
|
||||||
|
return obj.isoformat()
|
||||||
|
elif isinstance(obj, np.ndarray):
|
||||||
|
return tuple(obj)
|
||||||
|
elif isinstance(obj, DataFile):
|
||||||
|
return obj.__json__()
|
||||||
|
|
||||||
|
|
||||||
|
def _decode_datetime(s: str) -> datetime.date | datetime.datetime | str:
|
||||||
|
try:
|
||||||
|
return datetime.datetime.fromisoformat(s)
|
||||||
|
except Exception:
|
||||||
|
pass
|
||||||
|
try:
|
||||||
|
return datetime.date.fromisoformat(s)
|
||||||
|
except Exception:
|
||||||
|
pass
|
||||||
|
return s
|
||||||
|
|
||||||
|
|
||||||
|
def custom_decode_hook(obj):
|
||||||
|
"""
|
||||||
|
Some simple, non json-compatible objects are encoded as str, this function reconstructs the
|
||||||
|
original object and sets it in the decoded json structure
|
||||||
|
"""
|
||||||
|
for k, v in obj.items():
|
||||||
|
if isinstance(v, str):
|
||||||
|
obj[k] = _decode_datetime(v)
|
||||||
|
elif isinstance(v, list):
|
||||||
|
obj[k] = tuple(v)
|
||||||
|
return obj
|
||||||
|
|
||||||
|
|
||||||
|
@cache
|
||||||
|
def load_material_dico(name: str) -> dict[str, Any]:
|
||||||
|
"""
|
||||||
|
loads a material dictionary
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
name : str
|
||||||
|
name of the material
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
material_dico : dict
|
||||||
|
"""
|
||||||
|
return json.loads(data_file("materials.json").read_text())[name]
|
||||||
|
|
||||||
|
|
||||||
|
class PropagationIOHandler(Protocol):
|
||||||
|
def __len__(self) -> int: ...
|
||||||
|
|
||||||
|
def keys(self) -> list[str]: ...
|
||||||
|
|
||||||
|
def save_spectrum(self, index: int, spectrum: np.ndarray): ...
|
||||||
|
|
||||||
|
def load_spectrum(self, index: int) -> np.ndarray: ...
|
||||||
|
|
||||||
|
def save_data(self, name: str, data: bytes): ...
|
||||||
|
|
||||||
|
def load_data(self, name: str) -> bytes: ...
|
||||||
|
|
||||||
|
def clear(self): ...
|
||||||
|
|
||||||
|
|
||||||
|
class MemoryIOHandler:
|
||||||
|
spectra: dict[int, np.ndarray]
|
||||||
|
data: dict[str, bytes]
|
||||||
|
|
||||||
|
def __init__(self):
|
||||||
|
self.spectra = {}
|
||||||
|
self.data = {}
|
||||||
|
|
||||||
|
def __len__(self) -> int:
|
||||||
|
return len(self.spectra)
|
||||||
|
|
||||||
|
def keys(self) -> list[str]:
|
||||||
|
return list(self.data.keys())
|
||||||
|
|
||||||
|
def save_spectrum(self, index: int, spectrum: np.ndarray):
|
||||||
|
self.spectra[index] = spectrum
|
||||||
|
|
||||||
|
def load_spectrum(self, index: int) -> np.ndarray:
|
||||||
|
return self.spectra[index]
|
||||||
|
|
||||||
|
def save_data(self, name: str, data: bytes):
|
||||||
|
self.data[name] = data
|
||||||
|
|
||||||
|
def load_data(self, name: str) -> bytes:
|
||||||
|
return self.data[name]
|
||||||
|
|
||||||
|
def clear(self):
|
||||||
|
self.spectra = {}
|
||||||
|
self.data = {}
|
||||||
|
|
||||||
|
|
||||||
|
class ZipFileIOHandler:
|
||||||
|
file: BinaryIO
|
||||||
|
SPECTRUM_FN = "spectra/spectrum_{}.npy"
|
||||||
|
|
||||||
|
def __init__(self, file: os.PathLike):
|
||||||
|
"""
|
||||||
|
Create a IO handler to be used in Propagation.
|
||||||
|
This handler saves spectra as numpy `.npy` files.
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
file : os.PathLike
|
||||||
|
path to the desired zip file. Will be created if it doesn't exist.
|
||||||
|
Passing in an already opened file-like object is not supported at the moment
|
||||||
|
"""
|
||||||
|
self.file = Path(file)
|
||||||
|
if not self.file.exists():
|
||||||
|
ZipFile(self.file, "w").close()
|
||||||
|
|
||||||
|
def __len__(self) -> int:
|
||||||
|
with ZipFile(self.file, "r") as zip_file:
|
||||||
|
i = 0
|
||||||
|
while True:
|
||||||
|
try:
|
||||||
|
zip_file.open(self.SPECTRUM_FN.format(i))
|
||||||
|
except KeyError:
|
||||||
|
return i
|
||||||
|
i += 1
|
||||||
|
|
||||||
|
def keys(self) -> list[str]:
|
||||||
|
with ZipFile(self.file, "r") as zip_file:
|
||||||
|
return zip_file.namelist()
|
||||||
|
|
||||||
|
def save_spectrum(self, index: int, spectrum: np.ndarray):
|
||||||
|
with (
|
||||||
|
ZipFile(self.file, "a") as zip_file,
|
||||||
|
zip_file.open(self.SPECTRUM_FN.format(index), "w") as file,
|
||||||
|
):
|
||||||
|
np.lib.format.write_array(file, spectrum, allow_pickle=False)
|
||||||
|
|
||||||
|
def load_spectrum(self, index: int) -> np.ndarray:
|
||||||
|
with (
|
||||||
|
ZipFile(self.file, "r") as zip_file,
|
||||||
|
zip_file.open(self.SPECTRUM_FN.format(index), "r") as file,
|
||||||
|
):
|
||||||
|
return np.load(file)
|
||||||
|
|
||||||
|
def save_data(self, name: str, data: bytes):
|
||||||
|
with ZipFile(self.file, "a") as zip_file, zip_file.open(name, "w") as file:
|
||||||
|
file.write(data)
|
||||||
|
|
||||||
|
def load_data(self, name: str) -> bytes:
|
||||||
|
with ZipFile(self.file, "r") as zip_file, zip_file.open(name, "r") as file:
|
||||||
|
return file.read()
|
||||||
|
|
||||||
|
def clear(self):
|
||||||
|
self.file.unlink(missing_ok=True)
|
||||||
|
|
||||||
|
|
||||||
|
@dataclass
|
||||||
|
class DataFile:
|
||||||
|
"""
|
||||||
|
Holds information about external files necessary for a simulation.
|
||||||
|
In the current implementation, only reading data from the file is supported
|
||||||
|
"""
|
||||||
|
|
||||||
|
prefix: str | None
|
||||||
|
path: str
|
||||||
|
io: PropagationIOHandler
|
||||||
|
|
||||||
|
PREFIX_SEP = "::"
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def from_str(cls, s: str, io: PropagationIOHandler | None = None) -> DataFile:
|
||||||
|
if cls.PREFIX_SEP in s:
|
||||||
|
prefix, path = s.split(cls.PREFIX_SEP, 1)
|
||||||
|
else:
|
||||||
|
prefix = None
|
||||||
|
path = s
|
||||||
|
return cls(prefix, path, io)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def validate(cls, name: str, data: str | DataFile) -> DataFile:
|
||||||
|
"""To be used to automatically construct a DataFile when creating a Parameters obj"""
|
||||||
|
if isinstance(data, cls):
|
||||||
|
return data
|
||||||
|
elif isinstance(data, str):
|
||||||
|
return cls.from_str(data)
|
||||||
|
elif isinstance(data, Path):
|
||||||
|
return cls.from_str(os.fspath(data))
|
||||||
|
else:
|
||||||
|
raise TypeError(
|
||||||
|
f"{name!r} must be a path or a bundled file specifier, not a {type(data)!r}"
|
||||||
|
)
|
||||||
|
|
||||||
|
def __json__(self) -> str:
|
||||||
|
if self.prefix is None:
|
||||||
|
return os.fspath(Path(self.path))
|
||||||
|
return self.prefix + self.PREFIX_SEP + self.path
|
||||||
|
|
||||||
|
def load_bytes(self) -> bytes:
|
||||||
|
if self.prefix is not None and self.io is None:
|
||||||
|
raise ValueError(
|
||||||
|
f"a bundled file prefixed with {self.prefix} "
|
||||||
|
"must have a PropagationIOHandler attached"
|
||||||
|
)
|
||||||
|
# a DataFile obj may have a useless io obj attached to it
|
||||||
|
if self.prefix is not None:
|
||||||
|
return self.io.load_data(self.path)
|
||||||
|
else:
|
||||||
|
return Path(self.path).read_bytes()
|
||||||
|
|
||||||
|
@overload
|
||||||
|
def load_arrays(self, labels: str | tuple[str, ...]) -> tuple[np.ndarray]: ...
|
||||||
|
@overload
|
||||||
|
def load_arrays(
|
||||||
|
self, labels: str | tuple[str, ...], labels2: str | tuple[str, ...]
|
||||||
|
) -> tuple[np.ndarray, np.ndarray]: ...
|
||||||
|
def load_arrays(self, *labels: str | tuple[str, ...]) -> tuple[np.ndarray, ...]:
|
||||||
|
raw_data = self.load_bytes()
|
||||||
|
extension = self.path.lower().split(".")[-1]
|
||||||
|
return _parse_raw_data(raw_data, extension, *labels)
|
||||||
|
|
||||||
|
def similar_to(self, other: DataFile) -> bool:
|
||||||
|
return Path(self.path).name == Path(other.path).name
|
||||||
|
|
||||||
|
|
||||||
|
def open_data_file(path: os.PathLike, *labels: str) -> tuple[np.ndarray, ...]:
|
||||||
|
path = Path(path)
|
||||||
|
raw_data = path.read_bytes()
|
||||||
|
extension = path.suffix.lower()
|
||||||
|
return _parse_raw_data(raw_data, extension, *labels)
|
||||||
|
|
||||||
|
|
||||||
|
def _parse_raw_data(data: bytes, extension: str, *keys) -> tuple[np.ndarray, ...]:
|
||||||
|
if extension.endswith("npz"):
|
||||||
|
df = np.load(BytesIO(data))
|
||||||
|
return _parse_npz_data(df, *keys)
|
||||||
|
elif extension.endswith("npy"):
|
||||||
|
return tuple(np.load(BytesIO(data)))
|
||||||
|
else:
|
||||||
|
return _parse_text_data(data.decode())
|
||||||
|
|
||||||
|
|
||||||
|
def _parse_text_data(s: str) -> tuple[np.ndarray, ...]:
|
||||||
|
lines = s.splitlines()
|
||||||
|
for delimiter in ", \t;":
|
||||||
|
try:
|
||||||
|
return tuple(np.loadtxt(lines, delimiter=delimiter).T)
|
||||||
|
except ValueError:
|
||||||
|
continue
|
||||||
|
raise ValueError("Could not load text data as numpy array")
|
||||||
|
|
||||||
|
|
||||||
|
def _parse_npz_data(
|
||||||
|
df: np.lib.npyio.NpzFile, *labels: str | tuple[str, ...]
|
||||||
|
) -> tuple[np.ndarray, ...]:
|
||||||
|
if not labels:
|
||||||
|
return tuple(df.values())
|
||||||
|
out = []
|
||||||
|
for key in labels:
|
||||||
|
if not isinstance(key, (list, tuple, set)):
|
||||||
|
out.append(df[key])
|
||||||
|
continue
|
||||||
|
for possible_key in key:
|
||||||
|
try:
|
||||||
|
out.append(df[possible_key])
|
||||||
|
except KeyError:
|
||||||
|
continue
|
||||||
|
else:
|
||||||
|
break
|
||||||
|
else:
|
||||||
|
raise KeyError(f"no key of {key!r} present in {df}")
|
||||||
|
return tuple(out)
|
||||||
|
|
||||||
|
|
||||||
|
def unique_name(base_name: str, existing: set[str]) -> str:
|
||||||
|
name = base_name
|
||||||
|
p = Path(base_name)
|
||||||
|
base = p.stem
|
||||||
|
ext = p.suffix
|
||||||
|
i = 0
|
||||||
|
while name in existing:
|
||||||
|
name = f"{base}_{i}{ext}"
|
||||||
|
i += 1
|
||||||
|
return name
|
||||||
|
|
||||||
|
|
||||||
|
def format_graph(left_elements: Sequence[str], middle: str, right_elements: Sequence[str]):
|
||||||
|
if len(left_elements) == 0:
|
||||||
|
left_elements = [""]
|
||||||
|
if len(right_elements) == 0:
|
||||||
|
right_elements = [""]
|
||||||
|
mid_elements = ["."[:i] + el for i, el in enumerate(middle.split("."))]
|
||||||
|
left_height = len(left_elements)
|
||||||
|
right_height = len(right_elements)
|
||||||
|
|
||||||
|
max_left = max(len(el) for el in left_elements) + 1
|
||||||
|
max_right = max(len(el) for el in right_elements) + 1
|
||||||
|
max_mid = max(len(el) for el in mid_elements) + 2
|
||||||
|
|
||||||
|
right_elements = [fit_right(el, max_right) for el in right_elements][::-1]
|
||||||
|
left_elements = [fit_left(el, max_left) for el in left_elements][::-1]
|
||||||
|
mid_elements = ["─" * max_mid] + [fit_mid(el, max_mid) for el in mid_elements][::-1]
|
||||||
|
|
||||||
|
total_height = max(len(left_elements), len(right_elements), len(mid_elements))
|
||||||
|
|
||||||
|
line_pos = total_height - len(mid_elements)
|
||||||
|
|
||||||
|
left = left_col(
|
||||||
|
left_elements, line_pos, total_height, max_left, start=max(0, line_pos - left_height + 1)
|
||||||
|
)
|
||||||
|
right = right_col(
|
||||||
|
right_elements, line_pos, total_height, max_right, start=max(0, line_pos - right_height + 1)
|
||||||
|
)
|
||||||
|
middle = mid_col(mid_elements, line_pos, total_height, max_mid)
|
||||||
|
|
||||||
|
final = "\n".join(l + m + r for l, m, r in zip(left, middle, right))
|
||||||
|
return final
|
||||||
|
|
||||||
|
|
||||||
|
def fit_left(el, length, line=1, pad=1):
|
||||||
|
return f"{' ' * length}{el}{' ' * pad}{'─' * line}"[-(length + 1) :]
|
||||||
|
|
||||||
|
|
||||||
|
def fit_right(el, length, line=1, pad=1):
|
||||||
|
return f"{'─' * line}{' ' * pad}{el}{' ' * length}"[: length + 1]
|
||||||
|
|
||||||
|
|
||||||
|
def fit_mid(el, length, pad=1):
|
||||||
|
return f"{' ' * pad}{el}{' ' * length}"[:length]
|
||||||
|
|
||||||
|
|
||||||
|
def mid_col(mid_els, line_pos, height, pad_length):
|
||||||
|
out = [" " * pad_length] * line_pos + mid_els
|
||||||
|
while len(out) < height:
|
||||||
|
out.append(" " * pad_length)
|
||||||
|
return out[::-1]
|
||||||
|
|
||||||
|
|
||||||
|
def left_col(left_els, line_pos, height, pad_length, start=0):
|
||||||
|
out = [" " * (pad_length + 1)] * start
|
||||||
|
for rel_i, el in enumerate(left_els):
|
||||||
|
abs_j = rel_i + start
|
||||||
|
out.append(el + get_symb(False, rel_i, abs_j, line_pos, len(left_els) - 1))
|
||||||
|
while len(out) < height:
|
||||||
|
out.append(" " * (pad_length + 2))
|
||||||
|
return out[::-1]
|
||||||
|
|
||||||
|
|
||||||
|
def right_col(right_els, line_pos, height, pad_length, start=0):
|
||||||
|
out = [" " * (pad_length + 1)] * start
|
||||||
|
for rel_i, el in enumerate(right_els):
|
||||||
|
abs_j = rel_i + start
|
||||||
|
out.append(get_symb(True, rel_i, abs_j, line_pos, len(right_els) - 1) + el)
|
||||||
|
while len(out) < height:
|
||||||
|
out.append(" " * (pad_length + 2))
|
||||||
|
return out[::-1]
|
||||||
|
|
||||||
|
|
||||||
|
def get_symb(right: bool, rel_i, abs_j, line_pos, max_ind):
|
||||||
|
if max_ind == 0:
|
||||||
|
return "─"
|
||||||
|
elif rel_i == 0:
|
||||||
|
if abs_j < line_pos:
|
||||||
|
return "╯╰"[right]
|
||||||
|
elif abs_j == line_pos:
|
||||||
|
return "┴"
|
||||||
|
else:
|
||||||
|
raise ValueError("bottom of left columns cannot be above line")
|
||||||
|
elif rel_i < max_ind:
|
||||||
|
if abs_j == line_pos:
|
||||||
|
return "┼"
|
||||||
|
else:
|
||||||
|
return "┤├"[right]
|
||||||
|
else:
|
||||||
|
if abs_j == line_pos:
|
||||||
|
return "┬"
|
||||||
|
elif abs_j > line_pos:
|
||||||
|
return "╮╭"[right]
|
||||||
|
else:
|
||||||
|
raise ValueError("top of left columns cannot be below line")
|
||||||
|
|
||||||
|
|
||||||
|
def _to_num(s: str) -> str | float | int:
|
||||||
|
for f in int, float:
|
||||||
|
try:
|
||||||
|
return f(s)
|
||||||
|
except ValueError:
|
||||||
|
pass
|
||||||
|
return s
|
||||||
|
|
||||||
|
|
||||||
|
NUM_REGEX = r"[+-]?[\d]+(?:\.?[\d]+)?(?:[eE][+-]?\d+)?"
|
||||||
|
|
||||||
|
|
||||||
|
def logical_sort_key(s: os.PathLike | str) -> tuple:
|
||||||
|
return tuple(_to_num(el) for el in re.split(f"({NUM_REGEX})", str(s)) if el)
|
||||||
800
src/dispersionapp/math.py
Normal file
800
src/dispersionapp/math.py
Normal file
@@ -0,0 +1,800 @@
|
|||||||
|
"""
|
||||||
|
collection of purely mathematical function
|
||||||
|
"""
|
||||||
|
|
||||||
|
import math
|
||||||
|
import warnings
|
||||||
|
from dataclasses import dataclass
|
||||||
|
from functools import cache
|
||||||
|
from typing import Callable, Sequence, overload
|
||||||
|
|
||||||
|
import numba
|
||||||
|
import numpy as np
|
||||||
|
from scipy import fft as sfft
|
||||||
|
from scipy.interpolate import interp1d, lagrange
|
||||||
|
from scipy.special import jn_zeros
|
||||||
|
|
||||||
|
pi = np.pi
|
||||||
|
c = 299792458.0
|
||||||
|
|
||||||
|
|
||||||
|
def fft_functions(
|
||||||
|
full_field: bool,
|
||||||
|
) -> tuple[Callable[[np.ndarray], np.ndarray], Callable[[np.ndarray], np.ndarray]]:
|
||||||
|
if full_field:
|
||||||
|
return sfft.rfft, sfft.irfft
|
||||||
|
else:
|
||||||
|
return sfft.fft, sfft.ifft
|
||||||
|
|
||||||
|
|
||||||
|
def expm1_int(y: np.ndarray, dx: float) -> np.ndarray:
|
||||||
|
"""evaluates 1 - exp( -∫func(y(x))dx ) from x=-inf to x"""
|
||||||
|
return -np.expm1(-cumulative_simpson(y) * dx)
|
||||||
|
|
||||||
|
|
||||||
|
def span(*vec: np.ndarray) -> tuple[float, float]:
|
||||||
|
"""returns the min and max of whatever array-like is given. can accept many args"""
|
||||||
|
out = (np.inf, -np.inf)
|
||||||
|
if len(vec) == 0 or len(vec[0]) == 0:
|
||||||
|
raise ValueError("did not provide any value to span")
|
||||||
|
for x in vec:
|
||||||
|
x = np.atleast_1d(x)
|
||||||
|
out = (min(np.min(x), out[0]), max(np.max(x), out[1]))
|
||||||
|
return out
|
||||||
|
|
||||||
|
|
||||||
|
def total_extent(*vec: np.ndarray) -> float:
|
||||||
|
"""measure the distance between the min and max value of all given arrays"""
|
||||||
|
left, right = span(*vec)
|
||||||
|
return right - left
|
||||||
|
|
||||||
|
|
||||||
|
def span_above(arr: np.ndarray, threshold: float) -> tuple[int, int]:
|
||||||
|
"""returns the first and last index where the array is above the specified threshold"""
|
||||||
|
ind = np.where(arr >= threshold)[-1]
|
||||||
|
return np.min(ind), np.max(ind)
|
||||||
|
|
||||||
|
|
||||||
|
@overload
|
||||||
|
def argclosest(array: np.ndarray, target: float | int) -> int: ...
|
||||||
|
@overload
|
||||||
|
def argclosest(array: np.ndarray, target: Sequence[float | int] | np.ndarray) -> np.ndarray: ...
|
||||||
|
|
||||||
|
|
||||||
|
def argclosest(
|
||||||
|
array: np.ndarray, target: float | int | Sequence[float | int] | np.ndarray
|
||||||
|
) -> int | np.ndarray:
|
||||||
|
"""
|
||||||
|
returns the index/indices corresponding to the closest matches of target in array
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
array : np.ndarray, shape (n,)
|
||||||
|
array of values
|
||||||
|
target : number | np.ndarray
|
||||||
|
find the closest value to target in `array`. The index of the closest match is returned.
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
int | np.ndarray
|
||||||
|
index / indices of the closest match
|
||||||
|
|
||||||
|
"""
|
||||||
|
min_dist = np.inf
|
||||||
|
index = 0
|
||||||
|
if isinstance(target, (list, tuple, np.ndarray)):
|
||||||
|
return np.array([argclosest(array, t) for t in target])
|
||||||
|
for k, val in enumerate(array):
|
||||||
|
dist = abs(val - target)
|
||||||
|
if dist < min_dist:
|
||||||
|
min_dist = dist
|
||||||
|
index = k
|
||||||
|
|
||||||
|
return index
|
||||||
|
|
||||||
|
|
||||||
|
def extent(x):
|
||||||
|
return np.max(x) - np.min(x)
|
||||||
|
|
||||||
|
|
||||||
|
def power_fact(x, n):
|
||||||
|
"""
|
||||||
|
returns x ^ n / n!
|
||||||
|
"""
|
||||||
|
if isinstance(x, (int, float)):
|
||||||
|
return _power_fact_single(x, n)
|
||||||
|
|
||||||
|
elif isinstance(x, np.ndarray):
|
||||||
|
return _power_fact_array(x, n)
|
||||||
|
else:
|
||||||
|
raise TypeError(f"type {type(x)} of x not supported.")
|
||||||
|
|
||||||
|
|
||||||
|
def _power_fact_single(x, n):
|
||||||
|
result = 1.0
|
||||||
|
for k in range(n):
|
||||||
|
result = result * x / (n - k)
|
||||||
|
return result
|
||||||
|
|
||||||
|
|
||||||
|
def _power_fact_array(x, n):
|
||||||
|
"""returns x^2/n!"""
|
||||||
|
result = np.ones(len(x), dtype=np.float64)
|
||||||
|
for k in range(n):
|
||||||
|
result = result * x / (n - k)
|
||||||
|
return result
|
||||||
|
|
||||||
|
|
||||||
|
@numba.njit()
|
||||||
|
def abs2(z: np.ndarray) -> np.ndarray:
|
||||||
|
return z.real**2 + z.imag**2
|
||||||
|
|
||||||
|
|
||||||
|
def normalized(z: np.ndarray) -> np.ndarray:
|
||||||
|
ab = abs2(z)
|
||||||
|
return ab / ab.max()
|
||||||
|
|
||||||
|
|
||||||
|
def autocrop(
|
||||||
|
x, y, z, threshold: float = 1e-4, x_only: bool = False
|
||||||
|
) -> tuple[np.ndarray, np.ndarray, np.ndarray]:
|
||||||
|
thr = z.max()
|
||||||
|
yind, xind = np.where(z > thr * threshold)
|
||||||
|
xmin, xmax = xind.min(), xind.max()
|
||||||
|
if x_only:
|
||||||
|
ymin, ymax = 0, len(y) - 1
|
||||||
|
else:
|
||||||
|
ymin, ymax = yind.min(), yind.max()
|
||||||
|
return x[xmin : xmax + 1], y[ymin : ymax + 1], z[ymin : ymax + 1][:, xmin : xmax + 1]
|
||||||
|
|
||||||
|
|
||||||
|
def to_dB(arr: np.ndarray, ref=None, axis=None, default: float | None = None) -> np.ndarray:
|
||||||
|
"""
|
||||||
|
converts unitless values in dB
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
arr : np.ndarray
|
||||||
|
array of non-negative values. Any values 0 or below will be mapped to the minimum
|
||||||
|
positive value in dB
|
||||||
|
ref : float, optional
|
||||||
|
reference value corresponding to 0dB (default : max(arr))
|
||||||
|
axis : int | None, optional
|
||||||
|
on which axis to apply the transformation. If `ref` is given, this has no effect
|
||||||
|
|
||||||
|
Returns
|
||||||
|
----------
|
||||||
|
np.ndarray
|
||||||
|
array in dB
|
||||||
|
"""
|
||||||
|
if axis is not None and arr.ndim > 1 and ref is None:
|
||||||
|
return np.apply_along_axis(to_dB, axis, arr, default=default)
|
||||||
|
|
||||||
|
out = np.ones_like(arr)
|
||||||
|
if default is not None and math.isfinite(default):
|
||||||
|
out[:] *= default
|
||||||
|
else:
|
||||||
|
out *= np.nan
|
||||||
|
|
||||||
|
if ref is None:
|
||||||
|
ref = np.max(arr)
|
||||||
|
above_0 = arr > 0
|
||||||
|
if not np.any(above_0) or ref <= 0:
|
||||||
|
warnings.warn(f"invalid array to convert to dB, returning {default} instead")
|
||||||
|
if default is None:
|
||||||
|
out *= np.nan
|
||||||
|
return out
|
||||||
|
m = arr / ref
|
||||||
|
if default is None:
|
||||||
|
out *= 10 * np.log10(m[above_0].min())
|
||||||
|
return 10 * np.log10(m, out=out, where=above_0)
|
||||||
|
|
||||||
|
|
||||||
|
def u_nm(n, m):
|
||||||
|
"""
|
||||||
|
returns the mth zero of the Bessel function of order n-1
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
n-1 : order of the Bessel function
|
||||||
|
m : order of the zero
|
||||||
|
|
||||||
|
Returns
|
||||||
|
----------
|
||||||
|
float
|
||||||
|
"""
|
||||||
|
return jn_zeros(n - 1, m)[-1]
|
||||||
|
|
||||||
|
|
||||||
|
def all_zeros(x: np.ndarray, y: np.ndarray) -> np.ndarray:
|
||||||
|
"""find all the x values such that y(x)=0 with linear interpolation"""
|
||||||
|
pos = np.argwhere(y[1:] * y[:-1] < 0)[:, 0]
|
||||||
|
m = (y[pos + 1] - y[pos]) / (x[pos + 1] - x[pos])
|
||||||
|
return -y[pos] / m + x[pos]
|
||||||
|
|
||||||
|
|
||||||
|
def wspace(t: float | np.ndarray, t_num=0):
|
||||||
|
"""
|
||||||
|
frequency array such that x(t) <-> np.fft(x)(w)
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
t : float | np.ndarray
|
||||||
|
float : total width of the time window
|
||||||
|
array : time array
|
||||||
|
t_num : int-
|
||||||
|
if t is a float, specifies the number of points
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
w : array
|
||||||
|
linspace of frencies corresponding to t
|
||||||
|
"""
|
||||||
|
if isinstance(t, (np.ndarray, list, tuple)):
|
||||||
|
dt = t[1] - t[0]
|
||||||
|
t_num = len(t)
|
||||||
|
else:
|
||||||
|
dt = t / t_num
|
||||||
|
return np.fft.fftfreq(t_num, dt) * 2 * np.pi
|
||||||
|
|
||||||
|
|
||||||
|
def tspace(time_window: float | None = None, t_num: int | None = None, dt: float | None = None):
|
||||||
|
"""
|
||||||
|
returns a time array centered on 0
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
time_window : float
|
||||||
|
total time spanned
|
||||||
|
t_num : int
|
||||||
|
number of points
|
||||||
|
dt : float
|
||||||
|
time resolution
|
||||||
|
|
||||||
|
at least 2 arguments must be given. They are prioritize as such
|
||||||
|
t_num > time_window > dt
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
t : array
|
||||||
|
a linearily spaced time array
|
||||||
|
Raises
|
||||||
|
------
|
||||||
|
TypeError
|
||||||
|
missing at least 1 argument
|
||||||
|
"""
|
||||||
|
if t_num is not None:
|
||||||
|
if isinstance(time_window, (float, int)):
|
||||||
|
return np.linspace(-time_window / 2, time_window / 2, int(t_num))
|
||||||
|
elif isinstance(dt, (float, int)):
|
||||||
|
time_window = (t_num - 1) * dt
|
||||||
|
return np.linspace(-time_window / 2, time_window / 2, t_num)
|
||||||
|
elif isinstance(time_window, (float, int)) and isinstance(dt, (float, int)):
|
||||||
|
t_num = int(time_window / dt) + 1
|
||||||
|
return np.linspace(-time_window / 2, time_window / 2, t_num)
|
||||||
|
raise TypeError("not enough parameter to determine time vector")
|
||||||
|
|
||||||
|
|
||||||
|
def irfftfreq(freq: np.ndarray, retstep: bool = False):
|
||||||
|
"""
|
||||||
|
Given an array of positive only frequency, this returns the corresponding time array centered
|
||||||
|
around 0 that will be aligned with the `numpy.fft.irfft` of a spectrum aligned with `freq`.
|
||||||
|
if `retstep` is True, the sample spacing is returned as well
|
||||||
|
"""
|
||||||
|
df = freq[1] - freq[0]
|
||||||
|
nt = (len(freq) - 1) * 2
|
||||||
|
period = 1 / df
|
||||||
|
dt = period / nt
|
||||||
|
|
||||||
|
t = np.linspace(-(period - dt) / 2, (period - dt) / 2, nt)
|
||||||
|
if retstep:
|
||||||
|
return t, dt
|
||||||
|
else:
|
||||||
|
return t
|
||||||
|
|
||||||
|
|
||||||
|
def iwspace(w: np.ndarray, retstep: bool = False):
|
||||||
|
"""invserse of wspace: recovers the (symmetric) time array corresponsding to `w`"""
|
||||||
|
df = (w[1] - w[0]) * 0.5 / np.pi
|
||||||
|
nt = len(w)
|
||||||
|
period = 1 / df
|
||||||
|
dt = period / nt
|
||||||
|
t = np.linspace(-(period - dt) / 2, (period - dt) / 2, nt)
|
||||||
|
if retstep:
|
||||||
|
return t, dt
|
||||||
|
else:
|
||||||
|
return t
|
||||||
|
|
||||||
|
|
||||||
|
def dt_from_min_wl(wl_min: float, wavelength: float) -> float:
|
||||||
|
return 0.5 / c / (1 / wl_min - 1 / wavelength)
|
||||||
|
|
||||||
|
|
||||||
|
def min_wl_from_dt(dt: float, wavelength: float) -> float:
|
||||||
|
return wavelength / (1 + wavelength / (2 * c * dt))
|
||||||
|
|
||||||
|
|
||||||
|
def build_envelope_w_grid(t: np.ndarray, w0: float) -> tuple[np.ndarray, np.ndarray, np.ndarray]:
|
||||||
|
"""
|
||||||
|
convenience function to
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
t : np.ndarray, shape (t_num,)
|
||||||
|
time array
|
||||||
|
w0 : float
|
||||||
|
center frequency
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
w_c : np.ndarray, shape (n, )
|
||||||
|
centered angular frequencies in rad/s where 0 is the pump frequency
|
||||||
|
w : np.ndarray, shape (n, )
|
||||||
|
angular frequency grid
|
||||||
|
w_order : np.ndarray, shape (n,)
|
||||||
|
arrays of indices such that w[w_order] is sorted
|
||||||
|
"""
|
||||||
|
w_c = wspace(t)
|
||||||
|
w = w_c + w0
|
||||||
|
w_order = np.argsort(w)
|
||||||
|
return w_c, w, w_order
|
||||||
|
|
||||||
|
|
||||||
|
def build_full_field_w_grid(t_num: int, dt: float) -> tuple[np.ndarray, np.ndarray, np.ndarray]:
|
||||||
|
"""
|
||||||
|
Paramters
|
||||||
|
---------
|
||||||
|
t_num : int
|
||||||
|
number of temporal sampling points
|
||||||
|
dt : float
|
||||||
|
uniform spacing between sample points
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
w : np.ndarray, shape (n, )
|
||||||
|
angular frequency grid
|
||||||
|
w_order : np.ndarray, shape (n,)
|
||||||
|
arrays of indices such that w[w_order] is sorted
|
||||||
|
"""
|
||||||
|
w = 2 * pi * np.fft.rfftfreq(t_num, dt)
|
||||||
|
w_order = np.argsort(w)
|
||||||
|
ind = w != 0
|
||||||
|
wl = np.zeros(len(w))
|
||||||
|
wl[ind] = 2 * pi * c / w[ind]
|
||||||
|
if any(ind):
|
||||||
|
wl[~ind] = 2 * pi * c / (np.abs(w[ind]).min())
|
||||||
|
return w, w_order, wl
|
||||||
|
|
||||||
|
|
||||||
|
def build_z_grid(z_num: int, length: float) -> np.ndarray:
|
||||||
|
return np.linspace(0, length, z_num)
|
||||||
|
|
||||||
|
|
||||||
|
def build_t_grid(
|
||||||
|
time_window: float | None = None, t_num: int | None = None, dt: float | None = None
|
||||||
|
) -> tuple[np.ndarray, float, float, int]:
|
||||||
|
"""
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
t : np.ndarray, shape (t_num, )
|
||||||
|
temporal points in s
|
||||||
|
time_window : float
|
||||||
|
total width of the temporal grid in s, by default None
|
||||||
|
dt : float
|
||||||
|
spacing of the temporal grid in s, by default None
|
||||||
|
t_num : int
|
||||||
|
number of temporal grid points, by default None
|
||||||
|
"""
|
||||||
|
t = tspace(time_window, t_num, dt)
|
||||||
|
time_window = t.max() - t.min()
|
||||||
|
dt = t[1] - t[0]
|
||||||
|
t_num = len(t)
|
||||||
|
return t, time_window, dt, t_num
|
||||||
|
|
||||||
|
|
||||||
|
def polynom_extrapolation(x: np.ndarray, y: np.ndarray, degree: int) -> np.ndarray:
|
||||||
|
"""
|
||||||
|
performs a polynomial extrapolation on both ends of the support
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
x : np.ndarray (n,)
|
||||||
|
x values
|
||||||
|
y : np.ndarray (n,)
|
||||||
|
y values. The shape must correspond to that of x.
|
||||||
|
degree : int
|
||||||
|
degree of the polynom.
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
np.ndarray, shape (n,)
|
||||||
|
y array with zero values on either side replaces with polynomial extrapolation
|
||||||
|
|
||||||
|
Example
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
"""
|
||||||
|
out = y.copy()
|
||||||
|
order = np.argsort(x)
|
||||||
|
left_ind, *_, right_ind = np.nonzero(out[order])[0]
|
||||||
|
return _polynom_extrapolation_in_place(out[order], left_ind, right_ind, degree)[order.argsort]
|
||||||
|
|
||||||
|
|
||||||
|
def _polynom_extrapolation_in_place(y: np.ndarray, left_ind: int, right_ind: int, degree: float):
|
||||||
|
"""
|
||||||
|
extrapolates IN PLACE linearily on both side of the support
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
y : np.ndarray
|
||||||
|
array
|
||||||
|
left_ind : int
|
||||||
|
first value we want to keep (extrapolate to the left of that)
|
||||||
|
right_ind : int
|
||||||
|
last value we want to keep (extrapolate to the right of that)
|
||||||
|
"""
|
||||||
|
r_left = (1 + np.arange(left_ind))[::-1] ** degree
|
||||||
|
r_right = np.arange(len(y) - right_ind) ** degree
|
||||||
|
y[:left_ind] = r_left * (y[left_ind] - y[left_ind + 1]) + y[left_ind]
|
||||||
|
y[right_ind:] = r_right * (y[right_ind] - y[right_ind - 1]) + y[right_ind]
|
||||||
|
return y
|
||||||
|
|
||||||
|
|
||||||
|
def interp_2d(
|
||||||
|
old_x: np.ndarray,
|
||||||
|
old_y: np.ndarray,
|
||||||
|
z: np.ndarray,
|
||||||
|
new_x: np.ndarray | tuple,
|
||||||
|
new_y: np.ndarray | tuple,
|
||||||
|
kind="linear",
|
||||||
|
) -> np.ndarray:
|
||||||
|
if isinstance(new_x, tuple):
|
||||||
|
new_x = np.linspace(*new_x)
|
||||||
|
if isinstance(new_y, tuple):
|
||||||
|
new_y = np.linspace(*new_y)
|
||||||
|
z = interp1d(old_y, z, axis=0, kind=kind, bounds_error=False, fill_value=0)(new_y)
|
||||||
|
return interp1d(old_x, z, kind=kind, bounds_error=False, fill_value=0)(new_x)
|
||||||
|
|
||||||
|
|
||||||
|
@numba.jit(nopython=True)
|
||||||
|
def linear_interp_2d(old_x: np.ndarray, old_y: np.ndarray, new_x: np.ndarray):
|
||||||
|
new_vals = np.zeros((len(old_y), len(new_x)))
|
||||||
|
interpolable = (new_x > old_x[0]) & (new_x <= old_x[-1])
|
||||||
|
equal = new_x == old_x[0]
|
||||||
|
inds = np.searchsorted(old_x, new_x[interpolable])
|
||||||
|
for i, val in enumerate(old_y):
|
||||||
|
new_vals[i][interpolable] = val[inds - 1] + (new_x[interpolable] - old_x[inds - 1]) * (
|
||||||
|
val[inds] - val[inds - 1]
|
||||||
|
) / (old_x[inds] - old_x[inds - 1])
|
||||||
|
new_vals[i][equal] = val[0]
|
||||||
|
return new_vals
|
||||||
|
|
||||||
|
|
||||||
|
@numba.jit(nopython=True)
|
||||||
|
def linear_interp_1d(old_x: np.ndarray, old_y: np.ndarray, new_x: np.ndarray):
|
||||||
|
new_vals = np.zeros(len(new_x))
|
||||||
|
interpolable = (new_x > old_x[0]) & (new_x <= old_x[-1])
|
||||||
|
inds = np.searchsorted(old_x, new_x[interpolable])
|
||||||
|
new_vals[interpolable] = old_y[inds - 1] + (new_x[interpolable] - old_x[inds - 1]) * (
|
||||||
|
old_y[inds] - old_y[inds - 1]
|
||||||
|
) / (old_x[inds] - old_x[inds - 1])
|
||||||
|
new_vals[new_x == old_x[0]] = old_y[0]
|
||||||
|
return new_vals
|
||||||
|
|
||||||
|
|
||||||
|
def envelope_ind(
|
||||||
|
signal: np.ndarray, dmin: int = 1, dmax: int = 1, split: bool = False
|
||||||
|
) -> tuple[np.ndarray, np.ndarray]:
|
||||||
|
"""
|
||||||
|
Attempts to separate the envolope from a periodic signal and return the indices of the
|
||||||
|
top/bottom envelope of a signal
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
signal : np.ndarray, shape (n,)
|
||||||
|
signal array (must be sorted)
|
||||||
|
dmin, dmax : int, optional
|
||||||
|
size of chunks for lower/upper envelope
|
||||||
|
split: bool, optional
|
||||||
|
split the signal in half along its mean, might help to generate the envelope in some cases
|
||||||
|
this has the effect of forcing the envlopes to be on either side of the dc signal
|
||||||
|
by default False
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
np.ndarray, shape (m,), m <= n
|
||||||
|
lower envelope indices
|
||||||
|
np.ndarray, shape (l,), l <= n
|
||||||
|
upper envelope indices
|
||||||
|
"""
|
||||||
|
|
||||||
|
local_min = (np.diff(np.sign(np.diff(signal))) > 0).nonzero()[0] + 1
|
||||||
|
local_max = (np.diff(np.sign(np.diff(signal))) < 0).nonzero()[0] + 1
|
||||||
|
|
||||||
|
if split:
|
||||||
|
dc_value = np.mean(signal)
|
||||||
|
local_min = local_min[signal[local_min] < dc_value]
|
||||||
|
local_max = local_max[signal[local_max] > dc_value]
|
||||||
|
|
||||||
|
if dmin > 1:
|
||||||
|
local_min = local_min[
|
||||||
|
[i + np.argmin(signal[local_min[i : i + dmin]]) for i in range(0, len(local_min), dmin)]
|
||||||
|
]
|
||||||
|
if dmax > 1:
|
||||||
|
local_max = local_max[
|
||||||
|
[i + np.argmax(signal[local_max[i : i + dmax]]) for i in range(0, len(local_max), dmax)]
|
||||||
|
]
|
||||||
|
|
||||||
|
return local_min, local_max
|
||||||
|
|
||||||
|
|
||||||
|
def envelope_2d(x: np.ndarray, values: np.ndarray) -> np.ndarray:
|
||||||
|
"""
|
||||||
|
returns the envelope of a 2d propagation-like array
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
x : np.ndarray, shape (nt,)
|
||||||
|
x axis
|
||||||
|
values : np.ndarray, shape (nz, nt)
|
||||||
|
values of which to find the envelope
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
np.ndarray, shape (nz, nt)
|
||||||
|
interpolated values
|
||||||
|
"""
|
||||||
|
return np.array([envelope_1d(x, y) for y in values])
|
||||||
|
|
||||||
|
|
||||||
|
def envelope_1d(y: np.ndarray, x: np.ndarray | None = None) -> np.ndarray:
|
||||||
|
if x is None:
|
||||||
|
x = np.arange(len(y))
|
||||||
|
_, hi = envelope_ind(y)
|
||||||
|
return interp1d(x[hi], y[hi], kind="cubic", fill_value=0, bounds_error=False)(x)
|
||||||
|
|
||||||
|
|
||||||
|
@dataclass(frozen=True)
|
||||||
|
class LobeProps:
|
||||||
|
left_pos: float
|
||||||
|
left_fwhm: float
|
||||||
|
center: float
|
||||||
|
right_fwhm: float
|
||||||
|
right_pos: float
|
||||||
|
interp: interp1d
|
||||||
|
|
||||||
|
@property
|
||||||
|
@cache
|
||||||
|
def x(self) -> np.ndarray:
|
||||||
|
return np.array(
|
||||||
|
[self.left_pos, self.left_fwhm, self.center, self.right_fwhm, self.right_pos]
|
||||||
|
)
|
||||||
|
|
||||||
|
@property
|
||||||
|
@cache
|
||||||
|
def y(self) -> np.ndarray:
|
||||||
|
return self.interp(self.x)
|
||||||
|
|
||||||
|
@property
|
||||||
|
@cache
|
||||||
|
def fwhm(self) -> float:
|
||||||
|
return abs(self.right_fwhm - self.left_fwhm)
|
||||||
|
|
||||||
|
@property
|
||||||
|
@cache
|
||||||
|
def width(self) -> float:
|
||||||
|
return abs(self.right_pos - self.left_pos)
|
||||||
|
|
||||||
|
|
||||||
|
def measure_lobe(x_in, y_in, /, lobe_pos: int | None = None, thr_rel: float = 1 / 50) -> LobeProps:
|
||||||
|
"""
|
||||||
|
given a fairly smooth signal, finds the highest lobe and returns its position as well
|
||||||
|
as its fwhm points
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
x_in : np.ndarray, shape (n,)
|
||||||
|
x values
|
||||||
|
y_in : np.ndarray, shape (n,)
|
||||||
|
y values
|
||||||
|
lobe_pos : int, optional
|
||||||
|
index of the desired lobe, by default None (take highest peak)
|
||||||
|
thr_rel : float, optional
|
||||||
|
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
np.ndarray
|
||||||
|
(left limit, left half maximum, maximum position, right half maximum, right limit)
|
||||||
|
"""
|
||||||
|
interp = interp1d(x_in, y_in)
|
||||||
|
lobe_index = lobe_pos or np.argmax(y_in)
|
||||||
|
maxi = y_in[lobe_index]
|
||||||
|
maxi2 = maxi / 2
|
||||||
|
thr_abs = maxi * thr_rel
|
||||||
|
half_max_left: float = all_zeros(x_in[:lobe_index], y_in[:lobe_index] - maxi2)[-1]
|
||||||
|
half_max_right: float = all_zeros(x_in[lobe_index:], y_in[lobe_index:] - maxi2)[0]
|
||||||
|
|
||||||
|
poly = lagrange((half_max_left, x_in[lobe_index], half_max_right), (maxi2, maxi2 * 2, maxi2))
|
||||||
|
parabola_left, parabola_right = sorted(poly.roots)
|
||||||
|
|
||||||
|
r_cand = x_in > half_max_right
|
||||||
|
x_right = x_in[r_cand]
|
||||||
|
y_right = y_in[r_cand]
|
||||||
|
|
||||||
|
l_cand = x_in < half_max_left
|
||||||
|
x_left = x_in[l_cand][::-1]
|
||||||
|
y_left = y_in[l_cand][::-1]
|
||||||
|
|
||||||
|
d = {}
|
||||||
|
for x, y, central_parabola_root, sign in [
|
||||||
|
(x_left, y_left, parabola_left, 1),
|
||||||
|
(x_right, y_right, parabola_right, -1),
|
||||||
|
]:
|
||||||
|
candidates = []
|
||||||
|
slope = sign * np.gradient(y, x)
|
||||||
|
|
||||||
|
for y_test, num_to_take in [
|
||||||
|
(sign * np.gradient(slope, x), 2),
|
||||||
|
(y - thr_abs, 1),
|
||||||
|
(slope, 3),
|
||||||
|
]:
|
||||||
|
candidates.extend(all_zeros(x, y_test)[:num_to_take])
|
||||||
|
candidates = np.array(sorted(candidates))
|
||||||
|
|
||||||
|
side_parabola_root = x[0] - 2 * y[0] / (sign * slope[0])
|
||||||
|
weights = (
|
||||||
|
np.abs(candidates - side_parabola_root)
|
||||||
|
+ np.abs(candidates - central_parabola_root)
|
||||||
|
+ interp(candidates) / thr_abs
|
||||||
|
)
|
||||||
|
d[sign] = candidates[np.argmin(weights)]
|
||||||
|
|
||||||
|
return LobeProps(d[1], half_max_left, x_in[lobe_index], half_max_right, d[-1], interp)
|
||||||
|
|
||||||
|
|
||||||
|
@numba.jit(nopython=True)
|
||||||
|
def cumulative_simpson(x: np.ndarray) -> np.ndarray:
|
||||||
|
out = np.zeros_like(x)
|
||||||
|
c1 = 1 / 3
|
||||||
|
c2 = 4 / 3
|
||||||
|
out[1] = (x[1] + x[0]) * 0.5
|
||||||
|
for i in range(2, len(x)):
|
||||||
|
out[i] = out[i - 2] + x[i - 2] * c1 + x[i - 1] * c2 + c1 * x[i]
|
||||||
|
return out
|
||||||
|
|
||||||
|
|
||||||
|
@numba.jit(nopython=True)
|
||||||
|
def cumulative_boole(x: np.ndarray) -> np.ndarray:
|
||||||
|
out = np.zeros_like(x)
|
||||||
|
c1 = 14 / 45
|
||||||
|
c2 = 64 / 45
|
||||||
|
c3 = 24 / 45
|
||||||
|
c = np.array([c1, c2, c3, c2, c1])
|
||||||
|
ind = np.arange(5)
|
||||||
|
out[ind] = cumulative_simpson(x[ind])
|
||||||
|
for i in range(4, len(x)):
|
||||||
|
out[i] = out[i - 4] + np.sum(c * x[i - 4 : i + 1])
|
||||||
|
return out
|
||||||
|
|
||||||
|
|
||||||
|
def stencil_coefficients(stencil_points: Sequence, order: int) -> np.ndarray:
|
||||||
|
"""
|
||||||
|
Reference
|
||||||
|
---------
|
||||||
|
https://en.wikipedia.org/wiki/Finite_difference_coefficient#Arbitrary_stencil_points
|
||||||
|
"""
|
||||||
|
mat = np.power.outer(stencil_points, np.arange(len(stencil_points))).T
|
||||||
|
d = np.zeros(len(stencil_points))
|
||||||
|
d[order] = math.factorial(order)
|
||||||
|
return np.linalg.solve(mat, d)
|
||||||
|
|
||||||
|
|
||||||
|
@cache
|
||||||
|
def central_stencil_coefficients(n: int, order: int) -> np.ndarray:
|
||||||
|
"""
|
||||||
|
returns the coefficients of a centered finite difference scheme
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
n : int
|
||||||
|
number of points
|
||||||
|
order : int
|
||||||
|
order of differentiation
|
||||||
|
"""
|
||||||
|
return stencil_coefficients(np.arange(n * 2 + 1) - n, order)
|
||||||
|
|
||||||
|
|
||||||
|
@cache
|
||||||
|
def stencil_coefficients_set(n: int, order: int) -> tuple[np.ndarray, np.ndarray, np.ndarray]:
|
||||||
|
"""
|
||||||
|
coefficients for a forward, centered and backward finite difference differentation scheme of
|
||||||
|
order `order` that extends `n` points away from the evaluation point (`x_0`)
|
||||||
|
"""
|
||||||
|
central = central_stencil_coefficients(n, order)
|
||||||
|
left = stencil_coefficients(np.arange(n + 1), order)
|
||||||
|
right = stencil_coefficients(-np.arange(n + 1)[::-1], order)
|
||||||
|
return left, central, right
|
||||||
|
|
||||||
|
|
||||||
|
def differentiate_arr(
|
||||||
|
values: np.ndarray,
|
||||||
|
diff_order: int,
|
||||||
|
extent: int | None = None,
|
||||||
|
h: float = 1.0,
|
||||||
|
correct_edges=True,
|
||||||
|
) -> np.ndarray:
|
||||||
|
"""
|
||||||
|
takes a derivative of order `diff_order` using equally spaced values
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
---------
|
||||||
|
values : ndarray
|
||||||
|
equally spaced values
|
||||||
|
diff_order : int
|
||||||
|
order of differentiation
|
||||||
|
extent : int, optional
|
||||||
|
how many points away from the center the scheme uses. This determines accuracy.
|
||||||
|
example: extent=6 means that 13 (6 on either side + center) points are used to evaluate the
|
||||||
|
derivative at each point. by default diff_order + 2
|
||||||
|
h : float, optional
|
||||||
|
step size, by default 1.0
|
||||||
|
correct_edges : bool, optional
|
||||||
|
avoid artifacts by using forward/backward schemes on the edges, by default True
|
||||||
|
|
||||||
|
Reference
|
||||||
|
---------
|
||||||
|
https://en.wikipedia.org/wiki/Finite_difference_coefficient
|
||||||
|
|
||||||
|
"""
|
||||||
|
if extent is None:
|
||||||
|
extent = diff_order + 2
|
||||||
|
n_points = (diff_order + extent) // 2
|
||||||
|
|
||||||
|
if not correct_edges:
|
||||||
|
central_coefs = central_stencil_coefficients(n_points, diff_order)
|
||||||
|
result = np.convolve(values, central_coefs[::-1], mode="same")
|
||||||
|
else:
|
||||||
|
left_coefs, central_coefs, right_coefs = stencil_coefficients_set(n_points, diff_order)
|
||||||
|
result = np.concatenate(
|
||||||
|
(
|
||||||
|
np.convolve(values[: 2 * n_points], left_coefs[::-1], mode="valid"),
|
||||||
|
np.convolve(values, central_coefs[::-1], mode="valid"),
|
||||||
|
np.convolve(values[-2 * n_points :], right_coefs[::-1], mode="valid"),
|
||||||
|
)
|
||||||
|
)
|
||||||
|
return result / h**diff_order
|
||||||
|
|
||||||
|
|
||||||
|
def mean_angle(values: np.ndarray, axis: int = 0):
|
||||||
|
"""
|
||||||
|
computes the mean angle of an array along a given axis
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
spectra : np.ndarray
|
||||||
|
complex values from which to compute the mean phase
|
||||||
|
axis : int, optional
|
||||||
|
axis on which to take the mean, by default 0
|
||||||
|
|
||||||
|
Returns
|
||||||
|
----------
|
||||||
|
np.ndarray
|
||||||
|
array of complex numbers of unit length representing the mean phase, decimated along the
|
||||||
|
specified axis
|
||||||
|
|
||||||
|
Example
|
||||||
|
----------
|
||||||
|
>>> x = np.array([[1 + 1j, 0 + 2j, -3 - 1j],
|
||||||
|
[1 + 0j, 2 + 3j, -3 + 1j]])
|
||||||
|
>>> mean_angle(x)
|
||||||
|
array([ 0.92387953+0.38268343j, 0.28978415+0.95709203j, -1. +0.j ])
|
||||||
|
|
||||||
|
"""
|
||||||
|
values = np.divide(
|
||||||
|
values, np.abs(values), out=np.zeros(values.shape, dtype=values.dtype), where=values != 0
|
||||||
|
)
|
||||||
|
total_phase = np.sum(values, axis=axis)
|
||||||
|
return np.divide(total_phase, np.abs(total_phase), where=total_phase != 0, out=total_phase)
|
||||||
0
src/dispersionapp/physics/__init__.py
Normal file
0
src/dispersionapp/physics/__init__.py
Normal file
1202
src/dispersionapp/physics/fiber.py
Normal file
1202
src/dispersionapp/physics/fiber.py
Normal file
File diff suppressed because it is too large
Load Diff
445
src/dispersionapp/physics/materials.py
Normal file
445
src/dispersionapp/physics/materials.py
Normal file
@@ -0,0 +1,445 @@
|
|||||||
|
from __future__ import annotations
|
||||||
|
|
||||||
|
import warnings
|
||||||
|
from dataclasses import dataclass, field
|
||||||
|
from functools import cache
|
||||||
|
from typing import Any, overload
|
||||||
|
|
||||||
|
import numpy as np
|
||||||
|
|
||||||
|
import dispersionapp.io as io
|
||||||
|
import dispersionapp.math as math
|
||||||
|
import dispersionapp.physics.units as units
|
||||||
|
from dispersionapp.physics.units import NA, c, epsilon0, kB
|
||||||
|
|
||||||
|
type Num = np.floating | np.integer | float | int
|
||||||
|
|
||||||
|
|
||||||
|
@dataclass
|
||||||
|
class Sellmeier:
|
||||||
|
B: list[float] = field(default_factory=list)
|
||||||
|
C: list[float] = field(default_factory=list)
|
||||||
|
pressure_ref: float = 101325
|
||||||
|
temperature_ref: float = 273.15
|
||||||
|
kind: int = 2
|
||||||
|
constant: float = 0
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
@cache
|
||||||
|
def load(cls, name: str) -> Sellmeier:
|
||||||
|
mat_dico = io.load_material_dico(name)
|
||||||
|
s = mat_dico.get("sellmeier", {})
|
||||||
|
return cls(
|
||||||
|
**{
|
||||||
|
newk: s.get(k, None)
|
||||||
|
for newk, k in zip(
|
||||||
|
["B", "C", "pressure_ref", "temperature_ref", "kind", "constant"],
|
||||||
|
["B", "C", "P0", "T0", "kind", "const"],
|
||||||
|
)
|
||||||
|
if k in s
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
@overload
|
||||||
|
def chi(
|
||||||
|
self, wl: np.ndarray, temperature: float | None = None, pressure: float | None = None
|
||||||
|
) -> np.ndarray: ...
|
||||||
|
@overload
|
||||||
|
def chi(
|
||||||
|
self, wl: Num, temperature: float | None = None, pressure: float | None = None
|
||||||
|
) -> Num: ...
|
||||||
|
def chi(self, wl, temperature: float | None = None, pressure: float | None = None):
|
||||||
|
"""n^2 - 1"""
|
||||||
|
if isinstance(wl, np.ndarray):
|
||||||
|
chi = np.zeros_like(wl) # = n^2 - 1
|
||||||
|
else:
|
||||||
|
chi = 0
|
||||||
|
if self.kind == 1:
|
||||||
|
for b, c_ in zip(self.B, self.C):
|
||||||
|
chi += wl**2 * b / (wl**2 - c_)
|
||||||
|
elif self.kind == 2: # gives n-1
|
||||||
|
for b, c_ in zip(self.B, self.C):
|
||||||
|
chi += b / (c_ - 1 / wl**2)
|
||||||
|
chi += self.constant
|
||||||
|
chi = (chi + 1) ** 2 - 1
|
||||||
|
elif self.kind == 3: # Schott formula
|
||||||
|
for i, b in reversed(list(enumerate(self.B))):
|
||||||
|
chi += b * wl ** (-2 * (i - 1))
|
||||||
|
chi = chi - 1
|
||||||
|
else:
|
||||||
|
raise ValueError(f"kind {self.kind} is not recognized.")
|
||||||
|
|
||||||
|
if temperature is not None:
|
||||||
|
chi *= self.temperature_ref / temperature
|
||||||
|
|
||||||
|
if pressure is not None:
|
||||||
|
chi *= pressure / self.pressure_ref
|
||||||
|
return chi
|
||||||
|
|
||||||
|
@overload
|
||||||
|
def n_gas_2(
|
||||||
|
self, wl: np.ndarray, temperature: float | None = None, pressure: float | None = None
|
||||||
|
) -> np.ndarray: ...
|
||||||
|
@overload
|
||||||
|
def n_gas_2(
|
||||||
|
self, wl: Num, temperature: float | None = None, pressure: float | None = None
|
||||||
|
) -> float: ...
|
||||||
|
def n_gas_2(self, wl, temperature: float | None = None, pressure: float | None = None):
|
||||||
|
return self.chi(wl, temperature, pressure) + 1
|
||||||
|
|
||||||
|
@overload
|
||||||
|
def n(
|
||||||
|
self, wl: np.ndarray, temperature: float | None = None, pressure: float | None = None
|
||||||
|
) -> np.ndarray: ...
|
||||||
|
@overload
|
||||||
|
def n(
|
||||||
|
self, wl: Num, temperature: float | None = None, pressure: float | None = None
|
||||||
|
) -> float: ...
|
||||||
|
def n(self, wl, temperature: float | None = None, pressure: float | None = None):
|
||||||
|
return np.sqrt(self.n_gas_2(wl, temperature, pressure))
|
||||||
|
|
||||||
|
def delta(self, wl: np.ndarray, wl_zero_disp: float) -> np.ndarray:
|
||||||
|
"""
|
||||||
|
'delta' quantity that describes the gas dispersion according to eq. S7 in [1]
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
wl : ndarray
|
||||||
|
wavelength in m
|
||||||
|
wl_zero_disp : float
|
||||||
|
zero dispersion wavelength in m
|
||||||
|
|
||||||
|
Reference
|
||||||
|
---------
|
||||||
|
[1] TRAVERS, John C., GRIGOROVA, Teodora F., BRAHMS, Christian, et al. High-energy
|
||||||
|
pulse self-compression and ultraviolet generation through soliton dynamics in hollow
|
||||||
|
capillary fibres. Nature Photonics, 2019, vol. 13, no 8, p. 547-554.
|
||||||
|
"""
|
||||||
|
factor = (math.u_nm(1, 1) / c) ** 2 * (0.5 * wl / np.pi) ** 3
|
||||||
|
f = np.gradient(np.gradient(self.chi(wl), wl), wl)
|
||||||
|
ind = math.argclosest(wl, wl_zero_disp)
|
||||||
|
return factor * (f / f[ind] - 1)
|
||||||
|
|
||||||
|
|
||||||
|
class Gas:
|
||||||
|
name: str
|
||||||
|
sellmeier: Sellmeier
|
||||||
|
atomic_number: int | float
|
||||||
|
atomic_mass: float
|
||||||
|
chi3_0: float
|
||||||
|
ionization_energy: float | None
|
||||||
|
|
||||||
|
_raw_sellmeier: dict[str, Any]
|
||||||
|
_kerr_wl: np.ndarray
|
||||||
|
|
||||||
|
def __init__(self, gas_name: str):
|
||||||
|
self.name = gas_name
|
||||||
|
self._raw_sellmeier = io.load_material_dico(gas_name)
|
||||||
|
self.atomic_mass = self._raw_sellmeier["atomic_mass"]
|
||||||
|
self.atomic_number = self._raw_sellmeier["atomic_number"]
|
||||||
|
self.ionization_energy = self._raw_sellmeier.get("ionization_energy")
|
||||||
|
|
||||||
|
s = self._raw_sellmeier.get("sellmeier", {})
|
||||||
|
self.sellmeier = Sellmeier(
|
||||||
|
**{
|
||||||
|
newk: s.get(k, None)
|
||||||
|
for newk, k in zip(
|
||||||
|
["B", "C", "pressure_ref", "temperature_ref", "kind", "constant"],
|
||||||
|
["B", "C", "P0", "T0", "kind", "const"],
|
||||||
|
)
|
||||||
|
if k in s
|
||||||
|
}
|
||||||
|
)
|
||||||
|
kerr = self._raw_sellmeier["kerr"]
|
||||||
|
n2_0 = kerr["n2"]
|
||||||
|
self._kerr_wl = kerr.get("wavelength", 800e-9)
|
||||||
|
self.chi3_0 = (
|
||||||
|
4
|
||||||
|
/ 3
|
||||||
|
* units.epsilon0
|
||||||
|
* units.c
|
||||||
|
* self.sellmeier.n_gas_2(self._kerr_wl, kerr["T0"], kerr["P0"])
|
||||||
|
* n2_0
|
||||||
|
)
|
||||||
|
|
||||||
|
def pressure_from_relative_density(
|
||||||
|
self, density: float, temperature: float | None = None
|
||||||
|
) -> float:
|
||||||
|
temperature = temperature or self.sellmeier.temperature_ref
|
||||||
|
return self.sellmeier.temperature_ref / temperature * density * self.sellmeier.pressure_ref
|
||||||
|
|
||||||
|
def density_factor(self, temperature: float, pressure: float, ideal_gas: bool) -> float:
|
||||||
|
"""
|
||||||
|
returns the number density relative to reference values
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
temperature : float
|
||||||
|
target temperature in K
|
||||||
|
pressure : float
|
||||||
|
target pressure in Pa
|
||||||
|
ideal_gas : bool
|
||||||
|
whether to use ideal gas law
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
float
|
||||||
|
N / N_0
|
||||||
|
"""
|
||||||
|
if ideal_gas:
|
||||||
|
return (
|
||||||
|
pressure
|
||||||
|
/ self.sellmeier.pressure_ref
|
||||||
|
* self.sellmeier.temperature_ref
|
||||||
|
/ temperature
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
return self.number_density_van_der_waals(
|
||||||
|
pressure, temperature
|
||||||
|
) / self.number_density_van_der_waals(
|
||||||
|
self.sellmeier.pressure_ref,
|
||||||
|
self.sellmeier.temperature_ref,
|
||||||
|
)
|
||||||
|
|
||||||
|
def number_density(
|
||||||
|
self,
|
||||||
|
temperature: float | None = None,
|
||||||
|
pressure: float | None = None,
|
||||||
|
ideal_gas: bool = False,
|
||||||
|
) -> float:
|
||||||
|
"""
|
||||||
|
returns the number density in 1/m^3 using van der Waals equation
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
temperature : float, optional
|
||||||
|
temperature in K, by default None
|
||||||
|
pressure : float, optional
|
||||||
|
pressure in Pa, by default None
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
float
|
||||||
|
number density in 1/m^3
|
||||||
|
"""
|
||||||
|
pressure = pressure or self.sellmeier.pressure_ref
|
||||||
|
temperature = temperature or self.sellmeier.temperature_ref
|
||||||
|
if ideal_gas:
|
||||||
|
return pressure / temperature / kB
|
||||||
|
else:
|
||||||
|
return self.number_density_van_der_waals(pressure, temperature)
|
||||||
|
|
||||||
|
def number_density_van_der_waals(
|
||||||
|
self, pressure: float | None = None, temperature: float | None = None
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
returns the number density of a gas
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
pressure : float, optional
|
||||||
|
pressure in Pa, by default the reference pressure
|
||||||
|
temperature : float, optional
|
||||||
|
temperature in K, by default the reference temperature
|
||||||
|
|
||||||
|
Returns
|
||||||
|
----------
|
||||||
|
the numbers density (/m^3)
|
||||||
|
|
||||||
|
Raises
|
||||||
|
----------
|
||||||
|
ValueError : Since the Van der Waals equation is a cubic one, there could be more than one
|
||||||
|
real, positive solution
|
||||||
|
"""
|
||||||
|
|
||||||
|
if pressure == 0:
|
||||||
|
return 0
|
||||||
|
a = self._raw_sellmeier.get("a", 0)
|
||||||
|
b = self._raw_sellmeier.get("b", 0)
|
||||||
|
pressure = (
|
||||||
|
self._raw_sellmeier["sellmeier"].get("P0", 101325) if pressure is None else pressure
|
||||||
|
)
|
||||||
|
temperature = (
|
||||||
|
self._raw_sellmeier["sellmeier"].get("T0", 273.15)
|
||||||
|
if temperature is None
|
||||||
|
else temperature
|
||||||
|
)
|
||||||
|
ap = a / NA**2
|
||||||
|
bp = b / NA
|
||||||
|
|
||||||
|
# setup van der Waals equation for the number density
|
||||||
|
p3 = -ap * bp
|
||||||
|
p2 = ap
|
||||||
|
p1 = -(pressure * bp + kB * temperature)
|
||||||
|
p0 = pressure
|
||||||
|
|
||||||
|
# filter out unwanted matches
|
||||||
|
roots = np.roots([p3, p2, p1, p0])
|
||||||
|
roots = roots[np.isreal(roots)].real
|
||||||
|
roots = roots[roots > 0]
|
||||||
|
if len(roots) != 1:
|
||||||
|
s = f"Van der Waals eq with parameters P={pressure}, T={temperature}, a={a}, b={b}"
|
||||||
|
s += f", There is more than one possible number density : {roots}."
|
||||||
|
s += f", {np.min(roots)} was returned"
|
||||||
|
warnings.warn(s)
|
||||||
|
return np.min(roots)
|
||||||
|
|
||||||
|
def chi3(self, temperature: float | None = None, pressure: float | None = None) -> float:
|
||||||
|
"""nonlinear susceptibility"""
|
||||||
|
|
||||||
|
# if pressure and/or temperature are specified, adjustment is made
|
||||||
|
# according to number density ratio
|
||||||
|
if pressure is not None or temperature is not None:
|
||||||
|
N0 = self.number_density_van_der_waals()
|
||||||
|
N = self.number_density_van_der_waals(pressure, temperature)
|
||||||
|
ratio = N / N0
|
||||||
|
else:
|
||||||
|
ratio = 1
|
||||||
|
return ratio * self.chi3_0
|
||||||
|
|
||||||
|
def n2(self, temperature: float | None = None, pressure: float | None = None) -> float:
|
||||||
|
sellmeier = self.sellmeier.n_gas_2(self._kerr_wl, temperature, pressure)
|
||||||
|
chi3 = self.chi3(temperature, pressure)
|
||||||
|
return 0.75 * chi3 / (units.epsilon0 * units.c * sellmeier)
|
||||||
|
|
||||||
|
@property
|
||||||
|
def ionic_charge(self):
|
||||||
|
return 1
|
||||||
|
|
||||||
|
@property
|
||||||
|
def barrier_suppression(self) -> float:
|
||||||
|
"""
|
||||||
|
Compute the barrier suppression threshold (W/m^2)
|
||||||
|
"""
|
||||||
|
field_max = self.barrier_suppression_field
|
||||||
|
return 0.5 * units.c * units.epsilon0 * field_max**2
|
||||||
|
|
||||||
|
@property
|
||||||
|
def barrier_suppression_field(self) -> float:
|
||||||
|
"""
|
||||||
|
Barrier suppression threshold electric field
|
||||||
|
|
||||||
|
Reference
|
||||||
|
---------
|
||||||
|
[1] KRAINOV, V. P. Theory of barrier-suppression ionization of atoms. Journal of Nonlinear
|
||||||
|
Optical Physics & Materials, 1995, vol. 4, no 04, p. 775-798.
|
||||||
|
[2] BETHE, H. A. et SALPETER, E. E. Quantum mechanics of one-and two-electron atoms. 1977.
|
||||||
|
"""
|
||||||
|
# from [1-2] :
|
||||||
|
# field_max = 0.0625 / self.ionic_charge * (self.ionization_energy / 2.1787e-18) ** 2
|
||||||
|
# return field_max = 5.14220670712125e11
|
||||||
|
|
||||||
|
# from [3] :
|
||||||
|
if self.ionization_energy is None:
|
||||||
|
raise ValueError(f"no ionization_energy for {self.name}")
|
||||||
|
Z = self.ionic_charge
|
||||||
|
Ip_au = self.ionization_energy / 4.359744650021498e-18
|
||||||
|
ns = Z / np.sqrt(2 * Ip_au)
|
||||||
|
return Z**3 / (16 * ns**4) * 5.14220670712125e11
|
||||||
|
|
||||||
|
def get(self, key, default=None):
|
||||||
|
return self._raw_sellmeier.get(key, default)
|
||||||
|
|
||||||
|
def __getitem__(self, key):
|
||||||
|
return self._raw_sellmeier[key]
|
||||||
|
|
||||||
|
def __repr__(self) -> str:
|
||||||
|
return f"{self.__class__.__name__}({self.name!r})"
|
||||||
|
|
||||||
|
|
||||||
|
def n_gas_2(
|
||||||
|
wl: np.ndarray, gas_name: str, pressure: float | None, temperature: float | None
|
||||||
|
) -> np.ndarray:
|
||||||
|
"""Returns the sqare of the index of refraction of the specified gas"""
|
||||||
|
return Sellmeier.load(gas_name).n_gas_2(wl, temperature, pressure)
|
||||||
|
|
||||||
|
|
||||||
|
def pressure_from_gradient(ratio: float, p0: float, p1: float) -> float:
|
||||||
|
"""
|
||||||
|
returns the pressure as function of distance with eq. 20 in Markos et al. (2017)
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
ratio : relative position in the fiber (0 = start, 1 = end)
|
||||||
|
p0 : pressure at the start
|
||||||
|
p1 : pressure at the end
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
the pressure (float)
|
||||||
|
"""
|
||||||
|
return np.sqrt(p0**2 - ratio * (p0**2 - p1**2))
|
||||||
|
|
||||||
|
|
||||||
|
def delta_gas(w: np.ndarray, gas: Gas) -> np.ndarray:
|
||||||
|
"""
|
||||||
|
returns the value delta_t (eq. 24 in Markos(2017))
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
w : np.ndarray
|
||||||
|
angular frequency array
|
||||||
|
gas : Gas
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
delta_t
|
||||||
|
since 2 gradients are computed, it is recommended to exclude the 2 extremum values
|
||||||
|
"""
|
||||||
|
chi = gas.sellmeier.chi(units.m_rads(w))
|
||||||
|
N0 = gas.number_density_van_der_waals()
|
||||||
|
|
||||||
|
dchi_dw = np.gradient(chi, w)
|
||||||
|
return 1 / (N0 * c) * (dchi_dw + w / 2 * np.gradient(dchi_dw, w))
|
||||||
|
|
||||||
|
|
||||||
|
def gas_n2(gas_name: str, pressure: float, temperature: float) -> float:
|
||||||
|
"""returns the nonlinear refractive index
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
gas_name : str
|
||||||
|
gas name
|
||||||
|
pressure : float
|
||||||
|
pressure in Pa
|
||||||
|
temperature : float
|
||||||
|
temperature in K
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
float
|
||||||
|
n2 in m2/W
|
||||||
|
"""
|
||||||
|
return Gas(gas_name).n2(temperature, pressure)
|
||||||
|
|
||||||
|
|
||||||
|
def gas_chi3(gas_name: str, wavelength: float, pressure: float, temperature: float) -> float:
|
||||||
|
"""
|
||||||
|
returns the chi3 of a particular material
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
gas_name : str
|
||||||
|
[description]
|
||||||
|
pressure : float
|
||||||
|
[description]
|
||||||
|
temperature : float
|
||||||
|
[description]
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
float
|
||||||
|
[description]
|
||||||
|
"""
|
||||||
|
gas = Gas(gas_name)
|
||||||
|
n = gas.sellmeier.n(wavelength, temperature, pressure)
|
||||||
|
n2 = gas.n2(temperature, pressure)
|
||||||
|
return n2_to_chi3(n2, n)
|
||||||
|
|
||||||
|
|
||||||
|
def n2_to_chi3(n2: float, n0: float) -> float:
|
||||||
|
return n2 * 4 * epsilon0 * n0**2 * c / 3
|
||||||
|
|
||||||
|
|
||||||
|
def chi3_to_n2(chi3: float, n0: float) -> float:
|
||||||
|
return 3.0 * chi3 / (4.0 * epsilon0 * c * n0**2)
|
||||||
1438
src/dispersionapp/physics/pulse.py
Normal file
1438
src/dispersionapp/physics/pulse.py
Normal file
File diff suppressed because it is too large
Load Diff
460
src/dispersionapp/physics/units.py
Normal file
460
src/dispersionapp/physics/units.py
Normal file
@@ -0,0 +1,460 @@
|
|||||||
|
# series of functions to convert different values to angular frequencies
|
||||||
|
# For example, nm(X) means "I give the number X in nm, figure out the ang. freq."
|
||||||
|
# to be used especially when giving plotting ranges : (400, 1400, nm), (-4, 8, ps), ...
|
||||||
|
|
||||||
|
from __future__ import annotations
|
||||||
|
|
||||||
|
from typing import Callable, Protocol, Sequence, Union, overload
|
||||||
|
|
||||||
|
import numpy as np
|
||||||
|
from numpy import pi
|
||||||
|
|
||||||
|
c = 299792458.0
|
||||||
|
h = 6.62607015e-34
|
||||||
|
hbar = 0.5 * h / np.pi
|
||||||
|
NA = 6.02214076e23
|
||||||
|
R = 8.31446261815324
|
||||||
|
kB = 1.380649e-23
|
||||||
|
epsilon0 = 8.85418781e-12
|
||||||
|
me = 9.1093837015e-31
|
||||||
|
e = 1.602176634e-19
|
||||||
|
|
||||||
|
|
||||||
|
prefix = dict(P=1e12, G=1e9, M=1e6, k=1e3, d=1e-1, c=1e-2, m=1e-3, u=1e-6, n=1e-9, p=1e-12, f=1e-15)
|
||||||
|
|
||||||
|
"""
|
||||||
|
Below are common units. You can define your own unit function
|
||||||
|
provided you decorate it with @unit and provide at least a type and a label
|
||||||
|
types are "WL", "FREQ", "AFREQ", "TIME", "PRESSURE", "TEMPERATURE", "OTHER"
|
||||||
|
"""
|
||||||
|
type _UT[T] = Callable[[T], T]
|
||||||
|
PRIMARIES = dict(WL="m", FREQ="Rad/s", AFREQ="Rad/s", TIME="s", PRESSURE="Pa", TEMPERATURE="K")
|
||||||
|
|
||||||
|
|
||||||
|
class Unit(Protocol):
|
||||||
|
@overload
|
||||||
|
def __call__(self, v: np.ndarray) -> np.ndarray: ...
|
||||||
|
@overload
|
||||||
|
def __call__(self, v: float | int | np.floating | np.integer) -> float: ...
|
||||||
|
def __call__(self, v): ...
|
||||||
|
@overload
|
||||||
|
def inv(self, v: np.ndarray) -> np.ndarray: ...
|
||||||
|
@overload
|
||||||
|
def inv(self, v: float | int | np.floating | np.integer) -> float: ...
|
||||||
|
def inv(self, v): ...
|
||||||
|
def inverse(self, f: _UT) -> Unit: ...
|
||||||
|
|
||||||
|
|
||||||
|
class UnitMap(dict):
|
||||||
|
def __setitem__(self, new_name, new_func):
|
||||||
|
super().__setitem__(new_name, new_func)
|
||||||
|
already_here = [name for name in self if isinstance(name, str)]
|
||||||
|
for old_name in already_here:
|
||||||
|
super().__setitem__((old_name, new_name), self._chain(old_name, new_name))
|
||||||
|
super().__setitem__((new_name, old_name), self._chain(new_name, old_name))
|
||||||
|
|
||||||
|
def _chain(self, name_1: str, name_2: str) -> _UT:
|
||||||
|
c1 = self[name_1]
|
||||||
|
c2 = self[name_2]
|
||||||
|
|
||||||
|
def chained_function[T](x: T) -> T:
|
||||||
|
return c2.inv(c1(x))
|
||||||
|
|
||||||
|
chained_function.name = f"{name_1}_to_{name_2}"
|
||||||
|
chained_function.__name__ = f"{name_1}_to_{name_2}"
|
||||||
|
chained_function.__doc__ = f"converts x from {name_1} to {name_2}"
|
||||||
|
|
||||||
|
return chained_function
|
||||||
|
|
||||||
|
|
||||||
|
units_map: dict[Union[str, tuple[str, str]], _UT] = UnitMap()
|
||||||
|
|
||||||
|
|
||||||
|
class To:
|
||||||
|
def __init__(self, name: str):
|
||||||
|
self.name = name
|
||||||
|
|
||||||
|
def __getstate__(self):
|
||||||
|
"""make pickle happy"""
|
||||||
|
return self.name
|
||||||
|
|
||||||
|
def __setstate__(self, name):
|
||||||
|
"""make pickle happy"""
|
||||||
|
self.name = name
|
||||||
|
|
||||||
|
def __getattr__(self, key: str):
|
||||||
|
try:
|
||||||
|
return units_map[self.name, key]
|
||||||
|
except KeyError:
|
||||||
|
raise KeyError(f"no registered unit named {key!r}") from None
|
||||||
|
|
||||||
|
|
||||||
|
def W_to_Vm(n0: float, effective_area: float) -> float:
|
||||||
|
"""returns the factor to convert from [|E|²] = W to [|E|] = V/m
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
n : float
|
||||||
|
refractive index
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
float
|
||||||
|
p such that E_sqrt(W) * p = W_Vm
|
||||||
|
"""
|
||||||
|
return 1.0 / np.sqrt(effective_area * 0.5 * epsilon0 * c * n0)
|
||||||
|
|
||||||
|
|
||||||
|
def unit_formatter(
|
||||||
|
unit: str, decimals: int = 3, vmin: float | None = 1e-28
|
||||||
|
) -> Callable[[float | int], str]:
|
||||||
|
if not unit:
|
||||||
|
|
||||||
|
def formatter(val):
|
||||||
|
return f"{val:.{decimals}g}"
|
||||||
|
|
||||||
|
elif unit == "%":
|
||||||
|
|
||||||
|
def formatter(val):
|
||||||
|
return f"{100 * val:.{decimals}g}%"
|
||||||
|
|
||||||
|
else:
|
||||||
|
|
||||||
|
def formatter(val):
|
||||||
|
if vmin is not None and abs(val) < vmin:
|
||||||
|
return f"0{unit}"
|
||||||
|
base, true_exp = format(val, f".{3 + decimals}e").split("e")
|
||||||
|
true_exp = int(true_exp)
|
||||||
|
exp, mult = divmod(true_exp, 3)
|
||||||
|
if exp < -8:
|
||||||
|
mult -= -3 * (8 + exp)
|
||||||
|
exp = -8
|
||||||
|
elif exp > 8:
|
||||||
|
mult += 3 * (exp - 8)
|
||||||
|
exp = 8
|
||||||
|
|
||||||
|
prefix = "yzafpnµm kMGTPEZY"[8 + exp] if exp else ""
|
||||||
|
return f"{float(base) * 10**mult:.{decimals}g}{prefix}{unit}"
|
||||||
|
|
||||||
|
def _format(val):
|
||||||
|
if isinstance(val, (Sequence, np.ndarray)):
|
||||||
|
return f"({', '.join(_format(el) for el in val)})"
|
||||||
|
else:
|
||||||
|
return formatter(val)
|
||||||
|
|
||||||
|
def _format_mpl(val, _):
|
||||||
|
return _format(val)
|
||||||
|
|
||||||
|
setattr(_format, "for_mpl", _format_mpl)
|
||||||
|
|
||||||
|
return _format
|
||||||
|
|
||||||
|
|
||||||
|
class unit:
|
||||||
|
inv = None
|
||||||
|
|
||||||
|
def __init__(self, tpe: str, label: str):
|
||||||
|
self.type = tpe
|
||||||
|
self.label = label
|
||||||
|
|
||||||
|
def __call__(self, func) -> Unit:
|
||||||
|
self.name = func.__name__
|
||||||
|
self.func = func
|
||||||
|
self.inv = func
|
||||||
|
|
||||||
|
units_map[self.name] = self.func
|
||||||
|
|
||||||
|
func.to = To(self.name)
|
||||||
|
func.inv = func
|
||||||
|
func.inverse = self.inverse
|
||||||
|
func.type = self.type
|
||||||
|
func.label = self.label
|
||||||
|
func.name = self.name
|
||||||
|
func.__doc__ = f"Transform x from {self.name!r} to {PRIMARIES.get(self.type)!r}"
|
||||||
|
return func
|
||||||
|
|
||||||
|
def inverse(self, func: _UT):
|
||||||
|
if func.__name__ == self.name:
|
||||||
|
raise ValueError(
|
||||||
|
f"inverse function of {self.name} must be named something else than {self.name}"
|
||||||
|
)
|
||||||
|
self.inv = func
|
||||||
|
self.func.inv = func
|
||||||
|
return func
|
||||||
|
|
||||||
|
|
||||||
|
@unit("WL", r"Wavelength λ (m)")
|
||||||
|
def m(wl):
|
||||||
|
return wl
|
||||||
|
|
||||||
|
|
||||||
|
@unit("WL", r"Wavelength λ (nm)")
|
||||||
|
def nm(wl):
|
||||||
|
return wl * 1e-9
|
||||||
|
|
||||||
|
|
||||||
|
@nm.inverse
|
||||||
|
def nm_inv(wl):
|
||||||
|
return wl * 1e9
|
||||||
|
|
||||||
|
|
||||||
|
@unit("WL", r"Wavelength λ (μm)")
|
||||||
|
def um(wl):
|
||||||
|
return wl * 1e-6
|
||||||
|
|
||||||
|
|
||||||
|
@um.inverse
|
||||||
|
def um_inv(wl):
|
||||||
|
return wl * 1e6
|
||||||
|
|
||||||
|
|
||||||
|
@unit("FREQ", r"Frequency $f$ (Hz)")
|
||||||
|
def Hz(f):
|
||||||
|
return 2 * pi * f
|
||||||
|
|
||||||
|
|
||||||
|
@Hz.inverse
|
||||||
|
def Hz_inv(w):
|
||||||
|
return w / (2 * pi)
|
||||||
|
|
||||||
|
|
||||||
|
@unit("FREQ", r"Frequency $f$ (THz)")
|
||||||
|
def THz(f):
|
||||||
|
return 1e12 * 2 * pi * f
|
||||||
|
|
||||||
|
|
||||||
|
@THz.inverse
|
||||||
|
def THz_inv(w):
|
||||||
|
return w / (1e12 * 2 * pi)
|
||||||
|
|
||||||
|
|
||||||
|
@unit("FREQ", r"Frequency $f$ (PHz)")
|
||||||
|
def PHz(f):
|
||||||
|
return 1e15 * 2 * pi * f
|
||||||
|
|
||||||
|
|
||||||
|
@PHz.inverse
|
||||||
|
def PHz_inv(w):
|
||||||
|
return w / (1e15 * 2 * pi)
|
||||||
|
|
||||||
|
|
||||||
|
@unit("AFREQ", r"Angular frequency $\omega$ ($\frac{\mathrm{rad}}{\mathrm{s}}$)")
|
||||||
|
def rad_s(w):
|
||||||
|
return w
|
||||||
|
|
||||||
|
|
||||||
|
@unit("AFREQ", r"Angular frequency $\omega$ ($\frac{\mathrm{Prad}}{\mathrm{s}}$)")
|
||||||
|
def Prad_s(w):
|
||||||
|
return w * 1e15
|
||||||
|
|
||||||
|
|
||||||
|
@Prad_s.inverse
|
||||||
|
def Prad_s_inv(w):
|
||||||
|
return w * 1e-15
|
||||||
|
|
||||||
|
|
||||||
|
@unit("TIME", r"relative time ${\tau}/{\tau_\mathrm{0, FWHM}}$")
|
||||||
|
def rel_time(t):
|
||||||
|
return t
|
||||||
|
|
||||||
|
|
||||||
|
@unit("FREQ", r"relative angular freq. $(\omega - \omega_0)/\Delta\omega_0$")
|
||||||
|
def rel_freq(f):
|
||||||
|
return f
|
||||||
|
|
||||||
|
|
||||||
|
@unit("TIME", r"Time $t$ (s)")
|
||||||
|
def s(t):
|
||||||
|
return t
|
||||||
|
|
||||||
|
|
||||||
|
@unit("TIME", r"Time $t$ (us)")
|
||||||
|
def us(t):
|
||||||
|
return t * 1e-6
|
||||||
|
|
||||||
|
|
||||||
|
@us.inverse
|
||||||
|
def us_inv(t):
|
||||||
|
return t * 1e6
|
||||||
|
|
||||||
|
|
||||||
|
@unit("TIME", r"Time $t$ (ns)")
|
||||||
|
def ns(t):
|
||||||
|
return t * 1e-9
|
||||||
|
|
||||||
|
|
||||||
|
@ns.inverse
|
||||||
|
def ns_inv(t):
|
||||||
|
return t * 1e9
|
||||||
|
|
||||||
|
|
||||||
|
@unit("TIME", r"Time $t$ (ps)")
|
||||||
|
def ps(t):
|
||||||
|
return t * 1e-12
|
||||||
|
|
||||||
|
|
||||||
|
@ps.inverse
|
||||||
|
def ps_inv(t):
|
||||||
|
return t * 1e12
|
||||||
|
|
||||||
|
|
||||||
|
@unit("TIME", r"Time $t$ (fs)")
|
||||||
|
def fs(t):
|
||||||
|
return t * 1e-15
|
||||||
|
|
||||||
|
|
||||||
|
@fs.inverse
|
||||||
|
def fs_inv(t):
|
||||||
|
return t * 1e15
|
||||||
|
|
||||||
|
|
||||||
|
@unit("WL", "inverse")
|
||||||
|
def inv(x):
|
||||||
|
return 1 / x
|
||||||
|
|
||||||
|
|
||||||
|
@unit("PRESSURE", "Pressure (bar)")
|
||||||
|
def bar(p):
|
||||||
|
return 1e5 * p
|
||||||
|
|
||||||
|
|
||||||
|
@bar.inverse
|
||||||
|
def bar_inv(p):
|
||||||
|
return p * 1e-5
|
||||||
|
|
||||||
|
|
||||||
|
@unit("PRESSURE", "Pressure (mbar)")
|
||||||
|
def mbar(p):
|
||||||
|
return 1e2 * p
|
||||||
|
|
||||||
|
|
||||||
|
@mbar.inverse
|
||||||
|
def mbar_inv(p):
|
||||||
|
return 1e-2 * p
|
||||||
|
|
||||||
|
|
||||||
|
@unit("OTHER", r"$\beta_2$ (fs$^2$/cm)")
|
||||||
|
def beta2_fs_cm(b2):
|
||||||
|
return 1e-28 * b2
|
||||||
|
|
||||||
|
|
||||||
|
@beta2_fs_cm.inverse
|
||||||
|
def beta2_fs_cm_inv(b2):
|
||||||
|
return 1e28 * b2
|
||||||
|
|
||||||
|
|
||||||
|
@unit("OTHER", r"$\beta_2$ (ps$^2$/km)")
|
||||||
|
def beta2_ps_km(b2):
|
||||||
|
return 1e-27 * b2
|
||||||
|
|
||||||
|
|
||||||
|
@beta2_ps_km.inverse
|
||||||
|
def beta2_ps_km_inv(b2):
|
||||||
|
return 1e27 * b2
|
||||||
|
|
||||||
|
|
||||||
|
@unit("OTHER", r"$D$ (ps/(nm km))")
|
||||||
|
def D_ps_nm_km(D):
|
||||||
|
return 1e-6 * D
|
||||||
|
|
||||||
|
|
||||||
|
@D_ps_nm_km.inverse
|
||||||
|
def D_ps_nm_km_inv(D):
|
||||||
|
return 1e6 * D
|
||||||
|
|
||||||
|
|
||||||
|
@unit("OTHER", r"a.u.")
|
||||||
|
def unity(x):
|
||||||
|
return x
|
||||||
|
|
||||||
|
|
||||||
|
@unit("TEMPERATURE", r"Temperature (K)")
|
||||||
|
def K(t):
|
||||||
|
return t
|
||||||
|
|
||||||
|
|
||||||
|
@unit("TEMPERATURE", r"Temperature (°C)")
|
||||||
|
def C(t_C):
|
||||||
|
return t_C + 272.15
|
||||||
|
|
||||||
|
|
||||||
|
@C.inverse
|
||||||
|
def C_inv(t_K):
|
||||||
|
return t_K - 272.15
|
||||||
|
|
||||||
|
|
||||||
|
@unit("OTHER", r"a.u")
|
||||||
|
def no_unit(x):
|
||||||
|
return x
|
||||||
|
|
||||||
|
|
||||||
|
def nm_rads(nm):
|
||||||
|
return 2e9 * np.pi * c / nm
|
||||||
|
|
||||||
|
|
||||||
|
def nm_hz(nm):
|
||||||
|
return 1e9 * c / nm
|
||||||
|
|
||||||
|
|
||||||
|
def um_rads(um):
|
||||||
|
return 2e6 * np.pi * c / um
|
||||||
|
|
||||||
|
|
||||||
|
def um_hz(um):
|
||||||
|
return 1e6 * c / um
|
||||||
|
|
||||||
|
|
||||||
|
def m_rads(m):
|
||||||
|
return 2 * np.pi * c / m
|
||||||
|
|
||||||
|
|
||||||
|
def m_hz(m):
|
||||||
|
return c / m
|
||||||
|
|
||||||
|
|
||||||
|
def get_unit(unit: Union[str, Callable]) -> Callable[[float], float]:
|
||||||
|
if isinstance(unit, str):
|
||||||
|
return units_map[unit]
|
||||||
|
return unit
|
||||||
|
|
||||||
|
|
||||||
|
def beta2_coef(beta2_coefficients):
|
||||||
|
fac = 1e27
|
||||||
|
out = np.zeros_like(beta2_coefficients)
|
||||||
|
for i, b in enumerate(beta2_coefficients):
|
||||||
|
out[i] = fac * b
|
||||||
|
fac *= 1e12
|
||||||
|
return out
|
||||||
|
|
||||||
|
|
||||||
|
def to_WL(spectrum: np.ndarray, lambda_: np.ndarray) -> np.ndarray:
|
||||||
|
"""
|
||||||
|
rescales the spectrum because of uneven binning when going from freq to wl
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
spectrum : np.ndarray, shape (..., n)
|
||||||
|
intensity spectrum
|
||||||
|
lambda_ : np.ndarray, shape (n, )
|
||||||
|
wavelength in m
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
np.ndarray, shape (n, )
|
||||||
|
intensity spectrum correctly scaled
|
||||||
|
"""
|
||||||
|
m = 2 * pi * c / (lambda_**2) * spectrum
|
||||||
|
return m
|
||||||
|
|
||||||
|
|
||||||
|
def w_from_wl(wl_min_nm: float, wl_max_nm: float, n: int) -> np.ndarray:
|
||||||
|
return np.linspace(nm_rads(wl_max_nm), nm_rads(wl_min_nm), n)
|
||||||
|
|
||||||
|
|
||||||
|
def normalize_wavelengths(wl: np.ndarray) -> np.ndarray:
|
||||||
|
"""attempts to guess the units of wl and return the same array in base SI units (m)"""
|
||||||
|
if np.all((wl > 0.01) & (wl < 20)):
|
||||||
|
return wl * 1e-6
|
||||||
|
elif np.all(wl >= 20):
|
||||||
|
return wl * 1e-9
|
||||||
|
return wl
|
||||||
@@ -29,30 +29,17 @@ MPL_COLORS = [
|
|||||||
key_type = Union[str, int]
|
key_type = Union[str, int]
|
||||||
|
|
||||||
|
|
||||||
class Field(QtWidgets.QWidget):
|
class SliderField(QtWidgets.QWidget):
|
||||||
dtype: Type
|
dtype: Type
|
||||||
value: Any
|
value: Any
|
||||||
value_changed: QtCore.Signal
|
value_changed: QtCore.Signal
|
||||||
timer: QtCore.QTimer
|
|
||||||
|
|
||||||
@property
|
|
||||||
def value(self) -> Any:
|
|
||||||
raise NotImplementedError()
|
|
||||||
|
|
||||||
def values(self) -> list[Any]:
|
|
||||||
raise NotImplementedError()
|
|
||||||
|
|
||||||
|
|
||||||
class SliderField(Field):
|
|
||||||
dtype: Type
|
dtype: Type
|
||||||
possible_values: np.ndarray
|
possible_values: np.ndarray
|
||||||
_slider_max = 100
|
_slider_max = 100
|
||||||
_tuple_signal = QtCore.Signal(tuple)
|
|
||||||
_int_signal = QtCore.Signal(int)
|
_int_signal = QtCore.Signal(int)
|
||||||
_float_signal = QtCore.Signal(float)
|
_float_signal = QtCore.Signal(float)
|
||||||
_str_signal = QtCore.Signal(str)
|
|
||||||
|
|
||||||
def __init__(self, name: str, values: Iterable) -> None:
|
def __init__(self, name: str, values: Iterable[float] | Iterable[int]) -> None:
|
||||||
super().__init__()
|
super().__init__()
|
||||||
self.__value = None
|
self.__value = None
|
||||||
self.slider = QtWidgets.QSlider(QtCore.Qt.Orientation.Horizontal)
|
self.slider = QtWidgets.QSlider(QtCore.Qt.Orientation.Horizontal)
|
||||||
@@ -64,16 +51,18 @@ class SliderField(Field):
|
|||||||
self.field.editingFinished.connect(self.field_changed)
|
self.field.editingFinished.connect(self.field_changed)
|
||||||
|
|
||||||
self.step_backward_button = QtWidgets.QPushButton("<")
|
self.step_backward_button = QtWidgets.QPushButton("<")
|
||||||
|
self.step_backward_button.setFixedWidth(30)
|
||||||
self.step_backward_button.clicked.connect(self.step_backward)
|
self.step_backward_button.clicked.connect(self.step_backward)
|
||||||
|
|
||||||
self.step_forward_button = QtWidgets.QPushButton(">")
|
self.step_forward_button = QtWidgets.QPushButton(">")
|
||||||
|
self.step_forward_button.setFixedWidth(30)
|
||||||
self.step_forward_button.clicked.connect(self.step_forward)
|
self.step_forward_button.clicked.connect(self.step_forward)
|
||||||
|
|
||||||
self._layout = QtWidgets.QHBoxLayout()
|
self._layout = QtWidgets.QHBoxLayout()
|
||||||
self.setLayout(self._layout)
|
self.setLayout(self._layout)
|
||||||
self._layout.setContentsMargins(10, 0, 10, 0)
|
self._layout.setContentsMargins(10, 0, 10, 0)
|
||||||
|
|
||||||
pretty_name = " ".join(s.title() for s in name.split("_"))
|
pretty_name = " ".join(s for s in name.split("_"))
|
||||||
self.name_label = QtWidgets.QLabel(pretty_name + " :")
|
self.name_label = QtWidgets.QLabel(pretty_name + " :")
|
||||||
|
|
||||||
self._layout.addWidget(self.name_label)
|
self._layout.addWidget(self.name_label)
|
||||||
@@ -86,13 +75,13 @@ class SliderField(Field):
|
|||||||
self.value_changed = {
|
self.value_changed = {
|
||||||
int: self._int_signal,
|
int: self._int_signal,
|
||||||
float: self._float_signal,
|
float: self._float_signal,
|
||||||
str: self._str_signal,
|
|
||||||
tuple: self._tuple_signal,
|
|
||||||
}[self.dtype]
|
}[self.dtype]
|
||||||
self.value_changed.emit(self.__value)
|
self.value_changed.emit(self.__value)
|
||||||
|
|
||||||
def set_values(self, values: Iterable):
|
def set_values(self, values: Iterable):
|
||||||
self.possible_values = np.array(values)
|
self.possible_values = (
|
||||||
|
np.array(values) if not isinstance(values, np.ndarray) else values.copy()
|
||||||
|
)
|
||||||
self.value_to_slider_map = {v: i for i, v in enumerate(self.possible_values)}
|
self.value_to_slider_map = {v: i for i, v in enumerate(self.possible_values)}
|
||||||
self._slider_max = len(self.possible_values) - 1
|
self._slider_max = len(self.possible_values) - 1
|
||||||
self.slider.setRange(0, self._slider_max)
|
self.slider.setRange(0, self._slider_max)
|
||||||
@@ -115,7 +104,7 @@ class SliderField(Field):
|
|||||||
self.update_slider()
|
self.update_slider()
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def value(self) -> float:
|
def value(self) -> float | int:
|
||||||
return self.__value
|
return self.__value
|
||||||
|
|
||||||
@value.setter
|
@value.setter
|
||||||
@@ -130,11 +119,8 @@ class SliderField(Field):
|
|||||||
self.value_changed.emit(new_value)
|
self.value_changed.emit(new_value)
|
||||||
|
|
||||||
def field_changed(self):
|
def field_changed(self):
|
||||||
try:
|
|
||||||
new_val = self.dtype(self.field.text())
|
new_val = self.dtype(self.field.text())
|
||||||
except (ValueError, TypeError):
|
new_val = min(self.value_to_slider_map, key=lambda el: abs(el - new_val))
|
||||||
self.update_label()
|
|
||||||
return
|
|
||||||
self.value = new_val
|
self.value = new_val
|
||||||
|
|
||||||
def slider_changed(self):
|
def slider_changed(self):
|
||||||
@@ -168,7 +154,7 @@ class SliderField(Field):
|
|||||||
if self.dtype is int:
|
if self.dtype is int:
|
||||||
return format(self.value)
|
return format(self.value)
|
||||||
elif self.dtype is float:
|
elif self.dtype is float:
|
||||||
return format(self.value, ".3g")
|
return format(self.value, ".5g")
|
||||||
else:
|
else:
|
||||||
return format(self.value)
|
return format(self.value)
|
||||||
|
|
||||||
@@ -176,66 +162,6 @@ class SliderField(Field):
|
|||||||
return list(self.possible_values)
|
return list(self.possible_values)
|
||||||
|
|
||||||
|
|
||||||
class AnimatedSliderField(SliderField):
|
|
||||||
def __init__(self, name: str, values: Iterable) -> None:
|
|
||||||
super().__init__(name, values)
|
|
||||||
self.timer = QtCore.QTimer()
|
|
||||||
self.timer.timeout.connect(self.step_forward)
|
|
||||||
|
|
||||||
self.play_button = QtWidgets.QPushButton("⏯")
|
|
||||||
self.play_button.clicked.connect(self.toggle)
|
|
||||||
self.play_button.setMaximumWidth(30)
|
|
||||||
self.playing = False
|
|
||||||
|
|
||||||
self.interval_field = QtWidgets.QLineEdit()
|
|
||||||
self.interval_field.setMaximumWidth(60)
|
|
||||||
# self.interval_field.setValidator(QtGui.QIntValidator(1, 5000))
|
|
||||||
self.interval_field.editingFinished.connect(self.set_interval)
|
|
||||||
self.interval_field.inputRejected.connect(self.set_interval)
|
|
||||||
self.interval = 16
|
|
||||||
self.set_interval()
|
|
||||||
|
|
||||||
self._layout.addWidget(self.play_button)
|
|
||||||
self._layout.addWidget(self.interval_field)
|
|
||||||
|
|
||||||
def toggle(self):
|
|
||||||
if self.playing:
|
|
||||||
self.stop()
|
|
||||||
self.playing = False
|
|
||||||
else:
|
|
||||||
self.play()
|
|
||||||
self.playing = True
|
|
||||||
|
|
||||||
def play(self):
|
|
||||||
if self.slider.value() == self._slider_max:
|
|
||||||
self.slider.setValue(0)
|
|
||||||
self.timer.start(self.interval)
|
|
||||||
self.play_button.setStyleSheet("QPushButton {background-color: #DEF2DD;}")
|
|
||||||
|
|
||||||
def stop(self):
|
|
||||||
self.timer.stop()
|
|
||||||
self.play_button.setStyleSheet("QPushButton {background-color: none;}")
|
|
||||||
|
|
||||||
def set_interval(self):
|
|
||||||
try:
|
|
||||||
self.interval = max(1, int(self.interval_field.text()))
|
|
||||||
except ValueError:
|
|
||||||
self.interval_field.setText(str(self.interval))
|
|
||||||
if self.interval < 16:
|
|
||||||
self.increment = int(np.ceil(16 / self.interval))
|
|
||||||
self.interval *= self.increment
|
|
||||||
else:
|
|
||||||
self.increment = 1
|
|
||||||
|
|
||||||
def step_forward(self):
|
|
||||||
current = self.slider.value()
|
|
||||||
if current + self.increment <= self._slider_max:
|
|
||||||
self.slider.setValue(current + self.increment)
|
|
||||||
else:
|
|
||||||
self.slider.setValue(self._slider_max)
|
|
||||||
self.stop()
|
|
||||||
|
|
||||||
|
|
||||||
class Plot:
|
class Plot:
|
||||||
name: str
|
name: str
|
||||||
dock: Dock
|
dock: Dock
|
||||||
@@ -511,11 +437,12 @@ class PlotApp:
|
|||||||
self.params_widget = QtWidgets.QWidget()
|
self.params_widget = QtWidgets.QWidget()
|
||||||
self.header_widget = QtWidgets.QWidget()
|
self.header_widget = QtWidgets.QWidget()
|
||||||
self.info_label = QtWidgets.QLabel()
|
self.info_label = QtWidgets.QLabel()
|
||||||
|
# self.info_label.setMaximumWidth(120)
|
||||||
self.window.setCentralWidget(self.central_widget)
|
self.window.setCentralWidget(self.central_widget)
|
||||||
|
|
||||||
self.central_layout = QtWidgets.QVBoxLayout()
|
self.central_layout = QtWidgets.QVBoxLayout()
|
||||||
self.params_layout = QtWidgets.QVBoxLayout()
|
self.params_layout = QtWidgets.QGridLayout()
|
||||||
self.header_layout = QtWidgets.QHBoxLayout()
|
self.header_layout = QtWidgets.QVBoxLayout()
|
||||||
|
|
||||||
_pl = QtWidgets.QSizePolicy.Policy.Preferred
|
_pl = QtWidgets.QSizePolicy.Policy.Preferred
|
||||||
info_sp = QtWidgets.QSizePolicy(_pl, _pl)
|
info_sp = QtWidgets.QSizePolicy(_pl, _pl)
|
||||||
@@ -540,10 +467,10 @@ class PlotApp:
|
|||||||
|
|
||||||
self.__ran = False
|
self.__ran = False
|
||||||
self.params = {}
|
self.params = {}
|
||||||
for p_name, values in params.items():
|
for i, (p_name, values) in enumerate(params.items()):
|
||||||
field = AnimatedSliderField(p_name, values)
|
field = SliderField(p_name, values)
|
||||||
self.params[p_name] = field
|
self.params[p_name] = field
|
||||||
self.params_layout.addWidget(field)
|
self.params_layout.addWidget(field, *divmod(i, 2))
|
||||||
|
|
||||||
def set_antialiasing(self, val: bool):
|
def set_antialiasing(self, val: bool):
|
||||||
pg.setConfigOptions(antialias=val)
|
pg.setConfigOptions(antialias=val)
|
||||||
@@ -562,7 +489,7 @@ class PlotApp:
|
|||||||
opts = dict(zip(["v_min", "v_max", "v_num", "v_init"], opts))
|
opts = dict(zip(["v_min", "v_max", "v_num", "v_init"], opts))
|
||||||
yield p_name, dtype, opts
|
yield p_name, dtype, opts
|
||||||
|
|
||||||
def update(self, *p_names: str):
|
def update(self, first_param: str | Callable, *p_names: str):
|
||||||
"""
|
"""
|
||||||
use this as a decorator to connect the decorated function to
|
use this as a decorator to connect the decorated function to
|
||||||
the value_changed signal of some parameters
|
the value_changed signal of some parameters
|
||||||
@@ -595,8 +522,12 @@ class PlotApp:
|
|||||||
changes and is given its new value as argument
|
changes and is given its new value as argument
|
||||||
"""
|
"""
|
||||||
|
|
||||||
if len(p_names) == 1 and callable(p_names[0]):
|
if len(p_names) == 0 and callable(first_param) and not isinstance(first_param, str):
|
||||||
return self.update(*self._get_func_args(p_names[0]))(p_names[0])
|
return self.update(*self._get_func_args(first_param))(first_param)
|
||||||
|
elif not isinstance(first_param, str):
|
||||||
|
raise TypeError()
|
||||||
|
|
||||||
|
p_names = (first_param, *p_names)
|
||||||
|
|
||||||
def wrapper(func):
|
def wrapper(func):
|
||||||
def to_call(v=None):
|
def to_call(v=None):
|
||||||
@@ -724,12 +655,10 @@ class PlotApp:
|
|||||||
self.app.exec()
|
self.app.exec()
|
||||||
|
|
||||||
@overload
|
@overload
|
||||||
def __getitem__(self, key: tuple[key_type, key_type]) -> PlotDataItem:
|
def __getitem__(self, key: tuple[key_type, key_type]) -> PlotDataItem: ...
|
||||||
...
|
|
||||||
|
|
||||||
@overload
|
@overload
|
||||||
def __getitem__(self, key: key_type) -> Plot:
|
def __getitem__(self, key: key_type) -> Plot: ...
|
||||||
...
|
|
||||||
|
|
||||||
def __getitem__(self, key: key_type) -> Plot:
|
def __getitem__(self, key: key_type) -> Plot:
|
||||||
if isinstance(key, tuple):
|
if isinstance(key, tuple):
|
||||||
|
|||||||
704
uv.lock
generated
Normal file
704
uv.lock
generated
Normal file
@@ -0,0 +1,704 @@
|
|||||||
|
version = 1
|
||||||
|
revision = 3
|
||||||
|
requires-python = ">=3.13"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "annotated-types"
|
||||||
|
version = "0.7.0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/ee/67/531ea369ba64dcff5ec9c3402f9f51bf748cec26dde048a2f973a4eea7f5/annotated_types-0.7.0.tar.gz", hash = "sha256:aff07c09a53a08bc8cfccb9c85b05f1aa9a2a6f23728d790723543408344ce89", size = 16081, upload-time = "2024-05-20T21:33:25.928Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/78/b6/6307fbef88d9b5ee7421e68d78a9f162e0da4900bc5f5793f6d3d0e34fb8/annotated_types-0.7.0-py3-none-any.whl", hash = "sha256:1f02e8b43a8fbbc3f3e0d4f0f4bfc8131bcb4eebe8849b8e5c773f3a1c582a53", size = 13643, upload-time = "2024-05-20T21:33:24.1Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "click"
|
||||||
|
version = "8.3.1"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "colorama", marker = "sys_platform == 'win32'" },
|
||||||
|
]
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/3d/fa/656b739db8587d7b5dfa22e22ed02566950fbfbcdc20311993483657a5c0/click-8.3.1.tar.gz", hash = "sha256:12ff4785d337a1bb490bb7e9c2b1ee5da3112e94a8622f26a6c77f5d2fc6842a", size = 295065, upload-time = "2025-11-15T20:45:42.706Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/98/78/01c019cdb5d6498122777c1a43056ebb3ebfeef2076d9d026bfe15583b2b/click-8.3.1-py3-none-any.whl", hash = "sha256:981153a64e25f12d547d3426c367a4857371575ee7ad18df2a6183ab0545b2a6", size = 108274, upload-time = "2025-11-15T20:45:41.139Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "colorama"
|
||||||
|
version = "0.4.6"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/d8/53/6f443c9a4a8358a93a6792e2acffb9d9d5cb0a5cfd8802644b7b1c9a02e4/colorama-0.4.6.tar.gz", hash = "sha256:08695f5cb7ed6e0531a20572697297273c47b8cae5a63ffc6d6ed5c201be6e44", size = 27697, upload-time = "2022-10-25T02:36:22.414Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/d1/d6/3965ed04c63042e047cb6a3e6ed1a63a35087b6a609aa3a15ed8ac56c221/colorama-0.4.6-py2.py3-none-any.whl", hash = "sha256:4f1d9991f5acc0ca119f9d443620b77f9d6b33703e51011c16baf57afb285fc6", size = 25335, upload-time = "2022-10-25T02:36:20.889Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "contourpy"
|
||||||
|
version = "1.3.3"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "numpy" },
|
||||||
|
]
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/58/01/1253e6698a07380cd31a736d248a3f2a50a7c88779a1813da27503cadc2a/contourpy-1.3.3.tar.gz", hash = "sha256:083e12155b210502d0bca491432bb04d56dc3432f95a979b429f2848c3dbe880", size = 13466174, upload-time = "2025-07-26T12:03:12.549Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/68/35/0167aad910bbdb9599272bd96d01a9ec6852f36b9455cf2ca67bd4cc2d23/contourpy-1.3.3-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:177fb367556747a686509d6fef71d221a4b198a3905fe824430e5ea0fda54eb5", size = 293257, upload-time = "2025-07-26T12:01:39.367Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/96/e4/7adcd9c8362745b2210728f209bfbcf7d91ba868a2c5f40d8b58f54c509b/contourpy-1.3.3-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:d002b6f00d73d69333dac9d0b8d5e84d9724ff9ef044fd63c5986e62b7c9e1b1", size = 274034, upload-time = "2025-07-26T12:01:40.645Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/73/23/90e31ceeed1de63058a02cb04b12f2de4b40e3bef5e082a7c18d9c8ae281/contourpy-1.3.3-cp313-cp313-manylinux_2_26_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:348ac1f5d4f1d66d3322420f01d42e43122f43616e0f194fc1c9f5d830c5b286", size = 334672, upload-time = "2025-07-26T12:01:41.942Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ed/93/b43d8acbe67392e659e1d984700e79eb67e2acb2bd7f62012b583a7f1b55/contourpy-1.3.3-cp313-cp313-manylinux_2_26_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:655456777ff65c2c548b7c454af9c6f33f16c8884f11083244b5819cc214f1b5", size = 381234, upload-time = "2025-07-26T12:01:43.499Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/46/3b/bec82a3ea06f66711520f75a40c8fc0b113b2a75edb36aa633eb11c4f50f/contourpy-1.3.3-cp313-cp313-manylinux_2_26_s390x.manylinux_2_28_s390x.whl", hash = "sha256:644a6853d15b2512d67881586bd03f462c7ab755db95f16f14d7e238f2852c67", size = 385169, upload-time = "2025-07-26T12:01:45.219Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/4b/32/e0f13a1c5b0f8572d0ec6ae2f6c677b7991fafd95da523159c19eff0696a/contourpy-1.3.3-cp313-cp313-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:4debd64f124ca62069f313a9cb86656ff087786016d76927ae2cf37846b006c9", size = 362859, upload-time = "2025-07-26T12:01:46.519Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/33/71/e2a7945b7de4e58af42d708a219f3b2f4cff7386e6b6ab0a0fa0033c49a9/contourpy-1.3.3-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:a15459b0f4615b00bbd1e91f1b9e19b7e63aea7483d03d804186f278c0af2659", size = 1332062, upload-time = "2025-07-26T12:01:48.964Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/12/fc/4e87ac754220ccc0e807284f88e943d6d43b43843614f0a8afa469801db0/contourpy-1.3.3-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:ca0fdcd73925568ca027e0b17ab07aad764be4706d0a925b89227e447d9737b7", size = 1403932, upload-time = "2025-07-26T12:01:51.979Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/a6/2e/adc197a37443f934594112222ac1aa7dc9a98faf9c3842884df9a9d8751d/contourpy-1.3.3-cp313-cp313-win32.whl", hash = "sha256:b20c7c9a3bf701366556e1b1984ed2d0cedf999903c51311417cf5f591d8c78d", size = 185024, upload-time = "2025-07-26T12:01:53.245Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/18/0b/0098c214843213759692cc638fce7de5c289200a830e5035d1791d7a2338/contourpy-1.3.3-cp313-cp313-win_amd64.whl", hash = "sha256:1cadd8b8969f060ba45ed7c1b714fe69185812ab43bd6b86a9123fe8f99c3263", size = 226578, upload-time = "2025-07-26T12:01:54.422Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/8a/9a/2f6024a0c5995243cd63afdeb3651c984f0d2bc727fd98066d40e141ad73/contourpy-1.3.3-cp313-cp313-win_arm64.whl", hash = "sha256:fd914713266421b7536de2bfa8181aa8c699432b6763a0ea64195ebe28bff6a9", size = 193524, upload-time = "2025-07-26T12:01:55.73Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/c0/b3/f8a1a86bd3298513f500e5b1f5fd92b69896449f6cab6a146a5d52715479/contourpy-1.3.3-cp313-cp313t-macosx_10_13_x86_64.whl", hash = "sha256:88df9880d507169449d434c293467418b9f6cbe82edd19284aa0409e7fdb933d", size = 306730, upload-time = "2025-07-26T12:01:57.051Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/3f/11/4780db94ae62fc0c2053909b65dc3246bd7cecfc4f8a20d957ad43aa4ad8/contourpy-1.3.3-cp313-cp313t-macosx_11_0_arm64.whl", hash = "sha256:d06bb1f751ba5d417047db62bca3c8fde202b8c11fb50742ab3ab962c81e8216", size = 287897, upload-time = "2025-07-26T12:01:58.663Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ae/15/e59f5f3ffdd6f3d4daa3e47114c53daabcb18574a26c21f03dc9e4e42ff0/contourpy-1.3.3-cp313-cp313t-manylinux_2_26_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:e4e6b05a45525357e382909a4c1600444e2a45b4795163d3b22669285591c1ae", size = 326751, upload-time = "2025-07-26T12:02:00.343Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/0f/81/03b45cfad088e4770b1dcf72ea78d3802d04200009fb364d18a493857210/contourpy-1.3.3-cp313-cp313t-manylinux_2_26_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:ab3074b48c4e2cf1a960e6bbeb7f04566bf36b1861d5c9d4d8ac04b82e38ba20", size = 375486, upload-time = "2025-07-26T12:02:02.128Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/0c/ba/49923366492ffbdd4486e970d421b289a670ae8cf539c1ea9a09822b371a/contourpy-1.3.3-cp313-cp313t-manylinux_2_26_s390x.manylinux_2_28_s390x.whl", hash = "sha256:6c3d53c796f8647d6deb1abe867daeb66dcc8a97e8455efa729516b997b8ed99", size = 388106, upload-time = "2025-07-26T12:02:03.615Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/9f/52/5b00ea89525f8f143651f9f03a0df371d3cbd2fccd21ca9b768c7a6500c2/contourpy-1.3.3-cp313-cp313t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:50ed930df7289ff2a8d7afeb9603f8289e5704755c7e5c3bbd929c90c817164b", size = 352548, upload-time = "2025-07-26T12:02:05.165Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/32/1d/a209ec1a3a3452d490f6b14dd92e72280c99ae3d1e73da74f8277d4ee08f/contourpy-1.3.3-cp313-cp313t-musllinux_1_2_aarch64.whl", hash = "sha256:4feffb6537d64b84877da813a5c30f1422ea5739566abf0bd18065ac040e120a", size = 1322297, upload-time = "2025-07-26T12:02:07.379Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/bc/9e/46f0e8ebdd884ca0e8877e46a3f4e633f6c9c8c4f3f6e72be3fe075994aa/contourpy-1.3.3-cp313-cp313t-musllinux_1_2_x86_64.whl", hash = "sha256:2b7e9480ffe2b0cd2e787e4df64270e3a0440d9db8dc823312e2c940c167df7e", size = 1391023, upload-time = "2025-07-26T12:02:10.171Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b9/70/f308384a3ae9cd2209e0849f33c913f658d3326900d0ff5d378d6a1422d2/contourpy-1.3.3-cp313-cp313t-win32.whl", hash = "sha256:283edd842a01e3dcd435b1c5116798d661378d83d36d337b8dde1d16a5fc9ba3", size = 196157, upload-time = "2025-07-26T12:02:11.488Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b2/dd/880f890a6663b84d9e34a6f88cded89d78f0091e0045a284427cb6b18521/contourpy-1.3.3-cp313-cp313t-win_amd64.whl", hash = "sha256:87acf5963fc2b34825e5b6b048f40e3635dd547f590b04d2ab317c2619ef7ae8", size = 240570, upload-time = "2025-07-26T12:02:12.754Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/80/99/2adc7d8ffead633234817ef8e9a87115c8a11927a94478f6bb3d3f4d4f7d/contourpy-1.3.3-cp313-cp313t-win_arm64.whl", hash = "sha256:3c30273eb2a55024ff31ba7d052dde990d7d8e5450f4bbb6e913558b3d6c2301", size = 199713, upload-time = "2025-07-26T12:02:14.4Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/72/8b/4546f3ab60f78c514ffb7d01a0bd743f90de36f0019d1be84d0a708a580a/contourpy-1.3.3-cp314-cp314-macosx_10_13_x86_64.whl", hash = "sha256:fde6c716d51c04b1c25d0b90364d0be954624a0ee9d60e23e850e8d48353d07a", size = 292189, upload-time = "2025-07-26T12:02:16.095Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fd/e1/3542a9cb596cadd76fcef413f19c79216e002623158befe6daa03dbfa88c/contourpy-1.3.3-cp314-cp314-macosx_11_0_arm64.whl", hash = "sha256:cbedb772ed74ff5be440fa8eee9bd49f64f6e3fc09436d9c7d8f1c287b121d77", size = 273251, upload-time = "2025-07-26T12:02:17.524Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b1/71/f93e1e9471d189f79d0ce2497007731c1e6bf9ef6d1d61b911430c3db4e5/contourpy-1.3.3-cp314-cp314-manylinux_2_26_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:22e9b1bd7a9b1d652cd77388465dc358dafcd2e217d35552424aa4f996f524f5", size = 335810, upload-time = "2025-07-26T12:02:18.9Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/91/f9/e35f4c1c93f9275d4e38681a80506b5510e9327350c51f8d4a5a724d178c/contourpy-1.3.3-cp314-cp314-manylinux_2_26_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:a22738912262aa3e254e4f3cb079a95a67132fc5a063890e224393596902f5a4", size = 382871, upload-time = "2025-07-26T12:02:20.418Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b5/71/47b512f936f66a0a900d81c396a7e60d73419868fba959c61efed7a8ab46/contourpy-1.3.3-cp314-cp314-manylinux_2_26_s390x.manylinux_2_28_s390x.whl", hash = "sha256:afe5a512f31ee6bd7d0dda52ec9864c984ca3d66664444f2d72e0dc4eb832e36", size = 386264, upload-time = "2025-07-26T12:02:21.916Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/04/5f/9ff93450ba96b09c7c2b3f81c94de31c89f92292f1380261bd7195bea4ea/contourpy-1.3.3-cp314-cp314-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:f64836de09927cba6f79dcd00fdd7d5329f3fccc633468507079c829ca4db4e3", size = 363819, upload-time = "2025-07-26T12:02:23.759Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/3e/a6/0b185d4cc480ee494945cde102cb0149ae830b5fa17bf855b95f2e70ad13/contourpy-1.3.3-cp314-cp314-musllinux_1_2_aarch64.whl", hash = "sha256:1fd43c3be4c8e5fd6e4f2baeae35ae18176cf2e5cced681cca908addf1cdd53b", size = 1333650, upload-time = "2025-07-26T12:02:26.181Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/43/d7/afdc95580ca56f30fbcd3060250f66cedbde69b4547028863abd8aa3b47e/contourpy-1.3.3-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:6afc576f7b33cf00996e5c1102dc2a8f7cc89e39c0b55df93a0b78c1bd992b36", size = 1404833, upload-time = "2025-07-26T12:02:28.782Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e2/e2/366af18a6d386f41132a48f033cbd2102e9b0cf6345d35ff0826cd984566/contourpy-1.3.3-cp314-cp314-win32.whl", hash = "sha256:66c8a43a4f7b8df8b71ee1840e4211a3c8d93b214b213f590e18a1beca458f7d", size = 189692, upload-time = "2025-07-26T12:02:30.128Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/7d/c2/57f54b03d0f22d4044b8afb9ca0e184f8b1afd57b4f735c2fa70883dc601/contourpy-1.3.3-cp314-cp314-win_amd64.whl", hash = "sha256:cf9022ef053f2694e31d630feaacb21ea24224be1c3ad0520b13d844274614fd", size = 232424, upload-time = "2025-07-26T12:02:31.395Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/18/79/a9416650df9b525737ab521aa181ccc42d56016d2123ddcb7b58e926a42c/contourpy-1.3.3-cp314-cp314-win_arm64.whl", hash = "sha256:95b181891b4c71de4bb404c6621e7e2390745f887f2a026b2d99e92c17892339", size = 198300, upload-time = "2025-07-26T12:02:32.956Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/1f/42/38c159a7d0f2b7b9c04c64ab317042bb6952b713ba875c1681529a2932fe/contourpy-1.3.3-cp314-cp314t-macosx_10_13_x86_64.whl", hash = "sha256:33c82d0138c0a062380332c861387650c82e4cf1747aaa6938b9b6516762e772", size = 306769, upload-time = "2025-07-26T12:02:34.2Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/c3/6c/26a8205f24bca10974e77460de68d3d7c63e282e23782f1239f226fcae6f/contourpy-1.3.3-cp314-cp314t-macosx_11_0_arm64.whl", hash = "sha256:ea37e7b45949df430fe649e5de8351c423430046a2af20b1c1961cae3afcda77", size = 287892, upload-time = "2025-07-26T12:02:35.807Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/66/06/8a475c8ab718ebfd7925661747dbb3c3ee9c82ac834ccb3570be49d129f4/contourpy-1.3.3-cp314-cp314t-manylinux_2_26_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:d304906ecc71672e9c89e87c4675dc5c2645e1f4269a5063b99b0bb29f232d13", size = 326748, upload-time = "2025-07-26T12:02:37.193Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b4/a3/c5ca9f010a44c223f098fccd8b158bb1cb287378a31ac141f04730dc49be/contourpy-1.3.3-cp314-cp314t-manylinux_2_26_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:ca658cd1a680a5c9ea96dc61cdbae1e85c8f25849843aa799dfd3cb370ad4fbe", size = 375554, upload-time = "2025-07-26T12:02:38.894Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/80/5b/68bd33ae63fac658a4145088c1e894405e07584a316738710b636c6d0333/contourpy-1.3.3-cp314-cp314t-manylinux_2_26_s390x.manylinux_2_28_s390x.whl", hash = "sha256:ab2fd90904c503739a75b7c8c5c01160130ba67944a7b77bbf36ef8054576e7f", size = 388118, upload-time = "2025-07-26T12:02:40.642Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/40/52/4c285a6435940ae25d7410a6c36bda5145839bc3f0beb20c707cda18b9d2/contourpy-1.3.3-cp314-cp314t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:b7301b89040075c30e5768810bc96a8e8d78085b47d8be6e4c3f5a0b4ed478a0", size = 352555, upload-time = "2025-07-26T12:02:42.25Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/24/ee/3e81e1dd174f5c7fefe50e85d0892de05ca4e26ef1c9a59c2a57e43b865a/contourpy-1.3.3-cp314-cp314t-musllinux_1_2_aarch64.whl", hash = "sha256:2a2a8b627d5cc6b7c41a4beff6c5ad5eb848c88255fda4a8745f7e901b32d8e4", size = 1322295, upload-time = "2025-07-26T12:02:44.668Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/3c/b2/6d913d4d04e14379de429057cd169e5e00f6c2af3bb13e1710bcbdb5da12/contourpy-1.3.3-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:fd6ec6be509c787f1caf6b247f0b1ca598bef13f4ddeaa126b7658215529ba0f", size = 1391027, upload-time = "2025-07-26T12:02:47.09Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/93/8a/68a4ec5c55a2971213d29a9374913f7e9f18581945a7a31d1a39b5d2dfe5/contourpy-1.3.3-cp314-cp314t-win32.whl", hash = "sha256:e74a9a0f5e3fff48fb5a7f2fd2b9b70a3fe014a67522f79b7cca4c0c7e43c9ae", size = 202428, upload-time = "2025-07-26T12:02:48.691Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fa/96/fd9f641ffedc4fa3ace923af73b9d07e869496c9cc7a459103e6e978992f/contourpy-1.3.3-cp314-cp314t-win_amd64.whl", hash = "sha256:13b68d6a62db8eafaebb8039218921399baf6e47bf85006fd8529f2a08ef33fc", size = 250331, upload-time = "2025-07-26T12:02:50.137Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ae/8c/469afb6465b853afff216f9528ffda78a915ff880ed58813ba4faf4ba0b6/contourpy-1.3.3-cp314-cp314t-win_arm64.whl", hash = "sha256:b7448cb5a725bb1e35ce88771b86fba35ef418952474492cf7c764059933ff8b", size = 203831, upload-time = "2025-07-26T12:02:51.449Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "cycler"
|
||||||
|
version = "0.12.1"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/a9/95/a3dbbb5028f35eafb79008e7522a75244477d2838f38cbb722248dabc2a8/cycler-0.12.1.tar.gz", hash = "sha256:88bb128f02ba341da8ef447245a9e138fae777f6a23943da4540077d3601eb1c", size = 7615, upload-time = "2023-10-07T05:32:18.335Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e7/05/c19819d5e3d95294a6f5947fb9b9629efb316b96de511b418c53d245aae6/cycler-0.12.1-py3-none-any.whl", hash = "sha256:85cef7cff222d8644161529808465972e51340599459b8ac3ccbac5a854e0d30", size = 8321, upload-time = "2023-10-07T05:32:16.783Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "dispersionapp"
|
||||||
|
version = "0.2.2"
|
||||||
|
source = { editable = "." }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "click" },
|
||||||
|
{ name = "numba" },
|
||||||
|
{ name = "pydantic" },
|
||||||
|
{ name = "pyqtgraph" },
|
||||||
|
{ name = "pyside6" },
|
||||||
|
{ name = "scipy" },
|
||||||
|
{ name = "tomli" },
|
||||||
|
{ name = "tomli-w" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[package.dev-dependencies]
|
||||||
|
dev = [
|
||||||
|
{ name = "matplotlib" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[package.metadata]
|
||||||
|
requires-dist = [
|
||||||
|
{ name = "click" },
|
||||||
|
{ name = "numba", specifier = ">=0.62.1" },
|
||||||
|
{ name = "pydantic", specifier = ">=2" },
|
||||||
|
{ name = "pyqtgraph", specifier = ">=0.13.1" },
|
||||||
|
{ name = "pyside6", specifier = ">=6.4.0" },
|
||||||
|
{ name = "scipy", specifier = ">=1.16.3" },
|
||||||
|
{ name = "tomli" },
|
||||||
|
{ name = "tomli-w" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[package.metadata.requires-dev]
|
||||||
|
dev = [{ name = "matplotlib", specifier = ">=3.10.7" }]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "fonttools"
|
||||||
|
version = "4.60.1"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/4b/42/97a13e47a1e51a5a7142475bbcf5107fe3a68fc34aef331c897d5fb98ad0/fonttools-4.60.1.tar.gz", hash = "sha256:ef00af0439ebfee806b25f24c8f92109157ff3fac5731dc7867957812e87b8d9", size = 3559823, upload-time = "2025-09-29T21:13:27.129Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/7c/5b/cdd2c612277b7ac7ec8c0c9bc41812c43dc7b2d5f2b0897e15fdf5a1f915/fonttools-4.60.1-cp313-cp313-macosx_10_13_universal2.whl", hash = "sha256:6f68576bb4bbf6060c7ab047b1574a1ebe5c50a17de62830079967b211059ebb", size = 2825777, upload-time = "2025-09-29T21:12:01.22Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/d6/8a/de9cc0540f542963ba5e8f3a1f6ad48fa211badc3177783b9d5cadf79b5d/fonttools-4.60.1-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:eedacb5c5d22b7097482fa834bda0dafa3d914a4e829ec83cdea2a01f8c813c4", size = 2348080, upload-time = "2025-09-29T21:12:03.785Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/2d/8b/371ab3cec97ee3fe1126b3406b7abd60c8fec8975fd79a3c75cdea0c3d83/fonttools-4.60.1-cp313-cp313-manylinux1_x86_64.manylinux2014_x86_64.manylinux_2_17_x86_64.manylinux_2_5_x86_64.whl", hash = "sha256:b33a7884fabd72bdf5f910d0cf46be50dce86a0362a65cfc746a4168c67eb96c", size = 4903082, upload-time = "2025-09-29T21:12:06.382Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/04/05/06b1455e4bc653fcb2117ac3ef5fa3a8a14919b93c60742d04440605d058/fonttools-4.60.1-cp313-cp313-manylinux2014_aarch64.manylinux_2_17_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:2409d5fb7b55fd70f715e6d34e7a6e4f7511b8ad29a49d6df225ee76da76dd77", size = 4960125, upload-time = "2025-09-29T21:12:09.314Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/8e/37/f3b840fcb2666f6cb97038793606bdd83488dca2d0b0fc542ccc20afa668/fonttools-4.60.1-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:c8651e0d4b3bdeda6602b85fdc2abbefc1b41e573ecb37b6779c4ca50753a199", size = 4901454, upload-time = "2025-09-29T21:12:11.931Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fd/9e/eb76f77e82f8d4a46420aadff12cec6237751b0fb9ef1de373186dcffb5f/fonttools-4.60.1-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:145daa14bf24824b677b9357c5e44fd8895c2a8f53596e1b9ea3496081dc692c", size = 5044495, upload-time = "2025-09-29T21:12:15.241Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/f8/b3/cede8f8235d42ff7ae891bae8d619d02c8ac9fd0cfc450c5927a6200c70d/fonttools-4.60.1-cp313-cp313-win32.whl", hash = "sha256:2299df884c11162617a66b7c316957d74a18e3758c0274762d2cc87df7bc0272", size = 2217028, upload-time = "2025-09-29T21:12:17.96Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/75/4d/b022c1577807ce8b31ffe055306ec13a866f2337ecee96e75b24b9b753ea/fonttools-4.60.1-cp313-cp313-win_amd64.whl", hash = "sha256:a3db56f153bd4c5c2b619ab02c5db5192e222150ce5a1bc10f16164714bc39ac", size = 2266200, upload-time = "2025-09-29T21:12:20.14Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/9a/83/752ca11c1aa9a899b793a130f2e466b79ea0cf7279c8d79c178fc954a07b/fonttools-4.60.1-cp314-cp314-macosx_10_13_universal2.whl", hash = "sha256:a884aef09d45ba1206712c7dbda5829562d3fea7726935d3289d343232ecb0d3", size = 2822830, upload-time = "2025-09-29T21:12:24.406Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/57/17/bbeab391100331950a96ce55cfbbff27d781c1b85ebafb4167eae50d9fe3/fonttools-4.60.1-cp314-cp314-macosx_10_13_x86_64.whl", hash = "sha256:8a44788d9d91df72d1a5eac49b31aeb887a5f4aab761b4cffc4196c74907ea85", size = 2345524, upload-time = "2025-09-29T21:12:26.819Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/3d/2e/d4831caa96d85a84dd0da1d9f90d81cec081f551e0ea216df684092c6c97/fonttools-4.60.1-cp314-cp314-manylinux1_x86_64.manylinux2014_x86_64.manylinux_2_17_x86_64.manylinux_2_5_x86_64.whl", hash = "sha256:e852d9dda9f93ad3651ae1e3bb770eac544ec93c3807888798eccddf84596537", size = 4843490, upload-time = "2025-09-29T21:12:29.123Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/49/13/5e2ea7c7a101b6fc3941be65307ef8df92cbbfa6ec4804032baf1893b434/fonttools-4.60.1-cp314-cp314-manylinux2014_aarch64.manylinux_2_17_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:154cb6ee417e417bf5f7c42fe25858c9140c26f647c7347c06f0cc2d47eff003", size = 4944184, upload-time = "2025-09-29T21:12:31.414Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/0c/2b/cf9603551c525b73fc47c52ee0b82a891579a93d9651ed694e4e2cd08bb8/fonttools-4.60.1-cp314-cp314-musllinux_1_2_aarch64.whl", hash = "sha256:5664fd1a9ea7f244487ac8f10340c4e37664675e8667d6fee420766e0fb3cf08", size = 4890218, upload-time = "2025-09-29T21:12:33.936Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fd/2f/933d2352422e25f2376aae74f79eaa882a50fb3bfef3c0d4f50501267101/fonttools-4.60.1-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:583b7f8e3c49486e4d489ad1deacfb8d5be54a8ef34d6df824f6a171f8511d99", size = 4999324, upload-time = "2025-09-29T21:12:36.637Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/38/99/234594c0391221f66216bc2c886923513b3399a148defaccf81dc3be6560/fonttools-4.60.1-cp314-cp314-win32.whl", hash = "sha256:66929e2ea2810c6533a5184f938502cfdaea4bc3efb7130d8cc02e1c1b4108d6", size = 2220861, upload-time = "2025-09-29T21:12:39.108Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/3e/1d/edb5b23726dde50fc4068e1493e4fc7658eeefcaf75d4c5ffce067d07ae5/fonttools-4.60.1-cp314-cp314-win_amd64.whl", hash = "sha256:f3d5be054c461d6a2268831f04091dc82753176f6ea06dc6047a5e168265a987", size = 2270934, upload-time = "2025-09-29T21:12:41.339Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fb/da/1392aaa2170adc7071fe7f9cfd181a5684a7afcde605aebddf1fb4d76df5/fonttools-4.60.1-cp314-cp314t-macosx_10_13_universal2.whl", hash = "sha256:b6379e7546ba4ae4b18f8ae2b9bc5960936007a1c0e30b342f662577e8bc3299", size = 2894340, upload-time = "2025-09-29T21:12:43.774Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/bf/a7/3b9f16e010d536ce567058b931a20b590d8f3177b2eda09edd92e392375d/fonttools-4.60.1-cp314-cp314t-macosx_10_13_x86_64.whl", hash = "sha256:9d0ced62b59e0430b3690dbc5373df1c2aa7585e9a8ce38eff87f0fd993c5b01", size = 2375073, upload-time = "2025-09-29T21:12:46.437Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/9b/b5/e9bcf51980f98e59bb5bb7c382a63c6f6cac0eec5f67de6d8f2322382065/fonttools-4.60.1-cp314-cp314t-manylinux1_x86_64.manylinux2014_x86_64.manylinux_2_17_x86_64.manylinux_2_5_x86_64.whl", hash = "sha256:875cb7764708b3132637f6c5fb385b16eeba0f7ac9fa45a69d35e09b47045801", size = 4849758, upload-time = "2025-09-29T21:12:48.694Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e3/dc/1d2cf7d1cba82264b2f8385db3f5960e3d8ce756b4dc65b700d2c496f7e9/fonttools-4.60.1-cp314-cp314t-manylinux2014_aarch64.manylinux_2_17_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:a184b2ea57b13680ab6d5fbde99ccef152c95c06746cb7718c583abd8f945ccc", size = 5085598, upload-time = "2025-09-29T21:12:51.081Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/5d/4d/279e28ba87fb20e0c69baf72b60bbf1c4d873af1476806a7b5f2b7fac1ff/fonttools-4.60.1-cp314-cp314t-musllinux_1_2_aarch64.whl", hash = "sha256:026290e4ec76583881763fac284aca67365e0be9f13a7fb137257096114cb3bc", size = 4957603, upload-time = "2025-09-29T21:12:53.423Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/78/d4/ff19976305e0c05aa3340c805475abb00224c954d3c65e82c0a69633d55d/fonttools-4.60.1-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:f0e8817c7d1a0c2eedebf57ef9a9896f3ea23324769a9a2061a80fe8852705ed", size = 4974184, upload-time = "2025-09-29T21:12:55.962Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/63/22/8553ff6166f5cd21cfaa115aaacaa0dc73b91c079a8cfd54a482cbc0f4f5/fonttools-4.60.1-cp314-cp314t-win32.whl", hash = "sha256:1410155d0e764a4615774e5c2c6fc516259fe3eca5882f034eb9bfdbee056259", size = 2282241, upload-time = "2025-09-29T21:12:58.179Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/8a/cb/fa7b4d148e11d5a72761a22e595344133e83a9507a4c231df972e657579b/fonttools-4.60.1-cp314-cp314t-win_amd64.whl", hash = "sha256:022beaea4b73a70295b688f817ddc24ed3e3418b5036ffcd5658141184ef0d0c", size = 2345760, upload-time = "2025-09-29T21:13:00.375Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/c7/93/0dd45cd283c32dea1545151d8c3637b4b8c53cdb3a625aeb2885b184d74d/fonttools-4.60.1-py3-none-any.whl", hash = "sha256:906306ac7afe2156fcf0042173d6ebbb05416af70f6b370967b47f8f00103bbb", size = 1143175, upload-time = "2025-09-29T21:13:24.134Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "kiwisolver"
|
||||||
|
version = "1.4.9"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/5c/3c/85844f1b0feb11ee581ac23fe5fce65cd049a200c1446708cc1b7f922875/kiwisolver-1.4.9.tar.gz", hash = "sha256:c3b22c26c6fd6811b0ae8363b95ca8ce4ea3c202d3d0975b2914310ceb1bcc4d", size = 97564, upload-time = "2025-08-10T21:27:49.279Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/31/c1/c2686cda909742ab66c7388e9a1a8521a59eb89f8bcfbee28fc980d07e24/kiwisolver-1.4.9-cp313-cp313-macosx_10_13_universal2.whl", hash = "sha256:a5d0432ccf1c7ab14f9949eec60c5d1f924f17c037e9f8b33352fa05799359b8", size = 123681, upload-time = "2025-08-10T21:26:26.725Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ca/f0/f44f50c9f5b1a1860261092e3bc91ecdc9acda848a8b8c6abfda4a24dd5c/kiwisolver-1.4.9-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:efb3a45b35622bb6c16dbfab491a8f5a391fe0e9d45ef32f4df85658232ca0e2", size = 66464, upload-time = "2025-08-10T21:26:27.733Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/2d/7a/9d90a151f558e29c3936b8a47ac770235f436f2120aca41a6d5f3d62ae8d/kiwisolver-1.4.9-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:1a12cf6398e8a0a001a059747a1cbf24705e18fe413bc22de7b3d15c67cffe3f", size = 64961, upload-time = "2025-08-10T21:26:28.729Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e9/e9/f218a2cb3a9ffbe324ca29a9e399fa2d2866d7f348ec3a88df87fc248fc5/kiwisolver-1.4.9-cp313-cp313-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:b67e6efbf68e077dd71d1a6b37e43e1a99d0bff1a3d51867d45ee8908b931098", size = 1474607, upload-time = "2025-08-10T21:26:29.798Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/d9/28/aac26d4c882f14de59041636292bc838db8961373825df23b8eeb807e198/kiwisolver-1.4.9-cp313-cp313-manylinux_2_24_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:5656aa670507437af0207645273ccdfee4f14bacd7f7c67a4306d0dcaeaf6eed", size = 1276546, upload-time = "2025-08-10T21:26:31.401Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/8b/ad/8bfc1c93d4cc565e5069162f610ba2f48ff39b7de4b5b8d93f69f30c4bed/kiwisolver-1.4.9-cp313-cp313-manylinux_2_24_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:bfc08add558155345129c7803b3671cf195e6a56e7a12f3dde7c57d9b417f525", size = 1294482, upload-time = "2025-08-10T21:26:32.721Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/da/f1/6aca55ff798901d8ce403206d00e033191f63d82dd708a186e0ed2067e9c/kiwisolver-1.4.9-cp313-cp313-manylinux_2_24_s390x.manylinux_2_28_s390x.whl", hash = "sha256:40092754720b174e6ccf9e845d0d8c7d8e12c3d71e7fc35f55f3813e96376f78", size = 1343720, upload-time = "2025-08-10T21:26:34.032Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/d1/91/eed031876c595c81d90d0f6fc681ece250e14bf6998c3d7c419466b523b7/kiwisolver-1.4.9-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:497d05f29a1300d14e02e6441cf0f5ee81c1ff5a304b0d9fb77423974684e08b", size = 2224907, upload-time = "2025-08-10T21:26:35.824Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e9/ec/4d1925f2e49617b9cca9c34bfa11adefad49d00db038e692a559454dfb2e/kiwisolver-1.4.9-cp313-cp313-musllinux_1_2_ppc64le.whl", hash = "sha256:bdd1a81a1860476eb41ac4bc1e07b3f07259e6d55bbf739b79c8aaedcf512799", size = 2321334, upload-time = "2025-08-10T21:26:37.534Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/43/cb/450cd4499356f68802750c6ddc18647b8ea01ffa28f50d20598e0befe6e9/kiwisolver-1.4.9-cp313-cp313-musllinux_1_2_s390x.whl", hash = "sha256:e6b93f13371d341afee3be9f7c5964e3fe61d5fa30f6a30eb49856935dfe4fc3", size = 2488313, upload-time = "2025-08-10T21:26:39.191Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/71/67/fc76242bd99f885651128a5d4fa6083e5524694b7c88b489b1b55fdc491d/kiwisolver-1.4.9-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:d75aa530ccfaa593da12834b86a0724f58bff12706659baa9227c2ccaa06264c", size = 2291970, upload-time = "2025-08-10T21:26:40.828Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/75/bd/f1a5d894000941739f2ae1b65a32892349423ad49c2e6d0771d0bad3fae4/kiwisolver-1.4.9-cp313-cp313-win_amd64.whl", hash = "sha256:dd0a578400839256df88c16abddf9ba14813ec5f21362e1fe65022e00c883d4d", size = 73894, upload-time = "2025-08-10T21:26:42.33Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/95/38/dce480814d25b99a391abbddadc78f7c117c6da34be68ca8b02d5848b424/kiwisolver-1.4.9-cp313-cp313-win_arm64.whl", hash = "sha256:d4188e73af84ca82468f09cadc5ac4db578109e52acb4518d8154698d3a87ca2", size = 64995, upload-time = "2025-08-10T21:26:43.889Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e2/37/7d218ce5d92dadc5ebdd9070d903e0c7cf7edfe03f179433ac4d13ce659c/kiwisolver-1.4.9-cp313-cp313t-macosx_10_13_universal2.whl", hash = "sha256:5a0f2724dfd4e3b3ac5a82436a8e6fd16baa7d507117e4279b660fe8ca38a3a1", size = 126510, upload-time = "2025-08-10T21:26:44.915Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/23/b0/e85a2b48233daef4b648fb657ebbb6f8367696a2d9548a00b4ee0eb67803/kiwisolver-1.4.9-cp313-cp313t-macosx_10_13_x86_64.whl", hash = "sha256:1b11d6a633e4ed84fc0ddafd4ebfd8ea49b3f25082c04ad12b8315c11d504dc1", size = 67903, upload-time = "2025-08-10T21:26:45.934Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/44/98/f2425bc0113ad7de24da6bb4dae1343476e95e1d738be7c04d31a5d037fd/kiwisolver-1.4.9-cp313-cp313t-macosx_11_0_arm64.whl", hash = "sha256:61874cdb0a36016354853593cffc38e56fc9ca5aa97d2c05d3dcf6922cd55a11", size = 66402, upload-time = "2025-08-10T21:26:47.101Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/98/d8/594657886df9f34c4177cc353cc28ca7e6e5eb562d37ccc233bff43bbe2a/kiwisolver-1.4.9-cp313-cp313t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:60c439763a969a6af93b4881db0eed8fadf93ee98e18cbc35bc8da868d0c4f0c", size = 1582135, upload-time = "2025-08-10T21:26:48.665Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/5c/c6/38a115b7170f8b306fc929e166340c24958347308ea3012c2b44e7e295db/kiwisolver-1.4.9-cp313-cp313t-manylinux_2_24_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:92a2f997387a1b79a75e7803aa7ded2cfbe2823852ccf1ba3bcf613b62ae3197", size = 1389409, upload-time = "2025-08-10T21:26:50.335Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/bf/3b/e04883dace81f24a568bcee6eb3001da4ba05114afa622ec9b6fafdc1f5e/kiwisolver-1.4.9-cp313-cp313t-manylinux_2_24_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:a31d512c812daea6d8b3be3b2bfcbeb091dbb09177706569bcfc6240dcf8b41c", size = 1401763, upload-time = "2025-08-10T21:26:51.867Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/9f/80/20ace48e33408947af49d7d15c341eaee69e4e0304aab4b7660e234d6288/kiwisolver-1.4.9-cp313-cp313t-manylinux_2_24_s390x.manylinux_2_28_s390x.whl", hash = "sha256:52a15b0f35dad39862d376df10c5230155243a2c1a436e39eb55623ccbd68185", size = 1453643, upload-time = "2025-08-10T21:26:53.592Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/64/31/6ce4380a4cd1f515bdda976a1e90e547ccd47b67a1546d63884463c92ca9/kiwisolver-1.4.9-cp313-cp313t-musllinux_1_2_aarch64.whl", hash = "sha256:a30fd6fdef1430fd9e1ba7b3398b5ee4e2887783917a687d86ba69985fb08748", size = 2330818, upload-time = "2025-08-10T21:26:55.051Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fa/e9/3f3fcba3bcc7432c795b82646306e822f3fd74df0ee81f0fa067a1f95668/kiwisolver-1.4.9-cp313-cp313t-musllinux_1_2_ppc64le.whl", hash = "sha256:cc9617b46837c6468197b5945e196ee9ca43057bb7d9d1ae688101e4e1dddf64", size = 2419963, upload-time = "2025-08-10T21:26:56.421Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/99/43/7320c50e4133575c66e9f7dadead35ab22d7c012a3b09bb35647792b2a6d/kiwisolver-1.4.9-cp313-cp313t-musllinux_1_2_s390x.whl", hash = "sha256:0ab74e19f6a2b027ea4f845a78827969af45ce790e6cb3e1ebab71bdf9f215ff", size = 2594639, upload-time = "2025-08-10T21:26:57.882Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/65/d6/17ae4a270d4a987ef8a385b906d2bdfc9fce502d6dc0d3aea865b47f548c/kiwisolver-1.4.9-cp313-cp313t-musllinux_1_2_x86_64.whl", hash = "sha256:dba5ee5d3981160c28d5490f0d1b7ed730c22470ff7f6cc26cfcfaacb9896a07", size = 2391741, upload-time = "2025-08-10T21:26:59.237Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/2a/8f/8f6f491d595a9e5912971f3f863d81baddccc8a4d0c3749d6a0dd9ffc9df/kiwisolver-1.4.9-cp313-cp313t-win_arm64.whl", hash = "sha256:0749fd8f4218ad2e851e11cc4dc05c7cbc0cbc4267bdfdb31782e65aace4ee9c", size = 68646, upload-time = "2025-08-10T21:27:00.52Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/6b/32/6cc0fbc9c54d06c2969faa9c1d29f5751a2e51809dd55c69055e62d9b426/kiwisolver-1.4.9-cp314-cp314-macosx_10_13_universal2.whl", hash = "sha256:9928fe1eb816d11ae170885a74d074f57af3a0d65777ca47e9aeb854a1fba386", size = 123806, upload-time = "2025-08-10T21:27:01.537Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b2/dd/2bfb1d4a4823d92e8cbb420fe024b8d2167f72079b3bb941207c42570bdf/kiwisolver-1.4.9-cp314-cp314-macosx_10_13_x86_64.whl", hash = "sha256:d0005b053977e7b43388ddec89fa567f43d4f6d5c2c0affe57de5ebf290dc552", size = 66605, upload-time = "2025-08-10T21:27:03.335Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/f7/69/00aafdb4e4509c2ca6064646cba9cd4b37933898f426756adb2cb92ebbed/kiwisolver-1.4.9-cp314-cp314-macosx_11_0_arm64.whl", hash = "sha256:2635d352d67458b66fd0667c14cb1d4145e9560d503219034a18a87e971ce4f3", size = 64925, upload-time = "2025-08-10T21:27:04.339Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/43/dc/51acc6791aa14e5cb6d8a2e28cefb0dc2886d8862795449d021334c0df20/kiwisolver-1.4.9-cp314-cp314-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:767c23ad1c58c9e827b649a9ab7809fd5fd9db266a9cf02b0e926ddc2c680d58", size = 1472414, upload-time = "2025-08-10T21:27:05.437Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/3d/bb/93fa64a81db304ac8a246f834d5094fae4b13baf53c839d6bb6e81177129/kiwisolver-1.4.9-cp314-cp314-manylinux_2_24_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:72d0eb9fba308b8311685c2268cf7d0a0639a6cd027d8128659f72bdd8a024b4", size = 1281272, upload-time = "2025-08-10T21:27:07.063Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/70/e6/6df102916960fb8d05069d4bd92d6d9a8202d5a3e2444494e7cd50f65b7a/kiwisolver-1.4.9-cp314-cp314-manylinux_2_24_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:f68e4f3eeca8fb22cc3d731f9715a13b652795ef657a13df1ad0c7dc0e9731df", size = 1298578, upload-time = "2025-08-10T21:27:08.452Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/7c/47/e142aaa612f5343736b087864dbaebc53ea8831453fb47e7521fa8658f30/kiwisolver-1.4.9-cp314-cp314-manylinux_2_24_s390x.manylinux_2_28_s390x.whl", hash = "sha256:d84cd4061ae292d8ac367b2c3fa3aad11cb8625a95d135fe93f286f914f3f5a6", size = 1345607, upload-time = "2025-08-10T21:27:10.125Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/54/89/d641a746194a0f4d1a3670fb900d0dbaa786fb98341056814bc3f058fa52/kiwisolver-1.4.9-cp314-cp314-musllinux_1_2_aarch64.whl", hash = "sha256:a60ea74330b91bd22a29638940d115df9dc00af5035a9a2a6ad9399ffb4ceca5", size = 2230150, upload-time = "2025-08-10T21:27:11.484Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/aa/6b/5ee1207198febdf16ac11f78c5ae40861b809cbe0e6d2a8d5b0b3044b199/kiwisolver-1.4.9-cp314-cp314-musllinux_1_2_ppc64le.whl", hash = "sha256:ce6a3a4e106cf35c2d9c4fa17c05ce0b180db622736845d4315519397a77beaf", size = 2325979, upload-time = "2025-08-10T21:27:12.917Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fc/ff/b269eefd90f4ae14dcc74973d5a0f6d28d3b9bb1afd8c0340513afe6b39a/kiwisolver-1.4.9-cp314-cp314-musllinux_1_2_s390x.whl", hash = "sha256:77937e5e2a38a7b48eef0585114fe7930346993a88060d0bf886086d2aa49ef5", size = 2491456, upload-time = "2025-08-10T21:27:14.353Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fc/d4/10303190bd4d30de547534601e259a4fbf014eed94aae3e5521129215086/kiwisolver-1.4.9-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:24c175051354f4a28c5d6a31c93906dc653e2bf234e8a4bbfb964892078898ce", size = 2294621, upload-time = "2025-08-10T21:27:15.808Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/28/e0/a9a90416fce5c0be25742729c2ea52105d62eda6c4be4d803c2a7be1fa50/kiwisolver-1.4.9-cp314-cp314-win_amd64.whl", hash = "sha256:0763515d4df10edf6d06a3c19734e2566368980d21ebec439f33f9eb936c07b7", size = 75417, upload-time = "2025-08-10T21:27:17.436Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/1f/10/6949958215b7a9a264299a7db195564e87900f709db9245e4ebdd3c70779/kiwisolver-1.4.9-cp314-cp314-win_arm64.whl", hash = "sha256:0e4e2bf29574a6a7b7f6cb5fa69293b9f96c928949ac4a53ba3f525dffb87f9c", size = 66582, upload-time = "2025-08-10T21:27:18.436Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ec/79/60e53067903d3bc5469b369fe0dfc6b3482e2133e85dae9daa9527535991/kiwisolver-1.4.9-cp314-cp314t-macosx_10_13_universal2.whl", hash = "sha256:d976bbb382b202f71c67f77b0ac11244021cfa3f7dfd9e562eefcea2df711548", size = 126514, upload-time = "2025-08-10T21:27:19.465Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/25/d1/4843d3e8d46b072c12a38c97c57fab4608d36e13fe47d47ee96b4d61ba6f/kiwisolver-1.4.9-cp314-cp314t-macosx_10_13_x86_64.whl", hash = "sha256:2489e4e5d7ef9a1c300a5e0196e43d9c739f066ef23270607d45aba368b91f2d", size = 67905, upload-time = "2025-08-10T21:27:20.51Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/8c/ae/29ffcbd239aea8b93108de1278271ae764dfc0d803a5693914975f200596/kiwisolver-1.4.9-cp314-cp314t-macosx_11_0_arm64.whl", hash = "sha256:e2ea9f7ab7fbf18fffb1b5434ce7c69a07582f7acc7717720f1d69f3e806f90c", size = 66399, upload-time = "2025-08-10T21:27:21.496Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/a1/ae/d7ba902aa604152c2ceba5d352d7b62106bedbccc8e95c3934d94472bfa3/kiwisolver-1.4.9-cp314-cp314t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:b34e51affded8faee0dfdb705416153819d8ea9250bbbf7ea1b249bdeb5f1122", size = 1582197, upload-time = "2025-08-10T21:27:22.604Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/f2/41/27c70d427eddb8bc7e4f16420a20fefc6f480312122a59a959fdfe0445ad/kiwisolver-1.4.9-cp314-cp314t-manylinux_2_24_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:d8aacd3d4b33b772542b2e01beb50187536967b514b00003bdda7589722d2a64", size = 1390125, upload-time = "2025-08-10T21:27:24.036Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/41/42/b3799a12bafc76d962ad69083f8b43b12bf4fe78b097b12e105d75c9b8f1/kiwisolver-1.4.9-cp314-cp314t-manylinux_2_24_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:7cf974dd4e35fa315563ac99d6287a1024e4dc2077b8a7d7cd3d2fb65d283134", size = 1402612, upload-time = "2025-08-10T21:27:25.773Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/d2/b5/a210ea073ea1cfaca1bb5c55a62307d8252f531beb364e18aa1e0888b5a0/kiwisolver-1.4.9-cp314-cp314t-manylinux_2_24_s390x.manylinux_2_28_s390x.whl", hash = "sha256:85bd218b5ecfbee8c8a82e121802dcb519a86044c9c3b2e4aef02fa05c6da370", size = 1453990, upload-time = "2025-08-10T21:27:27.089Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/5f/ce/a829eb8c033e977d7ea03ed32fb3c1781b4fa0433fbadfff29e39c676f32/kiwisolver-1.4.9-cp314-cp314t-musllinux_1_2_aarch64.whl", hash = "sha256:0856e241c2d3df4efef7c04a1e46b1936b6120c9bcf36dd216e3acd84bc4fb21", size = 2331601, upload-time = "2025-08-10T21:27:29.343Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e0/4b/b5e97eb142eb9cd0072dacfcdcd31b1c66dc7352b0f7c7255d339c0edf00/kiwisolver-1.4.9-cp314-cp314t-musllinux_1_2_ppc64le.whl", hash = "sha256:9af39d6551f97d31a4deebeac6f45b156f9755ddc59c07b402c148f5dbb6482a", size = 2422041, upload-time = "2025-08-10T21:27:30.754Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/40/be/8eb4cd53e1b85ba4edc3a9321666f12b83113a178845593307a3e7891f44/kiwisolver-1.4.9-cp314-cp314t-musllinux_1_2_s390x.whl", hash = "sha256:bb4ae2b57fc1d8cbd1cf7b1d9913803681ffa903e7488012be5b76dedf49297f", size = 2594897, upload-time = "2025-08-10T21:27:32.803Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/99/dd/841e9a66c4715477ea0abc78da039832fbb09dac5c35c58dc4c41a407b8a/kiwisolver-1.4.9-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:aedff62918805fb62d43a4aa2ecd4482c380dc76cd31bd7c8878588a61bd0369", size = 2391835, upload-time = "2025-08-10T21:27:34.23Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/0c/28/4b2e5c47a0da96896fdfdb006340ade064afa1e63675d01ea5ac222b6d52/kiwisolver-1.4.9-cp314-cp314t-win_amd64.whl", hash = "sha256:1fa333e8b2ce4d9660f2cda9c0e1b6bafcfb2457a9d259faa82289e73ec24891", size = 79988, upload-time = "2025-08-10T21:27:35.587Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/80/be/3578e8afd18c88cdf9cb4cffde75a96d2be38c5a903f1ed0ceec061bd09e/kiwisolver-1.4.9-cp314-cp314t-win_arm64.whl", hash = "sha256:4a48a2ce79d65d363597ef7b567ce3d14d68783d2b2263d98db3d9477805ba32", size = 70260, upload-time = "2025-08-10T21:27:36.606Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "llvmlite"
|
||||||
|
version = "0.45.1"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/99/8d/5baf1cef7f9c084fb35a8afbde88074f0d6a727bc63ef764fe0e7543ba40/llvmlite-0.45.1.tar.gz", hash = "sha256:09430bb9d0bb58fc45a45a57c7eae912850bedc095cd0810a57de109c69e1c32", size = 185600, upload-time = "2025-10-01T17:59:52.046Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/1d/e2/c185bb7e88514d5025f93c6c4092f6120c6cea8fe938974ec9860fb03bbb/llvmlite-0.45.1-cp313-cp313-macosx_10_15_x86_64.whl", hash = "sha256:d9ea9e6f17569a4253515cc01dade70aba536476e3d750b2e18d81d7e670eb15", size = 43043524, upload-time = "2025-10-01T18:03:43.249Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/09/b8/b5437b9ecb2064e89ccf67dccae0d02cd38911705112dd0dcbfa9cd9a9de/llvmlite-0.45.1-cp313-cp313-macosx_12_0_arm64.whl", hash = "sha256:c9f3cadee1630ce4ac18ea38adebf2a4f57a89bd2740ce83746876797f6e0bfb", size = 37253121, upload-time = "2025-10-01T18:04:30.557Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/f7/97/ad1a907c0173a90dd4df7228f24a3ec61058bc1a9ff8a0caec20a0cc622e/llvmlite-0.45.1-cp313-cp313-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:57c48bf2e1083eedbc9406fb83c4e6483017879714916fe8be8a72a9672c995a", size = 56288210, upload-time = "2025-10-01T18:01:40.26Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/32/d8/c99c8ac7a326e9735401ead3116f7685a7ec652691aeb2615aa732b1fc4a/llvmlite-0.45.1-cp313-cp313-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:3aa3dfceda4219ae39cf18806c60eeb518c1680ff834b8b311bd784160b9ce40", size = 55140957, upload-time = "2025-10-01T18:02:46.244Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/09/56/ed35668130e32dbfad2eb37356793b0a95f23494ab5be7d9bf5cb75850ee/llvmlite-0.45.1-cp313-cp313-win_amd64.whl", hash = "sha256:080e6f8d0778a8239cd47686d402cb66eb165e421efa9391366a9b7e5810a38b", size = 38132232, upload-time = "2025-10-01T18:05:14.477Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "matplotlib"
|
||||||
|
version = "3.10.7"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "contourpy" },
|
||||||
|
{ name = "cycler" },
|
||||||
|
{ name = "fonttools" },
|
||||||
|
{ name = "kiwisolver" },
|
||||||
|
{ name = "numpy" },
|
||||||
|
{ name = "packaging" },
|
||||||
|
{ name = "pillow" },
|
||||||
|
{ name = "pyparsing" },
|
||||||
|
{ name = "python-dateutil" },
|
||||||
|
]
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/ae/e2/d2d5295be2f44c678ebaf3544ba32d20c1f9ef08c49fe47f496180e1db15/matplotlib-3.10.7.tar.gz", hash = "sha256:a06ba7e2a2ef9131c79c49e63dad355d2d878413a0376c1727c8b9335ff731c7", size = 34804865, upload-time = "2025-10-09T00:28:00.669Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/02/9c/207547916a02c78f6bdd83448d9b21afbc42f6379ed887ecf610984f3b4e/matplotlib-3.10.7-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:1d9d3713a237970569156cfb4de7533b7c4eacdd61789726f444f96a0d28f57f", size = 8273212, upload-time = "2025-10-09T00:26:56.752Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/bc/d0/b3d3338d467d3fc937f0bb7f256711395cae6f78e22cef0656159950adf0/matplotlib-3.10.7-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:37a1fea41153dd6ee061d21ab69c9cf2cf543160b1b85d89cd3d2e2a7902ca4c", size = 8128713, upload-time = "2025-10-09T00:26:59.001Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/22/ff/6425bf5c20d79aa5b959d1ce9e65f599632345391381c9a104133fe0b171/matplotlib-3.10.7-cp313-cp313-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:b3c4ea4948d93c9c29dc01c0c23eef66f2101bf75158c291b88de6525c55c3d1", size = 8698527, upload-time = "2025-10-09T00:27:00.69Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/d0/7f/ccdca06f4c2e6c7989270ed7829b8679466682f4cfc0f8c9986241c023b6/matplotlib-3.10.7-cp313-cp313-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:22df30ffaa89f6643206cf13877191c63a50e8f800b038bc39bee9d2d4957632", size = 9529690, upload-time = "2025-10-09T00:27:02.664Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b8/95/b80fc2c1f269f21ff3d193ca697358e24408c33ce2b106a7438a45407b63/matplotlib-3.10.7-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:b69676845a0a66f9da30e87f48be36734d6748024b525ec4710be40194282c84", size = 9593732, upload-time = "2025-10-09T00:27:04.653Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e1/b6/23064a96308b9aeceeffa65e96bcde459a2ea4934d311dee20afde7407a0/matplotlib-3.10.7-cp313-cp313-win_amd64.whl", hash = "sha256:744991e0cc863dd669c8dc9136ca4e6e0082be2070b9d793cbd64bec872a6815", size = 8122727, upload-time = "2025-10-09T00:27:06.814Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b3/a6/2faaf48133b82cf3607759027f82b5c702aa99cdfcefb7f93d6ccf26a424/matplotlib-3.10.7-cp313-cp313-win_arm64.whl", hash = "sha256:fba2974df0bf8ce3c995fa84b79cde38326e0f7b5409e7a3a481c1141340bcf7", size = 7992958, upload-time = "2025-10-09T00:27:08.567Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/4a/f0/b018fed0b599bd48d84c08794cb242227fe3341952da102ee9d9682db574/matplotlib-3.10.7-cp313-cp313t-macosx_10_13_x86_64.whl", hash = "sha256:932c55d1fa7af4423422cb6a492a31cbcbdbe68fd1a9a3f545aa5e7a143b5355", size = 8316849, upload-time = "2025-10-09T00:27:10.254Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b0/b7/bb4f23856197659f275e11a2a164e36e65e9b48ea3e93c4ec25b4f163198/matplotlib-3.10.7-cp313-cp313t-macosx_11_0_arm64.whl", hash = "sha256:5e38c2d581d62ee729a6e144c47a71b3f42fb4187508dbbf4fe71d5612c3433b", size = 8178225, upload-time = "2025-10-09T00:27:12.241Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/62/56/0600609893ff277e6f3ab3c0cef4eafa6e61006c058e84286c467223d4d5/matplotlib-3.10.7-cp313-cp313t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:786656bb13c237bbcebcd402f65f44dd61ead60ee3deb045af429d889c8dbc67", size = 8711708, upload-time = "2025-10-09T00:27:13.879Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/d8/1a/6bfecb0cafe94d6658f2f1af22c43b76cf7a1c2f0dc34ef84cbb6809617e/matplotlib-3.10.7-cp313-cp313t-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:09d7945a70ea43bf9248f4b6582734c2fe726723204a76eca233f24cffc7ef67", size = 9541409, upload-time = "2025-10-09T00:27:15.684Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/08/50/95122a407d7f2e446fd865e2388a232a23f2b81934960ea802f3171518e4/matplotlib-3.10.7-cp313-cp313t-musllinux_1_2_x86_64.whl", hash = "sha256:d0b181e9fa8daf1d9f2d4c547527b167cb8838fc587deabca7b5c01f97199e84", size = 9594054, upload-time = "2025-10-09T00:27:17.547Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/13/76/75b194a43b81583478a81e78a07da8d9ca6ddf50dd0a2ccabf258059481d/matplotlib-3.10.7-cp313-cp313t-win_amd64.whl", hash = "sha256:31963603041634ce1a96053047b40961f7a29eb8f9a62e80cc2c0427aa1d22a2", size = 8200100, upload-time = "2025-10-09T00:27:20.039Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/f5/9e/6aefebdc9f8235c12bdeeda44cc0383d89c1e41da2c400caf3ee2073a3ce/matplotlib-3.10.7-cp313-cp313t-win_arm64.whl", hash = "sha256:aebed7b50aa6ac698c90f60f854b47e48cd2252b30510e7a1feddaf5a3f72cbf", size = 8042131, upload-time = "2025-10-09T00:27:21.608Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/0d/4b/e5bc2c321b6a7e3a75638d937d19ea267c34bd5a90e12bee76c4d7c7a0d9/matplotlib-3.10.7-cp314-cp314-macosx_10_13_x86_64.whl", hash = "sha256:d883460c43e8c6b173fef244a2341f7f7c0e9725c7fe68306e8e44ed9c8fb100", size = 8273787, upload-time = "2025-10-09T00:27:23.27Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/86/ad/6efae459c56c2fbc404da154e13e3a6039129f3c942b0152624f1c621f05/matplotlib-3.10.7-cp314-cp314-macosx_11_0_arm64.whl", hash = "sha256:07124afcf7a6504eafcb8ce94091c5898bbdd351519a1beb5c45f7a38c67e77f", size = 8131348, upload-time = "2025-10-09T00:27:24.926Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/a6/5a/a4284d2958dee4116359cc05d7e19c057e64ece1b4ac986ab0f2f4d52d5a/matplotlib-3.10.7-cp314-cp314-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:c17398b709a6cce3d9fdb1595c33e356d91c098cd9486cb2cc21ea2ea418e715", size = 9533949, upload-time = "2025-10-09T00:27:26.704Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/de/ff/f3781b5057fa3786623ad8976fc9f7b0d02b2f28534751fd5a44240de4cf/matplotlib-3.10.7-cp314-cp314-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:7146d64f561498764561e9cd0ed64fcf582e570fc519e6f521e2d0cfd43365e1", size = 9804247, upload-time = "2025-10-09T00:27:28.514Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/47/5a/993a59facb8444efb0e197bf55f545ee449902dcee86a4dfc580c3b61314/matplotlib-3.10.7-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:90ad854c0a435da3104c01e2c6f0028d7e719b690998a2333d7218db80950722", size = 9595497, upload-time = "2025-10-09T00:27:30.418Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/0d/a5/77c95aaa9bb32c345cbb49626ad8eb15550cba2e6d4c88081a6c2ac7b08d/matplotlib-3.10.7-cp314-cp314-win_amd64.whl", hash = "sha256:4645fc5d9d20ffa3a39361fcdbcec731382763b623b72627806bf251b6388866", size = 8252732, upload-time = "2025-10-09T00:27:32.332Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/74/04/45d269b4268d222390d7817dae77b159651909669a34ee9fdee336db5883/matplotlib-3.10.7-cp314-cp314-win_arm64.whl", hash = "sha256:9257be2f2a03415f9105c486d304a321168e61ad450f6153d77c69504ad764bb", size = 8124240, upload-time = "2025-10-09T00:27:33.94Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/4b/c7/ca01c607bb827158b439208c153d6f14ddb9fb640768f06f7ca3488ae67b/matplotlib-3.10.7-cp314-cp314t-macosx_10_13_x86_64.whl", hash = "sha256:1e4bbad66c177a8fdfa53972e5ef8be72a5f27e6a607cec0d8579abd0f3102b1", size = 8316938, upload-time = "2025-10-09T00:27:35.534Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/84/d2/5539e66e9f56d2fdec94bb8436f5e449683b4e199bcc897c44fbe3c99e28/matplotlib-3.10.7-cp314-cp314t-macosx_11_0_arm64.whl", hash = "sha256:d8eb7194b084b12feb19142262165832fc6ee879b945491d1c3d4660748020c4", size = 8178245, upload-time = "2025-10-09T00:27:37.334Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/77/b5/e6ca22901fd3e4fe433a82e583436dd872f6c966fca7e63cf806b40356f8/matplotlib-3.10.7-cp314-cp314t-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:b4d41379b05528091f00e1728004f9a8d7191260f3862178b88e8fd770206318", size = 9541411, upload-time = "2025-10-09T00:27:39.387Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/9e/99/a4524db57cad8fee54b7237239a8f8360bfcfa3170d37c9e71c090c0f409/matplotlib-3.10.7-cp314-cp314t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:4a74f79fafb2e177f240579bc83f0b60f82cc47d2f1d260f422a0627207008ca", size = 9803664, upload-time = "2025-10-09T00:27:41.492Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e6/a5/85e2edf76ea0ad4288d174926d9454ea85f3ce5390cc4e6fab196cbf250b/matplotlib-3.10.7-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:702590829c30aada1e8cef0568ddbffa77ca747b4d6e36c6d173f66e301f89cc", size = 9594066, upload-time = "2025-10-09T00:27:43.694Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/39/69/9684368a314f6d83fe5c5ad2a4121a3a8e03723d2e5c8ea17b66c1bad0e7/matplotlib-3.10.7-cp314-cp314t-win_amd64.whl", hash = "sha256:f79d5de970fc90cd5591f60053aecfce1fcd736e0303d9f0bf86be649fa68fb8", size = 8342832, upload-time = "2025-10-09T00:27:45.543Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/04/5f/e22e08da14bc1a0894184640d47819d2338b792732e20d292bf86e5ab785/matplotlib-3.10.7-cp314-cp314t-win_arm64.whl", hash = "sha256:cb783436e47fcf82064baca52ce748af71725d0352e1d31564cbe9c95df92b9c", size = 8172585, upload-time = "2025-10-09T00:27:47.185Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "numba"
|
||||||
|
version = "0.62.1"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "llvmlite" },
|
||||||
|
{ name = "numpy" },
|
||||||
|
]
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/a3/20/33dbdbfe60e5fd8e3dbfde299d106279a33d9f8308346022316781368591/numba-0.62.1.tar.gz", hash = "sha256:7b774242aa890e34c21200a1fc62e5b5757d5286267e71103257f4e2af0d5161", size = 2749817, upload-time = "2025-09-29T10:46:31.551Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/22/76/501ea2c07c089ef1386868f33dff2978f43f51b854e34397b20fc55e0a58/numba-0.62.1-cp313-cp313-macosx_10_15_x86_64.whl", hash = "sha256:b72489ba8411cc9fdcaa2458d8f7677751e94f0109eeb53e5becfdc818c64afb", size = 2685766, upload-time = "2025-09-29T10:43:49.161Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/80/68/444986ed95350c0611d5c7b46828411c222ce41a0c76707c36425d27ce29/numba-0.62.1-cp313-cp313-macosx_12_0_arm64.whl", hash = "sha256:44a1412095534a26fb5da2717bc755b57da5f3053965128fe3dc286652cc6a92", size = 2688741, upload-time = "2025-09-29T10:44:10.07Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/78/7e/bf2e3634993d57f95305c7cee4c9c6cb3c9c78404ee7b49569a0dfecfe33/numba-0.62.1-cp313-cp313-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:8c9460b9e936c5bd2f0570e20a0a5909ee6e8b694fd958b210e3bde3a6dba2d7", size = 3804576, upload-time = "2025-09-29T10:42:59.53Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e8/b6/8a1723fff71f63bbb1354bdc60a1513a068acc0f5322f58da6f022d20247/numba-0.62.1-cp313-cp313-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:728f91a874192df22d74e3fd42c12900b7ce7190b1aad3574c6c61b08313e4c5", size = 3503367, upload-time = "2025-09-29T10:43:26.326Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/9c/ec/9d414e7a80d6d1dc4af0e07c6bfe293ce0b04ea4d0ed6c45dad9bd6e72eb/numba-0.62.1-cp313-cp313-win_amd64.whl", hash = "sha256:bbf3f88b461514287df66bc8d0307e949b09f2b6f67da92265094e8fa1282dd8", size = 2745529, upload-time = "2025-09-29T10:44:31.738Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "numpy"
|
||||||
|
version = "2.3.5"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/76/65/21b3bc86aac7b8f2862db1e808f1ea22b028e30a225a34a5ede9bf8678f2/numpy-2.3.5.tar.gz", hash = "sha256:784db1dcdab56bf0517743e746dfb0f885fc68d948aba86eeec2cba234bdf1c0", size = 20584950, upload-time = "2025-11-16T22:52:42.067Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/db/69/9cde09f36da4b5a505341180a3f2e6fadc352fd4d2b7096ce9778db83f1a/numpy-2.3.5-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:d0f23b44f57077c1ede8c5f26b30f706498b4862d3ff0a7298b8411dd2f043ff", size = 16728251, upload-time = "2025-11-16T22:50:19.013Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/79/fb/f505c95ceddd7027347b067689db71ca80bd5ecc926f913f1a23e65cf09b/numpy-2.3.5-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:aa5bc7c5d59d831d9773d1170acac7893ce3a5e130540605770ade83280e7188", size = 12254652, upload-time = "2025-11-16T22:50:21.487Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/78/da/8c7738060ca9c31b30e9301ee0cf6c5ffdbf889d9593285a1cead337f9a5/numpy-2.3.5-cp313-cp313-macosx_14_0_arm64.whl", hash = "sha256:ccc933afd4d20aad3c00bcef049cb40049f7f196e0397f1109dba6fed63267b0", size = 5083172, upload-time = "2025-11-16T22:50:24.562Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/a4/b4/ee5bb2537fb9430fd2ef30a616c3672b991a4129bb1c7dcc42aa0abbe5d7/numpy-2.3.5-cp313-cp313-macosx_14_0_x86_64.whl", hash = "sha256:afaffc4393205524af9dfa400fa250143a6c3bc646c08c9f5e25a9f4b4d6a903", size = 6622990, upload-time = "2025-11-16T22:50:26.47Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/95/03/dc0723a013c7d7c19de5ef29e932c3081df1c14ba582b8b86b5de9db7f0f/numpy-2.3.5-cp313-cp313-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:9c75442b2209b8470d6d5d8b1c25714270686f14c749028d2199c54e29f20b4d", size = 14248902, upload-time = "2025-11-16T22:50:28.861Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/f5/10/ca162f45a102738958dcec8023062dad0cbc17d1ab99d68c4e4a6c45fb2b/numpy-2.3.5-cp313-cp313-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:11e06aa0af8c0f05104d56450d6093ee639e15f24ecf62d417329d06e522e017", size = 16597430, upload-time = "2025-11-16T22:50:31.56Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/2a/51/c1e29be863588db58175175f057286900b4b3327a1351e706d5e0f8dd679/numpy-2.3.5-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:ed89927b86296067b4f81f108a2271d8926467a8868e554eaf370fc27fa3ccaf", size = 16024551, upload-time = "2025-11-16T22:50:34.242Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/83/68/8236589d4dbb87253d28259d04d9b814ec0ecce7cb1c7fed29729f4c3a78/numpy-2.3.5-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:51c55fe3451421f3a6ef9a9c1439e82101c57a2c9eab9feb196a62b1a10b58ce", size = 18533275, upload-time = "2025-11-16T22:50:37.651Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/40/56/2932d75b6f13465239e3b7b7e511be27f1b8161ca2510854f0b6e521c395/numpy-2.3.5-cp313-cp313-win32.whl", hash = "sha256:1978155dd49972084bd6ef388d66ab70f0c323ddee6f693d539376498720fb7e", size = 6277637, upload-time = "2025-11-16T22:50:40.11Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/0c/88/e2eaa6cffb115b85ed7c7c87775cb8bcf0816816bc98ca8dbfa2ee33fe6e/numpy-2.3.5-cp313-cp313-win_amd64.whl", hash = "sha256:00dc4e846108a382c5869e77c6ed514394bdeb3403461d25a829711041217d5b", size = 12779090, upload-time = "2025-11-16T22:50:42.503Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/8f/88/3f41e13a44ebd4034ee17baa384acac29ba6a4fcc2aca95f6f08ca0447d1/numpy-2.3.5-cp313-cp313-win_arm64.whl", hash = "sha256:0472f11f6ec23a74a906a00b48a4dcf3849209696dff7c189714511268d103ae", size = 10194710, upload-time = "2025-11-16T22:50:44.971Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/13/cb/71744144e13389d577f867f745b7df2d8489463654a918eea2eeb166dfc9/numpy-2.3.5-cp313-cp313t-macosx_10_13_x86_64.whl", hash = "sha256:414802f3b97f3c1eef41e530aaba3b3c1620649871d8cb38c6eaff034c2e16bd", size = 16827292, upload-time = "2025-11-16T22:50:47.715Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/71/80/ba9dc6f2a4398e7f42b708a7fdc841bb638d353be255655498edbf9a15a8/numpy-2.3.5-cp313-cp313t-macosx_11_0_arm64.whl", hash = "sha256:5ee6609ac3604fa7780e30a03e5e241a7956f8e2fcfe547d51e3afa5247ac47f", size = 12378897, upload-time = "2025-11-16T22:50:51.327Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/2e/6d/db2151b9f64264bcceccd51741aa39b50150de9b602d98ecfe7e0c4bff39/numpy-2.3.5-cp313-cp313t-macosx_14_0_arm64.whl", hash = "sha256:86d835afea1eaa143012a2d7a3f45a3adce2d7adc8b4961f0b362214d800846a", size = 5207391, upload-time = "2025-11-16T22:50:54.542Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/80/ae/429bacace5ccad48a14c4ae5332f6aa8ab9f69524193511d60ccdfdc65fa/numpy-2.3.5-cp313-cp313t-macosx_14_0_x86_64.whl", hash = "sha256:30bc11310e8153ca664b14c5f1b73e94bd0503681fcf136a163de856f3a50139", size = 6721275, upload-time = "2025-11-16T22:50:56.794Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/74/5b/1919abf32d8722646a38cd527bc3771eb229a32724ee6ba340ead9b92249/numpy-2.3.5-cp313-cp313t-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:1062fde1dcf469571705945b0f221b73928f34a20c904ffb45db101907c3454e", size = 14306855, upload-time = "2025-11-16T22:50:59.208Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/a5/87/6831980559434973bebc30cd9c1f21e541a0f2b0c280d43d3afd909b66d0/numpy-2.3.5-cp313-cp313t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:ce581db493ea1a96c0556360ede6607496e8bf9b3a8efa66e06477267bc831e9", size = 16657359, upload-time = "2025-11-16T22:51:01.991Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/dd/91/c797f544491ee99fd00495f12ebb7802c440c1915811d72ac5b4479a3356/numpy-2.3.5-cp313-cp313t-musllinux_1_2_aarch64.whl", hash = "sha256:cc8920d2ec5fa99875b670bb86ddeb21e295cb07aa331810d9e486e0b969d946", size = 16093374, upload-time = "2025-11-16T22:51:05.291Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/74/a6/54da03253afcbe7a72785ec4da9c69fb7a17710141ff9ac5fcb2e32dbe64/numpy-2.3.5-cp313-cp313t-musllinux_1_2_x86_64.whl", hash = "sha256:9ee2197ef8c4f0dfe405d835f3b6a14f5fee7782b5de51ba06fb65fc9b36e9f1", size = 18594587, upload-time = "2025-11-16T22:51:08.585Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/80/e9/aff53abbdd41b0ecca94285f325aff42357c6b5abc482a3fcb4994290b18/numpy-2.3.5-cp313-cp313t-win32.whl", hash = "sha256:70b37199913c1bd300ff6e2693316c6f869c7ee16378faf10e4f5e3275b299c3", size = 6405940, upload-time = "2025-11-16T22:51:11.541Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/d5/81/50613fec9d4de5480de18d4f8ef59ad7e344d497edbef3cfd80f24f98461/numpy-2.3.5-cp313-cp313t-win_amd64.whl", hash = "sha256:b501b5fa195cc9e24fe102f21ec0a44dffc231d2af79950b451e0d99cea02234", size = 12920341, upload-time = "2025-11-16T22:51:14.312Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/bb/ab/08fd63b9a74303947f34f0bd7c5903b9c5532c2d287bead5bdf4c556c486/numpy-2.3.5-cp313-cp313t-win_arm64.whl", hash = "sha256:a80afd79f45f3c4a7d341f13acbe058d1ca8ac017c165d3fa0d3de6bc1a079d7", size = 10262507, upload-time = "2025-11-16T22:51:16.846Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ba/97/1a914559c19e32d6b2e233cf9a6a114e67c856d35b1d6babca571a3e880f/numpy-2.3.5-cp314-cp314-macosx_10_15_x86_64.whl", hash = "sha256:bf06bc2af43fa8d32d30fae16ad965663e966b1a3202ed407b84c989c3221e82", size = 16735706, upload-time = "2025-11-16T22:51:19.558Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/57/d4/51233b1c1b13ecd796311216ae417796b88b0616cfd8a33ae4536330748a/numpy-2.3.5-cp314-cp314-macosx_11_0_arm64.whl", hash = "sha256:052e8c42e0c49d2575621c158934920524f6c5da05a1d3b9bab5d8e259e045f0", size = 12264507, upload-time = "2025-11-16T22:51:22.492Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/45/98/2fe46c5c2675b8306d0b4a3ec3494273e93e1226a490f766e84298576956/numpy-2.3.5-cp314-cp314-macosx_14_0_arm64.whl", hash = "sha256:1ed1ec893cff7040a02c8aa1c8611b94d395590d553f6b53629a4461dc7f7b63", size = 5093049, upload-time = "2025-11-16T22:51:25.171Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ce/0e/0698378989bb0ac5f1660c81c78ab1fe5476c1a521ca9ee9d0710ce54099/numpy-2.3.5-cp314-cp314-macosx_14_0_x86_64.whl", hash = "sha256:2dcd0808a421a482a080f89859a18beb0b3d1e905b81e617a188bd80422d62e9", size = 6626603, upload-time = "2025-11-16T22:51:27Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/5e/a6/9ca0eecc489640615642a6cbc0ca9e10df70df38c4d43f5a928ff18d8827/numpy-2.3.5-cp314-cp314-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:727fd05b57df37dc0bcf1a27767a3d9a78cbbc92822445f32cc3436ba797337b", size = 14262696, upload-time = "2025-11-16T22:51:29.402Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/c8/f6/07ec185b90ec9d7217a00eeeed7383b73d7e709dae2a9a021b051542a708/numpy-2.3.5-cp314-cp314-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:fffe29a1ef00883599d1dc2c51aa2e5d80afe49523c261a74933df395c15c520", size = 16597350, upload-time = "2025-11-16T22:51:32.167Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/75/37/164071d1dde6a1a84c9b8e5b414fa127981bad47adf3a6b7e23917e52190/numpy-2.3.5-cp314-cp314-musllinux_1_2_aarch64.whl", hash = "sha256:8f7f0e05112916223d3f438f293abf0727e1181b5983f413dfa2fefc4098245c", size = 16040190, upload-time = "2025-11-16T22:51:35.403Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/08/3c/f18b82a406b04859eb026d204e4e1773eb41c5be58410f41ffa511d114ae/numpy-2.3.5-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:2e2eb32ddb9ccb817d620ac1d8dae7c3f641c1e5f55f531a33e8ab97960a75b8", size = 18536749, upload-time = "2025-11-16T22:51:39.698Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/40/79/f82f572bf44cf0023a2fe8588768e23e1592585020d638999f15158609e1/numpy-2.3.5-cp314-cp314-win32.whl", hash = "sha256:66f85ce62c70b843bab1fb14a05d5737741e74e28c7b8b5a064de10142fad248", size = 6335432, upload-time = "2025-11-16T22:51:42.476Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/a3/2e/235b4d96619931192c91660805e5e49242389742a7a82c27665021db690c/numpy-2.3.5-cp314-cp314-win_amd64.whl", hash = "sha256:e6a0bc88393d65807d751a614207b7129a310ca4fe76a74e5c7da5fa5671417e", size = 12919388, upload-time = "2025-11-16T22:51:45.275Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/07/2b/29fd75ce45d22a39c61aad74f3d718e7ab67ccf839ca8b60866054eb15f8/numpy-2.3.5-cp314-cp314-win_arm64.whl", hash = "sha256:aeffcab3d4b43712bb7a60b65f6044d444e75e563ff6180af8f98dd4b905dfd2", size = 10476651, upload-time = "2025-11-16T22:51:47.749Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/17/e1/f6a721234ebd4d87084cfa68d081bcba2f5cfe1974f7de4e0e8b9b2a2ba1/numpy-2.3.5-cp314-cp314t-macosx_10_15_x86_64.whl", hash = "sha256:17531366a2e3a9e30762c000f2c43a9aaa05728712e25c11ce1dbe700c53ad41", size = 16834503, upload-time = "2025-11-16T22:51:50.443Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/5c/1c/baf7ffdc3af9c356e1c135e57ab7cf8d247931b9554f55c467efe2c69eff/numpy-2.3.5-cp314-cp314t-macosx_11_0_arm64.whl", hash = "sha256:d21644de1b609825ede2f48be98dfde4656aefc713654eeee280e37cadc4e0ad", size = 12381612, upload-time = "2025-11-16T22:51:53.609Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/74/91/f7f0295151407ddc9ba34e699013c32c3c91944f9b35fcf9281163dc1468/numpy-2.3.5-cp314-cp314t-macosx_14_0_arm64.whl", hash = "sha256:c804e3a5aba5460c73955c955bdbd5c08c354954e9270a2c1565f62e866bdc39", size = 5210042, upload-time = "2025-11-16T22:51:56.213Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/2e/3b/78aebf345104ec50dd50a4d06ddeb46a9ff5261c33bcc58b1c4f12f85ec2/numpy-2.3.5-cp314-cp314t-macosx_14_0_x86_64.whl", hash = "sha256:cc0a57f895b96ec78969c34f682c602bf8da1a0270b09bc65673df2e7638ec20", size = 6724502, upload-time = "2025-11-16T22:51:58.584Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/02/c6/7c34b528740512e57ef1b7c8337ab0b4f0bddf34c723b8996c675bc2bc91/numpy-2.3.5-cp314-cp314t-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:900218e456384ea676e24ea6a0417f030a3b07306d29d7ad843957b40a9d8d52", size = 14308962, upload-time = "2025-11-16T22:52:01.698Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/80/35/09d433c5262bc32d725bafc619e095b6a6651caf94027a03da624146f655/numpy-2.3.5-cp314-cp314t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:09a1bea522b25109bf8e6f3027bd810f7c1085c64a0c7ce050c1676ad0ba010b", size = 16655054, upload-time = "2025-11-16T22:52:04.267Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/7a/ab/6a7b259703c09a88804fa2430b43d6457b692378f6b74b356155283566ac/numpy-2.3.5-cp314-cp314t-musllinux_1_2_aarch64.whl", hash = "sha256:04822c00b5fd0323c8166d66c701dc31b7fbd252c100acd708c48f763968d6a3", size = 16091613, upload-time = "2025-11-16T22:52:08.651Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/c2/88/330da2071e8771e60d1038166ff9d73f29da37b01ec3eb43cb1427464e10/numpy-2.3.5-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:d6889ec4ec662a1a37eb4b4fb26b6100841804dac55bd9df579e326cdc146227", size = 18591147, upload-time = "2025-11-16T22:52:11.453Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/51/41/851c4b4082402d9ea860c3626db5d5df47164a712cb23b54be028b184c1c/numpy-2.3.5-cp314-cp314t-win32.whl", hash = "sha256:93eebbcf1aafdf7e2ddd44c2923e2672e1010bddc014138b229e49725b4d6be5", size = 6479806, upload-time = "2025-11-16T22:52:14.641Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/90/30/d48bde1dfd93332fa557cff1972fbc039e055a52021fbef4c2c4b1eefd17/numpy-2.3.5-cp314-cp314t-win_amd64.whl", hash = "sha256:c8a9958e88b65c3b27e22ca2a076311636850b612d6bbfb76e8d156aacde2aaf", size = 13105760, upload-time = "2025-11-16T22:52:17.975Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/2d/fd/4b5eb0b3e888d86aee4d198c23acec7d214baaf17ea93c1adec94c9518b9/numpy-2.3.5-cp314-cp314t-win_arm64.whl", hash = "sha256:6203fdf9f3dc5bdaed7319ad8698e685c7a3be10819f41d32a0723e611733b42", size = 10545459, upload-time = "2025-11-16T22:52:20.55Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "packaging"
|
||||||
|
version = "25.0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/a1/d4/1fc4078c65507b51b96ca8f8c3ba19e6a61c8253c72794544580a7b6c24d/packaging-25.0.tar.gz", hash = "sha256:d443872c98d677bf60f6a1f2f8c1cb748e8fe762d2bf9d3148b5599295b0fc4f", size = 165727, upload-time = "2025-04-19T11:48:59.673Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/20/12/38679034af332785aac8774540895e234f4d07f7545804097de4b666afd8/packaging-25.0-py3-none-any.whl", hash = "sha256:29572ef2b1f17581046b3a2227d5c611fb25ec70ca1ba8554b24b0e69331a484", size = 66469, upload-time = "2025-04-19T11:48:57.875Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pillow"
|
||||||
|
version = "12.0.0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/5a/b0/cace85a1b0c9775a9f8f5d5423c8261c858760e2466c79b2dd184638b056/pillow-12.0.0.tar.gz", hash = "sha256:87d4f8125c9988bfbed67af47dd7a953e2fc7b0cc1e7800ec6d2080d490bb353", size = 47008828, upload-time = "2025-10-15T18:24:14.008Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/62/f2/de993bb2d21b33a98d031ecf6a978e4b61da207bef02f7b43093774c480d/pillow-12.0.0-cp313-cp313-ios_13_0_arm64_iphoneos.whl", hash = "sha256:0869154a2d0546545cde61d1789a6524319fc1897d9ee31218eae7a60ccc5643", size = 4045493, upload-time = "2025-10-15T18:22:25.758Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/0e/b6/bc8d0c4c9f6f111a783d045310945deb769b806d7574764234ffd50bc5ea/pillow-12.0.0-cp313-cp313-ios_13_0_arm64_iphonesimulator.whl", hash = "sha256:a7921c5a6d31b3d756ec980f2f47c0cfdbce0fc48c22a39347a895f41f4a6ea4", size = 4120461, upload-time = "2025-10-15T18:22:27.286Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/5d/57/d60d343709366a353dc56adb4ee1e7d8a2cc34e3fbc22905f4167cfec119/pillow-12.0.0-cp313-cp313-ios_13_0_x86_64_iphonesimulator.whl", hash = "sha256:1ee80a59f6ce048ae13cda1abf7fbd2a34ab9ee7d401c46be3ca685d1999a399", size = 3576912, upload-time = "2025-10-15T18:22:28.751Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/a4/a4/a0a31467e3f83b94d37568294b01d22b43ae3c5d85f2811769b9c66389dd/pillow-12.0.0-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:c50f36a62a22d350c96e49ad02d0da41dbd17ddc2e29750dbdba4323f85eb4a5", size = 5249132, upload-time = "2025-10-15T18:22:30.641Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/83/06/48eab21dd561de2914242711434c0c0eb992ed08ff3f6107a5f44527f5e9/pillow-12.0.0-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:5193fde9a5f23c331ea26d0cf171fbf67e3f247585f50c08b3e205c7aeb4589b", size = 4650099, upload-time = "2025-10-15T18:22:32.73Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fc/bd/69ed99fd46a8dba7c1887156d3572fe4484e3f031405fcc5a92e31c04035/pillow-12.0.0-cp313-cp313-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:bde737cff1a975b70652b62d626f7785e0480918dece11e8fef3c0cf057351c3", size = 6230808, upload-time = "2025-10-15T18:22:34.337Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ea/94/8fad659bcdbf86ed70099cb60ae40be6acca434bbc8c4c0d4ef356d7e0de/pillow-12.0.0-cp313-cp313-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:a6597ff2b61d121172f5844b53f21467f7082f5fb385a9a29c01414463f93b07", size = 8037804, upload-time = "2025-10-15T18:22:36.402Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/20/39/c685d05c06deecfd4e2d1950e9a908aa2ca8bc4e6c3b12d93b9cafbd7837/pillow-12.0.0-cp313-cp313-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:0b817e7035ea7f6b942c13aa03bb554fc44fea70838ea21f8eb31c638326584e", size = 6345553, upload-time = "2025-10-15T18:22:38.066Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/38/57/755dbd06530a27a5ed74f8cb0a7a44a21722ebf318edbe67ddbd7fb28f88/pillow-12.0.0-cp313-cp313-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:f4f1231b7dec408e8670264ce63e9c71409d9583dd21d32c163e25213ee2a344", size = 7037729, upload-time = "2025-10-15T18:22:39.769Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ca/b6/7e94f4c41d238615674d06ed677c14883103dce1c52e4af16f000338cfd7/pillow-12.0.0-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:6e51b71417049ad6ab14c49608b4a24d8fb3fe605e5dfabfe523b58064dc3d27", size = 6459789, upload-time = "2025-10-15T18:22:41.437Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/9c/14/4448bb0b5e0f22dd865290536d20ec8a23b64e2d04280b89139f09a36bb6/pillow-12.0.0-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:d120c38a42c234dc9a8c5de7ceaaf899cf33561956acb4941653f8bdc657aa79", size = 7130917, upload-time = "2025-10-15T18:22:43.152Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/dd/ca/16c6926cc1c015845745d5c16c9358e24282f1e588237a4c36d2b30f182f/pillow-12.0.0-cp313-cp313-win32.whl", hash = "sha256:4cc6b3b2efff105c6a1656cfe59da4fdde2cda9af1c5e0b58529b24525d0a098", size = 6302391, upload-time = "2025-10-15T18:22:44.753Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/6d/2a/dd43dcfd6dae9b6a49ee28a8eedb98c7d5ff2de94a5d834565164667b97b/pillow-12.0.0-cp313-cp313-win_amd64.whl", hash = "sha256:4cf7fed4b4580601c4345ceb5d4cbf5a980d030fd5ad07c4d2ec589f95f09905", size = 7007477, upload-time = "2025-10-15T18:22:46.838Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/77/f0/72ea067f4b5ae5ead653053212af05ce3705807906ba3f3e8f58ddf617e6/pillow-12.0.0-cp313-cp313-win_arm64.whl", hash = "sha256:9f0b04c6b8584c2c193babcccc908b38ed29524b29dd464bc8801bf10d746a3a", size = 2435918, upload-time = "2025-10-15T18:22:48.399Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/f5/5e/9046b423735c21f0487ea6cb5b10f89ea8f8dfbe32576fe052b5ba9d4e5b/pillow-12.0.0-cp313-cp313t-macosx_10_13_x86_64.whl", hash = "sha256:7fa22993bac7b77b78cae22bad1e2a987ddf0d9015c63358032f84a53f23cdc3", size = 5251406, upload-time = "2025-10-15T18:22:49.905Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/12/66/982ceebcdb13c97270ef7a56c3969635b4ee7cd45227fa707c94719229c5/pillow-12.0.0-cp313-cp313t-macosx_11_0_arm64.whl", hash = "sha256:f135c702ac42262573fe9714dfe99c944b4ba307af5eb507abef1667e2cbbced", size = 4653218, upload-time = "2025-10-15T18:22:51.587Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/16/b3/81e625524688c31859450119bf12674619429cab3119eec0e30a7a1029cb/pillow-12.0.0-cp313-cp313t-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:c85de1136429c524e55cfa4e033b4a7940ac5c8ee4d9401cc2d1bf48154bbc7b", size = 6266564, upload-time = "2025-10-15T18:22:53.215Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/98/59/dfb38f2a41240d2408096e1a76c671d0a105a4a8471b1871c6902719450c/pillow-12.0.0-cp313-cp313t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:38df9b4bfd3db902c9c2bd369bcacaf9d935b2fff73709429d95cc41554f7b3d", size = 8069260, upload-time = "2025-10-15T18:22:54.933Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/dc/3d/378dbea5cd1874b94c312425ca77b0f47776c78e0df2df751b820c8c1d6c/pillow-12.0.0-cp313-cp313t-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:7d87ef5795da03d742bf49439f9ca4d027cde49c82c5371ba52464aee266699a", size = 6379248, upload-time = "2025-10-15T18:22:56.605Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/84/b0/d525ef47d71590f1621510327acec75ae58c721dc071b17d8d652ca494d8/pillow-12.0.0-cp313-cp313t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:aff9e4d82d082ff9513bdd6acd4f5bd359f5b2c870907d2b0a9c5e10d40c88fe", size = 7066043, upload-time = "2025-10-15T18:22:58.53Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/61/2c/aced60e9cf9d0cde341d54bf7932c9ffc33ddb4a1595798b3a5150c7ec4e/pillow-12.0.0-cp313-cp313t-musllinux_1_2_aarch64.whl", hash = "sha256:8d8ca2b210ada074d57fcee40c30446c9562e542fc46aedc19baf758a93532ee", size = 6490915, upload-time = "2025-10-15T18:23:00.582Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ef/26/69dcb9b91f4e59f8f34b2332a4a0a951b44f547c4ed39d3e4dcfcff48f89/pillow-12.0.0-cp313-cp313t-musllinux_1_2_x86_64.whl", hash = "sha256:99a7f72fb6249302aa62245680754862a44179b545ded638cf1fef59befb57ef", size = 7157998, upload-time = "2025-10-15T18:23:02.627Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/61/2b/726235842220ca95fa441ddf55dd2382b52ab5b8d9c0596fe6b3f23dafe8/pillow-12.0.0-cp313-cp313t-win32.whl", hash = "sha256:4078242472387600b2ce8d93ade8899c12bf33fa89e55ec89fe126e9d6d5d9e9", size = 6306201, upload-time = "2025-10-15T18:23:04.709Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/c0/3d/2afaf4e840b2df71344ababf2f8edd75a705ce500e5dc1e7227808312ae1/pillow-12.0.0-cp313-cp313t-win_amd64.whl", hash = "sha256:2c54c1a783d6d60595d3514f0efe9b37c8808746a66920315bfd34a938d7994b", size = 7013165, upload-time = "2025-10-15T18:23:06.46Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/6f/75/3fa09aa5cf6ed04bee3fa575798ddf1ce0bace8edb47249c798077a81f7f/pillow-12.0.0-cp313-cp313t-win_arm64.whl", hash = "sha256:26d9f7d2b604cd23aba3e9faf795787456ac25634d82cd060556998e39c6fa47", size = 2437834, upload-time = "2025-10-15T18:23:08.194Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/54/2a/9a8c6ba2c2c07b71bec92cf63e03370ca5e5f5c5b119b742bcc0cde3f9c5/pillow-12.0.0-cp314-cp314-ios_13_0_arm64_iphoneos.whl", hash = "sha256:beeae3f27f62308f1ddbcfb0690bf44b10732f2ef43758f169d5e9303165d3f9", size = 4045531, upload-time = "2025-10-15T18:23:10.121Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/84/54/836fdbf1bfb3d66a59f0189ff0b9f5f666cee09c6188309300df04ad71fa/pillow-12.0.0-cp314-cp314-ios_13_0_arm64_iphonesimulator.whl", hash = "sha256:d4827615da15cd59784ce39d3388275ec093ae3ee8d7f0c089b76fa87af756c2", size = 4120554, upload-time = "2025-10-15T18:23:12.14Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/0d/cd/16aec9f0da4793e98e6b54778a5fbce4f375c6646fe662e80600b8797379/pillow-12.0.0-cp314-cp314-ios_13_0_x86_64_iphonesimulator.whl", hash = "sha256:3e42edad50b6909089750e65c91aa09aaf1e0a71310d383f11321b27c224ed8a", size = 3576812, upload-time = "2025-10-15T18:23:13.962Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/f6/b7/13957fda356dc46339298b351cae0d327704986337c3c69bb54628c88155/pillow-12.0.0-cp314-cp314-macosx_10_15_x86_64.whl", hash = "sha256:e5d8efac84c9afcb40914ab49ba063d94f5dbdf5066db4482c66a992f47a3a3b", size = 5252689, upload-time = "2025-10-15T18:23:15.562Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fc/f5/eae31a306341d8f331f43edb2e9122c7661b975433de5e447939ae61c5da/pillow-12.0.0-cp314-cp314-macosx_11_0_arm64.whl", hash = "sha256:266cd5f2b63ff316d5a1bba46268e603c9caf5606d44f38c2873c380950576ad", size = 4650186, upload-time = "2025-10-15T18:23:17.379Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/86/62/2a88339aa40c4c77e79108facbd307d6091e2c0eb5b8d3cf4977cfca2fe6/pillow-12.0.0-cp314-cp314-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:58eea5ebe51504057dd95c5b77d21700b77615ab0243d8152793dc00eb4faf01", size = 6230308, upload-time = "2025-10-15T18:23:18.971Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/c7/33/5425a8992bcb32d1cb9fa3dd39a89e613d09a22f2c8083b7bf43c455f760/pillow-12.0.0-cp314-cp314-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:f13711b1a5ba512d647a0e4ba79280d3a9a045aaf7e0cc6fbe96b91d4cdf6b0c", size = 8039222, upload-time = "2025-10-15T18:23:20.909Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/d8/61/3f5d3b35c5728f37953d3eec5b5f3e77111949523bd2dd7f31a851e50690/pillow-12.0.0-cp314-cp314-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:6846bd2d116ff42cba6b646edf5bf61d37e5cbd256425fa089fee4ff5c07a99e", size = 6346657, upload-time = "2025-10-15T18:23:23.077Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/3a/be/ee90a3d79271227e0f0a33c453531efd6ed14b2e708596ba5dd9be948da3/pillow-12.0.0-cp314-cp314-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:c98fa880d695de164b4135a52fd2e9cd7b7c90a9d8ac5e9e443a24a95ef9248e", size = 7038482, upload-time = "2025-10-15T18:23:25.005Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/44/34/a16b6a4d1ad727de390e9bd9f19f5f669e079e5826ec0f329010ddea492f/pillow-12.0.0-cp314-cp314-musllinux_1_2_aarch64.whl", hash = "sha256:fa3ed2a29a9e9d2d488b4da81dcb54720ac3104a20bf0bd273f1e4648aff5af9", size = 6461416, upload-time = "2025-10-15T18:23:27.009Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b6/39/1aa5850d2ade7d7ba9f54e4e4c17077244ff7a2d9e25998c38a29749eb3f/pillow-12.0.0-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:d034140032870024e6b9892c692fe2968493790dd57208b2c37e3fb35f6df3ab", size = 7131584, upload-time = "2025-10-15T18:23:29.752Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/bf/db/4fae862f8fad0167073a7733973bfa955f47e2cac3dc3e3e6257d10fab4a/pillow-12.0.0-cp314-cp314-win32.whl", hash = "sha256:1b1b133e6e16105f524a8dec491e0586d072948ce15c9b914e41cdadd209052b", size = 6400621, upload-time = "2025-10-15T18:23:32.06Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/2b/24/b350c31543fb0107ab2599464d7e28e6f856027aadda995022e695313d94/pillow-12.0.0-cp314-cp314-win_amd64.whl", hash = "sha256:8dc232e39d409036af549c86f24aed8273a40ffa459981146829a324e0848b4b", size = 7142916, upload-time = "2025-10-15T18:23:34.71Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/0f/9b/0ba5a6fd9351793996ef7487c4fdbde8d3f5f75dbedc093bb598648fddf0/pillow-12.0.0-cp314-cp314-win_arm64.whl", hash = "sha256:d52610d51e265a51518692045e372a4c363056130d922a7351429ac9f27e70b0", size = 2523836, upload-time = "2025-10-15T18:23:36.967Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/f5/7a/ceee0840aebc579af529b523d530840338ecf63992395842e54edc805987/pillow-12.0.0-cp314-cp314t-macosx_10_15_x86_64.whl", hash = "sha256:1979f4566bb96c1e50a62d9831e2ea2d1211761e5662afc545fa766f996632f6", size = 5255092, upload-time = "2025-10-15T18:23:38.573Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/44/76/20776057b4bfd1aef4eeca992ebde0f53a4dce874f3ae693d0ec90a4f79b/pillow-12.0.0-cp314-cp314t-macosx_11_0_arm64.whl", hash = "sha256:b2e4b27a6e15b04832fe9bf292b94b5ca156016bbc1ea9c2c20098a0320d6cf6", size = 4653158, upload-time = "2025-10-15T18:23:40.238Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/82/3f/d9ff92ace07be8836b4e7e87e6a4c7a8318d47c2f1463ffcf121fc57d9cb/pillow-12.0.0-cp314-cp314t-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:fb3096c30df99fd01c7bf8e544f392103d0795b9f98ba71a8054bcbf56b255f1", size = 6267882, upload-time = "2025-10-15T18:23:42.434Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/9f/7a/4f7ff87f00d3ad33ba21af78bfcd2f032107710baf8280e3722ceec28cda/pillow-12.0.0-cp314-cp314t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:7438839e9e053ef79f7112c881cef684013855016f928b168b81ed5835f3e75e", size = 8071001, upload-time = "2025-10-15T18:23:44.29Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/75/87/fcea108944a52dad8cca0715ae6247e271eb80459364a98518f1e4f480c1/pillow-12.0.0-cp314-cp314t-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:5d5c411a8eaa2299322b647cd932586b1427367fd3184ffbb8f7a219ea2041ca", size = 6380146, upload-time = "2025-10-15T18:23:46.065Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/91/52/0d31b5e571ef5fd111d2978b84603fce26aba1b6092f28e941cb46570745/pillow-12.0.0-cp314-cp314t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:d7e091d464ac59d2c7ad8e7e08105eaf9dafbc3883fd7265ffccc2baad6ac925", size = 7067344, upload-time = "2025-10-15T18:23:47.898Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/7b/f4/2dd3d721f875f928d48e83bb30a434dee75a2531bca839bb996bb0aa5a91/pillow-12.0.0-cp314-cp314t-musllinux_1_2_aarch64.whl", hash = "sha256:792a2c0be4dcc18af9d4a2dfd8a11a17d5e25274a1062b0ec1c2d79c76f3e7f8", size = 6491864, upload-time = "2025-10-15T18:23:49.607Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/30/4b/667dfcf3d61fc309ba5a15b141845cece5915e39b99c1ceab0f34bf1d124/pillow-12.0.0-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:afbefa430092f71a9593a99ab6a4e7538bc9eabbf7bf94f91510d3503943edc4", size = 7158911, upload-time = "2025-10-15T18:23:51.351Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/a2/2f/16cabcc6426c32218ace36bf0d55955e813f2958afddbf1d391849fee9d1/pillow-12.0.0-cp314-cp314t-win32.whl", hash = "sha256:3830c769decf88f1289680a59d4f4c46c72573446352e2befec9a8512104fa52", size = 6408045, upload-time = "2025-10-15T18:23:53.177Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/35/73/e29aa0c9c666cf787628d3f0dcf379f4791fba79f4936d02f8b37165bdf8/pillow-12.0.0-cp314-cp314t-win_amd64.whl", hash = "sha256:905b0365b210c73afb0ebe9101a32572152dfd1c144c7e28968a331b9217b94a", size = 7148282, upload-time = "2025-10-15T18:23:55.316Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/c1/70/6b41bdcddf541b437bbb9f47f94d2db5d9ddef6c37ccab8c9107743748a4/pillow-12.0.0-cp314-cp314t-win_arm64.whl", hash = "sha256:99353a06902c2e43b43e8ff74ee65a7d90307d82370604746738a1e0661ccca7", size = 2525630, upload-time = "2025-10-15T18:23:57.149Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pydantic"
|
||||||
|
version = "2.12.4"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "annotated-types" },
|
||||||
|
{ name = "pydantic-core" },
|
||||||
|
{ name = "typing-extensions" },
|
||||||
|
{ name = "typing-inspection" },
|
||||||
|
]
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/96/ad/a17bc283d7d81837c061c49e3eaa27a45991759a1b7eae1031921c6bd924/pydantic-2.12.4.tar.gz", hash = "sha256:0f8cb9555000a4b5b617f66bfd2566264c4984b27589d3b845685983e8ea85ac", size = 821038, upload-time = "2025-11-05T10:50:08.59Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/82/2f/e68750da9b04856e2a7ec56fc6f034a5a79775e9b9a81882252789873798/pydantic-2.12.4-py3-none-any.whl", hash = "sha256:92d3d202a745d46f9be6df459ac5a064fdaa3c1c4cd8adcfa332ccf3c05f871e", size = 463400, upload-time = "2025-11-05T10:50:06.732Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pydantic-core"
|
||||||
|
version = "2.41.5"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "typing-extensions" },
|
||||||
|
]
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/71/70/23b021c950c2addd24ec408e9ab05d59b035b39d97cdc1130e1bce647bb6/pydantic_core-2.41.5.tar.gz", hash = "sha256:08daa51ea16ad373ffd5e7606252cc32f07bc72b28284b6bc9c6df804816476e", size = 460952, upload-time = "2025-11-04T13:43:49.098Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/87/06/8806241ff1f70d9939f9af039c6c35f2360cf16e93c2ca76f184e76b1564/pydantic_core-2.41.5-cp313-cp313-macosx_10_12_x86_64.whl", hash = "sha256:941103c9be18ac8daf7b7adca8228f8ed6bb7a1849020f643b3a14d15b1924d9", size = 2120403, upload-time = "2025-11-04T13:40:25.248Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/94/02/abfa0e0bda67faa65fef1c84971c7e45928e108fe24333c81f3bfe35d5f5/pydantic_core-2.41.5-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:112e305c3314f40c93998e567879e887a3160bb8689ef3d2c04b6cc62c33ac34", size = 1896206, upload-time = "2025-11-04T13:40:27.099Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/15/df/a4c740c0943e93e6500f9eb23f4ca7ec9bf71b19e608ae5b579678c8d02f/pydantic_core-2.41.5-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0cbaad15cb0c90aa221d43c00e77bb33c93e8d36e0bf74760cd00e732d10a6a0", size = 1919307, upload-time = "2025-11-04T13:40:29.806Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/9a/e3/6324802931ae1d123528988e0e86587c2072ac2e5394b4bc2bc34b61ff6e/pydantic_core-2.41.5-cp313-cp313-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:03ca43e12fab6023fc79d28ca6b39b05f794ad08ec2feccc59a339b02f2b3d33", size = 2063258, upload-time = "2025-11-04T13:40:33.544Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/c9/d4/2230d7151d4957dd79c3044ea26346c148c98fbf0ee6ebd41056f2d62ab5/pydantic_core-2.41.5-cp313-cp313-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:dc799088c08fa04e43144b164feb0c13f9a0bc40503f8df3e9fde58a3c0c101e", size = 2214917, upload-time = "2025-11-04T13:40:35.479Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e6/9f/eaac5df17a3672fef0081b6c1bb0b82b33ee89aa5cec0d7b05f52fd4a1fa/pydantic_core-2.41.5-cp313-cp313-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:97aeba56665b4c3235a0e52b2c2f5ae9cd071b8a8310ad27bddb3f7fb30e9aa2", size = 2332186, upload-time = "2025-11-04T13:40:37.436Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/cf/4e/35a80cae583a37cf15604b44240e45c05e04e86f9cfd766623149297e971/pydantic_core-2.41.5-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:406bf18d345822d6c21366031003612b9c77b3e29ffdb0f612367352aab7d586", size = 2073164, upload-time = "2025-11-04T13:40:40.289Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/bf/e3/f6e262673c6140dd3305d144d032f7bd5f7497d3871c1428521f19f9efa2/pydantic_core-2.41.5-cp313-cp313-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:b93590ae81f7010dbe380cdeab6f515902ebcbefe0b9327cc4804d74e93ae69d", size = 2179146, upload-time = "2025-11-04T13:40:42.809Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/75/c7/20bd7fc05f0c6ea2056a4565c6f36f8968c0924f19b7d97bbfea55780e73/pydantic_core-2.41.5-cp313-cp313-musllinux_1_1_aarch64.whl", hash = "sha256:01a3d0ab748ee531f4ea6c3e48ad9dac84ddba4b0d82291f87248f2f9de8d740", size = 2137788, upload-time = "2025-11-04T13:40:44.752Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/3a/8d/34318ef985c45196e004bc46c6eab2eda437e744c124ef0dbe1ff2c9d06b/pydantic_core-2.41.5-cp313-cp313-musllinux_1_1_armv7l.whl", hash = "sha256:6561e94ba9dacc9c61bce40e2d6bdc3bfaa0259d3ff36ace3b1e6901936d2e3e", size = 2340133, upload-time = "2025-11-04T13:40:46.66Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/9c/59/013626bf8c78a5a5d9350d12e7697d3d4de951a75565496abd40ccd46bee/pydantic_core-2.41.5-cp313-cp313-musllinux_1_1_x86_64.whl", hash = "sha256:915c3d10f81bec3a74fbd4faebe8391013ba61e5a1a8d48c4455b923bdda7858", size = 2324852, upload-time = "2025-11-04T13:40:48.575Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/1a/d9/c248c103856f807ef70c18a4f986693a46a8ffe1602e5d361485da502d20/pydantic_core-2.41.5-cp313-cp313-win32.whl", hash = "sha256:650ae77860b45cfa6e2cdafc42618ceafab3a2d9a3811fcfbd3bbf8ac3c40d36", size = 1994679, upload-time = "2025-11-04T13:40:50.619Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/9e/8b/341991b158ddab181cff136acd2552c9f35bd30380422a639c0671e99a91/pydantic_core-2.41.5-cp313-cp313-win_amd64.whl", hash = "sha256:79ec52ec461e99e13791ec6508c722742ad745571f234ea6255bed38c6480f11", size = 2019766, upload-time = "2025-11-04T13:40:52.631Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/73/7d/f2f9db34af103bea3e09735bb40b021788a5e834c81eedb541991badf8f5/pydantic_core-2.41.5-cp313-cp313-win_arm64.whl", hash = "sha256:3f84d5c1b4ab906093bdc1ff10484838aca54ef08de4afa9de0f5f14d69639cd", size = 1981005, upload-time = "2025-11-04T13:40:54.734Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ea/28/46b7c5c9635ae96ea0fbb779e271a38129df2550f763937659ee6c5dbc65/pydantic_core-2.41.5-cp314-cp314-macosx_10_12_x86_64.whl", hash = "sha256:3f37a19d7ebcdd20b96485056ba9e8b304e27d9904d233d7b1015db320e51f0a", size = 2119622, upload-time = "2025-11-04T13:40:56.68Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/74/1a/145646e5687e8d9a1e8d09acb278c8535ebe9e972e1f162ed338a622f193/pydantic_core-2.41.5-cp314-cp314-macosx_11_0_arm64.whl", hash = "sha256:1d1d9764366c73f996edd17abb6d9d7649a7eb690006ab6adbda117717099b14", size = 1891725, upload-time = "2025-11-04T13:40:58.807Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/23/04/e89c29e267b8060b40dca97bfc64a19b2a3cf99018167ea1677d96368273/pydantic_core-2.41.5-cp314-cp314-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:25e1c2af0fce638d5f1988b686f3b3ea8cd7de5f244ca147c777769e798a9cd1", size = 1915040, upload-time = "2025-11-04T13:41:00.853Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/84/a3/15a82ac7bd97992a82257f777b3583d3e84bdb06ba6858f745daa2ec8a85/pydantic_core-2.41.5-cp314-cp314-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:506d766a8727beef16b7adaeb8ee6217c64fc813646b424d0804d67c16eddb66", size = 2063691, upload-time = "2025-11-04T13:41:03.504Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/74/9b/0046701313c6ef08c0c1cf0e028c67c770a4e1275ca73131563c5f2a310a/pydantic_core-2.41.5-cp314-cp314-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:4819fa52133c9aa3c387b3328f25c1facc356491e6135b459f1de698ff64d869", size = 2213897, upload-time = "2025-11-04T13:41:05.804Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/8a/cd/6bac76ecd1b27e75a95ca3a9a559c643b3afcd2dd62086d4b7a32a18b169/pydantic_core-2.41.5-cp314-cp314-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:2b761d210c9ea91feda40d25b4efe82a1707da2ef62901466a42492c028553a2", size = 2333302, upload-time = "2025-11-04T13:41:07.809Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/4c/d2/ef2074dc020dd6e109611a8be4449b98cd25e1b9b8a303c2f0fca2f2bcf7/pydantic_core-2.41.5-cp314-cp314-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:22f0fb8c1c583a3b6f24df2470833b40207e907b90c928cc8d3594b76f874375", size = 2064877, upload-time = "2025-11-04T13:41:09.827Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/18/66/e9db17a9a763d72f03de903883c057b2592c09509ccfe468187f2a2eef29/pydantic_core-2.41.5-cp314-cp314-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:2782c870e99878c634505236d81e5443092fba820f0373997ff75f90f68cd553", size = 2180680, upload-time = "2025-11-04T13:41:12.379Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/d3/9e/3ce66cebb929f3ced22be85d4c2399b8e85b622db77dad36b73c5387f8f8/pydantic_core-2.41.5-cp314-cp314-musllinux_1_1_aarch64.whl", hash = "sha256:0177272f88ab8312479336e1d777f6b124537d47f2123f89cb37e0accea97f90", size = 2138960, upload-time = "2025-11-04T13:41:14.627Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/a6/62/205a998f4327d2079326b01abee48e502ea739d174f0a89295c481a2272e/pydantic_core-2.41.5-cp314-cp314-musllinux_1_1_armv7l.whl", hash = "sha256:63510af5e38f8955b8ee5687740d6ebf7c2a0886d15a6d65c32814613681bc07", size = 2339102, upload-time = "2025-11-04T13:41:16.868Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/3c/0d/f05e79471e889d74d3d88f5bd20d0ed189ad94c2423d81ff8d0000aab4ff/pydantic_core-2.41.5-cp314-cp314-musllinux_1_1_x86_64.whl", hash = "sha256:e56ba91f47764cc14f1daacd723e3e82d1a89d783f0f5afe9c364b8bb491ccdb", size = 2326039, upload-time = "2025-11-04T13:41:18.934Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ec/e1/e08a6208bb100da7e0c4b288eed624a703f4d129bde2da475721a80cab32/pydantic_core-2.41.5-cp314-cp314-win32.whl", hash = "sha256:aec5cf2fd867b4ff45b9959f8b20ea3993fc93e63c7363fe6851424c8a7e7c23", size = 1995126, upload-time = "2025-11-04T13:41:21.418Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/48/5d/56ba7b24e9557f99c9237e29f5c09913c81eeb2f3217e40e922353668092/pydantic_core-2.41.5-cp314-cp314-win_amd64.whl", hash = "sha256:8e7c86f27c585ef37c35e56a96363ab8de4e549a95512445b85c96d3e2f7c1bf", size = 2015489, upload-time = "2025-11-04T13:41:24.076Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/4e/bb/f7a190991ec9e3e0ba22e4993d8755bbc4a32925c0b5b42775c03e8148f9/pydantic_core-2.41.5-cp314-cp314-win_arm64.whl", hash = "sha256:e672ba74fbc2dc8eea59fb6d4aed6845e6905fc2a8afe93175d94a83ba2a01a0", size = 1977288, upload-time = "2025-11-04T13:41:26.33Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/92/ed/77542d0c51538e32e15afe7899d79efce4b81eee631d99850edc2f5e9349/pydantic_core-2.41.5-cp314-cp314t-macosx_10_12_x86_64.whl", hash = "sha256:8566def80554c3faa0e65ac30ab0932b9e3a5cd7f8323764303d468e5c37595a", size = 2120255, upload-time = "2025-11-04T13:41:28.569Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/bb/3d/6913dde84d5be21e284439676168b28d8bbba5600d838b9dca99de0fad71/pydantic_core-2.41.5-cp314-cp314t-macosx_11_0_arm64.whl", hash = "sha256:b80aa5095cd3109962a298ce14110ae16b8c1aece8b72f9dafe81cf597ad80b3", size = 1863760, upload-time = "2025-11-04T13:41:31.055Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/5a/f0/e5e6b99d4191da102f2b0eb9687aaa7f5bea5d9964071a84effc3e40f997/pydantic_core-2.41.5-cp314-cp314t-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3006c3dd9ba34b0c094c544c6006cc79e87d8612999f1a5d43b769b89181f23c", size = 1878092, upload-time = "2025-11-04T13:41:33.21Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/71/48/36fb760642d568925953bcc8116455513d6e34c4beaa37544118c36aba6d/pydantic_core-2.41.5-cp314-cp314t-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:72f6c8b11857a856bcfa48c86f5368439f74453563f951e473514579d44aa612", size = 2053385, upload-time = "2025-11-04T13:41:35.508Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/20/25/92dc684dd8eb75a234bc1c764b4210cf2646479d54b47bf46061657292a8/pydantic_core-2.41.5-cp314-cp314t-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:5cb1b2f9742240e4bb26b652a5aeb840aa4b417c7748b6f8387927bc6e45e40d", size = 2218832, upload-time = "2025-11-04T13:41:37.732Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e2/09/f53e0b05023d3e30357d82eb35835d0f6340ca344720a4599cd663dca599/pydantic_core-2.41.5-cp314-cp314t-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:bd3d54f38609ff308209bd43acea66061494157703364ae40c951f83ba99a1a9", size = 2327585, upload-time = "2025-11-04T13:41:40Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/aa/4e/2ae1aa85d6af35a39b236b1b1641de73f5a6ac4d5a7509f77b814885760c/pydantic_core-2.41.5-cp314-cp314t-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2ff4321e56e879ee8d2a879501c8e469414d948f4aba74a2d4593184eb326660", size = 2041078, upload-time = "2025-11-04T13:41:42.323Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/cd/13/2e215f17f0ef326fc72afe94776edb77525142c693767fc347ed6288728d/pydantic_core-2.41.5-cp314-cp314t-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:d0d2568a8c11bf8225044aa94409e21da0cb09dcdafe9ecd10250b2baad531a9", size = 2173914, upload-time = "2025-11-04T13:41:45.221Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/02/7a/f999a6dcbcd0e5660bc348a3991c8915ce6599f4f2c6ac22f01d7a10816c/pydantic_core-2.41.5-cp314-cp314t-musllinux_1_1_aarch64.whl", hash = "sha256:a39455728aabd58ceabb03c90e12f71fd30fa69615760a075b9fec596456ccc3", size = 2129560, upload-time = "2025-11-04T13:41:47.474Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/3a/b1/6c990ac65e3b4c079a4fb9f5b05f5b013afa0f4ed6780a3dd236d2cbdc64/pydantic_core-2.41.5-cp314-cp314t-musllinux_1_1_armv7l.whl", hash = "sha256:239edca560d05757817c13dc17c50766136d21f7cd0fac50295499ae24f90fdf", size = 2329244, upload-time = "2025-11-04T13:41:49.992Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/d9/02/3c562f3a51afd4d88fff8dffb1771b30cfdfd79befd9883ee094f5b6c0d8/pydantic_core-2.41.5-cp314-cp314t-musllinux_1_1_x86_64.whl", hash = "sha256:2a5e06546e19f24c6a96a129142a75cee553cc018ffee48a460059b1185f4470", size = 2331955, upload-time = "2025-11-04T13:41:54.079Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/5c/96/5fb7d8c3c17bc8c62fdb031c47d77a1af698f1d7a406b0f79aaa1338f9ad/pydantic_core-2.41.5-cp314-cp314t-win32.whl", hash = "sha256:b4ececa40ac28afa90871c2cc2b9ffd2ff0bf749380fbdf57d165fd23da353aa", size = 1988906, upload-time = "2025-11-04T13:41:56.606Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/22/ed/182129d83032702912c2e2d8bbe33c036f342cc735737064668585dac28f/pydantic_core-2.41.5-cp314-cp314t-win_amd64.whl", hash = "sha256:80aa89cad80b32a912a65332f64a4450ed00966111b6615ca6816153d3585a8c", size = 1981607, upload-time = "2025-11-04T13:41:58.889Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/9f/ed/068e41660b832bb0b1aa5b58011dea2a3fe0ba7861ff38c4d4904c1c1a99/pydantic_core-2.41.5-cp314-cp314t-win_arm64.whl", hash = "sha256:35b44f37a3199f771c3eaa53051bc8a70cd7b54f333531c59e29fd4db5d15008", size = 1974769, upload-time = "2025-11-04T13:42:01.186Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pyparsing"
|
||||||
|
version = "3.2.5"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/f2/a5/181488fc2b9d093e3972d2a472855aae8a03f000592dbfce716a512b3359/pyparsing-3.2.5.tar.gz", hash = "sha256:2df8d5b7b2802ef88e8d016a2eb9c7aeaa923529cd251ed0fe4608275d4105b6", size = 1099274, upload-time = "2025-09-21T04:11:06.277Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/10/5e/1aa9a93198c6b64513c9d7752de7422c06402de6600a8767da1524f9570b/pyparsing-3.2.5-py3-none-any.whl", hash = "sha256:e38a4f02064cf41fe6593d328d0512495ad1f3d8a91c4f73fc401b3079a59a5e", size = 113890, upload-time = "2025-09-21T04:11:04.117Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pyqtgraph"
|
||||||
|
version = "0.14.0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "colorama" },
|
||||||
|
{ name = "numpy" },
|
||||||
|
]
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/32/36/4c242f81fdcbfa4fb62a5645f6af79191f4097a0577bd5460c24f19cc4ef/pyqtgraph-0.14.0-py3-none-any.whl", hash = "sha256:7abb7c3e17362add64f8711b474dffac5e7b0e9245abdf992e9a44119b7aa4f5", size = 1924755, upload-time = "2025-11-16T19:43:22.251Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pyside6"
|
||||||
|
version = "6.10.0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "pyside6-addons" },
|
||||||
|
{ name = "pyside6-essentials" },
|
||||||
|
{ name = "shiboken6" },
|
||||||
|
]
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e6/98/84b16f78b5d92dd234fb1eb9890a350a5b0c83d985bb8c44a92f813a2d02/pyside6-6.10.0-cp39-abi3-macosx_13_0_universal2.whl", hash = "sha256:c2cbc5dc2a164e3c7c51b3435e24203e90e5edd518c865466afccbd2e5872bb0", size = 558115, upload-time = "2025-10-08T09:47:09.246Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/4e/76/0961c8c5653ecb60a6881b649dcb6b71a6be5bd1c8d441ecc48ac7f50b1a/pyside6-6.10.0-cp39-abi3-manylinux_2_34_x86_64.whl", hash = "sha256:ae8c3c8339cd7c3c9faa7cc5c52670dcc8662ccf4b63a6fed61c6345b90c4c01", size = 557762, upload-time = "2025-10-08T09:47:11.819Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/c8/73/6187502fff8b6599443d15c46dd900b2ded24be5aacb2becce33f6faf566/pyside6-6.10.0-cp39-abi3-manylinux_2_39_aarch64.whl", hash = "sha256:9f402f883e640048fab246d36e298a5e16df9b18ba2e8c519877e472d3602820", size = 558299, upload-time = "2025-10-08T09:47:14.255Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/43/67/94794ebaf198bbdb35cb77f19f38370f9b323b036ab149874bc33c38faab/pyside6-6.10.0-cp39-abi3-win_amd64.whl", hash = "sha256:70a8bcc73ea8d6baab70bba311eac77b9a1d31f658d0b418e15eb6ea36c97e6f", size = 564367, upload-time = "2025-10-08T09:47:16.287Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/1d/cc/552331d413c1b933d54ed45e33cc7ff29d0b239677975fe2528e7ac8bfbc/pyside6-6.10.0-cp39-abi3-win_arm64.whl", hash = "sha256:4b709bdeeb89d386059343a5a706fc185cee37b517bda44c7d6b64d5fdaf3339", size = 548826, upload-time = "2025-10-08T09:47:18.399Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pyside6-addons"
|
||||||
|
version = "6.10.0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "pyside6-essentials" },
|
||||||
|
{ name = "shiboken6" },
|
||||||
|
]
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/47/23/9fbdec2ce16244ac3fe28e6d44c39c70465c93a03325939a792fd00fde7f/pyside6_addons-6.10.0-cp39-abi3-macosx_13_0_universal2.whl", hash = "sha256:88e61e21ee4643cdd9efb39ec52f4dc1ac74c0b45c5b7fa453d03c094f0a8a5c", size = 322248256, upload-time = "2025-10-08T09:47:37.844Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b7/b8/d129210f2c7366b4e1bf5bb6230be42052b29e8ba1b1d7db6ef333cf5a39/pyside6_addons-6.10.0-cp39-abi3-manylinux_2_34_x86_64.whl", hash = "sha256:08d4ed46c4c9a353a9eb84134678f8fdd4ce17fb8cce2b3686172a7575025464", size = 170238987, upload-time = "2025-10-08T09:47:51.446Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/cf/ae/ede1edd009395092219f3437d2ee59f9ba93739c28c040542ed47c6cc831/pyside6_addons-6.10.0-cp39-abi3-manylinux_2_39_aarch64.whl", hash = "sha256:15d32229d681be0bba1b936c4a300da43d01e1917ada5b57f9e03a387c245ab0", size = 165939425, upload-time = "2025-10-08T09:48:02.073Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/7d/5d/a3c32f85ac7f905c95679967c0ddda0ba043c273b75623cc90d8185064e4/pyside6_addons-6.10.0-cp39-abi3-win_amd64.whl", hash = "sha256:99d93a32c17c5f6d797c3b90dd58f2a8bae13abde81e85802c34ceafaee11859", size = 164814172, upload-time = "2025-10-08T09:48:12.891Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/a3/2a/4ff71b09571202c8e1320c45276fc1d0cd81ee53107dfc17bb22d4243f88/pyside6_addons-6.10.0-cp39-abi3-win_arm64.whl", hash = "sha256:92536427413f3b6557cf53f1a515cd766725ee46a170aff57ad2ff1dfce0ffb1", size = 34104251, upload-time = "2025-10-08T09:48:18.287Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pyside6-essentials"
|
||||||
|
version = "6.10.0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "shiboken6" },
|
||||||
|
]
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e5/55/bad02ab890c8b8101abef0db4a2e5304be78a69e23a438e4d8555b664467/pyside6_essentials-6.10.0-cp39-abi3-macosx_13_0_universal2.whl", hash = "sha256:003e871effe1f3e5b876bde715c15a780d876682005a6e989d89f48b8b93e93a", size = 105034090, upload-time = "2025-10-08T09:48:24.944Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/5c/75/e17efc7eb900993e0e3925885635c6cf373c817196f09bcbcc102b00ac94/pyside6_essentials-6.10.0-cp39-abi3-manylinux_2_34_x86_64.whl", hash = "sha256:1d5e013a8698e37ab8ef360e6960794eb5ef20832a8d562e649b8c5a0574b2d8", size = 76362150, upload-time = "2025-10-08T09:48:31.849Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/06/62/fbd1e81caafcda97b147c03f5b06cfaadd8da5fa8298f527d2ec648fa5b7/pyside6_essentials-6.10.0-cp39-abi3-manylinux_2_39_aarch64.whl", hash = "sha256:b1dd0864f0577a448fb44426b91cafff7ee7cccd1782ba66491e1c668033f998", size = 75454169, upload-time = "2025-10-08T09:48:38.21Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/bb/3a/d8211d17e6ca70f641c6ebd309f08ef18930acda60e74082c75875a274da/pyside6_essentials-6.10.0-cp39-abi3-win_amd64.whl", hash = "sha256:fc167eb211dd1580e20ba90d299e74898e7a5a1306d832421e879641fc03b6fe", size = 74361794, upload-time = "2025-10-08T09:48:44.335Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/61/e9/0e22e3c10325c4ff09447fadb43f7962afb82cef0b65358f5704251c6b32/pyside6_essentials-6.10.0-cp39-abi3-win_arm64.whl", hash = "sha256:6dd0936394cb14da2fd8e869899f5e0925a738b1c8d74c2f22503720ea363fb1", size = 55099467, upload-time = "2025-10-08T09:48:50.902Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "python-dateutil"
|
||||||
|
version = "2.9.0.post0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "six" },
|
||||||
|
]
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/66/c0/0c8b6ad9f17a802ee498c46e004a0eb49bc148f2fd230864601a86dcf6db/python-dateutil-2.9.0.post0.tar.gz", hash = "sha256:37dd54208da7e1cd875388217d5e00ebd4179249f90fb72437e91a35459a0ad3", size = 342432, upload-time = "2024-03-01T18:36:20.211Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ec/57/56b9bcc3c9c6a792fcbaf139543cee77261f3651ca9da0c93f5c1221264b/python_dateutil-2.9.0.post0-py2.py3-none-any.whl", hash = "sha256:a8b2bc7bffae282281c8140a97d3aa9c14da0b136dfe83f850eea9a5f7470427", size = 229892, upload-time = "2024-03-01T18:36:18.57Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "scipy"
|
||||||
|
version = "1.16.3"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "numpy" },
|
||||||
|
]
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/0a/ca/d8ace4f98322d01abcd52d381134344bf7b431eba7ed8b42bdea5a3c2ac9/scipy-1.16.3.tar.gz", hash = "sha256:01e87659402762f43bd2fee13370553a17ada367d42e7487800bf2916535aecb", size = 30597883, upload-time = "2025-10-28T17:38:54.068Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/72/f1/57e8327ab1508272029e27eeef34f2302ffc156b69e7e233e906c2a5c379/scipy-1.16.3-cp313-cp313-macosx_10_14_x86_64.whl", hash = "sha256:d2ec56337675e61b312179a1ad124f5f570c00f920cc75e1000025451b88241c", size = 36617856, upload-time = "2025-10-28T17:33:31.375Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/44/13/7e63cfba8a7452eb756306aa2fd9b37a29a323b672b964b4fdeded9a3f21/scipy-1.16.3-cp313-cp313-macosx_12_0_arm64.whl", hash = "sha256:16b8bc35a4cc24db80a0ec836a9286d0e31b2503cb2fd7ff7fb0e0374a97081d", size = 28874306, upload-time = "2025-10-28T17:33:36.516Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/15/65/3a9400efd0228a176e6ec3454b1fa998fbbb5a8defa1672c3f65706987db/scipy-1.16.3-cp313-cp313-macosx_14_0_arm64.whl", hash = "sha256:5803c5fadd29de0cf27fa08ccbfe7a9e5d741bf63e4ab1085437266f12460ff9", size = 20865371, upload-time = "2025-10-28T17:33:42.094Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/33/d7/eda09adf009a9fb81827194d4dd02d2e4bc752cef16737cc4ef065234031/scipy-1.16.3-cp313-cp313-macosx_14_0_x86_64.whl", hash = "sha256:b81c27fc41954319a943d43b20e07c40bdcd3ff7cf013f4fb86286faefe546c4", size = 23524877, upload-time = "2025-10-28T17:33:48.483Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/7d/6b/3f911e1ebc364cb81320223a3422aab7d26c9c7973109a9cd0f27c64c6c0/scipy-1.16.3-cp313-cp313-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:0c3b4dd3d9b08dbce0f3440032c52e9e2ab9f96ade2d3943313dfe51a7056959", size = 33342103, upload-time = "2025-10-28T17:33:56.495Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/21/f6/4bfb5695d8941e5c570a04d9fcd0d36bce7511b7d78e6e75c8f9791f82d0/scipy-1.16.3-cp313-cp313-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:7dc1360c06535ea6116a2220f760ae572db9f661aba2d88074fe30ec2aa1ff88", size = 35697297, upload-time = "2025-10-28T17:34:04.722Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/04/e1/6496dadbc80d8d896ff72511ecfe2316b50313bfc3ebf07a3f580f08bd8c/scipy-1.16.3-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:663b8d66a8748051c3ee9c96465fb417509315b99c71550fda2591d7dd634234", size = 36021756, upload-time = "2025-10-28T17:34:13.482Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fe/bd/a8c7799e0136b987bda3e1b23d155bcb31aec68a4a472554df5f0937eef7/scipy-1.16.3-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:eab43fae33a0c39006a88096cd7b4f4ef545ea0447d250d5ac18202d40b6611d", size = 38696566, upload-time = "2025-10-28T17:34:22.384Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/cd/01/1204382461fcbfeb05b6161b594f4007e78b6eba9b375382f79153172b4d/scipy-1.16.3-cp313-cp313-win_amd64.whl", hash = "sha256:062246acacbe9f8210de8e751b16fc37458213f124bef161a5a02c7a39284304", size = 38529877, upload-time = "2025-10-28T17:35:51.076Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/7f/14/9d9fbcaa1260a94f4bb5b64ba9213ceb5d03cd88841fe9fd1ffd47a45b73/scipy-1.16.3-cp313-cp313-win_arm64.whl", hash = "sha256:50a3dbf286dbc7d84f176f9a1574c705f277cb6565069f88f60db9eafdbe3ee2", size = 25455366, upload-time = "2025-10-28T17:35:59.014Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/e2/a3/9ec205bd49f42d45d77f1730dbad9ccf146244c1647605cf834b3a8c4f36/scipy-1.16.3-cp313-cp313t-macosx_10_14_x86_64.whl", hash = "sha256:fb4b29f4cf8cc5a8d628bc8d8e26d12d7278cd1f219f22698a378c3d67db5e4b", size = 37027931, upload-time = "2025-10-28T17:34:31.451Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/25/06/ca9fd1f3a4589cbd825b1447e5db3a8ebb969c1eaf22c8579bd286f51b6d/scipy-1.16.3-cp313-cp313t-macosx_12_0_arm64.whl", hash = "sha256:8d09d72dc92742988b0e7750bddb8060b0c7079606c0d24a8cc8e9c9c11f9079", size = 29400081, upload-time = "2025-10-28T17:34:39.087Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/6a/56/933e68210d92657d93fb0e381683bc0e53a965048d7358ff5fbf9e6a1b17/scipy-1.16.3-cp313-cp313t-macosx_14_0_arm64.whl", hash = "sha256:03192a35e661470197556de24e7cb1330d84b35b94ead65c46ad6f16f6b28f2a", size = 21391244, upload-time = "2025-10-28T17:34:45.234Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/a8/7e/779845db03dc1418e215726329674b40576879b91814568757ff0014ad65/scipy-1.16.3-cp313-cp313t-macosx_14_0_x86_64.whl", hash = "sha256:57d01cb6f85e34f0946b33caa66e892aae072b64b034183f3d87c4025802a119", size = 23929753, upload-time = "2025-10-28T17:34:51.793Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/4c/4b/f756cf8161d5365dcdef9e5f460ab226c068211030a175d2fc7f3f41ca64/scipy-1.16.3-cp313-cp313t-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:96491a6a54e995f00a28a3c3badfff58fd093bf26cd5fb34a2188c8c756a3a2c", size = 33496912, upload-time = "2025-10-28T17:34:59.8Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/09/b5/222b1e49a58668f23839ca1542a6322bb095ab8d6590d4f71723869a6c2c/scipy-1.16.3-cp313-cp313t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:cd13e354df9938598af2be05822c323e97132d5e6306b83a3b4ee6724c6e522e", size = 35802371, upload-time = "2025-10-28T17:35:08.173Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/c1/8d/5964ef68bb31829bde27611f8c9deeac13764589fe74a75390242b64ca44/scipy-1.16.3-cp313-cp313t-musllinux_1_2_aarch64.whl", hash = "sha256:63d3cdacb8a824a295191a723ee5e4ea7768ca5ca5f2838532d9f2e2b3ce2135", size = 36190477, upload-time = "2025-10-28T17:35:16.7Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ab/f2/b31d75cb9b5fa4dd39a0a931ee9b33e7f6f36f23be5ef560bf72e0f92f32/scipy-1.16.3-cp313-cp313t-musllinux_1_2_x86_64.whl", hash = "sha256:e7efa2681ea410b10dde31a52b18b0154d66f2485328830e45fdf183af5aefc6", size = 38796678, upload-time = "2025-10-28T17:35:26.354Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b4/1e/b3723d8ff64ab548c38d87055483714fefe6ee20e0189b62352b5e015bb1/scipy-1.16.3-cp313-cp313t-win_amd64.whl", hash = "sha256:2d1ae2cf0c350e7705168ff2429962a89ad90c2d49d1dd300686d8b2a5af22fc", size = 38640178, upload-time = "2025-10-28T17:35:35.304Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/8e/f3/d854ff38789aca9b0cc23008d607ced9de4f7ab14fa1ca4329f86b3758ca/scipy-1.16.3-cp313-cp313t-win_arm64.whl", hash = "sha256:0c623a54f7b79dd88ef56da19bc2873afec9673a48f3b85b18e4d402bdd29a5a", size = 25803246, upload-time = "2025-10-28T17:35:42.155Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/99/f6/99b10fd70f2d864c1e29a28bbcaa0c6340f9d8518396542d9ea3b4aaae15/scipy-1.16.3-cp314-cp314-macosx_10_14_x86_64.whl", hash = "sha256:875555ce62743e1d54f06cdf22c1e0bc47b91130ac40fe5d783b6dfa114beeb6", size = 36606469, upload-time = "2025-10-28T17:36:08.741Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/4d/74/043b54f2319f48ea940dd025779fa28ee360e6b95acb7cd188fad4391c6b/scipy-1.16.3-cp314-cp314-macosx_12_0_arm64.whl", hash = "sha256:bb61878c18a470021fb515a843dc7a76961a8daceaaaa8bad1332f1bf4b54657", size = 28872043, upload-time = "2025-10-28T17:36:16.599Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/4d/e1/24b7e50cc1c4ee6ffbcb1f27fe9f4c8b40e7911675f6d2d20955f41c6348/scipy-1.16.3-cp314-cp314-macosx_14_0_arm64.whl", hash = "sha256:f2622206f5559784fa5c4b53a950c3c7c1cf3e84ca1b9c4b6c03f062f289ca26", size = 20862952, upload-time = "2025-10-28T17:36:22.966Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/dd/3a/3e8c01a4d742b730df368e063787c6808597ccb38636ed821d10b39ca51b/scipy-1.16.3-cp314-cp314-macosx_14_0_x86_64.whl", hash = "sha256:7f68154688c515cdb541a31ef8eb66d8cd1050605be9dcd74199cbd22ac739bc", size = 23508512, upload-time = "2025-10-28T17:36:29.731Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/1f/60/c45a12b98ad591536bfe5330cb3cfe1850d7570259303563b1721564d458/scipy-1.16.3-cp314-cp314-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:8b3c820ddb80029fe9f43d61b81d8b488d3ef8ca010d15122b152db77dc94c22", size = 33413639, upload-time = "2025-10-28T17:36:37.982Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/71/bc/35957d88645476307e4839712642896689df442f3e53b0fa016ecf8a3357/scipy-1.16.3-cp314-cp314-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:d3837938ae715fc0fe3c39c0202de3a8853aff22ca66781ddc2ade7554b7e2cc", size = 35704729, upload-time = "2025-10-28T17:36:46.547Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/3b/15/89105e659041b1ca11c386e9995aefacd513a78493656e57789f9d9eab61/scipy-1.16.3-cp314-cp314-musllinux_1_2_aarch64.whl", hash = "sha256:aadd23f98f9cb069b3bd64ddc900c4d277778242e961751f77a8cb5c4b946fb0", size = 36086251, upload-time = "2025-10-28T17:36:55.161Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/1a/87/c0ea673ac9c6cc50b3da2196d860273bc7389aa69b64efa8493bdd25b093/scipy-1.16.3-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:b7c5f1bda1354d6a19bc6af73a649f8285ca63ac6b52e64e658a5a11d4d69800", size = 38716681, upload-time = "2025-10-28T17:37:04.1Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/91/06/837893227b043fb9b0d13e4bd7586982d8136cb249ffb3492930dab905b8/scipy-1.16.3-cp314-cp314-win_amd64.whl", hash = "sha256:e5d42a9472e7579e473879a1990327830493a7047506d58d73fc429b84c1d49d", size = 39358423, upload-time = "2025-10-28T17:38:20.005Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/95/03/28bce0355e4d34a7c034727505a02d19548549e190bedd13a721e35380b7/scipy-1.16.3-cp314-cp314-win_arm64.whl", hash = "sha256:6020470b9d00245926f2d5bb93b119ca0340f0d564eb6fbaad843eaebf9d690f", size = 26135027, upload-time = "2025-10-28T17:38:24.966Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b2/6f/69f1e2b682efe9de8fe9f91040f0cd32f13cfccba690512ba4c582b0bc29/scipy-1.16.3-cp314-cp314t-macosx_10_14_x86_64.whl", hash = "sha256:e1d27cbcb4602680a49d787d90664fa4974063ac9d4134813332a8c53dbe667c", size = 37028379, upload-time = "2025-10-28T17:37:14.061Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/7c/2d/e826f31624a5ebbab1cd93d30fd74349914753076ed0593e1d56a98c4fb4/scipy-1.16.3-cp314-cp314t-macosx_12_0_arm64.whl", hash = "sha256:9b9c9c07b6d56a35777a1b4cc8966118fb16cfd8daf6743867d17d36cfad2d40", size = 29400052, upload-time = "2025-10-28T17:37:21.709Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/69/27/d24feb80155f41fd1f156bf144e7e049b4e2b9dd06261a242905e3bc7a03/scipy-1.16.3-cp314-cp314t-macosx_14_0_arm64.whl", hash = "sha256:3a4c460301fb2cffb7f88528f30b3127742cff583603aa7dc964a52c463b385d", size = 21391183, upload-time = "2025-10-28T17:37:29.559Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/f8/d3/1b229e433074c5738a24277eca520a2319aac7465eea7310ea6ae0e98ae2/scipy-1.16.3-cp314-cp314t-macosx_14_0_x86_64.whl", hash = "sha256:f667a4542cc8917af1db06366d3f78a5c8e83badd56409f94d1eac8d8d9133fa", size = 23930174, upload-time = "2025-10-28T17:37:36.306Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/16/9d/d9e148b0ec680c0f042581a2be79a28a7ab66c0c4946697f9e7553ead337/scipy-1.16.3-cp314-cp314t-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:f379b54b77a597aa7ee5e697df0d66903e41b9c85a6dd7946159e356319158e8", size = 33497852, upload-time = "2025-10-28T17:37:42.228Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/2f/22/4e5f7561e4f98b7bea63cf3fd7934bff1e3182e9f1626b089a679914d5c8/scipy-1.16.3-cp314-cp314t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:4aff59800a3b7f786b70bfd6ab551001cb553244988d7d6b8299cb1ea653b353", size = 35798595, upload-time = "2025-10-28T17:37:48.102Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/83/42/6644d714c179429fc7196857866f219fef25238319b650bb32dde7bf7a48/scipy-1.16.3-cp314-cp314t-musllinux_1_2_aarch64.whl", hash = "sha256:da7763f55885045036fabcebd80144b757d3db06ab0861415d1c3b7c69042146", size = 36186269, upload-time = "2025-10-28T17:37:53.72Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ac/70/64b4d7ca92f9cf2e6fc6aaa2eecf80bb9b6b985043a9583f32f8177ea122/scipy-1.16.3-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:ffa6eea95283b2b8079b821dc11f50a17d0571c92b43e2b5b12764dc5f9b285d", size = 38802779, upload-time = "2025-10-28T17:37:59.393Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/61/82/8d0e39f62764cce5ffd5284131e109f07cf8955aef9ab8ed4e3aa5e30539/scipy-1.16.3-cp314-cp314t-win_amd64.whl", hash = "sha256:d9f48cafc7ce94cf9b15c6bffdc443a81a27bf7075cf2dcd5c8b40f85d10c4e7", size = 39471128, upload-time = "2025-10-28T17:38:05.259Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/64/47/a494741db7280eae6dc033510c319e34d42dd41b7ac0c7ead39354d1a2b5/scipy-1.16.3-cp314-cp314t-win_arm64.whl", hash = "sha256:21d9d6b197227a12dcbf9633320a4e34c6b0e51c57268df255a0942983bac562", size = 26464127, upload-time = "2025-10-28T17:38:11.34Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "shiboken6"
|
||||||
|
version = "6.10.0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fd/78/3e730aea82089dd82b1e092bc265778bda329459e6ad9b7134eec5fff3f2/shiboken6-6.10.0-cp39-abi3-macosx_13_0_universal2.whl", hash = "sha256:7a5f5f400ebfb3a13616030815708289c2154e701a60b9db7833b843e0bee543", size = 476535, upload-time = "2025-10-08T09:49:08Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/ea/09/4ffa3284a17b6b765d45b41c9a7f1b2cde6c617c853ac6f170fb62bbbece/shiboken6-6.10.0-cp39-abi3-manylinux_2_34_x86_64.whl", hash = "sha256:e612734da515d683696980107cdc0396a3ae0f07b059f0f422ec8a2333810234", size = 271098, upload-time = "2025-10-08T09:49:09.47Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/31/29/00e26f33a0fb259c2edce9c761a7a438d7531ca514bdb1a4c072673bd437/shiboken6-6.10.0-cp39-abi3-manylinux_2_39_aarch64.whl", hash = "sha256:b01377e68d14132360efb0f4b7233006d26aa8ae9bb50edf00960c2a5f52d148", size = 267698, upload-time = "2025-10-08T09:49:10.694Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/11/30/e4624a7e3f0dc9796b701079b77defcce0d32d1afc86bb1d0df04bc3d9e2/shiboken6-6.10.0-cp39-abi3-win_amd64.whl", hash = "sha256:0bc5631c1bf150cbef768a17f5f289aae1cb4db6c6b0c19b2421394e27783717", size = 1234227, upload-time = "2025-10-08T09:49:12.774Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/dd/e5/0ab862005ea87dc8647ba958a3099b3b0115fd6491c65da5c5a0f6364db1/shiboken6-6.10.0-cp39-abi3-win_arm64.whl", hash = "sha256:dfc4beab5fec7dbbebbb418f3bf99af865d6953aa0795435563d4cbb82093b61", size = 1794775, upload-time = "2025-10-08T09:49:14.641Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "six"
|
||||||
|
version = "1.17.0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/94/e7/b2c673351809dca68a0e064b6af791aa332cf192da575fd474ed7d6f16a2/six-1.17.0.tar.gz", hash = "sha256:ff70335d468e7eb6ec65b95b99d3a2836546063f63acc5171de367e834932a81", size = 34031, upload-time = "2024-12-04T17:35:28.174Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b7/ce/149a00dd41f10bc29e5921b496af8b574d8413afcd5e30dfa0ed46c2cc5e/six-1.17.0-py2.py3-none-any.whl", hash = "sha256:4721f391ed90541fddacab5acf947aa0d3dc7d27b2e1e8eda2be8970586c3274", size = 11050, upload-time = "2024-12-04T17:35:26.475Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "tomli"
|
||||||
|
version = "2.3.0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/52/ed/3f73f72945444548f33eba9a87fc7a6e969915e7b1acc8260b30e1f76a2f/tomli-2.3.0.tar.gz", hash = "sha256:64be704a875d2a59753d80ee8a533c3fe183e3f06807ff7dc2232938ccb01549", size = 17392, upload-time = "2025-10-08T22:01:47.119Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/89/48/06ee6eabe4fdd9ecd48bf488f4ac783844fd777f547b8d1b61c11939974e/tomli-2.3.0-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:5192f562738228945d7b13d4930baffda67b69425a7f0da96d360b0a3888136b", size = 154819, upload-time = "2025-10-08T22:01:17.964Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/f1/01/88793757d54d8937015c75dcdfb673c65471945f6be98e6a0410fba167ed/tomli-2.3.0-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:be71c93a63d738597996be9528f4abe628d1adf5e6eb11607bc8fe1a510b5dae", size = 148766, upload-time = "2025-10-08T22:01:18.959Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/42/17/5e2c956f0144b812e7e107f94f1cc54af734eb17b5191c0bbfb72de5e93e/tomli-2.3.0-cp313-cp313-manylinux2014_aarch64.manylinux_2_17_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:c4665508bcbac83a31ff8ab08f424b665200c0e1e645d2bd9ab3d3e557b6185b", size = 240771, upload-time = "2025-10-08T22:01:20.106Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/d5/f4/0fbd014909748706c01d16824eadb0307115f9562a15cbb012cd9b3512c5/tomli-2.3.0-cp313-cp313-manylinux2014_x86_64.manylinux_2_17_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:4021923f97266babc6ccab9f5068642a0095faa0a51a246a6a02fccbb3514eaf", size = 248586, upload-time = "2025-10-08T22:01:21.164Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/30/77/fed85e114bde5e81ecf9bc5da0cc69f2914b38f4708c80ae67d0c10180c5/tomli-2.3.0-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:a4ea38c40145a357d513bffad0ed869f13c1773716cf71ccaa83b0fa0cc4e42f", size = 244792, upload-time = "2025-10-08T22:01:22.417Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/55/92/afed3d497f7c186dc71e6ee6d4fcb0acfa5f7d0a1a2878f8beae379ae0cc/tomli-2.3.0-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:ad805ea85eda330dbad64c7ea7a4556259665bdf9d2672f5dccc740eb9d3ca05", size = 248909, upload-time = "2025-10-08T22:01:23.859Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/f8/84/ef50c51b5a9472e7265ce1ffc7f24cd4023d289e109f669bdb1553f6a7c2/tomli-2.3.0-cp313-cp313-win32.whl", hash = "sha256:97d5eec30149fd3294270e889b4234023f2c69747e555a27bd708828353ab606", size = 96946, upload-time = "2025-10-08T22:01:24.893Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b2/b7/718cd1da0884f281f95ccfa3a6cc572d30053cba64603f79d431d3c9b61b/tomli-2.3.0-cp313-cp313-win_amd64.whl", hash = "sha256:0c95ca56fbe89e065c6ead5b593ee64b84a26fca063b5d71a1122bf26e533999", size = 107705, upload-time = "2025-10-08T22:01:26.153Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/19/94/aeafa14a52e16163008060506fcb6aa1949d13548d13752171a755c65611/tomli-2.3.0-cp314-cp314-macosx_10_13_x86_64.whl", hash = "sha256:cebc6fe843e0733ee827a282aca4999b596241195f43b4cc371d64fc6639da9e", size = 154244, upload-time = "2025-10-08T22:01:27.06Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/db/e4/1e58409aa78eefa47ccd19779fc6f36787edbe7d4cd330eeeedb33a4515b/tomli-2.3.0-cp314-cp314-macosx_11_0_arm64.whl", hash = "sha256:4c2ef0244c75aba9355561272009d934953817c49f47d768070c3c94355c2aa3", size = 148637, upload-time = "2025-10-08T22:01:28.059Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/26/b6/d1eccb62f665e44359226811064596dd6a366ea1f985839c566cd61525ae/tomli-2.3.0-cp314-cp314-manylinux2014_aarch64.manylinux_2_17_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:c22a8bf253bacc0cf11f35ad9808b6cb75ada2631c2d97c971122583b129afbc", size = 241925, upload-time = "2025-10-08T22:01:29.066Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/70/91/7cdab9a03e6d3d2bb11beae108da5bdc1c34bdeb06e21163482544ddcc90/tomli-2.3.0-cp314-cp314-manylinux2014_x86_64.manylinux_2_17_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:0eea8cc5c5e9f89c9b90c4896a8deefc74f518db5927d0e0e8d4a80953d774d0", size = 249045, upload-time = "2025-10-08T22:01:31.98Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/15/1b/8c26874ed1f6e4f1fcfeb868db8a794cbe9f227299402db58cfcc858766c/tomli-2.3.0-cp314-cp314-musllinux_1_2_aarch64.whl", hash = "sha256:b74a0e59ec5d15127acdabd75ea17726ac4c5178ae51b85bfe39c4f8a278e879", size = 245835, upload-time = "2025-10-08T22:01:32.989Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/fd/42/8e3c6a9a4b1a1360c1a2a39f0b972cef2cc9ebd56025168c4137192a9321/tomli-2.3.0-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:b5870b50c9db823c595983571d1296a6ff3e1b88f734a4c8f6fc6188397de005", size = 253109, upload-time = "2025-10-08T22:01:34.052Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/22/0c/b4da635000a71b5f80130937eeac12e686eefb376b8dee113b4a582bba42/tomli-2.3.0-cp314-cp314-win32.whl", hash = "sha256:feb0dacc61170ed7ab602d3d972a58f14ee3ee60494292d384649a3dc38ef463", size = 97930, upload-time = "2025-10-08T22:01:35.082Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/b9/74/cb1abc870a418ae99cd5c9547d6bce30701a954e0e721821df483ef7223c/tomli-2.3.0-cp314-cp314-win_amd64.whl", hash = "sha256:b273fcbd7fc64dc3600c098e39136522650c49bca95df2d11cf3b626422392c8", size = 107964, upload-time = "2025-10-08T22:01:36.057Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/54/78/5c46fff6432a712af9f792944f4fcd7067d8823157949f4e40c56b8b3c83/tomli-2.3.0-cp314-cp314t-macosx_10_13_x86_64.whl", hash = "sha256:940d56ee0410fa17ee1f12b817b37a4d4e4dc4d27340863cc67236c74f582e77", size = 163065, upload-time = "2025-10-08T22:01:37.27Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/39/67/f85d9bd23182f45eca8939cd2bc7050e1f90c41f4a2ecbbd5963a1d1c486/tomli-2.3.0-cp314-cp314t-macosx_11_0_arm64.whl", hash = "sha256:f85209946d1fe94416debbb88d00eb92ce9cd5266775424ff81bc959e001acaf", size = 159088, upload-time = "2025-10-08T22:01:38.235Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/26/5a/4b546a0405b9cc0659b399f12b6adb750757baf04250b148d3c5059fc4eb/tomli-2.3.0-cp314-cp314t-manylinux2014_aarch64.manylinux_2_17_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:a56212bdcce682e56b0aaf79e869ba5d15a6163f88d5451cbde388d48b13f530", size = 268193, upload-time = "2025-10-08T22:01:39.712Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/42/4f/2c12a72ae22cf7b59a7fe75b3465b7aba40ea9145d026ba41cb382075b0e/tomli-2.3.0-cp314-cp314t-manylinux2014_x86_64.manylinux_2_17_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:c5f3ffd1e098dfc032d4d3af5c0ac64f6d286d98bc148698356847b80fa4de1b", size = 275488, upload-time = "2025-10-08T22:01:40.773Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/92/04/a038d65dbe160c3aa5a624e93ad98111090f6804027d474ba9c37c8ae186/tomli-2.3.0-cp314-cp314t-musllinux_1_2_aarch64.whl", hash = "sha256:5e01decd096b1530d97d5d85cb4dff4af2d8347bd35686654a004f8dea20fc67", size = 272669, upload-time = "2025-10-08T22:01:41.824Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/be/2f/8b7c60a9d1612a7cbc39ffcca4f21a73bf368a80fc25bccf8253e2563267/tomli-2.3.0-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:8a35dd0e643bb2610f156cca8db95d213a90015c11fee76c946aa62b7ae7e02f", size = 279709, upload-time = "2025-10-08T22:01:43.177Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/7e/46/cc36c679f09f27ded940281c38607716c86cf8ba4a518d524e349c8b4874/tomli-2.3.0-cp314-cp314t-win32.whl", hash = "sha256:a1f7f282fe248311650081faafa5f4732bdbfef5d45fe3f2e702fbc6f2d496e0", size = 107563, upload-time = "2025-10-08T22:01:44.233Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/84/ff/426ca8683cf7b753614480484f6437f568fd2fda2edbdf57a2d3d8b27a0b/tomli-2.3.0-cp314-cp314t-win_amd64.whl", hash = "sha256:70a251f8d4ba2d9ac2542eecf008b3c8a9fc5c3f9f02c56a9d7952612be2fdba", size = 119756, upload-time = "2025-10-08T22:01:45.234Z" },
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/77/b8/0135fadc89e73be292b473cb820b4f5a08197779206b33191e801feeae40/tomli-2.3.0-py3-none-any.whl", hash = "sha256:e95b1af3c5b07d9e643909b5abbec77cd9f1217e6d0bca72b0234736b9fb1f1b", size = 14408, upload-time = "2025-10-08T22:01:46.04Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "tomli-w"
|
||||||
|
version = "1.2.0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/19/75/241269d1da26b624c0d5e110e8149093c759b7a286138f4efd61a60e75fe/tomli_w-1.2.0.tar.gz", hash = "sha256:2dd14fac5a47c27be9cd4c976af5a12d87fb1f0b4512f81d69cce3b35ae25021", size = 7184, upload-time = "2025-01-15T12:07:24.262Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/c7/18/c86eb8e0202e32dd3df50d43d7ff9854f8e0603945ff398974c1d91ac1ef/tomli_w-1.2.0-py3-none-any.whl", hash = "sha256:188306098d013b691fcadc011abd66727d3c414c571bb01b1a174ba8c983cf90", size = 6675, upload-time = "2025-01-15T12:07:22.074Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "typing-extensions"
|
||||||
|
version = "4.15.0"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/72/94/1a15dd82efb362ac84269196e94cf00f187f7ed21c242792a923cdb1c61f/typing_extensions-4.15.0.tar.gz", hash = "sha256:0cea48d173cc12fa28ecabc3b837ea3cf6f38c6d1136f85cbaaf598984861466", size = 109391, upload-time = "2025-08-25T13:49:26.313Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/18/67/36e9267722cc04a6b9f15c7f3441c2363321a3ea07da7ae0c0707beb2a9c/typing_extensions-4.15.0-py3-none-any.whl", hash = "sha256:f0fa19c6845758ab08074a0cfa8b7aecb71c999ca73d62883bc25cc018c4e548", size = 44614, upload-time = "2025-08-25T13:49:24.86Z" },
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "typing-inspection"
|
||||||
|
version = "0.4.2"
|
||||||
|
source = { registry = "https://pypi.org/simple" }
|
||||||
|
dependencies = [
|
||||||
|
{ name = "typing-extensions" },
|
||||||
|
]
|
||||||
|
sdist = { url = "https://files.pythonhosted.org/packages/55/e3/70399cb7dd41c10ac53367ae42139cf4b1ca5f36bb3dc6c9d33acdb43655/typing_inspection-0.4.2.tar.gz", hash = "sha256:ba561c48a67c5958007083d386c3295464928b01faa735ab8547c5692e87f464", size = 75949, upload-time = "2025-10-01T02:14:41.687Z" }
|
||||||
|
wheels = [
|
||||||
|
{ url = "https://files.pythonhosted.org/packages/dc/9b/47798a6c91d8bdb567fe2698fe81e0c6b7cb7ef4d13da4114b41d239f65d/typing_inspection-0.4.2-py3-none-any.whl", hash = "sha256:4ed1cacbdc298c220f1bd249ed5287caa16f34d44ef4e9c3d0cbad5b521545e7", size = 14611, upload-time = "2025-10-01T02:14:40.154Z" },
|
||||||
|
]
|
||||||
Reference in New Issue
Block a user