|
|
|
|
|
""" |
|
|
Quick test to verify the fixed predictor works correctly. |
|
|
Creates a synthetic video and tests the prediction pipeline. |
|
|
""" |
|
|
|
|
|
import sys |
|
|
import tempfile |
|
|
import logging |
|
|
from pathlib import Path |
|
|
import cv2 |
|
|
import numpy as np |
|
|
from PIL import Image, ImageDraw |
|
|
|
|
|
|
|
|
logging.basicConfig(level=logging.INFO, format='%(asctime)s - %(levelname)s - %(message)s') |
|
|
|
|
|
def create_test_video(output_path: Path, duration_seconds: float = 2.0, fps: int = 24): |
|
|
"""Create a synthetic test video with simple animation.""" |
|
|
|
|
|
width, height = 640, 480 |
|
|
total_frames = int(duration_seconds * fps) |
|
|
|
|
|
|
|
|
fourcc = cv2.VideoWriter_fourcc(*'mp4v') |
|
|
out = cv2.VideoWriter(str(output_path), fourcc, fps, (width, height)) |
|
|
|
|
|
logging.info(f"Creating test video: {total_frames} frames at {fps} FPS") |
|
|
|
|
|
for frame_num in range(total_frames): |
|
|
|
|
|
frame = np.zeros((height, width, 3), dtype=np.uint8) |
|
|
|
|
|
|
|
|
frame[:, :] = [50 + frame_num % 100, 100, 150 + frame_num % 50] |
|
|
|
|
|
|
|
|
center_x = width // 2 + int(50 * np.sin(frame_num * 0.3)) |
|
|
center_y = height // 2 + int(20 * np.sin(frame_num * 0.5)) |
|
|
|
|
|
|
|
|
cv2.circle(frame, (center_x, center_y), 40, (255, 220, 177), -1) |
|
|
|
|
|
|
|
|
for i in range(5): |
|
|
angle = -0.5 + i * 0.25 + 0.3 * np.sin(frame_num * 0.2 + i) |
|
|
finger_x = center_x + int(60 * np.cos(angle)) |
|
|
finger_y = center_y + int(60 * np.sin(angle)) |
|
|
cv2.circle(frame, (finger_x, finger_y), 15, (255, 200, 150), -1) |
|
|
|
|
|
|
|
|
cv2.putText(frame, f"Waving Hand - Frame {frame_num}", (50, 50), |
|
|
cv2.FONT_HERSHEY_SIMPLEX, 1, (255, 255, 255), 2) |
|
|
|
|
|
out.write(frame) |
|
|
|
|
|
out.release() |
|
|
logging.info(f"β Created test video: {output_path}") |
|
|
return output_path |
|
|
|
|
|
def test_predictor(): |
|
|
"""Test the fixed predictor with synthetic video.""" |
|
|
|
|
|
print("π§ͺ Testing Fixed Video Action Predictor") |
|
|
print("=" * 50) |
|
|
|
|
|
try: |
|
|
from predict_fixed import predict_actions |
|
|
|
|
|
with tempfile.TemporaryDirectory() as tmp_dir: |
|
|
tmp_path = Path(tmp_dir) |
|
|
video_path = tmp_path / "waving_test.mp4" |
|
|
|
|
|
|
|
|
create_test_video(video_path, duration_seconds=3.0, fps=15) |
|
|
|
|
|
|
|
|
print("\nπ Running prediction...") |
|
|
|
|
|
try: |
|
|
predictions = predict_actions(str(video_path), top_k=5) |
|
|
|
|
|
print(f"\nβ
Prediction successful! Got {len(predictions)} results:") |
|
|
print("-" * 60) |
|
|
|
|
|
for i, (label, confidence) in enumerate(predictions, 1): |
|
|
print(f"{i:2d}. {label:<35} {confidence:.4f}") |
|
|
|
|
|
|
|
|
waving_related = ['waving', 'hand waving', 'greeting', 'applauding', 'clapping'] |
|
|
found_relevant = False |
|
|
|
|
|
for label, confidence in predictions: |
|
|
for waving_term in waving_related: |
|
|
if waving_term in label.lower(): |
|
|
print(f"\nπ― Found relevant prediction: '{label}' ({confidence:.3f})") |
|
|
found_relevant = True |
|
|
break |
|
|
|
|
|
if not found_relevant: |
|
|
print("\nβ οΈ No obviously relevant predictions found, but system is working!") |
|
|
print("The top prediction might still be reasonable given the synthetic nature of the test video.") |
|
|
|
|
|
return True |
|
|
|
|
|
except Exception as prediction_error: |
|
|
print(f"\nβ Prediction failed: {prediction_error}") |
|
|
|
|
|
|
|
|
import traceback |
|
|
print("\nFull traceback:") |
|
|
traceback.print_exc() |
|
|
|
|
|
return False |
|
|
|
|
|
except ImportError as e: |
|
|
print(f"β Cannot import predict_fixed: {e}") |
|
|
return False |
|
|
except Exception as e: |
|
|
print(f"β Test setup failed: {e}") |
|
|
return False |
|
|
|
|
|
def test_tensor_format(): |
|
|
"""Test just the tensor creation to isolate any issues.""" |
|
|
|
|
|
print("\nπ§ Testing Tensor Creation") |
|
|
print("-" * 30) |
|
|
|
|
|
try: |
|
|
from predict_fixed import create_timesformer_tensor, normalize_frames |
|
|
from PIL import Image |
|
|
|
|
|
|
|
|
frames = [] |
|
|
colors = [(255, 0, 0), (0, 255, 0), (0, 0, 255), (255, 255, 0), |
|
|
(255, 0, 255), (0, 255, 255), (128, 128, 128), (255, 255, 255)] |
|
|
|
|
|
for i in range(8): |
|
|
color = colors[i] |
|
|
frame = Image.new('RGB', (224, 224), color) |
|
|
frames.append(frame) |
|
|
|
|
|
print(f"Created {len(frames)} test frames") |
|
|
|
|
|
|
|
|
frames = normalize_frames(frames) |
|
|
print(f"Normalized frames: {[f.size for f in frames[:3]]}...") |
|
|
|
|
|
|
|
|
tensor = create_timesformer_tensor(frames) |
|
|
print(f"Created tensor: {tensor.shape}") |
|
|
print(f"Tensor dtype: {tensor.dtype}") |
|
|
print(f"Value range: [{tensor.min():.3f}, {tensor.max():.3f}]") |
|
|
|
|
|
|
|
|
expected_shape = (1, 3, 1792, 224) |
|
|
if tensor.shape == expected_shape: |
|
|
print("β
Tensor shape is correct!") |
|
|
return True |
|
|
else: |
|
|
print(f"β Wrong tensor shape. Expected {expected_shape}, got {tensor.shape}") |
|
|
return False |
|
|
|
|
|
except Exception as e: |
|
|
print(f"β Tensor creation failed: {e}") |
|
|
import traceback |
|
|
traceback.print_exc() |
|
|
return False |
|
|
|
|
|
def main(): |
|
|
"""Run all tests.""" |
|
|
|
|
|
print("π Fixed Predictor Test Suite") |
|
|
print("=" * 60) |
|
|
|
|
|
|
|
|
tensor_ok = test_tensor_format() |
|
|
|
|
|
|
|
|
if tensor_ok: |
|
|
prediction_ok = test_predictor() |
|
|
else: |
|
|
print("\nβοΈ Skipping prediction test due to tensor issues") |
|
|
prediction_ok = False |
|
|
|
|
|
|
|
|
print("\nπ Test Results:") |
|
|
print(f" Tensor Creation: {'β
PASS' if tensor_ok else 'β FAIL'}") |
|
|
print(f" Full Pipeline: {'β
PASS' if prediction_ok else 'β FAIL'}") |
|
|
|
|
|
if tensor_ok and prediction_ok: |
|
|
print("\nπ All tests passed! The fixed predictor is working correctly.") |
|
|
print("\nThe system should now provide accurate predictions for real videos.") |
|
|
return 0 |
|
|
else: |
|
|
print("\nβ οΈ Some tests failed. Check the error messages above.") |
|
|
return 1 |
|
|
|
|
|
if __name__ == "__main__": |
|
|
exit(main()) |
|
|
|