Meine iOS-App verwendet eine benutzerdefinierte Höhe für die, UINavigationBar
was zu einigen Problemen auf dem neuen iPhone X führt.
Weiß jemand bereits, wie man programmgesteuert (in Objective-C) zuverlässig erkennt, ob eine App auf dem iPhone X ausgeführt wird?
BEARBEITEN:
Natürlich ist es möglich, die Größe des Bildschirms zu überprüfen. Ich frage mich jedoch, ob es eine "eingebaute" Methode gibt TARGET_OS_IPHONE
, mit der iOS erkannt werden kann ...
if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPhone) {
CGSize screenSize = [[UIScreen mainScreen] bounds].size;
if (screenSize.height == 812)
NSLog(@"iPhone X");
}
EDIT 2:
Ich glaube nicht, dass meine Frage ein Duplikat der verknüpften Frage ist. Natürlich gibt es Methoden, um verschiedene Eigenschaften des aktuellen Geräts zu "messen" und anhand der Ergebnisse zu entscheiden, welches Gerät verwendet wird. Dies war jedoch nicht der eigentliche Punkt meiner Frage, wie ich in meiner ersten Bearbeitung zu betonen versuchte.
Die eigentliche Frage lautet: "Kann direkt erkannt werden, ob es sich bei dem aktuellen Gerät um ein iPhone X handelt (z. B. durch eine SDK-Funktion), oder muss ich indirekte Messungen durchführen ? "
Bei den bisher gegebenen Antworten gehe ich davon aus, dass die Antwort "Nein, es gibt keine direkten Methoden. Messungen sind der richtige Weg" lautet.
quelle
Antworten:
Basierend auf Ihrer Frage lautet die Antwort nein. Es gibt keine direkten Methoden. Für weitere Informationen erhalten Sie die Informationen hier:
und
Die Höhe des iPhone X beträgt 2436 px
Vom Gerätebildschirm Größen und Auflösungen :
Von Gerätebildschirmgrößen und -ausrichtungen :
Swift 3 und höher :
Ziel-C :
Xamarin.iOS :
Basierend auf Ihrer Frage wie folgt:
Oder
screenSize.height
als float812.0f
nicht int verwenden812
.Weitere Informationen finden Sie auf der folgenden Seite in den Richtlinien für die Benutzeroberfläche von iOS:
Schnell :
Erkennen mit
topNotch
:Ziel-C :
UPDATE :
Verwenden Sie die
userInterfaceIdiom
Eigenschaft nicht, um den Gerätetyp zu identifizieren, wie in der Dokumentation zu userInterfaceIdiom erläutert:Das heißt, diese Eigenschaft wird nur verwendet, um den Ansichtsstil der laufenden App zu identifizieren. Die iPhone-App (nicht die universelle) kann jedoch über den App Store auf dem iPad-Gerät installiert werden. In diesem Fall wird die App
userInterfaceIdiom
zurückgegebenUIUserInterfaceIdiomPhone
auch.Der richtige Weg ist, den Maschinennamen über zu erhalten
uname
. Überprüfen Sie Folgendes für Details:quelle
userInterfaceIdiom
zurückgegebenUIUserInterfaceIdiomPhone
. Diese Antwort ist falsch.Eine weitere Möglichkeit, die unter iOS 11 und iOS 12 funktioniert, da das iPhone X das einzige mit einer Kerbe oben und einem Einschub von 44 ist. Das ist es, was ich hier wirklich erkenne:
Ziel c:
Swift 4:
Und natürlich müssen Sie möglicherweise die linken und rechten Sicherheitsbereiche überprüfen, wenn Sie sich im Querformat befinden.
Bearbeiten: _window ist das UIWindow des AppDelegate, in dem diese Prüfung in der Anwendung didFinishLaunchingWithOptions durchgeführt wird.
Die Antwort wurde für iOS 12 aktualisiert, um zu überprüfen, ob top> 24 statt top> 0 ist.
Bearbeiten: Im Simulator können Sie zu Hardware wechseln und die Statusleiste für eingehende Anrufe umschalten. Dies zeigt mir, dass sich die Höhe der Statusleiste auf dem iPhone X unter iOS 11 oder dem iPhone XS iOS 12 nicht ändert, wenn ein Anruf getätigt wird. Alles, was sich ändert, ist das Zeitsymbol, das in beiden Fällen einen grünen Hintergrund erhält. Hier ist ein Schnappschuss:
quelle
if _window.safeAreaInsets != UIEdgeInsets.zero
, um jede Geräteorientierung zu ermöglichen.top
,safeAreaInsets.bottom
wird 34 auf dem iPhone X und 0 auf anderen Geräten seinSie müssen je nach tatsächlichem Bedarf unterschiedliche Erkennungen des iPhone X durchführen.
für den Umgang mit der besten (Statusleiste, Navigationsleiste) usw.
für den Umgang mit der unteren Home-Anzeige (Tabbar) usw.
für Hintergrundgröße, Vollbildfunktionen usw.
Hinweis: Mischen Sie es schließlich mit
UIDevice.current.userInterfaceIdiom == .phone
Hinweis: Für diese Methode ist ein LaunchScreen-Storyboard oder die richtigen LaunchImages erforderlich
für Hintergrundverhältnis, Bildlauffunktionen usw.
Hinweis: Für diese Methode ist ein LaunchScreen-Storyboard oder geeignete LaunchImages erforderlich
für Analysen, Statistiken, Tracking usw.
Holen Sie sich die Maschinenkennung und vergleichen Sie sie mit dokumentierten Werten:
So nehmen Sie den Simulator als gültiges iPhone X in Ihre Analyse auf:
Um iPhone XS, XS Max und XR einzuschließen, suchen Sie einfach nach Modellen, die mit "iPhone11" beginnen:
für faceID-Unterstützung
quelle
return LAContext().biometryType == .typeFaceID
funktionieren würde, selbst wenn der Benutzer canEvaluatePolicy abgelehnt hätte, aber es funktioniert nicht für mich, es kehrt immer noch zurück.none
model == "iPhone10,3" || model == "iPhone10,6"
) verwenden. WenncanUseFaceID
false zurückgegeben wird, bedeutet dies, dass sie vom Benutzer abgelehnt wurde.Auf diese Weise können Sie das iPhone X- Gerät nach Abmessungen erkennen.
Schnell
Ziel c
Aber ,
Dies ist nicht ausreichend. Was wäre, wenn Apple das nächste iPhone mit der gleichen Größe wie das iPhone X ankündigen würde? Der beste Weg ist also, die Hardware-Zeichenfolge zu verwenden, um das Gerät zu erkennen.
Für neuere Geräte ist die Hardware-Zeichenfolge wie folgt.
iPhone 8 - iPhone10,1 oder iPhone iPhone
iPhone 8 Plus - iPhone 10,2 oder iPhone 10,5
iPhone X - iPhone10,3 oder iPhone10,6
quelle
[UIDevice currentDevice]
anstelle von[[UIDevice alloc] init]
Überprüfen Sie das Gerätemodell / den Computernamen. Verwenden Sie die Punkt- / Pixelanzahl NICHT direkt in Ihrem Code. Es handelt sich um harten Code und ist für die Gerätehardware bedeutungslos. Das Gerätemodell ist die einzige eindeutige Kennung für einen übereinstimmenden Gerätetyp .
Ergebnis:
Beziehen Sie sich auf diese Antwort .
Vollständige Code-Implementierung:
quelle
definiere IS_IPHONE_X (IS_IPHONE && [[UIScreen mainScreen] Grenzen] .size.height == 812.0)
Hinweis: - Seien Sie vorsichtig, es funktioniert nur für die Hochformatausrichtung
quelle
nativeScale
mit verwenden3.0
, oder?Nachdem ich mir alle Antworten angesehen hatte, tat ich Folgendes:
Lösung (Swift 4.1 kompatibel)
Verwenden
Hinweis
Vor Swift 4.1 können Sie überprüfen, ob die App auf einem Simulator wie folgt ausgeführt wird:
Ab Swift 4.1 können Sie anhand der Bedingung der Zielumgebungsplattform überprüfen, ob die App auf einem Simulator ausgeführt wird :
(Die ältere Methode wird weiterhin funktionieren, aber diese neue Methode ist zukunftssicherer.)
quelle
Alle diese auf Dimensionen basierenden Antworten können auf zukünftigen Geräten zu falschem Verhalten führen. Sie werden heute funktionieren, aber was ist, wenn es nächstes Jahr ein iPhone gibt, das die gleiche Größe hat, aber die Kamera usw. unter dem Glas hat, so dass es keine "Kerbe" gibt? Wenn die einzige Möglichkeit darin besteht, die App zu aktualisieren, ist dies eine schlechte Lösung für Sie und Ihre Kunden.
Sie können auch die Hardware-Modellzeichenfolge wie "iPhone10,1" überprüfen. Dies ist jedoch problematisch, da Apple manchmal unterschiedliche Modellnummern für verschiedene Netzbetreiber auf der ganzen Welt veröffentlicht.
Der richtige Ansatz besteht darin, das obere Layout neu zu gestalten oder die Probleme zu lösen, die Sie mit der Höhe der benutzerdefinierten Navigationsleiste haben (darauf würde ich mich konzentrieren). Wenn Sie sich jedoch entscheiden, keines dieser Dinge zu tun, stellen Sie fest, dass alles, was Sie tun, ein Hack ist, damit dies heute funktioniert , und Sie müssen es irgendwann korrigieren, möglicherweise mehrmals, um die Hacks beizubehalten Arbeiten.
quelle
SWIFT 4+ Antwort
iPhone X, XR, XS, XSMAX, 11 Pro, 11 Pro Max:
Hinweis: Benötigen Sie ein echtes Gerät zum Testen
Referenz
quelle
Wiederverwendbare SWIFT 4/5- Erweiterung mit iPhone 11- Unterstützung
quelle
UIDevice.current.hasHomeButton
Ja, es ist möglich. Laden Sie die UIDevice-Hardware-Erweiterung herunter (oder installieren Sie sie über den CocoaPod 'UIDevice-Hardware') und verwenden Sie dann:
Beachten Sie, dass dies im Simulator nicht funktioniert, sondern nur auf dem tatsächlichen Gerät.
quelle
ProcessInfo.processInfo.environment["SIMULATOR_MODEL_IDENTIFIER"]
in Simulator verwenden, um die tatsächlichen Werte von Xcode abzurufen .Laut der Antwort von @ saswanb handelt es sich um eine Swift 4-Version:
quelle
keyWindow
ist ,nil
bis die Hauptansicht - Controller genannt hatviewDidAppear
Ich weiß, dass es nur ein Swift ist Lösung ist, aber es könnte jemandem helfen.
Ich habe
globals.swift
in jedem Projekt und eines der Dinge, die ich immer hinzufüge, istDeviceType
, das Gerät des Benutzers leicht zu erkennen:Dann, um es zu benutzen:
Wenn Sie
LaunchImage
in Ihrem Projekt verwenden, stellen Sie sicher, dass Sie Bilder für alle unterstützten Geräte (wie XS Max, XR) hinzufügen, daUIScreen.main.bounds
ohne diese keine korrekten Werte zurückgegeben werden.quelle
if DeviceType.iPhoneX { //do something for iPhone X notch }else{ // don’t do anything about notch }
Alle Antworten, die das verwenden,
height
sind aus einem Grund nur der halbe Teil der Geschichte. Wenn Sie auf diese Weise prüfen, ob die Geräteorientierung stimmtlandscapeLeft
oderlandscapeRight
die Prüfung fehlschlägt, weil dieheight
mit der ausgetauscht wirdwidth
.Deshalb sieht meine Lösung in Swift 4.0 so aus:
quelle
Sie sollten nicht davon ausgehen, dass das einzige Gerät, das Apple mit einer anderen UINavigationBar-Höhe veröffentlicht, das iPhone X ist. Versuchen Sie, dieses Problem mit einer allgemeineren Lösung zu lösen. Wenn die Leiste immer 20 Pixel größer als die Standardhöhe sein soll, sollte Ihr Code die Höhe der Leiste um 20 Pixel erhöhen, anstatt sie auf 64 Pixel (44 Pixel + 20 Pixel) festzulegen.
quelle
quelle
Swift 3 + 4:
Beispiel:
quelle
quelle
quelle
Normalerweise benötigt der Programmierer dies, um sich auf oben oder unten zu beschränken, sodass diese Methoden hilfreich sein können
Für vor iPhone X geben diese Methoden Folgendes zurück: 0
Für iPhone X: 44 und 34 entsprechend
Fügen Sie diese Extras dann einfach zu den oberen oder unteren Einschränkungen hinzu
quelle
Für diejenigen, die 2001px anstelle von 2436px für die native Grenzhöhe erhalten (wie ich), liegt dies daran, dass Sie Ihre App mit einem älteren SDK vor iOS 11 erstellt haben (Xcode 8 anstelle von Xcode 9). Mit einem älteren SDK zeigt iOS die Apps "Black Boxed" auf dem iPhone X an, anstatt den Bildschirm von Rand zu Rand über die oberste "Sensorkerbe" hinaus zu erweitern. Dies reduziert die Bildschirmgröße, weshalb diese Eigenschaft 2001 anstelle von 2436 zurückgibt.
Die einfachste Lösung besteht darin, nur nach beiden Größen zu suchen, wenn Sie nur an der Geräteerkennung interessiert sind. Ich habe diese Methode zum Erkennen von FaceID verwendet, während ich mit einem älteren Xcode SDK erstellt habe, dessen ENUM-Wert nicht den biometrischen Typ angibt. In dieser Situation schien die Geräteerkennung anhand der Bildschirmhöhe der beste Weg zu sein, um festzustellen, ob das Gerät über FaceID oder TouchID verfügt, ohne Xcode aktualisieren zu müssen.
quelle
Verwenden Sie NICHT die Bildschirmpixelgröße, wie andere Lösungen vorgeschlagen haben. Dies ist schlecht, da dies bei zukünftigen Geräten zu Fehlalarmen führen kann. funktioniert nicht, wenn UIWindow noch nicht gerendert wurde (AppDelegate), funktioniert nicht in Landschafts-Apps und kann im Simulator fehlschlagen, wenn die Skalierung festgelegt ist.
Ich habe stattdessen ein Makro für diesen Zweck erstellt, das sehr einfach zu verwenden ist und sich auf Hardware-Flags stützt, um die oben genannten Probleme zu vermeiden.
Bearbeiten: Aktualisiert, um iPhoneX, iPhone XS, iPhoneXR, iPhoneXS max zu unterstützen
Benutzen:
Ja, wirklich.
Makro:
Kopieren Sie diese einfach und fügen Sie sie irgendwo ein. Ich bevorzuge den unteren Rand meiner .h-Datei danach
@end
quelle
if (@available(iOS 11.0, *)) { [UIApplication sharedApplication].keyWindow.safeAreaInsets.top }
Ich habe die Antworten Ihrer Mitarbeiter ausgearbeitet und UIDevice schnell erweitert. Ich mag schnelle Aufzählungen und "alles in Ordnung" & atomisiert. Ich habe eine Lösung erstellt, die sowohl auf dem Gerät als auch auf dem Simulator funktioniert.
Vorteile: - einfache Oberfläche, Verwendung zB
UIDevice.current.isIPhoneX
-UIDeviceModelType
Enum bietet Ihnen die Möglichkeit, modellspezifische Funktionen und Konstanten, die Sie in Ihrer App verwenden möchten, z. B. CornerRadius, einfach zu erweiternNachteil: - Es handelt sich um eine modellspezifische Lösung, nicht um eine auflösungsspezifische Lösung. - Wenn Apple beispielsweise ein anderes Modell mit denselben Spezifikationen herstellt, funktioniert dies nicht ordnungsgemäß und Sie müssen ein weiteres Modell hinzufügen, damit dies funktioniert. => Sie müssen Ihr Modell aktualisieren App.
quelle
Mirror
, ist die Verwendung schnellersysctlbyname
als in der Cloud9999Strife-Antwort (und auch in meiner Antwort).Ich verlasse mich auf die Höhe des Statusleistenrahmens, um festzustellen, ob es sich um ein iPhone X handelt:
Dies ist für die Anwendung un Porträt. Sie können die Größe auch entsprechend der Geräteorientierung überprüfen. Bei anderen iPhones ist die Statusleiste möglicherweise ausgeblendet, sodass die Rahmenhöhe gleich ist
0
. Auf dem iPhone X wird die Statusleiste niemals ausgeblendet.quelle
controller
:- (BOOL)prefersStatusBarHidden { return YES; }
Dann ist die Höhe der statusBar 0.Ich habe den Code von Peter Kreinz verwendet (weil er sauber war und das tat, was ich brauchte), aber dann wurde mir klar, dass er nur funktioniert, wenn sich das Gerät im Hochformat befindet (da die obere Polsterung natürlich oben ist). Also habe ich eine Erweiterung erstellt, um alle zu verarbeiten Ausrichtungen mit den jeweiligen Polsterungen, ohne die Bildschirmgröße zu beeinflussen:
Und auf Ihrer Anrufseite haben Sie nur:
quelle
Alternativ können Sie sich den Pod " DeviceKit " ansehen. Nach der Installation müssen Sie lediglich Folgendes überprüfen, um das Gerät zu überprüfen:
quelle
November 2019:
Folgendes verwende ich in all meinen Produktionsprojekten. Beachten Sie, dass dieser Kern ziemlich lang ist.
Funktioniert mit Simulatoren 💯
Verwendung: lassen Sie einfügen: CGFloat = DeviceUtility.isIphoneXType? 50,0: 40,0
quelle
Ich musste das gleiche Problem kürzlich lösen. Und während diese Frage definitiv beantwortet wird ("Nein"), kann dies anderen helfen, die ein iPhone X-spezifisches Layoutverhalten benötigen.
Ich war nicht wirklich daran interessiert, ob das Gerät ein iPhone X war. Ich war daran interessiert, ob das Gerät ein gekerbtes Display hatte.
Sie können auch eine
hasOnScreenHomeIndicator
Variable in die gleiche Richtung schreiben (obwohl Sie vielleicht den unteren sicheren Bereich überprüfen?).Im obigen Abschnitt wird meine Erweiterung
UIView
für den bequemen Zugriff auf die Sicherheitsbereiche unter iOS 10 und früheren Versionen verwendet.quelle
In Portrait nur verwende ich die Breite des Rahmens Ansicht und Höhe zu überprüfen:
Die Abmessungen des Hochformatbildschirms sind hier aufgelistet
quelle
Es gibt mehrere Gründe, um zu wissen, was das Gerät ist.
Sie können die Gerätehöhe (und -breite) überprüfen. Dies ist nützlich für das Layout, aber normalerweise möchten Sie dies nicht tun, wenn Sie das genaue Gerät kennen möchten.
Für Layoutzwecke können Sie auch verwenden
UIView.safeAreaInsets
.Wenn Sie den Gerätenamen anzeigen möchten, der beispielsweise zu Diagnosezwecken in eine E-Mail aufgenommen werden soll, können Sie nach dem Abrufen des Gerätemodells mithilfe
sysctl ()
des entsprechenden Namens den Namen ermitteln:quelle