//
//  STAppDelegate.m
//  Safe Terminal
//
//  Created by Nir on 22/02/06.
//  Copyright 2006 Nir Soffer. All rights reserved.
//

#import "STAppDelegate.h"

#define LocalizedString(key, comment) \
	[[NSBundle bundleForClass:[STAppDelegate class]] \
	localizedStringForKey:(key) value:@"" table:nil]


@implementation STAppDelegate

- (id)init;
{
    if ((self = [super init])) {
        NSString *bundleIdentifier = [[NSBundle mainBundle] bundleIdentifier];
        if (! [bundleIdentifier isEqualToString:@"com.apple.Terminal"]) {
            [self dealloc];
            return nil;
        }
        [self install];
        applicationDidFinishLounching = NO;
        applicationDidOpenFile = NO;
    }
    return self;    
}

- (void)install;
{    
    /* Set me as Terminal.app application delegate, and the original
    delegate as my delegate. This allow overiding or extending original
    delegate methods. */

    [self setDelegate:[NSApp delegate]];
    [NSApp setDelegate:self];
    NSLog(@"Safe Terminal loaded.");
    
    [[NSNotificationCenter defaultCenter]
        addObserver:self
           selector:@selector(applicationDidFinishLounching:)
               name:NSApplicationDidFinishLaunchingNotification
             object:NSApp];        
}

- (void)applicationDidFinishLounching:(NSNotification *)notification;
{
    applicationDidFinishLounching = YES;
    [[NSNotificationCenter defaultCenter] removeObserver:self];
        
    if (! applicationDidOpenFile)
        /* Remind the application to open a new shell. I don't know why
        it will not open one without this call. */
        [NSApp sendAction:@selector(new:) to:nil from:self];
}

- (BOOL)application:(NSApplication *)theApplication openFile:(NSString *)filename
{
    /* Extend the original method with confirmation dialog */

    int returnCode = [[self alertForFilename:filename] runModal];
    if ((returnCode == NSAlertSecondButtonReturn) && 
        ([delegate respondsToSelector:@selector(application:openFile:)])) {
        applicationDidOpenFile = [delegate application:theApplication
                                              openFile:filename];
        return applicationDidOpenFile;
    } else if (! applicationDidFinishLounching)
        /* Terminal was launched by opening a script and the user
        canceled. It is likely that the user is not interested in
        switching to the Terminal. */
        [NSApp terminate:self];
    return NO;
}

- (NSAlert *)alertForFilename:(NSString *)filename;
{
    /* Create an alert for filename */

    NSAlert *alert = [[NSAlert alloc] init];
    [alert setAlertStyle:NSCriticalAlertStyle];
    [alert setMessageText:[NSString stringWithFormat:
        LocalizedString(@"Are you sure you want to execute %@?", 
                        @"Script execution warning title"),
        [[NSFileManager defaultManager] displayNameAtPath:filename]]];
    [alert setInformativeText:
        LocalizedString(@"Executing scripts might harm your computer.", 
                        @"Script execution warning informative text")];
    [alert addButtonWithTitle:LocalizedString(@"Cancel", 
        @"Script execution warning button")];
    [alert addButtonWithTitle:LocalizedString(@"Execute Script", 
        @"Script execution warning button")];    
    return [alert autorelease];
}

- (void)setDelegate:(id)anObject;
{
    /* By convention Cocoa objects do not retain their delegates. */    
    delegate = anObject;
}

/* Delegate implementaion */

- (void)forwardInvocation:(NSInvocation *)invocation
{
    /* Forward anything I don't implement to the delegate */
    
    SEL aSelector = [invocation selector];
    
    if ([delegate respondsToSelector:aSelector])
        [invocation invokeWithTarget:delegate];
    else
        [self doesNotRecognizeSelector:aSelector];
}

- (NSMethodSignature *)methodSignatureForSelector:(SEL)aSelector
{
    /* Rquired to implement a delegate */
    
    return [delegate methodSignatureForSelector:aSelector];
}

@end
