2017-01-11



alvinashcraft
shared this story
from Telerik Developer Network.

By Angular, we mean Angular 2.

In this tutorial, we’re going to build an iTunes Search application. The app will use the open iTunes JSONP API to search for artists, display albums by that artist in a Kendo UI Grid. Each album will be expanded to show a detail grid which will contain all of the tracks. Each track will be playable with Web Audio.



You can view the completed application and get all of the code on GitHub. If you get stuck at any point, I recommend downloading the completed project for reference.

Prerequisites

The Angular CLI

Creating The App

Start by creating a new application specifying Sass as the style language of choice. If you don’t know Sass, don’t worry. You can still write plain ole CSS in Sass files. Using Sass just gives us the ability to easily include third-party style libraries. The Angular CLI will wire up all of the necessary build steps.

Run the application and leave it open. The application usually runs on port 4200. See this article for a more detailed explanation.

Next, install the Bootstrap Sass package from npm.

Add the Bootstrap Sass references to your project in the src/styles.scss file.

The app will update automatically. It looks slightly different because of the sans-serif font that Bootstrap uses.

Add the following markup to the src/app/app.component.html.

Creating a Service

Next, create a service that will call the iTunes Search JSON API. The Angular Style Guide recommends putting these in a “shared” folder, so create the shared folder under src/app.

Create the service using the Angular CLI generators that will scaffold out components, services and the like.

Open the src/app/shared/itunes.service/ts file and add in the code that imports the JSONP support for Angular 2, the toPromise and catch methods from rxjs, and exposes a function that makes the HTTP call to the iTunes Service and returns a promise.

The JSONP module must also be injected in the src/app/app.module.ts file, otherwise it won’t be available for use here in the service.

Creating Components

Now we’re going to add the Artist Component, which will contain the search bar and artist results. It will also call the iTunes Service to do a search for artists.

This creates an src/app/artist folder. It also injects the component into the app.module.ts file so that it can be used in the application. The Angular CLI does all of this when you use the generate component command.

Add the following markup to the src/app/artist/artist.component.html file.

This markup creates the search box and a two column layout for the artist search results on the left. When the user clicks on an artist, all of that artists album’s will be shown in a grid on the right.

Open the src/app/artist/artist.component.ts file. Add in the necessary code to support the binding from the artist.component.html file. It needs a search method to call the iTunes Service as the user types, as well as a collection of searchResults that will be displayed on the page, and finally a getAlbums event to fire when the user clicks on an artist result.

Calling the iTunes Service

Now we’ll add the ability to retrieve albums by artist from the iTunes Service. Open the src/app/shared/itunes/service file and add the following.

This code contains a new function, getAlbums that retrieves albums by artist ID from the iTunes API. It also caches calls to getAlbums in case the function is called repetitively with the same parameters. User interfaces tend to do that a lot.

Next, create the Album Component using the Angular CLI component generator.

Adding in Kendo UI

Now add in the Kendo UI Grid for Angular. Before you do this, stop the dev server by pressing ctrl+c. This is necessary with Kendo UI to ensure that files that need to be copied aren’t in use.

Reference the Kendo UI Default Theme in the src/styles.scss file.

Add the Kendo UI Grid to the src/app/app.module.ts file.

Now add the following markup to the src/app/album/album.component.html file.

Getting Albums by Artist

Add the logic for the Album Component that will pull in albums from the iTunes Service based on an Artist ID.

The @Input allows us to specify a variable on the Album Component that can be set by the parent component, which in this case is the Artist Component. We use a setter to ensure that every time the Artist Component sets an Artist ID, the Albums component will update the contents of the grid by calling getAlbums. This is one way that Angular components can communicate with each other. For more information, see Component Interaction on the Angular docs.

Add the Album Component to the src/app/artist.component.html file. Note the use of the artistId, which gets passed to the @Input.

Now the Albums Component will display albums when an artist is selected.

Paging Through Results

