2015-01-15 77 views
0

我有以下的Angular JS服務正在訪問cordova media插件。科爾多瓦媒體,如何獲得循環播放回調?

MediaSrv.loadMedia(filePath, mediaSuccess, null, status).then(function(media, status, test, status1){ 
        media.play({ numberOfLoops: 999 }); 
        media.setVolume(volume); 
        $scope.selectedSounds[index].state = 1; 
        $scope.selectedSounds[index].mediaInstance = media; 
        $scope.someSoundsArePlaying = true; 
       }); 

我想問一下,我該怎麼辦所選文件的循環再生,可以通過mediaInstance停止功能後停止?

我試過mediaSuccess回撥和狀態回叫,但它不能正常工作。

服務是以下幾點:

'use strict'; 

angular.module('MaxRelax') 
    .factory('MediaSrv', function($q, $ionicPlatform, $window){ 
     var service = { 
      loadMedia: loadMedia, 
      getStatusMessage: getStatusMessage, 
      getErrorMessage: getErrorMessage 
     }; 

     function loadMedia(src, onError, onStatus, onStop){ 
      var defer = $q.defer(); 
      $ionicPlatform.ready(function(){ 
       var mediaSuccess = function(){ 
        if(onStop){onStop();} 
       }; 
       var mediaError = function(err){ 
        _logError(src, err); 
        if(onError){onError(err);} 
       }; 
       var mediaStatus = function(status){ 
        console.log(status); 
        if(onStatus){onStatus(status);} 
       }; 

       if($ionicPlatform.is('android')){src = '/android_asset/www/' + src;} 
       defer.resolve(new $window.Media(src, mediaSuccess, mediaError, mediaStatus)); 
      }); 
      return defer.promise; 
     } 

     function _logError(src, err){ 
      console.error('media error', { 
       code: err.code, 
       message: getErrorMessage(err.code) 
      }); 
     } 

     function getStatusMessage(status){ 
      if(status === 0){return 'Media.MEDIA_NONE';} 
      else if(status === 1){return 'Media.MEDIA_STARTING';} 
      else if(status === 2){return 'Media.MEDIA_RUNNING';} 
      else if(status === 3){return 'Media.MEDIA_PAUSED';} 
      else if(status === 4){return 'Media.MEDIA_STOPPED';} 
      else {return 'Unknown status <'+status+'>';} 
     } 

     function getErrorMessage(code){ 
      if(code === 1){return 'MediaError.MEDIA_ERR_ABORTED';} 
      else if(code === 2){return 'MediaError.MEDIA_ERR_NETWORK';} 
      else if(code === 3){return 'MediaError.MEDIA_ERR_DECODE';} 
      else if(code === 4){return 'MediaError.MEDIA_ERR_NONE_SUPPORTED';} 
      else {return 'Unknown code <'+code+'>';} 
     } 

     return service; 
    }); 

很多,任何幫助非常感謝。

編輯:

項目的播放是通過以下方法處理:

$scope.playSelectedItem = function(index) { 
      try { 
       var fileName = $scope.selectedSounds[index].file; 
       var volume = $scope.selectedSounds[index].defaultVolume; 
       var filePath = "sounds/" +fileName+".mp3"; 
       console.log(filePath); 
       MediaSrv.loadMedia(
        filePath, 
        function onError(err){ console.log('onError', MediaSrv.getErrorMessage(err)); }, 
        function onStatus(status){ console.log('onStatus', MediaSrv.getStatusMessage(status)); }, 
        function onStop(){ console.log('onStop'); myMedia.play(); } 
       ).then(function(media){ 
        myMedia = media; 
        media.play({ numberOfLoops: 999 }); 
        media.setVolume(volume); 
        $scope.selectedSounds[index].state = 1; 
        $scope.selectedSounds[index].mediaInstance = media; 
        $scope.someSoundsArePlaying = true; 
       }); 
      } catch(e) { 
       alert(JSON.stringify(e)); 
       console.log(e); 
       $scope.showAlert("Error", "Error during the playing item"); 
      } 
     }; 

停車:

$scope.stopSelectedItem = function(index) { 
      try { 
       var leng = 0; 
       if($scope.selectedSounds[index].state == 1) { 
        var mediaInstance = $scope.selectedSounds[index].mediaInstance; 
        mediaInstance.stop(); 
        $scope.selectedSounds[index].state = 0; 
        $scope.selectedSounds[index].mediaInstance = ""; 
        myMedia.stop(); 
       } 

       angular.forEach($scope.selectedSounds, function loadMedia(selectedSound, idx){ 
        if($scope.selectedSounds[idx].state == 1) { 
         leng ++; 
        } 
       }); 

       if(leng <= 0) { 
        $scope.someSoundsArePlaying = false; 
        console.log("No sound are playing"); 
       } 
       if(leng > 0) { 
        $scope.someSoundsArePlaying = true; 
        console.log("Some sound are playing"); 
       } 
       console.log("Leng is:"); 
       console.log(leng); 
      } catch(e) { 
       alert(JSON.stringify(e)); 
       console.log(e); 
       $scope.showAlert("Error", "Cannot stop playing of item"); 
      } 
     }; 

