iOS удаляет особый звук из видео
У меня есть приложение, которое воспроизводит звук, а также записывает видео + аудио во время воспроизведения этого звука. Я хотел бы выяснить способ обработки видео таким образом, чтобы звук, полученный микрофоном, был удален из полученного видео.
Например, если я играю audioA, а затем записываю videoB с audioB (из микрофона), я хочу как-то отменить audioA из полученного audioB, чтобы audioB был только окружающим шумом, а не шумом от динамиков устройства.,
Есть идеи, если есть способ сделать это?
Бонусные баллы, если это можно сделать без какой-либо автономной обработки.
1 ответ
Вы должны иметь дело с партией воспроизведения. Но вот код для микширования выбранного аудио с записанным видео.
- (void)mixAudio:(AVAsset*)audioAsset startTime:(CMTime)startTime withVideo:(NSURL*)inputUrl affineTransform:(CGAffineTransform)affineTransform toUrl:(NSURL*)outputUrl outputFileType:(NSString*)outputFileType withMaxDuration:(CMTime)maxDuration withCompletionBlock:(void(^)(NSError *))completionBlock {
NSError * error = nil;
AVMutableComposition * composition = [[AVMutableComposition alloc] init];
AVMutableCompositionTrack * videoTrackComposition = [composition addMutableTrackWithMediaType:AVMediaTypeVideo preferredTrackID:kCMPersistentTrackID_Invalid];
AVMutableCompositionTrack * audioTrackComposition = [composition addMutableTrackWithMediaType:AVMediaTypeAudio preferredTrackID:kCMPersistentTrackID_Invalid];
AVURLAsset * fileAsset = [AVURLAsset URLAssetWithURL:inputUrl options:[NSDictionary dictionaryWithObject:[NSNumber numberWithBool:YES] forKey:AVURLAssetPreferPreciseDurationAndTimingKey]];
NSArray * videoTracks = [fileAsset tracksWithMediaType:AVMediaTypeVideo];
CMTime duration = ((AVAssetTrack*)[videoTracks objectAtIndex:0]).timeRange.duration;
if (CMTIME_COMPARE_INLINE(duration, >, maxDuration)) {
duration = maxDuration;
}
for (AVAssetTrack * track in [audioAsset tracksWithMediaType:AVMediaTypeAudio]) {
[audioTrackComposition insertTimeRange:CMTimeRangeMake(startTime, duration) ofTrack:track atTime:kCMTimeZero error:&error];
if (error != nil) {
completionBlock(error);
return;
}
}
for (AVAssetTrack * track in videoTracks) {
[videoTrackComposition insertTimeRange:CMTimeRangeMake(kCMTimeZero, duration) ofTrack:track atTime:kCMTimeZero error:&error];
if (error != nil) {
completionBlock(error);
return;
}
}
videoTrackComposition.preferredTransform = affineTransform;
AVAssetExportSession * exportSession = [[AVAssetExportSession alloc] initWithAsset:composition presetName:AVAssetExportPresetPassthrough];
exportSession.outputFileType = outputFileType;
exportSession.shouldOptimizeForNetworkUse = YES;
exportSession.outputURL = outputUrl;
[exportSession exportAsynchronouslyWithCompletionHandler:^ {
NSError * error = nil;
if (exportSession.error != nil) {
NSMutableDictionary * userInfo = [NSMutableDictionary dictionaryWithDictionary:exportSession.error.userInfo];
NSString * subLocalizedDescription = [userInfo objectForKey:NSLocalizedDescriptionKey];
[userInfo removeObjectForKey:NSLocalizedDescriptionKey];
[userInfo setObject:@"Failed to mix audio and video" forKey:NSLocalizedDescriptionKey];
[userInfo setObject:exportSession.outputFileType forKey:@"OutputFileType"];
[userInfo setObject:exportSession.outputURL forKey:@"OutputUrl"];
[userInfo setObject:subLocalizedDescription forKey:@"CauseLocalizedDescription"];
[userInfo setObject:[AVAssetExportSession allExportPresets] forKey:@"AllExportSessions"];
error = [NSError errorWithDomain:@"Error" code:500 userInfo:userInfo];
}
completionBlock(error);
}];
}