THE SITUATION:
I am exploring AngularJS by re-building a former project with it. I am using the angularjs-rails gem version 1.2.16. I have a page were I make an API call that returns an array of objects of music events. CONTROLLER:
d2jiveControllers.controller('VenueResultsCtrl', ['$scope','$http','$routeParams',
'$compile', '$sce', 'spotifyFactory', function($scope, $http, $routeParams,
$compile, $sce, spotifyFactory){
"use strict";
var venueId = $routeParams.venueId;
var baseUrl = 'http://api.songkick.com/api/3.0/venues/';
var apiKey = '/calendar.json?apikey=************';
var url = baseUrl + venueId + apiKey + '&jsoncallback=JSON_CALLBACK' ;
var init = function(url){
$http.jsonp(url)
.success(function (data) {
$scope.events = data.resultsPage.results.event;
console.log(data);
}).
error(function(){
console.log('failure');
});
};
$scope.tracks = function(artistName){
var artistTracks = spotifyFactory.getArtistTracks(artistName);
var spotifyIframe = $('spotifyIframe');
$scope.show_tracks = $sce.trustAsHtml("<iframe src='https://embed.spotify.com/?uri=spotify:trackset:Playlist:"+artistTracks.spotifyTracks + "'"+
"&theme=white'width='300' height='300'frameborder='0' allowtransparency='true'></iframe>")
console.log(artistTracks)
};
init(url);
}]);
I list them out using ng-repeat and attach an ng-click to each listing. HTML TEMPLATE:
<div class="eventContainer row" ng-controller="VenueResultsCtrl">
<div ng-repeat="event in events">
<h4>
{{event.displayName}}
</h4>
<p>
<a href="{{event.uri}}" target="_blank"> Buy Tickets</a>
</p>
<div ng-repeat="artist in event.performance">
<button ng-click="tracks(artist.displayName)">Discover
{{artist.displayName}}<br> -- {{artist.billing}}</button><br><br>
<div ng-bind-html="show_tracks"></div>
</div>
</div>
</div>
On click I want to make another API call to Spotify to get back track IDs that I then place into an iframe. To do this I tried both making the call in a directive and factory:
DIRECTIVE:
d2jive.directive('getSpotifyTracks', [function () {
// <div get-spotify-tracks="artist.displayName"></div>
var spotifyUrl = "http://ws.spotify.com/search/1/track.json?callback=JSON_CALLBACK&q=";
return {
restrict: 'AEC',
scope: {
artistName: '='
},
templateUrl: 'assets/d2jive/templates/artistTracks.html',
controller: ['$scope', '$http', function($scope, $http){
$scope.getTracks = function(artistName){
$http.jsonp(spotifyUrl + encodeURIComponent(artistName))
.success(function (data) {
var trackArray = [];
var tracks = data.tracks.slice(0,9);
for (var track in tracks){
grabbedTrack = tracks[track].href.slice(
14, tracks[track].href.length);
trackArray.push(grabbedTrack);
}
$scope.artistTracks = trackArray;
console.log(data);
});
};
}],
link: function(scope, element, attrs, ctrl){
scope.$watch('artist.displayName', function(displayName){
if (displayName){
scope.getTracks(displayName);
}
})
}
}
}]);
FACTORY::
d2jive.factory('spotifyFactory', ['$http','$q', function($http, $q){
var factory = {}
factory.getArtistTracks = function(artistName){
var tracks = {}
var spotifyUrl = "http://ws.spotify.com/search/1/track.json?q=";
var deferred = $q.defer();
var getTracks = function(artistName){
$http.get(spotifyUrl + encodeURIComponent(artistName))
.success(function (data) {
deferred.resolve(data);
});
return deferred.promise;
};
// tracks.spotifyTrakcs = getTracks(artistName);
var spotifyTracks = getTracks(artistName);
spotifyTracks.then(function(result){
var trackArray = [];
var tracks = result.tracks.slice(0,9);
for (var track in tracks){
grabbedTrack = tracks[track].href.slice(
14, tracks[track].href.length);
trackArray.push(grabbedTrack);
}
tracks.spotifyTracks = trackArray;
});
return tracks;
}
return factory;
}]);
THE PROBLEM:
I can't find a way to append the iframe HTML to a particular item and not each event that is listed. The directive didn't seem to work because it loaded right away and slowed down the app way too much. That is why I went with a Factory to make the API call to Spotify and append the iframe.
THE GOAL:
On ng-click make API call to Spotify, return the track ID's, insert them into the iframe, and then insert that right below the clicked item not below all of the items.
Any help will be much appreciated! Thanks.