web-dev-qa-db-ja.com

iOS9デバイスで3Dtouchがサポートされ、有効になっているかどうかを確認します

トレイトコレクションにアクセスして「forceTouchCapability」を確認しようとしましたが、「forceTouchCapability」はデバイスがiOS9.0以降かどうかを確認するだけです。

つまり、これはiOS 9を搭載したすべてのデバイスで、感圧タッチが「利用可能」であることを意味します。ユーザーデバイス(iPhone 6s)で3D Touchが実際にサポートされているかどうかを確認する方法が必要です。また、ユーザー補助設定で3DTouchオプションが実際に有効になっていることを確認する必要があります。

13
Prodigga

誤ってforceTouchCapabilityBOOLにキャストしていました(ブール値を返すように設定されたメソッドへの戻り値として使用していました)。 forceTouchCapabilityUIForceTouchCapabilityAvailableと等しいかどうかを確認する必要がありました。

の代わりに:

return [[MyView traitCollection] forceTouchCapability];

私は欲しい:

return [[MyView traitCollection] forceTouchCapability] == UIForceTouchCapabilityAvailable;
23
Prodigga

これをUIViewControllerに実装する場合、タイミングが重要になります。 viewDidLoadをチェックインすると、ライフサイクルの後半でUnknownが返されるときにAvailableが返されます。

- (void)traitCollectionDidChange:(nullable UITraitCollection *)previousTraitCollection {
    [self checkForForceTouch];
}

- (void)checkForForceTouch {
    if ([self.traitCollection respondsToSelector:@selector(forceTouchCapability)] &&
        self.traitCollection.forceTouchCapability == UIForceTouchCapabilityAvailable) {
        NSLog(@"Force touch found");
    }
}
12
amleszk

場合によっては、今すぐforceTouchCapability値を同期的に保持し、traitCollectionDidChange:イベントを待ちたくないことがあります。その場合、次のようなかなりばかげた関数を使用できます。

public func forceTouchCapability() -> UIForceTouchCapability {
    return UIApplication.sharedApplication().keyWindow?.rootViewController?.traitCollection.forceTouchCapability ?? .Unknown
}
3
_if ([MyView respondsToSelector:@selector(traitCollection)] &&
    [MyView.traitCollection respondsToSelector:@selector(forceTouchCapability)] &&
    MyView.traitCollection.forceTouchCapability == UIForceTouchCapabilityAvailable) {
        return YES;
    }
_

私のポイントは、iOS 7iOS 8もサポートしている場合は、[MyView respondsToSelector:@selector(traitCollection)][MyView.traitCollection respondsToSelector:@selector(forceTouchCapability)]

最初のチェックを続けると、アプリはiOS 7では正常に動作しますが、iOS8ではクラッシュします。基本的にAppleはiOS8でtraitCollectionプロパティを導入しましたが、iOS9でのみforceTouchCapabilityプロパティを追加しました。

fromUITraitCollection.h

_@property (nonatomic, readonly) UITraitCollection *traitCollection NS_AVAILABLE_IOS(8_0);

@property (nonatomic, readonly) UIForceTouchCapability forceTouchCapability NS_AVAILABLE_IOS(9_0);
_

PS:App Storeでアプリがクラッシュし始めた後、難しい方法でそれを学びました。

3
Aditya

Swift4.0および4.1。

import UIKit

class ViewController: UIViewController {
     override func viewDidLoad() {
        super.viewDidLoad()
        // Check device supports feature
        if self.traitCollection.forceTouchCapability == .available {
        // Enable 3D Touch feature here
         } else {
        // Fall back to other non 3D feature
         }
      }
      override func traitCollectionDidChange(_ previousTraitCollection: UITraitCollection?) {
        // Update the app's 3D Touch support
      if self.traitCollection.forceTouchCapability == .available {
          // Enable 3D Touch feature here
      } else {
          // Fall back to other non 3D feature
      }
    }
  }
0
Gurjinder Singh

valentin Sherginに続いて、同期呼び出しが必要な場合はSwift 4.2に更新:

func forceTouchCapability() -> UIForceTouchCapability {
    return UIApplication.shared.keyWindow?.rootViewController?.traitCollection.forceTouchCapability ?? .unknown
}


func hasForceTouchCapability() -> Bool {
    return forceTouchCapability() == .available
}
0
ingconti