Oczekuje się, że aplikacje będą miały kontroler widoku głównego pod koniec uruchamiania aplikacji

383

W mojej konsoli pojawia się następujący błąd:

Oczekuje się, że aplikacje będą miały kontroler widoku głównego pod koniec uruchamiania aplikacji

Poniżej moja application:didFinishLaunchWithOptionsmetoda:

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {

    // Set Background Color/Pattern
    self.window.backgroundColor = [UIColor blackColor];
    self.tabBarController.tabBar.backgroundColor = [UIColor clearColor];
    //self.window.backgroundColor = [UIColor colorWithPatternImage:[UIImage imageNamed:@"testbg.png"]];

    // Set StatusBar Color
    [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleBlackTranslucent];

    // Add the tab bar controller's current view as a subview of the window
    self.window.rootViewController = self.tabBarController;
    [self.window makeKeyAndVisible];
    return YES;
}

W interfejsie Konstruktora UITabBarControllerdelegat jest podłączony do delegata aplikacji.

Czy ktoś wie, jak rozwiązać ten problem?

ArtSabintsev
źródło
5
Wykonaj NSLog self.tabBarController bezpośrednio przed wykonaniem zadania. Komunikat jest wyzwalany tylko wtedy, gdy kontroler jest zerowy. Jeśli jest zero i upewniłeś się, że połączenia są prawidłowe, spróbuj utworzyć instancję kontrolera w kodzie.
FeifanZ
spróbuj skomentować inicjalizację okna .. sprawdź tę odpowiedź stackoverflow.com/a/33958144/1293445
mohammad alabid

Odpowiedzi:

188

Miałem ten sam problem. Sprawdź swoją główną. M. Ostatni argument powinien być ustawiony na nazwę klasy, która implementuje protokół UIApplicationDelegate.

retVal = UIApplicationMain(argc, argv, nil, @"AppDelegate");
sho
źródło
49
Inną opcją jest upewnienie się, że klasa delegowana aplikacji jest zaimportowana w trybie głównym i używana NSStringFromClass. W ten sposób Xcode tworzy teraz plik main.m. Na przykład: #import "AppDelegate.ha następnieint retVal = UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class]));
Sho
10
upewnij się, że self.windowjest zainicjowany jakself.window = [[[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]] autorelease];
Raptor,
1
Wypróbowałem powyższe opcje, nie działało dla mnie. I nie używam Storyboard.
jowie
3
Dla mnie nie miało to wpływu, ten sam komunikat „Oczekiwano aplikacji ...” po wprowadzeniu zmiany. Rozwiązaniem była odpowiedź OrdoDei (patrz wyżej lub poniżej), która działała idealnie.
Andrew
1
Jeśli widzisz biały widok w Symulatorze, ale spodziewasz się zobaczyć układ z scenorysu, upewnij się, że pozbyłeś się kodu w swojej funkcji root delegowania „aplikacja didFinishLaunchingWithOptions ...”, która jest wskazana w main.m i ma tylko „return TAK;" w tym.
Olivier de Jonge
435

Zamień w AppDelegate

 [window addSubview:[someController view]];

do

  [self.window setRootViewController:someController];
OrdoDei
źródło
Pozbyło się to dla mnie wiadomości. Nadal nie wyświetla się kolejne okno, ale może to być inny problem. Dzięki.
Jazzmine
3
Jeśli korzystasz z UINavigationController, powinieneś najpierw [[UINavigationController] initWithRootViewController: tableViewController], a następnie użyć kodu powyżej [self.window setRootViewController: self.navigationController], aby ustawić kontroler widoku głównego okna
emdog4
Cocos2d ma komentarz: „// AddSubView nie działa na iOS6”. To naprawiło to, ponieważ używam iOS 6.
Almo
1
addSubviewLinia była częścią szablonu projektu na wczesnej wersji Xcode / iOS SDK. Jeśli aplikacja ma długą historię, możesz ją mieć, nawet jeśli jej nie napisałeś.
Seva Alekseyev
cześć, dostaję ten błąd: - *** Błąd asercji w - [UIApplication _runWithMainScene: przejścieContext: zakończenie:], /BuildRoot/Library/Caches/com.apple.xbs/Sources/UIKit_Sim/UIKit-3505.16/UIApplication.m: 3294 jak rozwiązać ten problem
Akash Raghani
70

