Skip to main content
Una API asincrónica es una API que se devuelve rápidamente pero inicia una tarea asincrónica, y el resultado se devuelve cuando la tarea finaliza. Tradicionalmente, los juegos han tenido poco control sobre qué subproceso ejecuta la tarea asincrónica y qué subproceso devuelve los resultados al usar una devolución de llamada de finalización. Algunos juegos están diseñados de modo que una sección del montón (heap) solo la toca un único subproceso para evitar cualquier necesidad de sincronización de subprocesos. Si la devolución de llamada de finalización no se llama desde un subproceso que el juego controla, actualizar el estado compartido con el resultado de una tarea asincrónica requerirá sincronización de subprocesos. La API de C de XSAPI expone una nueva API de C asincrónica que ofrece a los desarrolladores control directo de los subprocesos al realizar una llamada a una API asincrónica, como XblSocialGetSocialRelationshipsAsync(), XblProfileGetUserProfileAsync() y XblAchievementsGetAchievementsForTitleIdAsync(). Este es un ejemplo básico de llamada a la API XblProfileGetUserProfileAsync:
Para comprender este patrón de llamada, necesitará comprender cómo usar el XAsyncBlock y el XTaskQueueHandle.
  • El XAsyncBlock contiene toda la información relativa a la tarea asincrónica y a la devolución de llamada de finalización.
  • El XTaskQueueHandle le permite determinar qué subproceso ejecuta la tarea asincrónica y qué subproceso llama a la devolución de llamada de finalización del XAsyncBlock.

El XAsyncBlock

Veamos en detalle el XAsyncBlock. Es una estructura definida de la siguiente manera:
El XAsyncBlock contiene:
  • queue: un XTaskQueueHandle, que es un identificador que representa información sobre dónde ejecutar un fragmento de trabajo. Si no se establece, se usará una cola predeterminada.
  • context: le permite pasar datos a la función de devolución de llamada.
  • callback: una función de devolución de llamada opcional a la que se llamará una vez realizado el trabajo asincrónico. Si no especifica una devolución de llamada, puede esperar a que el XAsyncBlock se complete con XAsyncGetStatus y, a continuación, obtener los resultados.
Debería crear un nuevo XAsyncBlock en el montón por cada API asincrónica a la que llame. El XAsyncBlock debe existir hasta que se llame a la devolución de llamada de finalización del XAsyncBlock y, a continuación, puede eliminarse.
Importante: Un XAsyncBlock debe permanecer en memoria hasta que se complete la tarea asincrónica. Si se asigna dinámicamente, puede eliminarse dentro de la devolución de llamada de finalización del XAsyncBlock.

Esperar a una tarea asincrónica

Puede saber que una tarea asincrónica se ha completado de varias maneras diferentes:
  • Se llama a la devolución de llamada de finalización del XAsyncBlock.
  • Llame a XAsyncGetStatus con true para esperar hasta que se complete.
Con XAsyncGetStatus, la tarea asincrónica se considera completa después de que se ejecute la devolución de llamada de finalización del XAsyncBlock; sin embargo, la devolución de llamada de finalización del XAsyncBlock es opcional. Una vez completada la tarea asincrónica, puede obtener los resultados.

Obtener el resultado de la tarea asincrónica

Para obtener el resultado, la mayoría de las funciones de API asincrónicas tienen una función [Nombre de la función]Result correspondiente para recibir el resultado de la llamada asincrónica. En nuestro código de ejemplo, XblProfileGetUserProfileAsync tiene una función XblProfileGetUserProfileResult correspondiente. Puede usar esta función para recuperar el resultado de la función y actuar en consecuencia. Para obtener todos los detalles sobre la recuperación de resultados, consulte la documentación de cada función de API asincrónica.

El XTaskQueueHandle

