/*
 * QEMU Cocoa display driver
 * 
 * Copyright (c) 2005 Pierre d'Herbemont
 *                    many code/inspiration from SDL 1.2 code (LGPL)
 * 
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 * THE SOFTWARE.
 */
/*
    Todo :    x  miniaturize window 
              x  center the window
              -  save window position
              -  handle keyboard event
              -  handle mouse event
              -  non 32 bpp support
              -  full screen
              -  mouse focus
              x  simple graphical prompt to demo
              -  better graphical prompt
*/

#import <Cocoa/Cocoa.h>

#include "vl.h"

NSWindow *window = NULL;
NSQuickDrawView *qd_view = NULL;


int gArgc;
char **gArgv;
DisplayState current_ds;

int grab = 0;
int modifiers_state[256];

/* main defined in qemu/vl.c */
int qemu_main(int argc, char **argv);

/* To deal with miniaturization */
@interface QemuWindow : NSWindow
{ }
@end


/*
 ------------------------------------------------------
    Qemu Video Driver
 ------------------------------------------------------
*/

/*
 ------------------------------------------------------
    cocoa_update
 ------------------------------------------------------
*/
static void cocoa_update(DisplayState *ds, int x, int y, int w, int h)
{
    //printf("updating x=%d y=%d w=%d h=%d\n", x, y, w, h);

    /* Use QDFlushPortBuffer() to flush content to display */
    RgnHandle dirty = NewRgn ();
    RgnHandle temp  = NewRgn ();

    SetEmptyRgn (dirty);

    /* Build the region of dirty rectangles */
    MacSetRectRgn (temp, x, y,
                        x + w, y + h);
    MacUnionRgn (dirty, temp, dirty);
                
    /* Flush the dirty region */
    QDFlushPortBuffer ( [ qd_view  qdPort ], dirty );
    DisposeRgn (dirty);
    DisposeRgn (temp);
}

/*
 ------------------------------------------------------
    cocoa_resize
 ------------------------------------------------------
*/
static void cocoa_resize(DisplayState *ds, int w, int h)
{
    const int device_bpp = 32;
    static void *screen_pixels;
    static int  screen_pitch;
    NSRect contentRect;
    
    //printf("resizing to %d %d\n", w, h);
    
    contentRect = NSMakeRect (0, 0, w, h);
    if(window)
    {
        [window close];
        [window release];
    }
    window = [ [ QemuWindow alloc ] initWithContentRect:contentRect
                                  styleMask:NSTitledWindowMask|NSMiniaturizableWindowMask|NSClosableWindowMask
                                  backing:NSBackingStoreBuffered defer:NO];
    if(!window)
    {
        fprintf(stderr, "(cocoa) can't create window\n");
        exit(1);
    }
    
    if(qd_view)
        [qd_view release];
    
    qd_view = [ [ NSQuickDrawView alloc ] initWithFrame:contentRect ];
    
    if(!qd_view)
    {
         fprintf(stderr, "(cocoa) can't create qd_view\n");
        exit(1);
    }
    
    [ window setAcceptsMouseMovedEvents:YES ];
    [ window setTitle:@"Qemu" ];
    [ window setReleasedWhenClosed:NO ];
    
    /* Set screen to black */
    [ window setBackgroundColor: [NSColor blackColor] ];
    
    /* set window position */
    [ window center ];
    
    [ qd_view setAutoresizingMask: NSViewWidthSizable | NSViewHeightSizable ];
    [ [ window contentView ] addSubview:qd_view ];
    [ qd_view release ];
    [ window makeKeyAndOrderFront:nil ];
    
    /* Careful here, the window seems to have to be onscreen to do that */
    LockPortBits ( [ qd_view qdPort ] );
    screen_pixels = GetPixBaseAddr ( GetPortPixMap ( [ qd_view qdPort ] ) );
    screen_pitch  = GetPixRowBytes ( GetPortPixMap ( [ qd_view qdPort ] ) );
    UnlockPortBits ( [ qd_view qdPort ] );
    { 
            int vOffset = [ window frame ].size.height - 
                [ qd_view frame ].size.height - [ qd_view frame ].origin.y;
            
            int hOffset = [ qd_view frame ].origin.x;
                    
            screen_pixels += (vOffset * screen_pitch) + hOffset * (device_bpp/8);
    }
    ds->data = screen_pixels;
    ds->linesize = screen_pitch;
    ds->depth = device_bpp;
    ds->width = w;
    ds->height = h;
    
    current_ds = *ds;
}