Miałem ten sam błąd podczas próby zmiany pierwszego kontrolera widoku, który został załadowany

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions

Na początku tak naprawdę nie wiedziałem, skąd dokładnie pochodzi błąd, więc zawęziłem go i dowiedziałem się, co poszło nie tak. Okazuje się, że próbowałem zmienić sposób wyświetlania widoku, zanim faktycznie pojawił się na ekranie. Rozwiązaniem było więc przeniesienie tego kodu do kontrolera widoków, który sprawiał mi problemy

- (void)viewDidLoad

do

- (void)viewDidAppear:(BOOL)animated

i błąd przestał się pojawiać. Mój problem był konkretnie spowodowany stworzeniem UIAlertViewprogramu.

W twoim przypadku sugeruję sprawdzenie kodu w aktywnym kontrolerze widoku tabBarController (ponieważ jest to prawdopodobnie problem w tym kontrolerze widoku). Jeśli to nie zadziała, spróbuj ustawić ustawienia początkowe w pliku stalówki zamiast w kodzie - lub jeśli chcesz to zrobić w kodzie, spróbuj przenieść kod do odpowiedniej metody aktywnej kontrolera widoku tabBarController.

Powodzenia!

Warkst
źródło
1
Warkst, dzięki za odpowiedź. W moim przypadku nie mogę przenieść kodu z viewDidLoad:(bez dodania flagi) i nie powinienem tego robić. Niezależnie od tego, dziękuję za sugestię!
ArtSabintsev,
2
Znalazłem to dzisiaj i cieszę się, że tak zrobiłem - ten sam problem - pokazywał uialertowi uruchomienie w viewDidLoad. Zmieniono na viewDidAppear i działa dobrze. Nie jestem pewien, co lepsze Apple osiąga, zmieniając to w iOS5.
GuybrushThreepwood
Dzięki za sugestię, że spowodował to widok alertu, ten sam problem również mi się przydarzył.
Chris
1
Czy możesz nam powiedzieć, jaki kod musiałeś usunąć, aby go rozwiązać? Używam mojego viewDidLoaddo wielu rzeczy, konfiguruję wszystkie rzeczy po raz pierwszy, takie jak dodawanie danych do UITableView. Nie mogę tego przenieść, viewDidAppear:ponieważ chcę, żeby wystrzelił tylko raz.
jowie
1
Problemem nie była zła funkcja. Problem polegał na tym, że zapomniałeś wywołać [super viewDidLoad] w swojej funkcji viewDidLoad, skutecznie zabijając obciążenie stalówki. To samo zdarzyło mi się więcej niż raz.
borrrden
47

Dostałem to, kiedy zaczynałem od szablonu „Pusta aplikacja”, a następnie ręcznie dodawałem XIB. Rozwiązałem go, ustawiając główną nazwę stalówki zgodnie z sugestią Sunny. Brakującym krokiem w tym scenariuszu jest usunięcie

self.window = [[[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]] autorelease];

od

application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions

Ponieważ spowoduje to zastąpienie wystąpienia okna utworzonego w pliku Xib. Zakłada się, że utworzyłeś ViewController i podłączyłeś go wraz z oknem i Delegatem aplikacji również w pliku XIB.

jlujan
źródło
To też mnie naprawiło. Korzystałem z aplikacji Tabbed z Storyboard, do której próbowałem dodać CoreData i napotkałem ten problem.
gitaarik
lol, jeśli to dodam, otrzymuję dwa ostrzeżenia, że ​​okna aplikacji powinny mieć kontroler widoku root !!
George Asda,
46

To mi się przydarzyło. Rozwiązany przez edycję pliku .plist. Podaj podstawową nazwę pliku głównej końcówki. (Powinien to być MainWindow.xib). Mam nadzieję, że to pomoże.

