ultralytics 8.3.4__tar.gz → 8.3.5__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of ultralytics might be problematic. Click here for more details.
- {ultralytics-8.3.4 → ultralytics-8.3.5}/PKG-INFO +1 -1
- {ultralytics-8.3.4 → ultralytics-8.3.5}/tests/test_solutions.py +2 -2
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/__init__.py +1 -1
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/default.yaml +1 -1
- ultralytics-8.3.5/ultralytics/cfg/solutions/default.yaml +12 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/base.py +37 -5
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/utils.py +3 -3
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/engine/validator.py +2 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/solutions/heatmap.py +2 -12
- ultralytics-8.3.5/ultralytics/solutions/object_counter.py +129 -0
- ultralytics-8.3.5/ultralytics/solutions/solutions.py +88 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/__init__.py +8 -8
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics.egg-info/PKG-INFO +1 -1
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics.egg-info/SOURCES.txt +2 -0
- ultralytics-8.3.4/ultralytics/solutions/object_counter.py +0 -243
- {ultralytics-8.3.4 → ultralytics-8.3.5}/LICENSE +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/README.md +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/pyproject.toml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/setup.cfg +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/tests/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/tests/conftest.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/tests/test_cli.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/tests/test_cuda.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/tests/test_engine.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/tests/test_explorer.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/tests/test_exports.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/tests/test_integrations.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/tests/test_python.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/assets/bus.jpg +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/assets/zidane.jpg +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/Argoverse.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/DOTAv1.5.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/DOTAv1.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/GlobalWheat2020.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/ImageNet.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/Objects365.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/SKU-110K.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/VOC.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/VisDrone.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/african-wildlife.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/brain-tumor.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/carparts-seg.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/coco-pose.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/coco.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/coco128-seg.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/coco128.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/coco8-pose.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/coco8-seg.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/coco8.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/crack-seg.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/dota8.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/hand-keypoints.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/lvis.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/open-images-v7.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/package-seg.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/signature.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/tiger-pose.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/datasets/xView.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/11/yolo11-cls.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/11/yolo11-obb.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/11/yolo11-pose.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/11/yolo11-seg.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/11/yolo11.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/rt-detr/rtdetr-l.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/rt-detr/rtdetr-resnet101.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/rt-detr/rtdetr-resnet50.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/rt-detr/rtdetr-x.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v10/yolov10b.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v10/yolov10l.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v10/yolov10m.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v10/yolov10n.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v10/yolov10s.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v10/yolov10x.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v3/yolov3-spp.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v3/yolov3-tiny.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v3/yolov3.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v5/yolov5-p6.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v5/yolov5.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v6/yolov6.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-cls-resnet101.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-cls-resnet50.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-cls.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-ghost-p2.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-ghost-p6.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-ghost.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-obb.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-p2.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-p6.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-pose-p6.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-pose.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-rtdetr.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-seg-p6.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-seg.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-world.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8-worldv2.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v8/yolov8.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v9/yolov9c-seg.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v9/yolov9c.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v9/yolov9e-seg.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v9/yolov9e.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v9/yolov9m.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v9/yolov9s.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/models/v9/yolov9t.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/trackers/botsort.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/cfg/trackers/bytetrack.yaml +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/annotator.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/augment.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/build.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/converter.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/dataset.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/explorer/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/explorer/explorer.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/explorer/gui/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/explorer/gui/dash.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/explorer/utils.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/loaders.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/data/split_dota.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/engine/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/engine/exporter.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/engine/model.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/engine/predictor.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/engine/results.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/engine/trainer.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/engine/tuner.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/hub/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/hub/auth.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/hub/google/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/hub/session.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/hub/utils.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/fastsam/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/fastsam/model.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/fastsam/predict.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/fastsam/utils.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/fastsam/val.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/nas/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/nas/model.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/nas/predict.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/nas/val.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/rtdetr/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/rtdetr/model.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/rtdetr/predict.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/rtdetr/train.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/rtdetr/val.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/amg.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/build.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/model.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/modules/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/modules/blocks.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/modules/decoders.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/modules/encoders.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/modules/memory_attention.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/modules/sam.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/modules/tiny_encoder.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/modules/transformer.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/modules/utils.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/sam/predict.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/utils/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/utils/loss.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/utils/ops.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/classify/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/classify/predict.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/classify/train.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/classify/val.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/detect/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/detect/predict.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/detect/train.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/detect/val.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/model.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/obb/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/obb/predict.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/obb/train.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/obb/val.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/pose/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/pose/predict.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/pose/train.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/pose/val.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/segment/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/segment/predict.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/segment/train.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/segment/val.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/world/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/world/train.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/models/yolo/world/train_world.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/nn/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/nn/autobackend.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/nn/modules/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/nn/modules/activation.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/nn/modules/block.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/nn/modules/conv.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/nn/modules/head.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/nn/modules/transformer.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/nn/modules/utils.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/nn/tasks.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/solutions/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/solutions/ai_gym.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/solutions/analytics.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/solutions/distance_calculation.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/solutions/parking_management.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/solutions/queue_management.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/solutions/speed_estimation.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/solutions/streamlit_inference.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/trackers/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/trackers/basetrack.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/trackers/bot_sort.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/trackers/byte_tracker.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/trackers/track.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/trackers/utils/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/trackers/utils/gmc.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/trackers/utils/kalman_filter.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/trackers/utils/matching.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/autobatch.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/benchmarks.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/callbacks/__init__.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/callbacks/base.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/callbacks/clearml.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/callbacks/comet.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/callbacks/dvc.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/callbacks/hub.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/callbacks/mlflow.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/callbacks/neptune.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/callbacks/raytune.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/callbacks/tensorboard.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/callbacks/wb.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/checks.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/dist.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/downloads.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/errors.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/files.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/instance.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/loss.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/metrics.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/ops.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/patches.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/plotting.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/tal.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/torch_utils.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/triton.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics/utils/tuner.py +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics.egg-info/dependency_links.txt +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics.egg-info/entry_points.txt +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics.egg-info/requires.txt +0 -0
- {ultralytics-8.3.4 → ultralytics-8.3.5}/ultralytics.egg-info/top_level.txt +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: ultralytics
|
|
3
|
-
Version: 8.3.
|
|
3
|
+
Version: 8.3.5
|
|
4
4
|
Summary: Ultralytics YOLO for SOTA object detection, multi-object tracking, instance segmentation, pose estimation and image classification.
|
|
5
5
|
Author: Ayush Chaurasia
|
|
6
6
|
Author-email: Glenn Jocher <glenn.jocher@ultralytics.com>, Jing Qiu <jing.qiu@ultralytics.com>
|
|
@@ -19,7 +19,7 @@ def test_major_solutions():
|
|
|
19
19
|
cap = cv2.VideoCapture("solutions_ci_demo.mp4")
|
|
20
20
|
assert cap.isOpened(), "Error reading video file"
|
|
21
21
|
region_points = [(20, 400), (1080, 404), (1080, 360), (20, 360)]
|
|
22
|
-
counter = solutions.ObjectCounter(reg_pts=region_points, names=names, view_img=False)
|
|
22
|
+
# counter = solutions.ObjectCounter(reg_pts=region_points, names=names, view_img=False)
|
|
23
23
|
heatmap = solutions.Heatmap(colormap=cv2.COLORMAP_PARULA, names=names, view_img=False)
|
|
24
24
|
speed = solutions.SpeedEstimator(reg_pts=region_points, names=names, view_img=False)
|
|
25
25
|
queue = solutions.QueueManager(names=names, reg_pts=region_points, view_img=False)
|
|
@@ -29,7 +29,7 @@ def test_major_solutions():
|
|
|
29
29
|
break
|
|
30
30
|
original_im0 = im0.copy()
|
|
31
31
|
tracks = model.track(im0, persist=True, show=False)
|
|
32
|
-
_ = counter.start_counting(original_im0.copy(), tracks)
|
|
32
|
+
# _ = counter.start_counting(original_im0.copy(), tracks)
|
|
33
33
|
_ = heatmap.generate_heatmap(original_im0.copy(), tracks)
|
|
34
34
|
_ = speed.estimate_speed(original_im0.copy(), tracks)
|
|
35
35
|
_ = queue.process_queue(original_im0.copy(), tracks)
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
# Ultralytics YOLO 🚀, AGPL-3.0 license
|
|
2
2
|
# Default training settings and hyperparameters for medium-augmentation COCO training
|
|
3
3
|
|
|
4
|
-
task: detect # (str) YOLO task, i.e. detect, segment, classify, pose
|
|
4
|
+
task: detect # (str) YOLO task, i.e. detect, segment, classify, pose, obb
|
|
5
5
|
mode: train # (str) YOLO mode, i.e. train, val, predict, export, track, benchmark
|
|
6
6
|
|
|
7
7
|
# Train settings -------------------------------------------------------------------------------------------------------
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
# Ultralytics YOLO 🚀, AGPL-3.0 license
|
|
2
|
+
|
|
3
|
+
# Configuration for Ultralytics Solutions
|
|
4
|
+
|
|
5
|
+
model: "yolo11n.pt" # The Ultralytics YOLO11 model to be used (e.g., yolo11n.pt for YOLO11 nano version)
|
|
6
|
+
|
|
7
|
+
region: # Object counting, queue or speed estimation region points
|
|
8
|
+
line_width: 2 # Thickness of the lines used to draw regions on the image/video frames
|
|
9
|
+
show: True # Flag to control whether to display output image or not
|
|
10
|
+
show_in: True # Flag to display objects moving *into* the defined region
|
|
11
|
+
show_out: True # Flag to display objects moving *out of* the defined region
|
|
12
|
+
classes: # To count specific classes
|
|
@@ -90,13 +90,15 @@ class BaseDataset(Dataset):
|
|
|
90
90
|
self.ims, self.im_hw0, self.im_hw = [None] * self.ni, [None] * self.ni, [None] * self.ni
|
|
91
91
|
self.npy_files = [Path(f).with_suffix(".npy") for f in self.im_files]
|
|
92
92
|
self.cache = cache.lower() if isinstance(cache, str) else "ram" if cache is True else None
|
|
93
|
-
if
|
|
94
|
-
if
|
|
93
|
+
if self.cache == "ram" and self.check_cache_ram():
|
|
94
|
+
if hyp.deterministic:
|
|
95
95
|
LOGGER.warning(
|
|
96
96
|
"WARNING ⚠️ cache='ram' may produce non-deterministic training results. "
|
|
97
97
|
"Consider cache='disk' as a deterministic alternative if your disk space allows."
|
|
98
98
|
)
|
|
99
99
|
self.cache_images()
|
|
100
|
+
elif self.cache == "disk" and self.check_cache_disk():
|
|
101
|
+
self.cache_images()
|
|
100
102
|
|
|
101
103
|
# Transforms
|
|
102
104
|
self.transforms = self.build_transforms(hyp=hyp)
|
|
@@ -206,25 +208,55 @@ class BaseDataset(Dataset):
|
|
|
206
208
|
if not f.exists():
|
|
207
209
|
np.save(f.as_posix(), cv2.imread(self.im_files[i]), allow_pickle=False)
|
|
208
210
|
|
|
211
|
+
def check_cache_disk(self, safety_margin=0.5):
|
|
212
|
+
"""Check image caching requirements vs available disk space."""
|
|
213
|
+
import shutil
|
|
214
|
+
|
|
215
|
+
b, gb = 0, 1 << 30 # bytes of cached images, bytes per gigabytes
|
|
216
|
+
n = min(self.ni, 30) # extrapolate from 30 random images
|
|
217
|
+
for _ in range(n):
|
|
218
|
+
im_file = random.choice(self.im_files)
|
|
219
|
+
im = cv2.imread(im_file)
|
|
220
|
+
if im is None:
|
|
221
|
+
continue
|
|
222
|
+
b += im.nbytes
|
|
223
|
+
if not os.access(Path(im_file).parent, os.W_OK):
|
|
224
|
+
self.cache = None
|
|
225
|
+
LOGGER.info(f"{self.prefix}Skipping caching images to disk, directory not writeable ⚠️")
|
|
226
|
+
return False
|
|
227
|
+
disk_required = b * self.ni / n * (1 + safety_margin) # bytes required to cache dataset to disk
|
|
228
|
+
total, used, free = shutil.disk_usage(Path(self.im_files[0]).parent)
|
|
229
|
+
if disk_required > free:
|
|
230
|
+
self.cache = None
|
|
231
|
+
LOGGER.info(
|
|
232
|
+
f"{self.prefix}{disk_required / gb:.1f}GB disk space required, "
|
|
233
|
+
f"with {int(safety_margin * 100)}% safety margin but only "
|
|
234
|
+
f"{free / gb:.1f}/{total / gb:.1f}GB free, not caching images to disk ⚠️"
|
|
235
|
+
)
|
|
236
|
+
return False
|
|
237
|
+
return True
|
|
238
|
+
|
|
209
239
|
def check_cache_ram(self, safety_margin=0.5):
|
|
210
240
|
"""Check image caching requirements vs available memory."""
|
|
211
241
|
b, gb = 0, 1 << 30 # bytes of cached images, bytes per gigabytes
|
|
212
242
|
n = min(self.ni, 30) # extrapolate from 30 random images
|
|
213
243
|
for _ in range(n):
|
|
214
244
|
im = cv2.imread(random.choice(self.im_files)) # sample image
|
|
245
|
+
if im is None:
|
|
246
|
+
continue
|
|
215
247
|
ratio = self.imgsz / max(im.shape[0], im.shape[1]) # max(h, w) # ratio
|
|
216
248
|
b += im.nbytes * ratio**2
|
|
217
249
|
mem_required = b * self.ni / n * (1 + safety_margin) # GB required to cache dataset into RAM
|
|
218
250
|
mem = psutil.virtual_memory()
|
|
219
|
-
|
|
220
|
-
if not success:
|
|
251
|
+
if mem_required > mem.available:
|
|
221
252
|
self.cache = None
|
|
222
253
|
LOGGER.info(
|
|
223
254
|
f"{self.prefix}{mem_required / gb:.1f}GB RAM required to cache images "
|
|
224
255
|
f"with {int(safety_margin * 100)}% safety margin but only "
|
|
225
256
|
f"{mem.available / gb:.1f}/{mem.total / gb:.1f}GB available, not caching images ⚠️"
|
|
226
257
|
)
|
|
227
|
-
|
|
258
|
+
return False
|
|
259
|
+
return True
|
|
228
260
|
|
|
229
261
|
def set_rectangle(self):
|
|
230
262
|
"""Sets the shape of bounding boxes for YOLO detections as rectangles."""
|
|
@@ -216,7 +216,7 @@ def polygons2masks_overlap(imgsz, segments, downsample_ratio=1):
|
|
|
216
216
|
ms = []
|
|
217
217
|
for si in range(len(segments)):
|
|
218
218
|
mask = polygon2mask(imgsz, [segments[si].reshape(-1)], downsample_ratio=downsample_ratio, color=1)
|
|
219
|
-
ms.append(mask)
|
|
219
|
+
ms.append(mask.astype(masks.dtype))
|
|
220
220
|
areas.append(mask.sum())
|
|
221
221
|
areas = np.asarray(areas)
|
|
222
222
|
index = np.argsort(-areas)
|
|
@@ -452,12 +452,12 @@ class HUBDatasetStats:
|
|
|
452
452
|
path = Path(path).resolve()
|
|
453
453
|
LOGGER.info(f"Starting HUB dataset checks for {path}....")
|
|
454
454
|
|
|
455
|
-
self.task = task # detect, segment, pose, classify
|
|
455
|
+
self.task = task # detect, segment, pose, classify, obb
|
|
456
456
|
if self.task == "classify":
|
|
457
457
|
unzip_dir = unzip_file(path)
|
|
458
458
|
data = check_cls_dataset(unzip_dir)
|
|
459
459
|
data["path"] = unzip_dir
|
|
460
|
-
else: # detect, segment, pose
|
|
460
|
+
else: # detect, segment, pose, obb
|
|
461
461
|
_, data_dir, yaml_path = self._unzip(Path(path))
|
|
462
462
|
try:
|
|
463
463
|
# Load YAML with checks
|
|
@@ -119,6 +119,8 @@ class BaseValidator:
|
|
|
119
119
|
self.args.plots &= trainer.stopper.possible_stop or (trainer.epoch == trainer.epochs - 1)
|
|
120
120
|
model.eval()
|
|
121
121
|
else:
|
|
122
|
+
if str(self.args.model).endswith(".yaml"):
|
|
123
|
+
LOGGER.warning("WARNING ⚠️ validating an untrained model YAML will result in 0 mAP.")
|
|
122
124
|
callbacks.add_integration_callbacks(self)
|
|
123
125
|
model = AutoBackend(
|
|
124
126
|
weights=model or self.args.model,
|
|
@@ -19,10 +19,7 @@ class Heatmap:
|
|
|
19
19
|
def __init__(
|
|
20
20
|
self,
|
|
21
21
|
names,
|
|
22
|
-
imw=0,
|
|
23
|
-
imh=0,
|
|
24
22
|
colormap=cv2.COLORMAP_JET,
|
|
25
|
-
heatmap_alpha=0.5,
|
|
26
23
|
view_img=False,
|
|
27
24
|
view_in_counts=True,
|
|
28
25
|
view_out_counts=True,
|
|
@@ -33,7 +30,6 @@ class Heatmap:
|
|
|
33
30
|
region_thickness=5,
|
|
34
31
|
line_dist_thresh=15,
|
|
35
32
|
line_thickness=2,
|
|
36
|
-
decay_factor=0.99,
|
|
37
33
|
shape="circle",
|
|
38
34
|
):
|
|
39
35
|
"""Initializes the heatmap class with default values for Visual, Image, track, count and heatmap parameters."""
|
|
@@ -46,8 +42,6 @@ class Heatmap:
|
|
|
46
42
|
self.names = names # Classes names
|
|
47
43
|
|
|
48
44
|
# Image information
|
|
49
|
-
self.imw = imw
|
|
50
|
-
self.imh = imh
|
|
51
45
|
self.im0 = None
|
|
52
46
|
self.tf = line_thickness
|
|
53
47
|
self.view_in_counts = view_in_counts
|
|
@@ -56,7 +50,6 @@ class Heatmap:
|
|
|
56
50
|
# Heatmap colormap and heatmap np array
|
|
57
51
|
self.colormap = colormap
|
|
58
52
|
self.heatmap = None
|
|
59
|
-
self.heatmap_alpha = heatmap_alpha
|
|
60
53
|
|
|
61
54
|
# Predict/track information
|
|
62
55
|
self.boxes = []
|
|
@@ -79,9 +72,6 @@ class Heatmap:
|
|
|
79
72
|
self.count_bg_color = count_bg_color
|
|
80
73
|
self.cls_txtdisplay_gap = 50
|
|
81
74
|
|
|
82
|
-
# Decay factor
|
|
83
|
-
self.decay_factor = decay_factor
|
|
84
|
-
|
|
85
75
|
# Check if environment supports imshow
|
|
86
76
|
self.env_check = check_imshow(warn=True)
|
|
87
77
|
|
|
@@ -133,7 +123,7 @@ class Heatmap:
|
|
|
133
123
|
self.heatmap = np.zeros((int(self.im0.shape[0]), int(self.im0.shape[1])), dtype=np.float32)
|
|
134
124
|
self.initialized = True
|
|
135
125
|
|
|
136
|
-
self.heatmap *=
|
|
126
|
+
self.heatmap *= 0.99 # decay factor
|
|
137
127
|
|
|
138
128
|
self.extract_results(tracks)
|
|
139
129
|
self.annotator = Annotator(self.im0, self.tf, None)
|
|
@@ -239,7 +229,7 @@ class Heatmap:
|
|
|
239
229
|
# Normalize, apply colormap to heatmap and combine with original image
|
|
240
230
|
heatmap_normalized = cv2.normalize(self.heatmap, None, 0, 255, cv2.NORM_MINMAX)
|
|
241
231
|
heatmap_colored = cv2.applyColorMap(heatmap_normalized.astype(np.uint8), self.colormap)
|
|
242
|
-
self.im0 = cv2.addWeighted(self.im0,
|
|
232
|
+
self.im0 = cv2.addWeighted(self.im0, 0.5, heatmap_colored, 0.5, 0)
|
|
243
233
|
|
|
244
234
|
if self.env_check and self.view_img:
|
|
245
235
|
self.display_frames()
|
|
@@ -0,0 +1,129 @@
|
|
|
1
|
+
# Ultralytics YOLO 🚀, AGPL-3.0 license
|
|
2
|
+
|
|
3
|
+
from shapely.geometry import LineString, Point
|
|
4
|
+
|
|
5
|
+
from ultralytics.solutions.solutions import BaseSolution # Import a parent class
|
|
6
|
+
from ultralytics.utils.plotting import Annotator, colors
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
class ObjectCounter(BaseSolution):
|
|
10
|
+
"""A class to manage the counting of objects in a real-time video stream based on their tracks."""
|
|
11
|
+
|
|
12
|
+
def __init__(self, **kwargs):
|
|
13
|
+
"""Initialization function for Count class, a child class of BaseSolution class, can be used for counting the
|
|
14
|
+
objects.
|
|
15
|
+
"""
|
|
16
|
+
super().__init__(**kwargs)
|
|
17
|
+
|
|
18
|
+
self.in_count = 0 # Counter for objects moving inward
|
|
19
|
+
self.out_count = 0 # Counter for objects moving outward
|
|
20
|
+
self.counted_ids = [] # List of IDs of objects that have been counted
|
|
21
|
+
self.classwise_counts = {} # Dictionary for counts, categorized by object class
|
|
22
|
+
|
|
23
|
+
self.initialize_region() # Setup region and counting areas
|
|
24
|
+
|
|
25
|
+
self.show_in = self.CFG["show_in"]
|
|
26
|
+
self.show_out = self.CFG["show_out"]
|
|
27
|
+
|
|
28
|
+
def count_objects(self, track_line, box, track_id, prev_position, cls):
|
|
29
|
+
"""
|
|
30
|
+
Helper function to count objects within a polygonal region.
|
|
31
|
+
|
|
32
|
+
Args:
|
|
33
|
+
track_line (dict): last 30 frame track record
|
|
34
|
+
box (list): Bounding box data for specific track in current frame
|
|
35
|
+
track_id (int): track ID of the object
|
|
36
|
+
prev_position (tuple): last frame position coordinates of the track
|
|
37
|
+
cls (int): Class index for classwise count updates
|
|
38
|
+
"""
|
|
39
|
+
if prev_position is None or track_id in self.counted_ids:
|
|
40
|
+
return
|
|
41
|
+
|
|
42
|
+
centroid = self.r_s.centroid
|
|
43
|
+
dx = (box[0] - prev_position[0]) * (centroid.x - prev_position[0])
|
|
44
|
+
dy = (box[1] - prev_position[1]) * (centroid.y - prev_position[1])
|
|
45
|
+
|
|
46
|
+
if len(self.region) >= 3 and self.r_s.contains(Point(track_line[-1])):
|
|
47
|
+
self.counted_ids.append(track_id)
|
|
48
|
+
# For polygon region
|
|
49
|
+
if dx > 0:
|
|
50
|
+
self.in_count += 1
|
|
51
|
+
self.classwise_counts[self.names[cls]]["IN"] += 1
|
|
52
|
+
else:
|
|
53
|
+
self.out_count += 1
|
|
54
|
+
self.classwise_counts[self.names[cls]]["OUT"] += 1
|
|
55
|
+
|
|
56
|
+
elif len(self.region) < 3 and LineString([prev_position, box[:2]]).intersects(self.l_s):
|
|
57
|
+
self.counted_ids.append(track_id)
|
|
58
|
+
# For linear region
|
|
59
|
+
if dx > 0 and dy > 0:
|
|
60
|
+
self.in_count += 1
|
|
61
|
+
self.classwise_counts[self.names[cls]]["IN"] += 1
|
|
62
|
+
else:
|
|
63
|
+
self.out_count += 1
|
|
64
|
+
self.classwise_counts[self.names[cls]]["OUT"] += 1
|
|
65
|
+
|
|
66
|
+
def store_classwise_counts(self, cls):
|
|
67
|
+
"""
|
|
68
|
+
Initialize class-wise counts if not already present.
|
|
69
|
+
|
|
70
|
+
Args:
|
|
71
|
+
cls (int): Class index for classwise count updates
|
|
72
|
+
"""
|
|
73
|
+
if self.names[cls] not in self.classwise_counts:
|
|
74
|
+
self.classwise_counts[self.names[cls]] = {"IN": 0, "OUT": 0}
|
|
75
|
+
|
|
76
|
+
def display_counts(self, im0):
|
|
77
|
+
"""
|
|
78
|
+
Helper function to display object counts on the frame.
|
|
79
|
+
|
|
80
|
+
Args:
|
|
81
|
+
im0 (ndarray): The input image or frame
|
|
82
|
+
"""
|
|
83
|
+
labels_dict = {
|
|
84
|
+
str.capitalize(key): f"{'IN ' + str(value['IN']) if self.show_in else ''} "
|
|
85
|
+
f"{'OUT ' + str(value['OUT']) if self.show_out else ''}".strip()
|
|
86
|
+
for key, value in self.classwise_counts.items()
|
|
87
|
+
if value["IN"] != 0 or value["OUT"] != 0
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
if labels_dict:
|
|
91
|
+
self.annotator.display_analytics(im0, labels_dict, (104, 31, 17), (255, 255, 255), 10)
|
|
92
|
+
|
|
93
|
+
def count(self, im0):
|
|
94
|
+
"""
|
|
95
|
+
Processes input data (frames or object tracks) and updates counts.
|
|
96
|
+
|
|
97
|
+
Args:
|
|
98
|
+
im0 (ndarray): The input image that will be used for processing
|
|
99
|
+
Returns
|
|
100
|
+
im0 (ndarray): The processed image for more usage
|
|
101
|
+
"""
|
|
102
|
+
self.annotator = Annotator(im0, line_width=self.line_width) # Initialize annotator
|
|
103
|
+
self.extract_tracks(im0) # Extract tracks
|
|
104
|
+
|
|
105
|
+
self.annotator.draw_region(
|
|
106
|
+
reg_pts=self.region, color=(104, 0, 123), thickness=self.line_width * 2
|
|
107
|
+
) # Draw region
|
|
108
|
+
|
|
109
|
+
# Iterate over bounding boxes, track ids and classes index
|
|
110
|
+
if self.track_data is not None and self.track_data.id is not None:
|
|
111
|
+
for box, track_id, cls in zip(self.boxes, self.track_ids, self.clss):
|
|
112
|
+
# Draw bounding box and counting region
|
|
113
|
+
self.annotator.box_label(box, label=self.names[cls], color=colors(track_id, True))
|
|
114
|
+
self.store_tracking_history(track_id, box) # Store track history
|
|
115
|
+
self.store_classwise_counts(cls) # store classwise counts in dict
|
|
116
|
+
|
|
117
|
+
# Draw centroid of objects
|
|
118
|
+
self.annotator.draw_centroid_and_tracks(
|
|
119
|
+
self.track_line, color=colors(int(track_id), True), track_thickness=self.line_width
|
|
120
|
+
)
|
|
121
|
+
|
|
122
|
+
# store previous position of track for object counting
|
|
123
|
+
prev_position = self.track_history[track_id][-2] if len(self.track_history[track_id]) > 1 else None
|
|
124
|
+
self.count_objects(self.track_line, box, track_id, prev_position, cls) # Perform object counting
|
|
125
|
+
|
|
126
|
+
self.display_counts(im0) # Display the counts on the frame
|
|
127
|
+
self.display_output(im0) # display output with base class function
|
|
128
|
+
|
|
129
|
+
return im0 # return output image for more usage
|
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
# Ultralytics YOLO 🚀, AGPL-3.0 license
|
|
2
|
+
|
|
3
|
+
from collections import defaultdict
|
|
4
|
+
from pathlib import Path
|
|
5
|
+
|
|
6
|
+
import cv2
|
|
7
|
+
from shapely.geometry import LineString, Polygon
|
|
8
|
+
|
|
9
|
+
from ultralytics import YOLO
|
|
10
|
+
from ultralytics.utils import yaml_load
|
|
11
|
+
from ultralytics.utils.checks import check_imshow
|
|
12
|
+
|
|
13
|
+
DEFAULT_SOL_CFG_PATH = Path(__file__).resolve().parents[1] / "cfg/solutions/default.yaml"
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
class BaseSolution:
|
|
17
|
+
"""A class to manage all the Ultralytics Solutions: https://docs.ultralytics.com/solutions/."""
|
|
18
|
+
|
|
19
|
+
def __init__(self, **kwargs):
|
|
20
|
+
"""
|
|
21
|
+
Base initializer for all solutions.
|
|
22
|
+
|
|
23
|
+
Child classes should call this with necessary parameters.
|
|
24
|
+
"""
|
|
25
|
+
# Load config and update with args
|
|
26
|
+
self.CFG = yaml_load(DEFAULT_SOL_CFG_PATH)
|
|
27
|
+
self.CFG.update(kwargs)
|
|
28
|
+
print("Ultralytics Solutions: ✅", self.CFG)
|
|
29
|
+
|
|
30
|
+
self.region = self.CFG["region"] # Store region data for other classes usage
|
|
31
|
+
self.line_width = self.CFG["line_width"] # Store line_width for usage
|
|
32
|
+
|
|
33
|
+
# Load Model and store classes names
|
|
34
|
+
self.model = YOLO(self.CFG["model"])
|
|
35
|
+
self.names = self.model.names
|
|
36
|
+
|
|
37
|
+
# Initialize environment and region setup
|
|
38
|
+
self.env_check = check_imshow(warn=True)
|
|
39
|
+
self.track_history = defaultdict(list)
|
|
40
|
+
|
|
41
|
+
def extract_tracks(self, im0):
|
|
42
|
+
"""
|
|
43
|
+
Apply object tracking and extract tracks.
|
|
44
|
+
|
|
45
|
+
Args:
|
|
46
|
+
im0 (ndarray): The input image or frame
|
|
47
|
+
"""
|
|
48
|
+
self.tracks = self.model.track(source=im0, persist=True, classes=self.CFG["classes"])
|
|
49
|
+
|
|
50
|
+
# Extract tracks for OBB or object detection
|
|
51
|
+
self.track_data = self.tracks[0].obb or self.tracks[0].boxes
|
|
52
|
+
|
|
53
|
+
if self.track_data and self.track_data.id is not None:
|
|
54
|
+
self.boxes = self.track_data.xyxy.cpu()
|
|
55
|
+
self.clss = self.track_data.cls.cpu().tolist()
|
|
56
|
+
self.track_ids = self.track_data.id.int().cpu().tolist()
|
|
57
|
+
|
|
58
|
+
def store_tracking_history(self, track_id, box):
|
|
59
|
+
"""
|
|
60
|
+
Store object tracking history.
|
|
61
|
+
|
|
62
|
+
Args:
|
|
63
|
+
track_id (int): The track ID of the object
|
|
64
|
+
box (list): Bounding box coordinates of the object
|
|
65
|
+
"""
|
|
66
|
+
# Store tracking history
|
|
67
|
+
self.track_line = self.track_history[track_id]
|
|
68
|
+
self.track_line.append(((box[0] + box[2]) / 2, (box[1] + box[3]) / 2))
|
|
69
|
+
if len(self.track_line) > 30:
|
|
70
|
+
self.track_line.pop(0)
|
|
71
|
+
|
|
72
|
+
def initialize_region(self):
|
|
73
|
+
"""Initialize the counting region and line segment based on config."""
|
|
74
|
+
self.region = [(20, 400), (1260, 400)] if self.region is None else self.region
|
|
75
|
+
self.r_s = Polygon(self.region) if len(self.region) >= 3 else LineString(self.region)
|
|
76
|
+
self.l_s = LineString([(self.region[0][0], self.region[0][1]), (self.region[1][0], self.region[1][1])])
|
|
77
|
+
|
|
78
|
+
def display_output(self, im0):
|
|
79
|
+
"""
|
|
80
|
+
Display the results of the processing, which could involve showing frames, printing counts, or saving results.
|
|
81
|
+
|
|
82
|
+
Args:
|
|
83
|
+
im0 (ndarray): The input image or frame
|
|
84
|
+
"""
|
|
85
|
+
if self.CFG.get("show") and self.env_check:
|
|
86
|
+
cv2.imshow("Ultralytics Solutions", im0)
|
|
87
|
+
if cv2.waitKey(1) & 0xFF == ord("q"):
|
|
88
|
+
return
|
|
@@ -61,8 +61,8 @@ HELP_MSG = """
|
|
|
61
61
|
from ultralytics import YOLO
|
|
62
62
|
|
|
63
63
|
# Load a model
|
|
64
|
-
model = YOLO("
|
|
65
|
-
model = YOLO("
|
|
64
|
+
model = YOLO("yolo11n.yaml") # build a new model from scratch
|
|
65
|
+
model = YOLO("yolo11n.pt") # load a pretrained model (recommended for training)
|
|
66
66
|
|
|
67
67
|
# Use the model
|
|
68
68
|
results = model.train(data="coco8.yaml", epochs=3) # train the model
|
|
@@ -77,21 +77,21 @@ HELP_MSG = """
|
|
|
77
77
|
yolo TASK MODE ARGS
|
|
78
78
|
|
|
79
79
|
Where TASK (optional) is one of [detect, segment, classify, pose, obb]
|
|
80
|
-
MODE (required) is one of [train, val, predict, export, benchmark]
|
|
80
|
+
MODE (required) is one of [train, val, predict, export, track, benchmark]
|
|
81
81
|
ARGS (optional) are any number of custom "arg=value" pairs like "imgsz=320" that override defaults.
|
|
82
82
|
See all ARGS at https://docs.ultralytics.com/usage/cfg or with "yolo cfg"
|
|
83
83
|
|
|
84
84
|
- Train a detection model for 10 epochs with an initial learning_rate of 0.01
|
|
85
|
-
yolo detect train data=coco8.yaml model=
|
|
85
|
+
yolo detect train data=coco8.yaml model=yolo11n.pt epochs=10 lr0=0.01
|
|
86
86
|
|
|
87
87
|
- Predict a YouTube video using a pretrained segmentation model at image size 320:
|
|
88
|
-
yolo segment predict model=
|
|
88
|
+
yolo segment predict model=yolo11n-seg.pt source='https://youtu.be/LNwODJXcvt4' imgsz=320
|
|
89
89
|
|
|
90
90
|
- Val a pretrained detection model at batch-size 1 and image size 640:
|
|
91
|
-
yolo detect val model=
|
|
91
|
+
yolo detect val model=yolo11n.pt data=coco8.yaml batch=1 imgsz=640
|
|
92
92
|
|
|
93
|
-
- Export a
|
|
94
|
-
yolo export model=
|
|
93
|
+
- Export a YOLO11n classification model to ONNX format at image size 224 by 128 (no TASK required)
|
|
94
|
+
yolo export model=yolo11n-cls.pt format=onnx imgsz=224,128
|
|
95
95
|
|
|
96
96
|
- Run special commands:
|
|
97
97
|
yolo help
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: ultralytics
|
|
3
|
-
Version: 8.3.
|
|
3
|
+
Version: 8.3.5
|
|
4
4
|
Summary: Ultralytics YOLO for SOTA object detection, multi-object tracking, instance segmentation, pose estimation and image classification.
|
|
5
5
|
Author: Ayush Chaurasia
|
|
6
6
|
Author-email: Glenn Jocher <glenn.jocher@ultralytics.com>, Jing Qiu <jing.qiu@ultralytics.com>
|
|
@@ -103,6 +103,7 @@ ultralytics/cfg/models/v9/yolov9e.yaml
|
|
|
103
103
|
ultralytics/cfg/models/v9/yolov9m.yaml
|
|
104
104
|
ultralytics/cfg/models/v9/yolov9s.yaml
|
|
105
105
|
ultralytics/cfg/models/v9/yolov9t.yaml
|
|
106
|
+
ultralytics/cfg/solutions/default.yaml
|
|
106
107
|
ultralytics/cfg/trackers/botsort.yaml
|
|
107
108
|
ultralytics/cfg/trackers/bytetrack.yaml
|
|
108
109
|
ultralytics/data/__init__.py
|
|
@@ -208,6 +209,7 @@ ultralytics/solutions/heatmap.py
|
|
|
208
209
|
ultralytics/solutions/object_counter.py
|
|
209
210
|
ultralytics/solutions/parking_management.py
|
|
210
211
|
ultralytics/solutions/queue_management.py
|
|
212
|
+
ultralytics/solutions/solutions.py
|
|
211
213
|
ultralytics/solutions/speed_estimation.py
|
|
212
214
|
ultralytics/solutions/streamlit_inference.py
|
|
213
215
|
ultralytics/trackers/__init__.py
|