/*
 ------------------------------------------------------
    keymap conversion
 ------------------------------------------------------
*/

int keymap[] =
{
//  SdlI    macI    macH    SdlH    104xtH  104xtC  sdl
    30, //  0       0x00    0x1e            A       QZ_a
    31, //  1       0x01    0x1f            S       QZ_s
    32, //  2       0x02    0x20            D       QZ_d
    33, //  3       0x03    0x21            F       QZ_f
    35, //  4       0x04    0x23            H       QZ_h
    34, //  5       0x05    0x22            G       QZ_g
    44, //  6       0x06    0x2c            Z       QZ_z
    45, //  7       0x07    0x2d            X       QZ_x
    46, //  8       0x08    0x2e            C       QZ_c
    47, //  9       0x09    0x2f            V       QZ_v
    0,  //  10      0x0A    Undefined
    48, //  11      0x0B    0x30            B       QZ_b
    16, //  12      0x0C    0x10            Q       QZ_q
    17, //  13      0x0D    0x11            W       QZ_w
    18, //  14      0x0E    0x12            E       QZ_e
    19, //  15      0x0F    0x13            R       QZ_r
    21, //  16      0x10    0x15            Y       QZ_y
    20, //  17      0x11    0x14            T       QZ_t
    2,  //  18      0x12    0x02            1       QZ_1
    3,  //  19      0x13    0x03            2       QZ_2
    4,  //  20      0x14    0x04            3       QZ_3
    5,  //  21      0x15    0x05            4       QZ_4
    7,  //  22      0x16    0x07            6       QZ_6
    6,  //  23      0x17    0x06            5       QZ_5
    13, //  24      0x18    0x0d            =       QZ_EQUALS
    10, //  25      0x19    0x0a            9       QZ_9
    8,  //  26      0x1A    0x08            7       QZ_7
    12, //  27      0x1B    0x0c            -       QZ_MINUS
    9,  //  28      0x1C    0x09            8       QZ_8
    11, //  29      0x1D    0x0b            0       QZ_0
    27, //  30      0x1E    0x1b            ]       QZ_RIGHTBRACKET
    24, //  31      0x1F    0x18            O       QZ_o
    22, //  32      0x20    0x16            U       QZ_u
    26, //  33      0x21    0x1a            [       QZ_LEFTBRACKET
    23, //  34      0x22    0x17            I       QZ_i
    25, //  35      0x23    0x19            P       QZ_p
    28, //  36      0x24    0x1c            ENTER   QZ_RETURN
    38, //  37      0x25    0x26            L       QZ_l
    36, //  38      0x26    0x24            J       QZ_j
    40, //  39      0x27    0x28            '       QZ_QUOTE
    37, //  40      0x28    0x25            K       QZ_k
    39, //  41      0x29    0x27            ;       QZ_SEMICOLON
    43, //  42      0x2A    0x2b            \       QZ_BACKSLASH
    51, //  43      0x2B    0x33            ,       QZ_COMMA
    53, //  44      0x2C    0x35            /       QZ_SLASH
    49, //  45      0x2D    0x31            N       QZ_n
    50, //  46      0x2E    0x32            M       QZ_m
    52, //  47      0x2F    0x34            .       QZ_PERIOD
    15, //  48      0x30    0x0f            TAB     QZ_TAB
    57, //  49      0x31    0x39            SPACE   QZ_SPACE
    41, //  50      0x32    0x29            `       QZ_BACKQUOTE
    14, //  51      0x33    0x0e            BKSP    QZ_BACKSPACE
    0,  //  52      0x34    Undefined
    1,  //  53      0x35    0x01            ESC     QZ_ESCAPE
    0,  //  54      0x36                            QZ_RMETA
    0,  //  55      0x37                            QZ_LMETA
    42, //  56      0x38    0x2a            L SHFT  QZ_LSHIFT
    58, //  57      0x39    0x3a            CAPS    QZ_CAPSLOCK
    56, //  58      0x3A    0x38            L ALT   QZ_LALT
    29, //  59      0x3B    0x1d            L CTRL  QZ_LCTRL
    54, //  60      0x3C    0x36            R SHFT  QZ_RSHIFT
    184,//  61      0x3D    0xb8    E0,38   R ALT   QZ_RALT
    157,//  62      0x3E    0x9d    E0,1D   R CTRL  QZ_RCTRL
    0,  //  63      0x3F    Undefined
    0,  //  64      0x40    Undefined
    0,  //  65      0x41    Undefined
    0,  //  66      0x42    Undefined
    55, //  67      0x43    0x37            KP *    QZ_KP_MULTIPLY
    0,  //  68      0x44    Undefined
    78, //  69      0x45    0x4e            KP +    QZ_KP_PLUS
    0,  //  70      0x46    Undefined
    69, //  71      0x47    0x45            NUM     QZ_NUMLOCK
    0,  //  72      0x48    Undefined
    0,  //  73      0x49    Undefined
    0,  //  74      0x4A    Undefined
    181,//  75      0x4B    0xb5    E0,35   KP /    QZ_KP_DIVIDE
    152,//  76      0x4C    0x9c    E0,1C   KP EN   QZ_KP_ENTER
    0,  //  77      0x4D    undefined
    74, //  78      0x4E    0x4a            KP -    QZ_KP_MINUS
    0,  //  79      0x4F    Undefined
    0,  //  80      0x50    Undefined
    0,  //  81      0x51                            QZ_KP_EQUALS
    82, //  82      0x52    0x52            KP 0    QZ_KP0
    79, //  83      0x53    0x4f            KP 1    QZ_KP1
    80, //  84      0x54    0x50            KP 2    QZ_KP2
    81, //  85      0x55    0x51            KP 3    QZ_KP3
    75, //  86      0x56    0x4b            KP 4    QZ_KP4
    76, //  87      0x57    0x4c            KP 5    QZ_KP5
    77, //  88      0x58    0x4d            KP 6    QZ_KP6
    71, //  89      0x59    0x47            KP 7    QZ_KP7
    0,  //  90      0x5A    Undefined
    72, //  91      0x5B    0x48            KP 8    QZ_KP8
    73, //  92      0x5C    0x49            KP 9    QZ_KP9
    0,  //  93      0x5D    Undefined
    0,  //  94      0x5E    Undefined
    0,  //  95      0x5F    Undefined
    63, //  96      0x60    0x3f            F5      QZ_F5
    64, //  97      0x61    0x40            F6      QZ_F6
    65, //  98      0x62    0x41            F7      QZ_F7
    61, //  99      0x63    0x3d            F3      QZ_F3
    66, //  100     0x64    0x42            F8      QZ_F8
    67, //  101     0x65    0x43            F9      QZ_F9
    0,  //  102     0x66    Undefined
    87, //  103     0x67    0x57            F11     QZ_F11
    0,  //  104     0x68    Undefined
    183,//  105     0x69    0xb7            QZ_PRINT
    0,  //  106     0x6A    Undefined
    70, //  107     0x6B    0x46            SCROLL  QZ_SCROLLOCK
    0,  //  108     0x6C    Undefined
    68, //  109     0x6D    0x44            F10     QZ_F10
    0,  //  110     0x6E    Undefined
    88, //  111     0x6F    0x58            F12     QZ_F12
    0,  //  112     0x70    Undefined
    110,//  113     0x71    0x0                     QZ_PAUSE
    210,//  114     0x72    0xd2    E0,52   INSERT  QZ_INSERT
    199,//  115     0x73    0xc7    E0,47   HOME    QZ_HOME
    201,//  116     0x74    0xc9    E0,49   PG UP   QZ_PAGEUP
    211,//  117     0x75    0xd3    E0,53   DELETE  QZ_DELETE
    62, //  118     0x76    0x3e            F4      QZ_F4
    207,//  119     0x77    0xcf    E0,4f   END     QZ_END
    60, //  120     0x78    0x3c            F2      QZ_F2
    209,//  121     0x79    0xd1    E0,51   PG DN   QZ_PAGEDOWN
    59, //  122     0x7A    0x3b            F1      QZ_F1
    203,//  123     0x7B    0xcb    e0,4B   L ARROW QZ_LEFT
    205,//  124     0x7C    0xcd    e0,4D   R ARROW QZ_RIGHT
    208,//  125     0x7D    0xd0    E0,50   D ARROW QZ_DOWN
    200,//  126     0x7E    0xc8    E0,48   U ARROW QZ_UP
/* completed according to http://www.libsdl.org/cgi/cvsweb.cgi/SDL12/src/video/quartz/SDL_QuartzKeys.h?rev=1.6&content-type=text/x-cvsweb-markup */
  
/* Aditional 104 Key XP-Keyboard Scancodes from http://www.computer-engineering.org/ps2keyboard/scancodes1.html */
/*
    219 //          0xdb            e0,5b   L GUI   
    220 //          0xdc            e0,5c   R GUI   
    221 //          0xdd            e0,5d   APPS    
        //              E0,2A,E0,37         PRNT SCRN   
        //              E1,1D,45,E1,9D,C5   PAUSE   
    83  //          0x53    0x53            KP .    
// ACPI Scan Codes                              
    222 //          0xde            E0, 5E  Power   
    223 //          0xdf            E0, 5F  Sleep   
    227 //          0xe3            E0, 63  Wake    
// Windows Multimedia Scan Codes                                
    153 //          0x99            E0, 19  Next Track  
    144 //          0x90            E0, 10  Previous Track  
    164 //          0xa4            E0, 24  Stop    
    162 //          0xa2            E0, 22  Play/Pause  
    160 //          0xa0            E0, 20  Mute    
    176 //          0xb0            E0, 30  Volume Up   
    174 //          0xae            E0, 2E  Volume Down 
    237 //          0xed            E0, 6D  Media Select    
    236 //          0xec            E0, 6C  E-Mail  
    161 //          0xa1            E0, 21  Calculator  
    235 //          0xeb            E0, 6B  My Computer 
    229 //          0xe5            E0, 65  WWW Search  
    178 //          0xb2            E0, 32  WWW Home    
    234 //          0xea            E0, 6A  WWW Back    
    233 //          0xe9            E0, 69  WWW Forward 
    232 //          0xe8            E0, 68  WWW Stop    
    231 //          0xe7            E0, 67  WWW Refresh 
    230 //          0xe6            E0, 66  WWW Favorites   
*/
};