wprowadź opis zdjęcia tutaj

Słonecznie
źródło
2
To zadziałało dla mnie! Działa to, gdy utworzysz pusty projekt w Xcode 4.2, w którym nie będzie żadnego MainWindow i w ten sposób musimy go podłączyć.
jeevangs
Problem pojawił się dla nas, gdy przypadkowo usunęliśmy wiersz „Podstawowa nazwa pliku głównej końcówki” z pliku „Info.plist”. Wstawienie tej linii ponownie rozwiązało problem.
rtovars
Możesz to również ustawić we właściwościach projektu. Wybierz projekt, swój cel, możesz go edytować w Podsumowanie -> Informacje o wdrożeniu iPhone / iPad.
doekman
był to dla mnie problem, prowadzący do wielu problemów związanych z wywoływaniem viewDidLoad i viewWillAppear dwukrotnie w rootViewController. W moim przypadku usunięcie tego było rozwiązaniem
dlaczego
27

Niedawno napotkałem ten sam problem podczas budowania projektu z ios5 sdk. Początkowo budował się i działał poprawnie, ale potem pojawił się błąd.
W moim przypadku rozwiązanie było dość proste.
Brakowało tego, że jakoś właściwość Interfejs główny na karcie podsumowania mojego celu aplikacji została usunięta. Więc musiałem to ustawić ponownie.


Jeśli nie o to chodzi, a tabBarController jest nadal zerowy, zawsze możesz programowo utworzyć kontroler okien i root. Jako rezerwowy dodałem następujący kod do mojego projektu

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{ 
    if (!window && !navigationController) {
        NSLog(@"Window and navigation controller not loaded from nib. Will be created programatically.");
        self.window = [[[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]] autorelease];
        UIViewController *viewController1, *viewController2;
        viewController1 = [[[FirstViewController alloc] initWithNibName:@"FirstViewController_iPhone" bundle:nil] autorelease];
        viewController2 = [[[SecondViewController alloc] initWithNibName:@"SecondViewController_iPhone" bundle:nil] autorelease];

        self.tabBarController = [[[UITabBarController alloc] init] autorelease];
        self.tabBarController.viewControllers = [NSArray arrayWithObjects:viewController1, viewController2, nil];
        self.window.rootViewController = self.tabBarController;

    }
    else {
        [window addSubview:[tabBarController view]];
    }
    [self.window makeKeyAndVisible];
    return YES;
}

Będzie to działać tylko wtedy, gdy zaimplementowane zostanie również rozwiązanie sho.

denicija
źródło
24

Uaktualniłem do iOS9 i zacząłem uzyskiwać ten błąd znikąd. Byłem w stanie to naprawić, ale dodając poniższy kod do- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions

NSArray *windows = [[UIApplication sharedApplication] windows];
for(UIWindow *window in windows) {
    if(window.rootViewController == nil){
        UIViewController* vc = [[UIViewController alloc]initWithNibName:nil bundle:nil];
        window.rootViewController = vc;
    }
}
Mike Flynn
źródło
Ciekawe, ile okien miała Twoja aplikacja i czy wszystkie miały kontroler widoku głównego. Dzięki
DrAL3X,
5
UWAGA : Ta odpowiedź jest obejściem i nie usuwa podstawowej przyczyny. Zobacz stackoverflow.com/a/33958144/1116061
lipka
Jesteś prawdziwym bohaterem!
user2161301
21

Żadna z powyższych sugestii nie rozwiązała mojego problemu. Moje było to:

Dodaj:

window.rootViewController = navigationController;

po:

[window addSubview:navigationController.view];

w mojej aplikacji

