如何使用Youtube API在RecyclerView中加载Youtube缩略图

我试图在RecyclerView中加载Youtubevideo缩略图。 我正面临一些问题。

这是我在我的适配器中做的事情:

public static class ItemViewHolder extends RecyclerView.ViewHolder { private YouTubeThumbnailView thumb; public Post post; public ItemViewHolder(View v) { thumb = (YouTubeThumbnailView) v.findViewById(R.id.youtube_thumbnail); } @Override public void onBindViewHolder(final RecyclerView.ViewHolder holder, final int position) { if (holder instanceof ItemViewHolder) { ((ItemViewHolder) holder).thumb.initialize(YOUTUPEKEY, new YouTubeThumbnailView.OnInitializedListener() { @Override public void onInitializationSuccess(YouTubeThumbnailView youTubeThumbnailView, YouTubeThumbnailLoader youTubeThumbnailLoader) { youTubeThumbnailLoader.setVideo(VIDEOID); } @Override public void onInitializationFailure(YouTubeThumbnailView youTubeThumbnailView, YouTubeInitializationResult youTubeInitializationResult) { }}); }}} 

它工作正常,但我不是我做对了。 当我在另一个活动中使用相同的适配器时,我得到这个错误:

 Activity com.example.yasser.version6.Mespublications has leaked ServiceConnection com.google.android.youtube.player.internal.r$e@4252bcb8 that was originally bound here 

加载缩略图需要一些时间,有时在缩略图之间混合。

我添加了一个函数来释放所有的Youtube加载器:

 public void ReleaseLoaders() { for (YouTubeThumbnailLoader loader : loaders.values()) { loader.release(); } } 

我从Activity Onstop()中调用这个函数:

 @Override public void onStop() { super.onStop(); mAdapter.ReleaseLoaders(); } 

它运行良好一段时间,但有时崩溃。

Solutions Collecting From Web of "如何使用Youtube API在RecyclerView中加载Youtube缩略图"

你可以试试这个吗? 它不使用API​​,但它很快。

使用Picasso从以下URL中加载图像到回收站视图中:

https://img.youtube.com/vi/ “这里是你的videoID”/default.jpg

– 编辑 –

经过一番研究和实验:

要获得默认的全尺寸缩略图,请执行此操作而不是default.jpg

https://img.youtube.com/vi/ “这里是你的videoID”/0.jpg

这里是链接: http : //www.reelseo.com/youtube-thumbnail-image/

编辑2:

刚刚find这样的人已经给了我这样一个快速简单的解决scheme的答案,并有更多的解释和select,你可以select。

如何从YouTube API获取YouTubevideo缩略图?


最终编辑:

这是工作代码。 我最近用api做了一个应用程序,所以我发现了你为什么得到这个错误。 因为你没有正确地释放装载机。

您可以通过两种方式释放装载机/装载机。

第一

(首选的,你会看到为什么在一秒钟)你想要释放它后,图像已被加载到视图,并为它的一个监听器和它的OnThumbNailLoadedListener。 那就是我发布的地方(如果你注意下面的代码)。 这意味着你不必再处理这个实例。 一旦缩略图加载完成。

第二

由于getView()被一直调用,因此您必须发布YouTubeThumbnailLoader的新实例。 这意味着你必须将所有这些存储在一个ArrayList中。 当activity是onStop()时,你只需要做一个高级for循环和调用释放。

现在你可能会明白为什么第一种方式是首选。 而且我知道你做了第二个select,所以只是让你知道第一个选项将永远保证工作(至less在我的情况下)。 我在一个活动中使用了一个YouTubeSupportFragment,它工作正常。 没有任何问题。 你绝对可以做第二个选项,但你必须处理很多特殊情况。

 final YouTubeThumbnailView youTubeThumbnailView = (YouTubeThumbnailView) convertView.findViewById(R.id.show_episode_thumbnail); youTubeThumbnailView.initialize(DeveloperKey.DEVELOPER_KEY, new YouTubeThumbnailView.OnInitializedListener() { @Override public void onInitializationSuccess(YouTubeThumbnailView youTubeThumbnailView, final YouTubeThumbnailLoader youTubeThumbnailLoader) { youTubeThumbnailLoader.setVideo(videoId); youTubeThumbnailLoader.setOnThumbnailLoadedListener(new YouTubeThumbnailLoader.OnThumbnailLoadedListener() { @Override public void onThumbnailLoaded(YouTubeThumbnailView youTubeThumbnailView, String s) { youTubeThumbnailLoader.release(); } @Override public void onThumbnailError(YouTubeThumbnailView youTubeThumbnailView, YouTubeThumbnailLoader.ErrorReason errorReason) { } }); } @Override public void onInitializationFailure(YouTubeThumbnailView youTubeThumbnailView, YouTubeInitializationResult youTubeInitializationResult) { } }); 

onBindViewHolder您试图一次又一次初始化相同的YoutubeThumbnailView ,而在onCreateViewHolder中创build视图时,您可以初始化一次。 通过将video标识设置为YoutubeThumbnailView标签,您可以防止混合(或)错误加载缩略图。


