Migrated to nix for dependency managment
This commit is contained in:
1 parent
e9da24b54d
commit
8005b38b67
11 files changed
+206
-23920
No files matched your search
@@ -1,24 +0,0 @@
|
|||||||
from pathlib import Path
|
|
||||||
|
|
||||||
from dodgeballtracker.logic import (DetectedObjectBox,
|
|
||||||
DodgeballTracker,
|
|
||||||
get_court_perspective_transform)
|
|
||||||
import numpy as np
|
|
||||||
|
|
||||||
|
|
||||||
here = Path(__file__).parent
|
|
||||||
input_dir = here / '..' / 'data'
|
|
||||||
output_dir = here / '..' / 'outputs'
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
|
||||||
detected_box_objects = [
|
|
||||||
DetectedObjectBox.from_viridis(threshold) for threshold in np.arange(0.5, 1, 0.05)
|
|
||||||
]
|
|
||||||
input_video = input_dir / "micro.mp4"
|
|
||||||
output_video = output_dir / "output-lmbn_n_cuhk03_d.mp4"
|
|
||||||
|
|
||||||
transformation_matrix = get_court_perspective_transform()
|
|
||||||
|
|
||||||
dodgeball_tracker = DodgeballTracker(input_video, output_video, detected_box_objects, transformation_matrix)
|
|
||||||
|
|
||||||
dodgeball_tracker.main()
|
|
||||||
@@ -0,0 +1,28 @@
|
|||||||
|
from pathlib import Path
|
||||||
|
|
||||||
|
from dodgeballtracker.logic import (DetectedObjectBox,
|
||||||
|
DodgeballTracker,
|
||||||
|
get_court_perspective_transform)
|
||||||
|
import numpy as np
|
||||||
|
import logging
|
||||||
|
|
||||||
|
|
||||||
|
here = Path(__file__).parent
|
||||||
|
input_dir = here / '..' / 'data'
|
||||||
|
output_dir = here / '..' / 'outputs'
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
logging.basicConfig(filename='tracker.log', level=logging.DEBUG)
|
||||||
|
|
||||||
|
detected_box_objects = [
|
||||||
|
DetectedObjectBox.from_viridis(threshold) for threshold in np.arange(0.5, 1, 0.05)
|
||||||
|
]
|
||||||
|
|
||||||
|
input_video = input_dir / "small.mp4"
|
||||||
|
output_video = output_dir / "foo.mp4"
|
||||||
|
|
||||||
|
transformation_matrix = get_court_perspective_transform()
|
||||||
|
|
||||||
|
dodgeball_tracker = DodgeballTracker(input_video, output_video, detected_box_objects, transformation_matrix)
|
||||||
|
|
||||||
|
dodgeball_tracker.main()
|
||||||
@@ -7,7 +7,7 @@ import cv2
|
|||||||
from dodgeballtracker.helper import create_video_writer, iter_frames
|
from dodgeballtracker.helper import create_video_writer, iter_frames
|
||||||
import matplotlib
|
import matplotlib
|
||||||
import numpy as np
|
import numpy as np
|
||||||
from boxmot import DeepOCSORT
|
from boxmot import DeepOcSort as DeepOCSORT
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@@ -125,19 +125,20 @@ class DodgeballTracker:
|
|||||||
|
|
||||||
def _get_tracker(self):
|
def _get_tracker(self):
|
||||||
return DeepOCSORT(
|
return DeepOCSORT(
|
||||||
model_weights=Path('lmbn_n_cuhk03_d.pt'), # which ReID model to use
|
Path('lmbn_n_cuhk03_d.pt'), # which ReID model to use
|
||||||
device=torch.device("mps"),
|
torch.device("cpu"),
|
||||||
fp16=True,
|
True,
|
||||||
)
|
)
|
||||||
|
|
||||||
def _get_detection_model(self):
|
def _get_detection_model(self):
|
||||||
"""
|
"""
|
||||||
load the pre-trained YOLOv8n model
|
load the pre-trained YOLOv8n model
|
||||||
"""
|
"""
|
||||||
return YOLO("yolov8n.pt")
|
return YOLO("yolo11n.pt", verbose=True)
|
||||||
|
|
||||||
def main(self):
|
def main(self):
|
||||||
# define some constants
|
# define some constants
|
||||||
|
print("started")
|
||||||
|
|
||||||
video_cap = cv2.VideoCapture(str(self.input_path))
|
video_cap = cv2.VideoCapture(str(self.input_path))
|
||||||
writer = create_video_writer(video_cap, str(self.output_path))
|
writer = create_video_writer(video_cap, str(self.output_path))
|
||||||
@@ -150,12 +151,15 @@ class DodgeballTracker:
|
|||||||
# run the YOLO model on the frame
|
# run the YOLO model on the frame
|
||||||
res = []
|
res = []
|
||||||
detections = self.run_model_on_frame(model, frame)
|
detections = self.run_model_on_frame(model, frame)
|
||||||
|
print("ici?")
|
||||||
for data in detections.boxes.data.tolist():
|
for data in detections.boxes.data.tolist():
|
||||||
|
print("la?")
|
||||||
is_good_box = self.plot_boxe_to_frame(data, frame)
|
is_good_box = self.plot_boxe_to_frame(data, frame)
|
||||||
if is_good_box:
|
if is_good_box:
|
||||||
res.append(data)
|
res.append(data)
|
||||||
|
|
||||||
# show the frame to our screen
|
# show the frame to our screen
|
||||||
|
print("tracker?")
|
||||||
data_ = tracker.update(np.array(res), frame)
|
data_ = tracker.update(np.array(res), frame)
|
||||||
self.print_tracker_data(data_, i, ts)
|
self.print_tracker_data(data_, i, ts)
|
||||||
|
|
||||||
@@ -163,8 +167,10 @@ class DodgeballTracker:
|
|||||||
|
|
||||||
if cv2.waitKey(1) == ord("q"):
|
if cv2.waitKey(1) == ord("q"):
|
||||||
break
|
break
|
||||||
|
print("fini")
|
||||||
|
|
||||||
video_cap.release()
|
video_cap.release()
|
||||||
writer.release()
|
writer.release()
|
||||||
cv2.destroyAllWindows()
|
cv2.destroyAllWindows()
|
||||||
self.persist_points()
|
self.persist_points()
|
||||||
|
print("finished")
|
||||||
Executable
+7
@@ -0,0 +1,7 @@
|
|||||||
|
#!/usr/bin/env bash
|
||||||
|
|
||||||
|
yt-dlp --write-info-json \
|
||||||
|
--output data/full.mp4 \
|
||||||
|
'https://www.youtube.com/watch?v=Spu6OlAZHUo'
|
||||||
|
|
||||||
|
ffmpeg -ss 00:19:15.00 -i data/full.mp4.webm -t 00:00:30.00 -c copy data/small.mp4
|
||||||
Generated
+130
@@ -0,0 +1,130 @@
|
|||||||
|
{
|
||||||
|
"nodes": {
|
||||||
|
"flake-utils": {
|
||||||
|
"inputs": {
|
||||||
|
"systems": "systems"
|
||||||
|
},
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1726560853,
|
||||||
|
"narHash": "sha256-X6rJYSESBVr3hBoH0WbKE5KvhPU5bloyZ2L4K60/fPQ=",
|
||||||
|
"owner": "numtide",
|
||||||
|
"repo": "flake-utils",
|
||||||
|
"rev": "c1dfcf08411b08f6b8615f7d8971a2bfa81d5e8a",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"owner": "numtide",
|
||||||
|
"repo": "flake-utils",
|
||||||
|
"type": "github"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"flake-utils_2": {
|
||||||
|
"inputs": {
|
||||||
|
"systems": "systems_2"
|
||||||
|
},
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1726560853,
|
||||||
|
"narHash": "sha256-X6rJYSESBVr3hBoH0WbKE5KvhPU5bloyZ2L4K60/fPQ=",
|
||||||
|
"owner": "numtide",
|
||||||
|
"repo": "flake-utils",
|
||||||
|
"rev": "c1dfcf08411b08f6b8615f7d8971a2bfa81d5e8a",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"owner": "numtide",
|
||||||
|
"repo": "flake-utils",
|
||||||
|
"type": "github"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"nixpkgs": {
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1729595756,
|
||||||
|
"narHash": "sha256-rNaLWDqjgy23Y6M3K/e7Kiyimq04ikDMrErpqgXWcV0=",
|
||||||
|
"owner": "NixOS",
|
||||||
|
"repo": "nixpkgs",
|
||||||
|
"rev": "782740762fb281404740b6b7084d356c3dab1173",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"owner": "NixOS",
|
||||||
|
"ref": "nixpkgs-unstable",
|
||||||
|
"repo": "nixpkgs",
|
||||||
|
"type": "github"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"nixpkgs_2": {
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1729595756,
|
||||||
|
"narHash": "sha256-rNaLWDqjgy23Y6M3K/e7Kiyimq04ikDMrErpqgXWcV0=",
|
||||||
|
"owner": "NixOS",
|
||||||
|
"repo": "nixpkgs",
|
||||||
|
"rev": "782740762fb281404740b6b7084d356c3dab1173",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"owner": "NixOS",
|
||||||
|
"ref": "nixpkgs-unstable",
|
||||||
|
"repo": "nixpkgs",
|
||||||
|
"type": "github"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"opencv-python-related": {
|
||||||
|
"inputs": {
|
||||||
|
"flake-utils": "flake-utils_2",
|
||||||
|
"nixpkgs": "nixpkgs_2"
|
||||||
|
},
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1729677213,
|
||||||
|
"narHash": "sha256-n+g2ROk4ytvZW84+vjaQMarVI/sFoiEUXxMxPnlM9BU=",
|
||||||
|
"owner": "all-dressed-programming",
|
||||||
|
"repo": "opencv-python-related",
|
||||||
|
"rev": "fb816cdf83b7779962c6b8479b377b2927a9ea2d",
|
||||||
|
"type": "gitlab"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"owner": "all-dressed-programming",
|
||||||
|
"repo": "opencv-python-related",
|
||||||
|
"type": "gitlab"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"root": {
|
||||||
|
"inputs": {
|
||||||
|
"flake-utils": "flake-utils",
|
||||||
|
"nixpkgs": "nixpkgs",
|
||||||
|
"opencv-python-related": "opencv-python-related"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"systems": {
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1681028828,
|
||||||
|
"narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=",
|
||||||
|
"owner": "nix-systems",
|
||||||
|
"repo": "default",
|
||||||
|
"rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"owner": "nix-systems",
|
||||||
|
"repo": "default",
|
||||||
|
"type": "github"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"systems_2": {
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1681028828,
|
||||||
|
"narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=",
|
||||||
|
"owner": "nix-systems",
|
||||||
|
"repo": "default",
|
||||||
|
"rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"owner": "nix-systems",
|
||||||
|
"repo": "default",
|
||||||
|
"type": "github"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"root": "root",
|
||||||
|
"version": 7
|
||||||
|
}
|
||||||
@@ -0,0 +1,25 @@
|
|||||||
|
{
|
||||||
|
description = "Pre-built CPU-only OpenCV packages for Python. ";
|
||||||
|
inputs = {
|
||||||
|
nixpkgs.url = "github:NixOS/nixpkgs/nixpkgs-unstable";
|
||||||
|
opencv-python-related.url = "gitlab:all-dressed-programming/opencv-python-related";
|
||||||
|
flake-utils.url = "github:numtide/flake-utils";
|
||||||
|
};
|
||||||
|
|
||||||
|
outputs = { self, nixpkgs, flake-utils, opencv-python-related }:
|
||||||
|
flake-utils.lib.eachDefaultSystem (system:
|
||||||
|
let
|
||||||
|
pkgs = nixpkgs.legacyPackages.${system};
|
||||||
|
pythonPackages = pkgs.python312Packages // opencv-python-related.packages.${system}.python312Packages;
|
||||||
|
virtual-env = pkgs.python312.withPackages (ps: [ ps.matplotlib
|
||||||
|
pythonPackages.opencv4
|
||||||
|
pythonPackages.boxmot
|
||||||
|
pythonPackages.ultralytics ]);
|
||||||
|
|
||||||
|
in {
|
||||||
|
packages = {
|
||||||
|
env = virtual-env;
|
||||||
|
};
|
||||||
|
devShells.default = pkgs.mkShell { buildInputs = [ virtual-env pkgs.yt-dlp pkgs.ffmpeg_7]; };
|
||||||
|
});
|
||||||
|
}
|
||||||
-23888
File diff suppressed because it is too large.
Load diff
@@ -35,7 +35,7 @@ apiRouter.get("/match/:id/pane/player", async function(ctx){
|
|||||||
});
|
});
|
||||||
|
|
||||||
apiRouter.get("/match/:id/pane/player/data", async function(ctx){
|
apiRouter.get("/match/:id/pane/player/data", async function(ctx){
|
||||||
ctx.response.body = <svg:rect width="100" height="100" />
|
ctx.response.body = <rect width="100" height="100"/>
|
||||||
});
|
});
|
||||||
|
|
||||||
apiRouter.get('/list-matches', async (ctx) => {
|
apiRouter.get('/list-matches', async (ctx) => {
|
||||||
|
|||||||
@@ -32,7 +32,8 @@ export class ViewTabService {
|
|||||||
playerTab(matchInfo: MatchInfo){
|
playerTab(matchInfo: MatchInfo){
|
||||||
return (<div>
|
return (<div>
|
||||||
<div id="foo"></div>
|
<div id="foo"></div>
|
||||||
<form hx-get={"/api/v1/match/:id/pane/player/data"}
|
<form hx-swap="innerHTML"
|
||||||
|
hx-get={"/api/v1/match/:id/pane/player/data"}
|
||||||
hx-target="#court-content">
|
hx-target="#court-content">
|
||||||
<div class="field is-horizontal">
|
<div class="field is-horizontal">
|
||||||
<div class="field-label is-normal">
|
<div class="field-label is-normal">
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ export function Head(){
|
|||||||
<link rel="stylesheet" href="https://cdn.jsdelivr.net/gh/highlightjs/cdn-release@11.9.0/build/styles/default.min.css"/>
|
<link rel="stylesheet" href="https://cdn.jsdelivr.net/gh/highlightjs/cdn-release@11.9.0/build/styles/default.min.css"/>
|
||||||
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/styles/atom-one-light.min.css"/>
|
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/styles/atom-one-light.min.css"/>
|
||||||
|
|
||||||
<script src="https://unpkg.com/htmx.org@1.9.9"></script>
|
<script src="/vendor/htmx/htmx.js"></script>
|
||||||
</head>)
|
</head>)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -19,6 +19,7 @@ function Court(){
|
|||||||
<line x1={600} x2={600} y1={0} y2={450} style={returnLine}></line>,
|
<line x1={600} x2={600} y1={0} y2={450} style={returnLine}></line>,
|
||||||
]
|
]
|
||||||
return (<svg class="court-side"
|
return (<svg class="court-side"
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
style={{width: 900 + 2 * margin, height: 450 + 2 * margin, backgroundColor: 'pink'}}>
|
style={{width: 900 + 2 * margin, height: 450 + 2 * margin, backgroundColor: 'pink'}}>
|
||||||
<g class="court-border" id="court" transform = {`translate(${margin} ${margin})`}>
|
<g class="court-border" id="court" transform = {`translate(${margin} ${margin})`}>
|
||||||
<rect width={900} height={450} style={courtBorder}/>
|
<rect width={900} height={450} style={courtBorder}/>
|
||||||
|
|||||||
Reference in new issue
Block a user