int cocoa_keycode_to_qemu(int keycode)
{
    if((sizeof(keymap)/sizeof(int)) <= keycode)
    {
        printf("(cocoa) warning unknow keycode 0x%x\n", keycode);
        return 0;
    }
    return keymap[keycode];
}

/*
 ------------------------------------------------------
    cocoa_refresh
 ------------------------------------------------------
*/
static void cocoa_refresh(DisplayState *ds)
{
    //printf("cocoa_refresh \n");
    NSDate *distantPast;
    NSEvent *event;
    NSAutoreleasePool *pool;
    
    pool = [ [ NSAutoreleasePool alloc ] init ];
    distantPast = [ NSDate distantPast ];
    
    vga_hw_update();

    do {
        event = [ NSApp nextEventMatchingMask:NSAnyEventMask untilDate:distantPast
                        inMode: NSDefaultRunLoopMode dequeue:YES ];
        if (event != nil) {
            switch ([event type]) {
                case NSFlagsChanged:
                    {
                        int keycode = cocoa_keycode_to_qemu([event keyCode]);

                        if (keycode)
                        {
                            if (keycode == 58 || keycode == 69) {
                                /* emulate caps lock and num lock keydown and keyup */
                                kbd_put_keycode(keycode);
                                kbd_put_keycode(keycode | 0x80);
                            } else if (is_graphic_console()) {
                                if (keycode & 0x80)
                                    kbd_put_keycode(0xe0);
                                if (modifiers_state[keycode] == 0) {
                                    /* keydown */
                                    kbd_put_keycode(keycode & 0x7f);
                                    modifiers_state[keycode] = 1;
                                } else {
                                    /* keyup */
                                    kbd_put_keycode(keycode | 0x80);
                                    modifiers_state[keycode] = 0;
                                }
                            }
                        }

                        /* release Mouse grab when pressing ctrl+alt */
                        if (([event modifierFlags] & NSControlKeyMask) && ([event modifierFlags] & NSAlternateKeyMask))
                        {
                            [window setTitle: @"QEMU"];
                            [NSCursor unhide];
                            CGAssociateMouseAndMouseCursorPosition ( TRUE );
                            grab = 0;
                        }
                    }
                    break;

                case NSKeyDown:
                    {
                        int keycode = cocoa_keycode_to_qemu([event keyCode]);               
                        
                        /* handle command Key Combos */
                        if ([event modifierFlags] & NSCommandKeyMask) {
                            switch ([event keyCode]) {
                                /* quit */
                                case 12: /* q key */
                                    /* switch to windowed View */
                                    exit(0);
                                    return;
                            }
                        }
                        
                        /* handle control + alt Key Combos */
                        if (([event modifierFlags] & NSControlKeyMask) && ([event modifierFlags] & NSAlternateKeyMask)) {
                            switch (keycode) {
                                /* toggle Monitor */
                                case 0x02 ... 0x0a: /* '1' to '9' keys */
                                    console_select(keycode - 0x02);
                                    break;
                            }
                        } else {
                            /* handle standard key events */
                            if (is_graphic_console()) {
                                if (keycode & 0x80) //check bit for e0 in front
                                    kbd_put_keycode(0xe0);
                                kbd_put_keycode(keycode & 0x7f); //remove e0 bit in front
                            /* handle monitor key events */
                            } else {
                                int keysym = 0;

                                switch([event keyCode]) {
                                case 115:
                                    keysym = QEMU_KEY_HOME;
                                    break;
                                case 117:
                                    keysym = QEMU_KEY_DELETE;
                                    break;
                                case 119:
                                    keysym = QEMU_KEY_END;
                                    break;
                                case 123:
                                    keysym = QEMU_KEY_LEFT;
                                    break;
                                case 124:
                                    keysym = QEMU_KEY_RIGHT;
                                    break;
                                case 125:
                                    keysym = QEMU_KEY_DOWN;
                                    break;
                                case 126:
                                    keysym = QEMU_KEY_UP;
                                    break;
                                default:
                                    {
                                        NSString *ks = [event characters];

                                        if ([ks length] > 0)
                                            keysym = [ks characterAtIndex:0];
                                    }
                                }
                                if (keysym)
                                    kbd_put_keysym(keysym);
                            }
                        }
                    }
                    break;
                    
                case NSKeyUp:
                    {
                        int keycode = cocoa_keycode_to_qemu([event keyCode]);   
                        if (is_graphic_console()) {
                            if (keycode & 0x80)
                                kbd_put_keycode(0xe0);
                            kbd_put_keycode(keycode | 0x80); //add 128 to signal release of key
                        }
                    }
                    break;
                    
                case NSMouseMoved:
                    if (grab) {
                        int dx = [event deltaX];
                        int dy = [event deltaY];
                        int dz = [event deltaZ];
                        int buttons = 0;
                        kbd_mouse_event(dx, dy, dz, buttons);
                    }
                    break;
                        
                case NSLeftMouseDown:
                    if (grab) {
                        int buttons = 0;
                        
                        /* leftclick+command simulates rightclick */
                        if ([event modifierFlags] & NSCommandKeyMask) {
                            buttons |= MOUSE_EVENT_RBUTTON;
                        } else {
                            buttons |= MOUSE_EVENT_LBUTTON;
                        }
                        kbd_mouse_event(0, 0, 0, buttons);
                    } else {
                        [NSApp sendEvent: event];
                    }
                    break;
                        
                case NSLeftMouseDragged:
                    if (grab) {
                        int dx = [event deltaX];
                        int dy = [event deltaY];
                        int dz = [event deltaZ];
                        int buttons = 0;
                        if ([[NSApp currentEvent] modifierFlags] & NSCommandKeyMask) { //leftclick+command simulates rightclick
                            buttons |= MOUSE_EVENT_RBUTTON;
                        } else {
                            buttons |= MOUSE_EVENT_LBUTTON;
                        }
                        kbd_mouse_event(dx, dy, dz, buttons);
                    }
                    break;
                        
                case NSLeftMouseUp:
                    if (grab) {
                        kbd_mouse_event(0, 0, 0, 0);
                    } else {
                        [window setTitle: @"QEMU (Press ctrl + alt to release Mouse)"];
                        [NSCursor hide];
                        CGAssociateMouseAndMouseCursorPosition ( FALSE );
                        grab = 1;
                        //[NSApp sendEvent: event];
                    }
                    break;
                        
                case NSRightMouseDown:
                    if (grab) {
                        int buttons = 0;
                        
                        buttons |= MOUSE_EVENT_RBUTTON;
                        kbd_mouse_event(0, 0, 0, buttons);
                    } else {
                        [NSApp sendEvent: event];
                    }
                    break;
                    
                case NSRightMouseDragged:
                    if (grab) {
                        int dx = [event deltaX];
                        int dy = [event deltaY];
                        int dz = [event deltaZ];
                        int buttons = 0;
                        buttons |= MOUSE_EVENT_RBUTTON;
                        kbd_mouse_event(dx, dy, dz, buttons);
                    }
                    break;
                    
                case NSRightMouseUp:
                    if (grab) {
                        kbd_mouse_event(0, 0, 0, 0);
                    } else {
                        [NSApp sendEvent: event];
                    }
                    break;
                        
                case NSOtherMouseDragged:
                    if (grab) {
                        int dx = [event deltaX];
                        int dy = [event deltaY];
                        int dz = [event deltaZ];
                        int buttons = 0;
                        buttons |= MOUSE_EVENT_MBUTTON;
                        kbd_mouse_event(dx, dy, dz, buttons);
                    }
                    break;
                    
                case NSOtherMouseDown:
                    if (grab) {
                        int buttons = 0;
                        buttons |= MOUSE_EVENT_MBUTTON;
                        kbd_mouse_event(0, 0, 0, buttons);
                    } else {
                        [NSApp sendEvent:event];
                    }
                    break;
                        
                case NSOtherMouseUp:
                    if (grab) {
                        kbd_mouse_event(0, 0, 0, 0);
                    } else {
                        [NSApp sendEvent: event];
                    }
                    break;
                        
                case NSScrollWheel:
                    if (grab) {
                        int dz = [event deltaY];
                        kbd_mouse_event(0, 0, -dz, 0);
                    }
                    break;
                
                default: [NSApp sendEvent:event];
            }
        }
    } while(event != nil);
}

