2011-11-08 12 views
13

एसओ पर अन्य प्रश्नों में been reported है, आईओएस 5 बदलता है कि इस रिलीज नोट के अनुसार विभाजित दृश्य नियंत्रकों के लिए रोटेशन कॉलबैक कैसे भेजे जाते हैं। यह एक शिकार (मुझे लगता है कि) नहीं है के रूप में मैं यह कैसे iOS 5 में विभाजित दृश्य नियंत्रक उपयोग को समायोजित करने के साथ संबंधित इतने पर एक और सवाल परिवर्तन से निपटने के लिए नहीं मिल सकता है: iOS 5 मेंआईओएस 5 UISplitViewController रोटेशन कॉलबैक तोड़ता है, मैन्युअल रूप से कैसे आवेदक?

रोटेशन कॉलबैक नियंत्रकों को देखने के लिए लागू नहीं हैं कि पूर्ण स्क्रीन पर प्रस्तुत किए गए हैं। इसका अर्थ यह है कि यदि आपका कोड किसी अन्य व्यू कंट्रोलर पर व्यू कंट्रोलर प्रस्तुत करता है, और उसके बाद उपयोगकर्ता बाद में बर्खास्तगी पर डिवाइस को एक अलग अभिविन्यास पर घुमाता है, अंतर्निहित नियंत्रक (यानी नियंत्रक प्रस्तुत करना) कोई रोटेशन प्राप्त नहीं करेगा कॉलबैक। नोट हालांकि जब यह पुन: प्रदर्शित है, और interfaceOrientation संपत्ति से इस विधि पूछे और सही ढंग से नियंत्रक बाहर बिछाने के लिए इस्तेमाल किया जा सकता है कि पेश नियंत्रक एक viewWillLayoutSubviews कॉल आएगी।

मुझे अपने रूट स्प्लिट व्यू कंट्रोलर में पॉपओवर बटन को कॉन्फ़िगर करने में समस्या हो रही है (जिसे चित्र में होने पर पॉपओवर में बाएं फलक दृश्य दिखाना है)। यहाँ कैसे मेरे एप्लिकेशन स्टार्टअप अनुक्रम आईओएस 4.x में काम करने के लिए तो उपकरण को लैंडस्केप मोड में है इस्तेमाल किया है:

  1. [window addSubview:splitViewController.view]; [window makeKeyAndVisible]; साथ विंडो में स्थापित विभाजित दृश्य नियंत्रक। इसके परिणामस्वरूप splitViewController:willHideViewController:withBarButtonItem:forPopoverController: प्रतिनिधि को बुलाया जा रहा है (यानी एक परिदृश्य अनुकरण -> चित्र रोटेशन) भले ही डिवाइस पहले से ही लैंडस्केप मोड में है।

  2. वर्तमान एक फुलस्क्रीन मोडल (मेरी लोड हो रहा है स्क्रीन) जो पूरी तरह से विभाजित दृश्य के नीचे शामिल किया गया।

  3. समाप्त लोड हो रहा है और लोड हो रहा है स्क्रीन मॉडल को खारिज। चूंकि डिवाइस लैंडस्केप मोड में है, क्योंकि स्प्लिट व्यू कंट्रोलर प्रकट होता है, इसलिए यह splitViewController:willShowViewController:invalidatingBarButtonItem: को प्रतिनिधि (यानी एक पोर्ट्रेट -> लैंडस्केप रोटेशन सिमुलेट) पर कॉल करने के लिए कारण बनता है, जिससे बार बटन आइटम को अमान्य कर दिया जाता है, इसे दाएं तरफ से हटा दिया जाता है विभाजन के दृश्य, और हमें छोड़कर जहां हम बनना चाहते हैं। हुर्रे!

तो, समस्या यह है कि क्योंकि परिवर्तन यह है कि रिलीज नोट में बताया गया है, जो कुछ भी iOS 4.3 कि splitViewController:willShowViewController:invalidatingBarButtonItem: में परिणाम नहीं रह गया है आईओएस 5 में होता है मैं UISplitViewController उपवर्गीकरण तो मैं प्रदान कर सकता है की कोशिश की बुलाया जा रहा है में आंतरिक रूप से होता है की रिलीज नोट द्वारा सुझाए गए अनुसार viewWillLayoutSubviews का एक कस्टम कार्यान्वयन, लेकिन मुझे नहीं पता कि आईओएस 4 ट्रिगर्स की आंतरिक घटनाओं के वांछित अनुक्रम को पुन: उत्पन्न कैसे करें। मैंने यह कोशिश की:

