Je suis au milieu de débogage un problème extrêmement inhabituel, et je me demandais si quelqu'un pourrait avoir une idée de ce qui pourrait aller mal:L'application modale NSPanel/sheet/dialog + NSThread == fenêtre se bloque?
Dans une classe de contrôleur à partir d'un NIB, je prends un NSPanel de cette même NIB, puis montrer app modalement sur une NSWindow (qui a été créé à la main dans le code):
[[NSApplication sharedApplication] beginSheet: myPanel
modalForWindow: window
modalDelegate: self
didEndSelector: @selector(sheetDidEnd:returnCode:contextInfo:)
contextInfo: nil];
[[NSApplication sharedApplication] runModalForWindow: myPanel];
maintenant, lorsque le bouton « terminer » sur cette feuille est cliqué, je lance un code pour désactiver certaines boutons et déclencher un thread pour s'assurer que l'entrée de l'utilisateur est valide (je dois valider avec un service distant). Ce fil est tiré à partir d'un objet validateur séparé Je crée:
// controller calls:
[validator validateCreds: creds
notify: @selector(validationComplete:)
onObject: self];
// validator object
validateInfo: (NSDictionary *)parms
notify: (SEL)notifySelector
onObject: (id)notifyObject
{
// build up data with parms and notify info
[[NSThread detachNewThreadSelector: @selector(remotevalidate:)
toTarget: self withObject: data];
}
Ensuite, lorsque la validation est terminée, le validateur informe mon objet contrôleur:
[notifyObject performSelectorOnMainThread: notifySelector
withObject: results waitUntilDone: NO];
Et puis mon objet contrôleur, dans la méthode que les appels de l'objet validateur, tue la boîte de dialogue:
- (void)validationComplete: (id)data
{
[[NSApplication sharedApplication] stopModal];
[createTwitterPanel orderOut: nil];
[[NSApplication sharedApplication] endSheet: createTwitterPanel
returnCode: NSOKButton];
}
- (void)sheetDidEnd:(NSWindow *)sheet
returnCode:(int)returnCode
contextInfo:(void *)contextInfo
{
m_returnCode = returnCode;
}
Mon problème: Bien que le panneau est fermé/disparait, t Le top NSApp runModalForWindow:
ne se termine pas tant qu'un événement système n'est pas envoyé à la fenêtre qui affichait la boîte de dialogue. Si vous tentez de déplacer, de redimensionner ou de faire quoi que ce soit dans la fenêtre, ou si vous vous éloignez de l'application, la méthode se ferme soudainement et l'exécution se poursuit. Aucune quantité d'attente ne semble aider, sinon, cependant.
J'ai vérifié que toutes les méthodes invoquées dans la classe de contrôleur sont toutes appelées sur le thread d'application principal. Un indice encore plus intéressant est que la boîte de dialogue a deux contrôles, un WebView, et un NSTextField: Même si je force la sortie de runModalForWindow:
en cliquant sur la fenêtre, TABULATION entre les deux contrôles reste vissée - ce n'est tout simplement jamais fonctionne à nouveau. C'est comme si ma boucle d'événement était bouchée.
J'ai essayé de changer validationComplete: à la place de poster une notification sur le thread principal, et j'ai également joué avec le waitUntilDone
sur la méthode performSelectorOnMainThread
, le tout sans effet.
Des idées? Les choses que je devrais essayer de regarder?
Ceci est une application ciblée sur 10.5, exécutant Xcode 3.2.1 sur 10.6.1 – MarcWan