/*
 ------------------------------------------------------
    cocoa_cleanup
 ------------------------------------------------------
*/

static void cocoa_cleanup(void) 
{

}

/*
 ------------------------------------------------------
    cocoa_display_init
 ------------------------------------------------------
*/

void cocoa_display_init(DisplayState *ds, int full_screen)
{
    ds->dpy_update = cocoa_update;
    ds->dpy_resize = cocoa_resize;
    ds->dpy_refresh = cocoa_refresh;
    
    cocoa_resize(ds, 640, 400);
    
    atexit(cocoa_cleanup);
}

/*
 ------------------------------------------------------
    Interface with Cocoa
 ------------------------------------------------------
*/


/*
 ------------------------------------------------------
    QemuWindow
    Some trick from SDL to use miniwindow
 ------------------------------------------------------
*/
static void QZ_SetPortAlphaOpaque ()
{    
    /* Assume 32 bit if( bpp == 32 )*/
    if ( 1 ) {
    
        uint32_t    *pixels = (uint32_t*) current_ds.data;
        uint32_t    rowPixels = current_ds.linesize / 4;
        uint32_t    i, j;
        
        for (i = 0; i < current_ds.height; i++)
            for (j = 0; j < current_ds.width; j++) {
        
                pixels[ (i * rowPixels) + j ] |= 0xFF000000;
            }
    }
}

