चेतावनी: अलग किए गए दृश्य नियंत्रकों पर दृश्य नियंत्रक नियंत्रित किया जाता है


180

अपने ऐप में, मैं एक नेविगेशन नियंत्रक का उपयोग कर रहा हूं। बाद में कुछ दृश्य में मैं presentViewControllerज़ूम वाली छवि दिखाने के लिए उपयोग कर रहा हूं । इसके अलावा मैं एक स्टोरीबोर्ड या नीब का उपयोग नहीं कर रहा हूं।

मुझे यह त्रुटि आईओएस 7 में ही मिल रही है। यह iOS 6 और पहले के संस्करण में ठीक काम करता है:

अलग किए गए दृश्य नियंत्रकों पर दृश्य नियंत्रक प्रस्तुत करना हतोत्साहित करता है


मैंने अभी तक पता नहीं लगाया। लेकिन मेरे ऐप में मैं window.rootviewcontroller को कोई भी व्यूकंट्रोलर असाइन नहीं कर रहा हूं। मैं विंडो में दृश्य जोड़ रहा हूं। हो सकता है कि यही मेरे लिए कारण है। लेकिन यकीन नहीं ...
गगन जोशी

@ गगनजोशी आपके द्वारा ऊपर बताए गए कारण का कारण नहीं हो सकता है। यहां तक ​​कि मैं भी इसी मुद्दे का सामना कर रहा हूं। और हमारी परियोजना में मैं window.rootviewcontroller के लिए एक दृश्य नियंत्रक प्रदान कर रहा हूं।
राजेश

1
मुझे लगता है कि अन्य टिप्पणियां रूटव्यूकंट्रोलर और विंडो कनेक्शन के बारे में कुछ से संबंधित हैं। मुझे यह समझ में नहीं आया है, लेकिन मैं कंट्रोलर को सीधे रूटव्यूकंट्रोलर पर नेविगेशन कंट्रोलर या उसके किसी एक बच्चे के बजाय कंट्रोलर को प्रस्तुत करके इस मुद्दे पर काम करने में सक्षम हूं।
रिच वाटर्स

जवाबों:


207

एक पुश नेविगेशन में चेतावनी प्राप्त करने से बचने के लिए, आप सीधे उपयोग कर सकते हैं:

[self.view.window.rootViewController presentViewController:viewController animated:YES completion:nil];

और फिर अपने मोडल व्यू कंट्रोलर में, जब सब कुछ खत्म हो जाता है, तो आप कॉल कर सकते हैं:

[self dismissViewControllerAnimated:YES completion:nil];


मैं इस लाइन कोड के साथ छवि पिकर प्रस्तुत कर रहा हूं "[self.view.window.rootViewController presentViewController: viewController एनिमेटेड: YES पूरा: nil];" लेकिन इस पंक्ति के साथ "" खुद को खारिज मत करो। बर्खास्तगी के लिए कोई वैकल्पिक विकल्प
kb920

@keyurbhalodiya आपको इसे काम करने के लिए modalView से बर्खास्तगी देखने की विधि को कॉल करने की आवश्यकता है। इसलिए यदि आपने [viewA.window.rootViewController presentViewController: viewB] के साथ एक viewA से एक दृश्य नाम प्रदर्शित किया है, तो viewB में आपको उदाहरण के लिए एक बटन जोड़ने की जरूरत है, जो एक कस्टम एक्शन कॉलिंग से संबंधित है [स्वयं को खारिज करने वाला ViewControllerAnimated]। क्या यह स्पष्ट है?
cdescours

11
IOS 8 में व्यूकंट्रोलर पेश नहीं करना।
राजेश मौर्य


31
self.navigationControllerमेरे लिए यह प्रयोग किया।
ब्रैंडन ज़ाचरी

62

इस चेतावनी का कारण यह है कि मैं एक छोटे दृश्य पर एक दृश्य नियंत्रक पेश कर रहा था जो पूर्ण आकार का दृश्य नहीं है। नीचे दिए गए मेरे प्रोजेक्ट की छवि है। जहां ऊपर चार विकल्प पर क्लिक करें। उपयोगकर्ता विभिन्न चाइल्डव्यूकंट्रोलर के दृश्य पर नेविगेट करता है। (यह tabViewcontroll की तरह काम करता है) लेकिन चाइल्डव्यूकंट्रोलर में छोटे आकार का दृश्य होता है। इसलिए यदि हम चाइल्डव्यूकंट्रोलर से एक दृश्य प्रस्तुत करते हैं तो यह चेतावनी देता है।

मास्टर विस्तार से देखें

और इससे बचने के लिए, आप चाइल्डव्यूकंट्रोलर के माता-पिता पर एक दृश्य प्रस्तुत कर सकते हैं

  [self.parentViewController presentViewController:viewController animated:YES completion:nil];

