Annotation of hatari/src/gui-osx/SDLMain.m, revision 1.1.1.10

1.1       root        1: /*   SDLMain.m - main entry point for our Cocoa-ized SDL app
                      2:        Initial Version: Darrell Walisser <[email protected]>
                      3:        Non-NIB-Code & other changes: Max Horn <[email protected]>
                      4: 
                      5:     Feel free to customize this file to suit your needs
                      6: */
                      7: 
1.1.1.6   root        8: #include "SDL.h"
                      9: #include "SDLMain.h"
                     10: #include <sys/param.h> /* for MAXPATHLEN */
                     11: #include <unistd.h>
                     12: 
                     13: // for Hatari
1.1       root       14: 
                     15: #include "dialog.h"
                     16: #include "floppy.h"
                     17: #include "reset.h"
                     18: #include "screenSnapShot.h"
                     19: #include "memorySnapShot.h"
                     20: #include "sound.h"
1.1.1.7   root       21: #include "screen.h"
                     22: #include "PrefsController.h"
                     23: #include "Shared.h"
1.1.1.6   root       24: #include "video.h"
                     25: #include "avi_record.h"
1.1.1.7   root       26: #include "../debug/debugui.h"
                     27: #include "clocks_timings.h"
1.1.1.10! root       28: #include "change.h"
1.1.1.6   root       29: 
                     30: // for Hatari
                     31: 
                     32: 
                     33: /* For some reaon, Apple removed setAppleMenu from the headers in 10.4,
                     34:  but the method still is there and works. To avoid warnings, we declare
                     35:  it ourselves here. */
                     36: @interface NSApplication(SDL_Missing_Methods)
                     37: - (void)setAppleMenu:(NSMenu *)menu;
                     38: @end
                     39: 
                     40: /* Use this flag to determine whether we use SDLMain.nib or not */
                     41: #define                SDL_USE_NIB_FILE        1
                     42: 
                     43: /* Use this flag to determine whether we use CPS (docking) or not */
                     44: #define                SDL_USE_CPS             1
                     45: #ifdef SDL_USE_CPS
                     46: /* Portions of CPS.h */
                     47: typedef struct CPSProcessSerNum
                     48: {
                     49:        UInt32          lo;
                     50:        UInt32          hi;
                     51: } CPSProcessSerNum;
                     52: 
                     53: extern OSErr   CPSGetCurrentProcess( CPSProcessSerNum *psn);
                     54: extern OSErr   CPSEnableForegroundOperation( CPSProcessSerNum *psn, UInt32 _arg2, UInt32 _arg3, UInt32 _arg4, UInt32 _arg5);
                     55: extern OSErr   CPSSetFrontProcess( CPSProcessSerNum *psn);
                     56: 
                     57: #endif /* SDL_USE_CPS */
1.1       root       58: 
                     59: static int    gArgc;
                     60: static char  **gArgv;
                     61: static BOOL   gFinderLaunch;
1.1.1.6   root       62: static BOOL   gCalledAppMainline = FALSE;
                     63: 
                     64: static NSString *getApplicationName(void)
                     65: {
                     66:     const NSDictionary *dict;
                     67:     NSString *appName = 0;
1.1       root       68: 
1.1.1.6   root       69:     /* Determine the application name */
                     70:     dict = (const NSDictionary *)CFBundleGetInfoDictionary(CFBundleGetMainBundle());
                     71:     if (dict)
                     72:         appName = [dict objectForKey: @"CFBundleName"];
                     73:     
                     74:     if (![appName length])
                     75:         appName = [[NSProcessInfo processInfo] processName];
                     76: 
                     77:     return appName;
                     78: }
                     79: 
                     80: #if SDL_USE_NIB_FILE
                     81: /* A helper category for NSString */
                     82: @interface NSString (ReplaceSubString)
                     83: - (NSString *)stringByReplacingRange:(NSRange)aRange with:(NSString *)aString;
1.1       root       84: @end
1.1.1.6   root       85: #endif
1.1       root       86: 
1.1.1.6   root       87: @interface NSApplication (SDLApplication)
                     88: @end
                     89: 
                     90: @implementation NSApplication (SDLApplication)
1.1       root       91: /* Invoked from the Quit menu item */
                     92: - (void)terminate:(id)sender
                     93: {
                     94:     /* Post a SDL_QUIT event */
                     95:     SDL_Event event;
                     96:     event.type = SDL_QUIT;
                     97:     SDL_PushEvent(&event);
                     98: }
                     99: @end
                    100: 
                    101: /* The main class of the application, the application's delegate */
                    102: @implementation SDLMain
                    103: 
