2015-12-06 18 views
5

मैं ध्वनि फ़ाइल में ध्वनि लिखने के लिए एक AVAudioFile बना रहा हूं। अगर फ़ाइल पहले से मौजूद है, तो मैं मौजूदा फ़ाइल को बदलने के बजाय अंत में लेखन जारी रखने के लिए, फ़ाइल के अंत में फ्रेमपॉज़िशन को स्थानांतरित करना चाहता हूं।AVAudioFile.length 0 है अगर फ़ाइल मौजूद है

मैंने कुछ परीक्षण किए, फ़ाइल से बफर को एक नई फ़ाइल में पढ़ने के लिए, एक अलग यूआरएल के साथ पढ़ने की कोशिश की, ताकि वह मूल फ़ाइल को ओवरराइट नहीं कर सके। मैं एक दुर्घटना जब मैं नई फ़ाइल में बफर पढ़ने के लिए कोशिश कर रहा हूँ हो रही है:

let audioFile = try AVAudioFile(forReading: [URL to existing .caf file]) 
let audioFrameCount = AVAudioFrameCount(UInt32(audioFile.length)) 
let audioBuffer = AVAudioPCMBuffer(PCMFormat: audioFile.processingFormat, frameCapacity: audioFrameCount) 

let newAudioFile = try AVAudioFile(forWriting: [another URL], settings: self.engine.mainMixerNode.outputFormatForBus(0).settings) 
try newAudioFile.readIntoBuffer(audioBuffer, frameCount: audioFrameCount!) <-- CRASHES ON THIS LINE 

क्रैश लॉग: न आया हुआ अपवाद 'com.apple.coreaudio.avfaudio', कारण की वजह से एप्लिकेशन समाप्त: ' त्रुटि -50 '

मैन, मैं वास्तव में CoreAudio क्रैश लॉग से नफरत करता हूं। वे मुझे बिल्कुल कुछ नहीं बताते हैं!

क्या लेखन के लिए बनाई गई फ़ाइल में डेटा को पढ़ना संभव नहीं है?

अद्यतन

ठीक है, तो कुछ सुझाव के बाद मैं कुछ परिवर्तन किया था। असल में, ये वे चरण हैं जिन्हें मैं ले रहा हूं:

  1. जांचें कि कोई फ़ाइल पहले से मौजूद है या नहीं।
  2. यदि ऐसा होता है, तो इसे पढ़ने और ऑडियो बफर प्राप्त करने के लिए खोलें।
  3. लिखने के लिए एक नई फ़ाइल (एक ही फाइल URL का उपयोग)
  4. उपयोग writeFromBuffer नई फ़ाइल
  5. अंत करने के लिए नई फ़ाइल की framePosition स्थानांतरित करने पुरानी फाइल से बफर लिखने के लिए बनाएं, ताकि मैं इसे लिखना/रिकॉर्डिंग जारी रख सकते हैं।

हालांकि, मैंने इसे लिखने के बाद नई फ़ाइल की लंबाई 0 है।

यहाँ मेरी कोड है:

//Check if a file already exists. If so continue to record at the end of it 
var audioBuffer : AVAudioPCMBuffer! 
var audioFrameCount : AVAudioFrameCount! 
if (NSFileManager.defaultManager().fileExistsAtPath(self.audioRecordURL.path!)) { 
    do { 
     let existingAudioFile = try AVAudioFile(forReading: self.audioRecordURL) 
     audioFrameCount = AVAudioFrameCount(existingAudioFile.length) 
     if (audioFrameCount > 0) { 
      audioBuffer = AVAudioPCMBuffer(PCMFormat: existingAudioFile.processingFormat, frameCapacity: audioFrameCount) 
     } 
    } catch let error as NSError { 
     NSLog("Error reading buffer from file %@", error.localizedDescription) 
    } 
} 

//Create a new file. This will replace the old file 
do { 
    self.audioFile = try AVAudioFile(forWriting: self.audioRecordURL, settings: self.engine.mainMixerNode.outputFormatForBus(0).settings) 
} catch let error as NSError { 
    NSLog("Error creating AVAudioFile %@", error.localizedDescription) 
} 

//Read the audio buffer from the old file into the new file 
if (audioBuffer != nil) { 
    do { 
     try self.audioFile.writeFromBuffer(audioBuffer) 
     self.audioFile.framePosition = self.audioFile.length 
    } catch let error as NSError { 
     NSLog("Error reading buffer into file %@", error.localizedDescription) 
    } 
} 

