代码之家  ›  专栏  ›  技术社区  ›  Raymond Led Carasco

自定义UITableViewCell中的按钮操作会影响其他单元格

  •  1
  • Raymond Led Carasco  · 技术社区  · 9 年前

    我有一个 表视图 有原型的 UITableView单元格 它有自己的类,

    自定义UITableViewCell类

    import UIKit
    
    class H_MissingPersonTableViewCell: UITableViewCell {
    
        @IBOutlet weak var strName: UILabel!
        @IBOutlet weak var imgPerson: UIImageView!
        @IBOutlet weak var Date1: UILabel!
        @IBOutlet weak var Date2: UILabel!
        @IBOutlet weak var MainView: UIView!
        @IBOutlet weak var btnGetUpdates: UIButton!
        @IBOutlet weak var btnComment: UIButton!
        @IBOutlet weak var btnReadMore: UIButton!
        
        
        override func awakeFromNib() {
            super.awakeFromNib()
            // Initialization code
        }
    
        override func setSelected(selected: Bool, animated: Bool) {
            super.setSelected(selected, animated: animated)
    
            // Configure the view for the selected state
        }
    
    }
    

    TableView完美加载,dataSource和委托工作正常。但是,当我单击IndexPath上的按钮时。行=0(零),然后向下滚动,我会看到随机(?)或由于单击第0行中的按钮而突出显示的其他单元格。。。

    以下是我的CellForRowAtIndexPath代码:

      func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
            
            println("called")
            var cell : CustomCell
            
            
            cell = tableView.dequeueReusableCellWithIdentifier("CustomCellID", forIndexPath: indexPath) as! CustomCell
            cell.strName.text = self.names[indexPath.row]
            cell.imgPerson.image = UIImage(named: "\(self.persons[indexPath.row])")!
    
            cell.btnGetUpdates.layer.borderColor = UIColor.darkGrayColor().CGColor
            cell.btnGetUpdates.layer.borderWidth = 1
            cell.btnGetUpdates.layer.cornerRadius = 5.0
            
    
            cell.btnComment.layer.borderColor = UIColor.darkGrayColor().CGColor
            cell.btnComment.layer.borderWidth = 1
            cell.btnComment.layer.cornerRadius = 5.0
            
            cell.btnReadMore.layer.borderColor = UIColor.darkGrayColor().CGColor
            cell.btnReadMore.layer.borderWidth = 1
            cell.btnReadMore.layer.cornerRadius = 5.0
            
            cell.dateMissingPersonPlace.text = self.MissingPeoplePlace[indexPath.row]
            cell.dateMissingPersonSince.text = self.MissingPeopleSince[indexPath.row]
            
            cell.btnGetUpdates.tag = indexPath.row
            cell.btnGetUpdates.addTarget(self, action: "GetUpdatesButton:", forControlEvents: .TouchUpInside)
            
            return cell
            
        }
    

    在我的 cell.btn获取更新 ,我在CellForIndex代码的最后一部分做了一个动作, 获取更新按钮:

    这是代码:

    func GetUpdatesButton(sender: UIButton){
        println("Button Clicked \(sender.tag)")
    
        var sen: UIButton = sender
        var g : NSIndexPath = NSIndexPath(forRow: sen.tag, inSection: 0)
        var t : CustomCell = self.myTableView.cellForRowAtIndexPath(g) as! CustomCell
        t.btnGetUpdates.backgroundColor = UIColor.redColor()
        }
    

    问题是,不仅索引0中的按钮被高亮显示,而且当我向下滚动tableView时,我还会看到其他索引/行中的随机按钮被高亮。

    我哪里出错了,我怎么只能更新我点击的按钮…而不是其他按钮。。

    我有20个项目(20行),当我单击第0行的按钮时,第3、6、9行……也有突出显示的按钮。

    ROW 0,单击按钮

    ROW ZERO , button clicked

    第三行,按钮也点击了,尽管我并没有真正点击它。 enter image description here

    5 回复  |  直到 4 年前
        1
  •  5
  •   Asha Dhola    9 年前

    这是由于UITableview具有可重用单元格策略而导致的。为了解决此问题,您需要在cellForRowAtIndexPath方法中维护一个选定项的数组,您必须验证此按钮是否被选定项数组保留。如果是,则应用选择样式,否则应用普通样式。

    检查以下按钮单击的源代码:

    func GetUpdatesButton(sender: UIButton) 
    {
        var sen: UIButton = sender
        var g : NSIndexPath = NSIndexPath(forRow: sen.tag, inSection: 0)
        var t : CustomCell = self.myTableView.cellForRowAtIndexPath(g) as!   CustomCell
        t.btnGetUpdates.backgroundColor = UIColor.redColor()
       self.selectedButtonsArray.addObject(indexpath.row)
    }
    

    以下代码用于在CellForRowAtIndexPath中的按钮上应用样式:

    func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
        var cell : CustomCell
        cell = tableView.dequeueReusableCellWithIdentifier("CustomCellID", forIndexPath: indexPath) as! CustomCell
        cell.strName.text = self.names[indexPath.row]
        cell.imgPerson.image = UIImage(named: "\(self.persons[indexPath.row])")!
    
        if(self.selectedButtonsArray.containsObject(indexpath.row)){
    
            cell.btnGetUpdates.backgroundColor = UIColor.redColor()
            cell.btnGetUpdates.layer.borderColor = UIColor.darkGrayColor().CGColor
            cell.btnGetUpdates.layer.borderWidth = 1
            cell.btnGetUpdates.layer.cornerRadius = 5.0
    
        }else{
    
            cell.btnGetUpdates.layer.borderColor = UIColor.darkGrayColor().CGColor
            cell.btnGetUpdates.layer.borderWidth = 1
            cell.btnGetUpdates.layer.cornerRadius = 5.0
    
       }
    
        cell.btnComment.layer.borderColor = UIColor.darkGrayColor().CGColor
        cell.btnComment.layer.borderWidth = 1
        cell.btnComment.layer.cornerRadius = 5.0
    
        cell.btnReadMore.layer.borderColor = UIColor.darkGrayColor().CGColor
        cell.btnReadMore.layer.borderWidth = 1
        cell.btnReadMore.layer.cornerRadius = 5.0
    
        cell.dateMissingPersonPlace.text = self.MissingPeoplePlace[indexPath.row]
        cell.dateMissingPersonSince.text = self.MissingPeopleSince[indexPath.row]
    
        cell.btnGetUpdates.tag = indexPath.row
        cell.btnGetUpdates.addTarget(self, action: "GetUpdatesButton:",forControlEvents: .TouchUpInside)
    
        return cell
    

    }

    我希望这有助于解决您的问题!谢谢

        2
  •  1
  •   Sujith Chandran    9 年前

    在GetUpdatesButton()函数中,保留indexPath的标志值。单独数组中的行值。然后重新加载表视图的特定单元格。

    现在,在cellForRowAtIndexPath函数中设置一个条件,检查标志值是否设置,如果设置,则更改背景颜色,否则设置默认颜色。

    PS:有各种各样的变通办法来解决这个问题。只需理解逻辑,然后选择代码中有用的逻辑。

        3
  •  1
  •   Saheb Roy    9 年前

    这是因为细胞正在被重复使用。 因此,当您使用按钮操作为单元格着色时,单元格的背景正在被绘制,我想这是正常的,但情况是,当您向上或向下滚动时,具有bg颜色的前一个单元格将被重新使用,因此您将获得以前的设置。

    提示是显式设置 UIButton UITableViewCell 在这种方法中 func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell ,因为每次它将被重复使用时,颜色将被设置为默认颜色,并且您将无法获得它被重复使用的前一种颜色。

    刚刚设置好

    func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
      cell.backgroundColor = [UIColor whiteColor];
      cell.btnGetUpdates setBackgroundColor:[UIColor whiteColor];
    //with along the other code, add these two lines.
    }
    

    编辑

    为了获得想要的效果,请设置一个实例变量,该变量存储所选单元格的indexPath,类似于int。

    在按钮操作方法中,将int存储到按钮。标记属性,也是索引路径。单元格的行属性。

    在您的 cellForRowAtIndexPath 方法,进行检查

    if(indexpath.row == selectedIntIndexPath){
      //change the colour whatever you want.
    }
    

    最后在按钮调用的IBAction方法中 [self.tableView reloadData]

    所以完整的代码应该是这样的

    @implementation ViewController{
    int selectedIntIndexPath;
    }
    
     -(IBAction)actionForButton:(id)sender{
    UIButton *btn = (UIButton *)sender;
    selectedIntIndexPath = btn.tag;
    [self.customTableView reloadData];
    }
    
    -(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
    UICustomTableViewCell *cell = (UICustomTableViewCell *)[tableView dequeueReusableCellWithIdentifier:@"reuseIdentifire" forIndexPath:indexPath];
    if(indexPath.row == selectedIntIndexPath){
        // do your colour
      }
     return cell;
    }
    
        4
  •  1
  •   xhinoda    6 年前

    这里是我的解决方案,以便扩展@RaymondLedCarasco评论:

    在Swift 4 Xcode 9.3中测试

    声明财产:

    var numberCells: [Int] = []
    

    单击“单元格”按钮时:

    self.numberCells.append(indexPath.row)
    

    在CellForRowAtIndex检查中:

    if self.numberCells.contains(indexPath.row) { ... } else { ... }
    
        5
  •  0
  •   Sreekanth G    5 年前

    这里是我解决的大多数TableViewCell问题,例如单击 单元格按钮 在滚动之后,可以改变剩余的行 didSelectRowAt索引路径:索引路径 可以选择滚动剩余行之后的行。所以我创建了一个应用程序来解决这些问题。此处添加GitHub代码 Find the code

    • 在第一个屏幕中,单击一个红色按钮,然后向下滚动,在UITableViewCell中看不到其他单元格会自动受到影响。

    • 单击 didSelectRowAt索引路径:索引路径 在第一个屏幕中,您可以转到作为第二个屏幕的详细信息屏幕,在该屏幕中,选择一行后,其他行将不会在UITableViewCell中自动选择。