web-dev-qa-db-fra.com

Comment vérifier si Haptic Engine (UIFeedbackGenerator) est pris en charge

Je me demande comment nous pourrions vérifier si la nouvelle API iOS 10 UIFeebackGenerator est disponible sur le périphérique actuel. Il y a encore quelques points à vérifier:

  1. L'appareil doit exécuter iOS 10.0 ou une version ultérieure.
  2. L'appareil doit être un iPhone 7 ou une version ultérieure.
  3. Haptic Engine doit être activé dans les paramètres 

Les deux premières vérifications peuvent être réalisées à l'aide de l'instruction #available(iOS 10, *) et d'une détection de périphérique (hacky), mais la dernière ne semble pas être vérifiable.

Est-ce que quelqu'un connaît une solution pour cela? Ou peut-être avons-nous besoin de déposer un radar Apple pour celui-ci. Merci!

12
Hans Knöchel

Basé sur la documentation UIFeedbackGenerator d'Apple , sonne comme iOS le fait pour vous. 

Notez que l'appel de ces méthodes ne joue pas directement les haptiques . Au lieu de cela, il informe le système de l'événement. Le système alors détermine si les haptiques doivent être lues en fonction du périphérique, le l’état de l’application, la quantité de charge restante de la batterie, et autres les facteurs.

Par exemple, le retour haptique est actuellement joué uniquement:

Sur un appareil doté d'un Taptic Engine pris en charge (iPhone 7 et iPhone 7 Plus).

Lorsque l'application est en cours d'exécution au premier plan.

Lorsque le paramètre System Haptics est activé.

Même si vous n'avez pas à vous soucier de vérifier si l'appareil peut prendre en charge les remarques haptiques, vous devez toujours vous assurer qu'il est appelé uniquement avec iOS 10 ou une version ultérieure, afin que vous puissiez accomplir cela avec:

    if #available(iOS 10,*) {
        // your haptic feedback method
    }

Voici un bref résumé des différentes options de retour haptique disponible dans iOS 10.

6
Adrian

Il y a une "chose privée" non documentée:

UIDevice.currentDevice().valueForKey("_feedbackSupportLevel");

it renvoie 2 pour les appareils avec retour haptique - iPhone 7/7 + vous permettant ainsi de l’utiliser facilement pour générer du retour Haptic:

let generator = UIImpactFeedbackGenerator(style: .heavy)
generator.prepare()
generator.impactOccurred()

renvoie 1 pour iPhone 6S, voici une solution de remplacement pour générer des bandes:

import AudioToolbox

AudioServicesPlaySystemSound(1519) // Actuate `Peek` feedback (weak boom)
AudioServicesPlaySystemSound(1520) // Actuate `Pop` feedback (strong boom)
AudioServicesPlaySystemSound(1521) // Actuate `Nope` feedback (series of three weak booms)

et renvoie 0 pour les appareils iPhone 6 ou plus anciens. Comme il s’agit d’une sorte de document non documenté, il pourrait vous bloquer pendant la phase de révision, même si j’ai réussi à passer en revue et à soumettre l’application avec un tel contrôle.

Plus de détails: http://www.mikitamanko.com/blog/2017/01/29/haptic-feedback-with-uifeedbackgenerator/

12
Mikita Manko

J'ai créé une extension pour UIDevice sans utiliser l'API privée 

extension UIDevice {

 static var isHapticsSupported : Bool {

    let feedback = UIImpactFeedbackGenerator(style: .heavy)
    feedback.prepare()
    var string = feedback.debugDescription
    string.removeLast()
    let number = string.suffix(1)

    if number == "1" {
        return true
    } else {
        return false
    }
  }
}

et vous l'utilisez comme ceci: 

UIDevice.isHapticsSupported 

renvoie true ou false

1
Rom4in

Vous savez que votre appareil supporte l’effet de vibration Haptic ou non avec le code ci-dessous

UIDevice.currentDevice().valueForKey("_feedbackSupportLevel");

Ces méthodes semblent revenir:

  • 0 = Taptic non disponible

  • 1 = Première génération (testé sur un iPhone 6s) ... ce qui n’empêche PAS support UINotificationFeedbackGenerator, etc.

  • 2 = Deuxième génération (testé sur un iPhone 7) ... qui prend en chargeit.

il renvoie 2 pour les appareils avec retour haptique - iPhone 7/7 + ou supérieur, vous pouvez donc facilement l'utiliser pour générer un retour Haptic

1
Ashish

Cela fonctionnera pour iPhone 7 et supérieur.

 var count = 0

 override func viewDidLoad() {
    super.viewDidLoad()

    let myButton = UIButton(frame: CGRect(x: 0, y: 100, width: 100, height: 50))
    myButton.setTitleColor(UIColor.green, for: .normal)
    myButton.setTitle("Press ME", for: .normal)
    myButton.addTarget(self, action: #selector(myButtonTapped), for: .touchUpInside)
    self.view.addSubview(myButton)

}

@objc func myButtonTapped() {
    count += 1
    print("Count \(count)")

    switch count {
    case 1:
        let generator = UINotificationFeedbackGenerator()
        generator.notificationOccurred(.error)

    case 2:
        let generator = UINotificationFeedbackGenerator()
        generator.notificationOccurred(.success)

    case 3:
        let generator = UINotificationFeedbackGenerator()
        generator.notificationOccurred(.warning)

    case 4:
        let generator = UIImpactFeedbackGenerator(style: .light)
        generator.impactOccurred()

    case 5:
        let generator = UIImpactFeedbackGenerator(style: .medium)
        generator.impactOccurred()

    case 6:
        let generator = UIImpactFeedbackGenerator(style: .heavy)
        generator.impactOccurred()

    default:
        let generator = UISelectionFeedbackGenerator()
        generator.selectionChanged()
        count = 0
    }
}
0
Yogendra Singh