Как показать NSPanel в виде листа - PullRequest
7 голосов
/ 22 сентября 2009

Я пытаюсь показать NSPanel в виде листа. Я наивно делаю что-то вроде этого:

SheetController *sheetController = [[[SheetController alloc]
                                      initWithWindowNibName:@"Sheet"] autorelease];

[[NSApplication sharedApplication] beginSheet:sheetController.window 
                               modalForWindow:self.window
                                modalDelegate:self
                               didEndSelector:@selector(sheetDidEnd:returnCode:contextInfo:) 
                                  contextInfo:nil];

По какой-то причине, которая ускользает от меня, это не работает. Когда вызывается эта часть кода, лист на мгновение мигает (из-за сообщения autorelease). Лист никогда не привязывается к окну.

Если кто-нибудь может указать мне, где я могу найти больше информации, это будет очень ценно.

Ответы [ 3 ]

16 голосов
/ 22 сентября 2009

Это звучит как классический случай, когда вы установили флажок «Видимо при запуске» для панели в IB. Выключи это.

2 голосов
/ 22 сентября 2009

Да, вам нужно владеть этим контроллером столько, сколько вы хотите, чтобы он продолжал функционировать. Вы не можете просто создать его, автоматически выпустить его и позволить ему умереть - вам нужно держаться за него столько, сколько вам нужно.

1 голос
/ 22 сентября 2009

Не забывайте, что если вы пытаетесь запустить это как «модальный» лист (то есть оно захватывает приложение, пока пользователь не отклонит его), вам нужно будет запустить новый цикл выполнения.

То, что вы сделали, это показало лист, а затем не переместило новый цикл, поэтому ОС просто показывает лист, видит, что нет причин его поддерживать, и таким образом выключает его и возобновляет выполнение на следующей строке :

Обычно я делаю листы следующим образом:

- (id)showPanelModalAgainstWindow: (NSWindow *)window
{
   [[NSApplication sharedApplication] beginSheet: panelToShow
                modalForWindow: window
                modalDelegate: self
                didEndSelector: @selector(sheetDidEnd:returnCode:contextInfo:)
                contextInfo: nil];

   [[NSApplication sharedApplication] runModalForWindow: panelToShow];
   if (m_returnCode == NSCancelButton) return nil;
}


- (void)sheetDidEnd:(NSWindow *)sheet
         returnCode:(int)returnCode
        contextInfo:(void  *)contextInfo
{
    UNUSED(sheet);
    UNUSED(contextInfo);
    m_returnCode = returnCode;
}

Затем в вашей кнопке подтверждения и / или отмены:

- (IBAction)continueButtonClicked:(id)sender
{
    UNUSED(sender);
    [[NSApplication sharedApplication] stopModal];
    [createAccountWizardPanel orderOut: nil];
    [[NSApplication sharedApplication] endSheet: createAccountWizardPanel
                                       returnCode: NSOKButton];

}

Я уверен, что есть немного менее кодовый способ сделать это, но я не стал вдаваться в подробности, потому что этот способ до сих пор прекрасно работал ...

Предыдущие комментарии о сроке службы контроллера и панельных объектов также актуальны - убедитесь, что точно понимаете, какие объекты вам нужны и для какого времени жизни при отображении модальной панели.

...