EDIT2:

我終於解決了它使用簡單的數組中存儲myMedia實例。

$scope.playSelectedItem = function(index) { 
      try { 
       var fileName = $scope.selectedSounds[index].file; 
       var volume = $scope.selectedSounds[index].defaultVolume; 
       var filePath = "sounds/" +fileName+".mp3"; 
       console.log(filePath); 
       MediaSrv.loadMedia(
        filePath, 
        function onError(err){ console.log('onError', MediaSrv.getErrorMessage(err)); }, 
        function onStatus(status){ console.log('onStatus', MediaSrv.getStatusMessage(status)); }, 
        function onStop(){ 
         console.log('onStop'); 
         if($scope.selectedSounds[index].state == 1) { 
          console.log('For index ' +index+' is state '+$scope.selectedSounds[index].state); 
          myMedia[index].play(); 
         } 

        } 
       ).then(function(media){ 
        myMedia[index] = media; 
        media.play({ numberOfLoops: 999 }); 
        media.setVolume(volume); 
        $scope.selectedSounds[index].state = 1; 
        $scope.selectedSounds[index].mediaInstance = media; 
        $scope.someSoundsArePlaying = true; 
       }); 
      } catch(e) { 
       alert(JSON.stringify(e)); 
       console.log(e); 
       $scope.showAlert("Error", "Error during the playing item"); 
      } 
     }; 

回答

1

我很高興你發現我的角度服務有用。

在您的例子中,你似乎亂用參數順序:
MediaSrv.loadMedia(filePath, mediaSuccess, null, status) VS
function loadMedia(src, onError, onStatus, onStop)

BTW,播放參數numberOfLoops似乎並不工作(至少在我nexus4)。如果您想循環播放,則每當mp3結束時您都需要撥打play()

下面是一個簡單的例子:

var myMedia = null; 
MediaSrv.loadMedia(
    'sounds/1023.mp3', 
    function onError(err){ console.log('onError', MediaSrv.getErrorMessage(err)); }, 
    function onStatus(status){ console.log('onStatus', MediaSrv.getStatusMessage(status)); }, 
    function onStop(){ console.log('onError'); myMedia.play(); }, 
).then(function(media){ 
    myMedia = media; 
    myMedia.play(); 
}); 

有了這個代碼,你的聲音應該發揮,永遠......要控制你的聲音應該停下來,我建議你添加一個控制參數,如下所示:

var myMedia = null; 
var shouldPlay = false; 
MediaSrv.loadMedia(
    'sounds/1023.mp3', 
    function onError(err){ console.log('onError', MediaSrv.getErrorMessage(err)); }, 
    function onStatus(status){ console.log('onStatus', MediaSrv.getStatusMessage(status)); }, 
    function onStop(){ console.log('onError'); if(shouldPlay){myMedia.play();} }, 
).then(function(media){ 
    myMedia = media; 
}); 

function playStart(){ 
    shouldPlay = true; 
    myMedia.play(); 
} 
function playStop(){ 
    shouldPlay = false; 
    myMedia.stop(); 
} 

要循環播放多個文件,您必須存儲所有媒體引用並連續播放它們。看到有:

var shouldPlay = false; 
var playingMedia = null; 
var soundFiles = ['sounds/1.mp3', 'sounds/2.mp3', 'sounds/3.mp3']; 
var mediaInstances = []; 
var onPlayStop = function(){ 
    if(shouldPlay){ 
     if(playingMedia === null){ 
      playingMedia = 0; 
     } else { 
      playingMedia = (playingMedia+1) % mediaInstances.length; 
     } 
     mediaInstances[playingMedia].play(); 
    } 
}; 
for(var i in soundFiles){ 
    MediaSrv.loadMedia(soundFiles[i], null, null, onPlayStop).then(function(media){ 
     mediaInstances.push(media); 
    }); 
} 

function playStart(){ 
    shouldPlay = true; 
    onPlayStop(); 
} 
function playStop(){ 
    shouldPlay = false; 
    mediaInstances[playingMedia].stop(); 
} 

我希望這將有助於:d

+0

非常感謝您的回覆,我想你的例子,但如果我想在循環播放多個聲音(例如問題,我想要在同一時間播放六種不同的聲音)。我剛剛更新了關於我用於播放和停止聲音的代碼的問題。 – redrom

+0

嗨,當然,如果你在同一時間播放很多歌曲,他們會做到這一點......;) 我沒有得到你的用例... 你想循環播放六個聲音? Like:s1,s2,s3,s4,s5,s6,s1,s2,s3,s4,s5,s6,s1,s2 ... –

+0

問題是,如果開始播放多個項目的時間只有最後一個(最後一項是循環播放) – redrom