@implementation QemuWindow
- (void)miniaturize:(id)sender
{
        
    /* make the alpha channel opaque so anim won't have holes in it */
    QZ_SetPortAlphaOpaque ();
    
    [ super miniaturize:sender ];
    
}
- (void)display
{    
    /* 
        This method fires just before the window deminaturizes from the Dock.
        
        We'll save the current visible surface, let the window manager redraw any
        UI elements, and restore the SDL surface. This way, no expose event 
        is required, and the deminiaturize works perfectly.
    */
    
    /* make sure pixels are fully opaque */
    QZ_SetPortAlphaOpaque ();
    
    /* save current visible SDL surface */
    [ self cacheImageInRect:[ qd_view frame ] ];
    
    /* let the window manager redraw controls, border, etc */
    [ super display ];
    
    /* restore visible SDL surface */
    [ self restoreCachedImage ];
}

@end


/*
 ------------------------------------------------------
    QemuCocoaGUIController
    NSApp's delegate - indeed main object
 ------------------------------------------------------
*/

@interface QemuCocoaGUIController : NSObject
{
}
- (void)applicationDidFinishLaunching: (NSNotification *) note;
- (void)applicationWillTerminate:(NSNotification *)aNotification;

- (void)openPanelDidEnd:(NSOpenPanel *)sheet returnCode:(int)returnCode contextInfo:(void *)contextInfo;