Add paging to the Grid by setting the Grid to pageable, defining the page size (how many records to show per page), setting the skip parameter (how many records to skip from the start of the collection) and the pageChange event on the Grid component in src/app/album/album.component.html.

Modify the src/app/album/album.compoment.ts file to handle the pageChange event by calling the getAlbums method again and trim the resulting array to the proper items for the current page.

The Grid now has paging support.

Displaying Detailed Track Results

Each row has a little “+” symbol next to it indicating that you could expand the row to reveal more information. Right now, nothing happens. The desired behavior is to display all of the available tracks for the selected item. To do that, we’ll need a Tracks Component.

First, add a getTracks method to the src/app/shared/itunes.service.ts file which will return all of the tracks for a given Album ID.

Create the Tracks Component with the Angular CLI.

Open the src/app/track/track.component.html file and add the following markup.

Add the following code to the src/app/track/track.component.ts file. Note the use of the @Input parameter to pass the Album ID to the Tracks Component. This is the exact same feature that was used to pass the Artist ID from the Artist Component to the Album Component.

Now add the Tracks Component to the src/app/album/album.component.html file.

Playing the Audio

The iTunes API provides a URL to an audio sample for each track. The browser can use the Web Audio API to play these tracks.

Create a Player Component that will control the audio player for the application.

Add the following markup to the src/app/player/player.component.html file.

Add the following code to the src/app/player/player.component.ts file. This will handle setting the audio source (src) for the player, as well as handling what to do when a track sample stops finishes playing.

Add the Player Component to src/app/app.component.html. There is only one audio control for the entire application. All tracks will use this audio player when the user clicks the ‘play’ icon next to a track.

Next, create a Track Control Component that will create play/pause buttons for each track, and communicate with the Player Component.

Notice that this component is nested inside of the Track Component folder. This is due to the fact that, while not directly dependent on each other, they are very closely related and therefore logically belong in a hierarchical structure.

Add the following markup to the src/app/track/track-control/track-control.component.html file to display the play/pause icons using the Bootstrap icon font.

Add the code to the src/app/track/track-control/track-control.component.ts, which controls the state of the track (isPlaying), as well as the click events from the play/pause icons.

Now add the Track Control Component to the src/app/track/track.component.html file.

At this point, each track will display a play/pause button. Each track also knows what it’s own URL is for it’s corresponding audio sample. However, the Track Control Component cannot yet communicate with the Player Component, so while the button changes from a playing to a paused state, no audio is actually played.

In order to facilitate this communication, we will use a shared service. Create a new service called Player Service.

The Player Service will contain some rxjs Subscriptions that other components can subscribe to. This allows components to trigger events and other components to respond to those events, even though they are completely unaware that the other component exists. For more information about communication via shared services, see the official Angular docs.

Add the following code to the src/app/player.service.ts file.

Inject the service into the src/app/player/player.component.ts file. This listens for when a track is selected and plays the file. It also stops playing a file if the user clicks the pause button. Lastly, it triggers an event when the sample is finished playing entirely.

Modify the src/app/track/track-control/track-control.component.ts file to also listen to a trigger track events via the service.

Lastly, inject the service into the src/app/app.component.ts. This component is top-level for both the Player Component and Track Control Component. Injecting the service here automatically injects it anywhere further down the component tree if it is referenced.

Now the app will play music when the play button is clicked next to a track. In addition, playing any other track while a track is playing will set the correct state for the play button on both the newly playing track, as well as the one that was playing before. This is how Angular 2 manages rather complex state.

Get The Kendo UI for Angular components

In this article, you’ve seen how to populate a grid with data, how to use paging and even how to wire up detail grids. The Grid is capable of much and more than just this. I highly recommend checking out the Grid tutorials.

You can see the finished app here. All of the code from this article is available on GitHub. Follow the README instructions to get it setup and running on your own machine.

The post Building An iTunes Player With Angular appeared first on Telerik Developer Network.

Show more