Validate bitrate ceilings and recovery without requiring filler data
This commit is contained in:
1 parent
eeb3ca5927
commit
1376f9f059
1 file changed
+12
-2
@@ -10,7 +10,11 @@ import android.os.Bundle
|
|||||||
/** Запускается только явно через adb am instrument; камера и реальные звонки не затрагиваются. */
|
/** Запускается только явно через adb am instrument; камера и реальные звонки не затрагиваются. */
|
||||||
class CallVideoProbe : Instrumentation() {
|
class CallVideoProbe : Instrumentation() {
|
||||||
private var remote: String? = null
|
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() {
|
override fun onStart() {
|
||||||
try {
|
try {
|
||||||
val decoders = CallVideoCodec.probeDecoders()
|
val decoders = CallVideoCodec.probeDecoders()
|
||||||
@@ -28,7 +32,9 @@ class CallVideoProbe : Instrumentation() {
|
|||||||
}
|
}
|
||||||
val codecs = CallVideoCodec.probe()
|
val codecs = CallVideoCodec.probe()
|
||||||
check(codecs.isNotEmpty() && decoders.isNotEmpty()) { "No verified encoders or decoders" }
|
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) {
|
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)
|
val f = CallVideoFormat(1, 640, 480, codec = codec, level = entry.level, profile = entry.profile)
|
||||||
verifyRateChanges(f, entry.name)
|
verifyRateChanges(f, entry.name)
|
||||||
CallVideoCodec(f, 1_000_000, entry.name).use { encoder ->
|
CallVideoCodec(f, 1_000_000, entry.name).use { encoder ->
|
||||||
@@ -80,7 +86,11 @@ class CallVideoProbe : Instrumentation() {
|
|||||||
"elapsed_ms=${(System.nanoTime() - started) / 1_000_000}"
|
"elapsed_ms=${(System.nanoTime() - started) / 1_000_000}"
|
||||||
android.util.Log.i("CallVideoProbe", "rate check $result")
|
android.util.Log.i("CallVideoProbe", "rate check $result")
|
||||||
check(input == 120 && output == 120 && key) { "Incomplete 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"
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in new issue
Block a user