Compare commits

..

4 Commits

7 changed files with 304 additions and 157 deletions

175
poetry.lock generated
View File

@ -189,6 +189,44 @@ ufo = ["fs (>=2.2.0,<3)"]
unicode = ["unicodedata2 (>=15.1.0)"] unicode = ["unicodedata2 (>=15.1.0)"]
woff = ["brotli (>=1.0.1)", "brotlicffi (>=0.8.0)", "zopfli (>=0.1.4)"] woff = ["brotli (>=1.0.1)", "brotlicffi (>=0.8.0)", "zopfli (>=0.1.4)"]
[[package]]
name = "h5py"
version = "3.12.1"
description = "Read and write HDF5 files from Python"
optional = false
python-versions = ">=3.9"
files = [
{file = "h5py-3.12.1-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:2f0f1a382cbf494679c07b4371f90c70391dedb027d517ac94fa2c05299dacda"},
{file = "h5py-3.12.1-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:cb65f619dfbdd15e662423e8d257780f9a66677eae5b4b3fc9dca70b5fd2d2a3"},
{file = "h5py-3.12.1-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3b15d8dbd912c97541312c0e07438864d27dbca857c5ad634de68110c6beb1c2"},
{file = "h5py-3.12.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:59685fe40d8c1fbbee088c88cd4da415a2f8bee5c270337dc5a1c4aa634e3307"},
{file = "h5py-3.12.1-cp310-cp310-win_amd64.whl", hash = "sha256:577d618d6b6dea3da07d13cc903ef9634cde5596b13e832476dd861aaf651f3e"},
{file = "h5py-3.12.1-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:ccd9006d92232727d23f784795191bfd02294a4f2ba68708825cb1da39511a93"},
{file = "h5py-3.12.1-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:ad8a76557880aed5234cfe7279805f4ab5ce16b17954606cca90d578d3e713ef"},
{file = "h5py-3.12.1-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1473348139b885393125126258ae2d70753ef7e9cec8e7848434f385ae72069e"},
{file = "h5py-3.12.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:018a4597f35092ae3fb28ee851fdc756d2b88c96336b8480e124ce1ac6fb9166"},
{file = "h5py-3.12.1-cp311-cp311-win_amd64.whl", hash = "sha256:3fdf95092d60e8130ba6ae0ef7a9bd4ade8edbe3569c13ebbaf39baefffc5ba4"},
{file = "h5py-3.12.1-cp312-cp312-macosx_10_13_x86_64.whl", hash = "sha256:06a903a4e4e9e3ebbc8b548959c3c2552ca2d70dac14fcfa650d9261c66939ed"},
{file = "h5py-3.12.1-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:7b3b8f3b48717e46c6a790e3128d39c61ab595ae0a7237f06dfad6a3b51d5351"},
{file = "h5py-3.12.1-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:050a4f2c9126054515169c49cb900949814987f0c7ae74c341b0c9f9b5056834"},
{file = "h5py-3.12.1-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5c4b41d1019322a5afc5082864dfd6359f8935ecd37c11ac0029be78c5d112c9"},
{file = "h5py-3.12.1-cp312-cp312-win_amd64.whl", hash = "sha256:e4d51919110a030913201422fb07987db4338eba5ec8c5a15d6fab8e03d443fc"},
{file = "h5py-3.12.1-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:513171e90ed92236fc2ca363ce7a2fc6f2827375efcbb0cc7fbdd7fe11fecafc"},
{file = "h5py-3.12.1-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:59400f88343b79655a242068a9c900001a34b63e3afb040bd7cdf717e440f653"},
{file = "h5py-3.12.1-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d3e465aee0ec353949f0f46bf6c6f9790a2006af896cee7c178a8c3e5090aa32"},
{file = "h5py-3.12.1-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ba51c0c5e029bb5420a343586ff79d56e7455d496d18a30309616fdbeed1068f"},
{file = "h5py-3.12.1-cp313-cp313-win_amd64.whl", hash = "sha256:52ab036c6c97055b85b2a242cb540ff9590bacfda0c03dd0cf0661b311f522f8"},
{file = "h5py-3.12.1-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:d2b8dd64f127d8b324f5d2cd1c0fd6f68af69084e9e47d27efeb9e28e685af3e"},
{file = "h5py-3.12.1-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:4532c7e97fbef3d029735db8b6f5bf01222d9ece41e309b20d63cfaae2fb5c4d"},
{file = "h5py-3.12.1-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6fdf6d7936fa824acfa27305fe2d9f39968e539d831c5bae0e0d83ed521ad1ac"},
{file = "h5py-3.12.1-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:84342bffd1f82d4f036433e7039e241a243531a1d3acd7341b35ae58cdab05bf"},
{file = "h5py-3.12.1-cp39-cp39-win_amd64.whl", hash = "sha256:62be1fc0ef195891949b2c627ec06bc8e837ff62d5b911b6e42e38e0f20a897d"},
{file = "h5py-3.12.1.tar.gz", hash = "sha256:326d70b53d31baa61f00b8aa5f95c2fcb9621a3ee8365d770c551a13dbbcbfdf"},
]
[package.dependencies]
numpy = ">=1.19.3"
[[package]] [[package]]
name = "kiwisolver" name = "kiwisolver"
version = "1.4.7" version = "1.4.7"
@ -410,66 +448,65 @@ files = [
{file = "mdurl-0.1.2.tar.gz", hash = "sha256:bb413d29f5eea38f31dd4754dd7377d4465116fb207585f97bf925588687c1ba"}, {file = "mdurl-0.1.2.tar.gz", hash = "sha256:bb413d29f5eea38f31dd4754dd7377d4465116fb207585f97bf925588687c1ba"},
] ]
[[package]]
name = "nixio"
version = "1.5.3"
description = "Python reimplementation of NIXIO (http://g-node.github.io/nix/)"
optional = false
python-versions = ">=3.6"
files = [
{file = "nixio-1.5.3-py3-none-any.whl", hash = "sha256:5bc6258b0911738070f7008237d4cef348a994cce7f557adf624452f0f4287cb"},
{file = "nixio-1.5.3.tar.gz", hash = "sha256:0ba7a65148297bd43a5ddaf143c4faad1c999771aa1d7e690aa0a5e31f368608"},
]
[package.dependencies]
h5py = "*"
numpy = "*"
six = "*"
[[package]] [[package]]
name = "numpy" name = "numpy"
version = "2.1.1" version = "1.26.4"
description = "Fundamental package for array computing in Python" description = "Fundamental package for array computing in Python"
optional = false optional = false
python-versions = ">=3.10" python-versions = ">=3.9"
files = [ files = [
{file = "numpy-2.1.1-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:c8a0e34993b510fc19b9a2ce7f31cb8e94ecf6e924a40c0c9dd4f62d0aac47d9"}, {file = "numpy-1.26.4-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:9ff0f4f29c51e2803569d7a51c2304de5554655a60c5d776e35b4a41413830d0"},
{file = "numpy-2.1.1-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:7dd86dfaf7c900c0bbdcb8b16e2f6ddf1eb1fe39c6c8cca6e94844ed3152a8fd"}, {file = "numpy-1.26.4-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:2e4ee3380d6de9c9ec04745830fd9e2eccb3e6cf790d39d7b98ffd19b0dd754a"},
{file = "numpy-2.1.1-cp310-cp310-macosx_14_0_arm64.whl", hash = "sha256:5889dd24f03ca5a5b1e8a90a33b5a0846d8977565e4ae003a63d22ecddf6782f"}, {file = "numpy-1.26.4-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d209d8969599b27ad20994c8e41936ee0964e6da07478d6c35016bc386b66ad4"},
{file = "numpy-2.1.1-cp310-cp310-macosx_14_0_x86_64.whl", hash = "sha256:59ca673ad11d4b84ceb385290ed0ebe60266e356641428c845b39cd9df6713ab"}, {file = "numpy-1.26.4-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ffa75af20b44f8dba823498024771d5ac50620e6915abac414251bd971b4529f"},
{file = "numpy-2.1.1-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:13ce49a34c44b6de5241f0b38b07e44c1b2dcacd9e36c30f9c2fcb1bb5135db7"}, {file = "numpy-1.26.4-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:62b8e4b1e28009ef2846b4c7852046736bab361f7aeadeb6a5b89ebec3c7055a"},
{file = "numpy-2.1.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:913cc1d311060b1d409e609947fa1b9753701dac96e6581b58afc36b7ee35af6"}, {file = "numpy-1.26.4-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:a4abb4f9001ad2858e7ac189089c42178fcce737e4169dc61321660f1a96c7d2"},
{file = "numpy-2.1.1-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:caf5d284ddea7462c32b8d4a6b8af030b6c9fd5332afb70e7414d7fdded4bfd0"}, {file = "numpy-1.26.4-cp310-cp310-win32.whl", hash = "sha256:bfe25acf8b437eb2a8b2d49d443800a5f18508cd811fea3181723922a8a82b07"},
{file = "numpy-2.1.1-cp310-cp310-musllinux_1_2_aarch64.whl", hash = "sha256:57eb525e7c2a8fdee02d731f647146ff54ea8c973364f3b850069ffb42799647"}, {file = "numpy-1.26.4-cp310-cp310-win_amd64.whl", hash = "sha256:b97fe8060236edf3662adfc2c633f56a08ae30560c56310562cb4f95500022d5"},
{file = "numpy-2.1.1-cp310-cp310-win32.whl", hash = "sha256:9a8e06c7a980869ea67bbf551283bbed2856915f0a792dc32dd0f9dd2fb56728"}, {file = "numpy-1.26.4-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:4c66707fabe114439db9068ee468c26bbdf909cac0fb58686a42a24de1760c71"},
{file = "numpy-2.1.1-cp310-cp310-win_amd64.whl", hash = "sha256:d10c39947a2d351d6d466b4ae83dad4c37cd6c3cdd6d5d0fa797da56f710a6ae"}, {file = "numpy-1.26.4-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:edd8b5fe47dab091176d21bb6de568acdd906d1887a4584a15a9a96a1dca06ef"},
{file = "numpy-2.1.1-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:0d07841fd284718feffe7dd17a63a2e6c78679b2d386d3e82f44f0108c905550"}, {file = "numpy-1.26.4-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:7ab55401287bfec946ced39700c053796e7cc0e3acbef09993a9ad2adba6ca6e"},
{file = "numpy-2.1.1-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:b5613cfeb1adfe791e8e681128f5f49f22f3fcaa942255a6124d58ca59d9528f"}, {file = "numpy-1.26.4-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:666dbfb6ec68962c033a450943ded891bed2d54e6755e35e5835d63f4f6931d5"},
{file = "numpy-2.1.1-cp311-cp311-macosx_14_0_arm64.whl", hash = "sha256:0b8cc2715a84b7c3b161f9ebbd942740aaed913584cae9cdc7f8ad5ad41943d0"}, {file = "numpy-1.26.4-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:96ff0b2ad353d8f990b63294c8986f1ec3cb19d749234014f4e7eb0112ceba5a"},
{file = "numpy-2.1.1-cp311-cp311-macosx_14_0_x86_64.whl", hash = "sha256:b49742cdb85f1f81e4dc1b39dcf328244f4d8d1ded95dea725b316bd2cf18c95"}, {file = "numpy-1.26.4-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:60dedbb91afcbfdc9bc0b1f3f402804070deed7392c23eb7a7f07fa857868e8a"},
{file = "numpy-2.1.1-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e8d5f8a8e3bc87334f025194c6193e408903d21ebaeb10952264943a985066ca"}, {file = "numpy-1.26.4-cp311-cp311-win32.whl", hash = "sha256:1af303d6b2210eb850fcf03064d364652b7120803a0b872f5211f5234b399f20"},
{file = "numpy-2.1.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d51fc141ddbe3f919e91a096ec739f49d686df8af254b2053ba21a910ae518bf"}, {file = "numpy-1.26.4-cp311-cp311-win_amd64.whl", hash = "sha256:cd25bcecc4974d09257ffcd1f098ee778f7834c3ad767fe5db785be9a4aa9cb2"},
{file = "numpy-2.1.1-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:98ce7fb5b8063cfdd86596b9c762bf2b5e35a2cdd7e967494ab78a1fa7f8b86e"}, {file = "numpy-1.26.4-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:b3ce300f3644fb06443ee2222c2201dd3a89ea6040541412b8fa189341847218"},
{file = "numpy-2.1.1-cp311-cp311-musllinux_1_2_aarch64.whl", hash = "sha256:24c2ad697bd8593887b019817ddd9974a7f429c14a5469d7fad413f28340a6d2"}, {file = "numpy-1.26.4-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:03a8c78d01d9781b28a6989f6fa1bb2c4f2d51201cf99d3dd875df6fbd96b23b"},
{file = "numpy-2.1.1-cp311-cp311-win32.whl", hash = "sha256:397bc5ce62d3fb73f304bec332171535c187e0643e176a6e9421a6e3eacef06d"}, {file = "numpy-1.26.4-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9fad7dcb1aac3c7f0584a5a8133e3a43eeb2fe127f47e3632d43d677c66c102b"},
{file = "numpy-2.1.1-cp311-cp311-win_amd64.whl", hash = "sha256:ae8ce252404cdd4de56dcfce8b11eac3c594a9c16c231d081fb705cf23bd4d9e"}, {file = "numpy-1.26.4-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:675d61ffbfa78604709862923189bad94014bef562cc35cf61d3a07bba02a7ed"},
{file = "numpy-2.1.1-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:7c803b7934a7f59563db459292e6aa078bb38b7ab1446ca38dd138646a38203e"}, {file = "numpy-1.26.4-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:ab47dbe5cc8210f55aa58e4805fe224dac469cde56b9f731a4c098b91917159a"},
{file = "numpy-2.1.1-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:6435c48250c12f001920f0751fe50c0348f5f240852cfddc5e2f97e007544cbe"}, {file = "numpy-1.26.4-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:1dda2e7b4ec9dd512f84935c5f126c8bd8b9f2fc001e9f54af255e8c5f16b0e0"},
{file = "numpy-2.1.1-cp312-cp312-macosx_14_0_arm64.whl", hash = "sha256:3269c9eb8745e8d975980b3a7411a98976824e1fdef11f0aacf76147f662b15f"}, {file = "numpy-1.26.4-cp312-cp312-win32.whl", hash = "sha256:50193e430acfc1346175fcbdaa28ffec49947a06918b7b92130744e81e640110"},
{file = "numpy-2.1.1-cp312-cp312-macosx_14_0_x86_64.whl", hash = "sha256:fac6e277a41163d27dfab5f4ec1f7a83fac94e170665a4a50191b545721c6521"}, {file = "numpy-1.26.4-cp312-cp312-win_amd64.whl", hash = "sha256:08beddf13648eb95f8d867350f6a018a4be2e5ad54c8d8caed89ebca558b2818"},
{file = "numpy-2.1.1-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:fcd8f556cdc8cfe35e70efb92463082b7f43dd7e547eb071ffc36abc0ca4699b"}, {file = "numpy-1.26.4-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:7349ab0fa0c429c82442a27a9673fc802ffdb7c7775fad780226cb234965e53c"},
{file = "numpy-2.1.1-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d2b9cd92c8f8e7b313b80e93cedc12c0112088541dcedd9197b5dee3738c1201"}, {file = "numpy-1.26.4-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:52b8b60467cd7dd1e9ed082188b4e6bb35aa5cdd01777621a1658910745b90be"},
{file = "numpy-2.1.1-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:afd9c680df4de71cd58582b51e88a61feed4abcc7530bcd3d48483f20fc76f2a"}, {file = "numpy-1.26.4-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d5241e0a80d808d70546c697135da2c613f30e28251ff8307eb72ba696945764"},
{file = "numpy-2.1.1-cp312-cp312-musllinux_1_2_aarch64.whl", hash = "sha256:8661c94e3aad18e1ea17a11f60f843a4933ccaf1a25a7c6a9182af70610b2313"}, {file = "numpy-1.26.4-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f870204a840a60da0b12273ef34f7051e98c3b5961b61b0c2c1be6dfd64fbcd3"},
{file = "numpy-2.1.1-cp312-cp312-win32.whl", hash = "sha256:950802d17a33c07cba7fd7c3dcfa7d64705509206be1606f196d179e539111ed"}, {file = "numpy-1.26.4-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:679b0076f67ecc0138fd2ede3a8fd196dddc2ad3254069bcb9faf9a79b1cebcd"},
{file = "numpy-2.1.1-cp312-cp312-win_amd64.whl", hash = "sha256:3fc5eabfc720db95d68e6646e88f8b399bfedd235994016351b1d9e062c4b270"}, {file = "numpy-1.26.4-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:47711010ad8555514b434df65f7d7b076bb8261df1ca9bb78f53d3b2db02e95c"},
{file = "numpy-2.1.1-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:046356b19d7ad1890c751b99acad5e82dc4a02232013bd9a9a712fddf8eb60f5"}, {file = "numpy-1.26.4-cp39-cp39-win32.whl", hash = "sha256:a354325ee03388678242a4d7ebcd08b5c727033fcff3b2f536aea978e15ee9e6"},
{file = "numpy-2.1.1-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:6e5a9cb2be39350ae6c8f79410744e80154df658d5bea06e06e0ac5bb75480d5"}, {file = "numpy-1.26.4-cp39-cp39-win_amd64.whl", hash = "sha256:3373d5d70a5fe74a2c1bb6d2cfd9609ecf686d47a2d7b1d37a8f3b6bf6003aea"},
{file = "numpy-2.1.1-cp313-cp313-macosx_14_0_arm64.whl", hash = "sha256:d4c57b68c8ef5e1ebf47238e99bf27657511ec3f071c465f6b1bccbef12d4136"}, {file = "numpy-1.26.4-pp39-pypy39_pp73-macosx_10_9_x86_64.whl", hash = "sha256:afedb719a9dcfc7eaf2287b839d8198e06dcd4cb5d276a3df279231138e83d30"},
{file = "numpy-2.1.1-cp313-cp313-macosx_14_0_x86_64.whl", hash = "sha256:8ae0fd135e0b157365ac7cc31fff27f07a5572bdfc38f9c2d43b2aff416cc8b0"}, {file = "numpy-1.26.4-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:95a7476c59002f2f6c590b9b7b998306fba6a5aa646b1e22ddfeaf8f78c3a29c"},
{file = "numpy-2.1.1-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:981707f6b31b59c0c24bcda52e5605f9701cb46da4b86c2e8023656ad3e833cb"}, {file = "numpy-1.26.4-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:7e50d0a0cc3189f9cb0aeb3a6a6af18c16f59f004b866cd2be1c14b36134a4a0"},
{file = "numpy-2.1.1-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2ca4b53e1e0b279142113b8c5eb7d7a877e967c306edc34f3b58e9be12fda8df"}, {file = "numpy-1.26.4.tar.gz", hash = "sha256:2a02aba9ed12e4ac4eb3ea9421c420301a0c6460d9830d74a9df87efa4912010"},
{file = "numpy-2.1.1-cp313-cp313-musllinux_1_1_x86_64.whl", hash = "sha256:e097507396c0be4e547ff15b13dc3866f45f3680f789c1a1301b07dadd3fbc78"},
{file = "numpy-2.1.1-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:f7506387e191fe8cdb267f912469a3cccc538ab108471291636a96a54e599556"},
{file = "numpy-2.1.1-cp313-cp313-win32.whl", hash = "sha256:251105b7c42abe40e3a689881e1793370cc9724ad50d64b30b358bbb3a97553b"},
{file = "numpy-2.1.1-cp313-cp313-win_amd64.whl", hash = "sha256:f212d4f46b67ff604d11fff7cc62d36b3e8714edf68e44e9760e19be38c03eb0"},
{file = "numpy-2.1.1-cp313-cp313t-macosx_10_13_x86_64.whl", hash = "sha256:920b0911bb2e4414c50e55bd658baeb78281a47feeb064ab40c2b66ecba85553"},
{file = "numpy-2.1.1-cp313-cp313t-macosx_11_0_arm64.whl", hash = "sha256:bab7c09454460a487e631ffc0c42057e3d8f2a9ddccd1e60c7bb8ed774992480"},
{file = "numpy-2.1.1-cp313-cp313t-macosx_14_0_arm64.whl", hash = "sha256:cea427d1350f3fd0d2818ce7350095c1a2ee33e30961d2f0fef48576ddbbe90f"},
{file = "numpy-2.1.1-cp313-cp313t-macosx_14_0_x86_64.whl", hash = "sha256:e30356d530528a42eeba51420ae8bf6c6c09559051887196599d96ee5f536468"},
{file = "numpy-2.1.1-cp313-cp313t-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e8dfa9e94fc127c40979c3eacbae1e61fda4fe71d84869cc129e2721973231ef"},
{file = "numpy-2.1.1-cp313-cp313t-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:910b47a6d0635ec1bd53b88f86120a52bf56dcc27b51f18c7b4a2e2224c29f0f"},
{file = "numpy-2.1.1-cp313-cp313t-musllinux_1_1_x86_64.whl", hash = "sha256:13cc11c00000848702322af4de0147ced365c81d66053a67c2e962a485b3717c"},
{file = "numpy-2.1.1-cp313-cp313t-musllinux_1_2_aarch64.whl", hash = "sha256:53e27293b3a2b661c03f79aa51c3987492bd4641ef933e366e0f9f6c9bf257ec"},
{file = "numpy-2.1.1-pp310-pypy310_pp73-macosx_10_15_x86_64.whl", hash = "sha256:7be6a07520b88214ea85d8ac8b7d6d8a1839b0b5cb87412ac9f49fa934eb15d5"},
{file = "numpy-2.1.1-pp310-pypy310_pp73-macosx_14_0_x86_64.whl", hash = "sha256:52ac2e48f5ad847cd43c4755520a2317f3380213493b9d8a4c5e37f3b87df504"},
{file = "numpy-2.1.1-pp310-pypy310_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:50a95ca3560a6058d6ea91d4629a83a897ee27c00630aed9d933dff191f170cd"},
{file = "numpy-2.1.1-pp310-pypy310_pp73-win_amd64.whl", hash = "sha256:99f4a9ee60eed1385a86e82288971a51e71df052ed0b2900ed30bc840c0f2e39"},
{file = "numpy-2.1.1.tar.gz", hash = "sha256:d0cf7d55b1051387807405b3898efafa862997b4cba8aa5dbe657be794afeafd"},
] ]
[[package]] [[package]]
@ -672,6 +709,20 @@ files = [
{file = "PyQt6_sip-13.8.0.tar.gz", hash = "sha256:2f74cf3d6d9cab5152bd9f49d570b2dfb87553ebb5c4919abfde27f5b9fd69d4"}, {file = "PyQt6_sip-13.8.0.tar.gz", hash = "sha256:2f74cf3d6d9cab5152bd9f49d570b2dfb87553ebb5c4919abfde27f5b9fd69d4"},
] ]
[[package]]
name = "pyqtgraph"
version = "0.13.7"
description = "Scientific Graphics and GUI Library for Python"
optional = false
python-versions = ">=3.9"
files = [
{file = "pyqtgraph-0.13.7-py3-none-any.whl", hash = "sha256:7754edbefb6c367fa0dfb176e2d0610da3ada20aa7a5318516c74af5fb72bf7a"},
{file = "pyqtgraph-0.13.7.tar.gz", hash = "sha256:64f84f1935c6996d0e09b1ee66fe478a7771e3ca6f3aaa05f00f6e068321d9e3"},
]
[package.dependencies]
numpy = ">=1.22.0"
[[package]] [[package]]
name = "python-dateutil" name = "python-dateutil"
version = "2.9.0.post0" version = "2.9.0.post0"
@ -777,14 +828,14 @@ files = [
] ]
[[package]] [[package]]
name = "tomli" name = "tomlkit"
version = "2.0.1" version = "0.13.2"
description = "A lil' TOML parser" description = "Style preserving TOML library"
optional = false optional = false
python-versions = ">=3.7" python-versions = ">=3.8"
files = [ files = [
{file = "tomli-2.0.1-py3-none-any.whl", hash = "sha256:939de3e7a6161af0c887ef91b7d41a53e7c5a1ca976325f429cb46ea9bc30ecc"}, {file = "tomlkit-0.13.2-py3-none-any.whl", hash = "sha256:7a974427f6e119197f670fbbbeae7bef749a6c14e793db934baefc1b5f03efde"},
{file = "tomli-2.0.1.tar.gz", hash = "sha256:de526c12914f0c550d15924c62d72abc48d6fe7364aa87328337a31007fe8a4f"}, {file = "tomlkit-0.13.2.tar.gz", hash = "sha256:fff5fe59a87295b278abd31bec92c15d9bc4a06885ab12bcea52c71119392e79"},
] ]
[[package]] [[package]]
@ -829,4 +880,4 @@ files = [
[metadata] [metadata]
lock-version = "2.0" lock-version = "2.0"
python-versions = "^3.12" python-versions = "^3.12"
content-hash = "477748fbc18bde095d13dea548108541c1b584242099398155787361b1dc31fe" content-hash = "7321f58bda2e65a4a0674d43997ce31402e0fed876a77b37a1b86d83d569707a"

View File

@ -1,3 +1,7 @@
[project]
organization = "de.uni-tuebingen.neuroetho"
copyright = "(c) 2020, Neuroethology lab, Uni Tuebingen"
[tool.poetry] [tool.poetry]
name = "pyrelacs" name = "pyrelacs"
version = "0.1.0" version = "0.1.0"
@ -6,14 +10,11 @@ authors = ["wendtalexander <wendtalexander@protonmail.com>"]
repository = "https://whale.am28.uni-tuebingen.de/git/awendt/pyrelacs" repository = "https://whale.am28.uni-tuebingen.de/git/awendt/pyrelacs"
readme = "README.md" readme = "README.md"
license = "MIT" license = "MIT"
organization = "de.uni-tuebingen.neuroetho"
classifiers = [ classifiers = [
"Topic :: Scientific/Engineering", "Topic :: Scientific/Engineering",
"Intended Audience :: Science/Research", "Intended Audience :: Science/Research",
"Intended Audience :: End Users/Desktop", "Intended Audience :: End Users/Desktop",
] ]
copyright = "(c) 2020, Neuroethology lab, Uni Tuebingen"
include = [ include = [
{ path = "pyproject.toml" } { path = "pyproject.toml" }
] ]
@ -23,15 +24,16 @@ python = "^3.12"
uldaq = "^1.2.3" uldaq = "^1.2.3"
typer = "^0.12.5" typer = "^0.12.5"
matplotlib = "^3.9.2" matplotlib = "^3.9.2"
numpy = "^2.1.1" numpy = "^1.9"
pyqt6 = "^6.7.1" pyqt6 = "^6.7.1"
tomli = "^2.0.1"
tomlkit = "^0.13.2" tomlkit = "^0.13.2"
scipy = "^1.14.1" scipy = "^1.14.1"
nixio = "^1.5.3"
pyqtgraph = "^0.13.7"
[tool.poetry.scripts] [tool.poetry.scripts]
pyrelacs = "pyrelacs.app:main" pyrelacs = "pyrelacs.app:main"
[build-system] [build-system]
requires = ["poetry-core"] requires = ["poetry-core>=1.0.0"]
build-backend = "poetry.core.masonry.api" build-backend = "poetry.core.masonry.api"

View File

@ -1,8 +1,8 @@
import pathlib
from PyQt6.QtGui import QAction from PyQt6.QtGui import QAction
import sys import sys
import pathlib
from PyQt6.QtCore import QProcess, QSize, QThreadPool, Qt, QSettings from PyQt6.QtCore import QSize, QThreadPool, QSettings
from PyQt6.QtWidgets import ( from PyQt6.QtWidgets import (
QApplication, QApplication,
QGridLayout, QGridLayout,
@ -12,9 +12,12 @@ from PyQt6.QtWidgets import (
QMainWindow, QMainWindow,
QPlainTextEdit, QPlainTextEdit,
) )
import pyqtgraph as pg
import uldaq import uldaq
from IPython import embed from IPython import embed
from scipy.signal import welch, find_peaks
import numpy as np import numpy as np
import nixio as nix
from pyrelacs.util.logging import config_logging from pyrelacs.util.logging import config_logging
import pyrelacs.info as info import pyrelacs.info as info
@ -29,6 +32,7 @@ class PyRelacs(QMainWindow):
super().__init__() super().__init__()
self.setWindowTitle("PyRelacs") self.setWindowTitle("PyRelacs")
self.setMinimumSize(1000, 1000) self.setMinimumSize(1000, 1000)
self.plot_graph = pg.PlotWidget()
self.threadpool = QThreadPool() self.threadpool = QThreadPool()
self.repros = Repro() self.repros = Repro()
@ -41,13 +45,18 @@ class PyRelacs(QMainWindow):
self.daq_disconnect_button.setCheckable(True) self.daq_disconnect_button.setCheckable(True)
self.daq_disconnect_button.clicked.connect(self.disconnect_dac) self.daq_disconnect_button.clicked.connect(self.disconnect_dac)
self.plot_calibration_button = QPushButton("Plot Calibration")
self.plot_calibration_button.setCheckable(True)
self.plot_calibration_button.clicked.connect(self.plot_calibration)
self.text = QPlainTextEdit() self.text = QPlainTextEdit()
self.text.setReadOnly(True) self.text.setReadOnly(True)
layout = QGridLayout() layout = QGridLayout()
layout.addWidget(self.daq_connect_button, 0, 0) layout.addWidget(self.plot_calibration_button, 0, 0)
layout.addWidget(self.daq_disconnect_button, 0, 1) layout.addWidget(self.daq_disconnect_button, 0, 1)
layout.addWidget(self.text, 2, 0, 1, 2) layout.addWidget(self.text, 3, 0, 1, 2)
layout.addWidget(self.plot_graph, 2, 0, 1, 2)
self.toolbar = QToolBar("Repros") self.toolbar = QToolBar("Repros")
self.addToolBar(self.toolbar) self.addToolBar(self.toolbar)
@ -58,6 +67,67 @@ class PyRelacs(QMainWindow):
widget.setLayout(layout) widget.setLayout(layout)
self.setCentralWidget(widget) self.setCentralWidget(widget)
self.nix_file = nix.File.open(
str(pathlib.Path(__file__).parent / "data"), nix.FileMode.ReadOnly
)
def plot_calibration(self):
def decibel(power, ref_power=1.0, min_power=1e-20):
"""Transform power to decibel relative to ref_power.
\\[ decibel = 10 \\cdot \\log_{10}(power/ref\\_power) \\]
Power values smaller than `min_power` are set to `-np.inf`.
Parameters
----------
power: float or array
Power values, for example from a power spectrum or spectrogram.
ref_power: float or None or 'peak'
Reference power for computing decibel.
If set to `None` or 'peak', the maximum power is used.
min_power: float
Power values smaller than `min_power` are set to `-np.inf`.
Returns
-------
decibel_psd: array
Power values in decibel relative to `ref_power`.
"""
if np.isscalar(power):
tmp_power = np.array([power])
decibel_psd = np.array([power])
else:
tmp_power = power
decibel_psd = power.copy()
if ref_power is None or ref_power == "peak":
ref_power = np.max(decibel_psd)
decibel_psd[tmp_power <= min_power] = float("-inf")
decibel_psd[tmp_power > min_power] = 10.0 * np.log10(
decibel_psd[tmp_power > min_power] / ref_power
)
if np.isscalar(power):
return decibel_psd[0]
else:
return decibel_psd
block = self.nix_file.blocks[0]
for stim, fish in zip(
list(block.data_arrays)[::2], list(block.data_arrays)[1::2]
):
beat = stim[:] + fish[:]
beat_squared = beat**2
f, powerspec = welch(beat, fs=40_000.0)
powerspec = decibel(powerspec)
f_sq, powerspec_sq = welch(beat_squared, fs=40_000.0)
powerspec_sq = decibel(powerspec_sq)
peaks = find_peaks(powerspec_sq, prominence=20)[0]
pen = pg.mkPen()
self.plot_graph.plot(
np.arange(0, len(beat)) / 40_000.0, beat_squared, pen=pen
)
def connect_dac(self): def connect_dac(self):
devices = uldaq.get_daq_device_inventory(uldaq.InterfaceType.USB) devices = uldaq.get_daq_device_inventory(uldaq.InterfaceType.USB)
try: try:
@ -93,7 +163,7 @@ class PyRelacs(QMainWindow):
def run_repro(self, n, fn): def run_repro(self, n, fn):
self.text.appendPlainText(f"started Repro {n}, {fn}") self.text.appendPlainText(f"started Repro {n}, {fn}")
worker = Worker(self.repros.run_repro, n, fn) worker = Worker(self.repros.run_repro, self.nix_file, n, fn)
worker.signals.result.connect(self.print_output) worker.signals.result.connect(self.print_output)
worker.signals.finished.connect(self.thread_complete) worker.signals.finished.connect(self.thread_complete)
worker.signals.progress.connect(self.progress_fn) worker.signals.progress.connect(self.progress_fn)
@ -142,4 +212,3 @@ def main():
if __name__ == "__main__": if __name__ == "__main__":
main() main()

BIN
pyrelacs/data Normal file

Binary file not shown.

View File

@ -1,9 +1,10 @@
import tomlkit import tomlkit
import pathlib import pathlib
def load_project_settings(project_root): def load_project_settings(project_root):
# Read the pyproject.toml file # Read the pyproject.toml file
with open(pathlib.Path.joinpath(project_root, 'pyproject.toml'), 'r') as f: with open(pathlib.Path.joinpath(project_root, "pyproject.toml"), "r") as f:
pyproject_content = f.read() pyproject_content = f.read()
# Parse the toml content # Parse the toml content
@ -11,16 +12,16 @@ def load_project_settings(project_root):
# Access project settings # Access project settings
return { return {
'name': pyproject['tool']['poetry']['name'], "name": pyproject["tool"]["poetry"]["name"],
'version': pyproject['tool']['poetry']['version'], "version": pyproject["tool"]["poetry"]["version"],
'description': pyproject['tool']['poetry']['description'], "description": pyproject["tool"]["poetry"]["description"],
'authors': pyproject['tool']['poetry']['authors'], "authors": pyproject["tool"]["poetry"]["authors"],
'readme': pyproject['tool']['poetry']['authors'], "readme": pyproject["tool"]["poetry"]["authors"],
'licence': pyproject['tool']['poetry']['license'], "licence": pyproject["tool"]["poetry"]["license"],
'organization': pyproject['tool']['poetry']['organization'], "organization": pyproject["project"]["organization"],
'classifiers': pyproject['tool']['poetry']['classifiers'], "classifiers": pyproject["tool"]["poetry"]["classifiers"],
'copyright': pyproject['tool']['poetry']['copyright'], "copyright": pyproject["project"]["copyright"],
"repository": pyproject['tool']['poetry']['repository'], "repository": pyproject["tool"]["poetry"]["repository"],
} }

View File

@ -3,6 +3,7 @@ import sys
import faulthandler import faulthandler
import time import time
import nixio as nix
import uldaq import uldaq
from IPython import embed from IPython import embed
import numpy as np import numpy as np
@ -26,9 +27,9 @@ class Calibration(MccDac):
self.SINFREQ = 750 self.SINFREQ = 750
@staticmethod @staticmethod
def run(): def run(nix_file: nix.File):
calb = Calibration() calb = Calibration()
calb.check_beat() calb.check_beat(nix_file)
def check_amplitude(self): def check_amplitude(self):
db_values = [0.0, -5.0, -10.0, -20.0, -50.0] db_values = [0.0, -5.0, -10.0, -20.0, -50.0]
@ -84,7 +85,7 @@ class Calibration(MccDac):
self.disconnect_dac() self.disconnect_dac()
def check_beat(self): def check_beat(self, nix_file: nix.File):
self.set_attenuation_level(db_channel1=-10.0, db_channel2=0.0) self.set_attenuation_level(db_channel1=-10.0, db_channel2=0.0)
t = np.arange(0, self.DURATION, 1 / self.SAMPLERATE) t = np.arange(0, self.DURATION, 1 / self.SAMPLERATE)
data = self.AMPLITUDE * np.sin(2 * np.pi * self.SINFREQ * t) data = self.AMPLITUDE * np.sin(2 * np.pi * self.SINFREQ * t)
@ -92,7 +93,8 @@ class Calibration(MccDac):
db_values = [0.0, -5.0, -8.5, -10.0] db_values = [0.0, -5.0, -8.5, -10.0]
colors = ["red", "blue", "black", "green"] colors = ["red", "blue", "black", "green"]
colors_in = ["lightcoral", "lightblue", "grey", "lightgreen"] colors_in = ["lightcoral", "lightblue", "grey", "lightgreen"]
fig, axes = plt.subplots(2, 2, sharex="col") block = nix_file.create_block("Calibration", "data")
# fig, axes = plt.subplots(2, 2, sharex="col")
for i, db_value in enumerate(db_values): for i, db_value in enumerate(db_values):
self.set_attenuation_level(db_channel1=db_value) self.set_attenuation_level(db_channel1=db_value)
stim = self.write_analog( stim = self.write_analog(
@ -127,8 +129,27 @@ class Calibration(MccDac):
log.debug( log.debug(
f"Status Analog_output {ao_status}\n, Status Analog_input {ai_status}" f"Status Analog_output {ao_status}\n, Status Analog_input {ai_status}"
) )
channel1 = np.array(readout[::2]) channel1 = np.array(readout[::2])
channel2 = np.array(readout[1::2]) channel2 = np.array(readout[1::2])
block.create_data_array(
f"stimulus_{db_value}",
"Array",
shape=data.shape,
data=channel1,
label="Voltage",
unit="V",
)
block.create_data_array(
f"fish_{db_value}",
"Array",
shape=data.shape,
data=channel2,
label="Voltage",
unit="V",
)
beat = channel1 + channel2 beat = channel1 + channel2
beat_square = beat**2 beat_square = beat**2
@ -145,69 +166,69 @@ class Calibration(MccDac):
f_in, powerspec_in = welch(channel2, fs=self.SAMPLERATE) f_in, powerspec_in = welch(channel2, fs=self.SAMPLERATE)
powerspec_in = decibel(powerspec_in) powerspec_in = decibel(powerspec_in)
axes[0, 0].plot( # axes[0, 0].plot(
t, # t,
channel1, # channel1,
label=f"{db_value} Readout Channel0", # label=f"{db_value} Readout Channel0",
color=colors[i], # color=colors[i],
) # )
axes[0, 0].plot( # axes[0, 0].plot(
t, # t,
channel2, # channel2,
label=f"{db_value} Readout Channel1", # label=f"{db_value} Readout Channel1",
color=colors_in[i], # color=colors_in[i],
) # )
#
axes[0, 1].plot( # axes[0, 1].plot(
f_stim, # f_stim,
powerspec_stim, # powerspec_stim,
label=f"{db_value} powerspec Channel0", # label=f"{db_value} powerspec Channel0",
color=colors[i], # color=colors[i],
) # )
axes[0, 1].plot( # axes[0, 1].plot(
f_in, # f_in,
powerspec_in, # powerspec_in,
label=f"{db_value} powerspec Channel2", # label=f"{db_value} powerspec Channel2",
color=colors_in[i], # color=colors_in[i],
) # )
axes[0, 1].set_xlabel("Freq [HZ]") # axes[0, 1].set_xlabel("Freq [HZ]")
axes[0, 1].set_ylabel("dB") # axes[0, 1].set_ylabel("dB")
#
axes[1, 0].plot( # axes[1, 0].plot(
t, # t,
beat, # beat,
label="Beat", # label="Beat",
color=colors[i], # color=colors[i],
) # )
axes[1, 0].plot( # axes[1, 0].plot(
t, # t,
beat**2, # beat**2,
label="Beat squared", # label="Beat squared",
color=colors_in[i], # color=colors_in[i],
) # )
axes[1, 0].legend() # axes[1, 0].legend()
#
axes[1, 1].plot( # axes[1, 1].plot(
f, # f,
powerspec, # powerspec,
color=colors[i], # color=colors[i],
) # )
axes[1, 1].plot( # axes[1, 1].plot(
f_sq, # f_sq,
powerspec_sq, # powerspec_sq,
color=colors_in[i], # color=colors_in[i],
label=f"dB {db_value}, first peak {np.min(f_sq[peaks])}", # label=f"dB {db_value}, first peak {np.min(f_sq[peaks])}",
) # )
axes[1, 1].scatter( # axes[1, 1].scatter(
f_sq[peaks], # f_sq[peaks],
powerspec_sq[peaks], # powerspec_sq[peaks],
color="maroon", # color="maroon",
) # )
axes[1, 1].set_xlabel("Freq [HZ]") # axes[1, 1].set_xlabel("Freq [HZ]")
axes[1, 1].set_ylabel("dB") # axes[1, 1].set_ylabel("dB")
axes[0, 0].legend() # axes[0, 0].legend()
axes[1, 1].legend() # axes[1, 1].legend()
plt.show() # plt.show()
self.set_analog_to_zero() self.set_analog_to_zero()
self.disconnect_dac() self.disconnect_dac()

View File

@ -4,6 +4,7 @@ import ast
import pathlib import pathlib
from IPython import embed from IPython import embed
import nixio as nix
from pyrelacs.util.logging import config_logging from pyrelacs.util.logging import config_logging
log = config_logging() log = config_logging()
@ -13,22 +14,24 @@ class Repro:
def __init__(self) -> None: def __init__(self) -> None:
pass pass
def run_repro(self, name: str, file: pathlib.Path, *args, **kwargs) -> None: def run_repro(
self, nix_file: nix.File, name: str, file: pathlib.Path, *args, **kwargs
) -> None:
spec = importlib.util.spec_from_file_location("rep", file) spec = importlib.util.spec_from_file_location("rep", file)
if not spec: if not spec:
log.error("Could not load the repro") log.error("Could not load the file")
else: else:
module = importlib.util.module_from_spec(spec) module = importlib.util.module_from_spec(spec)
if not module: if not module:
log.error("Could not load Class of the repro") log.error("Could not load the module of the repro")
else: else:
sys.modules[name] = module sys.modules[name] = module
spec.loader.exec_module(module) spec.loader.exec_module(module)
if hasattr(module, name): if hasattr(module, name):
rep_class = getattr(module, name) rep_class = getattr(module, name)
rep_class.run() rep_class.run(nix_file)
else: else:
raise AttributeError(f"{name} has no run function") raise AttributeError(f"{file.name} has no {name} class")
def names_of_repros(self): def names_of_repros(self):
file_path_cur = pathlib.Path(__file__).parent file_path_cur = pathlib.Path(__file__).parent