- (void)startEmulationWithArgc:(int)argc argv:(char**)argv;
@end

@implementation QemuCocoaGUIController
/* Called when the internal event loop has just started running */
- (void)applicationDidFinishLaunching: (NSNotification *) note
{

    /* Display an open dialog box if no argument were passed or
       if qemu was launched from the finder ( the Finder passes "-psn" ) */

    if( gArgc <= 1 || strncmp (gArgv[1], "-psn", 4) == 0)
    {
        NSOpenPanel *op = [[NSOpenPanel alloc] init];
        
        cocoa_resize(&current_ds, 640, 400);
        
        [op setPrompt:@"Boot image"];
        
        [op setMessage:@"Select the disk image you want to boot.\n\nHit the \"Cancel\" button to quit"];
        
        [op beginSheetForDirectory:nil file:nil types:[NSArray arrayWithObjects:@"img",@"iso",@"dmg",@"qcow",@"cow",@"cloop",@"vmdk",nil]
              modalForWindow:window modalDelegate:self
              didEndSelector:@selector(openPanelDidEnd:returnCode:contextInfo:) contextInfo:NULL];
    }
    else
    {
        /* or Launch Qemu, with the global args */
        [self startEmulationWithArgc:gArgc argv:gArgv];
    }
}

- (void)applicationWillTerminate:(NSNotification *)aNotification
{
    printf("Application will terminate\n");
    qemu_system_shutdown_request();
    /* In order to avoid a crash */
    exit(0);
}