1.1.1.7   root      104: 
1.1.1.6   root      105: /* Set the working directory to the .app's parent directory */
                    106: - (void) setupWorkingDirectory:(BOOL)shouldChdir
                    107: {
                    108:     if (shouldChdir)
                    109:     {
                    110:         char parentdir[MAXPATHLEN];
                    111:         CFURLRef url = CFBundleCopyBundleURL(CFBundleGetMainBundle());
                    112:         CFURLRef url2 = CFURLCreateCopyDeletingLastPathComponent(0, url);
                    113:         if (CFURLGetFileSystemRepresentation(url2, 1, (UInt8 *)parentdir, MAXPATHLEN)) {
                    114:             chdir(parentdir);   /* chdir to the binary app's parent */
                    115:         }
                    116:         CFRelease(url);
                    117:         CFRelease(url2);
                    118:     }
                    119: }
                    120: 
                    121: #if SDL_USE_NIB_FILE
                    122: 
                    123: /* Fix menu to contain the real app name instead of "SDL App" */
                    124: - (void)fixMenu:(NSMenu *)aMenu withAppName:(NSString *)appName
                    125: {
                    126:     NSRange aRange;
                    127:     NSEnumerator *enumerator;
                    128:     NSMenuItem *menuItem;
                    129: 
                    130:     aRange = [[aMenu title] rangeOfString:@"SDL App"];
                    131:     if (aRange.length != 0)
                    132:         [aMenu setTitle: [[aMenu title] stringByReplacingRange:aRange with:appName]];
                    133: 
                    134:     enumerator = [[aMenu itemArray] objectEnumerator];
                    135:     while ((menuItem = [enumerator nextObject]))
                    136:     {
                    137:         aRange = [[menuItem title] rangeOfString:@"SDL App"];
                    138:         if (aRange.length != 0)
                    139:             [menuItem setTitle: [[menuItem title] stringByReplacingRange:aRange with:appName]];
                    140:         if ([menuItem hasSubmenu])
                    141:             [self fixMenu:[menuItem submenu] withAppName:appName];
                    142:     }
                    143: }
                    144: 
                    145: #else
                    146: 
                    147: static void setApplicationMenu(void)
                    148: {
                    149:     /* warning: this code is very odd */
                    150:     NSMenu *appleMenu;
                    151:     NSMenuItem *menuItem;
                    152:     NSString *title;
                    153:     NSString *appName;
                    154:     
                    155:     appName = getApplicationName();
                    156:     appleMenu = [[NSMenu alloc] initWithTitle:@""];
                    157:     
                    158:     /* Add menu items */
                    159:     title = [@"About " stringByAppendingString:appName];
                    160:     [appleMenu addItemWithTitle:title action:@selector(orderFrontStandardAboutPanel:) keyEquivalent:@""];
                    161: 
                    162:     [appleMenu addItem:[NSMenuItem separatorItem]];
                    163: 
                    164:     title = [@"Hide " stringByAppendingString:appName];
                    165:     [appleMenu addItemWithTitle:title action:@selector(hide:) keyEquivalent:@"h"];
                    166: 
                    167:     menuItem = (NSMenuItem *)[appleMenu addItemWithTitle:@"Hide Others" action:@selector(hideOtherApplications:) keyEquivalent:@"h"];
                    168:     [menuItem setKeyEquivalentModifierMask:(NSAlternateKeyMask|NSCommandKeyMask)];
                    169: 
                    170:     [appleMenu addItemWithTitle:@"Show All" action:@selector(unhideAllApplications:) keyEquivalent:@""];
                    171: 
                    172:     [appleMenu addItem:[NSMenuItem separatorItem]];
                    173: 
                    174:     title = [@"Quit " stringByAppendingString:appName];
                    175:     [appleMenu addItemWithTitle:title action:@selector(terminate:) keyEquivalent:@"q"];
                    176: 
                    177:     
                    178:     /* Put menu into the menubar */
                    179:     menuItem = [[NSMenuItem alloc] initWithTitle:@"" action:nil keyEquivalent:@""];
                    180:     [menuItem setSubmenu:appleMenu];
                    181:     [[NSApp mainMenu] addItem:menuItem];
                    182: 
                    183:     /* Tell the application object that this is now the application menu */
                    184:     [NSApp setAppleMenu:appleMenu];
                    185: 
                    186:     /* Finally give up our references to the objects */
                    187:     [appleMenu release];
                    188:     [menuItem release];
                    189: }
                    190: 
                    191: /* Create a window menu */
                    192: static void setupWindowMenu(void)
                    193: {
                    194:     NSMenu      *windowMenu;
                    195:     NSMenuItem  *windowMenuItem;
                    196:     NSMenuItem  *menuItem;
                    197: 
                    198:     windowMenu = [[NSMenu alloc] initWithTitle:@"Window"];
                    199:     
                    200:     /* "Minimize" item */
                    201:     menuItem = [[NSMenuItem alloc] initWithTitle:@"Minimize" action:@selector(performMiniaturize:) keyEquivalent:@"m"];
                    202:     [windowMenu addItem:menuItem];
                    203:     [menuItem release];
                    204:     
                    205:     /* Put menu into the menubar */
                    206:     windowMenuItem = [[NSMenuItem alloc] initWithTitle:@"Window" action:nil keyEquivalent:@""];
                    207:     [windowMenuItem setSubmenu:windowMenu];
                    208:     [[NSApp mainMenu] addItem:windowMenuItem];
                    209:     
                    210:     /* Tell the application object that this is now the window menu */
                    211:     [NSApp setWindowsMenu:windowMenu];
                    212: 
                    213:     /* Finally give up our references to the objects */
                    214:     [windowMenu release];
                    215:     [windowMenuItem release];
                    216: }
                    217: 
                    218: /* Replacement for NSApplicationMain */
                    219: static void CustomApplicationMain (int argc, char **argv)
                    220: {
                    221:     NSAutoreleasePool  *pool = [[NSAutoreleasePool alloc] init];
                    222:     SDLMain                            *sdlMain;
                    223: 
                    224:     /* Ensure the application object is initialised */
                    225:     [NSApplication sharedApplication];
                    226:     
                    227: #ifdef SDL_USE_CPS
                    228:     {
                    229:         CPSProcessSerNum PSN;
                    230:         /* Tell the dock about us */
                    231:         if (!CPSGetCurrentProcess(&PSN))
                    232:             if (!CPSEnableForegroundOperation(&PSN,0x03,0x3C,0x2C,0x1103))
                    233:                 if (!CPSSetFrontProcess(&PSN))
                    234:                     [NSApplication sharedApplication];
                    235:     }
                    236: #endif /* SDL_USE_CPS */
                    237: 
                    238:     /* Set up the menubar */
                    239:     [NSApp setMainMenu:[[NSMenu alloc] init]];
                    240:     setApplicationMenu();
                    241:     setupWindowMenu();
                    242: 
                    243:     /* Create SDLMain and make it the app delegate */
                    244:     sdlMain = [[SDLMain alloc] init];
                    245:     [NSApp setDelegate:sdlMain];
                    246:     
                    247:     /* Start the main event loop */
                    248:     [NSApp run];
                    249:     
                    250:     [sdlMain release];
                    251:     [pool release];
                    252: }
                    253: 
                    254: #endif
                    255: 
                    256: 
                    257: /*
                    258:  * Catch document open requests...this lets us notice files when the app
                    259:  *  was launched by double-clicking a document, or when a document was
                    260:  *  dragged/dropped on the app's icon. You need to have a
                    261:  *  CFBundleDocumentsType section in your Info.plist to get this message,
                    262:  *  apparently.
                    263:  *
                    264:  * Files are added to gArgv, so to the app, they'll look like command line
                    265:  *  arguments. Previously, apps launched from the finder had nothing but
                    266:  *  an argv[0].
                    267:  *
                    268:  * This message may be received multiple times to open several docs on launch.
                    269:  *
                    270:  * This message is ignored once the app's mainline has been called.
                    271:  */
                    272: - (BOOL)application:(NSApplication *)theApplication openFile:(NSString *)filename
                    273: {
                    274:     const char *temparg;
                    275:     size_t arglen;
                    276:     char *arg;
                    277:     char **newargv;
                    278: 
                    279:     if (!gFinderLaunch)  /* MacOS is passing command line args. */
                    280:         return FALSE;
                    281: 
                    282:     if (gCalledAppMainline)  /* app has started, ignore this document. */
                    283:         return FALSE;
                    284: 
                    285:     temparg = [filename UTF8String];
                    286:     arglen = SDL_strlen(temparg) + 1;
                    287:     arg = (char *) SDL_malloc(arglen);
                    288:     if (arg == NULL)
                    289:         return FALSE;
                    290: 
                    291:     newargv = (char **) realloc(gArgv, sizeof (char *) * (gArgc + 2));
                    292:     if (newargv == NULL)
                    293:     {
                    294:         SDL_free(arg);
                    295:         return FALSE;
                    296:     }
                    297:     gArgv = newargv;
                    298: 
                    299:     SDL_strlcpy(arg, temparg, arglen);
                    300:     gArgv[gArgc++] = arg;
                    301:     gArgv[gArgc] = NULL;
                    302:     return TRUE;
                    303: }
                    304: 
                    305: 
                    306: /* Called when the internal event loop has just started running */
                    307: - (void) applicationDidFinishLaunching: (NSNotification *) note
                    308: {
                    309:     int status;
                    310: 
                    311:     /* Set the working directory to the .app's parent directory */
                    312:     [self setupWorkingDirectory:gFinderLaunch];
                    313: 
                    314: #if SDL_USE_NIB_FILE
                    315:     /* Set the main menu to contain the real app name instead of "SDL App" */
                    316:     [self fixMenu:[NSApp mainMenu] withAppName:getApplicationName()];
                    317: #endif
                    318: 
                    319:     /* Hand off to main application code */
                    320:     gCalledAppMainline = TRUE;
                    321:     status = SDL_main (gArgc, gArgv);
                    322: 
                    323:     /* We're done, thank you for playing */
                    324:     exit(status);
                    325: }
                    326: 
                    327: // Hatari Stuff
