2017-05-23 47 views
0

我在UIViewController裏面有一個UITableView。在我tableView(_:cellForRowAt:,我配置了一個自定義的按鈕detailDisclosure細胞,如下:爲UITableView自定義詳細信息披露按鈕配置操作

cell.accessoryType = .detailDisclosureButton 

我也實現tableView(_:accessoryButtonTappedForRowWith:)。使用「工廠」detailDisclosureButton完美。我不在乎這個圖標,所以我試圖改變它。

設置cell.accessoryType後,添加以下代碼:

// declare the button 
let customDetailDisclosureButton = UIButton.init(type: .detailDisclosure) 

// set the image for .normal and .selected 
customDetailDisclosureButton.setImage(UIImage(named: "info")?.withRenderingMode(.alwaysTemplate), for: .normal) 
customDetailDisclosureButton.setImage(UIImage(named: "info")?.withRenderingMode(.alwaysTemplate), for: .selected) 

// add a target action 
customDetailDisclosureButton.addTarget(self, action: #selector(tableView(_:accessoryButtonTappedForRowWith:)), for: .touchUpInside) 

cell.accessoryView = customDetailDisclosureButton 

當我加載tableView,它顯示優良。當我點擊detailDisclosureButton時,它崩潰。我究竟做錯了什麼?

這裏是控制檯輸出:

*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[UITouchesEvent length]: unrecognized selector sent to instance 0x6180000f1000' 
*** First throw call stack: 
(
    0 CoreFoundation      0x0000000102e9ab0b __exceptionPreprocess + 171 
    1 libobjc.A.dylib      0x00000001024ea141 objc_exception_throw + 48 
    2 CoreFoundation      0x0000000102f0a134 -[NSObject(NSObject) doesNotRecognizeSelector:] + 132 
    3 CoreFoundation      0x0000000102e21840 ___forwarding___ + 1024 
    4 CoreFoundation      0x0000000102e213b8 _CF_forwarding_prep_0 + 120 
    5 libswiftFoundation.dylib   0x000000010425c1a0 _TTSf4g_d___TFV10Foundation9IndexPathCfT11nsIndexPathCSo11NSIndexPath_S0_ + 32 
    6 libswiftFoundation.dylib   0x0000000104210a57 _TZFV10Foundation9IndexPath36_unconditionallyBridgeFromObjectiveCfGSqCSo11NSIndexPath_S0_ + 23 
    7 MyApp       0x0000000101e43ae7 _TToFC10MyApp22PlaylistViewController9tableViewfTCSo11UITableView31accessoryButtonTappedForRowWithV10Foundation9IndexPath_T_ + 71 
    8 UIKit        0x0000000104f17d22 -[UIApplication sendAction:to:from:forEvent:] + 83 
    9 UIKit        0x000000010509c25c -[UIControl sendAction:to:forEvent:] + 67 
    10 UIKit        0x000000010509c577 -[UIControl _sendActionsForEvents:withEvent:] + 450 
    11 UIKit        0x000000010509b4b2 -[UIControl touchesEnded:withEvent:] + 618 
    12 UIKit        0x0000000105440ea9 _UIGestureEnvironmentSortAndSendDelayedTouches + 5553 
    13 UIKit        0x000000010543bec0 _UIGestureEnvironmentUpdate + 1409 
    14 UIKit        0x000000010543b8f3 -[UIGestureEnvironment _deliverEvent:toGestureRecognizers:usingBlock:] + 484 
    15 UIKit        0x000000010543aaba -[UIGestureEnvironment _updateGesturesForEvent:window:] + 274 
    16 UIKit        0x0000000104f86b9a -[UIWindow sendEvent:] + 4092 
    17 UIKit        0x0000000104f337b0 -[UIApplication sendEvent:] + 352 
    18 UIKit        0x0000000105716adc __dispatchPreprocessedEventFromEventQueue + 2926 
    19 UIKit        0x000000010570ea3a __handleEventQueue + 1122 
    20 CoreFoundation      0x0000000102e40c01 __CFRUNLOOP_IS_CALLING_OUT_TO_A_SOURCE0_PERFORM_FUNCTION__ + 17 
    21 CoreFoundation      0x0000000102e260cf __CFRunLoopDoSources0 + 527 
    22 CoreFoundation      0x0000000102e255ff __CFRunLoopRun + 911 
    23 CoreFoundation      0x0000000102e25016 CFRunLoopRunSpecific + 406 
    24 GraphicsServices     0x0000000108d83a24 GSEventRunModal + 62 
    25 UIKit        0x0000000104f160d4 UIApplicationMain + 159 
    26 MyApp       0x0000000101e4df47 main + 55 
    27 libdyld.dylib      0x0000000104dfa65d start + 1 
    28 ???         0x0000000000000001 0x0 + 1 
) 
libc++abi.dylib: terminating with uncaught exception of 
+0

remove customDetailDisclosureButton.addTarget line –

+0

'tableView(_:accessoryButtonTappedForRowWith:)'與UIButton經典選擇器不兼容。第一個參數應該是按鈕(發件人),而不是tableView作爲委託方法。 – Larme

回答

1

替換

// add a target action 
customDetailDisclosureButton.addTarget(self, action: #selector(tableView(_:accessoryButtonTappedForRowWith:)), for: .touchUpInside) 

customDetailDisclosureButton.addTarget(self, action: #selector(ViewController.accessoryButtonTapped(sender:)), for: .touchUpInside) 

然後

func accessoryButtonTapped(sender : UIButton){ 
     let buttonPosition: CGPoint = (sender as! UIButton).convert(.zero, to: tableView) 
     let indexPath = tableView.indexPathForRow(at: buttonPosition) 
     // do what you gotta do with the indexPath 
    } 
+0

謝謝。我想用一個「工廠」解決方案,但是這樣做可以完成工作。我添加了代碼以從按鈕獲取indexPath。 – Adrian

0

嘗試使用,而不是選擇方法的委託方法:

func tableView(_ tableView: UITableView, accessoryButtonTappedForRowWith indexPath: IndexPath) { 
    // do you work 
} 

OR

添加查看及其選擇方法如下:

let button = UIButton(type: .custom) 
button.addTarget(self, action: #selector(HomeViewController.checkButtonTapped(_:event:)), for: .touchUpInside) 
cell?.accessoryView = button 

選擇

func checkButtonTapped(_ sender: Any, event: Any) { 
    let touches: Set<AnyHashable>? = (event as AnyObject).allTouches 
    let touch: UITouch? = touches?.first as! UITouch? 
    let currentTouchPosition: CGPoint? = touch?.location(in: tblViewHome) 
    let indexPath: IndexPath? = youtTblView?.indexPathForRow(at: currentTouchPosition!) 
    if indexPath != nil { 
     tableView(youtTblView!, accessoryButtonTappedForRowWith: indexPath!) 
    } 
} 
+0

我已經實現了。它與「工廠」委託方法一起工作。 – Adrian

相關問題