2017-10-14 11 views
0

アドレス帳から連絡先番号を選択しようとしていますが、その論理を改訂しようとしているときに、番号をクリックするとアドレス帳を選択できませんでしたその番号を呼び出しています。番号を選択しようとしている間は、代表団は呼び出されません。コンタクトピッカーの委任が正しく設定されていない

以下のコードはかなり長いですが、私はすべてを記述しようとしています(無関係のコードは省略しています)ので、問題のアイデアを得ることができます。

ので、複雑な物事は私がHomeHelper(のUITableViewとのUIView)と呼ばれるヘルパーからのすべてのデータを設定するのですHomeViewControllerを、持っている、です。 WidgetViewというビューからUITableViewCellを追加し、データはWidgetHelperから設定されています。 WidgetHelperは、WidgetProductAHelperという名前のUITableViewCell(およびWidgetProductAViewというビュー)を読み込みます。

WidgetProductAViewにはイメージボタンがあり、ボタンをクリックすると、コンタクトピッカーが表示されます。私はAddressBookHelperと呼ばれる新しいクラスにロジックを分けようとしているので、私は余分なことなしにこれをどこでも使うことができます。アドレス帳を表示するのに成功しますが、そのうちの1つをクリックしようとすると、peoplePickerNavigationControllerのメソッドを呼び出すのではなく、詳細の連絡先画面にリダイレクトされます。私はその代表団を設定しましたが、それでも動作しません。

これは1つのクラスにのみ書き込むときに機能します。何が間違っていますか?私は助手を使っていくつかの不適切な実装があると思うが、それを理解することはできないと思う。ありがとう。

HomeViewController.swift

class HomeViewController: UIViewController { 

    var dataSource : UITableViewDataSource? 
    var delegate : UITableViewDelegate? 

    override func viewDidLoad() { 
     // 
     let helper = HomeHelper() 

     helper.homeViewController = self 

     dataSource = helper 
     delegate = helper 

     tableView.dataSource = dataSource 
     tableView.delegate = delegate 
    } 

} 

HomeHelper.swift

class HomeHelper: UITableViewDataSource, UITableViewDelegate, WidgetViewDelegate { 

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell { 
     guard let cell = tableView.dequeueReusableCell(withIdentifier: "WidgetView", for: indexPath) as? UITableViewCell else { 
      return UITableViewCell() 
     } 

     if let customView = cell.customView as? WidgetView { 
      let helper = WidgetHelper() 
      customView.helperDataSource = helper 
      customView.helperDelegate = helper 
      customView.delegate = self 
      helper.controller = customView 

      customView.initCell() 

      return cell 
     } 
    } 

    // MARK: - WidgetViewDelegate 

    func presentOnHome(_ viewControllerToPresent: UIViewController, animated: Bool, completion: (() -> Swift.Void)? = nil) { 
     self.homeViewController?.present(viewControllerToPresent, animated: animated, completion: completion) 
    } 

} 

WidgetView.swift

protocol WidgetViewDelegate { 
    func presentOnHome(_ viewControllerToPresent: UIViewController, animated: Bool, completion: (() -> Swift.Void)?) 
} 

class WidgetView: NSObject { 

    var delegate: WidgetViewDelegate? 

    var helperDataSource: WidgetViewHelperDataSource? 
    var helperDelegate: WidgetViewHelperDelegate? 

    func initCell() { 
     // 
     tableView.dataSource = helperDataSource 
     tableView.delegate = helperDelegate 
    } 

    func presentOnHome(_ viewControllerToPresent: UIViewController, animated: Bool, completion: (() -> Swift.Void)?) { 
     delegate?.presentOnHome(viewControllerToPresent, animated: animated, completion: completion) 
    } 

} 

WidgetHelper.swift

class WidgetHelper: UITableViewDataSource, UITableViewDelegate, WidgetProductAHelperDelegate { 

    var controller: WidgetView? 

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell { 
     guard let cell = tableView.dequeueReusableCell(withIdentifier: "WidgetProductAView", for: indexPath) as? UITableViewCell else { 
      return UITableViewCell() 
     } 

     if let customView = cell.customView as? WidgetProductAHelper { 
      customView.parentHelper = self 
      customView.delegate = self 
      customView.initCell() 

      return cell 
     } 
    } 

    // MARK: - WidgetProductAHelperDelegate 

    func presentOnHome(_ viewControllerToPresent: UIViewController, animated: Bool, completion: (() -> Swift.Void)? = nil) { 
     self.homeViewController?.present(viewControllerToPresent, animated: animated, completion: completion) 
    } 

} 

WidgetProductAHelper.swift

protocol WidgetProductAHelperDelegate { 
    func presentOnHome(_ viewControllerToPresent: UIViewController, animated: Bool, completion: (() -> Swift.Void)?) 
} 

class WidgetProductAHelper: UITableViewDataSource, UITableViewDelegate { 

    @IBOutlet var contactImageButton: UIButton! 

