Почему canPerformAction вызывается снова, когда вызывается действие menuItem? - PullRequest
0 голосов
/ 08 мая 2018

Ниже мой код, я обнаружил, когда щелкнул меню «pasteAndGo», напечатаны две строки журнала: 1. вставить и перейти показать 2.paste и перейти нажал. Мое требование - когда отображается меню, отображается журнал «вставь и иди покажи». При щелчке по нему отображается журнал «вставь и нажми».

class MyTextField: UITextField {

      private func Init() {
          let menuController: UIMenuController = UIMenuController.shared
          menuController.isMenuVisible = true
          let pasteAndGoMenuItem: UIMenuItem = UIMenuItem(title: "pasteAndGo", action: #selector(pasteAndGo(sender:)))

          let myMenuItems: NSArray = [pasteAndGoMenuItem]
          menuController.menuItems = myMenuItems as? [UIMenuItem]
      }

      @objc private func pasteAndGo(sender: UIMenuItem) {
          Print("paste and go clicked")
      }

      override func canPerformAction(_ action: Selector, withSender sender: Any?) -> Bool {
          let pasteboard = UIPasteboard.general

          if action == #selector(pasteAndGo) {
              if pasteboard.url != nil {
              Print("paste and go show")
                  return true
          } else {
              return false
          }
        }

        return super.canPerformAction(action, withSender: sender)
    }
}

1 Ответ

0 голосов
/ 08 мая 2018

Ваш код работает как реализовано:

  • В тот момент, когда вы нажимаете элемент меню pasteAndGo , платформа UIKit вызывает canPerformAction, чтобы спросить, разрешено ли выполнять действие или нет. Здесь вы печатаете «вставить и пойти показать»
  • Так как вы возвращаете true, ваше действие pasteAndGo(sender:) выполняется и печатает «вставь и нажми»

Чтобы отреагировать на отображаемый элемент меню, вам необходимо зарегистрироваться в центре уведомлений с уведомлением UIMenuControllerWillShowMenu, например:

// create a property 
var token:NSObjectProtocol?

// then add observer  
self.token = NotificationCenter.default.addObserver(forName: Notification.Name.UIMenuControllerWillShowMenu,
                                           object: nil,
                                           queue: OperationQueue.main)
    { _ in
        print ("paste and go show")
    }

и не забудьте отписаться (NotificationCenter.default.removeObserver), как только ваш viewcontroller будет удален.

if let t = self.token {
    NSNotificationCenter.defaultCenter().removeObserver(t)
}

Обновление

Вы также можете сделать это (без свойств) в Init

// in Init
var token = NotificationCenter.default.addObserver(forName: Notification.Name.UIMenuControllerWillShowMenu,
                                           object: nil,
                                           queue: OperationQueue.main)
    { _ in
        print ("paste and go show")
        NSNotificationCenter.defaultCenter().removeObserver(token)
    }
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...