1
[self.view.window.rootViewController.navigationController pushViewController: Your_VIEW_CONTROLER एनिमेटेड: YES];
Fede Cugliandolo

1
"एक छोटे दृश्य पर एक दृश्य नियंत्रक प्रस्तुत कर रहा था जो पूर्ण आकार का दृश्य नहीं है।" ... बिल्कुल सही। अच्छा काम।
फेटी

61

इसके लिए प्रतीक्षा करें viewDidAppear():

यह त्रुटि तब भी उत्पन्न हो सकती है यदि आप दृश्य नियंत्रक को प्रस्तुत करने का प्रयास कर रहे हैं, इससे पहले कि वह वास्तव में दिखाई दे, उदाहरण के लिए viewWillAppear()या पहले दृश्य प्रस्तुत करता है । इसके बाद viewDidAppear()या इसके अंदर एक और दृश्य प्रस्तुत करने का प्रयास करें ।


9
दूसरे शब्दों में viewDidLoad(), लोगों में कोई भी दृश्य नियंत्रक प्रस्तुत नहीं करते हैं ! मैंने यह गलती कई बार की है ...
टी ब्लैंक

धन्यवाद इससे मदद मिली। मेरे पास देखने के लिए कोड है जहां यह अंत में एक संवाद प्रदर्शित करने की कोशिश करता है।
ArdenDev

यूनिट / एकीकरण परीक्षण चलाने के दौरान मुझे यह त्रुटि हो रही है जहां मैं एनिमेशन के साथ परीक्षण नहीं करता हूं।
mixtly87

21

मेरे मामले में, मैं एक sampleViewControllerदृश्य को एक सबव्यू के रूप में जोड़ा गया हूं , फिर एक पॉपओवर को यहां से देखने की कोशिश करता है sampleViewController( उदाहरण के selfबजाय यहां UIViewController):

[self.view addSubview:sampleViewController.view];

सही तरीका नीचे होना चाहिए:

// make sure the vc has been added as a child view controller as well
[self addChildViewController:sampleViewController];
[self.view addSubview:sampleViewController.view];
[sampleViewController didMoveToParentViewController:self];

Btw, यह उस मामले के लिए भी काम करता है जो एक पॉपओवर एक टेबलव्यू सेल पेश करता है, आपको बस यह सुनिश्चित करने की आवश्यकता है कि टेबलव्यू कंट्रोलर को चाइल्ड व्यू कंट्रोलर के रूप में भी जोड़ा गया है।


इसके अलावा कॉल didMoveToParentViewController। याचिकाएं देखें और निकालें ChildViewController: gist.github.com/tomohisa/2897676
Jakehao

@jianzong मुझे याद है कि अंतिम चरण करने की कोई आवश्यकता नहीं है। किसी भी तरह, मुझे इसे जोड़ने दें, सुझाव के लिए thx। :)
काजुल

हां यह अंतिम चरण के बिना काम करेगा। मुझे लगता है कि इसका उद्देश्य पेरेंटव्यूकंट्रोलर को सूचित करना है ताकि यह कुछ करने के लिए कुछ तरीकों को बुलाएगा। :)
जेकाहो

2
यह मेरे लिए काम करता है, एक अन्य नियंत्रक में एक नियंत्रक दृश्य का उपयोग करके im - (कंटेनर दृश्य प्रोग्रामिक रूप से), मैंने नहीं जोड़ा [self addChildViewController:sampleViewController];, अब मैंने इसे जोड़ा, धन्यवाद
ajnkmr

16

मुझे लगता है कि समस्या यह है कि आपके पास एक उचित दृश्य नियंत्रक पदानुक्रम नहीं है। ऐप के रूटव्यू कंट्रोलर को सेट करें और फिर उन पर नए व्यू कंट्रोलर्स को पुश या प्रेजेंट करके नए व्यूज दिखाएं। प्रत्येक दृश्य नियंत्रक को उनके विचार प्रबंधित करने दें। केवल कंटेनर व्यू कंट्रोलर, जैसे टैब्बरव्यूकंट्रोलर, को कभी भी अन्य व्यू कंट्रोलर्स व्यू को अपने विचार में जोड़ना चाहिए। व्यू कंट्रोलर का उपयोग करने के तरीके के बारे में अधिक जानने के लिए व्यू कंट्रोलर प्रोग्रामिंग गाइड पढ़ें। https://developer.apple.com/library/content/featuredarticles/ViewControllerPGforiPhoneOS/


14

स्विफ्ट 3

किसी को भी इस पर ठोकर खाने के लिए, यहाँ तेजी से जवाब है।

self.parent?.present(viewController, animated: true, completion: nil)