- (void)openPanelDidEnd:(NSOpenPanel *)sheet returnCode:(int)returnCode contextInfo:(void *)contextInfo
{
    if(returnCode == NSCancelButton)
    {
        exit(0);
    }
    
    if(returnCode == NSOKButton)
    {
        char *bin = "qemu";
        char *img = (char*)[ [ sheet filename ] cString];
        
        char **argv = (char**)malloc( sizeof(char*)*3 );
        
        asprintf(&argv[0], "%s", bin);
        asprintf(&argv[1], "-hda");
        asprintf(&argv[2], "%s", img);
        
        printf("Using argc %d argv %s -hda %s\n", 3, bin, img);
        
        [self startEmulationWithArgc:3 argv:(char**)argv];
    }
}

- (void)startEmulationWithArgc:(int)argc argv:(char**)argv
{
    int status;
    /* Launch Qemu */
    printf("starting qemu...\n");
    status = qemu_main (argc, argv);
    exit(status);
}
@end

/*
 ------------------------------------------------------
    Application Creation
 ------------------------------------------------------
*/

/* Dock Connection */
typedef struct CPSProcessSerNum
{
        UInt32                lo;
        UInt32                hi;
} CPSProcessSerNum;

extern OSErr    CPSGetCurrentProcess( CPSProcessSerNum *psn);
extern OSErr    CPSEnableForegroundOperation( CPSProcessSerNum *psn, UInt32 _arg2, UInt32 _arg3, UInt32 _arg4, UInt32 _arg5);
extern OSErr    CPSSetFrontProcess( CPSProcessSerNum *psn);

