2016-03-18 13 views
5

Ho un progetto UWP e voglio utilizzare l'API Windows.Media.Audio per riprodurre un file. Invece di usare FileInputNode, voglio eseguire il flusso del mio file in modo da poter determinare con precisione varie proprietà di temporizzazione.Decodifica audio utilizzando MediaStreamSource

Ho trovato l'API MediaStreamSource e reso il seguente codice nel tentativo di decodificare un canale 16 bit PCM 2 file wav

public async Task<Windows.Storage.Streams.Buffer> GetBuffer() 
    { 
     // check if the sample requested byte offset is within the file size 

     if (byteOffset + BufferSize <= mssStream.Size) 
     { 
      inputStream = mssStream.GetInputStreamAt(byteOffset); 

      // create the MediaStreamSample and assign to the request object. 
      // You could also create the MediaStreamSample using createFromBuffer(...) 

      MediaStreamSample sample = await MediaStreamSample.CreateFromStreamAsync(inputStream, BufferSize, timeOffset); 
      sample.Duration = sampleDuration; 
      sample.KeyFrame = true; 
      // increment the time and byte offset 

      byteOffset += BufferSize; 
      timeOffset = timeOffset.Add(sampleDuration); 


      return sample.Buffer; 
     } 
     else 
     { 

      return null; 
     } 
    } 

Invece di utilizzare il sistema di evento, feci un metodo che viene generato ogni volta my AudioFrameInputNode richiede un nuovo AudioFrame.

Ora sembra che la matrice di byte risultante in MediaStreamSample sia esattamente la stessa di quando ho semplicemente letto il mio StorageFile utilizzando un DataReader.

MediaStreamSample.CreateFromStreamAsync decodifica effettivamente l'audiofile in un array di byte float? Oppure questo è fatto in MediaElement quando riproduce l'esempio?

E se sì, come posso decodificare un audiofilo in modo che possa restituire l'AudioBuffer risultante al mio FrameInputNode?

risposta

1

Quando MediaStreamSample.CreateFromStreamAsync viene completato, restituisce il nuovo file come MediaStreamSample.

Se ho capito cosa vuoi, ecco un esempio di cosa puoi fare per realizzarlo.

function sampleRequestedHandler(e) { 
    var request = e.request; 
    if (!MyCustomFormatParser.IsAtEndOfStream(randomAccessStream)) { 
     var deferral = request.getDeferral(); 
     var inputStream = MyCustomFormatParser.getInputStream(randomAccessStream); 
     MediaStreamSample.createFromStreamAsync(inputStream, sampleSize, timeOffset). 
      then(function(sample) { 
       sample.duration = sampleDuration; 
       sample.keyFrame = true; 
       request.sample = sample;   
       deferral.complete(); 
      }); 
     } 
} 

Quando viene richiesto di esempio, il parser personalizzato estrae i dati audio da RandomAccessStream e restituisce un InputStream di soli campioni audio