所有 tableView 单元格为播放列表显示相同的艺术品图像

Posted

技术标签:

【中文标题】所有 tableView 单元格为播放列表显示相同的艺术品图像【英文标题】:All tableView Cells Show Same Artwork Image for Playlists 【发布时间】:2014-05-19 15:04:42 【问题描述】:

我有一个tableView,它显示了用户音乐库中的播放列表列表。我用来获取此列表的代码是:

@implementation playlistsViewController

    NSArray *playlists;
    MPMediaQuery *playlistsQuery;


- (void)viewDidLoad
        
    self.title = @"Playlists";

    playlistsQuery = [MPMediaQuery playlistsQuery];
    playlists = [playlistsQuery collections]; 


#pragma mark - Table view data source

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section

    return [playlists count];


- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
  ....

    // Configure the cell...

    MPMediaItem *rowItem = [playlists objectAtIndex:indexPath.row];

    cell.textLabel.text = [rowItem valueForProperty: MPMediaPlaylistPropertyName];

    cell.imageView.image = [self getAlbumArtworkWithSize:(CGSizeMake(44,44))];

    return cell;

然后我有getAlbumArtworkWithSize:

- (UIImage *) getAlbumArtworkWithSize: (CGSize) albumSize

    // IMAGE

    MPMediaQuery *playlistQuery = [MPMediaQuery playlistsQuery];
    MPMediaPropertyPredicate *playlistPredicate = [MPMediaPropertyPredicate predicateWithValue: playlistTitle forProperty: MPMediaPlaylistPropertyName];
    [playlistQuery addFilterPredicate:playlistPredicate];

    for (MPMediaPlaylist *playlist in playlists) 
        NSLog (@"%@", [playlist valueForProperty: MPMediaPlaylistPropertyName]);

        NSArray *songs = [playlist items];

        for (int i = 0; i < [songs count]; i++) 

            MPMediaItem *mediaItem = [songs objectAtIndex:i];
            UIImage *artworkImage;

            MPMediaItemArtwork *artwork = [mediaItem valueForProperty: MPMediaItemPropertyArtwork];
            tempImage = [artwork imageWithSize: CGSizeMake (1, 1)];

            if (tempImage) 
                tempImage = [artwork imageWithSize:albumSize];
                playlistImage = artworkImage;
                return artworkImage;
            
        
    
return [UIImage imageNamed:@"Songs.png"];

此代码的作用:它循环播放播放列表中的所有歌曲,直到找到带有专辑插图的歌曲,因为有些歌曲没有任何插图。然后它返回该图像。

但是,这只会为我的表格中的所有单元格返回相同的艺术品图像。如何为每个表格视图单元格(播放列表名称)运行getAlbumArtworkWithSize

这是我目前得到的:

.

【问题讨论】:

【参考方案1】:

这是因为您没有在 getAlbumArtworkWithSize 方法中遍历属于该行的播放列表特定的项目集合。为了使其更容易并减少执行时间(不在您的方法中进行额外查询),请尝试将集合传递给您的函数:

- (UIImage *)getAlbumArtworkWithSize:(CGSize)albumSize forPlaylist:(MPMediaItemCollection *)collection

    for (MPMediaItem *mediaItem in collection.items) 
        UIImage *artworkImage;

        MPMediaItemArtwork *artwork = [mediaItem valueForProperty: MPMediaItemPropertyArtwork];
        tempImage = [artwork imageWithSize: CGSizeMake (1, 1)];

        if (tempImage) 
            tempImage = [artwork imageWithSize:albumSize];
            playlistImage = artworkImage;
            return artworkImage;
        
    
    return [UIImage imageNamed:@"Songs.png"];

然后像这样使用它:

cell.imageView.image = [self getAlbumArtworkWithSize:CGSizeMake(44,44) forCollection:[playlists objectAtIndex:indexPath.row]];

我不推荐使用这种方法,因为播放列表包含约 1000 个项目,它可能会非常慢。最好使用集合的代表项,如果没有返回图像,则使用占位符。哪个会喜欢这样的:

- (UIImage *)getAlbumArtworkWithSize:(CGSize)albumSize forPlaylist:(MPMediaItemCollection *)collection

        UIImage *artworkImage;

        MPMediaItem *mediaItem = [collection representativeItem];
        MPMediaItemArtwork *artwork = [mediaItem valueForProperty: MPMediaItemPropertyArtwork];
        tempImage = [artwork imageWithSize: CGSizeMake (1, 1)];

        if (tempImage) 
            tempImage = [artwork imageWithSize:albumSize];
            playlistImage = artworkImage;
            return artworkImage;
        
    return [UIImage imageNamed:@"Songs.png"];

【讨论】:

感谢您的帮助。如果我的原始方法只是查找具有专辑插图的第一首歌曲,为什么我的原始方法在播放列表较大时会很慢?播放列表的前 10 首中的歌曲肯定会有一首,不是吗?只是好奇:)另外,我使用了第二种更有效的方法,正如你所说,但它并没有返回我所有播放列表的代表图像,尽管它们的歌曲有专辑封面。例如。播放次数最多的前 25 名 - My app 尽管播放列表中有专辑插图(请参阅 music app)。

以上是关于所有 tableView 单元格为播放列表显示相同的艺术品图像的主要内容,如果未能解决你的问题,请参考以下文章

为啥在 heightForRowAt 方法中我的单元格为零?

添加具有行动画的单元格时,将 tableview 保持在相同的滚动位置

以单击另一个单元格为条件突出显示单元格

重用自定义 tableView 单元格时重复显示相同的子视图(Swift 4.1)

RTF 表格之前的文本导致第一个表格单元格为空

Extjs 在以单元格为基础的整个网格行上显示工具提示