/* Menu Creation */
static void setApplicationMenu(void)
{
    /* warning: this code is very odd */
    NSMenu *appleMenu;
    NSMenuItem *menuItem;
    NSString *title;
    NSString *appName;
    
    appName = @"Qemu";
    appleMenu = [[NSMenu alloc] initWithTitle:@""];
    
    /* Add menu items */
    title = [@"About " stringByAppendingString:appName];
    [appleMenu addItemWithTitle:title action:@selector(orderFrontStandardAboutPanel:) keyEquivalent:@""];

    [appleMenu addItem:[NSMenuItem separatorItem]];

    title = [@"Hide " stringByAppendingString:appName];
    [appleMenu addItemWithTitle:title action:@selector(hide:) keyEquivalent:@"h"];

    menuItem = (NSMenuItem *)[appleMenu addItemWithTitle:@"Hide Others" action:@selector(hideOtherApplications:) keyEquivalent:@"h"];
    [menuItem setKeyEquivalentModifierMask:(NSAlternateKeyMask|NSCommandKeyMask)];

    [appleMenu addItemWithTitle:@"Show All" action:@selector(unhideAllApplications:) keyEquivalent:@""];

    [appleMenu addItem:[NSMenuItem separatorItem]];

    title = [@"Quit " stringByAppendingString:appName];
    [appleMenu addItemWithTitle:title action:@selector(terminate:) keyEquivalent:@"q"];

    
    /* Put menu into the menubar */
    menuItem = [[NSMenuItem alloc] initWithTitle:@"" action:nil keyEquivalent:@""];
    [menuItem setSubmenu:appleMenu];
    [[NSApp mainMenu] addItem:menuItem];

    /* Tell the application object that this is now the application menu */
    [NSApp setAppleMenu:appleMenu];

    /* Finally give up our references to the objects */
    [appleMenu release];
    [menuItem release];
}

/* Create a window menu */
static void setupWindowMenu(void)
{
    NSMenu      *windowMenu;
    NSMenuItem  *windowMenuItem;
    NSMenuItem  *menuItem;

    windowMenu = [[NSMenu alloc] initWithTitle:@"Window"];
    
    /* "Minimize" item */
    menuItem = [[NSMenuItem alloc] initWithTitle:@"Minimize" action:@selector(performMiniaturize:) keyEquivalent:@"m"];
    [windowMenu addItem:menuItem];
    [menuItem release];
    
    /* Put menu into the menubar */
    windowMenuItem = [[NSMenuItem alloc] initWithTitle:@"Window" action:nil keyEquivalent:@""];
    [windowMenuItem setSubmenu:windowMenu];
    [[NSApp mainMenu] addItem:windowMenuItem];
    
    /* Tell the application object that this is now the window menu */
    [NSApp setWindowsMenu:windowMenu];

    /* Finally give up our references to the objects */
    [windowMenu release];
    [windowMenuItem release];
}

static void CustomApplicationMain(void)
{
    NSAutoreleasePool   *pool = [[NSAutoreleasePool alloc] init];
    QemuCocoaGUIController *gui_controller;
    CPSProcessSerNum PSN;
    
    [NSApplication sharedApplication];
    
    if (!CPSGetCurrentProcess(&PSN))
        if (!CPSEnableForegroundOperation(&PSN,0x03,0x3C,0x2C,0x1103))
            if (!CPSSetFrontProcess(&PSN))
                [NSApplication sharedApplication];
                
    /* Set up the menubar */
    [NSApp setMainMenu:[[NSMenu alloc] init]];
    setApplicationMenu();
    setupWindowMenu();

    /* Create SDLMain and make it the app delegate */
    gui_controller = [[QemuCocoaGUIController alloc] init];
    [NSApp setDelegate:gui_controller];
    
    /* Start the main event loop */
    [NSApp run];
    
    [gui_controller release];
    [pool release];
}

/* Real main of qemu-cocoa */
int main(int argc, char **argv)
{
    gArgc = argc;
    gArgv = argv;

    CustomApplicationMain();

    return 0;
}
