2012-09-02 12 views
0

我創建了自定義UITableViewCell,每個單元格都從UITableViewController傳遞了AVPlayer對象的自定義子類。在每個單元上我都有一個播放按鈕,暫停按鈕和加載指示器。自定義UITableViewCell作爲委託 - UI元素意外重複使用

當我播放音頻時,元素根據需要工作,並在播放器狀態發生變化時更改。播放時,出現暫停按鈕,播放按鈕消失。當我在第二個單元上播放音頻時,第一個單元知道這一點,將其重置爲按鈕狀態,而第二個單元確實是業務。

所以這個功能很完美,唯一的問題是因爲UITableViewCell被重用,當我向下滾動到下面的單元格時,我開始看到它們上面出現暫停按鈕。這是因爲它們與上面(重用)的單元格相同,並且由於我的單元格是AVPlayer的自定義子類的代表,因此音頻播放器正在將消息發送到不正確的單元格。

我可以做些什麼來使每個UITableViewCell爲我的AVPlayer單獨的委託對象?

回答

0

我通過使UITableViewController委託音頻播放器解決了這個問題。然後將「正在播放」單元的indexPath保存爲UITableViewController中的@property

然後在- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath我檢查indexPath是否與「當前播放」單元的indexPath相同,如果是這樣設置「音頻播放」按鈕排列,如果沒有則設置默認按鈕排列。

由於您有唯一的標識符indexPath來區分細胞,因此可以更好地進行比較。

0

我對從JSON blob加載的圖像有同樣的問題。我使用了GCD並將我的圖像保存到與分配給每個單元的密鑰配對的NSDictionary中。

- (UIImage *)imageForRowAtIndexPath:(NSIndexPath *)indexPath 
{  
    // get the dictionary for the indexPath 
    NSDictionary *tweet = [tweets objectAtIndex:[indexPath row]]; 

    // get the user dictionary for the indexPath 
    NSDictionary *user = [tweet objectForKey:@"posts"]; 

    //get the image URL 
    NSURL *url = [NSURL URLWithString:[[[[[tweet objectForKey:@"photos"] objectAtIndex:0] objectForKey:@"alt_sizes"] objectAtIndex:3] objectForKey:@"url"]]; 

    // get the user's id and check for a cached image first 
    NSString *userID = [user objectForKey:@"id"]; 
    UIImage *image = [self.images objectForKey:userID]; 
    if(!image) 
    { 

     // if we didn't find an image, create a placeholder image and 
     // put it in the "cache". Start the download of the actual image 
     image = [UIImage imageNamed:@"Placeholder.png"]; 
     [self.images setValue:image forKey:userID]; 

     //get the string version of the URL for the image 
     //NSString *url = [user objectForKey:@"profile_image_url"]; 

     // create the queue if it doesn't exist 
     if (!queue) { 
      queue = dispatch_queue_create("image_queue", NULL); 
     } 

     //dispatch_async to get the image data 
     dispatch_async(queue, ^{ 

      NSData *data = [NSData dataWithContentsOfURL:url]; 
      UIImage *anImage = [UIImage imageWithData:data]; 
      [self.images setValue:anImage forKey:userID]; 
      UITableViewCell *cell = [self.tableView cellForRowAtIndexPath:indexPath]; 

      //dispatch_async on the main queue to update the UI 
      dispatch_async(dispatch_get_main_queue(), ^{ 
       cell.imageView.image = anImage; 
      }); 
     }); 


    } 

    // return the image, it could be the placeholder, or an image from the cache 
    return image; 
} 
1

你必須在重用刪除從細胞中的元素:

UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; 
if (cell == nil) { 
    cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier]; 
} else { 
    /* prepare for reuse */ 
    [cell.playButton removeFromSuperview]; 
    /* or */ 
    [[cell viewWithTag:10] removeFromSuperview]; 
} 
+0

UITableViewCell實際上有一個方法_called_ prepareForReuse,這將是一個很好的準備重用的地方。 – jrturton

+0

雅,但你不得不繼承UITableViewCell做到這一點.. – Snowman

+0

準備重用的問題是,因爲單元格正在重用,他們在內存中共享相同的點,所以當設置單元格作爲委託時,它指向到tableview中的多個單元格。我解決了我的問題,請檢查我的答案。 – Wasim

相關問題