- (void) viewWillLayoutSubviews 
{ 
    [super viewWillLayoutSubviews]; 

    UINavigationController *rightStack = [[self viewControllers] objectAtIndex:1]; 
    UIViewController *rightRoot = [[rightStack viewControllers] objectAtIndex:0]; 
    BOOL rightRootHasButton = ... // determine if bar button item for portrait mode is there 

    // iOS 4 never goes inside this 'if' branch 
    if (UIInterfaceOrientationIsLandscape([self interfaceOrientation]) && 
     rightRootHasButton) 
    { 
     // Manually invoke the delegate method to hide the popover bar button item 
     [self.delegate splitViewController:self 
        willShowViewController:[[self viewControllers] objectAtIndex:0] 
       invalidatingBarButtonItem:rightRoot.navigationItem.leftBarButtonItem]; 
    } 
} 

यह ज्यादातर काम करता है, लेकिन 100% नहीं। समस्या यह है कि प्रतिनिधि पद्धति का आह्वान करना वास्तव में बार बटन आइटम को अमान्य कर देता है, इसलिए पहली बार जब आप पोर्ट्रेट पर घुमाते हैं, तो सिस्टम सोचता है कि बार बटन आइटम अभी भी ठीक से स्थापित है और इसे पुनः स्थापित करने का प्रयास नहीं करता है। यह फिर से परिदृश्य में घूमने के बाद ही है और फिर पोर्ट्रेट पर वापस सिस्टम सही स्थिति में वापस आ गया है और वास्तव में पोर्ट्रॉइड बार बटन आइटम को पोर्ट्रेट मोड में इंस्टॉल करेगा।

this question के आधार पर, मैंने प्रतिनिधि पद्धति को फायर करने के बजाय मैन्युअल रूप से सभी रोटेशन कॉलबैक का आह्वान करने का भी प्रयास किया, उदाहरण के लिए:

// iOS 4 never goes inside this 'if' branch 
if (UIInterfaceOrientationIsLandscape([self interfaceOrientation]) && 
    rightRootHasButton) 
{ 
    [self willRotateToInterfaceOrientation:self.interfaceOrientation duration:0]; 
    [self willAnimateRotationToInterfaceOrientation:self.interfaceOrientation duration:0]; 
    [self didRotateFromInterfaceOrientation:self.interfaceOrientation]; 
} 

हालांकि यह सिर्फ एक अनंत लूप viewWillLayoutSubviews :(में वापस पैदा करने के लिए लगता है

किसी को भी पता है सही तरीका iOS4 शैली रोटेशन घटनाओं अनुकरण करने के लिए है कि से प्रकट होता है एक विभाजित दृश्य नियंत्रक के लिए क्या है एक पूर्ण-स्क्रीन मोडल के पीछे? या क्या आपको उनका अनुकरण नहीं करना चाहिए और क्या कोई अन्य सर्वोत्तम अभ्यास दृष्टिकोण है जो आईओएस 5 के लिए मानक बन गया है?

किसी भी मदद की वास्तव में सराहना की गई है क्योंकि यह समस्या हमें हमारे आईओएस 5 जमा करने से रोक रही है ऐप स्टोर में बगफिक्स रिलीज।

उत्तर

11

मुझे इस स्थिति को संभालने का सही तरीका नहीं पता है। हालांकि, निम्नलिखित आईओएस 5.

  1. में मेरे लिए काम करने splitViewController:willHideViewController:withBarButtonItem:forPopoverController: में लगता है, self.barButtonItem की तरह कुछ में barButtonItem के लिए एक संदर्भ की दुकान। बटन को एक अलग विधि में दिखाने के लिए कोड को ले जाएं, ShowRootPopoverButtonItem कहें।

  2. splitViewController:willShowViewController:invalidatingBarButtonItem: में, self.barButtonItem संदर्भ बाहर निकालें। बटन को एक अलग विधि में दिखाने के लिए कोड को ले जाएं, InvalidateRootPopoverButtonItem कहें।

  3. viewWillLayoutSubviews में, मैन्युअल रूप दिखाना या छिपाना बटन, इंटरफ़ेस उन्मुखीकरण

यहाँ viewWillLayoutSubviews की मेरी कार्यान्वयन के आधार पर। ध्यान दें कि self.interfaceOrientation पर कॉल करना हमेशा पोर्ट्रेट लौटा, इसलिए statusBarOrientation का मेरा उपयोग।

- (void)viewWillLayoutSubviews 
{ 
    if (UIInterfaceOrientationIsPortrait(
     [UIApplication sharedApplication].statusBarOrientation)) 
    { 
     [self ShowRootPopoverButtonItem:self.barButtonItem]; 
    } 
    else 
    { 
     [self InvalidateRootPopoverButtonItem:self.barButtonItem]; 
    } 
} 
+1

हे नोहा - समाधान के लिए धन्यवाद - यह मेरे लिए भी काम कर रहा है। यह थोड़ा दुर्भाग्यपूर्ण है क्योंकि ViewWillLayoutSubviews को रोटेशन इवेंट्स की तुलना में अधिक बार कहा जाता है, इसलिए वहां मौजूद सभी बटन छिपाने/तर्क दिखाने का मतलब है कि यह बहुत अधिक बार चला जाता है, लेकिन ऐसा लगता है कि यह आईओएस 5-आईश तरीका है यह सामान अब – glenc