make max target box a function of zoom factor

This commit is contained in:
Josh Hawkins
2026-10-04 07:29:14 -05:00
parent ed8367e51e
commit 920e8a1c9f
3 changed files with 15 additions and 23 deletions
+3 -3
View File
@@ -16,7 +16,7 @@ from frigate.config import (
ZoomingModeEnum, ZoomingModeEnum,
) )
from frigate.const import CLIPS_DIR, THUMB_DIR from frigate.const import CLIPS_DIR, THUMB_DIR
from frigate.ptz.autotrack import PtzAutoTracker from frigate.ptz.autotrack import PtzAutoTracker, calculate_max_target_box
from frigate.track.tracked_object import TrackedObject from frigate.track.tracked_object import TrackedObject
from frigate.util.image import ( from frigate.util.image import (
SharedMemoryFrameManager, SharedMemoryFrameManager,
@@ -134,8 +134,8 @@ class CameraState:
and self.camera_config.detect.width is not None and self.camera_config.detect.width is not None
and self.camera_config.detect.height is not None and self.camera_config.detect.height is not None
): ):
max_target_box = self.ptz_autotracker_thread.max_target_box( max_target_box = calculate_max_target_box(
self.name self.camera_config.onvif.autotracking.zoom_factor
) )
side_length = max_target_box * ( side_length = max_target_box * (
max( max(
+7 -7
View File
@@ -43,6 +43,11 @@ from frigate.util.image import SharedMemoryFrameManager, intersection_over_union
logger = logging.getLogger(__name__) logger = logging.getLogger(__name__)
def calculate_max_target_box(zoom_factor: float) -> float:
"""Return the largest target box ratio allowed for a zoom factor."""
return AUTOTRACKING_MAX_AREA_RATIO ** (1 / zoom_factor)
def ptz_moving_at_frame_time(frame_time, ptz_start_time, ptz_stop_time): def ptz_moving_at_frame_time(frame_time, ptz_start_time, ptz_stop_time):
# Determine if the PTZ was in motion at the set frame time # Determine if the PTZ was in motion at the set frame time
# for non ptz/autotracking cameras, this will always return False # for non ptz/autotracking cameras, this will always return False
@@ -332,11 +337,6 @@ class PtzAutoTracker(threading.Thread):
def _reset_tracked_object_metrics(self, camera: str) -> None: def _reset_tracked_object_metrics(self, camera: str) -> None:
self.tracked_object_metrics[camera] = {} self.tracked_object_metrics[camera] = {}
def max_target_box(self, camera: str) -> float:
"""Return the largest target box ratio allowed for the zoom factor."""
zoom_factor = self.config.cameras[camera].onvif.autotracking.zoom_factor
return AUTOTRACKING_MAX_AREA_RATIO ** (1 / zoom_factor)
async def _wait_until_stopped( async def _wait_until_stopped(
self, camera: str, metrics: PTZMetrics | None = None self, camera: str, metrics: PTZMetrics | None = None
) -> None: ) -> None:
@@ -945,7 +945,7 @@ class PtzAutoTracker(threading.Thread):
camera_config = self.config.cameras[camera] camera_config = self.config.cameras[camera]
tom = self.tracked_object_metrics[camera] tom = self.tracked_object_metrics[camera]
zoom_factor = camera_config.onvif.autotracking.zoom_factor zoom_factor = camera_config.onvif.autotracking.zoom_factor
max_target_box = self.max_target_box(camera) max_target_box = calculate_max_target_box(zoom_factor)
camera_width = camera_config.frame_shape[1] camera_width = camera_config.frame_shape[1]
camera_height = camera_config.frame_shape[0] camera_height = camera_config.frame_shape[0]
camera_fps = camera_config.detect.fps camera_fps = camera_config.detect.fps
@@ -1179,7 +1179,7 @@ class PtzAutoTracker(threading.Thread):
camera_config = self.config.cameras[camera] camera_config = self.config.cameras[camera]
tom = self.tracked_object_metrics[camera] tom = self.tracked_object_metrics[camera]
zoom_factor = camera_config.onvif.autotracking.zoom_factor zoom_factor = camera_config.onvif.autotracking.zoom_factor
max_target_box = self.max_target_box(camera) max_target_box = calculate_max_target_box(zoom_factor)
# frame width and height # frame width and height
camera_width = camera_config.frame_shape[1] camera_width = camera_config.frame_shape[1]
+5 -13
View File
@@ -17,7 +17,7 @@ from unittest.mock import MagicMock
from frigate.camera import PTZMetrics from frigate.camera import PTZMetrics
from frigate.config import FrigateConfig from frigate.config import FrigateConfig
from frigate.config.camera.updater import CameraConfigUpdateEnum from frigate.config.camera.updater import CameraConfigUpdateEnum
from frigate.ptz.autotrack import PtzAutoTracker from frigate.ptz.autotrack import PtzAutoTracker, calculate_max_target_box
CAMERA = "ptz_cam" CAMERA = "ptz_cam"
@@ -123,18 +123,10 @@ class TestAutotrackerDisable(unittest.TestCase):
self.assertIs(payload, autotracking) self.assertIs(payload, autotracking)
class TestAutotrackerMaxTargetBox(unittest.TestCase): class TestMaxTargetBox(unittest.TestCase):
def test_follows_live_zoom_factor(self) -> None: def test_follows_zoom_factor(self) -> None:
# the debug overlay and the zoom decisions both read this, so it has to self.assertAlmostEqual(calculate_max_target_box(0.5), 0.6**2)
# track a zoom_factor changed while an object is being followed self.assertAlmostEqual(calculate_max_target_box(0.25), 0.6**4)
tracker = _make_tracker()
autotracking = tracker.config.cameras[CAMERA].onvif.autotracking
autotracking.zoom_factor = 0.5
self.assertAlmostEqual(tracker.max_target_box(CAMERA), 0.6**2)
autotracking.zoom_factor = 0.25
self.assertAlmostEqual(tracker.max_target_box(CAMERA), 0.6**4)
if __name__ == "__main__": if __name__ == "__main__":