    var parentHelper: WidgetHelper? 
    var delegate: WidgetProductAHelperDelegate? 

} 

func initCell() { 
    // 
    contactImageButton.isUserInteractionEnabled = true; 
    contactImageButton.addGestureRecognizer(UITapGestureRecognizer(target: self, action: #selector(WidgetProductAHelper.contactImageButtonTapped(_:)))) 
} 

func contactImageButtonTapped(_ sender: UIGestureRecognizer) { 
    let addressBookHelper = AddressBookHelper() 
    addressBookHelper.contactImageButton = contactImageButton 
    addressBookHelper.completion = { (result) in 
     switch result { 
     case .presentOnHome(let viewControllerToPresent) : 
      self.parentHelper?.presentOnHome(viewControllerToPresent, animated: true, completion: nil) 

      break 
     } 
    } 
    addressBookHelper.addressBookButtonTapped() 
} 

AddressBookHelper.swift

あなたは、コードの下に見ての通り、私はにCNPickerのデリゲートを設定していますただし、デリゲートのメソッドを呼び出すことはありません。 displayErrorMessage()やdisplayPromptForAddressBookRequestAccess()のような別のものについては、ポップアップの表示にはうまくいきます。この機能では

enum AddressBookActionResult { 
    case presentOnHome(viewControllerToPresent: UIViewController) 
} 

class AddressBookHelper: NSObject, CNContactPickerDelegate { 

    var completion: ((AddressBookActionResult) ->())? 

    var contactImageButton: UIButton? 

    @available(iOS 9.0, *) 
    var CNPicker: CNContactPickerViewController { 
     return CNContactPickerViewController() 
    } 

    func addressBookButtonTapped() { 
     switch CNContactStore.authorizationStatus(for: .contacts) { 
     case .denied, .restricted: 
      // displayErrorMessage() 
      break 
     case .authorized: 
      openUserAddressBook() 
      break 
     case .notDetermined: 
      // displayPromptForAddressBookRequestAccess() 
      break 
     } 
    } 

    func openUserAddressBook() { 
     if #available(iOS 9.0, *) { 
      CNPicker.delegate = self 
      completion?(.presentOnHome(viewControllerToPresent: CNPicker)) 
     } 
    } 


    // MARK: - CNContactPickerDelegate 

    @available(iOS 9.0, *) 
    func contactPicker(_ picker: CNContactPickerViewController, didSelect contact: CNContact) { 
     // This method doesn't get called 
     //... 
    } 

} 

答えて

2

ルック:

func openUserAddressBook() { 
     let CNPicker: CNContactPickerViewController = CNContactPickerViewController() 
     CNPicker.delegate = self 
     completion?(.presentOnHome(viewControllerToPresent: CNPicker)) 
    } 

あなたは、その関数内CNPickerを作成していると、すぐにそれ終了openUserAddressBook関数として、CNPickerがリリースされます。

CNPickerをAddressBookHelperの最上部にあるプロパティにするとよいでしょう。

例えば:

class AddressBookHelper: NSObject, CNContactPickerDelegate { 

    // create CNContactPickerViewController once and only once 
    let cnPicker = CNContactPickerViewController() 

    var completion: ((AddressBookActionResult) ->())? 

    override init() 
    { 
     super.init() 

     // and set the delegate of the picker to this Helper class 
     self.cnPicker.delegate = self 
    } 

    func openUserAddressBook() { 
     completion?(.presentOnHome(viewControllerToPresent: self.cnPicker)) 
    } 

    func contactPicker(_ picker: CNContactPickerViewController, 
        didSelect contact: CNContact) 
    { 
     print("selected a contact!") 
    } 

    // and other delegate methods can be implemented and they 
    // will be called... 

} 
+0

こんにちは@Michael Dautermann、どうもありがとうございますが、それでも私のためには機能しません。私はあなたの参照のための質問を更新しました。 –

+0

あなたが今やっていることは、 'CNPicker'プロパティの各呼び出しに対して' return CNContactPickerViewController() 'が***それぞれ、参照されるたびに新しいCNContactPickerViewControllerを作成します。 CNContactPickerViewControllerを一度作成してプロパティに設定する必要があります。 –

+0

oic、それは今、感謝@マイケルDautermannを働いています:) –

0

CNContactPickerDelegateが、それは代わりに

func contactPicker(CNContactPickerViewController, didSelect: CNContact) 
Called after a contact has been selected by the user. 

あなたがここに https://developer.apple.com/documentation/contactsui/cncontactpickerdelegate

をデリゲートのメソッドの完全なリストを見ることができますを持っている方法

func peoplePickerNavigationController(_ peoplePicker: ABPeoplePickerNavigationController, didSelectPerson person: ABRecord) { 
     // This method doesn't get called 
     //... 
} 

を持っていません0

+0

こんにちは@Sergnsk、whoops申し訳ありませんが、私はちょうどコードを更新した、私は私のプロジェクトから間違ったコードをコピーしました。 –

関連する問題