El hilo de background de iOS se ralentiza cuando la interfaz de usuario está inactiva

Un poco de context primero

Tengo una aplicación Xamarin que esencialmente transmite video desde un server remoto. Tengo un hilo de background que hace loops como este (pseudo-código):

private void UpdateMethod() { while (running) { bool success = WaitForUpdate(); if (!success) { break; } Update update = GetUpdate(); SendUpdateToConcurentQueue(update); } Disconnect(); } 

Comienzo el hilo de background de esta manera:

 Thread thread = new Thread(UpdateMethod); thread.IsBackground = true; thread.Start(); 

La cuestión

Cuando comienzo la transmisión, todo es perfecto. Es solo después de 10 segundos de no interactuar con el dispositivo que se vuelve realmente lento. He publicado el número de actualizaciones desde el subprocess de background, y parecen venir mucho más lento. Normalmente obtengo alnetworkingedor de 2 a 6 actualizaciones para procesar por actualización (60 fps). Cuando es súper lento, obtengo 1 ciclo de actualización de 6 veces.

Una cosa que me desconcierta: cuando abro el menu de la barra superior de iOS, las actualizaciones vuelven a upload y la transmisión vuelve a la velocidad normal. La tasa de actualización aumenta durante ~ 10 segundos y vuelve a quedar rezagada como una locura.

Lo que he probado

Intenté iniciar una queue de envío con solo esto, así:

 DispatchQueue queue = new DispatchQueue("updateQueue"); queue.DispatchAsync(this.UpdateProcess); 

No pareció ayudar en absoluto.

También traté de cambiar la propiedad QualityOfService en mi hilo de actualización así:

 NSThread.Current.QualityOfService = NSQualityOfService.UserInitiated 

¡Tampoco funciona! Me parece que iOS networkinguce la prioridad de mi hilo por alguna razón. Si pongo un punto de interrupción en mi método UpdateMethod , se está UpdateMethod cuando la aplicación no se retrasa. Pero cuando hay retraso, el punto de interrupción no recibe un golpe. ¡Ahora esto realmente me desconcierta, ya que el código sigue funcionando! Todavía recibo las actualizaciones, es mucho más lento …

Edit: Probé usando Instruments y descubrí que la networking está siendo estrangulada … Investigando, pero si alguien tiene conocimiento de algún tipo de aceleración de networking en iOS, avíseme.

Intente configurar IdleTimerDisabled en true , lo hacemos todo el time en los juegos de iOS para evitar que iOS deje inactivos nuestros juegos.

Nota: Hacemos esto de una polite way solo cuando el usuario no está tocando la pantalla debido a una repetición de reproducción, segues multimedia que cambian de nivel, etc.

Nota: asegúrese de restablecer el ralentí cuando no lo necesite (cuando la aplicación se encuentra en segundo plano, etc.), como si matara la batería y los usuarios se sintieran abalanzados sobre su aplicación ante el verdadero asesino: Apple Rechazos de tiendas

Apple: información del timer de inactividad de la aplicación

Xamarin: propiedad UIKit.UIApplication.IdleTimerDisabled

El valor pnetworkingeterminado de esta propiedad es NO. Cuando la mayoría de las aplicaciones no tienen toques como la input del usuario por un período corto, el sistema coloca el dispositivo en un estado de "suspensión" donde la pantalla se atenúa. Esto se hace con el propósito de conservar energía. Sin embargo, las aplicaciones que no tienen input de usuario excepto por los acelerómetros -juegos, por ejemplo, pueden, al establecer esta propiedad en SÍ, deshabilitar el "timer inactivo" para evitar el reposo del sistema.

| IMPORTANTE

Debe establecer esta propiedad solo si es necesario y debe asegurarse de reiniciarlo en NO cuando la necesidad ya no exista. La mayoría de las aplicaciones deben permitir que el sistema apague la pantalla cuando transcurra el time de inactividad. Esto incluye aplicaciones de audio. Con el uso apropiado de los services de session de audio, la reproducción y la grabación se realizan de forma ininterrumpida cuando la pantalla se apaga. Las únicas aplicaciones que deberían desactivar el timer inactivo son las aplicaciones, juegos o progtwigs de asignación de maps en los que la aplicación necesita continuar mostrando contenido cuando la interacción del usuario es mínima.