9

मेरी लगभग यही समस्या है। कारण यह था कि मैंने दूसरे पर "कुछ" नियंत्रक पेश करने की कोशिश की और एनीमेशन पूरा होने के बाद मैं प्रस्तुत नियंत्रक को रूट के रूप में स्थापित कर रहा था। इस ऑपरेशन के बाद प्रस्तुत करने वाले अन्य सभी नियंत्रक मुझे चेतावनी देते हैं: " अलग किए गए दृश्य नियंत्रकों पर दृश्य नियंत्रक प्रस्तुत करना हतोत्साहित करता है "। और मैं इस चेतावनी को शुरू में बिना किसी प्रस्तुति के रूट के रूप में कुछ सेटिंग्स "कुछ" कंट्रोलर को हल करता हूं।

हटा दिया:

[[self rootController] presentViewController:controller animated:YES completion:^{

       [self window].rootViewController = controller;

       [[self window] makeKeyAndVisible];}];

बस किसी भी प्रस्तुति के बिना जड़ के रूप में:

 [[self window] setRootViewController:controller];

1
यह वास्तव में मेरी समस्या थी। एक UIModalTransitionStyleCrossDissolve के साथ इसे प्रस्तुत करने की कोशिश कर रहा था और फिर इसे rootViewController बना दिया। उसके बाद, दिए गए चेतावनी संदेश के साथ अन्य सभी प्रस्तुतियाँ विफल हो रही थीं। बस एनीमेशन के बिना rootViewcontroller के रूप में इसे स्थापित करने की कोशिश की। धन्यवाद!
बर्नार्डो ओलिवेरा

7

इसका एक समाधान यह है कि यदि आपके पास चाइल्डव्यूकंट्रोलर है, तो आप बस उसके द्वारा दिए गए अभिभावक पर मौजूद हैं

[self.parentViewController presentViewController:viewController animated:YES completion:nil];

और खारिज करने के लिए उसी बर्खास्तगी नियंत्रक का उपयोग करें।

[self dismissViewControllerAnimated:YES completion:nil];

यह मेरे लिए सही समाधान काम करता है।



5

इस कोड को आज़माएं

UINavigationController *navigationController = [[UINavigationController alloc] initWithRootViewController:<your ViewController object>];

[self.view.window.rootViewController presentViewController:navigationController animated:YES completion:nil];

4

TabBarControllerयदि यह एक TabBarControllerआधारित ऐप है, तो इसे प्रस्तुत करने का प्रयास करें ।

[self.tabBarController presentViewController:viewController animated:YES completion:nil];

कारण selfका बच्चा हो सकता है TabBarControllerऔर आप एक से प्रस्तुत करने की कोशिश कर रहे हैं ChildViewController


4

हां, मुझे अलर्ट कंट्रोलर को प्रदर्शित करते समय उसी चेतावनी संदेश का भी सामना करना पड़ा जो दूसरे दृश्य में था। बाद में मैंने पैरेंट व्यू कंट्रोलर से अलर्ट कंट्रोलर को नीचे प्रस्तुत करके इसे टाल दिया:

[self.parentViewController presentViewController:alertController animated:YES completion:nil];

3

आपको व्यू कंट्रोलर जोड़ने की जरूरत है जो नए कंट्रोलर को पेरेंट व्यू कंट्रोलर के बच्चे के रूप में प्रस्तुत करेगा।

मान लें कि आपके पास आपका मेन व्यू कंट्रोलर है, तो आप एक नया कंट्रोलर जोड़ते हैं, जिसे कंट्रोलर कहा जाता है, और फिर आप कंट्रोलर से कंट्रोलर नामक एक नया कंट्रोलर पेश करना चाहते हैं।

आपको कुछ इस तरह लिखना होगा:

[self addChildViewController:controllerA]; //self is yourMainViewController
[self.view addsubView:controllerA.view]; 

और नियंत्रक के भीतर आप चेतावनियों के बिना नए नियंत्रक को प्रस्तुत कर सकते हैं

[self presentViewController:controllerB animated:YES completion:nil]; //self is controllerA

3

स्विफ्ट 4.1 और एक्सकोड 9.4.1 में

उपाय है

DispatchQueue.main.async(execute: {
    self.present(alert, animated: true)
})

अगर मैं इस तरह लिख रहा हूँ मैं एक ही त्रुटि हो रही है

let alert = UIAlertController(title: "title", message: "message", preferredStyle: .alert)
let defaultAction = UIAlertAction(title: "OK", style: .default, handler: { action in
    })
alert.addAction(defaultAction)

present(alert, animated: true, completion: nil) 

मुझे वही त्रुटि हो रही है

