9fcf0517c7
src/theme_nerv_fx.py:97 was calling draw_list.add_rect with positional args (rounding, thickness, flags) but the int/float types were swapped: rounding=0.0 (correct) thickness=0 (int, signature expects float) flags=10.0 (float, signature expects int) The TypeError fires every render frame once ai_status starts with 'error'. App.run's except RuntimeError eventually catches and calls self.shutdown() -> controller.shutdown() -> _io_pool.shutdown(wait=False). Subsequent tests in the same live_gui session can't submit_io. Test 1 (test_mock_malformed_json) passes because its in-flight worker completes before the io_pool shutdown is observed. Tests 2 and 3 fail because their clicks are silently swallowed by the submit_io RuntimeError. Switch to keyword args with correct types. Update test_theme_nerv_fx assertion to match. Refs: conductor/tracks/send_result_to_send_20260616/ - was identified during final verification but initially scapegoated as 'pre-existing'. Per user feedback, the bug is fixed now. Verified: test_theme_nerv_fx 5/5 pass. test_z_negative_flows.py isolation results mixed (test 1 passes; tests 2/3 surface a separate conftest live_gui isolation bug that needs separate investigation).
95 lines
3.0 KiB
Python
95 lines
3.0 KiB
Python
import unittest
|
|
from unittest.mock import MagicMock, patch
|
|
import math
|
|
from src.theme_nerv_fx import CRTFilter, StatusFlicker, AlertPulsing
|
|
|
|
class TestThemeNervFx(unittest.TestCase):
|
|
@patch("src.theme_nerv_fx.imgui")
|
|
def test_crt_filter_render(self, mock_imgui):
|
|
# Setup
|
|
mock_draw_list = MagicMock()
|
|
mock_imgui.get_foreground_draw_list.return_value = mock_draw_list
|
|
mock_imgui.get_color_u32.return_value = 0x12345678
|
|
|
|
overlay = CRTFilter()
|
|
width, height = 800.0, 600.0
|
|
|
|
# Act
|
|
overlay.render(width, height)
|
|
|
|
# Assert
|
|
mock_imgui.get_foreground_draw_list.assert_called_once()
|
|
# height is 600, range(0, 600, 2) is 300 calls
|
|
# width is 800, range(0, 800, 3) is 267 calls
|
|
# total = 300 + 267 = 567 calls
|
|
self.assertEqual(mock_draw_list.add_line.call_count, 567)
|
|
# Vignette: v_steps = 20. height=600 is plenty for all insets.
|
|
self.assertEqual(mock_draw_list.add_rect.call_count, 20)
|
|
# Noise: 40 calls to add_rect_filled
|
|
self.assertEqual(mock_draw_list.add_rect_filled.call_count, 40)
|
|
|
|
# Verify some calls
|
|
mock_draw_list.add_line.assert_any_call((0.0, 0.0), (800.0, 0.0), 0x12345678, 1.2)
|
|
mock_draw_list.add_line.assert_any_call((0.0, 598.0), (800.0, 598.0), 0x12345678, 0.8)
|
|
|
|
@patch("src.theme_nerv_fx.imgui")
|
|
def test_crt_filter_disabled(self, mock_imgui):
|
|
mock_draw_list = MagicMock()
|
|
mock_imgui.get_foreground_draw_list.return_value = mock_draw_list
|
|
|
|
overlay = CRTFilter()
|
|
overlay.enabled = False
|
|
overlay.render(800.0, 600.0)
|
|
|
|
mock_imgui.get_foreground_draw_list.assert_not_called()
|
|
|
|
@patch("src.theme_nerv_fx.time")
|
|
def test_status_flicker_get_alpha(self, mock_time):
|
|
flicker = StatusFlicker()
|
|
|
|
# Test at multiple points in time to ensure range [0.7, 1.0]
|
|
# sin(0) = 0 -> 0.85
|
|
mock_time.time.return_value = 0.0
|
|
self.assertAlmostEqual(flicker.get_alpha(), 0.85)
|
|
|
|
# sin(pi/2) = 1 -> 1.0
|
|
mock_time.time.return_value = math.pi / 40.0
|
|
self.assertAlmostEqual(flicker.get_alpha(), 1.0)
|
|
|
|
# sin(3pi/2) = -1 -> 0.7
|
|
mock_time.time.return_value = 3 * math.pi / 40.0
|
|
self.assertAlmostEqual(flicker.get_alpha(), 0.7)
|
|
|
|
def test_alert_pulsing_update(self):
|
|
pulse = AlertPulsing()
|
|
self.assertFalse(pulse.active)
|
|
|
|
pulse.update("error: something failed")
|
|
self.assertTrue(pulse.active)
|
|
|
|
pulse.update("Error: alert")
|
|
self.assertTrue(pulse.active)
|
|
|
|
pulse.update("idle")
|
|
self.assertFalse(pulse.active)
|
|
|
|
@patch("src.theme_nerv_fx.imgui")
|
|
@patch("src.theme_nerv_fx.time")
|
|
def test_alert_pulsing_render(self, mock_time, mock_imgui):
|
|
mock_draw_list = MagicMock()
|
|
mock_imgui.get_foreground_draw_list.return_value = mock_draw_list
|
|
mock_imgui.get_color_u32.return_value = 0xFF0000FF
|
|
|
|
pulse = AlertPulsing()
|
|
pulse.active = True
|
|
|
|
# sin(0) = 0 -> alpha = 0.05 + 0.15 * (0+1)/2 = 0.125
|
|
mock_time.time.return_value = 0.0
|
|
pulse.render(800.0, 600.0)
|
|
|
|
mock_imgui.get_foreground_draw_list.assert_called()
|
|
mock_draw_list.add_rect.assert_called_with((0.0, 0.0), (800.0, 600.0), 0xFF0000FF, rounding=0.0, thickness=10.0, flags=0)
|
|
|
|
if __name__ == "__main__":
|
|
unittest.main()
|