- (void)applicationDidFinishLaunching:(UIApplication *)application {
RyeMAC3
źródło
20
  • Wybierz „Okno” w pliku stalówki
  • W „Inspektorze atrybutów” Zaznacz „Widoczny przy uruchomieniu”

wizerunek![]

  • Dzieje się tak, gdy plik stalówki jest tworzony ręcznie.
  • Ta poprawka działa w zwykłym trybie stalówki - nie w trybie scenorysu
niedźwiedzia
źródło
Myślę, że można go znaleźć tylko w trybie scenorysu.
ArtSabintsev
Nie, ten projekt był zwykłym trybem stalówki. To jest zrzut ekranu z trybu Storyboard. „Visible at Launch” vs. „Is Initial View Controller”.
bearMountain
3
Jeśli plik stalówki okna zostanie utworzony ręcznie, a opcja „widoczny przy uruchomieniu” jest domyślnie odznaczona, wyświetli ten komunikat po uruchomieniu aplikacji, to naprawi mój problem!
ZYiOS,
OCH DZIĘKUJE!!! Wreszcie rozwiązanie tego irytującego ostrzeżenia. Nawet jeśli makeKeyAndVisiblego masz, to nie rozwiązuje problemu. TYLKO to rozwiązało dla mnie ostrzeżenie. DZIĘKUJĘ CI!
tacos_tacos_tacos
„Dzieje się tak w zwykłym trybie stalówki - nie w trybie scenorysu” Niezbyt prawdziwe. Jestem stoi ten sam problem z Storyboardrównież
thesummersign
19

jak dodać RootViewController dla iOS5

jeśli twoja aplikacja do tej pory nie korzystała z RootViewController, po prostu utwórz go;), naciskając Plik> Nowy> Nowy plik; wybierz UIViewController subclass nazwij go RootViewController , odznacz With XIB dla interfejsu użytkownika (zakładając, że już go masz) i umieść ten kod w AppDelegate :: didFinishLaunchingWithOptions

rootViewController = [[RootViewController alloc] init];
window.rootViewController = rootViewController;

na pewno - musisz zaimportować plik RootViewController.h i utworzyć zmienną

tutaj jest fajny artykuł o RootViewController i AppDelegate,

rem
źródło
Link do artykułu cupofcocoa.com nie działa - masz pomysł, jeśli gdzieś jest kopia?
Ríomhaire
1
przeniesiono to na binpress.com, zaktualizowano link w odpowiedzi
rem
To świetny link. Dobra lektura i wyjaśnia, co się dzieje. Właśnie napotkałem ten problem, używając starej książki (ponieważ chcę najpierw nauczyć się Celu C), ale pisząc kod na najnowszym XCode 7, który nie ma starszych szablonów.
ibaralf
11

Miałem również ten błąd, ale w odróżnieniu od żadnej z wcześniej wymienionych odpowiedzi mój, ponieważ odkomentowałem metodę „loadView” w moim nowo wygenerowanym kontrolerze (xcode 4.2, ios5).

 //Implement loadView to create a view hierarchy programmatically, without using a nib.
- (void)loadView  
{
}

Powiedział mi nawet, że metoda służy do programowego tworzenia widoku, ale przeoczyłem go, ponieważ wyglądał tak podobnie jak inne metody, takie jak viewDidLoad, których normalnie używam, ale go nie złapałem.

Aby rozwiązać, po prostu usuń tę metodę, jeśli nie tworzysz programowo hierarchii widoków znanej również za pomocą stalówki lub scenorysu.

trcarden
źródło
Mogę potwierdzić, że może to powodować problem. Miałem tę samą sytuację, postępując zgodnie z samouczkiem na temat TableView, gdzie tworzą zestaw delegatów w loadView. Po przeniesieniu tego kodu do viewDidLoad i usunięciu loadView wszystko zaczęło działać w razie potrzeby.
Eugen,
Nadal możesz korzystać z widoku ładowania, ale dodać [super loadView]; na początku.
Hermann Klecker,
1
Hmm ... dokumentacja loadView wyraźnie stwierdza, że ​​nie powinieneś wywoływać metody super.
Joshua Sullivan
Przesłoniłem domyślny UIViewController w serii ujęć i stwierdziłem, że kod szablonu do tworzenia podklasy UIViewController ma domyślnie włączony loadView, co powoduje, że to dla mnie ... zmarnowane ponad godzinę na tę głupią rzecz. Dziękujemy za opublikowanie tego!
slycrel
11