适配器。

  private class ThumbnailAdapter extends RecyclerView.Adapter{ private final int UNINITIALIZED = 1; private final int INITIALIZING = 2; private final int INITIALIZED = 3; private int blackColor = Color.parseColor("#FF000000"); private int transparentColor = Color.parseColor("#00000000"); public class VideoViewHolder extends RecyclerView.ViewHolder{ public YouTubeThumbnailView ytThubnailView = null; public ImageView ivYtLogo = null; public TextView tvTitle = null; public VideoViewHolder(View itemView) { super(itemView); ytThubnailView = (YouTubeThumbnailView) itemView.findViewById(R.id.yt_thumbnail); ivYtLogo = (ImageView) itemView.findViewById(R.id.iv_yt_logo); tvTitle = (TextView) itemView.findViewById(R.id.tv_title); initialize(); } public void initialize(){ ivYtLogo.setBackgroundColor(blackColor); ytThubnailView.setTag(R.id.initialize, INITIALIZING); ytThubnailView.setTag(R.id.thumbnailloader, null); ytThubnailView.setTag(R.id.videoid, ""); ytThubnailView.initialize(API_KEY, new YouTubeThumbnailView.OnInitializedListener() { @Override public void onInitializationSuccess(YouTubeThumbnailView youTubeThumbnailView, YouTubeThumbnailLoader youTubeThumbnailLoader) { ytThubnailView.setTag(R.id.initialize, INITIALIZED); ytThubnailView.setTag(R.id.thumbnailloader, youTubeThumbnailLoader); youTubeThumbnailLoader.setOnThumbnailLoadedListener(new YouTubeThumbnailLoader.OnThumbnailLoadedListener() { @Override public void onThumbnailLoaded(YouTubeThumbnailView youTubeThumbnailView, String loadedVideoId) { String currentVideoId = (String) ytThubnailView.getTag(R.id.videoid); if(currentVideoId.equals(loadedVideoId)) { ivYtLogo.setBackgroundColor(transparentColor); } else{ ivYtLogo.setBackgroundColor(blackColor); } } @Override public void onThumbnailError(YouTubeThumbnailView youTubeThumbnailView, YouTubeThumbnailLoader.ErrorReason errorReason) { ivYtLogo.setBackgroundColor(blackColor); } }); String videoId = (String) ytThubnailView.getTag(R.id.videoid); if(videoId != null && !videoId.isEmpty()){ youTubeThumbnailLoader.setVideo(videoId); } } @Override public void onInitializationFailure(YouTubeThumbnailView youTubeThumbnailView, YouTubeInitializationResult youTubeInitializationResult) { ytThubnailView.setTag(R.id.initialize, UNINITIALIZED); ivYtLogo.setBackgroundColor(blackColor); } }); } } @Override public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { View view = getLayoutInflater().inflate(R.layout.row_video_item, parent, false); VideoViewHolder videoViewHolder = new VideoViewHolder(view); return videoViewHolder; } @Override public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) { final Entities e = entities.get(position); final VideoViewHolder videoViewHolder = (VideoViewHolder) holder; videoViewHolder.tvTitle.setText(e.name); videoViewHolder.ivYtLogo.setVisibility(View.VISIBLE); videoViewHolder.ytThubnailView.setTag(R.id.videoid, e.id); videoViewHolder.ivYtLogo.setBackgroundColor(blackColor); int state = (int) videoViewHolder.ytThubnailView.getTag(R.id.initialize); if(state == UNINITIALIZED){ videoViewHolder.initialize(); } else if(state == INITIALIZED){ YouTubeThumbnailLoader loader = (YouTubeThumbnailLoader) videoViewHolder.ytThubnailView.getTag(R.id.thumbnailloader); loader.setVideo(e.id); } } @Override public int getItemCount() { return entities.size(); } } 

每行使用的布局是。

 <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="vertical" android:layout_width="match_parent" android:layout_height="match_parent"> <RelativeLayout android:layout_width="match_parent" android:layout_height="200dp"> <com.google.android.youtube.player.YouTubeThumbnailView android:id="@+id/yt_thumbnail" android:layout_width="match_parent" android:layout_height="match_parent" /> <ImageView android:id="@+id/iv_yt_logo" android:layout_width="match_parent" android:layout_height="match_parent" android:scaleType="center" android:src="@mipmap/youtube_play" android:background="#00000000" android:layout_centerInParent="true"/> </RelativeLayout> <TextView android:id="@+id/tv_title" android:layout_width="match_parent" android:layout_height="wrap_content" android:textColor="#FF000000" android:textSize="16sp" android:text="Title"/> <View android:id="@+id/seperator" android:layout_width="match_parent" android:layout_height="2dp" android:layout_marginTop="5dp" android:layout_marginBottom="5dp" android:background="#FF642108"/> </LinearLayout> 

标签.xml。

位置: src / main / res / values / tags.xml

 <?xml version="1.0" encoding="utf-8"?> <resources> <item type="id" name="initialize" /> <item type="id" name="videoid"/> <item type="id" name="thumbnailloader"/> </resources> 

在这里输入图像说明