2015-07-29 15 views
9

Ich spiele HLS-Streams mit AVPlayer. Und ich muss diese Streams auch aufnehmen, wenn der Benutzer die Aufnahmetaste drückt. Der Ansatz, den ich verwende, besteht darin, Audio und Video getrennt aufzuzeichnen, und am Ende diese Dateien zusammenzuführen, um das endgültige Video zu erstellen. Und es ist erfolgreich mit Remote-MP4-Dateien.Extrahieren/Aufzeichnen von Audio aus HLS Stream (Video) während der Wiedergabe von iOS

Aber jetzt für die HLS (.m3u8) Dateien kann ich das Video mit AVAssetWriter aufnehmen, aber Probleme mit der Audioaufnahme haben.

Ich verwende MTAudioProccessingTap, um die rohen Audiodaten zu verarbeiten und in eine Datei zu schreiben. Ich folgte this Artikel. Ich bin in der Lage, Remote MP4 Audio aufzunehmen, aber es funktioniert nicht mit HLS-Streams. Anfangs konnte ich die Audiotracks mit AVAssetTrack * audioTrack = [Inhalt tracksWithMediaType: AVMediaTypeAudio] [0] nicht aus dem Stream extrahieren;

Aber ich war in der Lage, die audioTracks mit KVO zu extrahieren, um die MTAudioProcessingTap zu initialisieren.

Ich habe auch verfolgen TrackID zu überprüfen, ob die Spur geändert wird.

So initialisiere ich die MTAudioProcessingTap.

-(void)beginRecordingAudioFromTrack:(AVAssetTrack *)audioTrack{ 
// Configure an MTAudioProcessingTap to handle things. 
MTAudioProcessingTapRef tap; 
MTAudioProcessingTapCallbacks callbacks; 
callbacks.version = kMTAudioProcessingTapCallbacksVersion_0; 
callbacks.clientInfo = (__bridge void *)(self); 
callbacks.init = init; 
callbacks.prepare = prepare; 
callbacks.process = process; 
callbacks.unprepare = unprepare; 
callbacks.finalize = finalize; 

OSStatus err = MTAudioProcessingTapCreate(
    kCFAllocatorDefault, 
    &callbacks, 
    kMTAudioProcessingTapCreationFlag_PostEffects, 
    &tap 
); 

if(err) { 
    NSLog(@"Unable to create the Audio Processing Tap %d", (int)err); 
    NSError *error = [NSError errorWithDomain:NSOSStatusErrorDomain 
             code:err 
            userInfo:nil]; 
    NSLog(@"Error: %@", [error description]);; 
    return; 
} 

// Create an AudioMix and assign it to our currently playing "item", which 
// is just the stream itself. 


AVMutableAudioMix *audioMix = [AVMutableAudioMix audioMix]; 
AVMutableAudioMixInputParameters *inputParams = [AVMutableAudioMixInputParameters 
    audioMixInputParametersWithTrack:audioTrack]; 

inputParams.audioTapProcessor = tap; 
audioMix.inputParameters = @[inputParams]; 
_audioPlayer.currentItem.audioMix = audioMix; 
} 

aber jetzt mit dieser Audiospur MTAudioProcessingTap Rückrufe „Vorbereiten“ und „Process“ werden nie genannt.

Ist das Problem mit dem audioTrack ich durch KVO bekommen?

Jetzt würde ich wirklich schätzen, wenn jemand mir dabei helfen kann. Oder kann ich sagen, verwende ich den Schreibansatz, um HLS Streams aufzuzeichnen?

+0

Haben Sie erfolgreich eine mp4-Datei mit m3u8-Datei erstellt? –

+1

@Milan Ich habe die Antwort dafür geschrieben. bitte prüfe. –

+0

Vielen Dank Sajad. –

Antwort

8

Ich habe eine Lösung dafür gefunden und in meiner App verwendet. Wollte es früher posten, habe aber keine Zeit.

Also, um mit HLS zu spielen, sollten Sie etwas wissen, was sie genau sind. Bitte sehen Sie es hier auf der Apple Website.

