Merge branch 'develop' into yolov8-obb

This commit is contained in:
SkalskiP committed 2024-01-24 16:49:00 +01:00
commit 164b9bedce
32 files changed
+1364 -1150

No files matched your search

-1
View File
@@ -38,7 +38,6 @@ jobs:
numpy==1.21.2 \
opencv-python==4.5.5.64 \
packaging==23.2 \
Pillow==10.1.0 \
pluggy==1.3.0 \
pyparsing==3.1.1 \
pytest==7.2.0 \
+1
View File
@@ -13,6 +13,7 @@ repos:
- id: trailing-whitespace
exclude: test/.*\.py
- id: check-yaml
exclude: mkdocs.yml
- id: check-docstring-first
- id: check-executables-have-shebangs
- id: check-toml
+1 -1
View File
@@ -52,7 +52,7 @@ git push -u origin main
### Pre-commit tool
This project utilizes the [pre-commit](https://pre-commit.com/) tool to maintain code quality and consistency. Before submitting a pull request or making any commits, it is important to run the pre-commit tool to ensure that your changes meet the project's guidelines.
This project uses the [pre-commit](https://pre-commit.com/) tool to maintain code quality and consistency. Before submitting a pull request or making any commits, it is important to run the pre-commit tool to ensure that your changes meet the project's guidelines.
Furthermore, we have integrated a pre-commit GitHub Action into our workflow. This means that with every pull request opened, the pre-commit checks will be automatically enforced, streamlining the code review process and ensuring that all contributions adhere to our quality standards.
+89 -89
View File
@@ -46,17 +46,17 @@ Read more about desktop, headless, and local installation in our [guide](https:/
Supervision was designed to be model agnostic. Just plug in any classification, detection, or segmentation model. For your convenience, we have created [connectors](https://supervision.roboflow.com/detection/core/#detections) for the most popular libraries like Ultralytics, Transformers, or MMDetection.
```python
>>> import cv2
>>> import supervision as sv
>>> from ultralytics import YOLO
import cv2
import supervision as sv
from ultralytics import YOLO
>>> image = cv2.imread(...)
>>> model = YOLO('yolov8s.pt')
>>> result = model(image)[0]
>>> detections = sv.Detections.from_ultralytics(result)
image = cv2.imread(...)
model = YOLO('yolov8s.pt')
result = model(image)[0]
detections = sv.Detections.from_ultralytics(result)
>>> len(detections)
5
len(detections)
# 5
```
<details>
@@ -67,17 +67,17 @@ Supervision was designed to be model agnostic. Just plug in any classification,
Running with [Inference](https://github.com/roboflow/inference) requires a [Roboflow API KEY](https://docs.roboflow.com/api-reference/authentication#retrieve-an-api-key).
```python
>>> import cv2
>>> import supervision as sv
>>> from inference.models.utils import get_roboflow_model
import cv2
import supervision as sv
from inference.models.utils import get_roboflow_model
>>> image = cv2.imread(...)
>>> model = get_roboflow_model(model_id="yolov8s-640", api_key=<ROBOFLOW API KEY>)
>>> result = model.infer(image)[0]
>>> detections = sv.Detections.from_inference(result)
image = cv2.imread(...)
model = get_roboflow_model(model_id="yolov8s-640", api_key=<ROBOFLOW API KEY>)
result = model.infer(image)[0]
detections = sv.Detections.from_inference(result)
>>> len(detections)
>>> 5
len(detections)
# 5
```
@@ -88,17 +88,17 @@ Supervision was designed to be model agnostic. Just plug in any classification,
Supervision offers a wide range of highly customizable [annotators](https://supervision.roboflow.com/annotators/), allowing you to compose the perfect visualization for your use case.
```python
>>> import cv2
>>> import supervision as sv
import cv2
import supervision as sv
>>> image = cv2.imread(...)
>>> detections = sv.Detections(...)
image = cv2.imread(...)
detections = sv.Detections(...)
>>> bounding_box_annotator = sv.BoundingBoxAnnotator()
>>> annotated_frame = bounding_box_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
bounding_box_annotator = sv.BoundingBoxAnnotator()
annotated_frame = bounding_box_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
https://github.com/roboflow/supervision/assets/26109316/691e219c-0565-4403-9218-ab5644f39bce
@@ -108,19 +108,19 @@ https://github.com/roboflow/supervision/assets/26109316/691e219c-0565-4403-9218-
Supervision provides a set of [utils](https://supervision.roboflow.com/datasets/) that allow you to load, split, merge, and save datasets in one of the supported formats.
```python
>>> import supervision as sv
import supervision as sv
>>> dataset = sv.DetectionDataset.from_yolo(
... images_directory_path=...,
... annotations_directory_path=...,
... data_yaml_path=...
... )
dataset = sv.DetectionDataset.from_yolo(
images_directory_path=...,
annotations_directory_path=...,
data_yaml_path=...
)
>>> dataset.classes
dataset.classes
['dog', 'person']
>>> len(dataset)
1000
len(dataset)
# 1000
```
<details close>
@@ -129,86 +129,86 @@ Supervision provides a set of [utils](https://supervision.roboflow.com/datasets/
- load
```python
>>> dataset = sv.DetectionDataset.from_yolo(
... images_directory_path=...,
... annotations_directory_path=...,
... data_yaml_path=...
... )
dataset = sv.DetectionDataset.from_yolo(
images_directory_path=...,
annotations_directory_path=...,
data_yaml_path=...
)
>>> dataset = sv.DetectionDataset.from_pascal_voc(
... images_directory_path=...,
... annotations_directory_path=...
... )
dataset = sv.DetectionDataset.from_pascal_voc(
images_directory_path=...,
annotations_directory_path=...
)
>>> dataset = sv.DetectionDataset.from_coco(
... images_directory_path=...,
... annotations_path=...
... )
dataset = sv.DetectionDataset.from_coco(
images_directory_path=...,
annotations_path=...
)
```
- split
```python
>>> train_dataset, test_dataset = dataset.split(split_ratio=0.7)
>>> test_dataset, valid_dataset = test_dataset.split(split_ratio=0.5)
train_dataset, test_dataset = dataset.split(split_ratio=0.7)
test_dataset, valid_dataset = test_dataset.split(split_ratio=0.5)
>>> len(train_dataset), len(test_dataset), len(valid_dataset)
(700, 150, 150)
len(train_dataset), len(test_dataset), len(valid_dataset)
# (700, 150, 150)
```
- merge
```python
>>> ds_1 = sv.DetectionDataset(...)
>>> len(ds_1)
100
>>> ds_1.classes
['dog', 'person']
ds_1 = sv.DetectionDataset(...)
len(ds_1)
# 100
ds_1.classes
# ['dog', 'person']
>>> ds_2 = sv.DetectionDataset(...)
>>> len(ds_2)
200
>>> ds_2.classes
['cat']
ds_2 = sv.DetectionDataset(...)
len(ds_2)
# 200
ds_2.classes
# ['cat']
>>> ds_merged = sv.DetectionDataset.merge([ds_1, ds_2])
>>> len(ds_merged)
300
>>> ds_merged.classes
['cat', 'dog', 'person']
ds_merged = sv.DetectionDataset.merge([ds_1, ds_2])
len(ds_merged)
# 300
ds_merged.classes
# ['cat', 'dog', 'person']
```
- save
```python
>>> dataset.as_yolo(
... images_directory_path=...,
... annotations_directory_path=...,
... data_yaml_path=...
... )
dataset.as_yolo(
images_directory_path=...,
annotations_directory_path=...,
data_yaml_path=...
)
>>> dataset.as_pascal_voc(
... images_directory_path=...,
... annotations_directory_path=...
... )
dataset.as_pascal_voc(
images_directory_path=...,
annotations_directory_path=...
)
>>> dataset.as_coco(
... images_directory_path=...,
... annotations_path=...
... )
dataset.as_coco(
images_directory_path=...,
annotations_path=...
)
```
- convert
```python
>>> sv.DetectionDataset.from_yolo(
... images_directory_path=...,
... annotations_directory_path=...,
... data_yaml_path=...
... ).as_pascal_voc(
... images_directory_path=...,
... annotations_directory_path=...
... )
sv.DetectionDataset.from_yolo(
images_directory_path=...,
annotations_directory_path=...,
data_yaml_path=...
).as_pascal_voc(
images_directory_path=...,
annotations_directory_path=...
)
```
</details>
+151 -150
View File
@@ -1,20 +1,21 @@
---
comments: true
status: new
---
=== "BoundingBox"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> bounding_box_annotator = sv.BoundingBoxAnnotator()
>>> annotated_frame = bounding_box_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
bounding_box_annotator = sv.BoundingBoxAnnotator()
annotated_frame = bounding_box_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -26,16 +27,16 @@ comments: true
=== "RoundBox"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> round_box_annotator = sv.RoundBoxAnnotator()
>>> annotated_frame = round_box_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
round_box_annotator = sv.RoundBoxAnnotator()
annotated_frame = round_box_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -47,16 +48,16 @@ comments: true
=== "BoxCorner"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> corner_annotator = sv.BoxCornerAnnotator()
>>> annotated_frame = corner_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
corner_annotator = sv.BoxCornerAnnotator()
annotated_frame = corner_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -89,16 +90,16 @@ comments: true
=== "Color"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> color_annotator = sv.ColorAnnotator()
>>> annotated_frame = color_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
color_annotator = sv.ColorAnnotator()
annotated_frame = color_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -110,16 +111,16 @@ comments: true
=== "Circle"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> circle_annotator = sv.CircleAnnotator()
>>> annotated_frame = circle_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
circle_annotator = sv.CircleAnnotator()
annotated_frame = circle_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -131,16 +132,16 @@ comments: true
=== "Dot"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> dot_annotator = sv.DotAnnotator()
>>> annotated_frame = dot_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
dot_annotator = sv.DotAnnotator()
annotated_frame = dot_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -152,16 +153,16 @@ comments: true
=== "Triangle"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> triangle_annotator = sv.TriangleAnnotator()
>>> annotated_frame = triangle_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
triangle_annotator = sv.TriangleAnnotator()
annotated_frame = triangle_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -173,16 +174,16 @@ comments: true
=== "Ellipse"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> ellipse_annotator = sv.EllipseAnnotator()
>>> annotated_frame = ellipse_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
ellipse_annotator = sv.EllipseAnnotator()
annotated_frame = ellipse_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -194,16 +195,16 @@ comments: true
=== "Halo"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> halo_annotator = sv.HaloAnnotator()
>>> annotated_frame = halo_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
halo_annotator = sv.HaloAnnotator()
annotated_frame = halo_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -215,16 +216,16 @@ comments: true
=== "PercentageBar"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> percentage_bar_annotator = sv.PercentageBarAnnotator()
>>> annotated_frame = percentage_bar_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
percentage_bar_annotator = sv.PercentageBarAnnotator()
annotated_frame = percentage_bar_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -236,16 +237,16 @@ comments: true
=== "Mask"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> mask_annotator = sv.MaskAnnotator()
>>> annotated_frame = mask_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
mask_annotator = sv.MaskAnnotator()
annotated_frame = mask_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -257,16 +258,16 @@ comments: true
=== "Polygon"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> polygon_annotator = sv.PolygonAnnotator()
>>> annotated_frame = polygon_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
polygon_annotator = sv.PolygonAnnotator()
annotated_frame = polygon_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -278,16 +279,16 @@ comments: true
=== "Label"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> label_annotator = sv.LabelAnnotator(text_position=sv.Position.CENTER)
>>> annotated_frame = label_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
label_annotator = sv.LabelAnnotator(text_position=sv.Position.CENTER)
annotated_frame = label_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -299,16 +300,16 @@ comments: true
=== "Blur"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> blur_annotator = sv.BlurAnnotator()
>>> annotated_frame = blur_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
blur_annotator = sv.BlurAnnotator()
annotated_frame = blur_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -320,16 +321,16 @@ comments: true
=== "Pixelate"
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> pixelate_annotator = sv.PixelateAnnotator()
>>> annotated_frame = pixelate_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
pixelate_annotator = sv.PixelateAnnotator()
annotated_frame = pixelate_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
<div class="result" markdown>
@@ -341,26 +342,26 @@ comments: true
=== "Trace"
```python
>>> import supervision as sv
>>> from ultralytics import YOLO
import supervision as sv
from ultralytics import YOLO
>>> model = YOLO('yolov8x.pt')
model = YOLO('yolov8x.pt')
>>> trace_annotator = sv.TraceAnnotator()
trace_annotator = sv.TraceAnnotator()
>>> video_info = sv.VideoInfo.from_video_path(video_path='...')
>>> frames_generator = get_video_frames_generator(source_path='...')
>>> tracker = sv.ByteTrack()
video_info = sv.VideoInfo.from_video_path(video_path='...')
frames_generator = get_video_frames_generator(source_path='...')
tracker = sv.ByteTrack()
>>> with sv.VideoSink(target_path='...', video_info=video_info) as sink:
... for frame in frames_generator:
... result = model(frame)[0]
... detections = sv.Detections.from_ultralytics(result)
... detections = tracker.update_with_detections(detections)
... annotated_frame = trace_annotator.annotate(
... scene=frame.copy(),
... detections=detections)
... sink.write_frame(frame=annotated_frame)
with sv.VideoSink(target_path='...', video_info=video_info) as sink:
for frame in frames_generator:
result = model(frame)[0]
detections = sv.Detections.from_ultralytics(result)
detections = tracker.update_with_detections(detections)
annotated_frame = trace_annotator.annotate(
scene=frame.copy(),
detections=detections)
sink.write_frame(frame=annotated_frame)
```
<div class="result" markdown>
@@ -372,24 +373,24 @@ comments: true
=== "HeatMap"
```python
>>> import supervision as sv
>>> from ultralytics import YOLO
import supervision as sv
from ultralytics import YOLO
>>> model = YOLO('yolov8x.pt')
model = YOLO('yolov8x.pt')
>>> heat_map_annotator = sv.HeatMapAnnotator()
heat_map_annotator = sv.HeatMapAnnotator()
>>> video_info = sv.VideoInfo.from_video_path(video_path='...')
>>> frames_generator = get_video_frames_generator(source_path='...')
video_info = sv.VideoInfo.from_video_path(video_path='...')
frames_generator = get_video_frames_generator(source_path='...')
>>> with sv.VideoSink(target_path='...', video_info=video_info) as sink:
... for frame in frames_generator:
... result = model(frame)[0]
... detections = sv.Detections.from_ultralytics(result)
... annotated_frame = heat_map_annotator.annotate(
... scene=frame.copy(),
... detections=detections)
... sink.write_frame(frame=annotated_frame)
with sv.VideoSink(target_path='...', video_info=video_info) as sink:
for frame in frames_generator:
result = model(frame)[0]
detections = sv.Detections.from_ultralytics(result)
annotated_frame = heat_map_annotator.annotate(
scene=frame.copy(),
detections=detections)
sink.write_frame(frame=annotated_frame)
```
<div class="result" markdown>
+1
View File
@@ -1,5 +1,6 @@
---
comments: true
status: new
---
## Detections
+8
View File
@@ -0,0 +1,8 @@
---
comments: true
status: new
---
## Detection Smoother
:::supervision.detection.tools.smoother.DetectionsSmoother
-5
View File
@@ -1,5 +0,0 @@
---
comments: true
---
🚧 Page under construction.
-5
View File
@@ -1,5 +0,0 @@
---
comments: true
---
🚧 Page under construction.
+32
View File
@@ -17,6 +17,38 @@ comments: true
We write your reusable computer vision tools. Whether you need to load your dataset from your hard drive, draw detections on an image or video, or count how many detections are in a zone. You can count on us!
<div class="grid cards" markdown>
- __Detect and Annotate__
---
Annotate predictions from a range of object detection and segmentation models
[:octicons-arrow-right-24: Tutorial](how_to/detect_and_annotate)
- __Track Objects__
---
Discover how to enhance video analysis by implementing seamless object tracking
[:octicons-arrow-right-24: Tutorial](how_to/track_objects)
- > __Count Objects Crossing Line__
---
Explore methods to accurately count and analyze objects crossing a predefined line
- > __Filter Objects in Zone__
---
Master the techniques to selectively filter and focus on objects within a specific zone
</div>
## 💻 Install
You can install `supervision` with pip in a
+5 -2
View File
@@ -28,10 +28,8 @@ nav:
- Home: index.md
- How to:
- Detect and Annotate: how_to/detect_and_annotate.md
- Process Video: how_to/process_video.md
- Track Objects: how_to/track_objects.md
- Filter Detections: how_to/filter_detections.md
- Evaluate Model: how_to/evaluate_model.md
- API:
- Classifications:
- Core: classification/core.md
@@ -42,6 +40,7 @@ nav:
- Line Zone: detection/tools/line_zone.md
- Polygon Zone: detection/tools/polygon_zone.md
- Inference Slicer: detection/tools/inference_slicer.md
- Detection Smoother: detection/tools/smoother.md
- Annotators: annotators.md
- Trackers: trackers.md
- Datasets: datasets.md
@@ -82,6 +81,7 @@ theme:
code: Roboto Mono
features:
- content.code.copy
- content.code.annotate
plugins:
- mkdocstrings
@@ -97,6 +97,9 @@ markdown_extensions:
alternate_style: true
- toc:
permalink: true
- pymdownx.emoji:
emoji_index: !!python/name:material.extensions.emoji.twemoji
emoji_generator: !!python/name:material.extensions.emoji.to_svg
extra_javascript:
- "https://widget.kapa.ai/kapa-widget.bundle.js"
Generated
+275 -212
View File
@@ -672,47 +672,56 @@ test-no-images = ["pytest", "pytest-cov", "wurlitzer"]
[[package]]
name = "cryptography"
version = "41.0.7"
version = "42.0.0"
description = "cryptography is a package which provides cryptographic recipes and primitives to Python developers."
optional = false
python-versions = ">=3.7"
files = [
{file = "cryptography-41.0.7-cp37-abi3-macosx_10_12_universal2.whl", hash = "sha256:3c78451b78313fa81607fa1b3f1ae0a5ddd8014c38a02d9db0616133987b9cdf"},
{file = "cryptography-41.0.7-cp37-abi3-macosx_10_12_x86_64.whl", hash = "sha256:928258ba5d6f8ae644e764d0f996d61a8777559f72dfeb2eea7e2fe0ad6e782d"},
{file = "cryptography-41.0.7-cp37-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5a1b41bc97f1ad230a41657d9155113c7521953869ae57ac39ac7f1bb471469a"},
{file = "cryptography-41.0.7-cp37-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:841df4caa01008bad253bce2a6f7b47f86dc9f08df4b433c404def869f590a15"},
{file = "cryptography-41.0.7-cp37-abi3-manylinux_2_28_aarch64.whl", hash = "sha256:5429ec739a29df2e29e15d082f1d9ad683701f0ec7709ca479b3ff2708dae65a"},
{file = "cryptography-41.0.7-cp37-abi3-manylinux_2_28_x86_64.whl", hash = "sha256:43f2552a2378b44869fe8827aa19e69512e3245a219104438692385b0ee119d1"},
{file = "cryptography-41.0.7-cp37-abi3-musllinux_1_1_aarch64.whl", hash = "sha256:af03b32695b24d85a75d40e1ba39ffe7db7ffcb099fe507b39fd41a565f1b157"},
{file = "cryptography-41.0.7-cp37-abi3-musllinux_1_1_x86_64.whl", hash = "sha256:49f0805fc0b2ac8d4882dd52f4a3b935b210935d500b6b805f321addc8177406"},
{file = "cryptography-41.0.7-cp37-abi3-win32.whl", hash = "sha256:f983596065a18a2183e7f79ab3fd4c475205b839e02cbc0efbbf9666c4b3083d"},
{file = "cryptography-41.0.7-cp37-abi3-win_amd64.whl", hash = "sha256:90452ba79b8788fa380dfb587cca692976ef4e757b194b093d845e8d99f612f2"},
{file = "cryptography-41.0.7-pp310-pypy310_pp73-macosx_10_12_x86_64.whl", hash = "sha256:079b85658ea2f59c4f43b70f8119a52414cdb7be34da5d019a77bf96d473b960"},
{file = "cryptography-41.0.7-pp310-pypy310_pp73-manylinux_2_28_aarch64.whl", hash = "sha256:b640981bf64a3e978a56167594a0e97db71c89a479da8e175d8bb5be5178c003"},
{file = "cryptography-41.0.7-pp310-pypy310_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:e3114da6d7f95d2dee7d3f4eec16dacff819740bbab931aff8648cb13c5ff5e7"},
{file = "cryptography-41.0.7-pp310-pypy310_pp73-win_amd64.whl", hash = "sha256:d5ec85080cce7b0513cfd233914eb8b7bbd0633f1d1703aa28d1dd5a72f678ec"},
{file = "cryptography-41.0.7-pp38-pypy38_pp73-macosx_10_12_x86_64.whl", hash = "sha256:7a698cb1dac82c35fcf8fe3417a3aaba97de16a01ac914b89a0889d364d2f6be"},
{file = "cryptography-41.0.7-pp38-pypy38_pp73-manylinux_2_28_aarch64.whl", hash = "sha256:37a138589b12069efb424220bf78eac59ca68b95696fc622b6ccc1c0a197204a"},
{file = "cryptography-41.0.7-pp38-pypy38_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:68a2dec79deebc5d26d617bfdf6e8aab065a4f34934b22d3b5010df3ba36612c"},
{file = "cryptography-41.0.7-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:09616eeaef406f99046553b8a40fbf8b1e70795a91885ba4c96a70793de5504a"},
{file = "cryptography-41.0.7-pp39-pypy39_pp73-macosx_10_12_x86_64.whl", hash = "sha256:48a0476626da912a44cc078f9893f292f0b3e4c739caf289268168d8f4702a39"},
{file = "cryptography-41.0.7-pp39-pypy39_pp73-manylinux_2_28_aarch64.whl", hash = "sha256:c7f3201ec47d5207841402594f1d7950879ef890c0c495052fa62f58283fde1a"},
{file = "cryptography-41.0.7-pp39-pypy39_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:c5ca78485a255e03c32b513f8c2bc39fedb7f5c5f8535545bdc223a03b24f248"},
{file = "cryptography-41.0.7-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:d6c391c021ab1f7a82da5d8d0b3cee2f4b2c455ec86c8aebbc84837a631ff309"},
{file = "cryptography-41.0.7.tar.gz", hash = "sha256:13f93ce9bea8016c253b34afc6bd6a75993e5c40672ed5405a9c832f0d4a00bc"},
{file = "cryptography-42.0.0-cp37-abi3-macosx_10_12_universal2.whl", hash = "sha256:c640b0ef54138fde761ec99a6c7dc4ce05e80420262c20fa239e694ca371d434"},
{file = "cryptography-42.0.0-cp37-abi3-macosx_10_12_x86_64.whl", hash = "sha256:678cfa0d1e72ef41d48993a7be75a76b0725d29b820ff3cfd606a5b2b33fda01"},
{file = "cryptography-42.0.0-cp37-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:146e971e92a6dd042214b537a726c9750496128453146ab0ee8971a0299dc9bd"},
{file = "cryptography-42.0.0-cp37-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:87086eae86a700307b544625e3ba11cc600c3c0ef8ab97b0fda0705d6db3d4e3"},
{file = "cryptography-42.0.0-cp37-abi3-manylinux_2_28_aarch64.whl", hash = "sha256:0a68bfcf57a6887818307600c3c0ebc3f62fbb6ccad2240aa21887cda1f8df1b"},
{file = "cryptography-42.0.0-cp37-abi3-manylinux_2_28_x86_64.whl", hash = "sha256:5a217bca51f3b91971400890905a9323ad805838ca3fa1e202a01844f485ee87"},
{file = "cryptography-42.0.0-cp37-abi3-musllinux_1_1_aarch64.whl", hash = "sha256:ca20550bb590db16223eb9ccc5852335b48b8f597e2f6f0878bbfd9e7314eb17"},
{file = "cryptography-42.0.0-cp37-abi3-musllinux_1_1_x86_64.whl", hash = "sha256:33588310b5c886dfb87dba5f013b8d27df7ffd31dc753775342a1e5ab139e59d"},
{file = "cryptography-42.0.0-cp37-abi3-musllinux_1_2_aarch64.whl", hash = "sha256:9515ea7f596c8092fdc9902627e51b23a75daa2c7815ed5aa8cf4f07469212ec"},
{file = "cryptography-42.0.0-cp37-abi3-musllinux_1_2_x86_64.whl", hash = "sha256:35cf6ed4c38f054478a9df14f03c1169bb14bd98f0b1705751079b25e1cb58bc"},
{file = "cryptography-42.0.0-cp37-abi3-win32.whl", hash = "sha256:8814722cffcfd1fbd91edd9f3451b88a8f26a5fd41b28c1c9193949d1c689dc4"},
{file = "cryptography-42.0.0-cp37-abi3-win_amd64.whl", hash = "sha256:a2a8d873667e4fd2f34aedab02ba500b824692c6542e017075a2efc38f60a4c0"},
{file = "cryptography-42.0.0-cp39-abi3-macosx_10_12_universal2.whl", hash = "sha256:8fedec73d590fd30c4e3f0d0f4bc961aeca8390c72f3eaa1a0874d180e868ddf"},
{file = "cryptography-42.0.0-cp39-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:be41b0c7366e5549265adf2145135dca107718fa44b6e418dc7499cfff6b4689"},
{file = "cryptography-42.0.0-cp39-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3ca482ea80626048975360c8e62be3ceb0f11803180b73163acd24bf014133a0"},
{file = "cryptography-42.0.0-cp39-abi3-manylinux_2_28_aarch64.whl", hash = "sha256:c58115384bdcfe9c7f644c72f10f6f42bed7cf59f7b52fe1bf7ae0a622b3a139"},
{file = "cryptography-42.0.0-cp39-abi3-manylinux_2_28_x86_64.whl", hash = "sha256:56ce0c106d5c3fec1038c3cca3d55ac320a5be1b44bf15116732d0bc716979a2"},
{file = "cryptography-42.0.0-cp39-abi3-musllinux_1_1_aarch64.whl", hash = "sha256:324721d93b998cb7367f1e6897370644751e5580ff9b370c0a50dc60a2003513"},
{file = "cryptography-42.0.0-cp39-abi3-musllinux_1_1_x86_64.whl", hash = "sha256:d97aae66b7de41cdf5b12087b5509e4e9805ed6f562406dfcf60e8481a9a28f8"},
{file = "cryptography-42.0.0-cp39-abi3-musllinux_1_2_aarch64.whl", hash = "sha256:85f759ed59ffd1d0baad296e72780aa62ff8a71f94dc1ab340386a1207d0ea81"},
{file = "cryptography-42.0.0-cp39-abi3-musllinux_1_2_x86_64.whl", hash = "sha256:206aaf42e031b93f86ad60f9f5d9da1b09164f25488238ac1dc488334eb5e221"},
{file = "cryptography-42.0.0-cp39-abi3-win32.whl", hash = "sha256:74f18a4c8ca04134d2052a140322002fef535c99cdbc2a6afc18a8024d5c9d5b"},
{file = "cryptography-42.0.0-cp39-abi3-win_amd64.whl", hash = "sha256:14e4b909373bc5bf1095311fa0f7fcabf2d1a160ca13f1e9e467be1ac4cbdf94"},
{file = "cryptography-42.0.0-pp310-pypy310_pp73-macosx_10_12_x86_64.whl", hash = "sha256:3005166a39b70c8b94455fdbe78d87a444da31ff70de3331cdec2c568cf25b7e"},
{file = "cryptography-42.0.0-pp310-pypy310_pp73-manylinux_2_28_aarch64.whl", hash = "sha256:be14b31eb3a293fc6e6aa2807c8a3224c71426f7c4e3639ccf1a2f3ffd6df8c3"},
{file = "cryptography-42.0.0-pp310-pypy310_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:bd7cf7a8d9f34cc67220f1195884151426ce616fdc8285df9054bfa10135925f"},
{file = "cryptography-42.0.0-pp310-pypy310_pp73-win_amd64.whl", hash = "sha256:c310767268d88803b653fffe6d6f2f17bb9d49ffceb8d70aed50ad45ea49ab08"},
{file = "cryptography-42.0.0-pp39-pypy39_pp73-macosx_10_12_x86_64.whl", hash = "sha256:bdce70e562c69bb089523e75ef1d9625b7417c6297a76ac27b1b8b1eb51b7d0f"},
{file = "cryptography-42.0.0-pp39-pypy39_pp73-manylinux_2_28_aarch64.whl", hash = "sha256:e9326ca78111e4c645f7e49cbce4ed2f3f85e17b61a563328c85a5208cf34440"},
{file = "cryptography-42.0.0-pp39-pypy39_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:69fd009a325cad6fbfd5b04c711a4da563c6c4854fc4c9544bff3088387c77c0"},
{file = "cryptography-42.0.0-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:988b738f56c665366b1e4bfd9045c3efae89ee366ca3839cd5af53eaa1401bce"},
{file = "cryptography-42.0.0.tar.gz", hash = "sha256:6cf9b76d6e93c62114bd19485e5cb003115c134cf9ce91f8ac924c44f8c8c3f4"},
]
[package.dependencies]
cffi = ">=1.12"
cffi = {version = ">=1.12", markers = "platform_python_implementation != \"PyPy\""}
[package.extras]
docs = ["sphinx (>=5.3.0)", "sphinx-rtd-theme (>=1.1.1)"]
docstest = ["pyenchant (>=1.6.11)", "sphinxcontrib-spelling (>=4.0.1)", "twine (>=1.12.0)"]
docstest = ["pyenchant (>=1.6.11)", "readme-renderer", "sphinxcontrib-spelling (>=4.0.1)"]
nox = ["nox"]
pep8test = ["black", "check-sdist", "mypy", "ruff"]
pep8test = ["check-sdist", "click", "mypy", "ruff"]
sdist = ["build"]
ssh = ["bcrypt (>=3.1.5)"]
test = ["pretend", "pytest (>=6.2.0)", "pytest-benchmark", "pytest-cov", "pytest-xdist"]
test = ["certifi", "pretend", "pytest (>=6.2.0)", "pytest-benchmark", "pytest-cov", "pytest-xdist"]
test-randomorder = ["pytest-randomly"]
[[package]]
@@ -1254,13 +1263,13 @@ files = [
[[package]]
name = "jsonschema"
version = "4.21.0"
version = "4.21.1"
description = "An implementation of JSON Schema validation for Python"
optional = false
python-versions = ">=3.8"
files = [
{file = "jsonschema-4.21.0-py3-none-any.whl", hash = "sha256:70a09719d375c0a2874571b363c8a24be7df8071b80c9aa76bc4551e7297c63c"},
{file = "jsonschema-4.21.0.tar.gz", hash = "sha256:3ba18e27f7491ea4a1b22edce00fb820eec968d397feb3f9cb61d5894bb38167"},
{file = "jsonschema-4.21.1-py3-none-any.whl", hash = "sha256:7996507afae316306f9e2290407761157c6f78002dcf7419acb99822143d1c6f"},
{file = "jsonschema-4.21.1.tar.gz", hash = "sha256:85727c00279f5fa6bedbe6238d2aa6403bedd8b4864ab11207d07df3cc1b2ee5"},
]
[package.dependencies]
@@ -1419,13 +1428,13 @@ test = ["flaky", "ipykernel", "pre-commit", "pytest (>=7.0)", "pytest-console-sc
[[package]]
name = "jupyter-server-terminals"
version = "0.5.1"
version = "0.5.2"
description = "A Jupyter Server Extension Providing Terminals."
optional = false
python-versions = ">=3.8"
files = [
{file = "jupyter_server_terminals-0.5.1-py3-none-any.whl", hash = "sha256:5e63e947ddd97bb2832db5ef837a258d9ccd4192cd608c1270850ad947ae5dd7"},
{file = "jupyter_server_terminals-0.5.1.tar.gz", hash = "sha256:16d3be9cf48be6a1f943f3a6c93c033be259cf4779184c66421709cf63dccfea"},
{file = "jupyter_server_terminals-0.5.2-py3-none-any.whl", hash = "sha256:1b80c12765da979513c42c90215481bbc39bd8ae7c0350b4f85bc3eb58d0fa80"},
{file = "jupyter_server_terminals-0.5.2.tar.gz", hash = "sha256:396b5ccc0881e550bf0ee7012c6ef1b53edbde69e67cab1d56e89711b46052e8"},
]
[package.dependencies]
@@ -1687,61 +1696,71 @@ testing = ["coverage", "pytest", "pytest-cov", "pytest-regressions"]
[[package]]
name = "markupsafe"
version = "2.1.3"
version = "2.1.4"
description = "Safely add untrusted strings to HTML/XML markup."
optional = false
python-versions = ">=3.7"
files = [
{file = "MarkupSafe-2.1.3-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:cd0f502fe016460680cd20aaa5a76d241d6f35a1c3350c474bac1273803893fa"},
{file = "MarkupSafe-2.1.3-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:e09031c87a1e51556fdcb46e5bd4f59dfb743061cf93c4d6831bf894f125eb57"},
{file = "MarkupSafe-2.1.3-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:68e78619a61ecf91e76aa3e6e8e33fc4894a2bebe93410754bd28fce0a8a4f9f"},
{file = "MarkupSafe-2.1.3-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:65c1a9bcdadc6c28eecee2c119465aebff8f7a584dd719facdd9e825ec61ab52"},
{file = "MarkupSafe-2.1.3-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:525808b8019e36eb524b8c68acdd63a37e75714eac50e988180b169d64480a00"},
{file = "MarkupSafe-2.1.3-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:962f82a3086483f5e5f64dbad880d31038b698494799b097bc59c2edf392fce6"},
{file = "MarkupSafe-2.1.3-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:aa7bd130efab1c280bed0f45501b7c8795f9fdbeb02e965371bbef3523627779"},
{file = "MarkupSafe-2.1.3-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:c9c804664ebe8f83a211cace637506669e7890fec1b4195b505c214e50dd4eb7"},
{file = "MarkupSafe-2.1.3-cp310-cp310-win32.whl", hash = "sha256:10bbfe99883db80bdbaff2dcf681dfc6533a614f700da1287707e8a5d78a8431"},
{file = "MarkupSafe-2.1.3-cp310-cp310-win_amd64.whl", hash = "sha256:1577735524cdad32f9f694208aa75e422adba74f1baee7551620e43a3141f559"},
{file = "MarkupSafe-2.1.3-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:ad9e82fb8f09ade1c3e1b996a6337afac2b8b9e365f926f5a61aacc71adc5b3c"},
{file = "MarkupSafe-2.1.3-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:3c0fae6c3be832a0a0473ac912810b2877c8cb9d76ca48de1ed31e1c68386575"},
{file = "MarkupSafe-2.1.3-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b076b6226fb84157e3f7c971a47ff3a679d837cf338547532ab866c57930dbee"},
{file = "MarkupSafe-2.1.3-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bfce63a9e7834b12b87c64d6b155fdd9b3b96191b6bd334bf37db7ff1fe457f2"},
{file = "MarkupSafe-2.1.3-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:338ae27d6b8745585f87218a3f23f1512dbf52c26c28e322dbe54bcede54ccb9"},
{file = "MarkupSafe-2.1.3-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:e4dd52d80b8c83fdce44e12478ad2e85c64ea965e75d66dbeafb0a3e77308fcc"},
{file = "MarkupSafe-2.1.3-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:df0be2b576a7abbf737b1575f048c23fb1d769f267ec4358296f31c2479db8f9"},
{file = "MarkupSafe-2.1.3-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:5bbe06f8eeafd38e5d0a4894ffec89378b6c6a625ff57e3028921f8ff59318ac"},
{file = "MarkupSafe-2.1.3-cp311-cp311-win32.whl", hash = "sha256:dd15ff04ffd7e05ffcb7fe79f1b98041b8ea30ae9234aed2a9168b5797c3effb"},
{file = "MarkupSafe-2.1.3-cp311-cp311-win_amd64.whl", hash = "sha256:134da1eca9ec0ae528110ccc9e48041e0828d79f24121a1a146161103c76e686"},
{file = "MarkupSafe-2.1.3-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:8e254ae696c88d98da6555f5ace2279cf7cd5b3f52be2b5cf97feafe883b58d2"},
{file = "MarkupSafe-2.1.3-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:cb0932dc158471523c9637e807d9bfb93e06a95cbf010f1a38b98623b929ef2b"},
{file = "MarkupSafe-2.1.3-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9402b03f1a1b4dc4c19845e5c749e3ab82d5078d16a2a4c2cd2df62d57bb0707"},
{file = "MarkupSafe-2.1.3-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ca379055a47383d02a5400cb0d110cef0a776fc644cda797db0c5696cfd7e18e"},
{file = "MarkupSafe-2.1.3-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:b7ff0f54cb4ff66dd38bebd335a38e2c22c41a8ee45aa608efc890ac3e3931bc"},
{file = "MarkupSafe-2.1.3-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:c011a4149cfbcf9f03994ec2edffcb8b1dc2d2aede7ca243746df97a5d41ce48"},
{file = "MarkupSafe-2.1.3-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:56d9f2ecac662ca1611d183feb03a3fa4406469dafe241673d521dd5ae92a155"},
{file = "MarkupSafe-2.1.3-cp37-cp37m-win32.whl", hash = "sha256:8758846a7e80910096950b67071243da3e5a20ed2546e6392603c096778d48e0"},
{file = "MarkupSafe-2.1.3-cp37-cp37m-win_amd64.whl", hash = "sha256:787003c0ddb00500e49a10f2844fac87aa6ce977b90b0feaaf9de23c22508b24"},
{file = "MarkupSafe-2.1.3-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:2ef12179d3a291be237280175b542c07a36e7f60718296278d8593d21ca937d4"},
{file = "MarkupSafe-2.1.3-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:2c1b19b3aaacc6e57b7e25710ff571c24d6c3613a45e905b1fde04d691b98ee0"},
{file = "MarkupSafe-2.1.3-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8afafd99945ead6e075b973fefa56379c5b5c53fd8937dad92c662da5d8fd5ee"},
{file = "MarkupSafe-2.1.3-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8c41976a29d078bb235fea9b2ecd3da465df42a562910f9022f1a03107bd02be"},
{file = "MarkupSafe-2.1.3-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:d080e0a5eb2529460b30190fcfcc4199bd7f827663f858a226a81bc27beaa97e"},
{file = "MarkupSafe-2.1.3-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:69c0f17e9f5a7afdf2cc9fb2d1ce6aabdb3bafb7f38017c0b77862bcec2bbad8"},
{file = "MarkupSafe-2.1.3-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:504b320cd4b7eff6f968eddf81127112db685e81f7e36e75f9f84f0df46041c3"},
{file = "MarkupSafe-2.1.3-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:42de32b22b6b804f42c5d98be4f7e5e977ecdd9ee9b660fda1a3edf03b11792d"},
{file = "MarkupSafe-2.1.3-cp38-cp38-win32.whl", hash = "sha256:ceb01949af7121f9fc39f7d27f91be8546f3fb112c608bc4029aef0bab86a2a5"},
{file = "MarkupSafe-2.1.3-cp38-cp38-win_amd64.whl", hash = "sha256:1b40069d487e7edb2676d3fbdb2b0829ffa2cd63a2ec26c4938b2d34391b4ecc"},
{file = "MarkupSafe-2.1.3-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:8023faf4e01efadfa183e863fefde0046de576c6f14659e8782065bcece22198"},
{file = "MarkupSafe-2.1.3-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:6b2b56950d93e41f33b4223ead100ea0fe11f8e6ee5f641eb753ce4b77a7042b"},
{file = "MarkupSafe-2.1.3-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9dcdfd0eaf283af041973bff14a2e143b8bd64e069f4c383416ecd79a81aab58"},
{file = "MarkupSafe-2.1.3-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:05fb21170423db021895e1ea1e1f3ab3adb85d1c2333cbc2310f2a26bc77272e"},
{file = "MarkupSafe-2.1.3-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:282c2cb35b5b673bbcadb33a585408104df04f14b2d9b01d4c345a3b92861c2c"},
{file = "MarkupSafe-2.1.3-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:ab4a0df41e7c16a1392727727e7998a467472d0ad65f3ad5e6e765015df08636"},
{file = "MarkupSafe-2.1.3-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:7ef3cb2ebbf91e330e3bb937efada0edd9003683db6b57bb108c4001f37a02ea"},
{file = "MarkupSafe-2.1.3-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:0a4e4a1aff6c7ac4cd55792abf96c915634c2b97e3cc1c7129578aa68ebd754e"},
{file = "MarkupSafe-2.1.3-cp39-cp39-win32.whl", hash = "sha256:fec21693218efe39aa7f8599346e90c705afa52c5b31ae019b2e57e8f6542bb2"},
{file = "MarkupSafe-2.1.3-cp39-cp39-win_amd64.whl", hash = "sha256:3fd4abcb888d15a94f32b75d8fd18ee162ca0c064f35b11134be77050296d6ba"},
{file = "MarkupSafe-2.1.3.tar.gz", hash = "sha256:af598ed32d6ae86f1b747b82783958b1a4ab8f617b06fe68795c7f026abbdcad"},
{file = "MarkupSafe-2.1.4-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:de8153a7aae3835484ac168a9a9bdaa0c5eee4e0bc595503c95d53b942879c84"},
{file = "MarkupSafe-2.1.4-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:e888ff76ceb39601c59e219f281466c6d7e66bd375b4ec1ce83bcdc68306796b"},
{file = "MarkupSafe-2.1.4-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:a0b838c37ba596fcbfca71651a104a611543077156cb0a26fe0c475e1f152ee8"},
{file = "MarkupSafe-2.1.4-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:dac1ebf6983148b45b5fa48593950f90ed6d1d26300604f321c74a9ca1609f8e"},
{file = "MarkupSafe-2.1.4-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:0fbad3d346df8f9d72622ac71b69565e621ada2ce6572f37c2eae8dacd60385d"},
{file = "MarkupSafe-2.1.4-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:d5291d98cd3ad9a562883468c690a2a238c4a6388ab3bd155b0c75dd55ece858"},
{file = "MarkupSafe-2.1.4-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:a7cc49ef48a3c7a0005a949f3c04f8baa5409d3f663a1b36f0eba9bfe2a0396e"},
{file = "MarkupSafe-2.1.4-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:b83041cda633871572f0d3c41dddd5582ad7d22f65a72eacd8d3d6d00291df26"},
{file = "MarkupSafe-2.1.4-cp310-cp310-win32.whl", hash = "sha256:0c26f67b3fe27302d3a412b85ef696792c4a2386293c53ba683a89562f9399b0"},
{file = "MarkupSafe-2.1.4-cp310-cp310-win_amd64.whl", hash = "sha256:a76055d5cb1c23485d7ddae533229039b850db711c554a12ea64a0fd8a0129e2"},
{file = "MarkupSafe-2.1.4-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:9e9e3c4020aa2dc62d5dd6743a69e399ce3de58320522948af6140ac959ab863"},
{file = "MarkupSafe-2.1.4-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:0042d6a9880b38e1dd9ff83146cc3c9c18a059b9360ceae207805567aacccc69"},
{file = "MarkupSafe-2.1.4-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:55d03fea4c4e9fd0ad75dc2e7e2b6757b80c152c032ea1d1de487461d8140efc"},
{file = "MarkupSafe-2.1.4-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3ab3a886a237f6e9c9f4f7d272067e712cdb4efa774bef494dccad08f39d8ae6"},
{file = "MarkupSafe-2.1.4-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:abf5ebbec056817057bfafc0445916bb688a255a5146f900445d081db08cbabb"},
{file = "MarkupSafe-2.1.4-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:e1a0d1924a5013d4f294087e00024ad25668234569289650929ab871231668e7"},
{file = "MarkupSafe-2.1.4-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:e7902211afd0af05fbadcc9a312e4cf10f27b779cf1323e78d52377ae4b72bea"},
{file = "MarkupSafe-2.1.4-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:c669391319973e49a7c6230c218a1e3044710bc1ce4c8e6eb71f7e6d43a2c131"},
{file = "MarkupSafe-2.1.4-cp311-cp311-win32.whl", hash = "sha256:31f57d64c336b8ccb1966d156932f3daa4fee74176b0fdc48ef580be774aae74"},
{file = "MarkupSafe-2.1.4-cp311-cp311-win_amd64.whl", hash = "sha256:54a7e1380dfece8847c71bf7e33da5d084e9b889c75eca19100ef98027bd9f56"},
{file = "MarkupSafe-2.1.4-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:a76cd37d229fc385738bd1ce4cba2a121cf26b53864c1772694ad0ad348e509e"},
{file = "MarkupSafe-2.1.4-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:987d13fe1d23e12a66ca2073b8d2e2a75cec2ecb8eab43ff5624ba0ad42764bc"},
{file = "MarkupSafe-2.1.4-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5244324676254697fe5c181fc762284e2c5fceeb1c4e3e7f6aca2b6f107e60dc"},
{file = "MarkupSafe-2.1.4-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:78bc995e004681246e85e28e068111a4c3f35f34e6c62da1471e844ee1446250"},
{file = "MarkupSafe-2.1.4-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:a4d176cfdfde84f732c4a53109b293d05883e952bbba68b857ae446fa3119b4f"},
{file = "MarkupSafe-2.1.4-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:f9917691f410a2e0897d1ef99619fd3f7dd503647c8ff2475bf90c3cf222ad74"},
{file = "MarkupSafe-2.1.4-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:f06e5a9e99b7df44640767842f414ed5d7bedaaa78cd817ce04bbd6fd86e2dd6"},
{file = "MarkupSafe-2.1.4-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:396549cea79e8ca4ba65525470d534e8a41070e6b3500ce2414921099cb73e8d"},
{file = "MarkupSafe-2.1.4-cp312-cp312-win32.whl", hash = "sha256:f6be2d708a9d0e9b0054856f07ac7070fbe1754be40ca8525d5adccdbda8f475"},
{file = "MarkupSafe-2.1.4-cp312-cp312-win_amd64.whl", hash = "sha256:5045e892cfdaecc5b4c01822f353cf2c8feb88a6ec1c0adef2a2e705eef0f656"},
{file = "MarkupSafe-2.1.4-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:7a07f40ef8f0fbc5ef1000d0c78771f4d5ca03b4953fc162749772916b298fc4"},
{file = "MarkupSafe-2.1.4-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d18b66fe626ac412d96c2ab536306c736c66cf2a31c243a45025156cc190dc8a"},
{file = "MarkupSafe-2.1.4-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:698e84142f3f884114ea8cf83e7a67ca8f4ace8454e78fe960646c6c91c63bfa"},
{file = "MarkupSafe-2.1.4-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:49a3b78a5af63ec10d8604180380c13dcd870aba7928c1fe04e881d5c792dc4e"},
{file = "MarkupSafe-2.1.4-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:15866d7f2dc60cfdde12ebb4e75e41be862348b4728300c36cdf405e258415ec"},
{file = "MarkupSafe-2.1.4-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:6aa5e2e7fc9bc042ae82d8b79d795b9a62bd8f15ba1e7594e3db243f158b5565"},
{file = "MarkupSafe-2.1.4-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:54635102ba3cf5da26eb6f96c4b8c53af8a9c0d97b64bdcb592596a6255d8518"},
{file = "MarkupSafe-2.1.4-cp37-cp37m-win32.whl", hash = "sha256:3583a3a3ab7958e354dc1d25be74aee6228938312ee875a22330c4dc2e41beb0"},
{file = "MarkupSafe-2.1.4-cp37-cp37m-win_amd64.whl", hash = "sha256:d6e427c7378c7f1b2bef6a344c925b8b63623d3321c09a237b7cc0e77dd98ceb"},
{file = "MarkupSafe-2.1.4-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:bf1196dcc239e608605b716e7b166eb5faf4bc192f8a44b81e85251e62584bd2"},
{file = "MarkupSafe-2.1.4-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:4df98d4a9cd6a88d6a585852f56f2155c9cdb6aec78361a19f938810aa020954"},
{file = "MarkupSafe-2.1.4-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b835aba863195269ea358cecc21b400276747cc977492319fd7682b8cd2c253d"},
{file = "MarkupSafe-2.1.4-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:23984d1bdae01bee794267424af55eef4dfc038dc5d1272860669b2aa025c9e3"},
{file = "MarkupSafe-2.1.4-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:1c98c33ffe20e9a489145d97070a435ea0679fddaabcafe19982fe9c971987d5"},
{file = "MarkupSafe-2.1.4-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:9896fca4a8eb246defc8b2a7ac77ef7553b638e04fbf170bff78a40fa8a91474"},
{file = "MarkupSafe-2.1.4-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:b0fe73bac2fed83839dbdbe6da84ae2a31c11cfc1c777a40dbd8ac8a6ed1560f"},
{file = "MarkupSafe-2.1.4-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:c7556bafeaa0a50e2fe7dc86e0382dea349ebcad8f010d5a7dc6ba568eaaa789"},
{file = "MarkupSafe-2.1.4-cp38-cp38-win32.whl", hash = "sha256:fc1a75aa8f11b87910ffd98de62b29d6520b6d6e8a3de69a70ca34dea85d2a8a"},
{file = "MarkupSafe-2.1.4-cp38-cp38-win_amd64.whl", hash = "sha256:3a66c36a3864df95e4f62f9167c734b3b1192cb0851b43d7cc08040c074c6279"},
{file = "MarkupSafe-2.1.4-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:765f036a3d00395a326df2835d8f86b637dbaf9832f90f5d196c3b8a7a5080cb"},
{file = "MarkupSafe-2.1.4-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:21e7af8091007bf4bebf4521184f4880a6acab8df0df52ef9e513d8e5db23411"},
{file = "MarkupSafe-2.1.4-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d5c31fe855c77cad679b302aabc42d724ed87c043b1432d457f4976add1c2c3e"},
{file = "MarkupSafe-2.1.4-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:7653fa39578957bc42e5ebc15cf4361d9e0ee4b702d7d5ec96cdac860953c5b4"},
{file = "MarkupSafe-2.1.4-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:47bb5f0142b8b64ed1399b6b60f700a580335c8e1c57f2f15587bd072012decc"},
{file = "MarkupSafe-2.1.4-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:fe8512ed897d5daf089e5bd010c3dc03bb1bdae00b35588c49b98268d4a01e00"},
{file = "MarkupSafe-2.1.4-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:36d7626a8cca4d34216875aee5a1d3d654bb3dac201c1c003d182283e3205949"},
{file = "MarkupSafe-2.1.4-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:b6f14a9cd50c3cb100eb94b3273131c80d102e19bb20253ac7bd7336118a673a"},
{file = "MarkupSafe-2.1.4-cp39-cp39-win32.whl", hash = "sha256:c8f253a84dbd2c63c19590fa86a032ef3d8cc18923b8049d91bcdeeb2581fbf6"},
{file = "MarkupSafe-2.1.4-cp39-cp39-win_amd64.whl", hash = "sha256:8b570a1537367b52396e53325769608f2a687ec9a4363647af1cded8928af959"},
{file = "MarkupSafe-2.1.4.tar.gz", hash = "sha256:3aae9af4cac263007fd6309c64c6ab4506dd2b79382d9d19a1994f9240b8db4f"},
]
[[package]]
@@ -1907,13 +1926,13 @@ mkdocs = ">=1.1"
[[package]]
name = "mkdocs-material"
version = "9.5.4"
version = "9.5.5"
description = "Documentation that simply works"
optional = false
python-versions = ">=3.8"
files = [
{file = "mkdocs_material-9.5.4-py3-none-any.whl", hash = "sha256:efd7cc8ae03296d728da9bd38f4db8b07ab61f9738a0cbd0dfaf2a15a50e7343"},
{file = "mkdocs_material-9.5.4.tar.gz", hash = "sha256:3d196ee67fad16b2df1a458d650a8ac1890294eaae368d26cee71bc24ad41c40"},
{file = "mkdocs_material-9.5.5-py3-none-any.whl", hash = "sha256:ac50b2431a79a3b160fdefbba37c9132485f1a69166aba115ad49fafdbbbc5df"},
{file = "mkdocs_material-9.5.5.tar.gz", hash = "sha256:4480d9580faf42fed0123d0465502bfc1c0c239ecc9c4d66159cf0459ea1b4ae"},
]
[package.dependencies]
@@ -1925,7 +1944,7 @@ markdown = ">=3.2,<4.0"
mkdocs = ">=1.5.3,<1.6.0"
mkdocs-material-extensions = ">=1.3,<2.0"
paginate = ">=0.5,<1.0"
pillow = {version = ">=9.4,<10.0", optional = true, markers = "extra == \"imaging\""}
pillow = {version = ">=10.2,<11.0", optional = true, markers = "extra == \"imaging\""}
pygments = ">=2.16,<3.0"
pymdown-extensions = ">=10.2,<11.0"
regex = ">=2022.4"
@@ -1933,7 +1952,7 @@ requests = ">=2.26,<3.0"
[package.extras]
git = ["mkdocs-git-committers-plugin-2 (>=1.1,<2.0)", "mkdocs-git-revision-date-localized-plugin (>=1.2,<2.0)"]
imaging = ["cairosvg (>=2.6,<3.0)", "pillow (>=9.4,<10.0)"]
imaging = ["cairosvg (>=2.6,<3.0)", "pillow (>=10.2,<11.0)"]
recommended = ["mkdocs-minify-plugin (>=0.7,<1.0)", "mkdocs-redirects (>=1.2,<2.0)", "mkdocs-rss-plugin (>=1.6,<2.0)"]
[[package]]
@@ -2143,13 +2162,13 @@ test = ["pep440", "pre-commit", "pytest", "testpath"]
[[package]]
name = "nest-asyncio"
version = "1.5.9"
version = "1.6.0"
description = "Patch asyncio to allow nested event loops"
optional = false
python-versions = ">=3.5"
files = [
{file = "nest_asyncio-1.5.9-py3-none-any.whl", hash = "sha256:61ec07ef052e72e3de22045b81b2cc7d71fceb04c568ba0b2e4b2f9f5231bec2"},
{file = "nest_asyncio-1.5.9.tar.gz", hash = "sha256:d1e1144e9c6e3e6392e0fcf5211cb1c8374b5648a98f1ebe48e5336006b41907"},
{file = "nest_asyncio-1.6.0-py3-none-any.whl", hash = "sha256:87af6efd6b5e897c81050477ef65c62e2b2f35d51703cae01aff2905b1852e1c"},
{file = "nest_asyncio-1.6.0.tar.gz", hash = "sha256:6f172d5449aca15afd6c646851f4e31e02c598d553a667e38cafa997cfec55fe"},
]
[[package]]
@@ -2284,12 +2303,31 @@ files = [
{file = "opencv_python-4.8.1.78-cp37-abi3-win_amd64.whl", hash = "sha256:b983197f97cfa6fcb74e1da1802c7497a6f94ed561aba6980f1f33123f904956"},
]
[package.dependencies]
numpy = {version = ">=1.23.5", markers = "python_version >= \"3.11\""}
[[package]]
name = "opencv-python"
version = "4.9.0.80"
description = "Wrapper package for OpenCV python bindings."
optional = true
python-versions = ">=3.6"
files = [
{file = "opencv-python-4.9.0.80.tar.gz", hash = "sha256:1a9f0e6267de3a1a1db0c54213d022c7c8b5b9ca4b580e80bdc58516c922c9e1"},
{file = "opencv_python-4.9.0.80-cp37-abi3-macosx_10_16_x86_64.whl", hash = "sha256:7e5f7aa4486651a6ebfa8ed4b594b65bd2d2f41beeb4241a3e4b1b85acbbbadb"},
{file = "opencv_python-4.9.0.80-cp37-abi3-macosx_11_0_arm64.whl", hash = "sha256:71dfb9555ccccdd77305fc3dcca5897fbf0cf28b297c51ee55e079c065d812a3"},
{file = "opencv_python-4.9.0.80-cp37-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:7b34a52e9da36dda8c151c6394aed602e4b17fa041df0b9f5b93ae10b0fcca2a"},
{file = "opencv_python-4.9.0.80-cp37-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e4088cab82b66a3b37ffc452976b14a3c599269c247895ae9ceb4066d8188a57"},
{file = "opencv_python-4.9.0.80-cp37-abi3-win32.whl", hash = "sha256:dcf000c36dd1651118a2462257e3a9e76db789a78432e1f303c7bac54f63ef6c"},
{file = "opencv_python-4.9.0.80-cp37-abi3-win_amd64.whl", hash = "sha256:3f16f08e02b2a2da44259c7cc712e779eff1dd8b55fdb0323e8cab09548086c0"},
]
[package.dependencies]
numpy = [
{version = ">=1.21.0", markers = "python_version <= \"3.9\" and platform_system == \"Darwin\" and platform_machine == \"arm64\" and python_version >= \"3.8\""},
{version = ">=1.19.3", markers = "platform_system == \"Linux\" and platform_machine == \"aarch64\" and python_version >= \"3.8\" and python_version < \"3.10\" or python_version > \"3.9\" and python_version < \"3.10\" or python_version >= \"3.9\" and platform_system != \"Darwin\" and python_version < \"3.10\" or python_version >= \"3.9\" and platform_machine != \"arm64\" and python_version < \"3.10\""},
{version = ">=1.17.3", markers = "(platform_system != \"Darwin\" and platform_system != \"Linux\") and python_version >= \"3.8\" and python_version < \"3.9\" or platform_system != \"Darwin\" and python_version >= \"3.8\" and python_version < \"3.9\" and platform_machine != \"aarch64\" or platform_machine != \"arm64\" and python_version >= \"3.8\" and python_version < \"3.9\" and platform_system != \"Linux\" or (platform_machine != \"arm64\" and platform_machine != \"aarch64\") and python_version >= \"3.8\" and python_version < \"3.9\""},
{version = ">=1.23.5", markers = "python_version >= \"3.11\""},
{version = ">=1.23.5", markers = "python_version >= \"3.11\" and python_version < \"3.12\""},
{version = ">=1.21.4", markers = "python_version >= \"3.10\" and platform_system == \"Darwin\" and python_version < \"3.11\""},
{version = ">=1.21.2", markers = "platform_system != \"Darwin\" and python_version >= \"3.10\" and python_version < \"3.11\""},
]
@@ -2310,25 +2348,44 @@ files = [
{file = "opencv_python_headless-4.8.1.78-cp37-abi3-win_amd64.whl", hash = "sha256:0a0f1e9f836f7d5bad1dd164694944c8761711cbdf4b36ebbd4815a8ef731079"},
]
[package.dependencies]
numpy = {version = ">=1.23.5", markers = "python_version >= \"3.11\""}
[[package]]
name = "opencv-python-headless"
version = "4.9.0.80"
description = "Wrapper package for OpenCV python bindings."
optional = false
python-versions = ">=3.6"
files = [
{file = "opencv-python-headless-4.9.0.80.tar.gz", hash = "sha256:71a4cd8cf7c37122901d8e81295db7fb188730e33a0e40039a4e59c1030b0958"},
{file = "opencv_python_headless-4.9.0.80-cp37-abi3-macosx_10_16_x86_64.whl", hash = "sha256:2ea8a2edc4db87841991b2fbab55fc07b97ecb602e0f47d5d485bd75cee17c1a"},
{file = "opencv_python_headless-4.9.0.80-cp37-abi3-macosx_11_0_arm64.whl", hash = "sha256:e0ee54e27be493e8f7850847edae3128e18b540dac1d7b2e4001b8944e11e1c6"},
{file = "opencv_python_headless-4.9.0.80-cp37-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:57ce2865e8fec431c6f97a81e9faaf23fa5be61011d0a75ccf47a3c0d65fa73d"},
{file = "opencv_python_headless-4.9.0.80-cp37-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:976656362d68d9f40a5c66f83901430538002465f7db59142784f3893918f3df"},
{file = "opencv_python_headless-4.9.0.80-cp37-abi3-win32.whl", hash = "sha256:11e3849d83e6651d4e7699aadda9ec7ed7c38957cbbcb99db074f2a2d2de9670"},
{file = "opencv_python_headless-4.9.0.80-cp37-abi3-win_amd64.whl", hash = "sha256:a8056c2cb37cd65dfcdf4153ca16f7362afcf3a50d600d6bb69c660fc61ee29c"},
]
[package.dependencies]
numpy = [
{version = ">=1.21.0", markers = "python_version <= \"3.9\" and platform_system == \"Darwin\" and platform_machine == \"arm64\" and python_version >= \"3.8\""},
{version = ">=1.19.3", markers = "platform_system == \"Linux\" and platform_machine == \"aarch64\" and python_version >= \"3.8\" and python_version < \"3.10\" or python_version > \"3.9\" and python_version < \"3.10\" or python_version >= \"3.9\" and platform_system != \"Darwin\" and python_version < \"3.10\" or python_version >= \"3.9\" and platform_machine != \"arm64\" and python_version < \"3.10\""},
{version = ">=1.17.3", markers = "(platform_system != \"Darwin\" and platform_system != \"Linux\") and python_version >= \"3.8\" and python_version < \"3.9\" or platform_system != \"Darwin\" and python_version >= \"3.8\" and python_version < \"3.9\" and platform_machine != \"aarch64\" or platform_machine != \"arm64\" and python_version >= \"3.8\" and python_version < \"3.9\" and platform_system != \"Linux\" or (platform_machine != \"arm64\" and platform_machine != \"aarch64\") and python_version >= \"3.8\" and python_version < \"3.9\""},
{version = ">=1.23.5", markers = "python_version >= \"3.11\""},
{version = ">=1.23.5", markers = "python_version >= \"3.11\" and python_version < \"3.12\""},
{version = ">=1.21.4", markers = "python_version >= \"3.10\" and platform_system == \"Darwin\" and python_version < \"3.11\""},
{version = ">=1.21.2", markers = "platform_system != \"Darwin\" and python_version >= \"3.10\" and python_version < \"3.11\""},
]
[[package]]
name = "overrides"
version = "7.4.0"
version = "7.6.0"
description = "A decorator to automatically detect mismatch when overriding a method."
optional = false
python-versions = ">=3.6"
files = [
{file = "overrides-7.4.0-py3-none-any.whl", hash = "sha256:3ad24583f86d6d7a49049695efe9933e67ba62f0c7625d53c59fa832ce4b8b7d"},
{file = "overrides-7.4.0.tar.gz", hash = "sha256:9502a3cca51f4fac40b5feca985b6703a5c1f6ad815588a7ca9e285b9dca6757"},
{file = "overrides-7.6.0-py3-none-any.whl", hash = "sha256:c36e6635519ea9c5b043b65c36d4b886aee8bd45b7d4681d2a6df0898df4b654"},
{file = "overrides-7.6.0.tar.gz", hash = "sha256:01e15bbbf15b766f0675c275baa1878bd1c7dc9bc7b9ee13e677cdba93dc1bd9"},
]
[[package]]
@@ -2416,82 +2473,88 @@ files = [
[[package]]
name = "pillow"
version = "9.5.0"
version = "10.2.0"
description = "Python Imaging Library (Fork)"
optional = false
python-versions = ">=3.7"
python-versions = ">=3.8"
files = [
{file = "Pillow-9.5.0-cp310-cp310-macosx_10_10_x86_64.whl", hash = "sha256:ace6ca218308447b9077c14ea4ef381ba0b67ee78d64046b3f19cf4e1139ad16"},
{file = "Pillow-9.5.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:d3d403753c9d5adc04d4694d35cf0391f0f3d57c8e0030aac09d7678fa8030aa"},
{file = "Pillow-9.5.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5ba1b81ee69573fe7124881762bb4cd2e4b6ed9dd28c9c60a632902fe8db8b38"},
{file = "Pillow-9.5.0-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:fe7e1c262d3392afcf5071df9afa574544f28eac825284596ac6db56e6d11062"},
{file = "Pillow-9.5.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8f36397bf3f7d7c6a3abdea815ecf6fd14e7fcd4418ab24bae01008d8d8ca15e"},
{file = "Pillow-9.5.0-cp310-cp310-manylinux_2_28_aarch64.whl", hash = "sha256:252a03f1bdddce077eff2354c3861bf437c892fb1832f75ce813ee94347aa9b5"},
{file = "Pillow-9.5.0-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:85ec677246533e27770b0de5cf0f9d6e4ec0c212a1f89dfc941b64b21226009d"},
{file = "Pillow-9.5.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:b416f03d37d27290cb93597335a2f85ed446731200705b22bb927405320de903"},
{file = "Pillow-9.5.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:1781a624c229cb35a2ac31cc4a77e28cafc8900733a864870c49bfeedacd106a"},
{file = "Pillow-9.5.0-cp310-cp310-win32.whl", hash = "sha256:8507eda3cd0608a1f94f58c64817e83ec12fa93a9436938b191b80d9e4c0fc44"},
{file = "Pillow-9.5.0-cp310-cp310-win_amd64.whl", hash = "sha256:d3c6b54e304c60c4181da1c9dadf83e4a54fd266a99c70ba646a9baa626819eb"},
{file = "Pillow-9.5.0-cp311-cp311-macosx_10_10_x86_64.whl", hash = "sha256:7ec6f6ce99dab90b52da21cf0dc519e21095e332ff3b399a357c187b1a5eee32"},
{file = "Pillow-9.5.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:560737e70cb9c6255d6dcba3de6578a9e2ec4b573659943a5e7e4af13f298f5c"},
{file = "Pillow-9.5.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:96e88745a55b88a7c64fa49bceff363a1a27d9a64e04019c2281049444a571e3"},
{file = "Pillow-9.5.0-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:d9c206c29b46cfd343ea7cdfe1232443072bbb270d6a46f59c259460db76779a"},
{file = "Pillow-9.5.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:cfcc2c53c06f2ccb8976fb5c71d448bdd0a07d26d8e07e321c103416444c7ad1"},
{file = "Pillow-9.5.0-cp311-cp311-manylinux_2_28_aarch64.whl", hash = "sha256:a0f9bb6c80e6efcde93ffc51256d5cfb2155ff8f78292f074f60f9e70b942d99"},
{file = "Pillow-9.5.0-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:8d935f924bbab8f0a9a28404422da8af4904e36d5c33fc6f677e4c4485515625"},
{file = "Pillow-9.5.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:fed1e1cf6a42577953abbe8e6cf2fe2f566daebde7c34724ec8803c4c0cda579"},
{file = "Pillow-9.5.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:c1170d6b195555644f0616fd6ed929dfcf6333b8675fcca044ae5ab110ded296"},
{file = "Pillow-9.5.0-cp311-cp311-win32.whl", hash = "sha256:54f7102ad31a3de5666827526e248c3530b3a33539dbda27c6843d19d72644ec"},
{file = "Pillow-9.5.0-cp311-cp311-win_amd64.whl", hash = "sha256:cfa4561277f677ecf651e2b22dc43e8f5368b74a25a8f7d1d4a3a243e573f2d4"},
{file = "Pillow-9.5.0-cp311-cp311-win_arm64.whl", hash = "sha256:965e4a05ef364e7b973dd17fc765f42233415974d773e82144c9bbaaaea5d089"},
{file = "Pillow-9.5.0-cp312-cp312-win32.whl", hash = "sha256:22baf0c3cf0c7f26e82d6e1adf118027afb325e703922c8dfc1d5d0156bb2eeb"},
{file = "Pillow-9.5.0-cp312-cp312-win_amd64.whl", hash = "sha256:432b975c009cf649420615388561c0ce7cc31ce9b2e374db659ee4f7d57a1f8b"},
{file = "Pillow-9.5.0-cp37-cp37m-macosx_10_10_x86_64.whl", hash = "sha256:5d4ebf8e1db4441a55c509c4baa7a0587a0210f7cd25fcfe74dbbce7a4bd1906"},
{file = "Pillow-9.5.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:375f6e5ee9620a271acb6820b3d1e94ffa8e741c0601db4c0c4d3cb0a9c224bf"},
{file = "Pillow-9.5.0-cp37-cp37m-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:99eb6cafb6ba90e436684e08dad8be1637efb71c4f2180ee6b8f940739406e78"},
{file = "Pillow-9.5.0-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2dfaaf10b6172697b9bceb9a3bd7b951819d1ca339a5ef294d1f1ac6d7f63270"},
{file = "Pillow-9.5.0-cp37-cp37m-manylinux_2_28_aarch64.whl", hash = "sha256:763782b2e03e45e2c77d7779875f4432e25121ef002a41829d8868700d119392"},
{file = "Pillow-9.5.0-cp37-cp37m-manylinux_2_28_x86_64.whl", hash = "sha256:35f6e77122a0c0762268216315bf239cf52b88865bba522999dc38f1c52b9b47"},
{file = "Pillow-9.5.0-cp37-cp37m-win32.whl", hash = "sha256:aca1c196f407ec7cf04dcbb15d19a43c507a81f7ffc45b690899d6a76ac9fda7"},
{file = "Pillow-9.5.0-cp37-cp37m-win_amd64.whl", hash = "sha256:322724c0032af6692456cd6ed554bb85f8149214d97398bb80613b04e33769f6"},
{file = "Pillow-9.5.0-cp38-cp38-macosx_10_10_x86_64.whl", hash = "sha256:a0aa9417994d91301056f3d0038af1199eb7adc86e646a36b9e050b06f526597"},
{file = "Pillow-9.5.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:f8286396b351785801a976b1e85ea88e937712ee2c3ac653710a4a57a8da5d9c"},
{file = "Pillow-9.5.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c830a02caeb789633863b466b9de10c015bded434deb3ec87c768e53752ad22a"},
{file = "Pillow-9.5.0-cp38-cp38-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:fbd359831c1657d69bb81f0db962905ee05e5e9451913b18b831febfe0519082"},
{file = "Pillow-9.5.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f8fc330c3370a81bbf3f88557097d1ea26cd8b019d6433aa59f71195f5ddebbf"},
{file = "Pillow-9.5.0-cp38-cp38-manylinux_2_28_aarch64.whl", hash = "sha256:7002d0797a3e4193c7cdee3198d7c14f92c0836d6b4a3f3046a64bd1ce8df2bf"},
{file = "Pillow-9.5.0-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:229e2c79c00e85989a34b5981a2b67aa079fd08c903f0aaead522a1d68d79e51"},
{file = "Pillow-9.5.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:9adf58f5d64e474bed00d69bcd86ec4bcaa4123bfa70a65ce72e424bfb88ed96"},
{file = "Pillow-9.5.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:662da1f3f89a302cc22faa9f14a262c2e3951f9dbc9617609a47521c69dd9f8f"},
{file = "Pillow-9.5.0-cp38-cp38-win32.whl", hash = "sha256:6608ff3bf781eee0cd14d0901a2b9cc3d3834516532e3bd673a0a204dc8615fc"},
{file = "Pillow-9.5.0-cp38-cp38-win_amd64.whl", hash = "sha256:e49eb4e95ff6fd7c0c402508894b1ef0e01b99a44320ba7d8ecbabefddcc5569"},
{file = "Pillow-9.5.0-cp39-cp39-macosx_10_10_x86_64.whl", hash = "sha256:482877592e927fd263028c105b36272398e3e1be3269efda09f6ba21fd83ec66"},
{file = "Pillow-9.5.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:3ded42b9ad70e5f1754fb7c2e2d6465a9c842e41d178f262e08b8c85ed8a1d8e"},
{file = "Pillow-9.5.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c446d2245ba29820d405315083d55299a796695d747efceb5717a8b450324115"},
{file = "Pillow-9.5.0-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:8aca1152d93dcc27dc55395604dcfc55bed5f25ef4c98716a928bacba90d33a3"},
{file = "Pillow-9.5.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:608488bdcbdb4ba7837461442b90ea6f3079397ddc968c31265c1e056964f1ef"},
{file = "Pillow-9.5.0-cp39-cp39-manylinux_2_28_aarch64.whl", hash = "sha256:60037a8db8750e474af7ffc9faa9b5859e6c6d0a50e55c45576bf28be7419705"},
{file = "Pillow-9.5.0-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:07999f5834bdc404c442146942a2ecadd1cb6292f5229f4ed3b31e0a108746b1"},
{file = "Pillow-9.5.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:a127ae76092974abfbfa38ca2d12cbeddcdeac0fb71f9627cc1135bedaf9d51a"},
{file = "Pillow-9.5.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:489f8389261e5ed43ac8ff7b453162af39c3e8abd730af8363587ba64bb2e865"},
{file = "Pillow-9.5.0-cp39-cp39-win32.whl", hash = "sha256:9b1af95c3a967bf1da94f253e56b6286b50af23392a886720f563c547e48e964"},
{file = "Pillow-9.5.0-cp39-cp39-win_amd64.whl", hash = "sha256:77165c4a5e7d5a284f10a6efaa39a0ae8ba839da344f20b111d62cc932fa4e5d"},
{file = "Pillow-9.5.0-pp38-pypy38_pp73-macosx_10_10_x86_64.whl", hash = "sha256:833b86a98e0ede388fa29363159c9b1a294b0905b5128baf01db683672f230f5"},
{file = "Pillow-9.5.0-pp38-pypy38_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:aaf305d6d40bd9632198c766fb64f0c1a83ca5b667f16c1e79e1661ab5060140"},
{file = "Pillow-9.5.0-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0852ddb76d85f127c135b6dd1f0bb88dbb9ee990d2cd9aa9e28526c93e794fba"},
{file = "Pillow-9.5.0-pp38-pypy38_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:91ec6fe47b5eb5a9968c79ad9ed78c342b1f97a091677ba0e012701add857829"},
{file = "Pillow-9.5.0-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:cb841572862f629b99725ebaec3287fc6d275be9b14443ea746c1dd325053cbd"},
{file = "Pillow-9.5.0-pp39-pypy39_pp73-macosx_10_10_x86_64.whl", hash = "sha256:c380b27d041209b849ed246b111b7c166ba36d7933ec6e41175fd15ab9eb1572"},
{file = "Pillow-9.5.0-pp39-pypy39_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7c9af5a3b406a50e313467e3565fc99929717f780164fe6fbb7704edba0cebbe"},
{file = "Pillow-9.5.0-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5671583eab84af046a397d6d0ba25343c00cd50bce03787948e0fff01d4fd9b1"},
{file = "Pillow-9.5.0-pp39-pypy39_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:84a6f19ce086c1bf894644b43cd129702f781ba5751ca8572f08aa40ef0ab7b7"},
{file = "Pillow-9.5.0-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:1e7723bd90ef94eda669a3c2c19d549874dd5badaeefabefd26053304abe5799"},
{file = "Pillow-9.5.0.tar.gz", hash = "sha256:bf548479d336726d7a0eceb6e767e179fbde37833ae42794602631a070d630f1"},
{file = "pillow-10.2.0-cp310-cp310-macosx_10_10_x86_64.whl", hash = "sha256:7823bdd049099efa16e4246bdf15e5a13dbb18a51b68fa06d6c1d4d8b99a796e"},
{file = "pillow-10.2.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:83b2021f2ade7d1ed556bc50a399127d7fb245e725aa0113ebd05cfe88aaf588"},
{file = "pillow-10.2.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6fad5ff2f13d69b7e74ce5b4ecd12cc0ec530fcee76356cac6742785ff71c452"},
{file = "pillow-10.2.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:da2b52b37dad6d9ec64e653637a096905b258d2fc2b984c41ae7d08b938a67e4"},
{file = "pillow-10.2.0-cp310-cp310-manylinux_2_28_aarch64.whl", hash = "sha256:47c0995fc4e7f79b5cfcab1fc437ff2890b770440f7696a3ba065ee0fd496563"},
{file = "pillow-10.2.0-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:322bdf3c9b556e9ffb18f93462e5f749d3444ce081290352c6070d014c93feb2"},
{file = "pillow-10.2.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:51f1a1bffc50e2e9492e87d8e09a17c5eea8409cda8d3f277eb6edc82813c17c"},
{file = "pillow-10.2.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:69ffdd6120a4737710a9eee73e1d2e37db89b620f702754b8f6e62594471dee0"},
{file = "pillow-10.2.0-cp310-cp310-win32.whl", hash = "sha256:c6dafac9e0f2b3c78df97e79af707cdc5ef8e88208d686a4847bab8266870023"},
{file = "pillow-10.2.0-cp310-cp310-win_amd64.whl", hash = "sha256:aebb6044806f2e16ecc07b2a2637ee1ef67a11840a66752751714a0d924adf72"},
{file = "pillow-10.2.0-cp310-cp310-win_arm64.whl", hash = "sha256:7049e301399273a0136ff39b84c3678e314f2158f50f517bc50285fb5ec847ad"},
{file = "pillow-10.2.0-cp311-cp311-macosx_10_10_x86_64.whl", hash = "sha256:35bb52c37f256f662abdfa49d2dfa6ce5d93281d323a9af377a120e89a9eafb5"},
{file = "pillow-10.2.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:9c23f307202661071d94b5e384e1e1dc7dfb972a28a2310e4ee16103e66ddb67"},
{file = "pillow-10.2.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:773efe0603db30c281521a7c0214cad7836c03b8ccff897beae9b47c0b657d61"},
{file = "pillow-10.2.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:11fa2e5984b949b0dd6d7a94d967743d87c577ff0b83392f17cb3990d0d2fd6e"},
{file = "pillow-10.2.0-cp311-cp311-manylinux_2_28_aarch64.whl", hash = "sha256:716d30ed977be8b37d3ef185fecb9e5a1d62d110dfbdcd1e2a122ab46fddb03f"},
{file = "pillow-10.2.0-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:a086c2af425c5f62a65e12fbf385f7c9fcb8f107d0849dba5839461a129cf311"},
{file = "pillow-10.2.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:c8de2789052ed501dd829e9cae8d3dcce7acb4777ea4a479c14521c942d395b1"},
{file = "pillow-10.2.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:609448742444d9290fd687940ac0b57fb35e6fd92bdb65386e08e99af60bf757"},
{file = "pillow-10.2.0-cp311-cp311-win32.whl", hash = "sha256:823ef7a27cf86df6597fa0671066c1b596f69eba53efa3d1e1cb8b30f3533068"},
{file = "pillow-10.2.0-cp311-cp311-win_amd64.whl", hash = "sha256:1da3b2703afd040cf65ec97efea81cfba59cdbed9c11d8efc5ab09df9509fc56"},
{file = "pillow-10.2.0-cp311-cp311-win_arm64.whl", hash = "sha256:edca80cbfb2b68d7b56930b84a0e45ae1694aeba0541f798e908a49d66b837f1"},
{file = "pillow-10.2.0-cp312-cp312-macosx_10_10_x86_64.whl", hash = "sha256:1b5e1b74d1bd1b78bc3477528919414874748dd363e6272efd5abf7654e68bef"},
{file = "pillow-10.2.0-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:0eae2073305f451d8ecacb5474997c08569fb4eb4ac231ffa4ad7d342fdc25ac"},
{file = "pillow-10.2.0-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b7c2286c23cd350b80d2fc9d424fc797575fb16f854b831d16fd47ceec078f2c"},
{file = "pillow-10.2.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1e23412b5c41e58cec602f1135c57dfcf15482013ce6e5f093a86db69646a5aa"},
{file = "pillow-10.2.0-cp312-cp312-manylinux_2_28_aarch64.whl", hash = "sha256:52a50aa3fb3acb9cf7213573ef55d31d6eca37f5709c69e6858fe3bc04a5c2a2"},
{file = "pillow-10.2.0-cp312-cp312-manylinux_2_28_x86_64.whl", hash = "sha256:127cee571038f252a552760076407f9cff79761c3d436a12af6000cd182a9d04"},
{file = "pillow-10.2.0-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:8d12251f02d69d8310b046e82572ed486685c38f02176bd08baf216746eb947f"},
{file = "pillow-10.2.0-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:54f1852cd531aa981bc0965b7d609f5f6cc8ce8c41b1139f6ed6b3c54ab82bfb"},
{file = "pillow-10.2.0-cp312-cp312-win32.whl", hash = "sha256:257d8788df5ca62c980314053197f4d46eefedf4e6175bc9412f14412ec4ea2f"},
{file = "pillow-10.2.0-cp312-cp312-win_amd64.whl", hash = "sha256:154e939c5f0053a383de4fd3d3da48d9427a7e985f58af8e94d0b3c9fcfcf4f9"},
{file = "pillow-10.2.0-cp312-cp312-win_arm64.whl", hash = "sha256:f379abd2f1e3dddb2b61bc67977a6b5a0a3f7485538bcc6f39ec76163891ee48"},
{file = "pillow-10.2.0-cp38-cp38-macosx_10_10_x86_64.whl", hash = "sha256:8373c6c251f7ef8bda6675dd6d2b3a0fcc31edf1201266b5cf608b62a37407f9"},
{file = "pillow-10.2.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:870ea1ada0899fd0b79643990809323b389d4d1d46c192f97342eeb6ee0b8483"},
{file = "pillow-10.2.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b4b6b1e20608493548b1f32bce8cca185bf0480983890403d3b8753e44077129"},
{file = "pillow-10.2.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3031709084b6e7852d00479fd1d310b07d0ba82765f973b543c8af5061cf990e"},
{file = "pillow-10.2.0-cp38-cp38-manylinux_2_28_aarch64.whl", hash = "sha256:3ff074fc97dd4e80543a3e91f69d58889baf2002b6be64347ea8cf5533188213"},
{file = "pillow-10.2.0-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:cb4c38abeef13c61d6916f264d4845fab99d7b711be96c326b84df9e3e0ff62d"},
{file = "pillow-10.2.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:b1b3020d90c2d8e1dae29cf3ce54f8094f7938460fb5ce8bc5c01450b01fbaf6"},
{file = "pillow-10.2.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:170aeb00224ab3dc54230c797f8404507240dd868cf52066f66a41b33169bdbe"},
{file = "pillow-10.2.0-cp38-cp38-win32.whl", hash = "sha256:c4225f5220f46b2fde568c74fca27ae9771536c2e29d7c04f4fb62c83275ac4e"},
{file = "pillow-10.2.0-cp38-cp38-win_amd64.whl", hash = "sha256:0689b5a8c5288bc0504d9fcee48f61a6a586b9b98514d7d29b840143d6734f39"},
{file = "pillow-10.2.0-cp39-cp39-macosx_10_10_x86_64.whl", hash = "sha256:b792a349405fbc0163190fde0dc7b3fef3c9268292586cf5645598b48e63dc67"},
{file = "pillow-10.2.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:c570f24be1e468e3f0ce7ef56a89a60f0e05b30a3669a459e419c6eac2c35364"},
{file = "pillow-10.2.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d8ecd059fdaf60c1963c58ceb8997b32e9dc1b911f5da5307aab614f1ce5c2fb"},
{file = "pillow-10.2.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:c365fd1703040de1ec284b176d6af5abe21b427cb3a5ff68e0759e1e313a5e7e"},
{file = "pillow-10.2.0-cp39-cp39-manylinux_2_28_aarch64.whl", hash = "sha256:70c61d4c475835a19b3a5aa42492409878bbca7438554a1f89d20d58a7c75c01"},
{file = "pillow-10.2.0-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:b6f491cdf80ae540738859d9766783e3b3c8e5bd37f5dfa0b76abdecc5081f13"},
{file = "pillow-10.2.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:9d189550615b4948f45252d7f005e53c2040cea1af5b60d6f79491a6e147eef7"},
{file = "pillow-10.2.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:49d9ba1ed0ef3e061088cd1e7538a0759aab559e2e0a80a36f9fd9d8c0c21591"},
{file = "pillow-10.2.0-cp39-cp39-win32.whl", hash = "sha256:babf5acfede515f176833ed6028754cbcd0d206f7f614ea3447d67c33be12516"},
{file = "pillow-10.2.0-cp39-cp39-win_amd64.whl", hash = "sha256:0304004f8067386b477d20a518b50f3fa658a28d44e4116970abfcd94fac34a8"},
{file = "pillow-10.2.0-cp39-cp39-win_arm64.whl", hash = "sha256:0fb3e7fc88a14eacd303e90481ad983fd5b69c761e9e6ef94c983f91025da869"},
{file = "pillow-10.2.0-pp310-pypy310_pp73-macosx_10_10_x86_64.whl", hash = "sha256:322209c642aabdd6207517e9739c704dc9f9db943015535783239022002f054a"},
{file = "pillow-10.2.0-pp310-pypy310_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3eedd52442c0a5ff4f887fab0c1c0bb164d8635b32c894bc1faf4c618dd89df2"},
{file = "pillow-10.2.0-pp310-pypy310_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:cb28c753fd5eb3dd859b4ee95de66cc62af91bcff5db5f2571d32a520baf1f04"},
{file = "pillow-10.2.0-pp310-pypy310_pp73-manylinux_2_28_aarch64.whl", hash = "sha256:33870dc4653c5017bf4c8873e5488d8f8d5f8935e2f1fb9a2208c47cdd66efd2"},
{file = "pillow-10.2.0-pp310-pypy310_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:3c31822339516fb3c82d03f30e22b1d038da87ef27b6a78c9549888f8ceda39a"},
{file = "pillow-10.2.0-pp310-pypy310_pp73-win_amd64.whl", hash = "sha256:a2b56ba36e05f973d450582fb015594aaa78834fefe8dfb8fcd79b93e64ba4c6"},
{file = "pillow-10.2.0-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:d8e6aeb9201e655354b3ad049cb77d19813ad4ece0df1249d3c793de3774f8c7"},
{file = "pillow-10.2.0-pp39-pypy39_pp73-macosx_10_10_x86_64.whl", hash = "sha256:2247178effb34a77c11c0e8ac355c7a741ceca0a732b27bf11e747bbc950722f"},
{file = "pillow-10.2.0-pp39-pypy39_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:15587643b9e5eb26c48e49a7b33659790d28f190fc514a322d55da2fb5c2950e"},
{file = "pillow-10.2.0-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:753cd8f2086b2b80180d9b3010dd4ed147efc167c90d3bf593fe2af21265e5a5"},
{file = "pillow-10.2.0-pp39-pypy39_pp73-manylinux_2_28_aarch64.whl", hash = "sha256:7c8f97e8e7a9009bcacbe3766a36175056c12f9a44e6e6f2d5caad06dcfbf03b"},
{file = "pillow-10.2.0-pp39-pypy39_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:d1b35bcd6c5543b9cb547dee3150c93008f8dd0f1fef78fc0cd2b141c5baf58a"},
{file = "pillow-10.2.0-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:fe4c15f6c9285dc54ce6553a3ce908ed37c8f3825b5a51a15c91442bb955b868"},
{file = "pillow-10.2.0.tar.gz", hash = "sha256:e87f0b2c78157e12d7686b27d63c070fd65d994e8ddae6f328e0dcf4a0cd007e"},
]
[package.extras]
docs = ["furo", "olefile", "sphinx (>=2.4)", "sphinx-copybutton", "sphinx-inline-tabs", "sphinx-removed-in", "sphinxext-opengraph"]
fpx = ["olefile"]
mic = ["olefile"]
tests = ["check-manifest", "coverage", "defusedxml", "markdown2", "olefile", "packaging", "pyroma", "pytest", "pytest-cov", "pytest-timeout"]
typing = ["typing-extensions"]
xmp = ["defusedxml"]
[[package]]
name = "pkginfo"
@@ -2596,27 +2659,27 @@ wcwidth = "*"
[[package]]
name = "psutil"
version = "5.9.7"
version = "5.9.8"
description = "Cross-platform lib for process and system monitoring in Python."
optional = false
python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*, !=3.5.*"
files = [
{file = "psutil-5.9.7-cp27-cp27m-macosx_10_9_x86_64.whl", hash = "sha256:0bd41bf2d1463dfa535942b2a8f0e958acf6607ac0be52265ab31f7923bcd5e6"},
{file = "psutil-5.9.7-cp27-cp27m-manylinux2010_i686.whl", hash = "sha256:5794944462509e49d4d458f4dbfb92c47539e7d8d15c796f141f474010084056"},
{file = "psutil-5.9.7-cp27-cp27m-manylinux2010_x86_64.whl", hash = "sha256:fe361f743cb3389b8efda21980d93eb55c1f1e3898269bc9a2a1d0bb7b1f6508"},
{file = "psutil-5.9.7-cp27-cp27mu-manylinux2010_i686.whl", hash = "sha256:e469990e28f1ad738f65a42dcfc17adaed9d0f325d55047593cb9033a0ab63df"},
{file = "psutil-5.9.7-cp27-cp27mu-manylinux2010_x86_64.whl", hash = "sha256:3c4747a3e2ead1589e647e64aad601981f01b68f9398ddf94d01e3dc0d1e57c7"},
{file = "psutil-5.9.7-cp27-none-win32.whl", hash = "sha256:1d4bc4a0148fdd7fd8f38e0498639ae128e64538faa507df25a20f8f7fb2341c"},
{file = "psutil-5.9.7-cp27-none-win_amd64.whl", hash = "sha256:4c03362e280d06bbbfcd52f29acd79c733e0af33d707c54255d21029b8b32ba6"},
{file = "psutil-5.9.7-cp36-abi3-macosx_10_9_x86_64.whl", hash = "sha256:ea36cc62e69a13ec52b2f625c27527f6e4479bca2b340b7a452af55b34fcbe2e"},
{file = "psutil-5.9.7-cp36-abi3-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:1132704b876e58d277168cd729d64750633d5ff0183acf5b3c986b8466cd0284"},
{file = "psutil-5.9.7-cp36-abi3-manylinux_2_12_x86_64.manylinux2010_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:fe8b7f07948f1304497ce4f4684881250cd859b16d06a1dc4d7941eeb6233bfe"},
{file = "psutil-5.9.7-cp36-cp36m-win32.whl", hash = "sha256:b27f8fdb190c8c03914f908a4555159327d7481dac2f01008d483137ef3311a9"},
{file = "psutil-5.9.7-cp36-cp36m-win_amd64.whl", hash = "sha256:44969859757f4d8f2a9bd5b76eba8c3099a2c8cf3992ff62144061e39ba8568e"},
{file = "psutil-5.9.7-cp37-abi3-win32.whl", hash = "sha256:c727ca5a9b2dd5193b8644b9f0c883d54f1248310023b5ad3e92036c5e2ada68"},
{file = "psutil-5.9.7-cp37-abi3-win_amd64.whl", hash = "sha256:f37f87e4d73b79e6c5e749440c3113b81d1ee7d26f21c19c47371ddea834f414"},
{file = "psutil-5.9.7-cp38-abi3-macosx_11_0_arm64.whl", hash = "sha256:032f4f2c909818c86cea4fe2cc407f1c0f0cde8e6c6d702b28b8ce0c0d143340"},
{file = "psutil-5.9.7.tar.gz", hash = "sha256:3f02134e82cfb5d089fddf20bb2e03fd5cd52395321d1c8458a9e58500ff417c"},
{file = "psutil-5.9.8-cp27-cp27m-macosx_10_9_x86_64.whl", hash = "sha256:26bd09967ae00920df88e0352a91cff1a78f8d69b3ecabbfe733610c0af486c8"},
{file = "psutil-5.9.8-cp27-cp27m-manylinux2010_i686.whl", hash = "sha256:05806de88103b25903dff19bb6692bd2e714ccf9e668d050d144012055cbca73"},
{file = "psutil-5.9.8-cp27-cp27m-manylinux2010_x86_64.whl", hash = "sha256:611052c4bc70432ec770d5d54f64206aa7203a101ec273a0cd82418c86503bb7"},
{file = "psutil-5.9.8-cp27-cp27mu-manylinux2010_i686.whl", hash = "sha256:50187900d73c1381ba1454cf40308c2bf6f34268518b3f36a9b663ca87e65e36"},
{file = "psutil-5.9.8-cp27-cp27mu-manylinux2010_x86_64.whl", hash = "sha256:02615ed8c5ea222323408ceba16c60e99c3f91639b07da6373fb7e6539abc56d"},
{file = "psutil-5.9.8-cp27-none-win32.whl", hash = "sha256:36f435891adb138ed3c9e58c6af3e2e6ca9ac2f365efe1f9cfef2794e6c93b4e"},
{file = "psutil-5.9.8-cp27-none-win_amd64.whl", hash = "sha256:bd1184ceb3f87651a67b2708d4c3338e9b10c5df903f2e3776b62303b26cb631"},
{file = "psutil-5.9.8-cp36-abi3-macosx_10_9_x86_64.whl", hash = "sha256:aee678c8720623dc456fa20659af736241f575d79429a0e5e9cf88ae0605cc81"},
{file = "psutil-5.9.8-cp36-abi3-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:8cb6403ce6d8e047495a701dc7c5bd788add903f8986d523e3e20b98b733e421"},
{file = "psutil-5.9.8-cp36-abi3-manylinux_2_12_x86_64.manylinux2010_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d06016f7f8625a1825ba3732081d77c94589dca78b7a3fc072194851e88461a4"},
{file = "psutil-5.9.8-cp36-cp36m-win32.whl", hash = "sha256:7d79560ad97af658a0f6adfef8b834b53f64746d45b403f225b85c5c2c140eee"},
{file = "psutil-5.9.8-cp36-cp36m-win_amd64.whl", hash = "sha256:27cc40c3493bb10de1be4b3f07cae4c010ce715290a5be22b98493509c6299e2"},
{file = "psutil-5.9.8-cp37-abi3-win32.whl", hash = "sha256:bc56c2a1b0d15aa3eaa5a60c9f3f8e3e565303b465dbf57a1b730e7a2b9844e0"},
{file = "psutil-5.9.8-cp37-abi3-win_amd64.whl", hash = "sha256:8db4c1b57507eef143a15a6884ca10f7c73876cdf5d51e713151c1236a0e68cf"},
{file = "psutil-5.9.8-cp38-abi3-macosx_11_0_arm64.whl", hash = "sha256:d16bbddf0693323b8c6123dd804100241da461e41d6e332fb0ba6058f630f8c8"},
{file = "psutil-5.9.8.tar.gz", hash = "sha256:6be126e3225486dff286a8fb9a06246a5253f4c7c53b475ea5f5ac934e64194c"},
]
[package.extras]
@@ -3416,45 +3479,45 @@ test = ["asv", "gmpy2", "mpmath", "pooch", "pytest", "pytest-cov", "pytest-timeo
[[package]]
name = "scipy"
version = "1.11.4"
version = "1.12.0"
description = "Fundamental algorithms for scientific computing in Python"
optional = false
python-versions = ">=3.9"
files = [
{file = "scipy-1.11.4-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:bc9a714581f561af0848e6b69947fda0614915f072dfd14142ed1bfe1b806710"},
{file = "scipy-1.11.4-cp310-cp310-macosx_12_0_arm64.whl", hash = "sha256:cf00bd2b1b0211888d4dc75656c0412213a8b25e80d73898083f402b50f47e41"},
{file = "scipy-1.11.4-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b9999c008ccf00e8fbcce1236f85ade5c569d13144f77a1946bef8863e8f6eb4"},
{file = "scipy-1.11.4-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:933baf588daa8dc9a92c20a0be32f56d43faf3d1a60ab11b3f08c356430f6e56"},
{file = "scipy-1.11.4-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:8fce70f39076a5aa62e92e69a7f62349f9574d8405c0a5de6ed3ef72de07f446"},
{file = "scipy-1.11.4-cp310-cp310-win_amd64.whl", hash = "sha256:6550466fbeec7453d7465e74d4f4b19f905642c89a7525571ee91dd7adabb5a3"},
{file = "scipy-1.11.4-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:f313b39a7e94f296025e3cffc2c567618174c0b1dde173960cf23808f9fae4be"},
{file = "scipy-1.11.4-cp311-cp311-macosx_12_0_arm64.whl", hash = "sha256:1b7c3dca977f30a739e0409fb001056484661cb2541a01aba0bb0029f7b68db8"},
{file = "scipy-1.11.4-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:00150c5eae7b610c32589dda259eacc7c4f1665aedf25d921907f4d08a951b1c"},
{file = "scipy-1.11.4-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:530f9ad26440e85766509dbf78edcfe13ffd0ab7fec2560ee5c36ff74d6269ff"},
{file = "scipy-1.11.4-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:5e347b14fe01003d3b78e196e84bd3f48ffe4c8a7b8a1afbcb8f5505cb710993"},
{file = "scipy-1.11.4-cp311-cp311-win_amd64.whl", hash = "sha256:acf8ed278cc03f5aff035e69cb511741e0418681d25fbbb86ca65429c4f4d9cd"},
{file = "scipy-1.11.4-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:028eccd22e654b3ea01ee63705681ee79933652b2d8f873e7949898dda6d11b6"},
{file = "scipy-1.11.4-cp312-cp312-macosx_12_0_arm64.whl", hash = "sha256:2c6ff6ef9cc27f9b3db93a6f8b38f97387e6e0591600369a297a50a8e96e835d"},
{file = "scipy-1.11.4-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b030c6674b9230d37c5c60ab456e2cf12f6784596d15ce8da9365e70896effc4"},
{file = "scipy-1.11.4-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ad669df80528aeca5f557712102538f4f37e503f0c5b9541655016dd0932ca79"},
{file = "scipy-1.11.4-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:ce7fff2e23ab2cc81ff452a9444c215c28e6305f396b2ba88343a567feec9660"},
{file = "scipy-1.11.4-cp312-cp312-win_amd64.whl", hash = "sha256:36750b7733d960d7994888f0d148d31ea3017ac15eef664194b4ef68d36a4a97"},
{file = "scipy-1.11.4-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:6e619aba2df228a9b34718efb023966da781e89dd3d21637b27f2e54db0410d7"},
{file = "scipy-1.11.4-cp39-cp39-macosx_12_0_arm64.whl", hash = "sha256:f3cd9e7b3c2c1ec26364856f9fbe78695fe631150f94cd1c22228456404cf1ec"},
{file = "scipy-1.11.4-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d10e45a6c50211fe256da61a11c34927c68f277e03138777bdebedd933712fea"},
{file = "scipy-1.11.4-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:91af76a68eeae0064887a48e25c4e616fa519fa0d38602eda7e0f97d65d57937"},
{file = "scipy-1.11.4-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:6df1468153a31cf55ed5ed39647279beb9cfb5d3f84369453b49e4b8502394fd"},
{file = "scipy-1.11.4-cp39-cp39-win_amd64.whl", hash = "sha256:ee410e6de8f88fd5cf6eadd73c135020bfbbbdfcd0f6162c36a7638a1ea8cc65"},
{file = "scipy-1.11.4.tar.gz", hash = "sha256:90a2b78e7f5733b9de748f589f09225013685f9b218275257f8a8168ededaeaa"},
{file = "scipy-1.12.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:78e4402e140879387187f7f25d91cc592b3501a2e51dfb320f48dfb73565f10b"},
{file = "scipy-1.12.0-cp310-cp310-macosx_12_0_arm64.whl", hash = "sha256:f5f00ebaf8de24d14b8449981a2842d404152774c1a1d880c901bf454cb8e2a1"},
{file = "scipy-1.12.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e53958531a7c695ff66c2e7bb7b79560ffdc562e2051644c5576c39ff8efb563"},
{file = "scipy-1.12.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5e32847e08da8d895ce09d108a494d9eb78974cf6de23063f93306a3e419960c"},
{file = "scipy-1.12.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:4c1020cad92772bf44b8e4cdabc1df5d87376cb219742549ef69fc9fd86282dd"},
{file = "scipy-1.12.0-cp310-cp310-win_amd64.whl", hash = "sha256:75ea2a144096b5e39402e2ff53a36fecfd3b960d786b7efd3c180e29c39e53f2"},
{file = "scipy-1.12.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:408c68423f9de16cb9e602528be4ce0d6312b05001f3de61fe9ec8b1263cad08"},
{file = "scipy-1.12.0-cp311-cp311-macosx_12_0_arm64.whl", hash = "sha256:5adfad5dbf0163397beb4aca679187d24aec085343755fcdbdeb32b3679f254c"},
{file = "scipy-1.12.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c3003652496f6e7c387b1cf63f4bb720951cfa18907e998ea551e6de51a04467"},
{file = "scipy-1.12.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8b8066bce124ee5531d12a74b617d9ac0ea59245246410e19bca549656d9a40a"},
{file = "scipy-1.12.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:8bee4993817e204d761dba10dbab0774ba5a8612e57e81319ea04d84945375ba"},
{file = "scipy-1.12.0-cp311-cp311-win_amd64.whl", hash = "sha256:a24024d45ce9a675c1fb8494e8e5244efea1c7a09c60beb1eeb80373d0fecc70"},
{file = "scipy-1.12.0-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:e7e76cc48638228212c747ada851ef355c2bb5e7f939e10952bc504c11f4e372"},
{file = "scipy-1.12.0-cp312-cp312-macosx_12_0_arm64.whl", hash = "sha256:f7ce148dffcd64ade37b2df9315541f9adad6efcaa86866ee7dd5db0c8f041c3"},
{file = "scipy-1.12.0-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9c39f92041f490422924dfdb782527a4abddf4707616e07b021de33467f917bc"},
{file = "scipy-1.12.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a7ebda398f86e56178c2fa94cad15bf457a218a54a35c2a7b4490b9f9cb2676c"},
{file = "scipy-1.12.0-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:95e5c750d55cf518c398a8240571b0e0782c2d5a703250872f36eaf737751338"},
{file = "scipy-1.12.0-cp312-cp312-win_amd64.whl", hash = "sha256:e646d8571804a304e1da01040d21577685ce8e2db08ac58e543eaca063453e1c"},
{file = "scipy-1.12.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:913d6e7956c3a671de3b05ccb66b11bc293f56bfdef040583a7221d9e22a2e35"},
{file = "scipy-1.12.0-cp39-cp39-macosx_12_0_arm64.whl", hash = "sha256:bba1b0c7256ad75401c73e4b3cf09d1f176e9bd4248f0d3112170fb2ec4db067"},
{file = "scipy-1.12.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:730badef9b827b368f351eacae2e82da414e13cf8bd5051b4bdfd720271a5371"},
{file = "scipy-1.12.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6546dc2c11a9df6926afcbdd8a3edec28566e4e785b915e849348c6dd9f3f490"},
{file = "scipy-1.12.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:196ebad3a4882081f62a5bf4aeb7326aa34b110e533aab23e4374fcccb0890dc"},
{file = "scipy-1.12.0-cp39-cp39-win_amd64.whl", hash = "sha256:b360f1b6b2f742781299514e99ff560d1fe9bd1bff2712894b52abe528d1fd1e"},
{file = "scipy-1.12.0.tar.gz", hash = "sha256:4bf5abab8a36d20193c698b0f1fc282c1d083c94723902c447e5d2f1780936a3"},
]
[package.dependencies]
numpy = ">=1.21.6,<1.28.0"
numpy = ">=1.22.4,<1.29.0"
[package.extras]
dev = ["click", "cython-lint (>=0.12.2)", "doit (>=0.36.0)", "mypy", "pycodestyle", "pydevtool", "rich-click", "ruff", "types-psutil", "typing_extensions"]
doc = ["jupytext", "matplotlib (>2)", "myst-nb", "numpydoc", "pooch", "pydata-sphinx-theme (==0.9.0)", "sphinx (!=4.1.0)", "sphinx-design (>=0.2.0)"]
test = ["asv", "gmpy2", "mpmath", "pooch", "pytest", "pytest-cov", "pytest-timeout", "pytest-xdist", "scikit-umfpack", "threadpoolctl"]
test = ["asv", "gmpy2", "hypothesis", "mpmath", "pooch", "pytest", "pytest-cov", "pytest-timeout", "pytest-xdist", "scikit-umfpack", "threadpoolctl"]
[[package]]
name = "secretstorage"
@@ -3909,4 +3972,4 @@ desktop = ["opencv-python"]
[metadata]
lock-version = "2.0"
python-versions = "^3.8"
content-hash = "3d59673b11422c0c463ec7b7e20b8a295155d71a6c42ad97f819e9798643b0ef"
content-hash = "5e5a6f753fc524c096453bc89bb70514d1a7b4ffda3a9c8ed4938b549d194b3f"
+3 -3
View File
@@ -37,9 +37,8 @@ scipy = [
{ version = "1.10.0", python = "<3.9" },
{ version = "^1.10.0", python = ">=3.9" }
]
matplotlib = ">=3.5.0"
matplotlib = ">=3.6.0"
pyyaml = ">=5.3"
pillow = ">=9.4"
opencv-python = { version = ">=4.5.5.64", optional = true }
opencv-python-headless = ">=4.5.5.64"
requests = { version = ">=2.26.0,<=2.31.0", optional = true }
@@ -47,6 +46,7 @@ tqdm = { version = ">=4.62.3,<=4.66.1", optional = true }
defusedxml = "^0.7.1"
[tool.poetry.extras]
desktop = ["opencv-python"]
assets = ["requests","tqdm"]
@@ -65,7 +65,7 @@ tox = "^4.11.4"
[tool.poetry.group.docs.dependencies]
mkdocs-material = {extras = ["imaging"], version = "^9.5.4"}
mkdocs-material = {extras = ["imaging"], version = "^9.5.5"}
mkdocstrings = {extras = ["python"], version = ">=0.20,<0.25"}
+1
View File
@@ -38,6 +38,7 @@ from supervision.detection.core import Detections
from supervision.detection.line_counter import LineZone, LineZoneAnnotator
from supervision.detection.tools.inference_slicer import InferenceSlicer
from supervision.detection.tools.polygon_zone import PolygonZone, PolygonZoneAnnotator
from supervision.detection.tools.smoother import DetectionsSmoother
from supervision.detection.utils import (
box_iou_batch,
calculate_masks_centroids,
+154 -155
View File
@@ -57,16 +57,16 @@ class BoundingBoxAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> bounding_box_annotator = sv.BoundingBoxAnnotator()
>>> annotated_frame = bounding_box_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
bounding_box_annotator = sv.BoundingBoxAnnotator()
annotated_frame = bounding_box_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![bounding-box-annotator-example](https://media.roboflow.com/
@@ -176,7 +176,7 @@ class MaskAnnotator(BaseAnnotator):
!!! warning
This annotator utilizes the `sv.Detections.mask`.
This annotator uses `sv.Detections.mask`.
"""
def __init__(
@@ -217,16 +217,16 @@ class MaskAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> mask_annotator = sv.MaskAnnotator()
>>> annotated_frame = mask_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
mask_annotator = sv.MaskAnnotator()
annotated_frame = mask_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![mask-annotator-example](https://media.roboflow.com/
@@ -259,7 +259,7 @@ class PolygonAnnotator(BaseAnnotator):
!!! warning
This annotator utilizes the `sv.Detections.mask`.
This annotator uses `sv.Detections.mask`.
"""
def __init__(
@@ -300,16 +300,16 @@ class PolygonAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> polygon_annotator = sv.PolygonAnnotator()
>>> annotated_frame = polygon_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
polygon_annotator = sv.PolygonAnnotator()
annotated_frame = polygon_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![polygon-annotator-example](https://media.roboflow.com/
@@ -382,16 +382,16 @@ class ColorAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> color_annotator = sv.ColorAnnotator()
>>> annotated_frame = color_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
color_annotator = sv.ColorAnnotator()
annotated_frame = color_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![box-mask-annotator-example](https://media.roboflow.com/
@@ -427,7 +427,7 @@ class HaloAnnotator(BaseAnnotator):
!!! warning
This annotator utilizes the `sv.Detections.mask`.
This annotator uses `sv.Detections.mask`.
"""
def __init__(
@@ -472,16 +472,16 @@ class HaloAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> halo_annotator = sv.HaloAnnotator()
>>> annotated_frame = halo_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
halo_annotator = sv.HaloAnnotator()
annotated_frame = halo_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![halo-annotator-example](https://media.roboflow.com/
@@ -566,16 +566,16 @@ class EllipseAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> ellipse_annotator = sv.EllipseAnnotator()
>>> annotated_frame = ellipse_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
ellipse_annotator = sv.EllipseAnnotator()
annotated_frame = ellipse_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![ellipse-annotator-example](https://media.roboflow.com/
@@ -653,16 +653,16 @@ class BoxCornerAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> corner_annotator = sv.BoxCornerAnnotator()
>>> annotated_frame = corner_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
corner_annotator = sv.BoxCornerAnnotator()
annotated_frame = corner_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![box-corner-annotator-example](https://media.roboflow.com/
@@ -737,16 +737,16 @@ class CircleAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> circle_annotator = sv.CircleAnnotator()
>>> annotated_frame = circle_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
circle_annotator = sv.CircleAnnotator()
annotated_frame = circle_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
@@ -823,16 +823,16 @@ class DotAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> dot_annotator = sv.DotAnnotator()
>>> annotated_frame = dot_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
dot_annotator = sv.DotAnnotator()
annotated_frame = dot_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![dot-annotator-example](https://media.roboflow.com/
@@ -950,16 +950,16 @@ class LabelAnnotator:
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> label_annotator = sv.LabelAnnotator(text_position=sv.Position.CENTER)
>>> annotated_frame = label_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
label_annotator = sv.LabelAnnotator(text_position=sv.Position.CENTER)
annotated_frame = label_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![label-annotator-example](https://media.roboflow.com/
@@ -1064,16 +1064,16 @@ class BlurAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> blur_annotator = sv.BlurAnnotator()
>>> annotated_frame = circle_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
blur_annotator = sv.BlurAnnotator()
annotated_frame = circle_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![blur-annotator-example](https://media.roboflow.com/
@@ -1098,7 +1098,7 @@ class TraceAnnotator:
!!! warning
This annotator utilizes the `sv.Detections.tracker_id`. Read
This annotator uses the `sv.Detections.tracker_id`. Read
[here](https://supervision.roboflow.com/trackers/) to learn how to plug
tracking into your inference pipeline.
"""
@@ -1149,26 +1149,25 @@ class TraceAnnotator:
Example:
```python
>>> import supervision as sv
>>> from ultralytics import YOLO
import supervision as sv
from ultralytics import YOLO
>>> model = YOLO('yolov8x.pt')
model = YOLO('yolov8x.pt')
trace_annotator = sv.TraceAnnotator()
>>> trace_annotator = sv.TraceAnnotator()
video_info = sv.VideoInfo.from_video_path(video_path='...')
frames_generator = sv.get_video_frames_generator(source_path='...')
tracker = sv.ByteTrack()
>>> video_info = sv.VideoInfo.from_video_path(video_path='...')
>>> frames_generator = sv.get_video_frames_generator(source_path='...')
>>> tracker = sv.ByteTrack()
>>> with sv.VideoSink(target_path='...', video_info=video_info) as sink:
... for frame in frames_generator:
... result = model(frame)[0]
... detections = sv.Detections.from_ultralytics(result)
... detections = tracker.update_with_detections(detections)
... annotated_frame = trace_annotator.annotate(
... scene=frame.copy(),
... detections=detections)
... sink.write_frame(frame=annotated_frame)
with sv.VideoSink(target_path='...', video_info=video_info) as sink:
for frame in frames_generator:
result = model(frame)[0]
detections = sv.Detections.from_ultralytics(result)
detections = tracker.update_with_detections(detections)
annotated_frame = trace_annotator.annotate(
scene=frame.copy(),
detections=detections)
sink.write_frame(frame=annotated_frame)
```
![trace-annotator-example](https://media.roboflow.com/
@@ -1245,24 +1244,24 @@ class HeatMapAnnotator:
Example:
```python
>>> import supervision as sv
>>> from ultralytics import YOLO
import supervision as sv
from ultralytics import YOLO
>>> model = YOLO('yolov8x.pt')
model = YOLO('yolov8x.pt')
>>> heat_map_annotator = sv.HeatMapAnnotator()
heat_map_annotator = sv.HeatMapAnnotator()
>>> video_info = sv.VideoInfo.from_video_path(video_path='...')
>>> frames_generator = get_video_frames_generator(source_path='...')
video_info = sv.VideoInfo.from_video_path(video_path='...')
frames_generator = get_video_frames_generator(source_path='...')
>>> with sv.VideoSink(target_path='...', video_info=video_info) as sink:
... for frame in frames_generator:
... result = model(frame)[0]
... detections = sv.Detections.from_ultralytics(result)
... annotated_frame = heat_map_annotator.annotate(
... scene=frame.copy(),
... detections=detections)
... sink.write_frame(frame=annotated_frame)
with sv.VideoSink(target_path='...', video_info=video_info) as sink:
for frame in frames_generator:
result = model(frame)[0]
detections = sv.Detections.from_ultralytics(result)
annotated_frame = heat_map_annotator.annotate(
scene=frame.copy(),
detections=detections)
sink.write_frame(frame=annotated_frame)
```
![heatmap-annotator-example](https://media.roboflow.com/
@@ -1322,16 +1321,16 @@ class PixelateAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> pixelate_annotator = sv.PixelateAnnotator()
>>> annotated_frame = pixelate_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
pixelate_annotator = sv.PixelateAnnotator()
annotated_frame = pixelate_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![pixelate-annotator-example](https://media.roboflow.com/
@@ -1408,16 +1407,16 @@ class TriangleAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> triangle_annotator = sv.TriangleAnnotator()
>>> annotated_frame = triangle_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
triangle_annotator = sv.TriangleAnnotator()
annotated_frame = triangle_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![triangle-annotator-example](https://media.roboflow.com/
@@ -1501,16 +1500,16 @@ class RoundBoxAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> round_box_annotator = sv.RoundBoxAnnotator()
>>> annotated_frame = round_box_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
round_box_annotator = sv.RoundBoxAnnotator()
annotated_frame = round_box_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![round-box-annotator-example](https://media.roboflow.com/
@@ -1641,16 +1640,16 @@ class PercentageBarAnnotator(BaseAnnotator):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> image = ...
>>> detections = sv.Detections(...)
image = ...
detections = sv.Detections(...)
>>> percentage_bar_annotator = sv.BoundingBoxAnnotator()
>>> annotated_frame = percentage_bar_annotator.annotate(
... scene=image.copy(),
... detections=detections
... )
percentage_bar_annotator = sv.BoundingBoxAnnotator()
annotated_frame = percentage_bar_annotator.annotate(
scene=image.copy(),
detections=detections
)
```
![percentage-bar-example](https://media.roboflow.com/
+2 -2
View File
@@ -54,9 +54,9 @@ def download_assets(asset_name: Union[VideoAssets, str]) -> str:
Example:
```python
>>> from supervision.assets import download_assets, VideoAssets
from supervision.assets import download_assets, VideoAssets
>>> download_assets(VideoAssets.VEHICLES)
download_assets(VideoAssets.VEHICLES)
"vehicles.mp4"
```
"""
+33 -33
View File
@@ -59,18 +59,18 @@ class Classifications:
Example:
```python
>>> from PIL import Image
>>> import clip
>>> import supervision as sv
from PIL import Image
import clip
import supervision as sv
>>> model, preprocess = clip.load('ViT-B/32')
model, preprocess = clip.load('ViT-B/32')
>>> image = cv2.imread(SOURCE_IMAGE_PATH)
>>> image = preprocess(image).unsqueeze(0)
image = cv2.imread(SOURCE_IMAGE_PATH)
image = preprocess(image).unsqueeze(0)
>>> text = clip.tokenize(["a diagram", "a dog", "a cat"])
>>> output, _ = model(image, text)
>>> classifications = sv.Classifications.from_clip(output)
text = clip.tokenize(["a diagram", "a dog", "a cat"])
output, _ = model(image, text)
classifications = sv.Classifications.from_clip(output)
```
"""
@@ -97,15 +97,15 @@ class Classifications:
Example:
```python
>>> import cv2
>>> from ultralytics import YOLO
>>> import supervision as sv
import cv2
from ultralytics import YOLO
import supervision as sv
>>> image = cv2.imread(SOURCE_IMAGE_PATH)
>>> model = YOLO('yolov8n-cls.pt')
image = cv2.imread(SOURCE_IMAGE_PATH)
model = YOLO('yolov8n-cls.pt')
>>> output = model(image)[0]
>>> classifications = sv.Classifications.from_ultralytics(output)
output = model(image)[0]
classifications = sv.Classifications.from_ultralytics(output)
```
"""
confidence = ultralytics_results.probs.data.cpu().numpy()
@@ -125,25 +125,25 @@ class Classifications:
Example:
```python
>>> from PIL import Image
>>> import timm
>>> from timm.data import resolve_data_config, create_transform
>>> import supervision as sv
from PIL import Image
import timm
from timm.data import resolve_data_config, create_transform
import supervision as sv
>>> model = timm.create_model(
... model_name='hf-hub:nateraw/resnet50-oxford-iiit-pet',
... pretrained=True
... ).eval()
model = timm.create_model(
model_name='hf-hub:nateraw/resnet50-oxford-iiit-pet',
pretrained=True
).eval()
>>> config = resolve_data_config({}, model=model)
>>> transform = create_transform(**config)
config = resolve_data_config({}, model=model)
transform = create_transform(**config)
>>> image = Image.open(SOURCE_IMAGE_PATH).convert('RGB')
>>> x = transform(image).unsqueeze(0)
image = Image.open(SOURCE_IMAGE_PATH).convert('RGB')
x = transform(image).unsqueeze(0)
>>> output = model(x)
output = model(x)
>>> classifications = sv.Classifications.from_timm(output)
classifications = sv.Classifications.from_timm(output)
```
"""
confidence = timm_results.cpu().detach().numpy()[0]
@@ -168,11 +168,11 @@ class Classifications:
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> classifications = sv.Classifications(...)
classifications = sv.Classifications(...)
>>> classifications.get_top_k(1)
classifications.get_top_k(1)
(array([1]), array([0.9]))
```
+78 -81
View File
@@ -118,13 +118,13 @@ class DetectionDataset(BaseDataset):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> ds = sv.DetectionDataset(...)
>>> train_ds, test_ds = ds.split(split_ratio=0.7,
... random_state=42, shuffle=True)
>>> len(train_ds), len(test_ds)
(700, 300)
ds = sv.DetectionDataset(...)
train_ds, test_ds = ds.split(split_ratio=0.7,
random_state=42, shuffle=True)
len(train_ds), len(test_ds)
# (700, 300)
```
"""
@@ -231,24 +231,24 @@ class DetectionDataset(BaseDataset):
Example:
```python
>>> import roboflow
>>> from roboflow import Roboflow
>>> import supervision as sv
import roboflow
from roboflow import Roboflow
import supervision as sv
>>> roboflow.login()
roboflow.login()
>>> rf = Roboflow()
rf = Roboflow()
>>> project = rf.workspace(WORKSPACE_ID).project(PROJECT_ID)
>>> dataset = project.version(PROJECT_VERSION).download("voc")
project = rf.workspace(WORKSPACE_ID).project(PROJECT_ID)
dataset = project.version(PROJECT_VERSION).download("voc")
>>> ds = sv.DetectionDataset.from_pascal_voc(
... images_directory_path=f"{dataset.location}/train/images",
... annotations_directory_path=f"{dataset.location}/train/labels"
... )
ds = sv.DetectionDataset.from_pascal_voc(
images_directory_path=f"{dataset.location}/train/images",
annotations_directory_path=f"{dataset.location}/train/labels"
)
>>> ds.classes
['dog', 'person']
ds.classes
# ['dog', 'person']
```
"""
@@ -288,25 +288,24 @@ class DetectionDataset(BaseDataset):
Example:
```python
>>> import roboflow
>>> from roboflow import Roboflow
>>> import supervision as sv
import roboflow
from roboflow import Roboflow
import supervision as sv
>>> roboflow.login()
roboflow.login()
rf = Roboflow()
>>> rf = Roboflow()
project = rf.workspace(WORKSPACE_ID).project(PROJECT_ID)
dataset = project.version(PROJECT_VERSION).download("yolov5")
>>> project = rf.workspace(WORKSPACE_ID).project(PROJECT_ID)
>>> dataset = project.version(PROJECT_VERSION).download("yolov5")
ds = sv.DetectionDataset.from_yolo(
images_directory_path=f"{dataset.location}/train/images",
annotations_directory_path=f"{dataset.location}/train/labels",
data_yaml_path=f"{dataset.location}/data.yaml"
)
>>> ds = sv.DetectionDataset.from_yolo(
... images_directory_path=f"{dataset.location}/train/images",
... annotations_directory_path=f"{dataset.location}/train/labels",
... data_yaml_path=f"{dataset.location}/data.yaml"
... )
>>> ds.classes
['dog', 'person']
ds.classes
# ['dog', 'person']
```
"""
classes, images, annotations = load_yolo_annotations(
@@ -394,24 +393,23 @@ class DetectionDataset(BaseDataset):
Example:
```python
>>> import roboflow
>>> from roboflow import Roboflow
>>> import supervision as sv
import roboflow
from roboflow import Roboflow
import supervision as sv
>>> roboflow.login()
roboflow.login()
rf = Roboflow()
>>> rf = Roboflow()
project = rf.workspace(WORKSPACE_ID).project(PROJECT_ID)
dataset = project.version(PROJECT_VERSION).download("coco")
>>> project = rf.workspace(WORKSPACE_ID).project(PROJECT_ID)
>>> dataset = project.version(PROJECT_VERSION).download("coco")
ds = sv.DetectionDataset.from_coco(
images_directory_path=f"{dataset.location}/train",
annotations_path=f"{dataset.location}/train/_annotations.coco.json",
)
>>> ds = sv.DetectionDataset.from_coco(
... images_directory_path=f"{dataset.location}/train",
... annotations_path=f"{dataset.location}/train/_annotations.coco.json",
... )
>>> ds.classes
['dog', 'person']
ds.classes
# ['dog', 'person']
```
"""
classes, images, annotations = load_coco_annotations(
@@ -486,25 +484,25 @@ class DetectionDataset(BaseDataset):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> ds_1 = sv.DetectionDataset(...)
>>> len(ds_1)
100
>>> ds_1.classes
['dog', 'person']
ds_1 = sv.DetectionDataset(...)
len(ds_1)
# 100
ds_1.classes
# ['dog', 'person']
>>> ds_2 = sv.DetectionDataset(...)
>>> len(ds_2)
200
>>> ds_2.classes
['cat']
ds_2 = sv.DetectionDataset(...)
len(ds_2)
# 200
ds_2.classes
# ['cat']
>>> ds_merged = sv.DetectionDataset.merge([ds_1, ds_2])
>>> len(ds_merged)
300
>>> ds_merged.classes
['cat', 'dog', 'person']
ds_merged = sv.DetectionDataset.merge([ds_1, ds_2])
len(ds_merged)
# 300
ds_merged.classes
# ['cat', 'dog', 'person']
```
"""
merged_images, merged_annotations = {}, {}
@@ -571,13 +569,13 @@ class ClassificationDataset(BaseDataset):
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> cd = sv.ClassificationDataset(...)
>>> train_cd,test_cd = cd.split(split_ratio=0.7,
... random_state=42,shuffle=True)
>>> len(train_cd), len(test_cd)
(700, 300)
cd = sv.ClassificationDataset(...)
train_cd,test_cd = cd.split(split_ratio=0.7,
random_state=42,shuffle=True)
len(train_cd), len(test_cd)
# (700, 300)
```
"""
image_names = list(self.images.keys())
@@ -639,20 +637,19 @@ class ClassificationDataset(BaseDataset):
Example:
```python
>>> import roboflow
>>> from roboflow import Roboflow
>>> import supervision as sv
import roboflow
from roboflow import Roboflow
import supervision as sv
>>> roboflow.login()
roboflow.login()
rf = Roboflow()
>>> rf = Roboflow()
project = rf.workspace(WORKSPACE_ID).project(PROJECT_ID)
dataset = project.version(PROJECT_VERSION).download("folder")
>>> project = rf.workspace(WORKSPACE_ID).project(PROJECT_ID)
>>> dataset = project.version(PROJECT_VERSION).download("folder")
>>> cd = sv.ClassificationDataset.from_folder_structure(
... root_directory_path=f"{dataset.location}/train"
... )
cd = sv.ClassificationDataset.from_folder_structure(
root_directory_path=f"{dataset.location}/train"
)
```
"""
classes = os.listdir(root_directory_path)
+14 -15
View File
@@ -63,23 +63,22 @@ class BoxAnnotator:
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> classes = ['person', ...]
>>> image = ...
>>> detections = sv.Detections(...)
classes = ['person', ...]
image = ...
detections = sv.Detections(...)
>>> box_annotator = sv.BoxAnnotator()
>>> labels = [
... f"{classes[class_id]} {confidence:0.2f}"
... for _, _, confidence, class_id, _
... in detections
... ]
>>> annotated_frame = box_annotator.annotate(
... scene=image.copy(),
... detections=detections,
... labels=labels
... )
box_annotator = sv.BoxAnnotator()
labels = [
f"{classes[class_id]} {confidence:0.2f}"
for _, _, confidence, class_id, _ in detections
]
annotated_frame = box_annotator.annotate(
scene=image.copy(),
detections=detections,
labels=labels
)
```
"""
font = cv2.FONT_HERSHEY_SIMPLEX
+143 -147
View File
@@ -126,14 +126,14 @@ class Detections:
Example:
```python
>>> import cv2
>>> import torch
>>> import supervision as sv
import cv2
import torch
import supervision as sv
>>> image = cv2.imread(SOURCE_IMAGE_PATH)
>>> model = torch.hub.load('ultralytics/yolov5', 'yolov5s')
>>> result = model(image)
>>> detections = sv.Detections.from_yolov5(result)
image = cv2.imread(SOURCE_IMAGE_PATH)
model = torch.hub.load('ultralytics/yolov5', 'yolov5s')
result = model(image)
detections = sv.Detections.from_yolov5(result)
```
"""
yolov5_detections_predictions = yolov5_results.pred[0].cpu().cpu().numpy()
@@ -159,14 +159,14 @@ class Detections:
Example:
```python
>>> import cv2
>>> import supervision as sv
>>> from ultralytics import YOLO
import cv2
import supervision as sv
from ultralytics import YOLO
>>> image = cv2.imread(...)
>>> model = YOLO('yolov8s.pt')
>>> result = model(image)[0]
>>> detections = sv.Detections.from_ultralytics(result)
image = cv2.imread()
model = YOLO('yolov8s.pt')
result = model(image)[0]
detections = sv.Detections.from_ultralytics(result)
```
"""
@@ -209,14 +209,14 @@ class Detections:
Example:
```python
>>> import cv2
>>> from super_gradients.training import models
>>> import supervision as sv
import cv2
from super_gradients.training import models
import supervision as sv
>>> image = cv2.imread(SOURCE_IMAGE_PATH)
>>> model = models.get('yolo_nas_l', pretrained_weights="coco")
>>> result = list(model.predict(image, conf=0.35))[0]
>>> detections = sv.Detections.from_yolo_nas(result)
image = cv2.imread(SOURCE_IMAGE_PATH)
model = models.get('yolo_nas_l', pretrained_weights="coco")
result = list(model.predict(image, conf=0.35))[0]
detections = sv.Detections.from_yolo_nas(result)
```
"""
if np.asarray(yolo_nas_results.prediction.bboxes_xyxy).shape[0] == 0:
@@ -246,20 +246,16 @@ class Detections:
Example:
```python
>>> import tensorflow as tf
>>> import tensorflow_hub as hub
>>> import numpy as np
>>> import cv2
import tensorflow as tf
import tensorflow_hub as hub
import numpy as np
import cv2
>>> module_handle = "https://tfhub.dev/tensorflow/centernet/hourglass_512x512_kpts/1"
>>> model = hub.load(module_handle)
>>> img = np.array(cv2.imread(SOURCE_IMAGE_PATH))
>>> result = model(img)
>>> detections = sv.Detections.from_tensorflow(result)
module_handle = "https://tfhub.dev/tensorflow/centernet/hourglass_512x512_kpts/1"
model = hub.load(module_handle)
img = np.array(cv2.imread(SOURCE_IMAGE_PATH))
result = model(img)
detections = sv.Detections.from_tensorflow(result)
```
""" # noqa: E501 // docs
@@ -289,15 +285,15 @@ class Detections:
Example:
```python
>>> import supervision as sv
>>> from deepsparse import Pipeline
import supervision as sv
from deepsparse import Pipeline
>>> yolo_pipeline = Pipeline.create(
... task="yolo",
... model_path = "zoo:cv/detection/yolov5-l/pytorch/ultralytics/coco/pruned80_quant-none"
... )
>>> result = yolo_pipeline(<SOURCE IMAGE PATH>)
>>> detections = sv.Detections.from_deepsparse(result)
yolo_pipeline = Pipeline.create(
task="yolo",
model_path = "zoo:cv/detection/yolov5-l/pytorch/ultralytics/coco/pruned80_quant-none"
)
result = yolo_pipeline(<SOURCE IMAGE PATH>)
detections = sv.Detections.from_deepsparse(result)
```
""" # noqa: E501 // docs
@@ -326,14 +322,14 @@ class Detections:
Example:
```python
>>> import cv2
>>> import supervision as sv
>>> from mmdet.apis import DetInferencer
import cv2
import supervision as sv
from mmdet.apis import DetInferencer
>>> inferencer = DetInferencer(model_name, checkpoint, device)
>>> mmdet_result = inferencer(SOURCE_IMAGE_PATH, out_dir='./output',
... return_datasamples=True)["predictions"][0]
>>> detections = sv.Detections.from_mmdetection(mmdet_result)
inferencer = DetInferencer(model_name, checkpoint, device)
mmdet_result = inferencer(SOURCE_IMAGE_PATH, out_dir='./output',
return_datasamples=True)["predictions"][0]
detections = sv.Detections.from_mmdetection(mmdet_result)
```
"""
@@ -375,18 +371,18 @@ class Detections:
Example:
```python
>>> import cv2
>>> from detectron2.engine import DefaultPredictor
>>> from detectron2.config import get_cfg
>>> import supervision as sv
import cv2
from detectron2.engine import DefaultPredictor
from detectron2.config import get_cfg
import supervision as sv
>>> image = cv2.imread(SOURCE_IMAGE_PATH)
>>> cfg = get_cfg()
>>> cfg.merge_from_file("path/to/config.yaml")
>>> cfg.MODEL.WEIGHTS = "path/to/model_weights.pth"
>>> predictor = DefaultPredictor(cfg)
>>> result = predictor(image)
>>> detections = sv.Detections.from_detectron2(result)
image = cv2.imread(SOURCE_IMAGE_PATH)
cfg = get_cfg()
cfg.merge_from_file("path/to/config.yaml")
cfg.MODEL.WEIGHTS = "path/to/model_weights.pth"
predictor = DefaultPredictor(cfg)
result = predictor(image)
detections = sv.Detections.from_detectron2(result)
```
"""
@@ -423,14 +419,14 @@ class Detections:
Example:
```python
>>> import cv2
>>> import supervision as sv
>>> from inference.models.utils import get_roboflow_model
import cv2
import supervision as sv
from inference.models.utils import get_roboflow_model
>>> image = cv2.imread(...)
>>> model = get_roboflow_model(model_id="yolov8s-640")
>>> result = model.infer(image)[0]
>>> detections = sv.Detections.from_inference(result)
image = cv2.imread()
model = get_roboflow_model(model_id="yolov8s-640")
result = model.infer(image)[0]
detections = sv.Detections.from_inference(result)
```
"""
with suppress(AttributeError):
@@ -472,14 +468,14 @@ class Detections:
Example:
```python
>>> import cv2
>>> import supervision as sv
>>> from inference.models.utils import get_roboflow_model
import cv2
import supervision as sv
from inference.models.utils import get_roboflow_model
>>> image = cv2.imread(...)
>>> model = get_roboflow_model(model_id="yolov8s-640")
>>> result = model.infer(image)[0]
>>> detections = sv.Detections.from_roboflow(result)
image = cv2.imread()
model = get_roboflow_model(model_id="yolov8s-640")
result = model.infer(image)[0]
detections = sv.Detections.from_roboflow(result)
```
"""
return cls.from_inference(roboflow_result)
@@ -499,17 +495,17 @@ class Detections:
Example:
```python
>>> import supervision as sv
>>> from segment_anything import (
... sam_model_registry,
... SamAutomaticMaskGenerator
... )
import supervision as sv
from segment_anything import (
sam_model_registry,
SamAutomaticMaskGenerator
)
>>> sam_model_reg = sam_model_registry[MODEL_TYPE]
>>> sam = sam_model_reg(checkpoint=CHECKPOINT_PATH).to(device=DEVICE)
>>> mask_generator = SamAutomaticMaskGenerator(sam)
>>> sam_result = mask_generator.generate(IMAGE)
>>> detections = sv.Detections.from_sam(sam_result=sam_result)
sam_model_reg = sam_model_registry[MODEL_TYPE]
sam = sam_model_reg(checkpoint=CHECKPOINT_PATH).to(device=DEVICE)
mask_generator = SamAutomaticMaskGenerator(sam)
sam_result = mask_generator.generate(IMAGE)
detections = sv.Detections.from_sam(sam_result=sam_result)
```
"""
@@ -546,25 +542,25 @@ class Detections:
Example:
```python
>>> import requests
>>> import supervision as sv
import requests
import supervision as sv
>>> image = open(input, "rb").read()
image = open(input, "rb").read()
>>> endpoint = "https://.cognitiveservices.azure.com/"
>>> subscription_key = "..."
endpoint = "https://.cognitiveservices.azure.com/"
subscription_key = ""
>>> headers = {
... "Content-Type": "application/octet-stream",
... "Ocp-Apim-Subscription-Key": subscription_key
... }
headers = {
"Content-Type": "application/octet-stream",
"Ocp-Apim-Subscription-Key": subscription_key
}
>>> response = requests.post(endpoint,
... headers=self.headers,
... data=image
... ).json()
response = requests.post(endpoint,
headers=self.headers,
data=image
).json()
>>> detections = sv.Detections.from_azure_analyze_image(response)
detections = sv.Detections.from_azure_analyze_image(response)
```
"""
if "error" in azure_result:
@@ -628,21 +624,21 @@ class Detections:
Example:
```python
>>> import supervision as sv
>>> import paddle
>>> from ppdet.engine import Trainer
>>> from ppdet.core.workspace import load_config
import supervision as sv
import paddle
from ppdet.engine import Trainer
from ppdet.core.workspace import load_config
>>> weights = (...)
>>> config = (...)
weights = ()
config = ()
>>> cfg = load_config(config)
>>> trainer = Trainer(cfg, mode='test')
>>> trainer.load_weights(weights)
cfg = load_config(config)
trainer = Trainer(cfg, mode='test')
trainer.load_weights(weights)
>>> paddledet_result = trainer.predict([images])[0]
paddledet_result = trainer.predict([images])[0]
>>> detections = sv.Detections.from_paddledet(paddledet_result)
detections = sv.Detections.from_paddledet(paddledet_result)
```
"""
@@ -666,9 +662,9 @@ class Detections:
Example:
```python
>>> from supervision import Detections
from supervision import Detections
>>> empty_detections = Detections.empty()
empty_detections = Detections.empty()
```
"""
return cls(
@@ -700,29 +696,29 @@ class Detections:
import numpy as np
import supervision as sv
>>> detections_1 = sv.Detections(
... xyxy=np.array([[15, 15, 100, 100], [200, 200, 300, 300]]),
... class_id=np.array([1, 2]),
... data={'feature_vector': np.array([0.1, 0.2)])}
... )
detections_1 = sv.Detections(
xyxy=np.array([[15, 15, 100, 100], [200, 200, 300, 300]]),
class_id=np.array([1, 2]),
data={'feature_vector': np.array([0.1, 0.2)])}
)
>>> detections_2 = sv.Detections(
... xyxy=np.array([[30, 30, 120, 120]]),
... class_id=np.array([1]),
... data={'feature_vector': [np.array([0.3])]}
... )
detections_2 = sv.Detections(
xyxy=np.array([[30, 30, 120, 120]]),
class_id=np.array([1]),
data={'feature_vector': [np.array([0.3])]}
)
>>> merged_detections = Detections.merge([detections_1, detections_2])
merged_detections = Detections.merge([detections_1, detections_2])
>>> merged_detections.xyxy
merged_detections.xyxy
array([[ 15, 15, 100, 100],
[200, 200, 300, 300],
[ 30, 30, 120, 120]])
>>> merged_detections.class_id
merged_detections.class_id
array([1, 2, 1])
>>> merged_detections.data['feature_vector']
merged_detections.data['feature_vector']
array([0.1, 0.2, 0.3])
```
"""
@@ -855,17 +851,17 @@ class Detections:
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> detections = sv.Detections(...)
detections = sv.Detections()
>>> first_detection = detections[0]
>>> first_10_detections = detections[0:10]
>>> some_detections = detections[[0, 2, 4]]
>>> class_0_detections = detections[detections.class_id == 0]
>>> high_confidence_detections = detections[detections.confidence > 0.5]
first_detection = detections[0]
first_10_detections = detections[0:10]
some_detections = detections[[0, 2, 4]]
class_0_detections = detections[detections.class_id == 0]
high_confidence_detections = detections[detections.confidence > 0.5]
>>> feature_vector = detections['feature_vector']
feature_vector = detections['feature_vector']
```
"""
if isinstance(index, str):
@@ -891,22 +887,22 @@ class Detections:
Example:
```python
>>> import cv2
>>> from ultralytics import YOLO
>>> import supervision as sv
import cv2
from ultralytics import YOLO
import supervision as sv
>>> model = YOLO('yolov8s.pt')
model = YOLO('yolov8s.pt')
>>> image = cv2.imread(SOURCE_IMAGE_PATH)
image = cv2.imread(SOURCE_IMAGE_PATH)
>>> result = model(image)[0]
>>> detections = sv.Detections.from_ultralytics(result)
result = model(image)[0]
detections = sv.Detections.from_ultralytics(result)
>>> detections['names'] = [
... model.model.names[class_id]
... for class_id
... in detections.class_id
... ]
detections['names'] = [
model.model.names[class_id]
for class_id
in detections.class_id
]
```
"""
if not isinstance(value, (np.ndarray, list)):
@@ -926,7 +922,7 @@ class Detections:
Returns:
np.ndarray: An array of floats containing the area of each detection
in the format of `(area_1, area_2, ..., area_n)`,
in the format of `(area_1, area_2, , area_n)`,
where n is the number of detections.
"""
if self.mask is not None:
@@ -941,7 +937,7 @@ class Detections:
Returns:
np.ndarray: An array of floats containing the area of each bounding
box in the format of `(area_1, area_2, ..., area_n)`,
box in the format of `(area_1, area_2, , area_n)`,
where n is the number of detections.
"""
return (self.xyxy[:, 3] - self.xyxy[:, 1]) * (self.xyxy[:, 2] - self.xyxy[:, 0])
+1 -1
View File
@@ -15,7 +15,7 @@ class LineZone:
!!! warning
LineZone utilizes the `tracker_id`. Read
LineZone uses the `tracker_id`. Read
[here](https://supervision.roboflow.com/trackers/) to learn how to plug
tracking into your inference pipeline.
+10 -10
View File
@@ -77,20 +77,20 @@ class InferenceSlicer:
Example:
```python
>>> import cv2
>>> import supervision as sv
>>> from ultralytics import YOLO
import cv2
import supervision as sv
from ultralytics import YOLO
>>> image = cv2.imread(SOURCE_IMAGE_PATH)
>>> model = YOLO(...)
image = cv2.imread(SOURCE_IMAGE_PATH)
model = YOLO(...)
>>> def callback(image_slice: np.ndarray) -> sv.Detections:
... result = model(image_slice)[0]
... return sv.Detections.from_ultralytics(result)
def callback(image_slice: np.ndarray) -> sv.Detections:
result = model(image_slice)[0]
return sv.Detections.from_ultralytics(result)
>>> slicer = sv.InferenceSlicer(callback = callback)
slicer = sv.InferenceSlicer(callback = callback)
>>> detections = slicer(image)
detections = slicer(image)
```
"""
detections_list = []
+118
View File
@@ -0,0 +1,118 @@
from collections import defaultdict, deque
from copy import deepcopy
from typing import Optional
import numpy as np
from supervision.detection.core import Detections
class DetectionsSmoother:
"""
A utility class for smoothing detections over multiple frames in video tracking.
It maintains a history of detections for each track and provides smoothed
predictions based on these histories.
<video controls>
<source
src="https://media.roboflow.com/supervision-detection-smoothing.mp4"
type="video/mp4">
</video>
!!! warning
- `DetectionsSmoother` requires the `tracker_id` for each detection. Refer to
[Roboflow Trackers](https://supervision.roboflow.com/trackers/) for
information on integrating tracking into your inference pipeline.
- This class is not compatible with segmentation models.
Example:
```python
import supervision as sv
from ultralytics import YOLO
video_info = sv.VideoInfo.from_video_path(video_path=<SOURCE_FILE_PATH>)
frame_generator = sv.get_video_frames_generator(source_path=<SOURCE_FILE_PATH>)
model = YOLO(<MODEL_PATH>)
tracker = sv.ByteTrack(frame_rate=video_info.fps)
smoother = sv.DetectionsSmoother()
annotator = sv.BoundingBoxAnnotator()
with sv.VideoSink(<TARGET_FILE_PATH>, video_info=video_info) as sink:
for frame in frame_generator:
result = model(frame)[0]
detections = sv.Detections.from_ultralytics(result)
detections = tracker.update_with_detections(detections)
detections = smoother.update_with_detections(detections)
annotated_frame = bounding_box_annotator.annotate(frame.copy(), detections)
sink.write_frame(annotated_frame)
```
""" # noqa: E501 // docs
def __init__(self, length: int = 5) -> None:
"""
Args:
length (int): The maximum number of frames to consider for smoothing
detections. Defaults to 5.
"""
self.tracks = defaultdict(lambda: deque(maxlen=length))
def update_with_detections(self, detections: Detections) -> Detections:
"""
Updates the smoother with a new set of detections from a frame.
Args:
detections (Detections): The detections to add to the smoother.
"""
if detections.tracker_id is None:
print(
"Smoothing skipped. DetectionsSmoother requires tracker_id. Refer to "
"https://supervision.roboflow.com/trackers for more information."
)
return detections
for detection_idx in range(len(detections)):
tracker_id = detections.tracker_id[detection_idx]
if tracker_id is None:
continue
self.tracks[tracker_id].append(detections[detection_idx])
for track_id in self.tracks.keys():
if track_id not in detections.tracker_id:
self.tracks[track_id].append(None)
for track_id in list(self.tracks.keys()):
if all([d is None for d in self.tracks[track_id]]):
del self.tracks[track_id]
return self.get_smoothed_detections()
def get_track(self, track_id: int) -> Optional[Detections]:
track = self.tracks.get(track_id, None)
if track is None:
return None
track = [d for d in track if d is not None]
if len(track) == 0:
return None
ret = deepcopy(track[0])
ret.xyxy = np.mean([d.xyxy for d in track], axis=0)
ret.confidence = np.mean([d.confidence for d in track], axis=0)
return ret
def get_smoothed_detections(self) -> Detections:
tracked_detections = []
for track_id in self.tracks:
track = self.get_track(track_id)
if track is not None:
tracked_detections.append(track)
return Detections.merge(tracked_detections)
+20 -18
View File
@@ -415,16 +415,17 @@ def move_boxes(xyxy: np.ndarray, offset: np.ndarray) -> np.ndarray:
Example:
```python
>>> import numpy as np
>>> import supervision as sv
import numpy as np
import supervision as sv
>>> boxes = np.array([[10, 10, 20, 20], [30, 30, 40, 40]])
>>> offset = np.array([5, 5])
>>> sv.move_boxes(boxes, offset)
... array([
... [15, 15, 25, 25],
... [35, 35, 45, 45]
... ])
boxes = np.array([[10, 10, 20, 20], [30, 30, 40, 40]])
offset = np.array([5, 5])
moved_box = sv.move_boxes(boxes, offset)
print(moved_box)
# np.array([
# [15, 15, 25, 25],
# [35, 35, 45, 45]
# ])
```
"""
return xyxy + np.hstack([offset, offset])
@@ -446,16 +447,17 @@ def scale_boxes(xyxy: np.ndarray, factor: float) -> np.ndarray:
Example:
```python
>>> import numpy as np
>>> import supervision as sv
import numpy as np
import supervision as sv
>>> boxes = np.array([[10, 10, 20, 20], [30, 30, 40, 40]])
>>> factor = 1.5
>>> sv.scale_boxes(boxes, factor)
... array([
... [ 7.5, 7.5, 22.5, 22.5],
... [27.5, 27.5, 42.5, 42.5]
... ])
boxes = np.array([[10, 10, 20, 20], [30, 30, 40, 40]])
factor = 1.5
scaled_bb = sv.scale_boxes(boxes, factor)
print(scaled_bb)
# np.array([
# [ 7.5, 7.5, 22.5, 22.5],
# [27.5, 27.5, 42.5, 42.5]
# ])
```
"""
centers = (xyxy[:, :2] + xyxy[:, 2:]) / 2
+5 -3
View File
@@ -135,9 +135,11 @@ def draw_text(
Examples:
```python
>>> scene = np.zeros((100, 100, 3), dtype=np.uint8)
>>> text_anchor = Point(x=50, y=50)
>>> scene = draw_text(scene=scene, text="Hello, world!",text_anchor=text_anchor)
import numpy as np
scene = np.zeros((100, 100, 3), dtype=np.uint8)
text_anchor = Point(x=50, y=50)
scene = draw_text(scene=scene, text="Hello, world!",text_anchor=text_anchor)
```
"""
text_width, text_height = cv2.getTextSize(
+4 -3
View File
@@ -22,10 +22,11 @@ def get_polygon_center(polygon: np.ndarray) -> Point:
Examples:
```python
>>> from supervision.geometry.utils import get_polygon_center
from supervision.geometry.utils import get_polygon_center
import numpy as np
>>> vertices = np.array([[0, 0], [0, 1], [1, 1], [1, 0]])
>>> get_center(vertices)
vertices = np.array([[0, 0], [0, 1], [1, 1], [1, 0]])
get_center(vertices)
Point(x=0.5, y=0.5)
```
"""
+135 -133
View File
@@ -116,31 +116,31 @@ class ConfusionMatrix:
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> targets = [
... sv.Detections(...),
... sv.Detections(...)
... ]
targets = [
sv.Detections(...),
sv.Detections(...)
]
>>> predictions = [
... sv.Detections(...),
... sv.Detections(...)
... ]
predictions = [
sv.Detections(...),
sv.Detections(...)
]
>>> confusion_matrix = sv.ConfusionMatrix.from_detections(
... predictions=predictions,
... targets=target,
... classes=['person', ...]
... )
confusion_matrix = sv.ConfusionMatrix.from_detections(
predictions=predictions,
targets=target,
classes=['person', ...]
)
>>> confusion_matrix.matrix
array([
[0., 0., 0., 0.],
[0., 1., 0., 1.],
[0., 1., 1., 0.],
[1., 1., 0., 0.]
])
print(confusion_matrix.matrix)
# np.array([
# [0., 0., 0., 0.],
# [0., 1., 0., 1.],
# [0., 1., 1., 0.],
# [1., 1., 0., 0.]
# ])
```
"""
@@ -191,46 +191,47 @@ class ConfusionMatrix:
Example:
```python
>>> import supervision as sv
import supervision as sv
import numpy as np
>>> targets = (
... [
... array(
... [
... [0.0, 0.0, 3.0, 3.0, 1],
... [2.0, 2.0, 5.0, 5.0, 1],
... [6.0, 1.0, 8.0, 3.0, 2],
... ]
... ),
... array([1.0, 1.0, 2.0, 2.0, 2]),
... ]
... )
targets = (
[
np.array(
[
[0.0, 0.0, 3.0, 3.0, 1],
[2.0, 2.0, 5.0, 5.0, 1],
[6.0, 1.0, 8.0, 3.0, 2],
]
),
np.array([1.0, 1.0, 2.0, 2.0, 2]),
]
)
>>> predictions = [
... array(
... [
... [0.0, 0.0, 3.0, 3.0, 1, 0.9],
... [0.1, 0.1, 3.0, 3.0, 0, 0.9],
... [6.0, 1.0, 8.0, 3.0, 1, 0.8],
... [1.0, 6.0, 2.0, 7.0, 1, 0.8],
... ]
... ),
... array([[1.0, 1.0, 2.0, 2.0, 2, 0.8]])
... ]
predictions = [
np.array(
[
[0.0, 0.0, 3.0, 3.0, 1, 0.9],
[0.1, 0.1, 3.0, 3.0, 0, 0.9],
[6.0, 1.0, 8.0, 3.0, 1, 0.8],
[1.0, 6.0, 2.0, 7.0, 1, 0.8],
]
),
np.array([[1.0, 1.0, 2.0, 2.0, 2, 0.8]])
]
>>> confusion_matrix = sv.ConfusionMatrix.from_tensors(
... predictions=predictions,
... targets=targets,
... classes=['person', ...]
... )
confusion_matrix = sv.ConfusionMatrix.from_tensors(
predictions=predictions,
targets=targets,
classes=['person', ...]
)
>>> confusion_matrix.matrix
array([
[0., 0., 0., 0.],
[0., 1., 0., 1.],
[0., 1., 1., 0.],
[1., 1., 0., 0.]
])
print(confusion_matrix.matrix)
# np.array([
# [0., 0., 0., 0.],
# [0., 1., 0., 1.],
# [0., 1., 1., 0.],
# [1., 1., 0., 0.]
# ])
```
"""
validate_input_tensors(predictions, targets)
@@ -365,28 +366,28 @@ class ConfusionMatrix:
Example:
```python
>>> import supervision as sv
>>> from ultralytics import YOLO
import supervision as sv
from ultralytics import YOLO
>>> dataset = sv.DetectionDataset.from_yolo(...)
dataset = sv.DetectionDataset.from_yolo(...)
>>> model = YOLO(...)
>>> def callback(image: np.ndarray) -> sv.Detections:
... result = model(image)[0]
... return sv.Detections.from_ultralytics(result)
model = YOLO(...)
def callback(image: np.ndarray) -> sv.Detections:
result = model(image)[0]
return sv.Detections.from_ultralytics(result)
>>> confusion_matrix = sv.ConfusionMatrix.benchmark(
... dataset = dataset,
... callback = callback
... )
confusion_matrix = sv.ConfusionMatrix.benchmark(
dataset = dataset,
callback = callback
)
>>> confusion_matrix.matrix
array([
[0., 0., 0., 0.],
[0., 1., 0., 1.],
[0., 1., 1., 0.],
[1., 1., 0., 0.]
])
print(confusion_matrix.matrix)
# np.array([
# [0., 0., 0., 0.],
# [0., 1., 0., 1.],
# [0., 1., 1., 0.],
# [1., 1., 0., 0.]
# ])
```
"""
predictions, targets = [], []
@@ -532,25 +533,25 @@ class MeanAveragePrecision:
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> targets = [
... sv.Detections(...),
... sv.Detections(...)
... ]
targets = [
sv.Detections(...),
sv.Detections(...)
]
>>> predictions = [
... sv.Detections(...),
... sv.Detections(...)
... ]
predictions = [
sv.Detections(...),
sv.Detections(...)
]
>>> mean_average_precision = sv.MeanAveragePrecision.from_detections(
... predictions=predictions,
... targets=target,
... )
mean_average_precision = sv.MeanAveragePrecision.from_detections(
predictions=predictions,
targets=target,
)
>>> mean_average_precison.map50_95
0.2899
print(mean_average_precison.map50_95)
# 0.2899
```
"""
prediction_tensors = []
@@ -583,23 +584,23 @@ class MeanAveragePrecision:
Example:
```python
>>> import supervision as sv
>>> from ultralytics import YOLO
import supervision as sv
from ultralytics import YOLO
>>> dataset = sv.DetectionDataset.from_yolo(...)
dataset = sv.DetectionDataset.from_yolo(...)
>>> model = YOLO(...)
>>> def callback(image: np.ndarray) -> sv.Detections:
... result = model(image)[0]
... return sv.Detections.from_ultralytics(result)
model = YOLO(...)
def callback(image: np.ndarray) -> sv.Detections:
result = model(image)[0]
return sv.Detections.from_ultralytics(result)
>>> mean_average_precision = sv.MeanAveragePrecision.benchmark(
... dataset = dataset,
... callback = callback
... )
mean_average_precision = sv.MeanAveragePrecision.benchmark(
dataset = dataset,
callback = callback
)
>>> mean_average_precision.map50_95
0.433
print(mean_average_precision.map50_95)
# 0.433
```
"""
predictions, targets = [], []
@@ -637,40 +638,41 @@ class MeanAveragePrecision:
Example:
```python
>>> import supervision as sv
import supervision as sv
import numpy as np
>>> targets = (
... [
... array(
... [
... [0.0, 0.0, 3.0, 3.0, 1],
... [2.0, 2.0, 5.0, 5.0, 1],
... [6.0, 1.0, 8.0, 3.0, 2],
... ]
... ),
... array([1.0, 1.0, 2.0, 2.0, 2]),
... ]
... )
targets = (
[
np.array(
[
[0.0, 0.0, 3.0, 3.0, 1],
[2.0, 2.0, 5.0, 5.0, 1],
[6.0, 1.0, 8.0, 3.0, 2],
]
),
np.array([[1.0, 1.0, 2.0, 2.0, 2]]),
]
)
>>> predictions = [
... array(
... [
... [0.0, 0.0, 3.0, 3.0, 1, 0.9],
... [0.1, 0.1, 3.0, 3.0, 0, 0.9],
... [6.0, 1.0, 8.0, 3.0, 1, 0.8],
... [1.0, 6.0, 2.0, 7.0, 1, 0.8],
... ]
... ),
... array([[1.0, 1.0, 2.0, 2.0, 2, 0.8]])
... ]
predictions = [
np.array(
[
[0.0, 0.0, 3.0, 3.0, 1, 0.9],
[0.1, 0.1, 3.0, 3.0, 0, 0.9],
[6.0, 1.0, 8.0, 3.0, 1, 0.8],
[1.0, 6.0, 2.0, 7.0, 1, 0.8],
]
),
np.array([[1.0, 1.0, 2.0, 2.0, 2, 0.8]])
]
>>> mean_average_precison = sv.MeanAveragePrecision.from_tensors(
... predictions=predictions,
... targets=targets,
... )
mean_average_precison = sv.MeanAveragePrecision.from_tensors(
predictions=predictions,
targets=targets,
)
>>> mean_average_precison.map50_95
0.2899
print(mean_average_precison.map50_95)
# 0.6649
```
"""
validate_input_tensors(predictions, targets)
+20 -21
View File
@@ -205,30 +205,29 @@ class ByteTrack:
Detection: The updated detection results that now include tracking IDs.
Example:
```python
>>> import supervision as sv
>>> from ultralytics import YOLO
import supervision as sv
from ultralytics import YOLO
>>> model = YOLO(...)
>>> byte_tracker = sv.ByteTrack()
>>> annotator = sv.BoxAnnotator()
model = YOLO(...)
byte_tracker = sv.ByteTrack()
annotator = sv.BoxAnnotator()
>>> def callback(frame: np.ndarray, index: int) -> np.ndarray:
... results = model(frame)[0]
... detections = sv.Detections.from_ultralytics(results)
... detections = byte_tracker.update_with_detections(detections)
... labels = [
... f"#{tracker_id} {model.model.names[class_id]} {confidence:0.2f}"
... for _, _, confidence, class_id, tracker_id
... in detections
... ]
... return annotator.annotate(scene=frame.copy(),
... detections=detections, labels=labels)
def callback(frame: np.ndarray, index: int) -> np.ndarray:
results = model(frame)[0]
detections = sv.Detections.from_ultralytics(results)
detections = byte_tracker.update_with_detections(detections)
labels = [
f"#{tracker_id} {model.model.names[class_id]} {confidence:0.2f}"
for _, _, confidence, class_id, tracker_id in detections
]
return annotator.annotate(scene=frame.copy(),
detections=detections, labels=labels)
>>> sv.process_video(
... source_path='...',
... target_path='...',
... callback=callback
... )
sv.process_video(
source_path='...',
target_path='...',
callback=callback
)
```
"""
+6 -6
View File
@@ -34,14 +34,14 @@ def list_files_with_extensions(
Examples:
```python
>>> import supervision as sv
import supervision as sv
>>> # List all files in the directory
>>> files = sv.list_files_with_extensions(directory='my_directory')
# List all files in the directory
files = sv.list_files_with_extensions(directory='my_directory')
>>> # List only files with '.txt' and '.md' extensions
>>> files = sv.list_files_with_extensions(
... directory='my_directory', extensions=['txt', 'md'])
# List only files with '.txt' and '.md' extensions
files = sv.list_files_with_extensions(
directory='my_directory', extensions=['txt', 'md'])
```
"""
+12 -12
View File
@@ -20,13 +20,13 @@ def crop_image(image: np.ndarray, xyxy: np.ndarray) -> np.ndarray:
Examples:
```python
>>> import supervision as sv
import supervision as sv
>>> detection = sv.Detections(...)
>>> with sv.ImageSink(target_dir_path='target/directory/path') as sink:
... for xyxy in detection.xyxy:
... cropped_image = sv.crop_image(image=image, xyxy=xyxy)
... sink.save_image(image=image)
detection = sv.Detections(...)
with sv.ImageSink(target_dir_path='target/directory/path') as sink:
for xyxy in detection.xyxy:
cropped_image = sv.crop_image(image=image, xyxy=xyxy)
sink.save_image(image=image)
```
"""
@@ -55,13 +55,13 @@ class ImageSink:
Examples:
```python
>>> import supervision as sv
import supervision as sv
>>> with sv.ImageSink(target_dir_path='target/directory/path',
... overwrite=True) as sink:
... for image in sv.get_video_frames_generator(
... source_path='source_video.mp4', stride=2):
... sink.save_image(image=image)
with sv.ImageSink(target_dir_path='target/directory/path',
overwrite=True) as sink:
for image in sv.get_video_frames_generator(
source_path='source_video.mp4', stride=2):
sink.save_image(image=image)
```
"""
+12 -12
View File
@@ -18,13 +18,13 @@ def plot_image(
Examples:
```python
>>> import cv2
>>> import supervision as sv
import cv2
import supervision as sv
>>> image = cv2.imread("path/to/image.jpg")
image = cv2.imread("path/to/image.jpg")
%matplotlib inline
>>> sv.plot_image(image=image, size=(16, 16))
sv.plot_image(image=image, size=(16, 16))
```
"""
plt.figure(figsize=size)
@@ -63,18 +63,18 @@ def plot_images_grid(
Examples:
```python
>>> import cv2
>>> import supervision as sv
import cv2
import supervision as sv
>>> image1 = cv2.imread("path/to/image1.jpg")
>>> image2 = cv2.imread("path/to/image2.jpg")
>>> image3 = cv2.imread("path/to/image3.jpg")
image1 = cv2.imread("path/to/image1.jpg")
image2 = cv2.imread("path/to/image2.jpg")
image3 = cv2.imread("path/to/image3.jpg")
>>> images = [image1, image2, image3]
>>> titles = ["Image 1", "Image 2", "Image 3"]
images = [image1, image2, image3]
titles = ["Image 1", "Image 2", "Image 3"]
%matplotlib inline
>>> plot_images_grid(images, grid_size=(2, 2), titles=titles, size=(16, 16))
plot_images_grid(images, grid_size=(2, 2), titles=titles, size=(16, 16))
```
"""
nrows, ncols = grid_size
+30 -30
View File
@@ -24,15 +24,15 @@ class VideoInfo:
Examples:
```python
>>> import supervision as sv
import supervision as sv
>>> video_info = sv.VideoInfo.from_video_path(video_path='video.mp4')
video_info = sv.VideoInfo.from_video_path(video_path='video.mp4')
>>> video_info
VideoInfo(width=3840, height=2160, fps=25, total_frames=538)
video_info
# VideoInfo(width=3840, height=2160, fps=25, total_frames=538)
>>> video_info.resolution_wh
(3840, 2160)
video_info.resolution_wh
# (3840, 2160)
```
"""
@@ -71,14 +71,14 @@ class VideoSink:
Example:
```python
>>> import supervision as sv
import supervision as sv
>>> video_info = sv.VideoInfo.from_video_path('source.mp4')
>>> frames_generator = sv.get_video_frames_generator('source.mp4')
video_info = sv.VideoInfo.from_video_path('source.mp4')
frames_generator = sv.get_video_frames_generator('source.mp4')
>>> with sv.VideoSink(target_path='target.mp4', video_info=video_info) as sink:
... for frame in frames_generator:
... sink.write_frame(frame=frame)
with sv.VideoSink(target_path='target.mp4', video_info=video_info) as sink:
for frame in frames_generator:
sink.write_frame(frame=frame)
```
"""
@@ -143,10 +143,10 @@ def get_video_frames_generator(
Examples:
```python
>>> import supervision as sv
import supervision as sv
>>> for frame in sv.get_video_frames_generator(source_path='source_video.mp4'):
... ...
for frame in sv.get_video_frames_generator(source_path='source_video.mp4'):
...
```
"""
video, start, end = _validate_and_setup_video(source_path, start, end)
@@ -183,16 +183,16 @@ def process_video(
Examples:
```python
>>> import supervision as sv
import supervision as sv
>>> def callback(scene: np.ndarray, index: int) -> np.ndarray:
... ...
def callback(scene: np.ndarray, index: int) -> np.ndarray:
...
>>> process_video(
... source_path='...',
... target_path='...',
... callback=callback
... )
process_video(
source_path='...',
target_path='...',
callback=callback
)
```
"""
source_video_info = VideoInfo.from_video_path(video_path=source_path)
@@ -217,15 +217,15 @@ class FPSMonitor:
Examples:
```python
>>> import supervision as sv
import supervision as sv
>>> frames_generator = sv.get_video_frames_generator('source.mp4')
>>> fps_monitor = sv.FPSMonitor()
frames_generator = sv.get_video_frames_generator('source.mp4')
fps_monitor = sv.FPSMonitor()
>>> for frame in frames_generator:
... # your processing code here
... fps_monitor.tick()
... fps = fps_monitor()
for frame in frames_generator:
# your processing code here
fps_monitor.tick()
fps = fps_monitor()
```
"""
self.all_timestamps = deque(maxlen=sample_size)