[TUT] Click item in a ListView to show YouTube Video

Following on from the popular ‘Show YouTube Feed for a Users Videos in a ListView’ someone requested that when you click on one of the individual videos in the list that it links off to the YouTube video.

This in itself this is quite simple, but getting the architecture right and having the data you need in the right place takes a little bit of thought.

Using an interface it’s possible to do all the logic within the custom ListView we have written but still allow the Activity to receive the callback and do whatever it wants with the video i.e. start a video viewing Intent.

This blog post is going to brush over the basics of populating the ListView (as this is done in the previously mentioned tutorial) and just talk about how you can add a custom listener to your ListView that sends back to the activity the data for each row.

The whole source code is linked at the bottom of the post and I am just going to talk about the relevant code for the click listener here.

Firstly we need to define an Interface, interfaces allow you to declare that your class can do something but it leaves the implementation up to the class. i.e. if you had an Interface called “Move” and a method called “useLegs()” you could add this interface to your Activity. The activity can now be called by other classes that want to “Move” and they will call the useLegs method. The powerful thing is, it’s up to your activity what happens in the useLegs() method! It could have robot legs .. four legs … run or hop, it doesn’t matter its up to you!

If you don’t quite get that take a look at this. Here is the interface we have made for a special video listener:


package com.blundell.tut.ui;

import com.blundell.tut.domain.Video;

public interface VideoClickListener {

	public void onVideoClicked(Video video);
	
}

It’s declaring it is a VideoClickListener and wants you to implement a method called onVideoClicked. So that means if you implement this interface you will have to react to some type of video being clicked and you get passed the video.
(This sounds great if we were passed the video that was clicked from the list πŸ˜‰ ).

Now that we have the interface there are two things we need to do. The activity needs to implement the interface (to receive calls to the onVideoClicked method) and also something needs to send those calls.

Let’s send the calls first. In our custom ListView we create a reference to this interface then when the list is clicked we simply call the method. It makes much more sense in practice, look:

package com.blundell.tut.ui.widget;

import java.util.List;

import android.content.Context;
import android.util.AttributeSet;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ListAdapter;
import android.widget.ListView;

import com.blundell.tut.domain.Video;
import com.blundell.tut.ui.VideoClickListener;
import com.blundell.tut.ui.adapter.VideosAdapter;

/**
 * @author paul.blundell
 */
public class VideosListView extends ListView implements android.widget.AdapterView.OnItemClickListener {

	private List<Video> videos;
	private VideoClickListener videoClickListener;

	public VideosListView(Context context, AttributeSet attrs, int defStyle) {
		super(context, attrs, defStyle);
	}

	public VideosListView(Context context, AttributeSet attrs) {
		super(context, attrs);
	}

	public VideosListView(Context context) {
		super(context);
	}

	public void setVideos(List<Video> videos){
		this.videos = videos;
		VideosAdapter adapter = new VideosAdapter(getContext(), videos);
		setAdapter(adapter);
		// When the videos are set we also set an item click listener to the list
		// this will callback to our custom list whenever an item it pressed
		// it will tell us what position in the list is pressed
		setOnItemClickListener(this);
	}
	
	// Calling this method sets a listener to the list
	// Whatever class is passed in will be notified when the list is pressed
	// (The class that is passed in just has to 'implement VideoClickListener'
	// meaning is has the methods available we want to call)
	public void setOnVideoClickListener(VideoClickListener l) {
		videoClickListener = l;
	}
	
	@Override
	public void setAdapter(ListAdapter adapter) {
		super.setAdapter(adapter);
	}

	// When we receive a notification that a list item was pressed
	// we check to see if a video listener has been set
	// if it has we can then tell the listener 'hey a video has just been clicked' also passing the video
	@Override
	public void onItemClick(AdapterView<?> adapter, View v, int position, long id) {
		if(videoClickListener != null){
			videoClickListener.onVideoClicked(videos.get(position));
		}
	}
}

So thats it when your ListView is clicked it will tell whatever is listening that it has been clicked and pass the video! However nothing is listening yet we need to update our activity:

package com.blundell.tut.ui.phone;

import android.app.Activity;
import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.view.View;

import com.blundell.tut.R;
import com.blundell.tut.domain.Library;
import com.blundell.tut.domain.Video;
import com.blundell.tut.service.task.GetYouTubeUserVideosTask;
import com.blundell.tut.ui.VideoClickListener;
import com.blundell.tut.ui.widget.VideosListView;

/**
 * The Activity can retrieve Videos for a specific username from YouTube</br>
 * It then displays them into a list including the Thumbnail preview and the title</br>
 * There is a reference to each video on YouTube as well but this isn't used in this tutorial</br>
 * </br>
 * <b>Note<b/> orientation change isn't covered in this tutorial, you will want to override
 * onSaveInstanceState() and onRestoreInstanceState() when you come to this
 * </br>
 * @author paul.blundell
 */
