gpt4 book ai didi

ios - 从mp3格式的视频中提取音频

转载 作者:可可西里 更新时间:2023-11-01 04:57:59 24 4
gpt4 key购买 nike

目标:我想从 mp3 格式的视频中提取音频。视频可以是任何 iOS 支持的格式

我尝试了以下技术来实现上述目标,并且我使用的是 lame 库:

第 1 步:通过将源文件 URL 传递给它来创建一个 AVURLAsset 对象。

第 2 步:创建一个 AVAssetExportSession 对象,并将源 Assets 的输出文件类型设置为 m4a。

第 3 步:提取其音频,然后我尝试将其转换为 mp3 格式。

这是我使用的代码:

NSURL *videoFileUrl = [NSURL fileURLWithPath:originalVideoPath];
AVURLAsset *anAsset = [[AVURLAsset alloc] initWithURL:videoFileUrl options:nil];

exportSession=[AVAssetExportSession exportSessionWithAsset:anAsset presetName:AVAssetExportPresetPassthrough];

[exportSession determineCompatibleFileTypesWithCompletionHandler:^(NSArray *compatibleFileTypes) {
NSLog(@"compatiblefiletypes: %@",compatibleFileTypes);
}];

NSURL *furl = [NSURL fileURLWithPath:tmpVideoPath];
exportSession.outputURL = furl;
exportSession.outputFileType=AVFileTypeAppleM4A;

CMTime duration = anAsset.duration;
CMTimeRange range = CMTimeRangeMake(kCMTimeZero, duration);
exportSession.timeRange = range;

[exportSession exportAsynchronouslyWithCompletionHandler:^{
dispatch_async(dispatch_get_main_queue(), ^{
[SVProgressHUD dismiss];
});
switch (exportSession.status)
{
case AVAssetExportSessionStatusCompleted:
{
dispatch_async(dispatch_get_main_queue(), ^{
[SVProgressHUD showProgress:0 status:@"Converting..." maskType:SVProgressHUDMaskTypeGradient];
[self performSelector:@selector(convertToMp3) withObject:nil afterDelay:0.3f];
});
break;
}
case AVAssetExportSessionStatusFailed:
{
dispatch_async(dispatch_get_main_queue(), ^{
[MyUtility showAlertViewWithTitle:kAlertTitle msg:exportSession.error.localizedDescription];
});
break;
}
case AVAssetExportSessionStatusCancelled:
NSLog(@"Export canceled");
break;
default:

break;
}
}];

__weak AVAssetExportSession *weakSession = exportSession;
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_LOW, 0), ^{
while (weakSession.status == AVAssetExportSessionStatusWaiting
|| weakSession.status == AVAssetExportSessionStatusExporting) {
dispatch_sync(dispatch_get_main_queue(), ^{
[SVProgressHUD showProgress:exportSession.progress status:@"Extracting..." maskType:SVProgressHUDMaskTypeGradient];
});
}
});
- (void)convertToMp3
{
NSURL *extractedAudioFileURL = [[NSURL alloc] initWithString:tmpVideoPath];
NSError *error;
AVAudioPlayer *audioPlayer = [[AVAudioPlayer alloc] initWithContentsOfURL:extractedAudioFileURL error:&error];

float noOfChannels = [[audioPlayer.settings objectForKey:AVNumberOfChannelsKey] floatValue];
float sampleRate = [[audioPlayer.settings objectForKey:AVSampleRateKey] floatValue];
float bitRate = 16;//[[audioPlayer.settings objectForKey:AVLinearPCMBitDepthKey] floatValue];

@try {
int read, write;

FILE *pcm = fopen([tmpVideoPath cStringUsingEncoding:1], "rb"); //source
fseek(pcm, 4*1024, SEEK_CUR); //skip file header
FILE *mp3 = fopen([tmpMp3FilePath cStringUsingEncoding:1], "wb"); //output

const int PCM_SIZE = 8192;
const int MP3_SIZE = 8192;
short int pcm_buffer[PCM_SIZE*2];
unsigned char mp3_buffer[MP3_SIZE];

lame_t lame = lame_init();
lame_set_in_samplerate(lame, sampleRate);
lame_set_VBR(lame, vbr_default);
lame_init_params(lame);

long long fileSize = [[[[NSFileManager defaultManager] attributesOfItemAtPath:tmpVideoPath error:nil] objectForKey:NSFileSize] longLongValue];
long duration = (fileSize * 8.0f) / (sampleRate * noOfChannels);

lame_set_num_samples(lame, (duration * sampleRate));
lame_get_num_samples(lame);

int percent = 0;
int totalframes = lame_get_totalframes(lame);

do {
read = fread(pcm_buffer, 2*sizeof(short int), PCM_SIZE, pcm);
if (read == 0)
write = lame_encode_flush(lame, mp3_buffer, MP3_SIZE);
else
write = lame_encode_buffer_interleaved(lame, pcm_buffer, read, mp3_buffer, MP3_SIZE);

fwrite(mp3_buffer, write, 1, mp3);

int frameNum = lame_get_frameNum(lame);
if (frameNum < totalframes)
percent = (int) (100. * frameNum / totalframes + 0.5);
else
percent = 100;

[SVProgressHUD showProgress:percent status:@"Converting..." maskType:SVProgressHUDMaskTypeGradient];

NSLog(@"progress: %d",percent);

} while (read != 0);

lame_close(lame);
fclose(mp3);
fclose(pcm);
}
@catch (NSException *exception) {
NSLog(@"%@",[exception description]);
}
@finally {
[SVProgressHUD dismiss];
}
}

我得到的结果音频只有噪音,而且它的持续时间也是错误的。我用谷歌搜索,发现“libmp3lame”只理解线性 PCM 音频,而 m4a 是压缩音频格式。

现在如何将音频从 m4a 或任何其他方式转换为 mp3 格式以直接从 mp3 格式的视频中提取音频。

谢谢。

最佳答案

不要导出到 AVFileTypeAppleM4A,而是尝试导出到 AVFileTypeAIFF。这将为您提供跛脚编码器所需的线性 PCM。显然,临时文件会比 m4a 大,但这可能是您会注意到的唯一区别。

关于ios - 从mp3格式的视频中提取音频,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22350245/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com