Annotation of hatari/src/gui-osx/PrefsController.m, revision 1.1.1.2

1.1       root        1: /*
                      2:   Hatari - PrefsController.m
                      3: 
                      4:   This file is distributed under the GNU Public License, version 2 or at
                      5:   your option any later version. Read the file gpl.txt for details.
                      6: 
                      7:   Preferences window controller implementation file
                      8: 
                      9:   Feb-Mar 2006, Sébastien Molines - Created
1.1.1.2 ! root       10:   Jan 2006, Sébastien Molines - Updated for recent emulator updates
1.1       root       11: */
                     12: 
                     13: // TODO: Set the default paths to MacOS-friendly values
                     14: // TODO: Move hardcoded string to localizable resources (e.g. string "Reset the emulator?")
                     15: 
                     16: 
                     17: #import "PrefsController.h"
                     18: #import "Shared.h"
                     19: 
                     20: #include "main.h"
                     21: #include "configuration.h"
                     22: #include "dialog.h"
                     23: #include "file.h"
                     24: #include "floppy.h"
                     25: #include "screen.h"
                     26: #include "sdlgui.h"
                     27: 
                     28: // Macros to transfer data between Cocoa controls and Hatari data structures
                     29: #define EXPORT_TEXTFIELD(nstextfield, target) GuiOsx_ExportPathString([nstextfield stringValue], target, sizeof((target)))
                     30: #define EXPORT_SWITCH(nsbutton, target) target = ([(nsbutton) state] == NSOnState)
                     31: #define EXPORT_RADIO(nsmatrix, target) target = [[(nsmatrix) selectedCell] tag]
                     32: #define EXPORT_DROPDOWN(nspopupbutton, target) target = [[(nspopupbutton) selectedItem] tag]
                     33: #define IMPORT_TEXTFIELD(nstextfield, source) [(nstextfield) setStringValue:[[NSString stringWithCString:(source)] stringByAbbreviatingWithTildeInPath]]
                     34: #define IMPORT_SWITCH(nsbutton, source) [(nsbutton) setState:((source))? NSOnState : NSOffState]
                     35: #define IMPORT_RADIO(nsmatrix, source) [(nsmatrix) selectCellWithTag:(source)]
                     36: #define IMPORT_DROPDOWN(nspopupbutton, source) [(nspopupbutton) selectItemAtIndex:[(nspopupbutton) indexOfItemWithTag:(source)]]
                     37: 
                     38: // Keys to be listed in the Joysticks dropdowns
                     39: SDLKey Preferences_KeysForJoysticks[] =
                     40: {
                     41:        SDLK_BACKSPACE,
                     42:        SDLK_TAB,
                     43:        SDLK_CLEAR,
                     44:        SDLK_RETURN,
                     45:        SDLK_PAUSE,
                     46:        SDLK_ESCAPE,
                     47:        SDLK_SPACE,
                     48:        SDLK_EXCLAIM,
                     49:        SDLK_QUOTEDBL,
                     50:        SDLK_HASH,
                     51:        SDLK_DOLLAR,
                     52:        SDLK_AMPERSAND,
                     53:        SDLK_QUOTE,
                     54:        SDLK_LEFTPAREN,
                     55:        SDLK_RIGHTPAREN,
                     56:        SDLK_ASTERISK,
                     57:        SDLK_PLUS,
                     58:        SDLK_COMMA,
                     59:        SDLK_MINUS,
                     60:        SDLK_PERIOD,
                     61:        SDLK_SLASH,
                     62:        SDLK_0,
                     63:        SDLK_1,
                     64:        SDLK_2,
                     65:        SDLK_3,
                     66:        SDLK_4,
                     67:        SDLK_5,
                     68:        SDLK_6,
                     69:        SDLK_7,
                     70:        SDLK_8,
                     71:        SDLK_9,
                     72:        SDLK_COLON,
                     73:        SDLK_SEMICOLON,
                     74:        SDLK_LESS,
                     75:        SDLK_EQUALS,
                     76:        SDLK_GREATER,
                     77:        SDLK_QUESTION,
                     78:        SDLK_AT,
                     79:        SDLK_LEFTBRACKET,
                     80:        SDLK_BACKSLASH,
                     81:        SDLK_RIGHTBRACKET,
                     82:        SDLK_CARET,
                     83:        SDLK_UNDERSCORE,
                     84:        SDLK_BACKQUOTE,
                     85:        SDLK_a,
                     86:        SDLK_b,
                     87:        SDLK_c,
                     88:        SDLK_d,
                     89:        SDLK_e,
                     90:        SDLK_f,
                     91:        SDLK_g,
                     92:        SDLK_h,
                     93:        SDLK_i,
                     94:        SDLK_j,
                     95:        SDLK_k,
                     96:        SDLK_l,
                     97:        SDLK_m,
                     98:        SDLK_n,
                     99:        SDLK_o,
                    100:        SDLK_p,
                    101:        SDLK_q,
                    102:        SDLK_r,
                    103:        SDLK_s,
                    104:        SDLK_t,
                    105:        SDLK_u,
                    106:        SDLK_v,
                    107:        SDLK_w,
                    108:        SDLK_x,
                    109:        SDLK_y,
                    110:        SDLK_z,
                    111:        SDLK_DELETE,
                    112:        SDLK_KP0,
                    113:        SDLK_KP1,
                    114:        SDLK_KP2,
                    115:        SDLK_KP3,
                    116:        SDLK_KP4,
                    117:        SDLK_KP5,
                    118:        SDLK_KP6,
                    119:        SDLK_KP7,
                    120:        SDLK_KP8,
                    121:        SDLK_KP9,
                    122:        SDLK_KP_PERIOD,
                    123:        SDLK_KP_DIVIDE,
                    124:        SDLK_KP_MULTIPLY,
                    125:        SDLK_KP_MINUS,
                    126:        SDLK_KP_PLUS,
                    127:        SDLK_KP_ENTER,
                    128:        SDLK_KP_EQUALS,
                    129:        SDLK_UP,
                    130:        SDLK_DOWN,
                    131:        SDLK_RIGHT,
                    132:        SDLK_LEFT,
                    133:        SDLK_INSERT,
                    134:        SDLK_HOME,
                    135:        SDLK_END,
                    136:        SDLK_PAGEUP,
                    137:        SDLK_PAGEDOWN,
                    138:        SDLK_F1,
                    139:        SDLK_F2,
                    140:        SDLK_F3,
                    141:        SDLK_F4,
                    142:        SDLK_F5,
                    143:        SDLK_F6,
                    144:        SDLK_F7,
                    145:        SDLK_F8,
                    146:        SDLK_F9,
                    147:        SDLK_F10,
                    148:        SDLK_F11,
                    149:        SDLK_F12,
                    150:        SDLK_F13,
                    151:        SDLK_F14,
                    152:        SDLK_F15,
                    153:        SDLK_NUMLOCK,
                    154:        SDLK_CAPSLOCK,
                    155:        SDLK_SCROLLOCK,
                    156:        SDLK_RSHIFT,
                    157:        SDLK_LSHIFT,
                    158:        SDLK_RCTRL,
                    159:        SDLK_LCTRL,
                    160:        SDLK_RALT,
                    161:        SDLK_LALT,
                    162:        SDLK_RMETA,
                    163:        SDLK_LMETA,
                    164:        SDLK_LSUPER,
                    165:        SDLK_RSUPER,
                    166:        SDLK_MODE,
                    167:        SDLK_COMPOSE,
                    168:        SDLK_HELP,
                    169:        SDLK_PRINT,
                    170:        SDLK_SYSREQ,
                    171:        SDLK_BREAK,
                    172:        SDLK_MENU,
                    173:        SDLK_POWER,
                    174:        SDLK_EURO,
                    175:        SDLK_UNDO
                    176: };
                    177: 
                    178: size_t Preferences_cKeysForJoysticks = sizeof(Preferences_KeysForJoysticks) / sizeof(Preferences_KeysForJoysticks[0]);
                    179: 
                    180: 
                    181: @implementation PrefsController
                    182: 
                    183: 
                    184: /*-----------------------------------------------------------------------*/
                    185: /*
                    186:   Helper method for Choose buttons
                    187:   Returns: TRUE is the user selected a path, FALSE if he/she aborted
                    188: */
                    189: - (BOOL)choosePathForControl:(NSTextField*)textField chooseDirectories:(bool)chooseDirectories defaultInitialDir:(NSString*)defaultInitialDir
                    190: {
                    191:        // Create and configure an OpenPanel
                    192:     NSOpenPanel *openPanel = [NSOpenPanel openPanel];
                    193:        [openPanel setCanChooseDirectories: chooseDirectories];
                    194:        [openPanel setCanChooseFiles: !chooseDirectories];
                    195: 
                    196:        NSString *directoryToOpen;
                    197:        NSString *fileToPreselect;
                    198:        NSString *oldPath = [textField stringValue];
                    199:        if ((oldPath != nil) && ([oldPath length] > 0))
                    200:        {
                    201:                // There is existing path: we will open its directory with its file pre-selected.
                    202:                directoryToOpen = [oldPath stringByDeletingLastPathComponent];
                    203:                fileToPreselect = [oldPath lastPathComponent];
                    204:        }
                    205:        else
                    206:        {
                    207:                // Currently no path: we will open the user's directory with no file selected.
                    208:                directoryToOpen = [defaultInitialDir stringByExpandingTildeInPath];
                    209:                fileToPreselect = nil;
                    210:        }
                    211:        
                    212:        // Run the OpenPanel, then check if the user clicked OK and selected at least one file
                    213:     if ( (NSOKButton == [openPanel runModalForDirectory:directoryToOpen file:fileToPreselect types:nil] )
                    214:            && ([[openPanel filenames] count] > 0) )
                    215:        {
                    216:                // Get the path to the selected file
                    217:                NSString *path = [[openPanel filenames] objectAtIndex:0];
                    218:                
                    219:                // Set the control to it (abbreviated if possible)
                    220:                [textField setStringValue:[path stringByAbbreviatingWithTildeInPath]];
                    221:                
                    222:                // Signal completion
                    223:                return TRUE;
                    224:     }
                    225:        
                    226:        // Signal that the selection was aborted
                    227:        return FALSE;
                    228: }
                    229: 
                    230: 
                    231: /*-----------------------------------------------------------------------*/
                    232: /*
                    233:   Helper method to insert a floppy image
                    234:   TODO: Add code to restrict to known file types
                    235: */
                    236: - (void)insertFloppyImageIntoDrive:(int)drive forTextField:(NSTextField*)floppyTextField
                    237: {
                    238:        if ([self choosePathForControl:floppyTextField chooseDirectories:FALSE defaultInitialDir:[defaultImagesLocation stringValue]])
                    239:        {
                    240:                // Get the full path to the selected file
                    241:                NSString *path = [[floppyTextField stringValue] stringByExpandingTildeInPath];
                    242:                
                    243:                // Make a non-const C string out of it
                    244:                const char* constSzPath = [path cString];
                    245:                size_t cbPath = strlen(constSzPath) + 1;
                    246:                char szPath[cbPath];
                    247:                strncpy(szPath, constSzPath, cbPath);
                    248: 
                    249:                // Insert the floppy image at this path
1.1.1.2 ! root      250:                Floppy_InsertDiskIntoDrive(drive, szPath, cbPath);
1.1       root      251:        }
                    252: }
                    253: 
                    254: 
                    255: /*-----------------------------------------------------------------------*/
                    256: /*
                    257:   Methods for all the "Choose" buttons
                    258: */
                    259: - (IBAction)chooseCartridgeImage:(id)sender;
                    260: {
                    261:        [self choosePathForControl: cartridgeImage chooseDirectories:FALSE defaultInitialDir:@"~"];
                    262: }
                    263: 
                    264: - (IBAction)chooseDefaultImagesLocation:(id)sender
                    265: {
                    266:        [self choosePathForControl: defaultImagesLocation chooseDirectories:TRUE defaultInitialDir:@"~"];
                    267: }
                    268: 
                    269: - (IBAction)chooseFloppyImageA:(id)sender
                    270: {
                    271:        [self insertFloppyImageIntoDrive:0 forTextField: floppyImageA];
                    272: }
                    273: 
                    274: - (IBAction)chooseFloppyImageB:(id)sender
                    275: {
                    276:        [self insertFloppyImageIntoDrive:1 forTextField: floppyImageB];
                    277: }
                    278: 
                    279: - (IBAction)chooseGemdosImage:(id)sender
                    280: {
                    281:        [self choosePathForControl: gemdosImage chooseDirectories:TRUE defaultInitialDir:@"~"];
                    282: }
                    283: 
                    284: - (IBAction)chooseHdImage:(id)sender
                    285: {
                    286:        [self choosePathForControl: hdImage chooseDirectories:FALSE defaultInitialDir:@"~"];
                    287: }
                    288: 
                    289: - (IBAction)chooseKeyboardMappingFile:(id)sender
                    290: {
                    291:        [self choosePathForControl: keyboardMappingFile chooseDirectories:FALSE defaultInitialDir:@"~"];
                    292: }
                    293: 
                    294: - (IBAction)chooseMidiOutputFile:(id)sender
                    295: {
                    296:        [self choosePathForControl: writeMidiToFile chooseDirectories:FALSE defaultInitialDir:@"~"];
                    297: }
                    298: 
                    299: - (IBAction)choosePrintToFile:(id)sender
                    300: {
                    301:        [self choosePathForControl: printToFile chooseDirectories:FALSE defaultInitialDir:@"~"];
                    302: }
                    303: 
                    304: - (IBAction)chooseRS232InputFile:(id)sender
                    305: {
                    306:        [self choosePathForControl: readRS232FromFile chooseDirectories:FALSE defaultInitialDir:@"~"];
                    307: }
                    308: 
                    309: - (IBAction)chooseRS232OutputFile:(id)sender
                    310: {
                    311:        [self choosePathForControl: writeRS232ToFile chooseDirectories:FALSE defaultInitialDir:@"~"];
                    312: }
                    313: 
                    314: - (IBAction)chooseTosImage:(id)sender;
                    315: {
                    316:        [self choosePathForControl: tosImage chooseDirectories:FALSE defaultInitialDir:@"~"];
                    317: }
                    318: 
                    319: 
                    320: /*-----------------------------------------------------------------------*/
                    321: /*
                    322:   Methods for the "Eject" buttons
                    323: */
                    324: - (IBAction)ejectFloppyA:(id)sender
                    325: {
                    326:        Floppy_EjectDiskFromDrive(0, FALSE);
                    327:        
                    328:        // Refresh the control
                    329:        [floppyImageA setStringValue:@""];
                    330: }
                    331: 
                    332: - (IBAction)ejectFloppyB:(id)sender
                    333: {
                    334:        Floppy_EjectDiskFromDrive(1, FALSE);
                    335: 
                    336:        // Refresh the control
                    337:        [floppyImageB setStringValue:@""];
                    338: }
                    339: 
                    340: - (IBAction)ejectGemdosImage:(id)sender
                    341: {
                    342:        // Clear the control. Later. saveAllControls will set the DialogParams accordingly to signal this is ejected
                    343:        [gemdosImage setStringValue:@""];
                    344: }
                    345: 
                    346: - (IBAction)ejectHdImage:(id)sender
                    347: {
                    348:        // Clear the control. Later. saveAllControls will set the DialogParams accordingly to signal this is ejected
                    349:        [hdImage setStringValue:@""];
                    350: }
                    351: 
                    352: 
                    353: /*-----------------------------------------------------------------------*/
                    354: /*
                    355:   Methods for the "Load Config" and "Save Config" buttons
                    356: */
                    357: - (IBAction)loadConfig:(id)sender
                    358: {
                    359:        // Load the config into DialogParams
                    360:        Dialog_LoadParams();
                    361:        
                    362:        // Refresh all the controls to match DialogParams
                    363:        [self setAllControls];
                    364: }
                    365: 
                    366: - (IBAction)saveConfig:(id)sender
                    367: {
                    368:        // Update the DialogParams from the controls
                    369:        [self saveAllControls];
                    370: 
                    371:        // Save the DialogParams to the config file
                    372:        Dialog_SaveParams();
                    373: }
                    374: 
                    375: 
                    376: /*-----------------------------------------------------------------------*/
                    377: /*
                    378:   Commits and closes
                    379: */
                    380: - (IBAction)commitAndClose:(id)sender
                    381: {
                    382:        BOOL applyChanges = TRUE;
                    383: 
                    384:        // The user clicked OK
                    385:        [self saveAllControls];
                    386:        
                    387:        // If a reset is required, ask the user first
                    388:        if (Dialog_DoNeedReset())
                    389:        {
                    390:                applyChanges = ( 0 == NSRunAlertPanel (@"Reset the emulator?", 
                    391:                @"The emulator must be reset in order to apply your changes.\nAll current work will be lost.",
                    392:                @"Don't reset", @"Reset", nil) );
                    393:        }
                    394:        
                    395:        // Commit the new configuration
                    396:        if (applyChanges)
                    397:        {
                    398:                Dialog_CopyDialogParamsToConfiguration(FALSE);
                    399:        }
                    400: 
                    401:        // Close the window
                    402:        [window close]; 
                    403: }
                    404: 
                    405: - (void)initKeysDropDown:(NSPopUpButton*)dropDown
                    406: {
                    407:        [dropDown removeAllItems];
                    408:        int i;
                    409:        for (i = 0; i < Preferences_cKeysForJoysticks; i++)
                    410:        {
                    411:                SDLKey key = Preferences_KeysForJoysticks[i];
                    412:                const char* szKeyName = SDL_GetKeyName(key);
                    413:                [dropDown addItemWithTitle:[[NSString stringWithCString:szKeyName] capitalizedString]]; 
                    414:                [[dropDown lastItem] setTag:key];
                    415:        }
                    416: }
                    417: 
                    418: 
                    419: /*-----------------------------------------------------------------------*/
                    420: /*
                    421:   Displays the Preferences dialog
                    422: */
                    423: - (IBAction)loadPrefs:(id)sender
                    424: {
                    425:        if (!bInitialized)
                    426:        {
                    427:                // Note: These inits cannot be done in awakeFromNib as by this time SDL is not yet initialized.
                    428: 
                    429:                // Fill the keyboard dropdowns
                    430:                [self initKeysDropDown:joystickUp];
                    431:                [self initKeysDropDown:joystickRight];
                    432:                [self initKeysDropDown:joystickDown];
                    433:                [self initKeysDropDown:joystickLeft];           
                    434:                [self initKeysDropDown:joystickFire];
                    435:                
                    436:                // Get and store the number of real joysticks
                    437:                cRealJoysticks = SDL_NumJoysticks();
                    438: 
                    439:                // Fill the real joysticks dropdown, if any are available
                    440:                if (cRealJoysticks > 0)
                    441:                {
                    442:                        [realJoystick removeAllItems];
                    443:                        int i;
                    444:                        for (i = 0; i < cRealJoysticks; i++)
                    445:                        {
                    446:                                const char* szJoystickName = SDL_JoystickName(i);
                    447:                                [realJoystick addItemWithTitle:[[NSString stringWithCString:szJoystickName] capitalizedString]];        
                    448:                                [[realJoystick lastItem] setTag:i];     
                    449:                        }
                    450:                }
                    451:                else    // No real joysticks: Disable the controls
                    452:                {
                    453:                        [[joystickMode cellWithTag:1] setEnabled:FALSE];
                    454:                        [realJoystick setEnabled:FALSE];
                    455:                }
                    456:                
                    457:                bInitialized = TRUE;
                    458:        }
                    459: 
                    460: 
                    461:        // Copy configuration settings to DialogParams (which we will only commit back to the configuration settings if choosing OK)
                    462:        DialogParams = ConfigureParams;
                    463: 
                    464:        [self setAllControls];
                    465: 
                    466:        // Display the window
                    467:        [[ModalWrapper alloc] runModal:window];
                    468: }
                    469: 
                    470: 
                    471: /*-----------------------------------------------------------------------*/
                    472: /*
                    473:   Updates the controls following a change in the joystick selection
                    474: */
                    475: - (IBAction)changeViewedJoystick:(id)sender
                    476: {
                    477:        // Save the pre-joystick controls, as we are about to change them
                    478:        [self saveJoystickControls];
                    479:        
                    480:        // Refresh the per-joystick controls
                    481:        [self setJoystickControls];
                    482:        
                    483:        // Update the controls' enabled states
                    484:        [self updateEnabledStates:self];
                    485: }
                    486: 
                    487: 
                    488: /*-----------------------------------------------------------------------*/
                    489: /*
                    490:   Initializes all controls
                    491: */
                    492: - (void)setAllControls
                    493: {
                    494:        // Import the floppy paths into their controls.
                    495:        // Note: Floppy images are exposed in the prefs dialog, however they aren't stored with the prefs and won't need to be saved on exit.
                    496:        IMPORT_TEXTFIELD(floppyImageA, EmulationDrives[0].szFileName); 
                    497:        IMPORT_TEXTFIELD(floppyImageB, EmulationDrives[1].szFileName); 
                    498:        
                    499:        // Import all the preferences into their controls
                    500:        IMPORT_SWITCH(autoInsertB, DialogParams.DiskImage.bAutoInsertDiskB);
                    501:     IMPORT_SWITCH(blitter, DialogParams.System.bBlitter);
                    502:        IMPORT_SWITCH(bootFromHD, DialogParams.HardDisk.bBootFromHardDisk);     
                    503:     IMPORT_SWITCH(captureOnChange, DialogParams.Screen.bCaptureChange);
                    504:     IMPORT_TEXTFIELD(cartridgeImage, DialogParams.Rom.szCartridgeImageFileName);
                    505:     IMPORT_RADIO(colorDepth, DialogParams.Screen.nVdiColors);
                    506:     IMPORT_SWITCH(compatibleCpu, DialogParams.System.bCompatibleCpu);
                    507:     IMPORT_RADIO(cpuClock, DialogParams.System.nCpuFreq);
                    508:     IMPORT_RADIO(cpuType, DialogParams.System.nCpuLevel);
                    509:        IMPORT_TEXTFIELD(defaultImagesLocation, DialogParams.DiskImage.szDiskImageDirectory);
                    510:     IMPORT_SWITCH(enableMidi, DialogParams.Midi.bEnableMidi);
                    511:     IMPORT_SWITCH(enablePrinter, DialogParams.Printer.bEnablePrinting);
                    512:     IMPORT_SWITCH(enableRS232, DialogParams.RS232.bEnableRS232);
                    513:     IMPORT_SWITCH(enableSound, DialogParams.Sound.bEnableSound);
1.1.1.2 ! root      514:     IMPORT_DROPDOWN(frameSkip, DialogParams.Screen.FrameSkips);
1.1       root      515:     IMPORT_RADIO(keyboardMapping, DialogParams.Keyboard.nKeymapType);
                    516:     IMPORT_TEXTFIELD(keyboardMappingFile, DialogParams.Keyboard.szMappingFileName);
                    517:     IMPORT_RADIO(machineType, DialogParams.System.nMachineType);
1.1.1.2 ! root      518:     IMPORT_RADIO(monitor, DialogParams.Screen.MonitorType);
1.1       root      519:     IMPORT_SWITCH(patchTimerD, DialogParams.System.bPatchTimerD);
                    520:     IMPORT_RADIO(playbackQuality, DialogParams.Sound.nPlaybackQuality);
                    521:     IMPORT_TEXTFIELD(printToFile, DialogParams.Printer.szPrintToFileName);
                    522:     IMPORT_RADIO(ramSize, DialogParams.Memory.nMemorySize);
                    523:     IMPORT_TEXTFIELD(readRS232FromFile, DialogParams.RS232.szInFileName);
                    524:     IMPORT_SWITCH(realTime, DialogParams.System.bRealTimeClock);
                    525:     IMPORT_SWITCH(slowFDC, DialogParams.System.bSlowFDC);
                    526:     IMPORT_TEXTFIELD(tosImage, DialogParams.Rom.szTosImageFileName);
                    527:     IMPORT_SWITCH(useBorders, DialogParams.Screen.bAllowOverscan);
                    528:     IMPORT_SWITCH(useVDIResolution, DialogParams.Screen.bUseExtVdiResolutions);
                    529:     IMPORT_TEXTFIELD(writeMidiToFile, DialogParams.Midi.szMidiOutFileName);
                    530:        IMPORT_RADIO(writeProtection, DialogParams.DiskImage.nWriteProtection);
                    531:     IMPORT_TEXTFIELD(writeRS232ToFile, DialogParams.RS232.szOutFileName);
1.1.1.2 ! root      532:     IMPORT_SWITCH(zoomSTLowRes, DialogParams.Screen.bZoomLowRes);
        !           533: 
        !           534:        [(force8bpp) setState:((DialogParams.Screen.nForceBpp==8))? NSOnState : NSOffState];
        !           535: 
        !           536:        if (DialogParams.Screen.nVdiWidth >= 1024)
        !           537:                [resolution selectCellWithTag:(2)];
        !           538:        else if (DialogParams.Screen.nVdiWidth >= 768)
        !           539:                [resolution selectCellWithTag:(1)];
        !           540:        else
        !           541:                [resolution selectCellWithTag:(0)];
        !           542: 
1.1       root      543:        // If the HD flag is set, load the HD path, otherwise make it blank
                    544:        if (DialogParams.HardDisk.bUseHardDiskImage)
                    545:        {
                    546:                IMPORT_TEXTFIELD(hdImage, DialogParams.HardDisk.szHardDiskImage);       
                    547:        }
                    548:        else
                    549:        {
                    550:                [hdImage setStringValue:@""];
                    551:        }
                    552:        
                    553:        // If the Gemdos flag is set, load the Gemdos path, otherwise make it blank
                    554:        if (DialogParams.HardDisk.bUseHardDiskDirectories)
                    555:        {
                    556:                IMPORT_TEXTFIELD(gemdosImage, DialogParams.HardDisk.szHardDiskDirectories[0]);
                    557:        }
                    558:        else
                    559:        {
                    560:                [gemdosImage setStringValue:@""];
                    561:        }
                    562:        
                    563:        // Set the per-joystick controls                
                    564:        [self setJoystickControls];
                    565:        
                    566:        // Update the controls' enabled states
                    567:        [self updateEnabledStates:self];        
                    568: }
                    569: 
                    570: 
                    571: /*-----------------------------------------------------------------------*/
                    572: /*
                    573:   Updates the enabled states of controls who depend on other controls
                    574: */
                    575: - (IBAction)updateEnabledStates:(id)sender
                    576: {
                    577:        // Joystick key controls are only enabled if "Use keyboard" is selected
                    578:        int nJoystickMode;
                    579:        EXPORT_RADIO(joystickMode, nJoystickMode);
                    580:        BOOL bUsingKeyboard = (nJoystickMode == JOYSTICK_KEYBOARD);
                    581:        [joystickUp setEnabled:bUsingKeyboard];         
                    582:        [joystickRight setEnabled:bUsingKeyboard];              
                    583:        [joystickDown setEnabled:bUsingKeyboard];               
                    584:        [joystickLeft setEnabled:bUsingKeyboard];               
                    585:        [joystickFire setEnabled:bUsingKeyboard];               
                    586: 
                    587:        // Resolution and colour depth depend on Extended GEM VDI resolution
                    588:        BOOL bUsingVDI;
                    589:        EXPORT_SWITCH(useVDIResolution, bUsingVDI);
                    590:        [resolution setEnabled:bUsingVDI];              
                    591:        [colorDepth setEnabled:bUsingVDI];
                    592:        
                    593:        // Playback quality depends on enable sound
                    594:        BOOL bSoundEnabled;
                    595:     EXPORT_SWITCH(enableSound, bSoundEnabled);
                    596:        [playbackQuality setEnabled:bSoundEnabled];
                    597: }
                    598: 
                    599: 
                    600: /*-----------------------------------------------------------------------*/
                    601: /*
                    602:   Updates the joystick controls to match the new joystick selection
                    603: */
                    604: - (void)setJoystickControls
                    605: {
                    606:        // Get and persist the ID of the newly selected joystick
                    607:        EXPORT_DROPDOWN(currentJoystick, nCurrentJoystick);
                    608: 
                    609:        // Data validation: If the JoyID is out of bounds, correct it and, if set to use real joystick, change to disabled
                    610:        if ( (DialogParams.Joysticks.Joy[nCurrentJoystick].nJoyId < 0)
                    611:        || (DialogParams.Joysticks.Joy[nCurrentJoystick].nJoyId >= cRealJoysticks) )
                    612:        {
                    613:                DialogParams.Joysticks.Joy[nCurrentJoystick].nJoyId = 0;
                    614:                if (DialogParams.Joysticks.Joy[nCurrentJoystick].nJoystickMode == JOYSTICK_REALSTICK)
                    615:                {
                    616:                        DialogParams.Joysticks.Joy[nCurrentJoystick].nJoystickMode = JOYSTICK_DISABLED;
                    617:                }       
                    618:        }
                    619: 
                    620:        // Don't change the realJoystick dropdown if none is available (to keep "(None available)" selected)
                    621:        if (cRealJoysticks > 0)
                    622:        {
                    623:                IMPORT_DROPDOWN(realJoystick, DialogParams.Joysticks.Joy[nCurrentJoystick].nJoyId);
                    624:        }
                    625: 
                    626:        IMPORT_RADIO(joystickMode, DialogParams.Joysticks.Joy[nCurrentJoystick].nJoystickMode);
                    627:        IMPORT_DROPDOWN(joystickUp, DialogParams.Joysticks.Joy[nCurrentJoystick].nKeyCodeUp);
                    628:        IMPORT_DROPDOWN(joystickRight, DialogParams.Joysticks.Joy[nCurrentJoystick].nKeyCodeRight);
                    629:        IMPORT_DROPDOWN(joystickDown, DialogParams.Joysticks.Joy[nCurrentJoystick].nKeyCodeDown);
                    630:        IMPORT_DROPDOWN(joystickLeft, DialogParams.Joysticks.Joy[nCurrentJoystick].nKeyCodeLeft);
                    631:        IMPORT_DROPDOWN(joystickFire, DialogParams.Joysticks.Joy[nCurrentJoystick].nKeyCodeFire);
                    632:        IMPORT_SWITCH(enableAutoFire, DialogParams.Joysticks.Joy[nCurrentJoystick].bEnableAutoFire);
                    633: }
                    634: 
                    635: 
                    636: /*-----------------------------------------------------------------------*/
                    637: /*
                    638:   Saves the setting for the joystick currently being viewed
                    639: */
                    640: - (void)saveJoystickControls
                    641: {
                    642:        EXPORT_RADIO(joystickMode, DialogParams.Joysticks.Joy[nCurrentJoystick].nJoystickMode); 
                    643:        EXPORT_DROPDOWN(realJoystick, DialogParams.Joysticks.Joy[nCurrentJoystick].nJoyId);
                    644:        EXPORT_DROPDOWN(joystickUp, DialogParams.Joysticks.Joy[nCurrentJoystick].nKeyCodeUp);
                    645:        EXPORT_DROPDOWN(joystickRight, DialogParams.Joysticks.Joy[nCurrentJoystick].nKeyCodeRight);
                    646:        EXPORT_DROPDOWN(joystickDown, DialogParams.Joysticks.Joy[nCurrentJoystick].nKeyCodeDown);
                    647:        EXPORT_DROPDOWN(joystickLeft, DialogParams.Joysticks.Joy[nCurrentJoystick].nKeyCodeLeft);
                    648:        EXPORT_DROPDOWN(joystickFire, DialogParams.Joysticks.Joy[nCurrentJoystick].nKeyCodeFire);
                    649:        EXPORT_SWITCH(enableAutoFire, DialogParams.Joysticks.Joy[nCurrentJoystick].bEnableAutoFire);
                    650: }
                    651: 
                    652: 
                    653: /*-----------------------------------------------------------------------*/
                    654: /*
                    655:   Saves the settings for all controls
                    656: */
                    657: - (void)saveAllControls
                    658: {
                    659:        // Export the preference controls into their vars
                    660:        EXPORT_SWITCH(autoInsertB, DialogParams.DiskImage.bAutoInsertDiskB);
                    661:     EXPORT_SWITCH(blitter, DialogParams.System.bBlitter);
                    662:        EXPORT_SWITCH(bootFromHD, DialogParams.HardDisk.bBootFromHardDisk);
                    663:     EXPORT_SWITCH(captureOnChange, DialogParams.Screen.bCaptureChange);
                    664:     EXPORT_TEXTFIELD(cartridgeImage, DialogParams.Rom.szCartridgeImageFileName);
                    665:     EXPORT_RADIO(colorDepth, DialogParams.Screen.nVdiColors);
                    666:     EXPORT_SWITCH(compatibleCpu, DialogParams.System.bCompatibleCpu);
                    667:     EXPORT_RADIO(cpuClock, DialogParams.System.nCpuFreq);
                    668:     EXPORT_RADIO(cpuType, DialogParams.System.nCpuLevel);
                    669:        EXPORT_TEXTFIELD(defaultImagesLocation, DialogParams.DiskImage.szDiskImageDirectory);
                    670:     EXPORT_SWITCH(enableMidi, DialogParams.Midi.bEnableMidi);
                    671:     EXPORT_SWITCH(enablePrinter, DialogParams.Printer.bEnablePrinting);
                    672:     EXPORT_SWITCH(enableRS232, DialogParams.RS232.bEnableRS232);
                    673:     EXPORT_SWITCH(enableSound, DialogParams.Sound.bEnableSound);
1.1.1.2 ! root      674:     EXPORT_DROPDOWN(frameSkip, DialogParams.Screen.FrameSkips);
1.1       root      675:     EXPORT_RADIO(keyboardMapping, DialogParams.Keyboard.nKeymapType);
                    676:     EXPORT_TEXTFIELD(keyboardMappingFile, DialogParams.Keyboard.szMappingFileName);
                    677:     EXPORT_RADIO(machineType, DialogParams.System.nMachineType);
1.1.1.2 ! root      678:     EXPORT_RADIO(monitor, DialogParams.Screen.MonitorType);
1.1       root      679:     EXPORT_SWITCH(patchTimerD, DialogParams.System.bPatchTimerD);
                    680:     EXPORT_RADIO(playbackQuality, DialogParams.Sound.nPlaybackQuality);
                    681:     EXPORT_TEXTFIELD(printToFile, DialogParams.Printer.szPrintToFileName);
                    682:     EXPORT_RADIO(ramSize, DialogParams.Memory.nMemorySize);
                    683:     EXPORT_TEXTFIELD(readRS232FromFile, DialogParams.RS232.szInFileName);
                    684:     EXPORT_SWITCH(realTime, DialogParams.System.bRealTimeClock);
                    685:     EXPORT_SWITCH(slowFDC, DialogParams.System.bSlowFDC);
                    686:     EXPORT_TEXTFIELD(tosImage, DialogParams.Rom.szTosImageFileName);
                    687:     EXPORT_SWITCH(useBorders, DialogParams.Screen.bAllowOverscan);
                    688:     EXPORT_SWITCH(useVDIResolution, DialogParams.Screen.bUseExtVdiResolutions);
                    689:     EXPORT_TEXTFIELD(writeMidiToFile, DialogParams.Midi.szMidiOutFileName);
                    690:        EXPORT_RADIO(writeProtection, DialogParams.DiskImage.nWriteProtection);
                    691:     EXPORT_TEXTFIELD(writeRS232ToFile, DialogParams.RS232.szOutFileName);
1.1.1.2 ! root      692:     EXPORT_SWITCH(zoomSTLowRes, DialogParams.Screen.bZoomLowRes);      
        !           693: 
        !           694:        DialogParams.Screen.nForceBpp = ([force8bpp state] == NSOnState) ? 8 : 16;
        !           695: 
        !           696:        switch ([[resolution selectedCell] tag])
        !           697:        {
        !           698:         case 0:
        !           699:                DialogParams.Screen.nVdiWidth = 640;
        !           700:                DialogParams.Screen.nVdiHeight = 480;
        !           701:                break;
        !           702:         case 1:
        !           703:                DialogParams.Screen.nVdiWidth = 800;
        !           704:                DialogParams.Screen.nVdiHeight = 600;
        !           705:                break;
        !           706:         case 2:
        !           707:                DialogParams.Screen.nVdiWidth = 1024;
        !           708:                DialogParams.Screen.nVdiHeight = 768;
        !           709:                break;
        !           710:        }
1.1       root      711: 
                    712:        // Define the HD flag, and export the HD path if one is selected
                    713:        if ([[hdImage stringValue] length] > 0)
                    714:        {
                    715:                EXPORT_TEXTFIELD(hdImage, DialogParams.HardDisk.szHardDiskImage);
                    716:                DialogParams.HardDisk.bUseHardDiskImage = TRUE;
                    717:        }
                    718:        else
                    719:        {
                    720:                DialogParams.HardDisk.bUseHardDiskImage = FALSE;
                    721:        }
                    722:        
                    723:        // Define the Gemdos flag, and export the Gemdos path if one is selected
                    724:        if ([[gemdosImage stringValue] length] > 0)
                    725:        {
                    726:                EXPORT_TEXTFIELD(gemdosImage, DialogParams.HardDisk.szHardDiskDirectories[0]);
                    727:                DialogParams.HardDisk.bUseHardDiskDirectories = TRUE;
                    728:        }
                    729:        else
                    730:        {
                    731:                DialogParams.HardDisk.bUseHardDiskDirectories = FALSE;
                    732:        }
                    733:        
                    734:        // Save the per-joystick controls               
                    735:        [self saveJoystickControls];    
                    736: }
                    737: 
                    738: @end

unix.superglobalmegacorp.com

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