While recording a video, if an interruption occurs such as an
incoming call or an alarm sound, the camera frezees and the video is not saved. I would like to handle this situation interrupting the video and saving it or removing the audio while it keeps recording.
But after the interruption starts and the event is recognized, the variables
regarding the video already recorded are reinitialized, causing the app
not to save anything.
This is part of the CameraManager class:
var captureSession: AVCaptureSession?
public func fileOutput(_: AVCaptureFileOutput, didStartRecordingTo _: URL, from _: [AVCaptureConnection]) {
NotificationCenter.default.addObserver(self, selector: #selector(sessionInterruptionBegin), name: .AVCaptureSessionWasInterrupted, object: captureSession)
NotificationCenter.default.addObserver(self, selector: #selector(sessionInterruptionEnd),name: .AVCaptureSessionInterruptionEnded, object: captureSession)
NotificationCenter.default.addObserver(self, selector: #selector(audioSessionInterrupted), name: AVAudioSession.interruptionNotification, object: AVAudioSession.sharedInstance)
print("STO PASSANDO DA AVCaptureFileOutputRecordingDelegate")
captureSession?.beginConfiguration()
if flashMode != .off {
_updateIlluminationMode(flashMode)
}
captureSession?.commitConfiguration() //at this point captureSession starts collecting data about the video
}
extension CameraManager {
@objc func sessionInterruptionBegin(notification: Notification) {
print("Capture Session Interruption begin Notification!")
guard let reasonNumber = notification.userInfo?[AVCaptureSessionInterruptionReasonKey] as? NSNumber else {
return
}
let reason = AVCaptureSession.InterruptionReason(rawValue: reasonNumber.intValue)
switch reason {
case .audioDeviceInUseByAnotherClient:
removeAudioInput()
default:
break
}
}
func addAudioInput() throws {
if audioDeviceInput != nil {
return
}
removeAudioInput()
print("Adding audio input...")
captureSession?.beginConfiguration()
guard let audioDevice = AVCaptureDevice.default(for: .audio) else {
throw NSError()
}
audioDeviceInput = try AVCaptureDeviceInput(device: audioDevice)
guard captureSession!.canAddInput(audioDeviceInput!) else {
throw NSError()
}
captureSession?.addInput(audioDeviceInput!)
captureSession?.automaticallyConfiguresApplicationAudioSession = false
captureSession?.commitConfiguration()
}
func removeAudioInput() {
//when the code reaches this point audioDeviceInput is reinitialized so the audio session is not removed from the recording
//captureSession is not filled with the data about the video recorded
guard let audioInput = audioDeviceInput else {
return
}
captureSession?.beginConfiguration()
captureSession?.removeInput(audioInput)
audioDeviceInput = nil
captureSession?.commitConfiguration()
}
@objc func sessionInterruptionEnd(notification: Notification) {
print("Capture Session Interruption end Notification!")
guard let reasonNumber = notification.userInfo?[AVCaptureSessionInterruptionReasonKey] as? NSNumber else {
return
}
let reason = AVCaptureSession.InterruptionReason(rawValue: reasonNumber.intValue)
switch reason {
case .audioDeviceInUseByAnotherClient:
// add audio again because we removed it when we received the interruption.
configureAudioSession()
default:
// don't do anything, iOS will automatically resume session
break
}
}
@objc func audioSessionInterrupted(notification: Notification) {
print("Audio Session Interruption Notification!")
guard let userInfo = notification.userInfo,
let typeValue = userInfo[AVAudioSessionInterruptionTypeKey] as? UInt,
let type = AVAudioSession.InterruptionType(rawValue: typeValue) else {
return
}
switch type {
case .began:
print("The Audio Session was interrupted!")
removeAudioInput()
case .ended:
print("The Audio Session interruption has ended.")
guard let optionsValue = userInfo[AVAudioSessionInterruptionOptionKey] as? UInt else { return }
let options = AVAudioSession.InterruptionOptions(rawValue: optionsValue)
if options.contains(.shouldResume) {
print("Resuming interrupted Audio Session...")
// restart audio session because interruption is over
configureAudioSession()
} else {
print("Cannot resume interrupted Audio Session!")
}
@unknown default: ()
}
}
func configureAudioSession() {
let start = DispatchTime.now()
do {
try self.addAudioInput()
let audioSession = AVAudioSession.sharedInstance()
if audioSession.category != .playAndRecord {
// allow background music playback
try audioSession.setCategory(AVAudioSession.Category.playAndRecord, options: [.mixWithOthers, .allowBluetoothA2DP, .defaultToSpeaker])
}
// activate current audio session because camera is active
try audioSession.setActive(true)
} catch let error as NSError {
switch error.code {
case 561_017_449:
print(error.description)
default:
print(error.description)
}
self.removeAudioInput()
}
let end = DispatchTime.now()
let nanoTime = end.uptimeNanoseconds - start.uptimeNanoseconds
print("Configured Audio session in \(Double(nanoTime) / 1_000_000)ms!")
}
}
Selecting any option will automatically load the page
Post
Replies
Boosts
Views
Activity
We have detected the problem during the implementation of in-app purchases with the Apple StoreKit.
We have created some products on Apple store connect with specific prices
and we have added the StoreKit to our Application.
In order to understand if everything was working, we have made some
tests with the StoreKit and we have discovered that it is not working
well.
Using an US sandbox account everything works well: each product appears
with the correct price (we checked them on Apple Prices Matrix for
in-app purchases).
Using an IT sandbox account there are problems; in particular, all the
prices are different compared to the apple Prices Matrix. E.g. price 6
should be 5.99 € but StoreKit tell us 6.99 or price 87 should be 999.99 €
and StoreKit send us 1099.99.
We have also tried to use the storeKit in a new empty app so as to understand if there was our fault but it's still not working. Is there anyone else that have found the same problem?
Topic:
App Store Distribution & Marketing
SubTopic:
App Store Connect
Tags:
In-App Purchase
App Store Connect
StoreKit
StoreKit Test