El XTaskQueueHandle le permite determinar qué subproceso ejecuta la tarea asincrónica y qué subproceso llama a la devolución de llamada de finalización del XAsyncBlock. Puede controlar qué subproceso realiza estas operaciones estableciendo un modo de distribución. Hay tres modos de distribución disponibles:
  • Manual: las colas manuales no se distribuyen automáticamente. Corresponde al desarrollador distribuirlas en el subproceso que desee. Esto puede usarse para asignar el lado del trabajo o el de la devolución de llamada de una llamada asincrónica a un subproceso específico. Esto se analiza con más detalle a continuación.
  • Grupo de subprocesos: distribuye mediante un grupo de subprocesos. El grupo de subprocesos invoca las llamadas en paralelo, tomando por turno una llamada de la cola para ejecutarla a medida que los subprocesos del grupo quedan disponibles. Es el más fácil de usar, pero le da la menor cantidad de control sobre qué subproceso se usa.
  • Grupo de subprocesos serializado: distribuye mediante un grupo de subprocesos. El grupo de subprocesos invoca las llamadas en serie, tomando por turno una llamada de la cola para ejecutarla a medida que el único subproceso del grupo queda disponible.
  • Inmediato: distribuye inmediatamente el trabajo en cola en el subproceso desde el que se envió.
Para crear un nuevo XTaskQueueHandle, deberá llamar a XTaskQueueCreate. Por ejemplo:
Esta función toma dos parámetros XTaskQueueDispatchMode. Hay tres valores posibles para XTaskQueueDispatchMode:
workDispatchMode determina el modo de distribución del subproceso que gestiona el trabajo asincrónico, mientras que completionDispatchMode determina el modo de distribución del subproceso que gestiona la finalización de la operación asincrónica. Una vez creado su XTaskQueueHandle, simplemente agréguelo al XAsyncBlock para controlar los subprocesos de sus funciones de trabajo y de finalización. Cuando termine de usar el XTaskQueueHandle, normalmente cuando el juego está finalizando, puede cerrarlo con XTaskQueueCloseHandle:
Ejemplo de llamada:

Distribuir manualmente un XTaskQueueHandle

Si usó el modo de distribución de cola manual para la cola de trabajo o de finalización de un XTaskQueueHandle, tendrá que distribuir manualmente. Supongamos que se creó un XTaskQueueHandle en el que tanto la cola de trabajo como la cola de finalización están configuradas para distribuirse manualmente, de esta manera:
Para distribuir el trabajo al que se le ha asignado XTaskQueueDispatchMode::Manual, tendrá que distribuirlo con la función XTaskQueueDispatch.
Ejemplo de llamada
  • queue: la cola en la que se distribuye el trabajo.
  • port: una instancia de la enumeración XTaskQueuePort.
  • timeoutInMs: un uint32_t para el tiempo de espera en milisegundos.
Hay dos tipos de devolución de llamada definidos por la enumeración XTaskQueuePort:

Cuándo llamar a XTaskQueueDispatch

Para comprobar cuándo la cola ha recibido un nuevo elemento, puede llamar a XTaskQueueRegisterMonitor para establecer un controlador de eventos que informe a su código de que hay trabajo o finalizaciones listos para ser distribuidos.
XTaskQueueRegisterMonitor toma los siguientes parámetros:
  • queue: la cola asincrónica para la que envía la devolución de llamada.
  • callbackContext: un puntero a los datos que deben pasarse a la devolución de llamada de envío.
  • callback: la función que se invocará cuando se envíe una nueva devolución de llamada a la cola.
  • token: un token que se usará en una llamada posterior a XTaskQueueUnregisterMonitor para quitar la devolución de llamada.
Por ejemplo, esta es una llamada a XTaskQueueRegisterMonitor: XTaskQueueRegisterMonitor(queue, nullptr, HandleAsyncQueueCallback, &m_callbackToken); La devolución de llamada XTaskQueueMonitorCallback correspondiente podría implementarse de la siguiente manera:
Después, en un subproceso en segundo plano, puede escuchar esta variable de condición para reactivarse y llamar a XTaskQueueDispatch.

Consulte también

Introducción a las API de C de XSAPI Referencia de XSAPI libHttpClient
Última modificación el 28 de agosto de 2026