

# SDK di trasmissione IVS: Dispositivi misti
<a name="broadcast-mixed-devices"></a>

I dispositivi misti sono dispositivi audio e video che prendono più sorgenti di ingresso e generano una singola uscita. I dispositivi di mixaggio sono una potente funzionalità che consente di definire e gestire più elementi sullo schermo (video) e tracce audio. È possibile combinare video e audio da più sorgenti come fotocamere, microfoni, catture dello schermo e audio e video generati dall'app. È possibile utilizzare le transizioni per spostare queste sorgenti nel video trasmesso in streaming su IVS, nonché aggiungere e rimuovere sorgenti durante lo streaming.

I dispositivi misti sono disponibili nelle versioni audio e immagine. Per creare un dispositivo con immagini misto, chiamare:

`DeviceDiscovery.createMixedImageDevice()` su Android

`IVSDeviceDiscovery.createMixedImageDevice()` su iOS

Il dispositivo restituito può essere collegato a una `BroadcastSession` (streaming a bassa latenza) o `Stage` (streaming in tempo reale), come qualsiasi altro dispositivo.

## Terminologia
<a name="broadcast-mixed-devices-terminology"></a>

![\[Terminologia per i dispositivi misti per la trasmissione IVS.\]](http://docs.aws.amazon.com/it_it/ivs/latest/RealTimeUserGuide/images/Broadcast_SDK_Mixer_Glossary.png)



| Termine | Descrizione | 
| --- | --- | 
| Dispositivo | Un componente hardware o software che produce input audio o immagine. Esempi di dispositivi sono microfoni, fotocamere, cuffie Bluetooth e dispositivi virtuali come catture di schermo o ingressi di immagini personalizzate. | 
| Dispositivi misti | Un `Device` che può essere collegato a una `BroadcastSession` come qualsiasi altro `Device`, ma con API aggiuntive che consentono di aggiungere oggetti `Source`. I dispositivi misti dispongono di mixer interni che combinano audio o immagini, producendo un unico flusso di audio e immagini in uscita. I dispositivi misti sono disponibili nelle versioni audio e immagine.  | 
| Configurazione del dispositivo misto | Un oggetto di configurazione per il dispositivo misto. Per i dispositivi con immagini miste, questa opzione configura proprietà quali dimensioni e framerate. Per i dispositivi audio misti, configura il numero di canali. | 
|  Origine | Un container che definisce la posizione di un elemento visivo sullo schermo e le proprietà di una traccia audio nel mix audio. Un dispositivo misto può essere configurato con zero o più sorgenti. Alle sorgenti viene assegnata una configurazione che influisce sul modo in cui vengono utilizzati i contenuti multimediali della sorgente. L'immagine qui sopra mostra quattro sorgenti di immagini: [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/it_it/ivs/latest/RealTimeUserGuide/broadcast-mixed-devices.html)  | 
| Configurazione della sorgente |  Un oggetto di configurazione per la sorgente che entra in un dispositivo misto. Gli oggetti di configurazione completi sono descritti di seguito.   | 
| Transition | Per spostare uno slot in una nuova posizione o modificarne alcune proprietà, utilizza `MixedDevice.transitionToConfiguration()`. Questo metodo richiede: [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/it_it/ivs/latest/RealTimeUserGuide/broadcast-mixed-devices.html) | 

## Dispositivo audio misto
<a name="broadcast-mixed-audio-device"></a>

### Configurazione
<a name="broadcast-mixed-audio-device-configuration"></a>

`MixedAudioDeviceConfiguration` su Android

`IVSMixedAudioDeviceConfiguration` su iOS


| Name | Tipo | Descrizione | 
| --- | --- | --- | 
| `channels` | Numero intero | Numero di canali di output dal mixer audio. Valori validi: 1, 2. Il canale 1 è audio mono mentre il canale 2 è audio stereo. Default: 2 | 

### Configurazione della sorgente
<a name="broadcast-mixed-audio-device-source-configuration"></a>

`MixedAudioDeviceSourceConfiguration` su Android

`IVSMixedAudioDeviceSourceConfiguration` su iOS


| Name | Tipo | Descrizione | 
| --- | --- | --- | 
| `gain` | Float | Guadagno audio. Questo è un moltiplicatore, quindi qualsiasi valore maggiore di 1 aumenta il guadagno e qualsiasi valore minore di 1 lo diminuisce. Valori validi: 0-2. Default: 1.  | 

## Dispositivo di immagine
<a name="broadcast-mixed-image-device"></a>

### Configurazione
<a name="broadcast-mixed-image-device-configuration"></a>

`MixedImageDeviceConfiguration` su Android

`IVSMixedImageDeviceConfiguration` su iOS


| Name | Tipo | Descrizione | 
| --- | --- | --- | 
| `size` | Vec2 | Dimensioni della tela video. | 
| `targetFramerate` | Numero intero | Il numero di frame di destinazione al secondo per il dispositivo misto. In media questo valore dovrebbe essere raggiunto, ma il sistema potrebbe perdere frame in determinate circostanze (ad esempio, con carico elevato della CPU o della GPU). | 
| `transparencyEnabled` | Booleano | Ciò consente la fusione utilizzando la proprietà `alpha` sulle configurazioni delle sorgenti delle immagini. L'impostazione di questa opzione su `true` aumenta il consumo di memoria e CPU. Impostazione predefinita: `false`. | 

### Configurazione della sorgente
<a name="broadcast-mixed-image-device-source-configuration"></a>

`MixedImageDeviceSourceConfiguration` su Android

`IVSMixedImageDeviceSourceConfiguration` su iOS


| Name | Tipo | Descrizione | 
| --- | --- | --- | 
| `alpha` | Float | L'alfa dello slot. Questo è un fattore moltiplicativo con qualsiasi valore alfa nell'immagine. Valori validi: 0-1, dove 0 è completamente trasparente e 1 è completamente opaco. Default: 1. | 
| `aspect` | AspectMode | La modalità proporzioni per qualsiasi immagine renderizzata nello slot. Valori validi: [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/it_it/ivs/latest/RealTimeUserGuide/broadcast-mixed-devices.html) Impostazione predefinita: `Fit`  | 
| `fillColor` | Vec 4 | Il colore di riempimento da utilizzare con `aspect Fit` quando le proporzioni dello slot e dell'immagine non corrispondono. Il formato è (rosso, verde, blu, alfa). Valore valido (per ciascun canale): 0 - 1. Default: (0, 0, 0, 0). | 
| `position` | Vec2 | Posizione dello slot (in pixel) rispetto all'angolo superiore sinistro della tela. Anche l'origine dello slot è in alto a sinistra. | 
| `size` | Vec2 | Dimensioni dello slot, in pixel. L'impostazione di questo valore imposta anche `matchCanvasSize` su `false`. Default: (0, 0); tuttavia, perché `matchCanvasSize` di default è `true`, la dimensione renderizzata dello slot è la dimensione della tela, non (0, 0). | 
| `zIndex` | Float | Ordinamento relativo degli slot. Gli slot con valori `zIndex` più elevati sono disegnati sopra gli slot con valori `zIndex` minori. | 

## Creazione e configurazione di un dispositivo di immagini misto
<a name="broadcast-mixed-image-device-creating-configuring"></a>

![\[Configurazione di una sessione di tramissione per il mixaggio.\]](http://docs.aws.amazon.com/it_it/ivs/latest/RealTimeUserGuide/images/Broadcast_SDK_Mixer_Configuring.png)


Qui creiamo una scena simile a quella all'inizio di questa guida, con tre elementi sullo schermo:
+ Slot in basso a sinistra per una fotocamera.
+ Slot in basso a destra per una sovrapposizione del logo.
+ Slot in alto a destra per un filmato.

Nota che l'origine della tela è l'angolo in alto a sinistra e questa è la stessa per gli slot. Quindi, posizionando uno slot in (0, 0) sarà posizionato nell'angolo in alto a sinistra con l'intero slot visibile.

### iOS
<a name="broadcast-mixed-image-device-creating-configuring-ios"></a>

```
let deviceDiscovery = IVSDeviceDiscovery()
let mixedImageConfig = IVSMixedImageDeviceConfiguration()
mixedImageConfig.size = CGSize(width: 1280, height: 720)
try mixedImageConfig.setTargetFramerate(60)
mixedImageConfig.isTransparencyEnabled = true
let mixedImageDevice = deviceDiscovery.createMixedImageDevice(with: mixedImageConfig)

// Bottom Left
let cameraConfig = IVSMixedImageDeviceSourceConfiguration()
cameraConfig.size = CGSize(width: 320, height: 180)
cameraConfig.position = CGPoint(x: 20, y: mixedImageConfig.size.height - cameraConfig.size.height - 20)
cameraConfig.zIndex = 2
let camera = deviceDiscovery.listLocalDevices().first(where: { $0 is IVSCamera }) as? IVSCamera
let cameraSource = IVSMixedImageDeviceSource(configuration: cameraConfig, device: camera)
mixedImageDevice.add(cameraSource)

// Top Right
let streamConfig = IVSMixedImageDeviceSourceConfiguration()
streamConfig.size = CGSize(width: 640, height: 320)
streamConfig.position = CGPoint(x: mixedImageConfig.size.width - streamConfig.size.width - 20, y: 20)
streamConfig.zIndex = 1
let streamDevice = deviceDiscovery.createImageSource(withName: "stream")
let streamSource = IVSMixedImageDeviceSource(configuration: streamConfig, device: streamDevice)
mixedImageDevice.add(streamSource)

// Bottom Right
let logoConfig = IVSMixedImageDeviceSourceConfiguration()
logoConfig.size = CGSize(width: 320, height: 180)
logoConfig.position = CGPoint(x: mixedImageConfig.size.width - logoConfig.size.width - 20,
                              y: mixedImageConfig.size.height - logoConfig.size.height - 20)
logoConfig.zIndex = 3
let logoDevice = deviceDiscovery.createImageSource(withName: "logo")
let logoSource = IVSMixedImageDeviceSource(configuration: logoConfig, device: logoDevice)
mixedImageDevice.add(logoSource)
```

### Android
<a name="broadcast-mixed-image-device-creating-configuring-android"></a>

```
val deviceDiscovery = DeviceDiscovery(this /* context */)
val mixedImageConfig = MixedImageDeviceConfiguration().apply {
    setSize(BroadcastConfiguration.Vec2(1280f, 720f))
    setTargetFramerate(60)
    setEnableTransparency(true)
}
val mixedImageDevice = deviceDiscovery.createMixedImageDevice(mixedImageConfig)

// Bottom Left
val cameraConfig = MixedImageDeviceSourceConfiguration().apply {
    setSize(BroadcastConfiguration.Vec2(320f, 180f))
    setPosition(BroadcastConfiguration.Vec2(20f, mixedImageConfig.size.y - size.y - 20))
    setZIndex(2)
}
val camera = deviceDiscovery.listLocalDevices().firstNotNullOf { it as? CameraSource }
val cameraSource = MixedImageDeviceSource(cameraConfig, camera)
mixedImageDevice.addSource(cameraSource)

// Top Right
val streamConfig = MixedImageDeviceSourceConfiguration().apply {
    setSize(BroadcastConfiguration.Vec2(640f, 320f))
    setPosition(BroadcastConfiguration.Vec2(mixedImageConfig.size.x - size.x - 20, 20f))
    setZIndex(1)
}
val streamDevice = deviceDiscovery.createImageInputSource(streamConfig.size)
val streamSource = MixedImageDeviceSource(streamConfig, streamDevice)
mixedImageDevice.addSource(streamSource)

// Bottom Right
val logoConfig = MixedImageDeviceSourceConfiguration().apply {
    setSize(BroadcastConfiguration.Vec2(320f, 180f))
    setPosition(BroadcastConfiguration.Vec2(mixedImageConfig.size.x - size.x - 20, mixedImageConfig.size.y - size.y - 20))
    setZIndex(1)
}
val logoDevice = deviceDiscovery.createImageInputSource(logoConfig.size)
val logoSource = MixedImageDeviceSource(logoConfig, logoDevice)
mixedImageDevice.addSource(logoSource)
```

## Rimozione delle sorgenti
<a name="broadcast-mixed-devices-removing-sources"></a>

Per rimuovere una sorgente, chiamare `MixedDevice.remove` con l'oggetto di `Source` che desideri rimuovere.

## Animazioni con transizioni
<a name="broadcast-mixed-devices-animations-transitions"></a>

Il metodo di transizione sostituisce la configurazione di una sorgente con una nuova configurazione. Questa sostituzione può essere animata nel tempo impostando una durata superiore a 0, in secondi. 

### Quali proprietà possono essere animate?
<a name="broadcast-mixed-devices-animations-properties"></a>

Non tutte le proprietà nella struttura dello slot possono essere animate. Qualsiasi proprietà basata su tipi Float può essere animata; altre proprietà hanno effetto all'inizio o alla fine dell'animazione.


| Name | Può essere animato? | Punto d'impatto | 
| --- | --- | --- | 
| `Audio.gain` | Sì | Interpolato | 
| `Image.alpha` | Sì | Interpolato | 
| `Image.aspect` | No | End | 
| `Image.fillColor` | Sì | Interpolato | 
| `Image.position` | Sì | Interpolato | 
| `Image.size` | Sì | Interpolato | 
| `Image.zIndex` Nota: `zIndex` sposta i piani 2D attraverso lo spazio 3D, quindi la transizione avviene quando i due piani si incrociano in un certo punto al centro dell'animazione. Questo potrebbe essere calcolato, ma dipende dai valori di `zIndex` di inizio e di fine. Per una transizione più fluida, combinalo con `alpha`.  | Sì | Sconosciuto | 

### Esempi semplici
<a name="broadcast-mixed-devices-animations-examples"></a>

Di seguito sono riportati esempi di acquisizione di una fotocamera a schermo intero utilizzando la configurazione definita in alto in [Creazione e configurazione di un dispositivo di immagini misto](#broadcast-mixed-image-device-creating-configuring). Questo è animato per 0,5 secondi.

#### iOS
<a name="broadcast-mixed-devices-animations-examples-ios"></a>

```
// Continuing the example from above, modifying the existing cameraConfig object.
cameraConfig.size = CGSize(width: 1280, height: 720)
cameraConfig.position = CGPoint.zero
cameraSource.transition(to: cameraConfig, duration: 0.5) { completed in
    if completed {
        print("Animation completed")
    } else {
        print("Animation interrupted")
    }
}
```

#### Android
<a name="broadcast-mixed-devices-animations-examples-android"></a>

```
// Continuing the example from above, modifying the existing cameraConfig object.
cameraConfig.setSize(BroadcastConfiguration.Vec2(1280f, 720f))
cameraConfig.setPosition(BroadcastConfiguration.Vec2(0f, 0f))
cameraSource.transitionToConfiguration(cameraConfig, 500) { completed ->
    if (completed) {
        print("Animation completed")
    } else {
        print("Animation interrupted")
    }
}
```

## Mirroring della trasmissione
<a name="broadcast-mixed-devices-mirroring"></a>


| Per eseguire il mirroring di un dispositivo immagine collegato nella trasmissione in questa direzione... | Usa un valore negativo per... | 
| --- | --- | 
| Orizzontalmente | La larghezza dello slot | 
| Verticalmente | L’altezza dello slot | 
| Sia orizzontalmente che verticalmente | Larghezza e altezza dello slot | 

La posizione dovrà essere regolata dello stesso valore per mettere lo slot nella posizione corretta quando viene eseguito il mirroring.

Di seguito sono riportati alcuni esempi di mirroring della trasmissione in orizzontale e in verticale.

### iOS
<a name="broadcast-mixed-devices-mirroring-ios"></a>

Mirroring orizzontale:

```
let cameraSource = IVSMixedImageDeviceSourceConfiguration()
cameraSource.size = CGSize(width: -320, height: 720)
// Add 320 to position x since our width is -320
cameraSource.position = CGPoint(x: 320, y: 0)
```

Mirroring verticale:

```
let cameraSource = IVSMixedImageDeviceSourceConfiguration()
cameraSource.size = CGSize(width: 320, height: -720)
// Add 720 to position y since our height is -720
cameraSource.position = CGPoint(x: 0, y: 720)
```

### Android
<a name="broadcast-mixed-devices-mirroring-android"></a>

Mirroring orizzontale:

```
val cameraConfig = MixedImageDeviceSourceConfiguration().apply {
    setSize(BroadcastConfiguration.Vec2(-320f, 180f))
   // Add 320f to position x since our width is -320f
    setPosition(BroadcastConfiguration.Vec2(320f, 0f))
}
```

Mirroring verticale:

```
val cameraConfig = MixedImageDeviceSourceConfiguration().apply {
    setSize(BroadcastConfiguration.Vec2(320f, -180f))
    // Add 180f to position y since our height is -180f
    setPosition(BroadcastConfiguration.Vec2(0f, 180f))
}
```

Nota: questo mirroring è diverso dal metodo `setMirrored` su `ImagePreviewView` (Android) e `IVSImagePreviewView` (iOS). Questo metodo influisce solo sulla visualizzazione dell'anteprima locale sul dispositivo e non ha alcun impatto sulla trasmissione.