Hier sind die Schritte, denen ich folge. 1. Holen Sie sich das m3u8 zuerst und parsen Sie es. Sie können es mit diesem nützlichen Kit M3U8Kit analysieren. dieses Kit können Sie in der M3U8MediaPlaylist oder M3U8MasterPlaylist bekommen (wenn es sich um eine Master-Playlist), wenn Sie die Master-Playlist bekommen können Sie diese auch analysieren M3U8MediaPlaylist

(void) parseM3u8 
{ 
NSString *plainString = [self.url m3u8PlanString]; 
BOOL isMasterPlaylist = [plainString isMasterPlaylist]; 


NSError *error; 
NSURL *baseURL; 

if(isMasterPlaylist) 
{ 

    M3U8MasterPlaylist *masterList = [[M3U8MasterPlaylist alloc] initWithContentOfURL:self.url error:&error]; 
    self.masterPlaylist = masterList; 

    M3U8ExtXStreamInfList *xStreamInfList = masterList.xStreamList; 
    M3U8ExtXStreamInf *StreamInfo = [xStreamInfList extXStreamInfAtIndex:0]; 

    NSString *URI = StreamInfo.URI; 
    NSRange range = [URI rangeOfString:@"dailymotion.com"]; 
    NSString *baseURLString = [URI substringToIndex:(range.location+range.length)]; 
    baseURL = [NSURL URLWithString:baseURLString]; 

    plainString = [[NSURL URLWithString:URI] m3u8PlanString]; 
} 



M3U8MediaPlaylist *mediaPlaylist = [[M3U8MediaPlaylist alloc] initWithContent:plainString baseURL:baseURL]; 
self.mediaPlaylist = mediaPlaylist; 

M3U8SegmentInfoList *segmentInfoList = mediaPlaylist.segmentList; 

NSMutableArray *segmentUrls = [[NSMutableArray alloc] init]; 

for (int i = 0; i < segmentInfoList.count; i++) 
{ 
    M3U8SegmentInfo *segmentInfo = [segmentInfoList segmentInfoAtIndex:i]; 

    NSString *segmentURI = segmentInfo.URI; 
    NSURL *mediaURL = [baseURL URLByAppendingPathComponent:segmentURI]; 

    [segmentUrls addObject:mediaURL]; 
    if(!self.segmentDuration) 
     self.segmentDuration = segmentInfo.duration; 
} 

self.segmentFilesURLs = segmentUrls; 



} 

Sie zu sehen bekommen, dass Sie die Links bekommen zu den .ts-Dateien aus dem m3u8 parsen es.

  1. Laden Sie nun alle .ts-Dateien in einen lokalen Ordner herunter.
  2. Diese .ts-Dateien in eine mp4-Datei zusammenführen und exportieren. Sie können tun, dass mit dieser wunderbaren C-Bibliothek TS2MP4

und dann können Sie die .ts Dateien löschen oder behalten, wenn Sie sie benötigen.

+1

Dies ist hilfreich, wenn die m3u8 eine statische Liste von ts-Segmenten ist. Wenn Sie jedoch einen Livestream aufnehmen möchten, wird dies nicht funktionieren, da Sie Duplikate verwalten müssen, wenn Sie regelmäßig den Server erreichen. Ich brauche das ziemlich verzweifelt, auch wenn es bedeutet, einen Berater zu engagieren. –

+0

Ja Carlos F Sie haben Recht, dass Sie es verwalten müssen, da dies auch ein Durcheinander verursachen wird, wenn der Spieler zuerst den Server trifft und Sie später versuchen, zu analysieren. Aber ich habe es geschafft, Live-Streams auch mit diesem Ansatz aufzunehmen. –

2

Das ist nicht gut Ansatz, was Sie tun können, ist, M3U8 Link zu analysieren. Versuchen Sie dann, Segmentdateien (.ts) herunterzuladen. Wenn Sie diese Dateien erhalten können, können Sie sie zusammenführen, um MP4-Datei zu generieren.