Visión general

Actualizado

El Camo SDK de Reincubate brinda la capacidad de enviar datos audiovisuales en tiempo real desde su aplicación a Camo Studio en macOS y Windows. Funciona a través de USB y está optimizado para baja latencia y rendimiento; consumiendo la menor cantidad posible de recursos en su aplicación.

Actualmente, el SDK solo admite aplicaciones de iOS que se ejecutan en un dispositivo físico iOS o iPadOS (excluyendo simuladores y Mac Catalyst) en iOS 12 o superior. Camo SDK no tiene compatibilidad con Objective-C de fábrica, por lo que si su aplicación es principalmente Objective-C, es posible que deba crear un contenedor.


Referencia de API

Si desea saltar directamente, puede ver la referencia completa de la API , que documenta todos los símbolos proporcionados por Camo SDK. De lo contrario, este documento lo guiará a través de una integración de muestra con el SDK.


Instalación de Camo SDK

When you receive the Camo SDK, you will have received a file called CamoProducerKit.xcframework. This self-contained framework has everything you need with no external dependencies, so installation is easy.

  1. Seleccione el proyecto de su aplicación en el Navegador de proyectos.
  2. Elija el destino de su aplicación en la barra lateral de destino del proyecto. Si no ve una barra lateral, es posible que esté en un menú desplegable en la parte superior de la página.
  3. Asegúrese de estar en la pestaña 'General' y desplácese hacia abajo hasta el encabezado "Marcos, bibliotecas y contenido incrustado".
  4. Arrastre el CamoProducerKit.xcframework y suéltelo en la lista de archivos debajo de ese encabezado.
  5. Asegúrese de que el SDK esté configurado en "Insertar y firmar".

Cuando haya terminado, debería ver el marco como se muestra en la imagen:

Integrarse con su aplicación

Controlando el servicio de Camo

En el núcleo de CamoProducerKit se encuentra CamoController , que proporciona a su aplicación una interfaz centralizada para controlar el Camo SDK.

En su aplicación, debe inicializar una instancia de CamoController . Puede optar por hacer esto al iniciar la aplicación o guardarlo para más tarde. Hasta que se inicie explícitamente con start() , el controlador Camo utilizará muy pocos recursos. Sin embargo, se preparará para la codificación de audio y video tras la inicialización.

import CamoProducerKit

class MyVideoManager {
    let controller = CamoController()

    // ...
}

Cuando desee activar la integración de Camo en su aplicación, iniciando el servicio Camo para facilitar las conexiones, puede llamar al start() . Una vez que haya terminado, puede detenerlo llamando a stop() .

controller.start()
// ...
controller.stop()

Este código es un comienzo, pero aún no puede aceptar nuevas conexiones de Camo Studio.

Respondiendo a nuevas conexiones

Antes de que su aplicación pueda aceptar nuevas conexiones de Camo Studio, deberá implementar CamoControllerDelegate . Al implementar estos dos métodos delegados, puede recibir notificaciones sobre cambios en el estado de la conexión y decidir si acepta o rechaza una conexión.

extension MyVideoManager: CamoControllerDelegate {
    // Upon receiving a connection request, you can decide whether or not to accept it.
    func camoControllerShouldAcceptIncomingConnection(_ controller: CamoController) -> Bool {
        // You could return false if you aren't ready to accept connections, such as during onboarding.
        return true
    }

    // Called whenever the connection state changes, such as if the Camo service starts or stops, or if a new connection is made.
    func camoController(_ controller: CamoController, stateDidChangeTo state: CamoControllerState?) {
        // From here, you can update your UI and other state
        print("New state:", state)
    }
}

Una vez hecho esto, ahora debería poder abrir su aplicación, conectarse a USB y ver su dispositivo en Camo Studio.

Determinar el estado de la conexión

CamoController proporciona una propiedad CamoControllerState , que también se incluye en el método de delegado de cambio de estado como se ve arriba. Esta enumeración proporciona información útil para su aplicación, como el nombre de la computadora conectada para mostrar en la interfaz de usuario.