1.1       root      328: - (IBAction)prefsMenu:(id)sender
                    329: {
                    330:        static int in_propdialog =  0;
1.1.1.6   root      331: 
1.1       root      332:        if (in_propdialog)
                    333:                return;
                    334:        ++in_propdialog;
1.1.1.6   root      335:        Dialog_DoProperty();
1.1       root      336:        --in_propdialog;
                    337: }
                    338: 
1.1.1.9   root      339: - (IBAction) openPreferences:(id)sender 
                    340: {
                    341:        [[PrefsController prefs] loadPrefs:sender];
                    342: }
                    343: 
                    344: 
1.1.1.6   root      345: - (IBAction)debugUI:(id)sender
                    346: {
1.1.1.8   root      347:        DebugUI(REASON_USER);
1.1.1.6   root      348: }
                    349: 
1.1       root      350: - (IBAction)warmReset:(id)sender
                    351: {
                    352:        int b;
1.1.1.6   root      353: 
                    354:        b = NSRunAlertPanel (
                    355:                                                 NSLocalizedStringFromTable(@"Warm reset",@"Localizable",@"comment"),
                    356:                                                 NSLocalizedStringFromTable(@"Really reset the emulator?",@"Localizable",@"comment"),
                    357:                                                 NSLocalizedStringFromTable(@"OK",@"Localizable",@"comment"), 
                    358:                                                 NSLocalizedStringFromTable(@"Cancel",@"Localizable",@"comment"), nil);
1.1       root      359:        //printf("b=%i\n",b);
                    360:        if (b == 1)
                    361:                Reset_Warm();
1.1.1.10! root      362: } 
1.1       root      363: 
                    364: - (IBAction)coldReset:(id)sender
                    365: {
                    366:        int b;
1.1.1.6   root      367: 
                    368:        b = NSRunAlertPanel (
                    369:                                                 NSLocalizedStringFromTable(@"Cold reset!",@"Localizable",@"comment"), 
                    370:                                                 NSLocalizedStringFromTable(@"Really reset the emulator?",@"Localizable",@"comment") ,
                    371:                                                 NSLocalizedStringFromTable(@"OK",@"Localizable",@"comment"), 
                    372:                                                 NSLocalizedStringFromTable(@"Cancel",@"Localizable",@"comment"), nil);
1.1       root      373:        //printf("b=%i\n",b);
                    374:        if (b == 1)
                    375:                Reset_Cold();
                    376: }
                    377: 
                    378: - (IBAction)insertDiskA:(id)sender
                    379: {
1.1.1.6   root      380:        NSString *path = nil;
                    381:        NSOpenPanel *openPanel = [ NSOpenPanel openPanel ];
                    382: 
                    383:        if ( [ openPanel runModalForDirectory:nil
                    384:                                                                         file:@"SavedGame" types:nil ] )
                    385:        {
                    386:                path = [ [ openPanel filenames ] objectAtIndex:0 ];
                    387:        }
                    388: 
1.1       root      389:        if (path != nil)
                    390:        {
                    391:                // Make a non-const C string out of it
1.1.1.6   root      392:                const char* constSzPath = [path cStringUsingEncoding:NSASCIIStringEncoding];
1.1       root      393:                size_t cbPath = strlen(constSzPath) + 1;
                    394:                char szPath[cbPath];
1.1.1.6   root      395:                strncpy(szPath, constSzPath, cbPath);
1.1.1.3   root      396: 
                    397:                Floppy_SetDiskFileName(0, szPath, NULL);
                    398:                Floppy_InsertDiskIntoDrive(0);
1.1       root      399:        }
                    400: }
                    401: 
                    402: - (IBAction)insertDiskB:(id)sender
                    403: {
1.1.1.6   root      404:        NSString *path = nil;
                    405:        NSOpenPanel *openPanel = [ NSOpenPanel openPanel ];
                    406: 
                    407:        if ( [ openPanel runModalForDirectory:nil
                    408:                                                                         file:@"SavedGame" types:nil ] )
                    409:        {
                    410:                path = [ [ openPanel filenames ] objectAtIndex:0 ];
                    411:        }
                    412: 
1.1       root      413:        if (path != nil)
                    414:        {
                    415:                // Make a non-const C string out of it
1.1.1.6   root      416:                const char* constSzPath = [path cStringUsingEncoding:NSASCIIStringEncoding];
1.1       root      417:                size_t cbPath = strlen(constSzPath) + 1;
                    418:                char szPath[cbPath];
                    419:                strncpy(szPath, constSzPath, cbPath);   
1.1.1.6   root      420: 
1.1.1.3   root      421:                Floppy_SetDiskFileName(1, szPath, NULL);
                    422:                Floppy_InsertDiskIntoDrive(1);
1.1       root      423:        }
                    424: }
                    425: 
                    426: /*-----------------------------------------------------------------------*/
                    427: /*
1.1.1.6   root      428:  Controls the enabled state of the menu items
                    429:  */
