2010-05-05 2 views

Antwort

883

Die window property Sicht ist ungleich Null, wenn eine Ansicht zur Zeit sichtbar ist, so die Hauptansicht überprüfen im View-Controller:

[EDIT] Aufrufen der view Methode bewirkt, dass die zu laden (wenn es nicht geladen ist), was unnötig ist und unerwünscht sein kann. Es wäre besser, zuerst zu prüfen, ob es bereits geladen ist. Ich habe den Aufruf von isViewLoaded hinzugefügt, um dieses Problem zu vermeiden.

if (viewController.isViewLoaded && viewController.view.window) { 
    // viewController is visible 
} 

Oder wenn Sie einen UINavigationController der View-Controller verwalten, können Sie seine visibleViewController Eigenschaft stattdessen überprüfen.

Auch in Swift auf iOS 9 (oder höher):

if viewController.viewIfLoaded?.window != nil { 
    // viewController is visible 
} 
+9

Das einzige Problem mit der visibleViewControllee-Eigenschaft eines UINavigationControllers ist der Fall, in dem Ihr visualViewController einen modalen View-Controller darstellt. In diesem Fall wird die modale Ansicht zum visibleViewController, was unerwünscht sein kann. Wie würdest du damit umgehen? – Moshe

+12

Dies ist wahrscheinlich für jeden offensichtlich, aber für mich musste der Code selbst sein.isViewLoaded && self.view.window – JeffB6688

+0

Beachten Sie, dass ein Navigations-Controller in iOS 7 nicht sofort einen Pushed-View-Controller in den Speicher lädt. Dies ist anders als bei iOS 6, wo Sie einen View-Controller verschieben können und sofort sehen, dass navController.topViewController.isViewLoaded wahr ist. – InkGolem

25

Sie wollen die UITabBarController ‚s selectedViewController Eigenschaft verwenden. Alle View-Controller auf eine Tab-Leiste Controller angeschlossen haben eine tabBarController Eigenschaft festgelegt, so können Sie, von innerhalb eines der Code Ansicht-Controller:

if([[[self tabBarController] selectedViewController] isEqual:self]){ 
    //we're in the active controller 
}else{ 
    //we are not 
} 
+2

Dies funktioniert nicht, wenn der View-Controller in einem Navigationscontroller enthalten ist und dieser Controller zum Tab-Controller hinzugefügt wird. Der Aufruf von selectedViewController gibt den Navigationscontroller und nicht den aktuellen Ansichtscontroller zurück. –

+2

@AntonHolmberg in diesem Fall, den sichtbaren View-Controller wie folgt: '((UINavigationController *) self.tabBarController.selectedViewController) .visibleViewController' – ma11hew28

+0

Oder sogar 'self.tabBarController.selectedIndex' Eigenschaft verwenden, wenn wir so weit gegangen sind. –

82

Hier @ progrmr-Lösung als UIViewController Kategorie:

// UIViewController+Additions.h 

@interface UIViewController (Additions) 

- (BOOL)isVisible; 

@end 


// UIViewController+Additions.m 

#import "UIViewController+Additions.h" 

@implementation UIViewController (Additions) 

- (BOOL)isVisible { 
    return [self isViewLoaded] && self.view.window; 
} 

@end 
2

Sie können es durch window Eigenschaft

if(viewController.view.window){ 

// view visible 

}else{ 

// no visible 

} 
3

, wenn Sie eine UINavigationController nutzen sind und wollen auch zu handhaben modale Ansichten, das folgende ist, was ich verwende:

+2