Też mam problemy. dostałem mój projekt w xcode4.2.1. Przeczytałem tam wszystkie komentarze, ale nikt nie jest dla mnie fajny. po chwili stwierdziłem, że skomentowałem kawałek kodu.

//self.window = [[[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]] autorelease];

potem odkomentowałem to. wszystko jest dla mnie w porządku. mam nadzieję, że to by wam pomogło.

Bruce Lee
źródło
Kod: „self.window = [[UIWindow przydziel] initWithFrame: [[UIScreen mainScreen] ogranicza]];” spowodować błąd, więc właśnie go usunąłem.
Grigori A.
11

Upewnij się, że masz tę funkcję w delegacie aplikacji.

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:    (NSDictionary *)launchOptions {
   return YES;
}

Upewnij się, że didFinishLaunchingWithOptions zwraca TAK. Usunięcie wiersza „return YES” spowoduje błąd. Ten błąd może występować szczególnie często u użytkowników scenariuszy.

antycyklopy
źródło
wiele pochwał, tego właśnie chciałem (pusty projekt ze scenariuszem)
Shtirlic
2
To samo tutaj. Dzięki. Jeśli utworzysz pustą aplikację, ta metoda zostanie wypełniona ręcznym utworzeniem okna. Należy to zmienić, aby po prostu zwrócić TAK. Thx
Ben G
10

W pierwszym widoku MenuViewControllerdodałem:

MenuViewController *menuViewController = [[MenuViewController alloc]init];
self.window.rootViewController = menuViewController;

w metodzie delegowania aplikacji:

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
}

To się udało.

cujino
źródło
10

Nastąpiła niewielka zmiana w stosunku do iOS 5.0 lub podobnej, wymagająca posiadania kontrolera widoku root. Jeśli Twój kod jest oparty na starszym przykładowym kodzie, takim jak GLES2Sample , wówczas w tych przykładach kodu nie został utworzony kontroler widoku głównego.

Aby to naprawić (na przykład ten GLES2Sample), od razu applicationDidFinishLaunchingtworzę kontroler widoku głównego i dołączam do niego mój glView.

- (void) applicationDidFinishLaunching:(UIApplication *)application
{
  // To make the 'Application windows are expected
  // to have a root view controller
  // at the end of application launch' warning go away,
  // you should have a rootviewcontroller,
  // but this app doesn't have one at all.
  window.rootViewController = [[UIViewController alloc] init];  // MAKE ONE
  window.rootViewController.view = glView; // MUST SET THIS UP OTHERWISE
  // THE ROOTVIEWCONTROLLER SEEMS TO INTERCEPT TOUCH EVENTS
}

To sprawia, że ​​ostrzeżenie znika i tak naprawdę nie wpływa na twoją aplikację.

bobobobo
źródło
9

Spróbuj podłączyć IBOutlet kontrolera paska kart do widoku głównego w Konstruktorze interfejsów zamiast

self.window.rootViewController = self.tabBarController;

Ale tak naprawdę nie widziałem wcześniej takiego błędu.

d.lebedev
źródło
8

Rozwiązałem problem, wykonując następujące czynności (żadne z powyższych rozwiązań nie pomogło):

Z menu rozwijanego związanego z „Głównym interfejsem” wybierz inny wpis, a następnie ponownie wybierz „MainWindow”, a następnie przebuduj.

wprowadź opis zdjęcia tutaj

RawMean
źródło
8

Natknąłem się na ten sam problem, ale używałem storyboard

Przypisywanie mojego storyboard InitialViewControllerdo moich okien rootViewController.

W

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions{
...
UIStoryboard *stb = [UIStoryboard storyboardWithName:@"myStoryboard" bundle:nil];
self.window.rootViewController = [stb instantiateInitialViewController];
return YES;
}

i to rozwiązało problem.

letni znak
źródło
7

Ten sam problem zacząłem zaraz po uaktualnieniu do Xcode 4.3 i tylko podczas uruchamiania projektu od zera (tj. Utwórz pusty projekt, następnie utwórz kontroler UIView, a następnie utwórz osobny plik stalówki).

