UITableView invoke swipe actions programmatically

匿名 (未验证) 提交于 2019-12-03 02:06:01

问题:

I have a UITableView where the user can swipe left to reveal actions (like in iOS 8 mail). That all works as expected. I want to trigger this when the user taps on a certain part of the cell. How can I invoke this slide action programmatically?

Current behavior: User must swipe the cell left to disclose the action buttons.

Desired behavior: User taps (an actions button) on the cell. Cell slides over to disclose the action buttons.

回答1:

Well I couldn't find a way to do this programmatically, but I came up with this workaround. When the user taps the cell, I animated (pan) it to the left to momentarily reveal afake "Swipe Me" button. This is quickly reversed so the cell is back to normal. This provides a visual cue to let the user know that they can swipe the cell:

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{     UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath];      __block UILabel *swipeLabel = [[UILabel alloc]initWithFrame:CGRectMake(cell.bounds.size.width,                                                                    0,                                                                    200,                                                                    cell.bounds.size.height)];      swipeLabel.text = @"  Swipe Me";     swipeLabel.backgroundColor = [UIColor greenColor];     swipeLabel.textColor = [UIColor whiteColor];     [cell addSubview:swipeLabel];      [UIView animateWithDuration:0.3 animations:^{         [cell setFrame:CGRectMake(cell.frame.origin.x - 100, cell.frame.origin.y, cell.bounds.size.width, cell.bounds.size.height)];     } completion:^(BOOL finished) {         [UIView animateWithDuration:0.3 animations:^{             [cell setFrame:CGRectMake(cell.frame.origin.x + 100, cell.frame.origin.y, cell.bounds.size.width, cell.bounds.size.height)];         } completion:^(BOOL finished) {             [swipeLabel removeFromSuperview];             swipeLabel = nil;         }];     }]; } 

Hope this helps someone.

Note that you need to set your tableViewCell's selection type to none. Else the gray bar will obscure it.

Update. I thought I'd post a more Swifty version:

func previewActions(forCellAt indexPath: IndexPath) {     guard let cell = tableView.cellForRow(at: indexPath) else {         return     }      let label: UILabel = {         let label = UILabel(frame: CGRect.zero)         label.text = "  Swipe Me  "         label.backgroundColor = .blue         label.textColor = .white         return label     }()      // Figure out the best width and update label.frame     let bestSize = label.sizeThatFits(label.frame.size)     label.frame = CGRect(x: cell.bounds.width - bestSize.width, y: 0, width: bestSize.width, height: cell.bounds.height)     cell.insertSubview(label, belowSubview: cell.contentView)      UIView.animate(withDuration: 0.3, animations: {         cell.transform = CGAffineTransform.identity.translatedBy(x: -label.bounds.width, y: 0)         label.transform = CGAffineTransform.identity.translatedBy(x: label.bounds.width, y: 0)     }) { (finished) in         UIView.animateKeyframes(withDuration: 0.3, delay: 0.25, options: [], animations: {             cell.transform = CGAffineTransform.identity             label.transform = CGAffineTransform.identity         }, completion: { (finished) in             label.removeFromSuperview()         })     } }  func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {     previewActions(forCellAt: indexPath)     return } 


回答2:

For anyone in search of the Swift version of VaporwareWolf's answer, here it is:

func animateRevealHideActionForRow(tableView: UITableView, indexPath: NSIndexPath) {     let cell = tableView.cellForRowAtIndexPath(indexPath);      // Should be used in a block     var swipeLabel: UILabel? = UILabel.init(frame: CGRectMake(cell!.bounds.size.width,         0,         200,         cell!.bounds.size.height))      swipeLabel!.text = "  Swipe Me";     swipeLabel!.backgroundColor = UIColor.init(red: 255/255, green: 41/255, blue: 53/255, alpha: 1) // Red     swipeLabel!.textColor = UIColor.whiteColor()     cell!.addSubview(swipeLabel!)      UIView.animateWithDuration(0.3, animations: {          cell!.frame = CGRectMake(cell!.frame.origin.x - 100, cell!.frame.origin.y, cell!.bounds.size.width + 100, cell!.bounds.size.height)      }) { (finished) in         UIView.animateWithDuration(0.3, animations: {              cell!.frame = CGRectMake(cell!.frame.origin.x + 100, cell!.frame.origin.y, cell!.bounds.size.width - 100, cell!.bounds.size.height)              }, completion: { (finished) in                 swipeLabel?.removeFromSuperview()                 swipeLabel = nil;         })      } } 


回答3:

And for a Swift 3 version where you want to call this function for every row.

override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {      let cell = tableView.cellForRow(at: indexPath);     UIView.animate(withDuration: 0.3, animations: {          cell!.frame = CGRect(x: cell!.frame.origin.x - 100, y: cell!.frame.origin.y, width: cell!.bounds.size.width + 100, height: cell!.bounds.size.height)      }) { (finished) in         UIView.animate(withDuration: 0.3, animations: {              cell!.frame = CGRect(x: cell!.frame.origin.x + 100, y: cell!.frame.origin.y, width: cell!.bounds.size.width - 100, height: cell!.bounds.size.height)          }, completion: { (finished) in         })     } } 


回答4:

Swift 3 Equivalent of Burak's answer. You can programmatically fire off this call wherever you want, I put it in a helper function so any table view could show this. And the first time a user uses my app I swipe it open (I felt a longer animation time was needed).

class func animateRevealHideActionForRow(tableView: UITableView, indexPath: NSIndexPath) {     let cell = tableView.cellForRow(at: indexPath as IndexPath);      // Should be used in a block     var swipeLabel: UILabel? = UILabel.init(frame: CGRect.init(x: cell!.bounds.size.width, y: 0, width: 200, height: cell!.bounds.size.height))      swipeLabel!.text = "  Swipe Me";     swipeLabel!.backgroundColor = UIColor.red     swipeLabel!.textColor = UIColor.white     cell!.addSubview(swipeLabel!)      UIView.animate(withDuration: 1.0, animations: {         cell!.frame = CGRect.init(x: cell!.frame.origin.x - 100, y: cell!.frame.origin.y, width: cell!.bounds.size.width + 100, height: cell!.bounds.size.height)     }) { (finished) in         UIView.animate(withDuration: 1.0, animations: {             cell!.frame = CGRect.init(x: cell!.frame.origin.x + 100, y: cell!.frame.origin.y, width: cell!.bounds.size.width - 100, height: cell!.bounds.size.height)         }, completion: { (finished) in             swipeLabel?.removeFromSuperview()             swipeLabel = nil;         })     } } 


易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!