1.1       root      430: - (BOOL)validateMenuItem:(NSMenuItem*)item
                    431: {
                    432:        if (item == beginCaptureAnim)
                    433:        {
1.1.1.6   root      434:                return !Avi_AreWeRecording();
1.1       root      435:        }
                    436:        if (item == endCaptureAnim)
                    437:        {
1.1.1.6   root      438:                return Avi_AreWeRecording();
1.1       root      439:        }
                    440:        if (item == beginCaptureSound)
                    441:        {
                    442:                return !Sound_AreWeRecording();
                    443:        }
                    444:        if (item == endCaptureSound)
                    445:        {
                    446:                return Sound_AreWeRecording();
                    447:        }
                    448: 
                    449:        return YES;
                    450: }
                    451: 
1.1.1.7   root      452: - (NSString*)displayFileSelection:(const char*)pathInParams preferredFileName:(NSString*)preferredFileName allowedExtensions:(NSArray*)allowedExtensions
1.1       root      453: {
1.1.1.7   root      454:        
1.1       root      455:        // Get the path from the user settings
1.1.1.7   root      456:        NSString *preferredPath = [[NSString stringWithCString:(pathInParams) encoding:NSASCIIStringEncoding] stringByAbbreviatingWithTildeInPath];
                    457:        
1.1       root      458:        // Determine the directory and filename
                    459:        NSString *directoryToOpen;
                    460:        NSString *fileToPreselect;
                    461:        if ((preferredPath != nil) && ([preferredPath length] > 0))
                    462:        {
                    463:                // There is existing path: we will open its directory with its file pre-selected.
                    464:                directoryToOpen = [preferredPath stringByDeletingLastPathComponent];
                    465:                fileToPreselect = [preferredPath lastPathComponent];
                    466:        }
                    467:        else
                    468:        {
                    469:                // Currently no path: we will open the user's directory with no file selected.
                    470:                directoryToOpen = [@"~" stringByExpandingTildeInPath];
1.1.1.7   root      471:                fileToPreselect = preferredFileName;
1.1       root      472:        }       
1.1.1.7   root      473:        
1.1       root      474:        // Create and configure a SavePanel for choosing what file to write
                    475:        NSSavePanel *savePanel = [NSSavePanel savePanel];
1.1.1.7   root      476:        [savePanel setAllowedFileTypes:allowedExtensions];
1.1       root      477:        [savePanel setExtensionHidden:NO];
1.1.1.7   root      478:        NSString* extensionList = [allowedExtensions componentsJoinedByString:@" or a ."];
1.1       root      479:        
1.1.1.7   root      480:        [savePanel setMessage:[NSString stringWithFormat:@"Please specify a .%@ file",extensionList]];  // TODO: Move to localizable resources  
1.1       root      481:        // Run the SavePanel, then check if the user clicked OK and selected at least one file
1.1.1.6   root      482:        if (NSFileHandlingPanelOKButton == [savePanel runModalForDirectory:directoryToOpen file:fileToPreselect] )
1.1.1.7   root      483:                return [[savePanel URL] path];
                    484:        return nil;
                    485: }
                    486: 
                    487: - (IBAction)captureScreen:(id)sender
                    488: {
                    489:        GuiOsx_Pause();
                    490:        ScreenSnapShot_SaveScreen();
                    491:        GuiOsx_Resume();
                    492: }
                    493: 
                    494: - (IBAction)captureAnimation:(id)sender
                    495: {
                    496:        GuiOsx_Pause();
                    497:        if(!Avi_AreWeRecording()) {
                    498:                NSString* path = [self displayFileSelection:ConfigureParams.Video.AviRecordFile preferredFileName:@"hatari.avi" 
                    499:                                                                         allowedExtensions:[NSArray arrayWithObjects:@"avi", nil]];
1.1       root      500:                
1.1.1.7   root      501:                if(path) {
                    502:                        GuiOsx_ExportPathString(path, ConfigureParams.Video.AviRecordFile, sizeof(ConfigureParams.Video.AviRecordFile));
                    503:                        Avi_StartRecording ( ConfigureParams.Video.AviRecordFile , ConfigureParams.Screen.bCrop ,
                    504:                                        ConfigureParams.Video.AviRecordFps == 0 ?
                    505:                                        ClocksTimings_GetVBLPerSec ( ConfigureParams.System.nMachineType , nScreenRefreshRate ) :
                    506:                                        (Uint32)ConfigureParams.Video.AviRecordFps << CLOCKS_TIMINGS_SHIFT_VBL ,
                    507:                                1 << CLOCKS_TIMINGS_SHIFT_VBL ,
                    508:                                ConfigureParams.Video.AviRecordVcodec );
                    509:                }
1.1.1.6   root      510:                
1.1.1.7   root      511:        } else {
                    512:                Avi_StopRecording();
1.1.1.6   root      513:        }
1.1.1.7   root      514:        GuiOsx_Resume();
                    515: }
