Return-Path: X-Original-To: archive-asf-public-internal@cust-asf2.ponee.io Delivered-To: archive-asf-public-internal@cust-asf2.ponee.io Received: from cust-asf.ponee.io (cust-asf.ponee.io [163.172.22.183]) by cust-asf2.ponee.io (Postfix) with ESMTP id 56F72200C88 for ; Thu, 27 Apr 2017 22:02:11 +0200 (CEST) Received: by cust-asf.ponee.io (Postfix) id 54B61160B9E; Thu, 27 Apr 2017 20:02:11 +0000 (UTC) Delivered-To: archive-asf-public@cust-asf.ponee.io Received: from mail.apache.org (hermes.apache.org [140.211.11.3]) by cust-asf.ponee.io (Postfix) with SMTP id 0D29B160BBF for ; Thu, 27 Apr 2017 22:02:09 +0200 (CEST) Received: (qmail 96734 invoked by uid 500); 27 Apr 2017 20:02:09 -0000 Mailing-List: contact commits-help@cordova.apache.org; run by ezmlm Precedence: bulk List-Help: List-Unsubscribe: List-Post: List-Id: Delivered-To: mailing list commits@cordova.apache.org Received: (qmail 96542 invoked by uid 99); 27 Apr 2017 20:02:09 -0000 Received: from git1-us-west.apache.org (HELO git1-us-west.apache.org) (140.211.11.23) by apache.org (qpsmtpd/0.29) with ESMTP; Thu, 27 Apr 2017 20:02:09 +0000 Received: by git1-us-west.apache.org (ASF Mail Server at git1-us-west.apache.org, from userid 33) id 0C265E01BC; Thu, 27 Apr 2017 20:02:09 +0000 (UTC) Content-Type: text/plain; charset="us-ascii" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit From: filmaj@apache.org To: commits@cordova.apache.org Date: Thu, 27 Apr 2017 20:02:15 -0000 Message-Id: <1e2efaf6e6d7441785aee1a70a857e74@git.apache.org> In-Reply-To: <562ebad197a14e14a76f3d3955dbaf30@git.apache.org> References: <562ebad197a14e14a76f3d3955dbaf30@git.apache.org> X-Mailer: ASF-Git Admin Mailer Subject: [08/10] cordova-plugin-media git commit: CB-12542: (ios) Fix wav file recording, add m4a extension. make IOS status handling compatible with Android/Windows archived-at: Thu, 27 Apr 2017 20:02:11 -0000 CB-12542: (ios) Fix wav file recording, add m4a extension. make IOS status handling compatible with Android/Windows implement a "messageChannel" command and if the messageChannel command is called the plugin hands back results to the plugin container via "sendPluginResult" instead of "evalJs" even for oldschool usage it cleans the code Closes #134. Project: http://git-wip-us.apache.org/repos/asf/cordova-plugin-media/repo Commit: http://git-wip-us.apache.org/repos/asf/cordova-plugin-media/commit/b61d97cd Tree: http://git-wip-us.apache.org/repos/asf/cordova-plugin-media/tree/b61d97cd Diff: http://git-wip-us.apache.org/repos/asf/cordova-plugin-media/diff/b61d97cd Branch: refs/heads/3.0.x Commit: b61d97cd718f989f4b16fa3ee52c5c0095538008 Parents: 3353eac Author: Leo Schubert Authored: Sat Mar 11 10:49:28 2017 +0100 Committer: filmaj Committed: Wed Apr 26 12:10:01 2017 -0700 ---------------------------------------------------------------------- README.md | 2 +- src/ios/CDVSound.h | 4 +- src/ios/CDVSound.m | 185 ++++++++++++++++++++++++------------------------ 3 files changed, 97 insertions(+), 94 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/cordova-plugin-media/blob/b61d97cd/README.md ---------------------------------------------------------------------- diff --git a/README.md b/README.md index 2b4705a..184bd7b 100644 --- a/README.md +++ b/README.md @@ -558,7 +558,7 @@ function recordAudio() { ### iOS Quirks -- iOS only records to files of type _.wav_ and returns an error if the file name extension is not correct. +- iOS only records to files of type _.wav_ and _.m4a_ and returns an error if the file name extension is not correct. - If a full path is not provided, the recording is placed in the application's `documents/tmp` directory. This can be accessed via the `File` API using `LocalFileSystem.TEMPORARY`. Any subdirectory specified at record time must already exist. http://git-wip-us.apache.org/repos/asf/cordova-plugin-media/blob/b61d97cd/src/ios/CDVSound.h ---------------------------------------------------------------------- diff --git a/src/ios/CDVSound.h b/src/ios/CDVSound.h index 3f123b0..4b7602e 100644 --- a/src/ios/CDVSound.h +++ b/src/ios/CDVSound.h @@ -87,10 +87,12 @@ typedef NSUInteger CDVMediaMsg; NSString* currMediaId; AVAudioSession* avSession; AVPlayer* avPlayer; + NSString* statusCallbackId; } @property (nonatomic, strong) NSMutableDictionary* soundCache; @property (nonatomic, strong) AVAudioSession* avSession; @property (nonatomic, strong) NSString* currMediaId; +@property (nonatomic, strong) NSString* statusCallbackId; - (void)startPlayingAudio:(CDVInvokedUrlCommand*)command; - (void)pausePlayingAudio:(CDVInvokedUrlCommand*)command; @@ -110,7 +112,7 @@ typedef NSUInteger CDVMediaMsg; - (CDVAudioFile*)audioFileForResource:(NSString*)resourcePath withId:(NSString*)mediaId doValidation:(BOOL)bValidate forRecording:(BOOL)bRecord; - (CDVAudioFile*)audioFileForResource:(NSString*)resourcePath withId:(NSString*)mediaId doValidation:(BOOL)bValidate forRecording:(BOOL)bRecord suppressValidationErrors:(BOOL)bSuppress; - (BOOL)prepareToPlay:(CDVAudioFile*)audioFile withId:(NSString*)mediaId; -- (NSString*)createMediaErrorWithCode:(CDVMediaError)code message:(NSString*)message; +- (NSDictionary*)createMediaErrorWithCode:(CDVMediaError)code message:(NSString*)message; - (void)startRecordingAudio:(CDVInvokedUrlCommand*)command; - (void)stopRecordingAudio:(CDVInvokedUrlCommand*)command; http://git-wip-us.apache.org/repos/asf/cordova-plugin-media/blob/b61d97cd/src/ios/CDVSound.m ---------------------------------------------------------------------- diff --git a/src/ios/CDVSound.m b/src/ios/CDVSound.m index 8666843..e154287 100644 --- a/src/ios/CDVSound.m +++ b/src/ios/CDVSound.m @@ -24,11 +24,10 @@ #define HTTP_SCHEME_PREFIX @"http://" #define HTTPS_SCHEME_PREFIX @"https://" #define CDVFILE_PREFIX @"cdvfile://" -#define RECORDING_WAV @"wav" @implementation CDVSound -@synthesize soundCache, avSession, currMediaId; +@synthesize soundCache, avSession, currMediaId, statusCallbackId; // Maps a url for a resource path for recording - (NSURL*)urlForRecording:(NSString*)resourcePath @@ -38,9 +37,11 @@ NSString* docsPath = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)[0]; // first check for correct extension - if ([[resourcePath pathExtension] caseInsensitiveCompare:RECORDING_WAV] != NSOrderedSame) { + NSString* ext=[resourcePath pathExtension]; + if ([ext caseInsensitiveCompare:@"wav"] != NSOrderedSame && + [ext caseInsensitiveCompare:@"m4a"] != NSOrderedSame) { resourceURL = nil; - NSLog(@"Resource for recording must have %@ extension", RECORDING_WAV); + NSLog(@"Resource for recording must have wav or m4a extension"); } else if ([resourcePath hasPrefix:DOCUMENTS_SCHEME_PREFIX]) { // try to find Documents:// resources filePath = [resourcePath stringByReplacingOccurrencesOfString:DOCUMENTS_SCHEME_PREFIX withString:[NSString stringWithFormat:@"%@/", docsPath]]; @@ -136,7 +137,6 @@ BOOL bError = NO; CDVMediaError errcode = MEDIA_ERR_NONE_SUPPORTED; NSString* errMsg = @""; - NSString* jsString = nil; CDVAudioFile* audioFile = nil; NSURL* resourceURL = nil; @@ -174,8 +174,8 @@ } if (bError) { - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%@);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, [self createMediaErrorWithCode:errcode message:errMsg]]; - [self.commandDelegate evalJs:jsString]; + [self onStatus:MEDIA_ERROR mediaId:mediaId param: + [self createMediaErrorWithCode:errcode message:errMsg]]; } return audioFile; @@ -207,15 +207,19 @@ } // helper function to create a error object string -- (NSString*)createMediaErrorWithCode:(CDVMediaError)code message:(NSString*)message +- (NSDictionary*)createMediaErrorWithCode:(CDVMediaError)code message:(NSString*)message { NSMutableDictionary* errorDict = [NSMutableDictionary dictionaryWithCapacity:2]; [errorDict setObject:[NSNumber numberWithUnsignedInteger:code] forKey:@"code"]; [errorDict setObject:message ? message:@"" forKey:@"message"]; + return errorDict; +} - NSData* jsonData = [NSJSONSerialization dataWithJSONObject:errorDict options:0 error:nil]; - return [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding]; +//helper function to create specifically an abort error +-(NSDictionary*)createAbortError:(NSString*)message +{ + return [self createMediaErrorWithCode:MEDIA_ERR_ABORTED message:message]; } - (void)create:(CDVInvokedUrlCommand*)command @@ -227,8 +231,8 @@ if (audioFile == nil) { NSString* errorMessage = [NSString stringWithFormat:@"Failed to initialize Media file with path %@", resourcePath]; - NSString* jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%@);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, [self createMediaErrorWithCode:MEDIA_ERR_ABORTED message:errorMessage]]; - [self.commandDelegate evalJs:jsString]; + [self onStatus:MEDIA_ERROR mediaId:mediaId param: + [self createAbortError:errorMessage]]; } else { NSURL* resourceUrl = audioFile.resourceURL; @@ -326,7 +330,6 @@ NSDictionary* options = [command argumentAtIndex:2 withDefault:nil]; BOOL bError = NO; - NSString* jsString = nil; CDVAudioFile* audioFile = [self audioFileForResource:resourcePath withId:mediaId doValidation:YES forRecording:NO]; if ((audioFile != nil) && (audioFile.resourceURL != nil)) { @@ -400,8 +403,8 @@ duration = round(audioFile.player.duration * 1000) / 1000; } - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%.3f);\n%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_DURATION, duration, @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_STATE, MEDIA_RUNNING]; - [self.commandDelegate evalJs:jsString]; + [self onStatus:MEDIA_DURATION mediaId:mediaId param:@(duration)]; + [self onStatus:MEDIA_STATE mediaId:mediaId param:@(MEDIA_RUNNING)]; } } if (bError) { @@ -418,9 +421,8 @@ [audioFile.player play]; } */ // error creating the session or player - // jsString = [NSString stringWithFormat: @"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, MEDIA_ERR_NONE_SUPPORTED]; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%@);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, [self createMediaErrorWithCode:MEDIA_ERR_NONE_SUPPORTED message:nil]]; - [self.commandDelegate evalJs:jsString]; + [self onStatus:MEDIA_ERROR mediaId:mediaId + param:[self createMediaErrorWithCode:MEDIA_ERR_NONE_SUPPORTED message:nil]]; } } // else audioFile was nil - error already returned from audioFile for resource @@ -484,13 +486,12 @@ { NSString* mediaId = [command argumentAtIndex:0]; CDVAudioFile* audioFile = [[self soundCache] objectForKey:mediaId]; - NSString* jsString = nil; if ((audioFile != nil) && (audioFile.player != nil)) { NSLog(@"Stopped playing audio sample '%@'", audioFile.resourcePath); [audioFile.player stop]; audioFile.player.currentTime = 0; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_STATE, MEDIA_STOPPED]; + [self onStatus:MEDIA_STATE mediaId:mediaId param:@(MEDIA_STOPPED)]; } // seek to start and pause if (avPlayer.currentItem && avPlayer.currentItem.asset) { @@ -502,24 +503,20 @@ completionHandler: ^(BOOL finished){ if (finished) [avPlayer pause]; }]; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_STATE, MEDIA_STOPPED]; + [self onStatus:MEDIA_STATE mediaId:mediaId param:@(MEDIA_STOPPED)]; } else { // cannot seek, wrong state CDVMediaError errcode = MEDIA_ERR_NONE_ACTIVE; NSString* errMsg = @"Cannot service stop request until the avPlayer is in 'AVPlayerStatusReadyToPlay' state."; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%@);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, [self createMediaErrorWithCode:errcode message:errMsg]]; + [self onStatus:MEDIA_ERROR mediaId:mediaId param: + [self createMediaErrorWithCode:errcode message:errMsg]]; } } - // ignore if no media playing - if (jsString) { - [self.commandDelegate evalJs:jsString]; - } } - (void)pausePlayingAudio:(CDVInvokedUrlCommand*)command { NSString* mediaId = [command argumentAtIndex:0]; - NSString* jsString = nil; CDVAudioFile* audioFile = [[self soundCache] objectForKey:mediaId]; if ((audioFile != nil) && ((audioFile.player != nil) || (avPlayer != nil))) { @@ -530,12 +527,7 @@ [avPlayer pause]; } - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_STATE, MEDIA_PAUSED]; - } - // ignore if no media playing - - if (jsString) { - [self.commandDelegate evalJs:jsString]; + [self onStatus:MEDIA_STATE mediaId:mediaId param:@(MEDIA_PAUSED)]; } } @@ -550,7 +542,6 @@ CDVAudioFile* audioFile = [[self soundCache] objectForKey:mediaId]; double position = [[command argumentAtIndex:1] doubleValue]; double posInSeconds = position / 1000; - NSString* jsString; if ((audioFile != nil) && (audioFile.player != nil)) { @@ -558,12 +549,10 @@ // The seek is past the end of file. Stop media and reset to beginning instead of seeking past the end. [audioFile.player stop]; audioFile.player.currentTime = 0; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%.3f);\n%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_POSITION, 0.0, @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_STATE, MEDIA_STOPPED]; - // NSLog(@"seekToEndJsString=%@",jsString); + [self onStatus:MEDIA_STATE mediaId:mediaId param:@(MEDIA_STOPPED)]; } else { audioFile.player.currentTime = posInSeconds; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%f);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_POSITION, posInSeconds]; - // NSLog(@"seekJsString=%@",jsString); + [self onStatus:MEDIA_POSITION mediaId:mediaId param:@(posInSeconds)]; } } else if (avPlayer != nil) { @@ -584,13 +573,11 @@ if (isPlaying) [avPlayer play]; }]; } else { - CDVMediaError errcode = MEDIA_ERR_ABORTED; NSString* errMsg = @"AVPlayerItem cannot service a seek request with a completion handler until its status is AVPlayerItemStatusReadyToPlay."; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%@);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, [self createMediaErrorWithCode:errcode message:errMsg]]; + [self onStatus:MEDIA_ERROR mediaId:mediaId param: + [self createAbortError:errMsg]]; } } - - [self.commandDelegate evalJs:jsString]; } @@ -642,8 +629,7 @@ CDVPluginResult* result = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsDouble:position]; - NSString* jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%.3f);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_POSITION, position]; - [self.commandDelegate evalJs:jsString]; + [self onStatus:MEDIA_POSITION mediaId:mediaId param:@(position)]; [self.commandDelegate sendPluginResult:result callbackId:callbackId]; } @@ -655,7 +641,6 @@ NSString* mediaId = [command argumentAtIndex:0]; CDVAudioFile* audioFile = [self audioFileForResource:[command argumentAtIndex:1] withId:mediaId doValidation:YES forRecording:YES]; - __block NSString* jsString = nil; __block NSString* errorMsg = @""; if ((audioFile != nil) && (audioFile.resourceURL != nil)) { @@ -678,19 +663,27 @@ if (![weakSelf.avSession setActive:YES error:&error]) { // other audio with higher priority that does not allow mixing could cause this to fail errorMsg = [NSString stringWithFormat:@"Unable to record audio: %@", [error localizedFailureReason]]; - // jsString = [NSString stringWithFormat: @"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, MEDIA_ERR_ABORTED]; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%@);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, [weakSelf createMediaErrorWithCode:MEDIA_ERR_ABORTED message:errorMsg]]; - [weakSelf.commandDelegate evalJs:jsString]; + [weakSelf onStatus:MEDIA_ERROR mediaId:mediaId param: + [self createAbortError:errorMsg]]; return; } } // create a new recorder for each start record - NSDictionary *audioSettings = @{AVFormatIDKey: @(kAudioFormatMPEG4AAC), - AVSampleRateKey: @(44100), + bool isWav=[[audioFile.resourcePath pathExtension] isEqualToString:@"wav"]; + NSMutableDictionary *audioSettings = [NSMutableDictionary dictionaryWithDictionary: + @{AVSampleRateKey: @(44100), AVNumberOfChannelsKey: @(1), - AVEncoderAudioQualityKey: @(AVAudioQualityMedium) - }; + }]; + if (isWav) { + audioSettings[AVFormatIDKey]=@(kAudioFormatLinearPCM); + audioSettings[AVLinearPCMBitDepthKey]=@(16); + audioSettings[AVLinearPCMIsBigEndianKey]=@(false); + audioSettings[AVLinearPCMIsFloatKey]=@(false); + } else { + audioSettings[AVFormatIDKey]=@(kAudioFormatMPEG4AAC); + audioSettings[AVEncoderAudioQualityKey]=@(AVAudioQualityMedium); + } audioFile.recorder = [[CDVAudioRecorder alloc] initWithURL:audioFile.resourceURL settings:audioSettings error:&error]; bool recordingSuccess = NO; @@ -701,8 +694,7 @@ recordingSuccess = [audioFile.recorder record]; if (recordingSuccess) { NSLog(@"Started recording audio sample '%@'", audioFile.resourcePath); - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_STATE, MEDIA_RUNNING]; - [weakSelf.commandDelegate evalJs:jsString]; + [weakSelf onStatus:MEDIA_STATE mediaId:mediaId param:@(MEDIA_RUNNING)]; } } @@ -716,8 +708,8 @@ if (weakSelf.avSession) { [weakSelf.avSession setActive:NO error:nil]; } - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%@);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, [weakSelf createMediaErrorWithCode:MEDIA_ERR_ABORTED message:errorMsg]]; - [weakSelf.commandDelegate evalJs:jsString]; + [weakSelf onStatus:MEDIA_ERROR mediaId:mediaId param: + [self createAbortError:errorMsg]]; } }; @@ -736,8 +728,8 @@ if (weakSelf.avSession) { [weakSelf.avSession setActive:NO error:nil]; } - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%@);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, [self createMediaErrorWithCode:MEDIA_ERR_ABORTED message:msg]]; - [weakSelf.commandDelegate evalJs:jsString]; + [weakSelf onStatus:MEDIA_ERROR mediaId:mediaId param: + [self createAbortError:msg]]; } }]; #pragma clang diagnostic pop @@ -748,8 +740,8 @@ } else { // file did not validate NSString* errorMsg = [NSString stringWithFormat:@"Could not record audio at '%@'", audioFile.resourcePath]; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%@);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, [self createMediaErrorWithCode:MEDIA_ERR_ABORTED message:errorMsg]]; - [self.commandDelegate evalJs:jsString]; + [self onStatus:MEDIA_ERROR mediaId:mediaId param: + [self createAbortError:errorMsg]]; } } @@ -758,17 +750,12 @@ NSString* mediaId = [command argumentAtIndex:0]; CDVAudioFile* audioFile = [[self soundCache] objectForKey:mediaId]; - NSString* jsString = nil; if ((audioFile != nil) && (audioFile.recorder != nil)) { NSLog(@"Stopped recording audio sample '%@'", audioFile.resourcePath); [audioFile.recorder stop]; // no callback - that will happen in audioRecorderDidFinishRecording } - // ignore if no media recording - if (jsString) { - [self.commandDelegate evalJs:jsString]; - } } - (void)audioRecorderDidFinishRecording:(AVAudioRecorder*)recorder successfully:(BOOL)flag @@ -776,21 +763,19 @@ CDVAudioRecorder* aRecorder = (CDVAudioRecorder*)recorder; NSString* mediaId = aRecorder.mediaId; CDVAudioFile* audioFile = [[self soundCache] objectForKey:mediaId]; - NSString* jsString = nil; if (audioFile != nil) { NSLog(@"Finished recording audio sample '%@'", audioFile.resourcePath); } if (flag) { - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_STATE, MEDIA_STOPPED]; + [self onStatus:MEDIA_STATE mediaId:mediaId param:@(MEDIA_STOPPED)]; } else { - // jsString = [NSString stringWithFormat: @"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, MEDIA_ERR_DECODE]; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%@);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, [self createMediaErrorWithCode:MEDIA_ERR_DECODE message:nil]]; + [self onStatus:MEDIA_ERROR mediaId:mediaId param: + [self createMediaErrorWithCode:MEDIA_ERR_DECODE message:nil]]; } if (self.avSession) { [self.avSession setActive:NO error:nil]; } - [self.commandDelegate evalJs:jsString]; } - (void)audioPlayerDidFinishPlaying:(AVAudioPlayer*)player successfully:(BOOL)flag @@ -799,34 +784,30 @@ CDVAudioPlayer* aPlayer = (CDVAudioPlayer*)player; NSString* mediaId = aPlayer.mediaId; CDVAudioFile* audioFile = [[self soundCache] objectForKey:mediaId]; - NSString* jsString = nil; if (audioFile != nil) { NSLog(@"Finished playing audio sample '%@'", audioFile.resourcePath); } if (flag) { audioFile.player.currentTime = 0; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_STATE, MEDIA_STOPPED]; + [self onStatus:MEDIA_STATE mediaId:mediaId param:@(MEDIA_STOPPED)]; } else { - // jsString = [NSString stringWithFormat: @"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, MEDIA_ERR_DECODE]; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%@);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_ERROR, [self createMediaErrorWithCode:MEDIA_ERR_DECODE message:nil]]; + [self onStatus:MEDIA_ERROR mediaId:mediaId param: + [self createMediaErrorWithCode:MEDIA_ERR_DECODE message:nil]]; } if (self.avSession) { [self.avSession setActive:NO error:nil]; } - [self.commandDelegate evalJs:jsString]; } -(void)itemDidFinishPlaying:(NSNotification *) notification { // Will be called when AVPlayer finishes playing playerItem NSString* mediaId = self.currMediaId; - NSString* jsString = nil; - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_STATE, MEDIA_STOPPED]; if (self.avSession) { [self.avSession setActive:NO error:nil]; } - [self.commandDelegate evalJs:jsString]; + [self onStatus:MEDIA_STATE mediaId:mediaId param:@(MEDIA_STOPPED)]; } -(void)itemStalledPlaying:(NSNotification *) notification { @@ -900,19 +881,14 @@ NSString* mediaId = [command argumentAtIndex:0]; CDVAudioFile* audioFile = [[self soundCache] objectForKey:mediaId]; - NSString* jsString = nil; if ((audioFile != nil) && (audioFile.recorder != nil)) { NSLog(@"Resumed recording audio sample '%@'", audioFile.resourcePath); [audioFile.recorder record]; // no callback - that will happen in audioRecorderDidFinishRecording - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_STATE, MEDIA_RUNNING]; + [self onStatus:MEDIA_STATE mediaId:mediaId param:@(MEDIA_RUNNING)]; } - // ignore if no media recording - if (jsString) { - [self.commandDelegate evalJs:jsString]; - } } - (void)pauseRecordingAudio:(CDVInvokedUrlCommand*)command @@ -920,22 +896,47 @@ NSString* mediaId = [command argumentAtIndex:0]; CDVAudioFile* audioFile = [[self soundCache] objectForKey:mediaId]; - NSString* jsString = nil; if ((audioFile != nil) && (audioFile.recorder != nil)) { NSLog(@"Paused recording audio sample '%@'", audioFile.resourcePath); [audioFile.recorder pause]; // no callback - that will happen in audioRecorderDidFinishRecording - // no callback - that will happen in audioRecorderDidFinishRecording - jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%d);", @"cordova.require('cordova-plugin-media.Media').onStatus", mediaId, MEDIA_STATE, MEDIA_PAUSED]; + [self onStatus:MEDIA_STATE mediaId:mediaId param:@(MEDIA_PAUSED)]; } - - // ignore if no media recording - if (jsString) { - [self.commandDelegate evalJs:jsString]; - } } +- (void)messageChannel:(CDVInvokedUrlCommand*)command +{ + self.statusCallbackId = command.callbackId; +} + +- (void)onStatus:(CDVMediaMsg)what mediaId:(NSString*)mediaId param:(NSObject*)param +{ + if (self.statusCallbackId!=nil) { //new way, android,windows compatible + NSMutableDictionary* status=[NSMutableDictionary dictionary]; + status[@"msgType"] = @(what); + //in the error case contains a dict with "code" and "message" + //otherwise a NSNumber + status[@"value"] = param; + status[@"id"] = mediaId; + NSMutableDictionary* dict=[NSMutableDictionary dictionary]; + dict[@"action"] = @"status"; + dict[@"status"] = status; + CDVPluginResult* result = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsDictionary:dict]; + [result setKeepCallbackAsBool:YES]; //we keep this forever + [self.commandDelegate sendPluginResult:result callbackId:self.statusCallbackId]; + } else { //old school evalJs way + if (what==MEDIA_ERROR) { + NSData* jsonData = [NSJSONSerialization dataWithJSONObject:param options:0 error:nil]; + param=[[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding]; + } + NSString* jsString = [NSString stringWithFormat:@"%@(\"%@\",%d,%@);", + @"cordova.require('cordova-plugin-media.Media').onStatus", + mediaId, (int)what, param]; + [self.commandDelegate evalJs:jsString]; + } +} + @end @implementation CDVAudioFile --------------------------------------------------------------------- To unsubscribe, e-mail: commits-unsubscribe@cordova.apache.org For additional commands, e-mail: commits-help@cordova.apache.org