diff --git a/tools/chatgui-android/app/src/debug/java/com/utun/chat/data/CallVideoProbe.kt b/tools/chatgui-android/app/src/debug/java/com/utun/chat/data/CallVideoProbe.kt index fc5c4e56..65f7f570 100644 --- a/tools/chatgui-android/app/src/debug/java/com/utun/chat/data/CallVideoProbe.kt +++ b/tools/chatgui-android/app/src/debug/java/com/utun/chat/data/CallVideoProbe.kt @@ -10,7 +10,11 @@ import android.os.Bundle /** Запускается только явно через adb am instrument; камера и реальные звонки не затрагиваются. */ class CallVideoProbe : Instrumentation() { private var remote: String? = null - override fun onCreate(arguments: Bundle?) { remote = arguments?.getString("remote"); super.onCreate(arguments); start() } + private var selectedCodec = 0 + override fun onCreate(arguments: Bundle?) { + remote = arguments?.getString("remote"); selectedCodec = arguments?.getString("codec")?.toIntOrNull() ?: 0 + super.onCreate(arguments); start() + } override fun onStart() { try { val decoders = CallVideoCodec.probeDecoders() @@ -28,7 +32,9 @@ class CallVideoProbe : Instrumentation() { } val codecs = CallVideoCodec.probe() check(codecs.isNotEmpty() && decoders.isNotEmpty()) { "No verified encoders or decoders" } + check(selectedCodec == 0 || selectedCodec in codecs) { "Requested codec unavailable: $selectedCodec" } for ((codec, entry) in codecs) { + if (selectedCodec != 0 && selectedCodec != codec) continue val f = CallVideoFormat(1, 640, 480, codec = codec, level = entry.level, profile = entry.profile) verifyRateChanges(f, entry.name) CallVideoCodec(f, 1_000_000, entry.name).use { encoder -> @@ -80,7 +86,11 @@ class CallVideoProbe : Instrumentation() { "elapsed_ms=${(System.nanoTime() - started) / 1_000_000}" android.util.Log.i("CallVideoProbe", "rate check $result") check(input == 120 && output == 120 && key) { "Incomplete rate check: $result" } - check(measured > rate / 2 && measured < rate.toLong() * 3 / 2) { "Bitrate change ineffective: $result" } + // При сильной квантизации шум исчезает: low-rate кадр может занять меньше целевой полосы. + // Игнорирование команды ловит верхний предел, возврат к 4M — нижний предел high-rate фаз. + check(measured > 0 && measured < rate.toLong() * 3 / 2 && (rate == 300_000 || measured > rate / 2)) { + "Bitrate change ineffective: $result" + } } } }