1.1       root      516: 
1.1.1.7   root      517: - (IBAction)endCaptureAnimation:(id)sender
                    518: {
                    519:        //?
                    520: }
                    521: 
                    522: - (IBAction)captureSound:(id)sender
                    523: {
                    524:        GuiOsx_Pause();
                    525:        NSString* path = [self displayFileSelection:ConfigureParams.Sound.szYMCaptureFileName preferredFileName:@"hatari.wav" 
                    526:                                                                 allowedExtensions:[NSArray arrayWithObjects:@"ym", @"wav", nil]];
                    527:        if(path) {
                    528:                GuiOsx_ExportPathString(path, ConfigureParams.Sound.szYMCaptureFileName, sizeof(ConfigureParams.Sound.szYMCaptureFileName));
                    529:                Sound_BeginRecording(ConfigureParams.Sound.szYMCaptureFileName);
                    530:        }
1.1.1.5   root      531:        GuiOsx_Resume();
1.1       root      532: }
                    533: 
                    534: - (IBAction)endCaptureSound:(id)sender
                    535: {
1.1.1.5   root      536:        GuiOsx_Pause();
1.1       root      537:        Sound_EndRecording();
1.1.1.5   root      538:        GuiOsx_Resume();
1.1       root      539: }
                    540: 
                    541: - (IBAction)saveMemorySnap:(id)sender
                    542: {
1.1.1.5   root      543:        GuiOsx_Pause();
1.1       root      544: 
1.1.1.7   root      545:        NSString* path = [self displayFileSelection:ConfigureParams.Memory.szMemoryCaptureFileName preferredFileName:@"hatari.sav" 
                    546:                                                                 allowedExtensions:[NSArray arrayWithObjects:@"sav",nil]];
                    547:        if(path) {
1.1       root      548:                GuiOsx_ExportPathString(path, ConfigureParams.Memory.szMemoryCaptureFileName, sizeof(ConfigureParams.Memory.szMemoryCaptureFileName));
1.1.1.2   root      549:                MemorySnapShot_Capture(ConfigureParams.Memory.szMemoryCaptureFileName, TRUE);
1.1.1.6   root      550:        }
1.1.1.7   root      551:        
1.1.1.5   root      552:        GuiOsx_Resume();
1.1       root      553: }
                    554: 
                    555: - (IBAction)restoreMemorySnap:(id)sender
                    556: {
1.1.1.5   root      557:        GuiOsx_Pause();
1.1       root      558: 
                    559:        // Create and configure an OpenPanel
1.1.1.6   root      560:        NSOpenPanel *openPanel = [NSOpenPanel openPanel];
1.1       root      561: 
                    562:        // Get the path from the user settings
1.1.1.6   root      563:        NSString *oldPath = [NSString stringWithCString:(ConfigureParams.Memory.szMemoryCaptureFileName) encoding:NSASCIIStringEncoding];
1.1       root      564: 
                    565:        // Determine the directory and filename
                    566:        NSString *directoryToOpen;
                    567:        NSString *fileToPreselect;
                    568:        if ((oldPath != nil) && ([oldPath length] > 0))
                    569:        {
                    570:                // There is existing path: we will open its directory with its file pre-selected.
                    571:                directoryToOpen = [oldPath stringByDeletingLastPathComponent];
                    572:                fileToPreselect = [oldPath lastPathComponent];
                    573:        }
                    574:        else
                    575:        {
                    576:                // Currently no path: we will open the user's directory with no file selected.
                    577:                directoryToOpen = [@"~" stringByExpandingTildeInPath];
                    578:                fileToPreselect = nil;
                    579:        }
1.1.1.6   root      580: 
1.1       root      581:        // Run the OpenPanel, then check if the user clicked OK and selected at least one file
1.1.1.6   root      582:        if ( (NSOKButton == [openPanel runModalForDirectory:directoryToOpen file:fileToPreselect types:nil] )
1.1       root      583:            && ([[openPanel filenames] count] > 0) )
                    584:        {
                    585:                // Get the path to the selected file
                    586:                NSString *path = [[openPanel filenames] objectAtIndex:0];
                    587:                
                    588:                // Perform the memory snapshot load
1.1.1.6   root      589:                MemorySnapShot_Restore([path cStringUsingEncoding:NSASCIIStringEncoding], TRUE);
                    590:        }
                    591: 
1.1.1.5   root      592:        GuiOsx_Resume();
1.1       root      593: }
                    594: 
                    595: - (IBAction)doFullScreen:(id)sender
                    596: {
                    597:        // A call to Screen_EnterFullScreen() would be required, but this causes a crash when using SDL runtime 1.2.11, probably due to conflicts between Cocoa and SDL.
                    598:        // Therefore we simulate the fullscreen key press instead
                    599:        
                    600:        SDL_KeyboardEvent event;
1.1.1.6   root      601:        event.type = SDL_KEYDOWN;
                    602:        event.which = 0;
                    603:        event.state = SDL_PRESSED;
                    604:        event.keysym.sym = SDLK_F11;
                    605:        SDL_PushEvent((SDL_Event*)&event);      // Send the F11 key press
                    606:        event.type = SDL_KEYUP;
                    607:        event.state = SDL_RELEASED;
                    608:        SDL_PushEvent((SDL_Event*)&event);      // Send the F11 key release
1.1       root      609: }
                    610: 