public class MainActivity extends Activity implements VideoClickListener {
    // A reference to our list that will hold the video details
	private VideosListView listView;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        
        listView = (VideosListView) findViewById(R.id.videosListView);
        // Here we are adding this activity as a listener for when any row in the List is 'clicked'
        // The activity will be sent back the video that has been pressed to do whatever it wants with
        // in this case we will retrieve the URL of the video and fire off an intent to view it
        listView.setOnVideoClickListener(this);
    }

    public void getUserYouTubeFeed(View v){
    	new Thread(new GetYouTubeUserVideosTask(responseHandler, "blundellp")).start();
    }
   
	Handler responseHandler = new Handler() {
		public void handleMessage(Message msg) {
			populateListWithVideos(msg);
		};
	};

	private void populateListWithVideos(Message msg) {
		Library lib = (Library) msg.getData().get(GetYouTubeUserVideosTask.LIBRARY);
		listView.setVideos(lib.getVideos());
	}
	
	@Override
	protected void onStop() {
		responseHandler = null;
		super.onStop();
	}

	// This is the interface method that is called when a video in the listview is clicked!
	// The interface is a contract between this activity and the listview
	@Override
	public void onVideoClicked(Video video) {
		Intent intent = new Intent(Intent.ACTION_VIEW);
		intent.setData(Uri.parse(video.getUrl()));
		startActivity(intent);
	}
}

Hope I’ve made it clear enough. Now when the list is clicked our activity knows about it. Not only does it know though, it also is passed the video that has been clicked letting us act upon it.

All source code has been commented to help you out!

Enjoy!

Eclipse Source Project – User Feed YouTube Click Through Tut

34 thoughts on “[TUT] Click item in a ListView to show YouTube Video

  1. Very nice tutorial. http://www.itcuties.com has youtube player for single video if u have the video id. This opens the video in app. Is there anyway u can direct me on how to merge the class from itcuties with this code inorder for app video not to open with browser when clicked

    1. Sure MainActivity line 69, this is what you would need to change. The Video object has video.getUrl() which you could use with itcuties

  2. Click item in a ListView to show YouTube Video….?
    it is posible to play video whitin my application instand of youtube player?
    Click item in a ListView to show YouTube Video

  3. I’ve attempted to follow this tutorial but it does not seem to work when I attempt to run it – any suggestions as to what I may have done wrong?

  4. Question – are there any resources anywhere showing how one of these videos can be clicked then played within the app? (Instead of being played in the youtube app?)

  5. The order of the videos is not the same as youtube. Its sort by date to stay the same channel?

    Thiago – Brazil
    Translated by google translate.

  6. hi, great work dude,but when I click any video it just goes to YouTube main page.I see that someone else is having the same issue,and you replied him “Hmm maybe they aren’t allowed on mobile, or the url is incorrect?” how is that not allowed ? how could the url be incorrect I use my correct name and also the video thumbnails do appear in the listview which I think means URL is correct!!!Am I right dude?

    1. yeah right. It goes to the homepage. I was expecting that if I clicked the video from the playlist it would play automatically. But it goes only to the Youtube homepage. What to do?! πŸ™

      1. hmm the link might not be correct? There are new YouTube API’s for playing videos inside app’s I should do follow up TUT

  7. Hi i had succesful found a code and modified it to streamyoutube videos within the appusingyoutbe api..how do integrate it here?

  8. what the android version that you test? In my version, all videos are go to main page of youtube “http://m.youtube.com./#/home”

    1. first of all we dont add the video’s url in this code. we are adding the “QUERY” to fetch the videos from the youtube server…. that query we are adding in the GetYouTubeUserVideos.java class inside the run portion of the thread .,][

  9. This tutorial and the “Show YouTube Feed for a Users Videos in a ListView” was such a great help. Really awesome!. Thanks!

  10. i got force close exception when i test your code on emulator!! everything i check all permission ,nd all dat!!! when i try to run this source code on emulator its getting force close. can u tel me iz it work perfectly when i test it on real device.

    1. Hi Ram, please check what the error is in LogCat and what Android version your emulator is running as this code should work perfectly

  11. Thank you so much for this tutorial. Love your work & style. I purchase from play often, I’ll now do so through your link πŸ™‚
    Bind all of your tutorials together, sell them as an ebook! Thank you for sharing!

    1. In Columbo style, one more thing… would you know why some videos open to a default youtube list, when they actually exist?
      Thanks again for sharing

Leave a Reply

Your email address will not be published. Required fields are marked *