Ich habe diesen Weg gefunden zuverlässiger als die angenommene Antwort, wenn ein Navigationscontroller verfügbar ist. Dies kann wie folgt verkürzt werden: if ([self.navigationController.visibleViewController isKindOfClass: [eigene Klasse]]) { – Darren

2

Der Ansatz, den ich für einen modalen präsentierten View-Controller verwendet wurde, war die Klasse der präsentierten Controller zu überprüfen. Wenn der vorgestellte View-Controller ViewController2 wäre, würde ich etwas Code ausführen.

UIViewController *vc = [self presentedViewController]; 

if ([vc isKindOfClass:[ViewController2 class]]) { 
    NSLog(@"this is VC2"); 
} 
39

Es gibt ein paar Probleme mit den oben genannten Lösungen. Wenn Sie verwenden, beispielsweise ein UISplitViewController, wird die Master-Ansicht immer true zurück für

if(viewController.isViewLoaded && viewController.view.window) { 
    //Always true for master view in split view controller 
} 

Stattdessen nimmt diesen einfachen Ansatz, der in den meisten gut zu funktionieren scheint, wenn nicht alle Fälle:

- (void)viewDidDisappear:(BOOL)animated { 
    [super viewDidDisappear:animated]; 

    //We are now invisible 
    self.visible = false; 
} 

- (void)viewDidAppear:(BOOL)animated { 
    [super viewDidAppear:animated]; 

    //We are now visible 
    self.visible = true; 
} 
+1

Ist dies in xCode 7.1.1 immer noch richtig? Der Master in meinem UISplitViewController gibt NO für viewController.view.window zurück. Ich mag etwas falsch machen, aber ich bin mir ziemlich sicher, dass dies der Fall ist. – SAHM

7

Für meine Zwecke im Zusammenhang mit einem Container-view-Controller, habe ich festgestellt, dass

- (BOOL)isVisible { 
    return (self.isViewLoaded && self.view.window && self.parentViewController != nil); 
} 

gut funktioniert.

17

Für eine Präsentation im Vollbild- oder Over-Context-Modus bedeutet "is visible", dass es sich auf dem View-Controller-Stack befindet oder nur sichtbar ist, aber von einem anderen View-Controller abgedeckt wird.

Um zu überprüfen, ob der View-Controller "der Top-View-Controller" ist, unterscheidet er sich deutlich von "ist sichtbar". Überprüfen Sie den View-Controller-Stack des View-Controllers.

schrieb ich ein Stück Code, um dieses Problem zu lösen:

extension UIViewController { 
    public var isVisible: Bool { 
     if isViewLoaded() { 
      return view.window != nil 
     } 
     return false 
    } 

    public var isTopViewController: Bool { 
     if self.navigationController != nil { 
      return self.navigationController?.visibleViewController === self 
     } else if self.tabBarController != nil { 
      return self.tabBarController?.selectedViewController == self && self.presentedViewController == nil 
     } else { 
      return self.presentedViewController == nil && self.isVisible 
     } 
    } 
} 
+0

Netter Beitrag! FYI 'isViewLoaded' ist eine Eigenschaft seit Swift 3.0. –

11

I basierend auf @ progrmr Antwort eine rasche Erweiterung gemacht.

Es ermöglicht Ihnen, leicht zu überprüfen, ob ein UIViewController auf dem Bildschirm ist etwa so:

if someViewController.isOnScreen { 
    // Do stuff here 
} 

Die Erweiterung:

// 
// UIViewControllerExtension.swift 
// 

import UIKit 

extension UIViewController{ 
    var isOnScreen: Bool{ 
     return self.isViewLoaded() && view.window != nil 
    } 
} 
1

ich diese Funktion in UIViewController.h gefunden.

/* 
    These four methods can be used in a view controller's appearance callbacks to determine if it is being 
    presented, dismissed, or added or removed as a child view controller. For example, a view controller can 
    check if it is disappearing because it was dismissed or popped by asking itself in its viewWillDisappear: 
    method by checking the expression ([self isBeingDismissed] || [self isMovingFromParentViewController]). 
*/ 

- (BOOL)isBeingPresented NS_AVAILABLE_IOS(5_0); 
- (BOOL)isBeingDismissed NS_AVAILABLE_IOS(5_0); 

- (BOOL)isMovingToParentViewController NS_AVAILABLE_IOS(5_0); 
- (BOOL)isMovingFromParentViewController NS_AVAILABLE_IOS(5_0); 

Vielleicht sind die oben genannten Funktionen können erkennen, die ViewController erschienen ist oder nicht.

3

XCode 6.4 für iOS 8.4, aktiviert ARC

Offensichtlich viele Möglichkeiten, es zu tun. Die eine, die für mich gearbeitet hat, wird der folgende ...

@property(nonatomic, readonly, getter=isKeyWindow) BOOL keyWindow 

Dies kann in jeder View-Controller in der folgenden Art und Weise verwendet werden,

[self.view.window isKeyWindow] 

Wenn Sie diese Eigenschaft nennen in -(void)viewDidLoad Sie 0 erhalten , dann, wenn Sie dies nach -(void)viewDidAppear:(BOOL)animated anrufen, erhalten Sie 1.

Hoffe, dass dies jemand hilft. Vielen Dank! Prost.

33

diejenigen von Ihnen für eine Swift 2.2 Version der Antwort suchen:

if self.isViewLoaded() && (self.view.window != nil) { 
    // viewController is visible 
} 

und Swift 3:

if self.isViewLoaded && (self.view.window != nil) { 
     // viewController is visible 
} 
2

Wenn Sie ein Navigationscontroller und nur verwenden wollen Um zu wissen, ob Sie in der aktiven und obersten Controller sind, dann verwenden Sie:

if navigationController?.topViewController == self { 
    // Do something 
} 

Diese Antwort basiert auf @mattdipasquale 's Kommentar.

Wenn Sie ein komplizierteres Szenario haben, lesen Sie die anderen Antworten oben.

-2

Da UIAlertController aus UIViewController abgeleitet Sie nur die isBeingPresented können

if (alertController.isBeingPresented) { 
    // alert is showing 
} 
Verwandte Themen