快速重用单元格自定义视图问题

时间:2019-12-28 03:15:05

标签: ios swift uitableview

我在自定义tableview单元格内有一个自定义视图(tagListView)。 当我在“ cellForRowAt”内部将addTag调用到cell.tagListView时,它将为每个单元格添加一个标签。 如何仅为该单元格添加标签?我试图保持计数,所以我只向没有标签的标签添加标签。但是看来所有细胞的计数都一样吗?我知道这与可重复使用的单元格有关。

 func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        let cell = topicListTableView.dequeueReusableCell(withIdentifier: "TopicListTableCell", for: indexPath)
        if let myCell =  cell as? TopicListTableCell {
             if let model=topicListModel{
                let t=model.topics[(indexPath.row)]
                if let subject=t.subject{
                    let (tags,title)=util().getTag(subject: subject)
                     myCell.subject.text=title
                    if(myCell.tagCount==0){
                        myCell.tagList.addTags(tags)
                        myCell.tagCount+=1
                    }
                }
                myCell.content.text=t.content
                myCell.authorTime.text=t.author
                if let replynum=t.replies{
                    myCell.commentNum.text=String(replynum)
                }
                if let upvoteNum=t.score{
                   myCell.upVote.text=String(upvoteNum)
                }
                if indexPath.row%2==1{
                    myCell.background.backgroundColor=util().lightyellow
                }else{
                    myCell.background.backgroundColor=util().darkeryellow
                }

            }
        }

       return cell

    }

单元格代码:

class TopicListTableCell: UITableViewCell{
    @IBOutlet weak var content: UILabel!
    @IBOutlet weak var upVote: UILabel!
    @IBOutlet weak var commentNum: UILabel!
    @IBOutlet weak var subject: UILabel!
    @IBOutlet weak var authorTime: UILabel!
    @IBOutlet weak var background: UIView!
    @IBOutlet weak var tagList: TagListView!
    var tagCount = 0
}

1 个答案:

答案 0 :(得分:0)

如dfd所述,由于UITableViews在iOS中的工作方式,您的方法不合适。 您应该为tableView(一个数组或字典)提供一个dataSource,其中包含以所需方式呈现单元格所需的所有信息。

因此,我将制作一个包含所有我需要填充一个单元格的信息的结构,然后制作一个这些结构的数组以用它们所需的信息填充所有单元格。 像这样:

// In your model:
struct TopicItem {
  let topic: Topic
  let tags: [Tag]
  let title: String
}
var topicItems = [TopicItem]()

// This is function is only a draft, so you get a better idea what i mean
func updateTopicItems() {
  topicItems.removeAll()

  for topic in topics {
    let tags: [Tag]
    let title: String

    if let subject = topic.subject {
      // I would refactor this function, it is called getTag() but it returns tags and title. Kinda confusing
      (tags,title) = util().getTag(subject: subject)
    } else {
      tags = [Tag]()
      title = ""
    }

    topicItems.append(TopicItem(topic: topic, tags: tags, title: title))
  }
} 

我还添加了一些重构和注释,希望它们可以帮助您将来保持代码的清洁和可维护:)

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
  // cell can be force unwrapped, it will never be something different than a TopicListTableCell, unless you change your code
  // and even then you want a crash, so you find the error fast (crash will only occur during development)
  let cell = topicListTableView.dequeueReusableCell(withIdentifier: "TopicListTableCell", for: indexPath) as! TopicListTableCell
  guard let model = topicListModel else { return cell } // If there is no model, there is nothing to do
  let topicItem = model.topicItems[(indexPath.row)]
  let t = topicItem.topic

  cell.subject.text = topicItem.title

  // You should replace the addTags() function with a setTags() function, otherwise you will get more and more tags every time you present the cell
  cell.tagList.addTags(topicItem.tags)

  cell.content.text = t.content
  cell.authorTime.text = t.author

  if let replynum = t.replies {
    cell.commentNum.text = String(replynum)
  } else {
    // Because cells are getting reused, you need to always set all fields, otherwise you get cells with content from other cells
    cell.commentNum.text = ""
  }

  if let upvoteNum = t.score {
    cell.upVote.text = String(upvoteNum)
  } else {
    // Again always set all fields
    cell.upVote.text = ""
  }

  if indexPath.row %2 == 1 {
    cell.background.backgroundColor=util().lightyellow
  } else {
    cell.background.backgroundColor=util().darkeryellow
  }

  return cell

}