Presenting view controllers on detached view controllers is discouraged <MyAppName.ViewController: 0x7fa95560Z070>.

पूरा समाधान है

let alert = UIAlertController(title: "title", message: "message", preferredStyle: .alert)
let defaultAction = UIAlertAction(title: "OK", style: .default, handler: { action in
     })
alert.addAction(defaultAction)
//Made Changes here    
DispatchQueue.main.async(execute: {
    self.present(alert, animated: true)
})

DispatchQueue के माध्यम से इसे चलाना मेरे लिए इस तरह काम करता है। मैं एक मोडल व्यू कंट्रोलर के लिए एक परफॉर्म कर रहा हूं, जिसे व्यूडीडलड से मेरे पहले व्यू कंट्रोलर (नए यूजर्स को ओरिएंट करने के लिए पहला लॉन्च इंट्रो स्क्रीन) से बुलाया गया है। यह ठीक लोड हो रहा था, लेकिन चेतावनी पैदा कर रहा था। DispatchQueue async कॉल में PerformSegue कॉल को रैप करने से चेतावनी समाप्त हो जाती है। धन्यवाद!
ग्रांट न्यूफेल्ड

1

सुनिश्चित करें कि आपके पास शुरू करने के लिए एक रूट व्यू कंट्रोलर है। आप इसमें सेट कर सकते हैं didFinishLaunchingWithOptions

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {    
    [window setRootViewController:viewController];
}

1

इस चेतावनी के लिए बहुत सारे कारण। मेरा इसलिए है क्योंकि मेरे पास एक ViewController से दूसरे से जुड़ा हुआ है जिसे मामूली रूप से प्रस्तुत किया जाएगा। लेकिन, मैं जो ViewController पेश कर रहा हूं वह गतिशील रूप से एक PageViewController द्वारा उत्पन्न किया जा रहा है। यही कारण है कि यह स्टोरीबोर्ड में अलग है। मेरा ऐप इसकी वजह से क्रैश नहीं हो रहा है; लेकिन मैं चेतावनी को चुप करना चाहूंगा।


1

मैं इस थ्रेड पर पहुंचा, जहां मेरे पास एक कस्टम नेविगेशन बार है और मैं इसके माध्यम से एक AlertViewController बुला रहा था।

मुझे इसे एक बच्चे के रूप में अपने मुख्य दृश्य नियंत्रक में जोड़ना था। तब मैं इसे बिना किसी चेतावनी के प्रस्तुत कर सकता था।

आपको अपना जोड़ना चाहिए Zoomed Image View Controller मुख्य ViewController के बच्चे के रूप में ।

(उदाहरण के लिए)

[self addChildViewController:ZoomedImageViewController];

तब आप अपने ZoomedImageViewController को कॉल कर पाएंगे

[self presentViewController:ZoomedImageViewController];

1

बहुत से उत्तर सही हैं।

  • अपने presentingViewController की जाँच करें parentViewController है या नहीं।
  • यदि नहीं, तो इसे कहीं और जोड़ दें
  • इसके अलावा, यह देखें कि पेरेंटव्यू कंट्रोलर के पास पेरेंटव्यूकंट्रोलर है, जब तक कि हर व्यू कॉन्ट्रोलर के पास पैरेंट नहीं है

यह समस्या मुझे तब हुई जब मेरे सहकर्मी ने एवीईवीकंट्रोलर को बीवीईवाईकंट्रोलर में जोड़ा। किसी तरह, वह सिर्फ AViewController का दृश्य BViewController के दृश्य में जोड़ देता है।

BViewController.addChild (aViewController) द्वारा निर्धारित


1
धन्यवाद! मेरे हीरो में AddChild जोड़ने से। पूरा किया गया ब्लॉक पूरी तरह से मेरी समस्या को हल कर देता है।
लैंडब्लाक

0

यह निर्भर करता है कि आप अपने अलर्ट को दिखाना चाहते हैं या यूआईईवीसीओंट्रोलर के कहीं भी समान है।

आप इस कोड उदाहरण का उपयोग कर सकते हैं:

UIAlertController* alert = [UIAlertController alertControllerWithTitle:@"Alert" message:@"Example" preferredStyle:UIAlertControllerStyleAlert];

UIAlertAction *cancelAction = [UIAlertAction actionWithTitle:@"Cancel" style:UIAlertActionStyleDefault handler:nil];

[alert addAction:cancelAction];


[[[[[UIApplication sharedApplication] delegate] window] rootViewController] presentViewController:alert animated:true completion:nil];

आपके कोड के साथ, यह काम नहीं करता है और यह लॉग देता हैAttempt to present <UIAlertController: 0x7fc01a1eb600> on <ViewController: 0x7fc019821e00> whose view is not in the window hierarchy!
नावेद अब्बास
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.