1.1.1.9   root      611: 
1.1       root      612: - (IBAction)help:(id)sender
                    613: {
1.1.1.10! root      614: NSString *l_aide ;
        !           615:        
        !           616:        l_aide = [[NSBundle mainBundle] pathForResource:@"manual" ofType:@"html" inDirectory:@"AideHatari"] ;
        !           617:        
        !           618:        if (![[NSWorkspace sharedWorkspace] openFile:l_aide withApplication:@"HelpViewer"])
        !           619:                if (![[NSWorkspace sharedWorkspace] openFile:l_aide withApplication:@"Help Viewer"])
        !           620:              [[NSWorkspace sharedWorkspace] openFile:l_aide] ;
1.1       root      621: }
                    622: 
1.1.1.10! root      623: - (IBAction)compat:(id)sender
        !           624: {
        !           625: NSString *C_aide ;
        !           626:        
        !           627:        C_aide = [[NSBundle mainBundle] pathForResource:@"compatibility" ofType:@"html" inDirectory:@"AideHatari"] ;
        !           628:        
        !           629:        if (![[NSWorkspace sharedWorkspace] openFile:C_aide withApplication:@"HelpViewer"])
        !           630:                if (![[NSWorkspace sharedWorkspace] openFile:C_aide withApplication:@"Help Viewer"])
        !           631:              [[NSWorkspace sharedWorkspace] openFile:C_aide] ;
        !           632: }
