#import <Cocoa/Cocoa.h>
#include <sys/param.h>
#include <sys/syslimits.h>
#include <unistd.h>
#include <crt_externs.h>
#include <mach-o/dyld.h>
#include "EXTERN.h"
#include "SDL.h"
#include "perl.h"

static void xs_init (pTHX);
static PerlInterpreter *my_perl;

EXTERN_C void boot_DynaLoader (pTHX_ CV* cv);

EXTERN_C void
xs_init(pTHX)
{
       char *file = __FILE__;
       /* DynaLoader is a special case */
       newXS("DynaLoader::boot_DynaLoader", boot_DynaLoader, file);
}

@interface MyAppDelegate : NSObject
@end
@implementation MyAppDelegate
-(NSApplicationTerminateReply)applicationShouldTerminate:(NSApplication *)sender {
    if (my_perl == NULL) {
        return NSTerminateNow;
    }
    /* push SDL_Quit, application will terminate */
    SDL_Event event;
    event.type = SDL_QUIT;
    SDL_PushEvent(&event);
    return NSTerminateCancel;
}

-(void)toggleColourblind:(id)sender {
    if (my_perl) {
        eval_pv("if (1) {package main;if (!$is_playing_game) {$colourblind = !$colourblind; reload_bubbles();}}", TRUE);
    }
}

-(void)applicationDidFinishLaunching:(NSNotification *)notification {
    char progname[PATH_MAX];
    const char *childArgv[3];
    NSBundle *mainBundle = [NSBundle mainBundle];
    int i;
    unsigned long prognamesize;

    // find main perl file.  __main__.pl seems to be a standard.
    NSArray *possibleMains = [NSArray arrayWithObjects:
        @"__main__.pl",
        [[mainBundle infoDictionary] objectForKey:@"PerlScript"],
        nil];
    NSEnumerator *possibleMainsEnumerator = [possibleMains objectEnumerator];
    NSString *mainPerlPath;
    NSString *nextFileName;

    while ((nextFileName = [possibleMainsEnumerator nextObject])) {
        mainPerlPath = [mainBundle pathForResource: nextFileName ofType: nil];
        if ( mainPerlPath )
            break;
    }

    if ( !mainPerlPath )
        [NSException raise: NSInternalInconsistencyException
                    format: @"%s:%d sdlperl_main() Failed to find one of %@ in app wrapper.  Exiting.", __FILE__, __LINE__, possibleMains];
    const char *mainPerlPathPtr = [mainPerlPath UTF8String];

    chdir([[mainBundle resourcePath] UTF8String]);

    progname[0] = '\0';
    prognamesize = sizeof(progname);
    _NSGetExecutablePath(progname, &prognamesize);
    i = 0;
    childArgv[i++] = (const char *)progname;
    childArgv[i++] = mainPerlPathPtr;
    childArgv[i++] = NULL;

    my_perl = perl_alloc();
    perl_construct(my_perl);
    perl_parse(my_perl, xs_init, i-1, (char **)childArgv, NULL);
    av_clear(GvAV(PL_incgv));
    av_push(GvAV(PL_incgv), newSVpv(".", 0));
    perl_run(my_perl);
    if (my_perl) {
        perl_destruct(my_perl);
        perl_free(my_perl);
        my_perl = NULL;
    }
    [NSApp terminate:self];
}
@end

#ifdef main
#undef main
#endif
int main(int argc, const char *argv[])
{
    return NSApplicationMain(argc, argv);
}
