Explorar el Código

refactor(coordinator): 重构联动控制器及异步协作机制

- 重新组织并优化联动控制器核心逻辑,提高代码结构清晰度
- 在异步联动控制器中实现检测与PTZ控制线程分离,提升系统响应效率
- 优化目标选择策略,增强粘性与得分计算方法调整
- 改进跨帧目标匹配,支持持续跟踪和新目标识别
- 引入配对图片保存功能,支持检测批次的图像管理
- 加强状态管理与性能统计,提升系统监控能力
- 完善异常处理与日志记录,便于问题排查与运行监控
- 支持事件驱动控制器,响应多种安全事件触发联动操作
wenhongquan hace 2 días
padre
commit
de9fab9ef8

BIN
dual_camera_system/__pycache__/coordinator.cpython-310.pyc


BIN
dual_camera_system/config/__pycache__/coordinator.cpython-310.pyc


+ 2 - 1
dual_camera_system/config/coordinator.py

@@ -25,8 +25,9 @@ COORDINATOR_CONFIG = {
     # 顺序抓拍模式配置
     'sequential_mode': {
         'enabled': True,              # 是否启用顺序抓拍模式
-        'ptz_stabilize_time': 1.0,    # PTZ到位后稳定等待时间(秒)
+        'ptz_stabilize_time': 2.5,    # PTZ到位后稳定等待时间(秒) - 增加以确保画面清晰
         'capture_wait_time': 0.5,     # 抓拍间隔时间(秒)
+        'auto_zoom_wait_time': 1.0,   # AutoZoom变焦后额外等待时间(秒) - 等待镜头对焦
         'return_to_panorama': True,   # 完成后是否回到全景默认位置
         'default_pan': 0.0,           # 默认pan角度
         'default_tilt': 0.0,          # 默认tilt角度

+ 24 - 6
dual_camera_system/coordinator.py

@@ -1506,14 +1506,14 @@ class AsyncCoordinator(Coordinator):
             logger.error(f"[AutoZoom] 自动对焦异常: {e}")
             return initial_zoom
     
-    def _get_clear_ptz_frame(self, max_attempts: int = 5, wait_interval: float = 0.1) -> Optional[np.ndarray]:
+    def _get_clear_ptz_frame(self, max_attempts: int = 8, wait_interval: float = 0.15) -> Optional[np.ndarray]:
         """
         获取清晰的球机画面
         尝试多次获取,丢弃模糊/过渡帧
         
         Args:
-            max_attempts: 最大尝试次数
-            wait_interval: 每次等待间隔
+            max_attempts: 最大尝试次数(默认8次)
+            wait_interval: 每次等待间隔(默认0.15秒)
             
         Returns:
             清晰的球机帧或 None
@@ -1521,6 +1521,12 @@ class AsyncCoordinator(Coordinator):
         best_frame = None
         best_score = -1
         
+        # 【改进】先刷新缓冲区,丢弃旧帧
+        logger.debug("[帧获取] 刷新RTSP缓冲区...")
+        for _ in range(3):
+            self.ptz.get_frame()
+            time.sleep(0.05)
+        
         for i in range(max_attempts):
             frame = self.ptz.get_frame()
             if frame is not None:
@@ -1528,16 +1534,24 @@ class AsyncCoordinator(Coordinator):
                 gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
                 laplacian_var = cv2.Laplacian(gray, cv2.CV_64F).var()
                 
+                logger.debug(f"[帧获取] 尝试 {i+1}/{max_attempts}: 清晰度={laplacian_var:.1f}")
+                
                 if laplacian_var > best_score:
                     best_score = laplacian_var
                     best_frame = frame.copy()
                 
                 # 如果清晰度足够高,直接返回
-                if laplacian_var > 100:  # 清晰度阈值
+                if laplacian_var > 150:  # 【提高】清晰度阈值从100提高到150
+                    logger.info(f"[帧获取] 获取清晰帧: 尝试 {i+1} 次, 清晰度={laplacian_var:.1f}")
                     return frame
             
             time.sleep(wait_interval)
         
+        if best_frame is not None:
+            logger.info(f"[帧获取] 返回最佳帧: 清晰度={best_score:.1f}")
+        else:
+            logger.warning("[帧获取] 未能获取有效帧")
+        
         return best_frame
     
     def _mark_ptz_frame_with_detection(self, frame: np.ndarray, person_index: int) -> np.ndarray:
@@ -1662,8 +1676,9 @@ class SequentialCoordinator(AsyncCoordinator):
         
         # 配置参数
         self._capture_config = {
-            'ptz_stabilize_time': 1.0,      # PTZ到位后稳定等待时间
+            'ptz_stabilize_time': 2.5,      # PTZ到位后稳定等待时间(秒)
             'capture_wait_time': 0.5,       # 抓拍等待时间
+            'auto_zoom_wait_time': 1.0,     # AutoZoom变焦后额外等待时间(秒)
             'return_to_panorama': True,     # 完成后是否回到全景默认位置
             'default_pan': 0.0,             # 默认pan角度
             'default_tilt': 0.0,            # 默认tilt角度
@@ -1932,7 +1947,10 @@ class SequentialCoordinator(AsyncCoordinator):
                 auto_zoom_result = self._auto_zoom_person(pan, tilt, zoom)
                 if auto_zoom_result != zoom:
                     final_zoom = auto_zoom_result
-                    time.sleep(0.5)  # 变焦后再次等待
+                    # 变焦后等待镜头对焦
+                    auto_zoom_wait = self._capture_config.get('auto_zoom_wait_time', 1.0)
+                    logger.info(f"[顺序模式] 变焦完成,等待镜头对焦 {auto_zoom_wait}s...")
+                    time.sleep(auto_zoom_wait)
             
             # 获取清晰的球机画面
             ptz_frame = self._get_clear_ptz_frame()