Po wstawieniu WSZYSTKICH wierszy i upewnieniu się, że mam prawidłowe połączenia, otrzymywałem ten błąd, a plik nib, który próbowałem załadować przez kontroler widoku (który został ustawiony jako rootController) nigdy nie pokazywał się w symulatorze.

Utworzyłem pojedynczy szablon widoku za pomocą Xcode i porównałem go z moim kodem i NAPRAWDĘ znalazłem problem!

Xcode 4.3 wydaje się dodawać domyślnie metodę - (void) loadView; do sekcji implementacji kontrolera widoku. Po uważnym przeczytaniu zawartych w nim komentarzy stało się jasne, na czym polega problem. Komentarz wskazał, aby zastąpić metodę loadView, jeśli programowo tworzysz widok (a ja parafrazuję), w przeciwnym razie NIE zastępuj loadView, jeśli używasz stalówki. W tej metodzie nie było nic innego, więc w efekcie przesłoniłem metodę (i nic nie robiłem) PODCZAS używania pliku stalówki, co spowodowało błąd.

ROZWIĄZANIE polegało albo na całkowitym usunięciu metody loadView z sekcji implementacji, albo na wywołaniu metody nadrzędnej poprzez dodanie [super loadView].

Najlepiej byłoby usunąć go, jeśli użyjesz pliku NIB, ponieważ dodanie innego kodu spowoduje jego zastąpienie.

Raz
źródło
to był dokładnie mój problem! Dodałem implementację loadView, ale nie wywołałem super. Wprowadziłem kilka innych zmian w kodzie, nie mogłem sobie przypomnieć, co do cholery zrobiłem. Utknąłem na 2 godziny, ponieważ ta zmiana wydawała się taka nieszkodliwa.
LearnCocos2D
6

Miałem ten sam komunikat o błędzie w dzienniku. Miałem wyskakujące okienko UIAlertView w aplikacji: didFinishLaunchingWithOptions. Rozwiązałem to, opóźniając połączenie z alertView, aby dać czas kontrolerowi rootowania na zakończenie ładowania.

W aplikacji: didFinishLaunchingWithOptions:

[self performSelector:@selector(callPopUp) withObject:nil afterDelay:1.0];

który dzwoni po 1 sekundzie:

- (void)callPopUp
{
    // call UIAlertView
}
janeway
źródło
Dzięki, to rozwiązało mój problem. Musisz poczekać, aby pokazać alert, aż do załadowania okna. W moim przypadku właśnie to zrobiłem [alert performSelector: @selector (show) withObject: zero poDelay: 1.0];
deepwinter
6

Miałem ten sam problem. Jeśli budujesz aplikację opartą na oknie „od zera” tak jak ja, musisz wykonać następujące czynności: (uwaga: są to kroki dla Xcode 4.2).

0. Upewnij się, że delegat aplikacji jest zgodny z protokołem UIApplicationDelegate.

Załóżmy na przykład, że nasz delegat nazywa się MyAppDelegate. W MyAppDelegate.h powinniśmy mieć coś takiego:

@interface MyAppDelegate : 
    NSObject <UIApplicationDelegate> // etc...

1. Określ delegata aplikacji w main.m

Na przykład,

#import "MyAppDelegate.h"

int main(int argc, char *argv[])
{
  @autoreleasepool {
    return UIApplicationMain(argc, argv,
      nil, NSStringFromClass([MyAppDelegate class]));
  }
}

2. Utwórz plik interfejsu głównego okna.

Aby to zrobić, kliknij projekt prawym przyciskiem myszy i wybierz Nowy plik. Następnie wybierz Okno z sekcji iOS -> Interfejs użytkownika.

Po dodaniu pliku do projektu przejdź do podsumowania projektu (kliknij lewym przyciskiem myszy na projekt; kliknij podsumowanie). W obszarze Informacje o wdrożeniu iPhone / iPod (i odpowiedniej sekcji iPada, jeśli chcesz) i wybierz nowy plik interfejsu w „ Główny interfejs ”.

