Question

Je fais des progrès sur la prise d'un son et l'enregistrer comme PCM compressé (mp3). De plus, je voulais diviser le fichier original en morceaux qui sont 2 secondes, dans le même processus. Il me semble réussir, mais je suis un peu confus quant à pourquoi.

Comme je l'ai lu des blocs de données audio et écrire les fichiers, je vérifie pour voir si je suis sur le point d'écrire un morceau qui rendrait mon dossier dépasse mes 2 deuxième limite. Si oui, je vous écris assez pour 2 secondes, fermez le fichier, puis ouvrez un nouveau fichier et d'écrire le reste dans le nouveau fichier, puis lire plus de données. Quelque chose comme ceci:

framesInTimedSegment += numFrames;
if ((framesInTimedSegment  > (2.0 * sampleRate)) && (j < 5)) {
    UInt32 newNumFrames = numFrames;
    numFrames = framesInTimedSegment - (2.0 * sampleRate);
    newNumFrames -= numFrames;
// Question A
    UInt32 segmentOffset = newNumFrames * numChannels * 2;
    error = ExtAudioFileWrite(segmentFile, newNumFrames, &fillBufList);
// Question B
       // handle this error!  We might have an interruption
    if (segmentFile) ExtAudioFileDispose(segmentFile);
    XThrowIfError(ExtAudioFileCreateWithURL(urlArray[++j], kAudioFileCAFType, &dstFormat, NULL, kAudioFileFlags_EraseFile, &breakoutFile), "ExtAudioFileCreateWithURL failed! - segmentFile");
    size = sizeof(clientFormat);
    XThrowIfError(ExtAudioFileSetProperty(segmentFile, kExtAudioFileProperty_ClientDataFormat, size, &clientFormat), "couldn't set destination client format"); 
    fillBufList.mBuffers[0].mData = srcBuffer + segmentOffset;
    fillBufList.mBuffers[0].mDataByteSize = numFrames * fillBufList.mBuffers[0].mNumberChannels * 2;
    framesInTimedSegment = numFrames;
}
error = ExtAudioFileWrite(segmentFile, numFrames, &fillBufList);

Voici mes questions (j'ai essayé d'étiqueter la ligne correspondante):

A: Y at-il une meilleure façon de trouver le décalage dans mon tampon, donc je ne suis pas le code par erreur dur une valeur là-dedans? Par exemple, est-il un moyen béni pour obtenir les données décalées par rapport à numéro d'image?

B: Si ExtAudioFileWrite fait la conversion du comprimé à décompressé, puis les données que je suis en train d'écrire n'a pas encore été décompressé (à droite?), Donc je ne devrais pas avoir à se soucier de jouer avec les chiffres de cadre et les décalages quand je je traite des données compressées? Dois-je à la place convertira d'abord le fichier, que ce soit dans un fichier PCM ou dans la mémoire, puis le partage que PCM?

Merci!

-mahboud

ps.

Le clientFormat est défini comme suit:

        clientFormat = dstFormat;

et dstFormat:

        dstFormat.mFormatID = outputFormat;
        dstFormat.mChannelsPerFrame = srcFormat.NumberChannels();
        dstFormat.mBitsPerChannel = 16;
        dstFormat.mBytesPerPacket = dstFormat.mBytesPerFrame = 2 * dstFormat.mChannelsPerFrame;
        dstFormat.mFramesPerPacket = 1;
        dstFormat.mFormatFlags = kLinearPCMFormatFlagIsPacked | kLinearPCMFormatFlagIsSignedInteger; // little-endian
Était-ce utile?

La solution

Il est difficile de répondre correctement sans voir un peu plus de code. Mais, en supposant clientFormat est un format PCM entrelacée:

B) ExtAudioFileWrite ne fonctionne pas la conversion du comprimé à décompressé, ExtAudioFileRead does- selon le format client que vous avez défini. En supposant un fichier source MP3 et 16 bits « standard » 44,1 KHz format client PCM, les appels à ExtAudioFileRead convertira des octets de MP3 à données PCM. Cela se fait sous le capot en utilisant AudioFile et les API AudioConverter.

A) Ceci est un peu difficile de répondre sans voir comment srcBuffer est défini (je suppose un tableau de int16_t). Si vous travaillez avec des données PCM, ce que vous faites semble OK. Vous pouvez également utiliser newNumFrames * clientFormat.mBytesPerFrame * clientFormat.mChannelsPerFrame, mais en supposant des données PCM 16 bits, mBytesPerFrame == == mBytesPerPacket 2. Si vous travaillez avec des données non CBR vous devez vous préoccuper des descriptions de paquets, mais cela ne semble pas être le cas.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top