2015-08-05 16 views
6

Ho riscontrato un problema con Youtube Iframe Api utilizzato con angularjs.Youtube iframe Api e rotta Angularjs

Penso che il problema sia la chiamata della funzione "onYouTubeIframeAPIReady".

Io uso angularjs con percorsi e la funzione non si attiva quando il percorso viene modificato, tuttavia quando prendo F5 è ok il lettore è caricato.

C'è un modo per rendere angularjs con i percorsi e le API di youtube funzionano?

Non sono riuscito ad aggiungere più file nel codice, ma "pageX.htm" assomiglia a questo:

<button ng-click="video()">Create</button> 
<div youtube-player id="test-playerX" ></div> 

e v'è il codice per "index.htm"

<!DOCTYPE html> 
 
<html ng-app="sc"> 
 
    <body> 
 

 
    Homepage - <a href="#page1">Page1</a> - <a href="#page2">Page2</a> 
 

 
    <div ng-view></div> 
 

 
    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.3/angular.min.js"></script> 
 
    <script src="https://code.angularjs.org/1.4.3/angular-route.min.js"></script> 
 
    
 
    <script> 
 
     var sc = angular.module('sc', ['ngRoute']); 
 

 
     sc.config(['$routeProvider', function($routeProvider) { 
 
     $routeProvider 
 
      .when('/page1', { 
 
      templateUrl: 'page1.htm' 
 
      }) 
 
      .when('/page2', { 
 
      templateUrl: 'page2.htm' 
 
      }) 
 
     }]); 
 

 
      // Run 
 
     sc.run(['$rootScope', function($rootScope) { 
 

 
       var tag = document.createElement('script'); 
 

 
       // This is a protocol-relative URL as described here: 
 
       //  http://paulirish.com/2010/the-protocol-relative-url/ 
 
       // If you're testing a local page accessed via a file:/// URL, please set tag.src to 
 
       //  "https://www.youtube.com/iframe_api" instead. 
 
       tag.src = "http://www.youtube.com/iframe_api"; 
 
       var firstScriptTag = document.getElementsByTagName('script')[0]; 
 
       firstScriptTag.parentNode.insertBefore(tag, firstScriptTag); 
 
      }]); 
 

 

 
     sc.service('youtubePlayerApi', ['$window', '$rootScope', '$log', function ($window, $rootScope, $log) { 
 
     var service = $rootScope.$new(true); 
 

 
     // Youtube callback when API is ready 
 
     $window.onYouTubeIframeAPIReady = function() { 
 
      $log.info('Youtube API is ready'); 
 
      service.ready = true; 
 
      service.createPlayer(); 
 
     }; 
 

 
     service.ready = false; 
 
     service.playerId = null; 
 
     service.player = null; 
 
     service.videoId = "sGPrx9bjgC8"; 
 
     service.playerHeight = '390'; 
 
     service.playerWidth = '640'; 
 

 
     service.bindVideoPlayer = function (elementId) { 
 
      $log.info('Binding to player ' + elementId); 
 
      service.playerId = elementId; 
 
     }; 
 

 
     service.createPlayer = function() { 
 
      $log.info('Creating a new Youtube player for DOM id ' + this.playerId + ' and video ' + this.videoId); 
 
      return new YT.Player(this.playerId, { 
 
       height: this.playerHeight, 
 
       width: this.playerWidth, 
 
       videoId: this.videoId 
 
      }); 
 
     }; 
 

 
     service.loadPlayer = function() { 
 
      // API ready? 
 
      if (this.ready && this.playerId && this.videoId) { 
 
       if(this.player) { 
 
        this.player.destroy(); 
 
       } 
 

 
       this.player = this.createPlayer(); 
 
      } 
 
     }; 
 

 
     return service; 
 
     }]); 
 

 
     sc.directive('youtubePlayer', ['youtubePlayerApi', function (youtubePlayerApi) { 
 
      return { 
 
       restrict:'A', 
 
       link:function (scope, element) { 
 
        youtubePlayerApi.bindVideoPlayer(element[0].id); 
 
       } 
 
      }; 
 
     }]); 
 
     
 
     sc.controller('replaycontroller', function ($scope,youtubePlayerApi) { 
 
       $scope.video = function() { 
 
       youtubePlayerApi.createPlayer(); 
 
       console.log("test"); 
 
       } 
 

 
      }); 
 
    </script> 
 

 

 
    </body> 
 
</html>

Qualsiasi aiuto è apprezzato :)

[EDIT]: Ho aggiornato il codice per testare la funzione createPlayer e confermare che il lettore funziona quando si cambiano le pagine

risposta

2

OK Ho trovato una soluzione, non è molto pulita ma funziona.

Ammetto che nel controller quando si cambiano percorsi, l'API di youtube è già inizializzata. Quindi il controller crea solo il giocatore.