वैसे, readIntoBuffer के नामकरण मेरे लिए बेहद भ्रामक है। ऐसा लगता है जैसे आपको फ़ाइल को बफर में पढ़ने के लिए उस विधि का उपयोग करना चाहिए, लेकिन दस्तावेज़ीकरण के अनुसार आपको फ़ाइल में बफर पढ़ने के लिए इसका उपयोग करना चाहिए? तो मैं अपनी फ़ाइल में बफर जोड़ने के लिए उस विधि का उपयोग क्यों नहीं कर सकता? मुझे WriteFromBuffer का उपयोग क्यों करना है?

अद्यतन 2

तो, मैं इसे हल करने में कामयाब रहे। जाहिर है, मुझे इसे इस्तेमाल करने से पहले डेटा के साथ वास्तव में बफर भरने के लिए readIntoBuffer को कॉल करना पड़ा था।इसलिए मैं

audioBuffer = AVAudioPCMBuffer(PCMFormat: existingAudioFile.processingFormat, frameCapacity: audioFrameCount) 
+0

'-50' आम तौर पर एक पैरामीटर त्रुटि है। क्या 'ऑडियोफ्रेम कार्ड' के पीछे '! 'वास्तव में जरूरी है? क्या 'audioFrameCount' का वैध मान है? – hendrik

+0

मैंने हटा दिया! (मुझे नहीं पता कि मेरे पास ऐसा क्यों था)। हां, ऑडियोफ्रेम कार्ड का वैध मान है। – andlin

+0

और आप अभी भी -50 प्राप्त कर रहे हैं? या तो लिखने के लिए खोले गए फ़ाइल से पढ़ने के लिए वास्तव में संभव नहीं है या आपकी सेटिंग्स किसी भी तरह से ऑडियो बफर प्रारूप से मेल नहीं खाती है। फ़ाइल को पहले पढ़ने, पढ़ने, बंद करने के लिए फ़ाइल को क्यों नहीं खोलते हैं और फिर इस मुद्दे के आसपास काम करने के लिए इसे लिखने के लिए खोलते हैं? – hendrik

उत्तर

1

अगर यह सिर्फ कोड तुम यहाँ प्रदान की है में कोई गलती है सुनिश्चित नहीं हैं के बाद इस लाइन

try existingAudioFile.readIntoBuffer(audioBuffer) 

जोड़ा, और मैं इस क्षेत्र में एक विशेषज्ञ नहीं हूँ, लेकिन शायद क्योंकि यह कारण है कि आप एक फ़ाइल से लेखन (newAudioFile) के लिए खोला नहीं पढ़ सकते हैं खड़ा है

try audioFile.readIntoBuffer(audioBuffer, frameCount: audioFrameCount!) 

: आप लाइन है कि दुर्घटनाओं होना है करने के लिए होती।

और फिर है कि बफर भरने के बाद आप writeFromBuffer https://developer.apple.com/library/ios/documentation/AVFoundation/Reference/AVAudioFile_Class/#//apple_ref/occ/instm/AVAudioFile/writeFromBuffer:error का उपयोग कर नए फाइल करने के लिए लिखना चाहते हैं:

+0

मैं अपने पुराने ऑडियो फ़ाइल से बफर को अपने नए बनाए गए एक में जोड़ना चाहता हूं (और उसके बाद रिकॉर्डिंग जारी रखता हूं)। क्या मुझे इसके बजाय writeFromBuffer का उपयोग करना चाहिए? ऐसा करने से मुझे कोई दुर्घटना नहीं मिलती है, मेरी ऑडियो फ़ाइल की लंबाई लिखने के बाद 0 है। मैं कुछ और जानकारी – andlin

+0

के साथ अपना प्रश्न अपडेट करूँगा, इसे हल करने में मेरी सहायता के लिए धन्यवाद। मुझे एहसास नहीं हुआ कि बफर का उपयोग करने से पहले, मुझे वास्तव में पुरानी फ़ाइल से डेटा के साथ बफर भरने के लिए readIntoBuffer को कॉल करना पड़ा था। ReadIntoBuffer के लिए प्रलेखन "बफर जो फ़ाइल में पढ़ने के लिए है।" जो मेरे लिए वास्तव में इसके विपरीत के विपरीत लगता है। – andlin

संबंधित मुद्दे