A continuación, se muestra un ejemplo de cómo podría actualizar su interfaz de usuario para reflejar el estado de la conexión:

func camoController(_ controller: CamoController, stateDidChangeTo state: CamoControllerState?) {
    let statusText = { () -> String in
        guard case let .running(serviceState) = state else {
            return "Camo service not running"
        }
        switch serviceState {
        case .active(let connection): return "Connected to \(connection.name)"
        case .paused(let connection): return "Paused, but connected to \(connection.name)"
        case .notConnected: return "Camo service running, but no connection"
        }
    }()

    DispatchQueue.main.async {
        self.statusTextLabel.text = statusText
    }
}

Envío de datos audiovisuales

Para permitir a los clientes la mayor flexibilidad posible, Camo SDK no proporciona ni controla ninguna captura. En cambio, usted es responsable de proporcionar al CamoController datos de audio y video. Esto se puede hacer con dos simples llamadas a la API:

// upon receiving video from the camera or elsewhere
camoController.enqueueVideo(sampleBuffer: sampleBuffer)

// upon receiving audio from the microphone or elsewhere
camoController.enqueuePCMAudio(data: chunk)

Enviando video

Si tiene acceso a un CMSampleBuffer en su canal de video, es trivial pasar estos datos al Camo SDK.

Debido a esto, configurar esto con un AVCaptureSession de video básico es extremadamente simple. Aquí hay un ejemplo de eso en acción.

class CaptureController: AVCaptureVideoDataOutputSampleBufferDelegate {
    // ...

    func startSession() throws {
        guard let camera = AVCaptureDevice.default(for: .video) else { fatalError("No camera found") }

        let input = try AVCaptureDeviceInput(device: camera)
        captureSession.addInput(input)

        let output = AVCaptureVideoDataOutput()
        output.alwaysDiscardsLateVideoFrames = true
        output.setSampleBufferDelegate(self, queue: videoDataOutputQueue)
        captureSession.addOutput(output)

        captureSession.startRunning()
    }

    // ...

    func captureOutput(_ output: AVCaptureOutput, didOutput sampleBuffer: CMSampleBuffer, from connection: AVCaptureConnection) {
        camoController.enqueueVideo(sampleBuffer: sampleBuffer)
    }
}

Al enviar fotogramas de video, asegúrese de que:

  • La duración del cuadro es de 30 FPS.
  • El formato de píxel es kCVPixelFormatType_32BGRA .

Puede ver más detalles en la referencia de API .

Envío de audio

Enviar audio es similar al video, pero puede requerir algunos pasos más dependiendo de cómo lo reciba su aplicación. Para ver una implementación de muestra, consulte la aplicación de demostración incluida con Camo SDK.

Al enviar datos de audio, asegúrese de que:

  • Su frecuencia de muestreo es de 48 kHz.
  • El códec de audio es LPCM.
  • El número de canales es 2.
  • La profundidad de bits es 32.
  • La cantidad de muestras por paquete de audio depende de Studio (macOS o Windows), puede obtenerla de CamoController.audioSamplesRequired .

Puede ver más detalles en la referencia de API .

¿Cómo podemos ayudar?

¡Nuestro equipo de soporte está aquí para ayudar!

Nuestro horario de atención es de lunes a viernes de 9 a.m. a 5 p.m. GMT. El tiempo es actualmente 4:35 AM GMT.

Intentamos responder todos los mensajes en un plazo de un día laboral.

Nuestro increíble equipo de soporte.

Unete a la communidad

¡Únase a una comunidad centrada en conectar a nuestros usuarios! La comunidad de Camo ofrecerá foros de discusión y soporte, transmisiones de video, juegos, obsequios y más a medida que crecemos.

Regístrese aquí para recibir las últimas actualizaciones sobre nuestros próximos eventos.

© 2008 - 2021 Reincubate Ltd. Todos los derechos reservados. Registrado en Inglaterra y Gales #5189175, VAT GB151788978. Reincubate® y Camo® son marcas registradas. Política de privacidad & condiciones. Construido con en Londres.