3. Połącz wszystko w edytorze interfejsu

Wybierz plik interfejsu z listy plików, aby wyświetlić edytor interfejsu.

Upewnij się, że panel Narzędzia jest otwarty.

Dodaj nowy obiekt, przeciągając obiekt z listy Obiekty w panelu Narzędzia na przestrzeń powyżej obiektu Windows. Wybierz obiekt. Kliknij Inspektora tożsamości w panelu Narzędzia. Zmień klasę na delegata aplikacji (w tym przykładzie MyAppDelegate).

Wyświetl inspektora połączeń dla MyAppDelegate. Podłącz wylot okna do okna, które już istnieje w pliku interfejsu.

Kliknij właściciela pliku po lewej, a następnie kliknij Inspektora tożsamości w panelu Narzędzia. Zmień klasę naUIApplication

Wyświetl inspektora połączeń dla właściciela pliku. Podłącz ujście delegata do obiektu MyAppDelegate.

4. Na koniec, co bardzo ważne, kliknij obiekt Window w pliku interfejsu. Otwórz Inspektora atrybutów. Upewnij się, że „Visible at Launch” jest zaznaczone.

To wszystko, co musiałem zrobić, aby działało dla mnie. Powodzenia!

Tomek
źródło
6

Jeśli użyjesz MTStatusBarOverlay, otrzymasz ten błąd.

MTStatusBarOverlay tworzy dodatkowe okno (okna [[UIApplication sharedApplication]), które nie mają kontrolera głównego.

To nie wydaje się powodować problemu.

Zmieszany Vorlon
źródło
Jesteś pewien? Przetestowałeś to?
Sergey Grischyov
Jestem pewien, że tworzy okno i jestem pewien, że nie stwarza to problemu w moich aplikacjach.
Zmieszany Vorlon,
Możesz ustawić atrapę VC w MTStatusBarOverlay, aby to naprawić.
Wesley,
To był dokładnie mój problem. Miałem podobną konfigurację z oknem, które zostało dodane do paska powiadomień, a kiedy skomentowałem, błąd zniknął! W tym przypadku wydaje się nieszkodliwy.
Aaron Zinman,
6

Otrzymałem ten sam błąd po zamianie mojego interfejsu użytkownika na Storyboard przy użyciu XCode 4.6.3 i iOS 6.1

Rozwiązano go, usuwając cały kod z didFinishLaucnhingWithOptions w AppDelegate

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    return YES;
}
Pétur Ingi Egilsson
źródło
5

OrdoDei udzielił poprawnej i wartościowej odpowiedzi. Dodaję tę odpowiedź, aby podać przykład didFinishLaunchingWithOptionsmetody, która korzysta z jego odpowiedzi, a także uwzględnia komentarze innych osób dotyczące Nawigatora.

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];

    // Override point for customization after application launch.

    // Instantiate the main menu view controller (UITableView with menu items).
    // Pass that view controller to the nav controller as the root of the nav stack.
    // This nav stack drives our *entire* app.
    UIViewController *viewController = [[XMMainMenuTableViewController alloc] init];
    self.navigationController = [[UINavigationController alloc] initWithRootViewController:viewController];

    // Instantiate the app's window. Then get the nav controller's view into that window, and onto the screen.
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
    // [self.window addSubview:self.navigationController.view];
    // The disabled line above was replaced by line below. Fixed Apple's complaint in log: Application windows are expected to have a root view controller at the end of application launch
    [self.window setRootViewController:self.navigationController];
    self.window.backgroundColor = [UIColor whiteColor];
    [self.window makeKeyAndVisible];
    return YES;
}
Basil Bourque
źródło
4

Stało się tak, ponieważ przypadkowo skomentowałem:

[self.window makeKeyAndVisible];

od

- (BOOL)application:(UIApplication*) didFinishLaunchingWithOptions:(NSDictionary*)
nicerobot
źródło
4

Byłem w stanie ustawić początkowy kontroler widoku na ekranie podsumowania xcode.

