Da der Panel-Vervollständigungshandler aufgerufen wird, bevor das Panel effektiv geschlossen wurde,1 ist eine Lösung, NSWindowDidEndSheetNotification
auf Ihrem Modal-Panel zu beobachten:
- Deklarieren Sie eine Instanzvariable/-eigenschaft in Ihrer Klasse, um den Validierungsfehler zu halten;
- Deklarieren Sie eine Methode, die ausgeführt wird, wenn das Panel effektiv geschlossen wird. Definieren Sie sie so, dass sie den Fehler auf dem aktuellen Fenster präsentiert;
- Lassen Sie Ihre Klasse auf
NSWindowDidEndSheetNotification
auf [self window]
hören und führen Sie die oben deklarierte Methode aus, wenn die Benachrichtigung gesendet wird;
- Im Panel-Vervollständigungshandler, wenn die Validierung fehlschlägt, weisen Sie den Fehler der oben deklarierten Instanzvariable/-eigenschaft zu.
Indem Sie dies tun, setzt der Vervollständigungshandler nur den Validierungsfehler. Kurz nachdem der Handler aufgerufen wurde, wird das geöffnete Panel geschlossen und die Benachrichtigung wird an Ihr Objekt gesendet, das dann den Validierungsfehler präsentiert, der vom Vervollständigungshandler gesetzt wurde.
Zum Beispiel:
In Ihrer Klassendeklaration fügen Sie hinzu:
@property (retain) NSError *validationError;
- (void)openPanelDidClose:(NSNotification *)notification;
In Ihrer Klassenimplementierung fügen Sie hinzu:
@synthesize validationError;
- (void)dealloc {
[validationError release];
[super dealloc];
}
- (void)openPanelDidClose:(NSNotification *)notification {
if (self.validationError) [self presentError:error];
// oder [[self window] presentError:error];
// Löschen Sie validationError, damit weitere Benachrichtigungen
// den Fehler nicht anzeigen, es sei denn, ein neuer Fehler wurde festgelegt
self.validationError = nil;
// Wenn [self window] andere Dialogfelder anzeigt, möchten Sie nicht,
// dass diese Methode für sie ausgeführt wird
[[NSNotificationCenter defaultCenter] removeObserver:self
name:NSWindowDidEndSheetNotification
object:[self window]];
}
// Angenommen, ein Aktion löst das Öffnen des Panels aus
- (IBAction)showOpenPanel:(id)sender {
NSOpenPanel *openPanel = [NSOpenPanel openPanel];
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(openPanelDidClose:)
name:NSWindowDidEndSheetNotification
object:[self window]];
void (^openPanelHandler)(NSInteger) = ^(NSInteger returnCode) {
if (returnCode == NSFileHandlingPanelOKButton) {
// meine Validierung durchführen
// oh oh, etwas Schlimmes ist passiert
self.validationError = error;
}
};
[openPanel beginSheetModalForWindow:[self window]
completionHandler:openPanelHandler];
}
1Wenn Sie dieses Verhalten für falsch halten, erwägen Sie, einen Fehlerbericht bei Apple einzureichen. Ich erinnere mich nicht genau, ob ein Fehler über einem Öffnen/Speichern-Panel präsentiert werden sollte.