1.1       root      633: 
1.1.1.9   root      634: - (IBAction)openConfig:(id)sender 
                    635: {
                    636:        BOOL applyChanges = true;
                    637:        NSString *ConfigFile = [NSString stringWithCString:(sConfigFileName) encoding:NSASCIIStringEncoding];
                    638:        NSOpenPanel *openPanel = [ NSOpenPanel openPanel ];
                    639:        
                    640:        CNF_PARAMS CurrentParams;
                    641:        
                    642:        
                    643:        // Backup of configuration settings to CurrentParams (which we will only
                    644:        // commit back to the configuration settings if choosing user confirm)
                    645:        CurrentParams = ConfigureParams;
                    646:        
                    647:        GuiOsx_Pause();
                    648:        
                    649:        if ( [ openPanel runModalForDirectory:nil file:ConfigFile types:nil ] )
                    650:        {
                    651:                ConfigFile = [ [ openPanel filenames ] objectAtIndex:0 ];
                    652:        }
                    653:        else
                    654:        {
                    655:                ConfigFile = nil;
                    656:        }
                    657:        
                    658:        //[openPanel release];
                    659:        
                    660:        if (ConfigFile != nil)
                    661:        {
                    662:                // Make a non-const C string out of it
                    663:                const char* constSzPath = [ConfigFile cStringUsingEncoding:NSASCIIStringEncoding];
                    664:                size_t cbPath = strlen(constSzPath) + 1;
                    665:                char szPath[cbPath];
                    666:                strncpy(szPath, constSzPath, cbPath);   
                    667:                
                    668:                // Load the config into ConfigureParams
                    669:                Configuration_Load(szPath);
                    670:                strcpy(sConfigFileName,szPath);
                    671:                // Refresh all the controls to match ConfigureParams
                    672:                
                    673:                if (Change_DoNeedReset(&CurrentParams, &ConfigureParams))
                    674:                {
                    675:                        applyChanges = ( 0 == NSRunAlertPanel (
                    676:                                                                                                   NSLocalizedStringFromTable(@"Reset the emulator",@"Localizable",@"comment"), 
                    677:                                                                                                   NSLocalizedStringFromTable(@"Must be reset",@"Localizable",@"comment"),
                    678:                                                                                                   NSLocalizedStringFromTable(@"Don't reset",@"Localizable",@"comment"), 
                    679:                                                                                                   NSLocalizedStringFromTable(@"Reset",@"Localizable",@"comment"), nil) );
                    680:                }
                    681:                
                    682:                // Commit the new configuration
                    683:                if (applyChanges)
                    684:                {
1.1.1.10! root      685:                        Change_CopyChangedParamsToConfiguration(&CurrentParams, &ConfigureParams, true);
1.1.1.9   root      686:                }
                    687:                else
                    688:                {
                    689:                        ConfigureParams = CurrentParams;
                    690:                }
                    691:                
                    692:                
                    693:        }
                    694:        
                    695:        GuiOsx_Resume();
                    696:        //[ConfigFile release];
1.1       root      697: }
                    698: 