Quando F5 o caricamento iniziale richiesto, è necessario attivareYouTubeIframeAPIReady per istanziare il lettore.

Ecco il codice:

<!DOCTYPE html> 
 
<html ng-app="sc"> 
 
    <body> 
 

 
    Homepage - <a href="#page1">Page1</a> - <a href="#page2">Page2</a> 
 

 
    <div ng-view></div> 
 

 
    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.3/angular.min.js"></script> 
 
    <script src="https://code.angularjs.org/1.4.3/angular-route.min.js"></script> 
 
    
 
    <script> 
 
     var sc = angular.module('sc', ['ngRoute']); 
 

 
     sc.config(['$routeProvider', function($routeProvider) { 
 
     $routeProvider 
 
      .when('/page1', { 
 
      templateUrl: 'page1.htm', 
 
      controller: 'replaycontroller' 
 
      }) 
 
      .when('/page2', { 
 
      templateUrl: 'page2.htm' 
 
      }) 
 
     }]); 
 

 
      // Run 
 
     sc.run(['$rootScope', function($rootScope) { 
 
       var tag = document.createElement('script'); 
 

 
       // This is a protocol-relative URL as described here: 
 
       //  http://paulirish.com/2010/the-protocol-relative-url/ 
 
       // If you're testing a local page accessed via a file:/// URL, please set tag.src to 
 
       //  "https://www.youtube.com/iframe_api" instead. 
 
       tag.src = "http://www.youtube.com/iframe_api"; 
 
       var firstScriptTag = document.getElementsByTagName('script')[0]; 
 
       firstScriptTag.parentNode.insertBefore(tag, firstScriptTag); 
 
       
 
      }]); 
 

 

 
     sc.service('youtubePlayerApi', ['$window', '$rootScope', '$log', function ($window, $rootScope, $log) { 
 
     var service = $rootScope.$new(true); 
 

 
     // Youtube callback when API is ready 
 
     $window.onYouTubeIframeAPIReady = function() { 
 
      $log.info('Youtube API is ready'); 
 
      service.ready = true; 
 
      service.createPlayer(); 
 
     }; 
 

 
     service.ready = false; 
 
     service.playerId = null; 
 
     service.player = null; 
 
     service.videoId = "sGPrx9bjgC8"; 
 
     service.playerHeight = '390'; 
 
     service.playerWidth = '640'; 
 

 
     service.getStatus = function() { 
 
      return service.ready; 
 
     }; 
 

 
     service.bindVideoPlayer = function (elementId) { 
 
      $log.info('Binding to player ' + elementId); 
 
      service.playerId = elementId; 
 
     }; 
 

 
     service.createPlayer = function() { 
 
      $log.info('Creating a new Youtube player for DOM id ' + this.playerId + ' and video ' + this.videoId); 
 
      return new YT.Player(this.playerId, { 
 
       height: this.playerHeight, 
 
       width: this.playerWidth, 
 
       videoId: this.videoId 
 
      }); 
 
     }; 
 

 
     service.loadPlayer = function() { 
 
      // API ready? 
 
      if (this.ready && this.playerId && this.videoId) { 
 
       if(this.player) { 
 
        this.player.destroy(); 
 
       } 
 

 
       this.player = this.createPlayer(); 
 
      } 
 
     }; 
 

 
     return service; 
 
     }]); 
 

 
     sc.directive('youtubePlayer', ['youtubePlayerApi', function (youtubePlayerApi) { 
 
      return { 
 
       restrict:'A', 
 
       link:function (scope, element) { 
 
        youtubePlayerApi.bindVideoPlayer(element[0].id); 
 
       } 
 
      }; 
 
     }]); 
 

 
     sc.controller('replaycontroller', function ($scope,youtubePlayerApi) { 
 
     if (youtubePlayerApi.getStatus() == true) { 
 
      youtubePlayerApi.bindVideoPlayer("test-player1"); 
 
      youtubePlayerApi.createPlayer(); 
 
     } 
 
     }); 
 

 
     
 
    </script> 
 

 

 
    </body> 
 
</html>

+0

Come hai usarlo finalmente? Come posso usarlo con più video di youtube sulla stessa pagina? Quindi in pratica avrò tutti gli ID dei video di youtube in un array, e mi piacerebbe inizializzarli sulla pagina come video in una ng-repeat e quindi catturare gli eventi su ognuno di essi individualmente. Qualche idea su come si possa fare? –

+0

Ciao finalmente non uso più youtube api ma tag iframe su youtube ... Non è davvero facile implementare l'API di YouTube su un'app angularjs. Spiacente, non ho aiutato – djutopie

+0

trovato il modo migliore per farlo. Se vuoi implementarlo tu stesso, utilizza l'API iFrame di Google. oppure utilizzare il repo angolare https://github.com/brandly/angular-youtube-embed. Ho usato quest'ultimo. :) –

Problemi correlati