2011-12-21 20 views
10

Trong ShareKit, mã cần xác định nơi rootViewController là để nó có thể hiển thị một chế độ xem phương thức. Vì một số lý do, mã không thành công trong iOS 5:Tìm rootViewController trong iOS

// Try to find the root view controller programmically 

    // Find the top window (that is not an alert view or other window) 
    UIWindow *topWindow = [[UIApplication sharedApplication] keyWindow]; 
    if (topWindow.windowLevel != UIWindowLevelNormal) 
    { 
     NSArray *windows = [[UIApplication sharedApplication] windows]; 
     for(topWindow in windows) 
     { 
      if (topWindow.windowLevel == UIWindowLevelNormal) 
       break; 
     } 
    } 

    UIView *rootView = [[topWindow subviews] objectAtIndex:0]; 
    id nextResponder = [rootView nextResponder]; 

    if ([nextResponder isKindOfClass:[UIViewController class]]) 
     self.rootViewController = nextResponder; 

    else 
     NSAssert(NO, @"ShareKit: Could not find a root view controller. You can assign one manually by calling [[SHK currentHelper] setRootViewController:YOURROOTVIEWCONTROLLER]."); 

Đây là sự khẳng định.

Điều gì sai khi chỉ sử dụng mã sau đây?

rootViewController = [[[UIApplication sharedApplication] keyWindow] rootViewController]; 

Điều này có vẻ hoạt động tốt. Nó sẽ thất bại trong một số điều kiện?

Trả lời

27

Tôi không chắc chắn liệu bạn có thể dựa vào window.rootViewController b/c bạn không phải đặt nó hay không. Bạn chỉ có thể thêm một subview vào cửa sổ. Sau đây dường như làm việc tốt:

id rootVC = [[[[[UIApplication sharedApplication] keyWindow] subviews] objectAtIndex:0] nextResponder]; 
+0

Cảm ơn. Các rootViewController được thiết lập, trong trường hợp này. Nó không rõ ràng với tôi rằng chỉ cần thiết lập rằng tự động làm cho nó rootViewController cho mục đích của mã ShareKit này. Đây là một ứng dụng toàn cầu, và trong mã iPhone, rootViewController là một UITabBarController được phân lớp. Tôi nên thêm rằng tôi cũng có một UIAlertView và UIView được thêm dưới dạng subviews vào cửa sổ ứng dụng. (Tôi có thể hiển thị một hoặc cả hai người trong số họ bất kể xem từ tabbarcontroller được hiển thị.) Mã của bạn trả về UIAlertView là objectAtIndex: 0. Tôi chỉ có thể lặp lại thông qua phần còn lại, tôi đoán vậy. – Jim

+1

nếu bạn đang đặt nó trong ứng dụng của mình thì chắc chắn nó sẽ hoạt động. Tôi không biết nếu bạn đang tạo một thư viện cho người khác sử dụng nơi bạn không thể dựa vào 'window.rootViewController' đang được thiết lập. – XJones

+0

@XJones, nếu window.rootViewController không được đặt? có cách nào khác đáng tin cậy để có được bộ điều khiển xem hiện tại không? – Zennichimaro

1

cách Swift để làm điều đó, bạn có thể gọi đây là từ bất cứ đâu:

/// EZSwiftExtensions - Gives you the VC on top so you can easily push your popups 
public var topMostVC: UIViewController? { 
    var presentedVC = UIApplication.sharedApplication().keyWindow?.rootViewController 
    while let pVC = presentedVC?.presentedViewController { 
     presentedVC = pVC 
    } 

    if presentedVC == nil { 
     print("EZSwiftExtensions Error: You don't have any views set. You may be calling them in viewDidLoad. Try viewDidAppear instead.") 
    } 
    return presentedVC 
} 

của nó bao gồm như là một chức năng tiêu chuẩn trong:

https://github.com/goktugyil/EZSwiftExtensions

Các vấn đề liên quan