1.1.1.9   root      699: 
1.1.1.6   root      700: - (IBAction)saveConfig:(id)sender {
1.1       root      701: }
                    702: 
                    703: @end
                    704: 
                    705: 
                    706: @implementation NSString (ReplaceSubString)
                    707: 
                    708: - (NSString *)stringByReplacingRange:(NSRange)aRange with:(NSString *)aString
                    709: {
                    710:     unsigned int bufferSize;
                    711:     unsigned int selfLen = [self length];
                    712:     unsigned int aStringLen = [aString length];
                    713:     unichar *buffer;
                    714:     NSRange localRange;
                    715:     NSString *result;
                    716: 
                    717:     bufferSize = selfLen + aStringLen - aRange.length;
1.1.1.6   root      718:     buffer = (unichar *)NSAllocateMemoryPages(bufferSize*sizeof(unichar));
1.1       root      719:     
                    720:     /* Get first part into buffer */
                    721:     localRange.location = 0;
                    722:     localRange.length = aRange.location;
                    723:     [self getCharacters:buffer range:localRange];
                    724:     
                    725:     /* Get middle part into buffer */
                    726:     localRange.location = 0;
                    727:     localRange.length = aStringLen;
                    728:     [aString getCharacters:(buffer+aRange.location) range:localRange];
                    729:      
                    730:     /* Get last part into buffer */
                    731:     localRange.location = aRange.location + aRange.length;
                    732:     localRange.length = selfLen - localRange.location;
                    733:     [self getCharacters:(buffer+aRange.location+aStringLen) range:localRange];
                    734:     
                    735:     /* Build output string */
                    736:     result = [NSString stringWithCharacters:buffer length:bufferSize];
                    737:     
                    738:     NSDeallocateMemoryPages(buffer, bufferSize);
                    739:     
                    740:     return result;
                    741: }
                    742: 
                    743: @end
                    744: 
                    745: 
                    746: 
                    747: #ifdef main
                    748: #  undef main
                    749: #endif
                    750: 
                    751: 
                    752: /* Main entry point to executable - should *not* be SDL_main! */
                    753: int main (int argc, char **argv)
                    754: {
                    755:     /* Copy the arguments into a global variable */
                    756:     /* This is passed if we are launched by double-clicking */
                    757:     if ( argc >= 2 && strncmp (argv[1], "-psn", 4) == 0 ) {
1.1.1.6   root      758:         gArgv = (char **) SDL_malloc(sizeof (char *) * 2);
                    759:         gArgv[0] = argv[0];
                    760:         gArgv[1] = NULL;
1.1       root      761:         gArgc = 1;
1.1.1.6   root      762:         gFinderLaunch = YES;
1.1       root      763:     } else {
1.1.1.6   root      764:         int i;
1.1       root      765:         gArgc = argc;
1.1.1.6   root      766:         gArgv = (char **) SDL_malloc(sizeof (char *) * (argc+1));
                    767:         for (i = 0; i <= argc; i++)
                    768:             gArgv[i] = argv[i];
                    769:         gFinderLaunch = NO;
1.1       root      770:     }
                    771: 
1.1.1.6   root      772: #if SDL_USE_NIB_FILE
1.1.1.7   root      773:     NSApplicationMain (argc, (const char**)argv);
1.1.1.6   root      774: #else
                    775:     CustomApplicationMain (argc, argv);
                    776: #endif
1.1       root      777:     return 0;
                    778: }
1.1.1.6   root      779: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.