从项目访问保存在今天扩展中的文件
Accessing File saved in today extension from project
我正在尝试访问我今天保存的文件 extension.In 我今天的扩展 我这样做是为了保存文件:
func startRecording() {
let audioFilename = getDocumentsDirectory().appendingPathComponent("recording.m4a")
let settings = [
AVFormatIDKey: Int(kAudioFormatMPEG4AAC),
AVSampleRateKey: 12000,
AVNumberOfChannelsKey: 1,
AVEncoderAudioQualityKey: AVAudioQuality.high.rawValue
]
do {
audioRecorder = try AVAudioRecorder(url: audioFilename, settings: settings)
audioRecorder.delegate = self
audioRecorder.record()
recordButton.setTitle("Stop", for: .normal)
} catch {
finishRecording(success: false)
}
}
func getDocumentsDirectory() -> URL {
let paths = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)
let documentsDirectory = paths[0]
return documentsDirectory
}
然后我尝试使用以下代码在项目的主要部分获取我的 AVAudio Player 的数据:
let path = Bundle.main.path(forResource: "recording.m4a", ofType:nil)!
let url = URL(fileURLWithPath: path)
但是,它给出了错误:在展开一个 Optional 值时意外发现 nil。
感谢您的帮助。
您的扩展程序将文件保存到其文档目录中,并且您的应用程序代码正在应用程序包中查找该文件。应用程序包仅包含随应用程序分发的资源。您需要深入研究文件系统。
但是,还有一个问题。扩展程序和包含的应用程序不共享文档目录。他们每个人都有自己的容器,用于在本地写入数据。如果您想在它们之间共享数据,则需要多做一些工作。总结:
- 为要共享的应用程序和扩展程序创建一个应用程序组标识符。
- 使用
FileManager.containerURL(forSecurityApplicationGroupIdentifier:)
获取共享容器目录的文件URL。
- 从容器 URL 追加文件名。
- 在扩展程序中,您将像往常一样设置
AVAudioRecorder
并开始录制。
- 在主应用程序中,您需要使用
NSFileCoordinator
API 来确保一次只有一个进程正在写入文件。希望 AVAudioRecorder
在内部使用 NSFileCoordinator
API,尽管我没有立即找到对此的确认。
有关共享容器的更多详细信息,请参阅此 blog post。
我只是尝试了同样的方法 - 从 Today Extension 录制音频。代码看起来很眼熟,所以我大胆猜测:您想捕获语音并将文件发送到 Google Speech API,对吗?
尽管如此,我认为我们遇到了扩展限制:根据 https://developer.apple.com/library/content/qa/qa1872/_index.html 判断,扩展无法录制音频。这篇文章是为 iOS 8 写的,但我不相信 Apple 曾经解除过限制。如果我错了,请纠正我,因为我一直 运行 在做 OP 自己做的事情时遇到问题。
顺便说一下,检查 audioRecorder.record()
的结果。它可能是 false
并表明捕获从未开始(这是我当前的错误)。
我正在尝试访问我今天保存的文件 extension.In 我今天的扩展 我这样做是为了保存文件:
func startRecording() {
let audioFilename = getDocumentsDirectory().appendingPathComponent("recording.m4a")
let settings = [
AVFormatIDKey: Int(kAudioFormatMPEG4AAC),
AVSampleRateKey: 12000,
AVNumberOfChannelsKey: 1,
AVEncoderAudioQualityKey: AVAudioQuality.high.rawValue
]
do {
audioRecorder = try AVAudioRecorder(url: audioFilename, settings: settings)
audioRecorder.delegate = self
audioRecorder.record()
recordButton.setTitle("Stop", for: .normal)
} catch {
finishRecording(success: false)
}
}
func getDocumentsDirectory() -> URL {
let paths = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)
let documentsDirectory = paths[0]
return documentsDirectory
}
然后我尝试使用以下代码在项目的主要部分获取我的 AVAudio Player 的数据:
let path = Bundle.main.path(forResource: "recording.m4a", ofType:nil)!
let url = URL(fileURLWithPath: path)
但是,它给出了错误:在展开一个 Optional 值时意外发现 nil。 感谢您的帮助。
您的扩展程序将文件保存到其文档目录中,并且您的应用程序代码正在应用程序包中查找该文件。应用程序包仅包含随应用程序分发的资源。您需要深入研究文件系统。
但是,还有一个问题。扩展程序和包含的应用程序不共享文档目录。他们每个人都有自己的容器,用于在本地写入数据。如果您想在它们之间共享数据,则需要多做一些工作。总结:
- 为要共享的应用程序和扩展程序创建一个应用程序组标识符。
- 使用
FileManager.containerURL(forSecurityApplicationGroupIdentifier:)
获取共享容器目录的文件URL。 - 从容器 URL 追加文件名。
- 在扩展程序中,您将像往常一样设置
AVAudioRecorder
并开始录制。 - 在主应用程序中,您需要使用
NSFileCoordinator
API 来确保一次只有一个进程正在写入文件。希望AVAudioRecorder
在内部使用NSFileCoordinator
API,尽管我没有立即找到对此的确认。
有关共享容器的更多详细信息,请参阅此 blog post。
我只是尝试了同样的方法 - 从 Today Extension 录制音频。代码看起来很眼熟,所以我大胆猜测:您想捕获语音并将文件发送到 Google Speech API,对吗?
尽管如此,我认为我们遇到了扩展限制:根据 https://developer.apple.com/library/content/qa/qa1872/_index.html 判断,扩展无法录制音频。这篇文章是为 iOS 8 写的,但我不相信 Apple 曾经解除过限制。如果我错了,请纠正我,因为我一直 运行 在做 OP 自己做的事情时遇到问题。
顺便说一下,检查 audioRecorder.record()
的结果。它可能是 false
并表明捕获从未开始(这是我当前的错误)。