Kliknij najwyższą nazwę projektu w Eksploratorze plików po lewej stronie (powinna mieć małą ikonę planu). W środkowej kolumnie kliknij nazwę swojego projektu pod „CELAMI” (obok powinna znajdować się ikona ołówka „A”). Przejrzyj „Informacje dotyczące wdrażania iPhone'a / iPoda” i „Główny interfejs”. Powinieneś być w stanie wybrać opcję z menu rozwijanego.

RachelD
źródło
4

Oprócz odpowiedzi „sho”, która jest poprawna (czwarty parametr UIApplicationMain powinien być nazwą głównego kontrolera), dodaję kilka komentarzy.

Niedawno zmieniłem „model” mojej aplikacji z używania MainWindow.xib do programowania okna. Aplikacja korzystała ze starszego szablonu, który automatycznie utworzył MainWindow. Ponieważ chciałem obsługiwać inny widok kontrolera XIB dla iPhone'a 5, łatwiej jest programowo wybrać odpowiedni XIB, gdy tworzony jest Delegat aplikacji. Usunąłem również MainWindow.xib z projektu.

Problem polegał na tym, że zapomniałem wypełnić czwarty parametr w głównym UIApplication i ZAPOMNIAŁEM USUNĄĆ MainWindow z „Main Interface” w Podsumowaniu projektu.

Spowodowało to WIELKI problem: spowodowało nieszkodliwe ostrzeżenie „Oczekuje się, że aplikacje ...” na urządzeniach programistycznych, ale kiedy trafiło do App Store, zepsuło się na telefonach konsumenckich, powodując awarię, ponieważ MainWindow nie było już w pakiecie! Musiałem poprosić o przyspieszoną recenzję poprawki.

Innym objawem jest to, że czasami biały blok, jak pusty UIView, czasami pojawiał się, gdy Ustawienia były zmieniane, a aplikacja była umieszczana na pierwszym planie. W iPhonie 5 było jasne, że jest to blok 320 x 480. Być może brakujący MainWindow był tworzony w trybie programistycznym, przy użyciu starego rozmiaru. Właśnie znalazłem ten błąd, gdy pierwsze raporty o awarii dotarły do ​​skrzynki odbiorczej.

Zainstalowanie aplikacji z App Store zamiast z XCode pokazało, że aplikacja rzeczywiście uległa awarii, a problem MainWindow ujawnił się w logu, więc mogłem zobaczyć, że nie była to specjalna kombinacja urządzeń + wersji IOS.

epx
źródło
4

Aby dodać do odpowiedzi Mike'a Flynna, od aktualizacji do Xcode 7 i uruchomienia mojej aplikacji na urządzeniu z iOS 9, dodałem to do mojego (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions

// Hide any window that isn't the main window
NSArray *windows = [[UIApplication sharedApplication] windows];
for (UIWindow *window in windows) {
    if (window != self.window) {
        window.hidden = YES;
    }
}
Kevin_TA
źródło
Ciekawe, ile okien miała Twoja aplikacja i czy wszystkie miały kontroler widoku głównego. Dzięki
DrAL3X
3

Ten problem występuje, gdy nie masz poprawnie skonfigurowanego Konstruktora interfejsów.

Upewnij się, że okno Delegata aplikacji i ujścia kontrolerów są podłączone:

W pliku MainWindow.xib przytrzymaj kontrolę, kliknij polecenie Deleguj aplikację i przeciągnij do obiektu Window. Wybierz okno. Przejmij kontrolę i ponownie wybierz delegata aplikacji, przeciągnij do głównego kontrolera widoku i wybierz viewController.

uranazo
źródło
3

Ten błąd pojawia się również, gdy właściciel pliku MainWindow.xib jest nieprawidłowo ustawiony.

Właścicielem pliku jest UIApplication
-> wstawiony obiekt klasy delegowanej aplikacji z wylotem okna podłączonym do okna

JakubKnejzlik
źródło
Plik Xib utworzyłem ręcznie i zacząłem otrzymywać ten błąd. wielkie dzięki!
RawMean