OSDN Git Service

110a310ac9f5dddada39b0f874e19901a23c938a
[handbrake-jp/handbrake-jp-git.git] / macosx / Controller.mm
1 /* $Id: Controller.mm,v 1.79 2005/11/04 19:41:32 titer Exp $
2
3    This file is part of the HandBrake source code.
4    Homepage: <http://handbrake.m0k.org/>.
5    It may be used under the terms of the GNU General Public License. */
6
7 #include "Controller.h"
8 #include "a52dec/a52.h"
9 #import "HBOutputPanelController.h"
10 #import "HBPreferencesController.h"
11 /* Added to integrate scanning into HBController */
12 #include <IOKit/IOKitLib.h>
13 #include <IOKit/storage/IOMedia.h>
14 #include <IOKit/storage/IODVDMedia.h>
15 #include "HBDVDDetector.h"
16 #include "dvdread/dvd_reader.h"
17
18 #define _(a) NSLocalizedString(a,NULL)
19
20 static int FormatSettings[4][10] =
21   { { HB_MUX_MP4 | HB_VCODEC_FFMPEG | HB_ACODEC_FAAC,
22           HB_MUX_MP4 | HB_VCODEC_X264   | HB_ACODEC_FAAC,
23           0,
24           0 },
25     { HB_MUX_MKV | HB_VCODEC_FFMPEG | HB_ACODEC_FAAC,
26           HB_MUX_MKV | HB_VCODEC_FFMPEG | HB_ACODEC_AC3,
27           HB_MUX_MKV | HB_VCODEC_FFMPEG | HB_ACODEC_LAME,
28           HB_MUX_MKV | HB_VCODEC_FFMPEG | HB_ACODEC_VORBIS,
29           HB_MUX_MKV | HB_VCODEC_X264   | HB_ACODEC_FAAC,
30           HB_MUX_MKV | HB_VCODEC_X264   | HB_ACODEC_AC3,
31           HB_MUX_MKV | HB_VCODEC_X264   | HB_ACODEC_LAME,
32           HB_MUX_MKV | HB_VCODEC_X264   | HB_ACODEC_VORBIS,
33           0,
34           0 },
35     { HB_MUX_AVI | HB_VCODEC_FFMPEG | HB_ACODEC_LAME,
36           HB_MUX_AVI | HB_VCODEC_FFMPEG | HB_ACODEC_AC3,
37           HB_MUX_AVI | HB_VCODEC_X264   | HB_ACODEC_LAME,
38           HB_MUX_AVI | HB_VCODEC_X264   | HB_ACODEC_AC3},
39     { HB_MUX_OGM | HB_VCODEC_FFMPEG | HB_ACODEC_VORBIS,
40           HB_MUX_OGM | HB_VCODEC_FFMPEG | HB_ACODEC_LAME,
41           0,
42           0 } };
43
44 /* We setup the toolbar values here */
45 static NSString *        ToggleDrawerIdentifier             = @"Toggle Drawer Item Identifier";
46 static NSString *        StartEncodingIdentifier            = @"Start Encoding Item Identifier";
47 static NSString *        PauseEncodingIdentifier            = @"Pause Encoding Item Identifier";
48 static NSString *        ShowQueueIdentifier                = @"Show Queue Item Identifier";
49 static NSString *        AddToQueueIdentifier               = @"Add to Queue Item Identifier";
50 static NSString *        ShowActivityIdentifier             = @"Debug Output Item Identifier";
51 static NSString *        ChooseSourceIdentifier             = @"Choose Source Item Identifier";
52
53
54 /*******************************
55  * HBController implementation *
56  *******************************/
57 @implementation HBController
58
59 - init
60 {
61     self = [super init];
62     [HBPreferencesController registerUserDefaults];
63     fHandle = NULL;
64     /* Check for check for the app support directory here as
65         * outputPanel needs it right away, as may other future methods
66         */
67     /* We declare the default NSFileManager into fileManager */
68         NSFileManager * fileManager = [NSFileManager defaultManager];
69         /* we set the files and support paths here */
70         AppSupportDirectory = @"~/Library/Application Support/HandBrake";
71     AppSupportDirectory = [AppSupportDirectory stringByExpandingTildeInPath];
72     /* We check for the app support directory for handbrake */
73         if ([fileManager fileExistsAtPath:AppSupportDirectory] == 0) 
74         {
75                 // If it doesnt exist yet, we create it here 
76                 [fileManager createDirectoryAtPath:AppSupportDirectory attributes:nil];
77         }
78     
79     outputPanel = [[HBOutputPanelController alloc] init];
80     fPictureController = [[PictureController alloc] initWithDelegate:self];
81     fQueueController = [[HBQueueController alloc] init];
82     fAdvancedOptions = [[HBAdvancedController alloc] init];
83     fPreferencesController = [[HBPreferencesController alloc] init];
84     return self;
85 }
86
87
88 - (void) applicationDidFinishLaunching: (NSNotification *) notification
89 {
90     int    build;
91     char * version;
92     
93     // Init libhb
94         int debugLevel = [[NSUserDefaults standardUserDefaults] boolForKey:@"ShowVerboseOutput"] ? HB_DEBUG_ALL : HB_DEBUG_NONE;
95     fHandle = hb_init(debugLevel, [[NSUserDefaults standardUserDefaults] boolForKey:@"CheckForUpdates"]);
96     
97         // Set the Growl Delegate
98     [GrowlApplicationBridge setGrowlDelegate: self];    
99     /* Init others controllers */
100     [fPictureController SetHandle: fHandle];
101     [fQueueController   setHandle: fHandle];
102     [fQueueController   setHBController: self];
103         
104     fChapterTitlesDelegate = [[ChapterTitles alloc] init];
105     [fChapterTable setDataSource:fChapterTitlesDelegate];
106     
107     /* Call UpdateUI every 1/2 sec */
108     [[NSRunLoop currentRunLoop] addTimer: [NSTimer
109         scheduledTimerWithTimeInterval: 0.5 target: self
110                               selector: @selector( updateUI: ) userInfo: NULL repeats: YES]
111                                 forMode: NSEventTrackingRunLoopMode];
112     
113     // Open debug output window now if it was visible when HB was closed
114     if ([[NSUserDefaults standardUserDefaults] boolForKey:@"OutputPanelIsOpen"])
115         [self showDebugOutputPanel:nil];
116     
117     // Open queue window now if it was visible when HB was closed
118     if ([[NSUserDefaults standardUserDefaults] boolForKey:@"QueueWindowIsOpen"])
119         [self showQueueWindow:nil];
120     
121         [self openMainWindow:nil];
122     
123     if( ( build = hb_check_update( fHandle, &version ) ) > -1 )
124     {
125         /* Update available - tell the user */
126         
127         NSBeginInformationalAlertSheet( _( @"Update is available" ),
128                                         _( @"Go get it!" ), _( @"Discard" ), NULL, fWindow, self,
129                                         @selector( updateAlertDone:returnCode:contextInfo: ),
130                                         NULL, NULL, [NSString stringWithFormat:
131                                             _( @"HandBrake %s (build %d) is now available for download." ),
132                                             version, build] );
133         return;
134         
135     }
136         
137     /* Show Browse Sources Window ASAP */
138     [self performSelectorOnMainThread: @selector(browseSources:)
139                            withObject: NULL waitUntilDone: NO];
140                            }
141
142 - (void) updateAlertDone: (NSWindow *) sheet
143               returnCode: (int) returnCode contextInfo: (void *) contextInfo
144 {
145     if( returnCode == NSAlertDefaultReturn )
146     {
147         /* Go to HandBrake homepage and exit */
148         [self openHomepage: NULL];
149         [NSApp terminate: self];
150      
151     }
152     else
153     {
154          /* Show scan panel */
155         [self performSelectorOnMainThread: @selector(showScanPanel:)
156                                withObject: NULL waitUntilDone: NO];
157         return;
158                /* Go to HandBrake homepage and exit */
159         [self openHomepage: NULL];
160         [NSApp terminate: self];
161     }
162 }
163
164 - (NSApplicationTerminateReply) applicationShouldTerminate: (NSApplication *) app
165 {
166     // Warn if encoding a movie
167     hb_state_t s;
168     hb_get_state( fHandle, &s );
169     hb_job_t * job = hb_current_job( fHandle );
170     if ( job && ( s.state != HB_STATE_IDLE ) )
171     {
172         hb_job_t * job = hb_current_job( fHandle );
173         int result = NSRunCriticalAlertPanel(
174                 NSLocalizedString(@"Are you sure you want to quit HandBrake?", nil),
175                 NSLocalizedString(@"%@ is currently encoding. If you quit HandBrake, your movie will be lost. Do you want to quit anyway?", nil),
176                 NSLocalizedString(@"Quit", nil), NSLocalizedString(@"Don't Quit", nil), nil,
177                 job ? [NSString stringWithUTF8String:job->title->name] : @"A movie" );
178         
179         if (result == NSAlertDefaultReturn)
180         {
181             [self doCancelCurrentJob];
182             return NSTerminateNow;
183         }
184         else
185             return NSTerminateCancel;
186     }
187     
188     // Warn if items still in the queue
189     else if ( hb_count( fHandle ) > 0 )
190     {
191         int result = NSRunCriticalAlertPanel(
192                 NSLocalizedString(@"Are you sure you want to quit HandBrake?", nil),
193                 NSLocalizedString(@"One or more encodes are queued for encoding. Do you want to quit anyway?", nil),
194                 NSLocalizedString(@"Quit", nil), NSLocalizedString(@"Don't Quit", nil), nil);
195         
196         if ( result == NSAlertDefaultReturn )
197             return NSTerminateNow;
198         else
199             return NSTerminateCancel;
200     }
201     
202     return NSTerminateNow;
203 }
204
205 - (void)applicationWillTerminate:(NSNotification *)aNotification
206 {
207         [outputPanel release];
208         [fQueueController release];
209         hb_close(&fHandle);
210 }
211
212
213 - (void) awakeFromNib
214 {
215     [fWindow center];
216     [fWindow setExcludedFromWindowsMenu:YES];
217     [fAdvancedOptions setView:fAdvancedView];
218
219     /* Initialize currentScanCount so HB can use it to
220                 evaluate successive scans */
221         currentScanCount = 0;
222         
223     /* Init UserPresets .plist */
224         [self loadPresets];
225                 
226         fRipIndicatorShown = NO;  // initially out of view in the nib
227         
228         /* Show/Dont Show Presets drawer upon launch based
229                 on user preference DefaultPresetsDrawerShow*/
230         if ([[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultPresetsDrawerShow"] > 0)
231         {
232                 [fPresetDrawer open];
233         }
234         
235         
236     /* Destination box*/
237     [fDstFormatPopUp removeAllItems];
238     [fDstFormatPopUp addItemWithTitle: _( @"MP4 file" )];
239         [fDstFormatPopUp addItemWithTitle: _( @"MKV file" )];
240     [fDstFormatPopUp addItemWithTitle: _( @"AVI file" )];
241     [fDstFormatPopUp addItemWithTitle: _( @"OGM file" )];
242     [fDstFormatPopUp selectItemAtIndex: 0];
243         
244     [self formatPopUpChanged: NULL];
245     
246         /* We enable the create chapters checkbox here since we are .mp4 */     
247         [fCreateChapterMarkers setEnabled: YES];
248         if ([fDstFormatPopUp indexOfSelectedItem] == 0 && [[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultChapterMarkers"] > 0)
249         {
250                 [fCreateChapterMarkers setState: NSOnState];
251         }
252         
253         
254         
255         
256     [fDstFile2Field setStringValue: [NSString stringWithFormat:
257         @"%@/Desktop/Movie.mp4", NSHomeDirectory()]];
258         
259     /* Video encoder */
260     [fVidEncoderPopUp removeAllItems];
261     [fVidEncoderPopUp addItemWithTitle: @"FFmpeg"];
262     [fVidEncoderPopUp addItemWithTitle: @"XviD"];
263         
264     
265         
266     /* Video quality */
267     [fVidTargetSizeField setIntValue: 700];
268         [fVidBitrateField    setIntValue: 1000];
269         
270     [fVidQualityMatrix   selectCell: fVidBitrateCell];
271     [self videoMatrixChanged: NULL];
272         
273     /* Video framerate */
274     [fVidRatePopUp removeAllItems];
275         [fVidRatePopUp addItemWithTitle: _( @"Same as source" )];
276     for( int i = 0; i < hb_video_rates_count; i++ )
277     {
278         if ([[NSString stringWithCString: hb_video_rates[i].string] isEqualToString: [NSString stringWithFormat: @"%.3f",23.976]])
279                 {
280                         [fVidRatePopUp addItemWithTitle:[NSString stringWithFormat: @"%@%@",
281                                 [NSString stringWithCString: hb_video_rates[i].string], @" (NTSC Film)"]];
282                 }
283                 else if ([[NSString stringWithCString: hb_video_rates[i].string] isEqualToString: [NSString stringWithFormat: @"%d",25]])
284                 {
285                         [fVidRatePopUp addItemWithTitle:[NSString stringWithFormat: @"%@%@",
286                                 [NSString stringWithCString: hb_video_rates[i].string], @" (PAL Film/Video)"]];
287                 }
288                 else if ([[NSString stringWithCString: hb_video_rates[i].string] isEqualToString: [NSString stringWithFormat: @"%.2f",29.97]])
289                 {
290                         [fVidRatePopUp addItemWithTitle:[NSString stringWithFormat: @"%@%@",
291                                 [NSString stringWithCString: hb_video_rates[i].string], @" (NTSC Video)"]];
292                 }
293                 else
294                 {
295                         [fVidRatePopUp addItemWithTitle:
296                                 [NSString stringWithCString: hb_video_rates[i].string]];
297                 }
298     }
299     [fVidRatePopUp selectItemAtIndex: 0];
300         
301         /* Picture Settings */
302         [fPicLabelPAROutputX setStringValue: @""];
303         [fPicSettingPARWidth setStringValue: @""];
304         [fPicSettingPARHeight setStringValue:  @""];
305         
306         /* Set Auto Crop to On at launch */
307     [fPictureController setAutoCrop:YES];
308         
309         /* Audio bitrate */
310     [fAudBitratePopUp removeAllItems];
311     for( int i = 0; i < hb_audio_bitrates_count; i++ )
312     {
313         [fAudBitratePopUp addItemWithTitle:
314                                 [NSString stringWithCString: hb_audio_bitrates[i].string]];
315
316     }
317     [fAudBitratePopUp selectItemAtIndex: hb_audio_bitrates_default];
318         
319     /* Audio samplerate */
320     [fAudRatePopUp removeAllItems];
321     for( int i = 0; i < hb_audio_rates_count; i++ )
322     {
323         [fAudRatePopUp addItemWithTitle:
324             [NSString stringWithCString: hb_audio_rates[i].string]];
325     }
326     [fAudRatePopUp selectItemAtIndex: hb_audio_rates_default];
327         
328     /* Bottom */
329     [fStatusField setStringValue: @""];
330         
331     [self enableUI: NO];
332         [self setupToolbar];
333         
334         [fPresetsActionButton setMenu:fPresetsActionMenu];
335         
336         /* We disable the Turbo 1st pass checkbox since we are not x264 */
337         [fVidTurboPassCheck setEnabled: NO];
338         [fVidTurboPassCheck setState: NSOffState];
339         
340         
341         /* lets get our default prefs here */
342         [self getDefaultPresets: NULL];
343         /* lets initialize the current successful scancount here to 0 */
344         currentSuccessfulScanCount = 0;
345     
346 }
347
348 - (void) TranslateStrings
349 {
350     [fSrcTitleField     setStringValue: _( @"Title:" )];
351     [fSrcChapterField   setStringValue: _( @"Chapters:" )];
352     [fSrcChapterToField setStringValue: _( @"to" )];
353     [fSrcDuration1Field setStringValue: _( @"Duration:" )];
354
355     [fDstFormatField    setStringValue: _( @"Format:" )];
356     [fDstCodecsField    setStringValue: _( @"Codecs:" )];
357     [fDstFile1Field     setStringValue: _( @"File:" )];
358     [fDstBrowseButton   setTitle:       _( @"Browse" )];
359
360     [fVidRateField      setStringValue: _( @"Framerate (fps):" )];
361     [fVidEncoderField   setStringValue: _( @"Encoder:" )];
362     [fVidQualityField   setStringValue: _( @"Quality:" )];
363 }
364
365
366 - (void) enableUI: (bool) b
367 {
368     NSControl * controls[] =
369       { fSrcTitleField, fSrcTitlePopUp,
370         fSrcChapterField, fSrcChapterStartPopUp, fSrcChapterToField,
371         fSrcChapterEndPopUp, fSrcDuration1Field, fSrcDuration2Field,
372         fDstFormatField, fDstFormatPopUp, fDstCodecsField,
373         fDstCodecsPopUp, fDstFile1Field, fDstFile2Field,
374         fDstBrowseButton, fVidRateField, fVidRatePopUp,
375         fVidEncoderField, fVidEncoderPopUp, fVidQualityField,
376         fVidQualityMatrix, fVidGrayscaleCheck, fSubField, fSubPopUp,
377         fAudLang1Field, fAudLang1PopUp, fAudLang2Field, fAudLang2PopUp,
378         fAudTrack1MixLabel, fAudTrack1MixPopUp, fAudTrack2MixLabel, fAudTrack2MixPopUp,
379         fAudRateField, fAudRatePopUp, fAudBitrateField,
380         fAudBitratePopUp, fPictureButton,fQueueStatus, 
381                 fPicSrcWidth,fPicSrcHeight,fPicSettingWidth,fPicSettingHeight,fPicSettingARkeep,
382                 fPicSettingDeinterlace,fPicLabelSettings,fPicLabelSrc,fPicLabelOutp,
383                 fPicLabelAr,fPicLabelDeinterlace,fPicLabelSrcX,fPicLabelOutputX,
384                 fPicLabelPAROutputX,fPicSettingPARWidth,fPicSettingPARHeight,
385                 fPicSettingPAR,fPicLabelAnamorphic,tableView,fPresetsAdd,fPresetsDelete,
386                 fCreateChapterMarkers,fVidTurboPassCheck,fDstMpgLargeFileCheck,fPicLabelAutoCrop,
387                 fPicSettingAutoCrop,fPicSettingDetelecine,fPicLabelDetelecine,fPicLabelDenoise,fPicSettingDenoise,
388         fSubForcedCheck,fPicSettingDeblock,fPicLabelDeblock,};
389
390     for( unsigned i = 0;
391          i < sizeof( controls ) / sizeof( NSControl * ); i++ )
392     {
393         if( [[controls[i] className] isEqualToString: @"NSTextField"] )
394         {
395             NSTextField * tf = (NSTextField *) controls[i];
396             if( ![tf isBezeled] )
397             {
398                 [tf setTextColor: b ? [NSColor controlTextColor] :
399                     [NSColor disabledControlTextColor]];
400                 continue;
401             }
402         }
403         [controls[i] setEnabled: b];
404
405     }
406         
407         if (b) {
408
409         /* if we're enabling the interface, check if the audio mixdown controls need to be enabled or not */
410         /* these will have been enabled by the mass control enablement above anyway, so we're sense-checking it here */
411         [self setEnabledStateOfAudioMixdownControls: NULL];
412         
413         } else {
414
415                 [tableView setEnabled: NO];
416         
417         }
418
419     [self videoMatrixChanged: NULL];
420     [fAdvancedOptions enableUI:b];
421 }
422
423
424 /***********************************************************************
425  * UpdateDockIcon
426  ***********************************************************************
427  * Shows a progression bar on the dock icon, filled according to
428  * 'progress' (0.0 <= progress <= 1.0).
429  * Called with progress < 0.0 or progress > 1.0, restores the original
430  * icon.
431  **********************************************************************/
432 - (void) UpdateDockIcon: (float) progress
433 {
434     NSImage * icon;
435     NSData * tiff;
436     NSBitmapImageRep * bmp;
437     uint32_t * pen;
438     uint32_t black = htonl( 0x000000FF );
439     uint32_t red   = htonl( 0xFF0000FF );
440     uint32_t white = htonl( 0xFFFFFFFF );
441     int row_start, row_end;
442     int i, j;
443
444     /* Get application original icon */
445     icon = [NSImage imageNamed: @"NSApplicationIcon"];
446
447     if( progress < 0.0 || progress > 1.0 )
448     {
449         [NSApp setApplicationIconImage: icon];
450         return;
451     }
452
453     /* Get it in a raw bitmap form */
454     tiff = [icon TIFFRepresentationUsingCompression:
455             NSTIFFCompressionNone factor: 1.0];
456     bmp = [NSBitmapImageRep imageRepWithData: tiff];
457     
458     /* Draw the progression bar */
459     /* It's pretty simple (ugly?) now, but I'm no designer */
460
461     row_start = 3 * (int) [bmp size].height / 4;
462     row_end   = 7 * (int) [bmp size].height / 8;
463
464     for( i = row_start; i < row_start + 2; i++ )
465     {
466         pen = (uint32_t *) ( [bmp bitmapData] + i * [bmp bytesPerRow] );
467         for( j = 0; j < (int) [bmp size].width; j++ )
468         {
469             pen[j] = black;
470         }
471     }
472     for( i = row_start + 2; i < row_end - 2; i++ )
473     {
474         pen = (uint32_t *) ( [bmp bitmapData] + i * [bmp bytesPerRow] );
475         pen[0] = black;
476         pen[1] = black;
477         for( j = 2; j < (int) [bmp size].width - 2; j++ )
478         {
479             if( j < 2 + (int) ( ( [bmp size].width - 4.0 ) * progress ) )
480             {
481                 pen[j] = red;
482             }
483             else
484             {
485                 pen[j] = white;
486             }
487         }
488         pen[j]   = black;
489         pen[j+1] = black;
490     }
491     for( i = row_end - 2; i < row_end; i++ )
492     {
493         pen = (uint32_t *) ( [bmp bitmapData] + i * [bmp bytesPerRow] );
494         for( j = 0; j < (int) [bmp size].width; j++ )
495         {
496             pen[j] = black;
497         }
498     }
499
500     /* Now update the dock icon */
501     tiff = [bmp TIFFRepresentationUsingCompression:
502             NSTIFFCompressionNone factor: 1.0];
503     icon = [[NSImage alloc] initWithData: tiff];
504     [NSApp setApplicationIconImage: icon];
505     [icon release];
506 }
507
508 - (void) updateUI: (NSTimer *) timer
509 {
510
511     hb_list_t  * list;
512     list = hb_get_titles( fHandle );    
513     /* check to see if there has been a new scan done
514         this bypasses the constraints of HB_STATE_WORKING
515         not allowing setting a newly scanned source */
516         int checkScanCount = hb_get_scancount( fHandle );
517         if (checkScanCount > currentScanCount)
518         {
519                 
520                 currentScanCount = checkScanCount;
521                 //[fScanController Cancel: NULL];
522                 [fScanIndicator setIndeterminate: NO];
523                 [fScanIndicator setDoubleValue: 0.0];
524                 [fScanIndicator setHidden: YES];
525
526                 [self showNewScan: NULL];
527         }
528         
529     hb_state_t s;
530     hb_get_state( fHandle, &s );
531         
532         
533     switch( s.state )
534     {
535         case HB_STATE_IDLE:
536                 break;
537 #define p s.param.scanning                      
538         case HB_STATE_SCANNING:
539                 {
540             [fSrcDVD2Field setStringValue: [NSString stringWithFormat:
541                 _( @"Scanning title %d of %d..." ),
542                 p.title_cur, p.title_count]];
543             [fScanIndicator setIndeterminate: NO];
544                         [fScanIndicator setDoubleValue: 100.0 * ( p.title_cur - 1 ) /
545                 p.title_count];
546             break;
547                 }
548 #undef p
549         
550 #define p s.param.scandone
551         case HB_STATE_SCANDONE:
552         {
553                         
554                         [fScanIndicator setIndeterminate: NO];
555             [fScanIndicator setDoubleValue: 0.0];
556                         [fScanIndicator setHidden: YES];
557                         [self showNewScan: NULL];
558             [toolbar validateVisibleItems];
559                         break;
560         }
561 #undef p
562                         
563 #define p s.param.working
564         case HB_STATE_WORKING:
565         {
566             float progress_total;
567             NSMutableString * string;
568                         /* Currently, p.job_cur and p.job_count get screwed up when adding
569                                 jobs during encoding, if they cannot be fixed in libhb, will implement a
570                                 nasty but working cocoa solution */
571                         /* Update text field */
572                         string = [NSMutableString stringWithFormat: _( @"Encoding: task %d of %d, %.2f %%" ), p.job_cur, p.job_count, 100.0 * p.progress];
573             
574                         if( p.seconds > -1 )
575             {
576                 [string appendFormat:
577                     _( @" (%.2f fps, avg %.2f fps, ETA %02dh%02dm%02ds)" ),
578                     p.rate_cur, p.rate_avg, p.hours, p.minutes, p.seconds];
579             }
580             [fStatusField setStringValue: string];
581                         
582             /* Update slider */
583                         progress_total = ( p.progress + p.job_cur - 1 ) / p.job_count;
584             [fRipIndicator setIndeterminate: NO];
585             [fRipIndicator setDoubleValue: 100.0 * progress_total];
586                         
587             // If progress bar hasn't been revealed at the bottom of the window, do
588             // that now. This code used to be in doRip. I moved it to here to handle
589             // the case where hb_start is called by HBQueueController and not from
590             // HBController.
591             if (!fRipIndicatorShown)
592             {
593                 NSRect frame = [fWindow frame];
594                 if (frame.size.width <= 591)
595                     frame.size.width = 591;
596                 frame.size.height += 36;
597                 frame.origin.y -= 36;
598                 [fWindow setFrame:frame display:YES animate:YES];
599                 fRipIndicatorShown = YES;
600                 /* We check to see if we need to warn the user that the computer will go to sleep
601                    or shut down when encoding is finished */
602                 [self remindUserOfSleepOrShutdown];
603             }
604
605             /* Update dock icon */
606             [self UpdateDockIcon: progress_total];
607                         
608             // Has current job changed? That means the queue has probably changed as
609                         // well so update it
610             [fQueueController hblibStateChanged: s];
611             
612             break;
613         }
614 #undef p
615                         
616 #define p s.param.muxing
617         case HB_STATE_MUXING:
618         {
619             NSMutableString * string;
620                         
621             /* Update text field */
622             string = [NSMutableString stringWithFormat:
623                 _( @"Muxing..." )];
624             [fStatusField setStringValue: string];
625                         
626             /* Update slider */
627             [fRipIndicator setIndeterminate: YES];
628             [fRipIndicator startAnimation: nil];
629                         
630             /* Update dock icon */
631             [self UpdateDockIcon: 1.0];
632                         
633                         // Pass along the info to HBQueueController
634             [fQueueController hblibStateChanged: s];
635                         
636             break;
637         }
638 #undef p
639                         
640         case HB_STATE_PAUSED:
641                     [fStatusField setStringValue: _( @"Paused" )];
642             
643                         // Pass along the info to HBQueueController
644             [fQueueController hblibStateChanged: s];
645
646             break;
647                         
648         case HB_STATE_WORKDONE:
649         {
650             // HB_STATE_WORKDONE happpens as a result of hblib finishing all its jobs
651             // or someone calling hb_stop. In the latter case, hb_stop does not clear
652             // out the remaining passes/jobs in the queue. We'll do that here.
653                         
654             // Delete all remaining scans of this job, ie, delete whole encodes.
655             hb_job_t * job;
656             while( ( job = hb_job( fHandle, 0 ) ) && (job->sequence_id != 0) )
657                 hb_rem( fHandle, job );
658
659             // Start processing back up if jobs still left in queue
660             if (hb_count(fHandle) > 0)
661             {
662                 hb_start(fHandle);
663                 fEncodeState = 1;
664                 // Validate the toolbar (hack). The toolbar will usually get autovalidated
665                 // before we had the chance to restart the queue, hence it will now be in
666                 // the wrong state.
667                 [toolbar validateVisibleItems];
668                 break;
669             }
670
671             [fStatusField setStringValue: _( @"Done." )];
672             [fRipIndicator setIndeterminate: NO];
673             [fRipIndicator setDoubleValue: 0.0];
674             [toolbar validateVisibleItems];
675
676             /* Restore dock icon */
677             [self UpdateDockIcon: -1.0];
678
679             if (fRipIndicatorShown)
680             {
681                 NSRect frame = [fWindow frame];
682                 if (frame.size.width <= 591)
683                                     frame.size.width = 591;
684                 frame.size.height += -36;
685                 frame.origin.y -= -36;
686                 [fWindow setFrame:frame display:YES animate:YES];
687                                 fRipIndicatorShown = NO;
688                         }
689                         
690                         // Pass along the info to HBQueueController
691             [fQueueController hblibStateChanged: s];
692                         
693             /* Check to see if the encode state has not been cancelled
694                                 to determine if we should check for encode done notifications */
695                         if (fEncodeState != 2)                  {
696                                 /* If Growl Notification or Window and Growl has been selected */
697                                 if ([[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Growl Notification"] || 
698                                         [[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Alert Window And Growl"])
699                 {
700                                         /*Growl Notification*/
701                                         [self showGrowlDoneNotification: NULL];
702                 }
703                 /* If Alert Window or Window and Growl has been selected */
704                                 if ([[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Alert Window"] || 
705                                         [[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Alert Window And Growl"])
706                 {
707                                         /*On Screen Notification*/
708                                         int status;
709                                         NSBeep();
710                                         status = NSRunAlertPanel(@"Put down that cocktail...",@"Your HandBrake encode is done!", @"OK", nil, nil);
711                                         [NSApp requestUserAttention:NSCriticalRequest];
712                                         if ( status == NSAlertDefaultReturn ) 
713                                         {
714                                                 [self enableUI: YES];
715                                         }
716                 }
717                                 else
718                                 {
719                                         [self enableUI: YES];
720                                 }
721                                    /* If sleep has been selected */ 
722             if ([[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Put Computer To Sleep"]) 
723                 { 
724                /* Sleep */ 
725                NSDictionary* errorDict; 
726                NSAppleEventDescriptor* returnDescriptor = NULL; 
727                NSAppleScript* scriptObject = [[NSAppleScript alloc] initWithSource: 
728                         @"tell application \"Finder\" to sleep"]; 
729                returnDescriptor = [scriptObject executeAndReturnError: &errorDict]; 
730                [scriptObject release]; 
731                [self enableUI: YES]; 
732                 } 
733             /* If Shutdown has been selected */ 
734             if ([[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Shut Down Computer"]) 
735                 { 
736                /* Shut Down */ 
737                NSDictionary* errorDict; 
738                NSAppleEventDescriptor* returnDescriptor = NULL; 
739                NSAppleScript* scriptObject = [[NSAppleScript alloc] initWithSource: 
740                         @"tell application \"Finder\" to shut down"]; 
741                returnDescriptor = [scriptObject executeAndReturnError: &errorDict]; 
742                [scriptObject release]; 
743                [self enableUI: YES]; 
744                 }
745                         
746                                                 // MetaX insertion via AppleScript
747                         if([[NSUserDefaults standardUserDefaults] boolForKey: @"sendToMetaX"] == YES)
748                         {
749                         NSAppleScript *myScript = [[NSAppleScript alloc] initWithSource: [NSString stringWithFormat: @"%@%@%@", @"tell application \"MetaX\" to open (POSIX file \"", [fDstFile2Field stringValue], @"\")"]];
750                         [myScript executeAndReturnError: nil];
751                         [myScript release];
752                         }
753                         
754                         
755                         }
756                         else
757                         {
758                                 [self enableUI: YES];
759                         }
760             break;
761         }
762     }
763         
764     /* Lets show the queue status here in the main window */
765         int queue_count = hb_count( fHandle );
766         if( queue_count )
767         {
768                 [fQueueStatus setStringValue: [NSString stringWithFormat:
769                         @"%d pass%s in the queue",
770                                                  queue_count, ( queue_count > 1 ) ? "es" : ""]];
771         }
772         else
773         {
774                 [fQueueStatus setStringValue: @""];
775         }
776 }
777
778
779 #pragma mark -
780 #pragma mark Toolbar
781 // ============================================================
782 // NSToolbar Related Methods
783 // ============================================================
784
785 - (void) setupToolbar {
786     toolbar = [[[NSToolbar alloc] initWithIdentifier: @"HandBrake Toolbar"] autorelease];
787     
788     [toolbar setAllowsUserCustomization: YES];
789     [toolbar setAutosavesConfiguration: YES];
790     [toolbar setDisplayMode: NSToolbarDisplayModeIconAndLabel];
791     
792     [toolbar setDelegate: self];
793     
794     [fWindow setToolbar: toolbar];
795 }
796
797 - (NSToolbarItem *) toolbar: (NSToolbar *)toolbar itemForItemIdentifier:
798     (NSString *) itemIdent willBeInsertedIntoToolbar:(BOOL) willBeInserted {
799     NSToolbarItem * item = [[NSToolbarItem alloc] initWithItemIdentifier: itemIdent];
800     
801     if ([itemIdent isEqualToString: ToggleDrawerIdentifier])
802     {
803         [item setLabel: @"Toggle Presets"];
804         [item setPaletteLabel: @"Toggler Presets"];
805         [item setToolTip: @"Open/Close Preset Drawer"];
806         [item setImage: [NSImage imageNamed: @"Drawer"]];
807         [item setTarget: self];
808         [item setAction: @selector(toggleDrawer:)];
809         [item setAutovalidates: NO];
810     }
811     else if ([itemIdent isEqualToString: StartEncodingIdentifier])
812     {
813         [item setLabel: @"Start"];
814         [item setPaletteLabel: @"Start Encoding"];
815         [item setToolTip: @"Start Encoding"];
816         [item setImage: [NSImage imageNamed: @"Play"]];
817         [item setTarget: self];
818         [item setAction: @selector(Rip:)];
819     }
820     else if ([itemIdent isEqualToString: ShowQueueIdentifier])
821     {
822         [item setLabel: @"Show Queue"];
823         [item setPaletteLabel: @"Show Queue"];
824         [item setToolTip: @"Show Queue"];
825         [item setImage: [NSImage imageNamed: @"Queue"]];
826         [item setTarget: self];
827         [item setAction: @selector(showQueueWindow:)];
828         [item setAutovalidates: NO];
829     }
830     else if ([itemIdent isEqualToString: AddToQueueIdentifier])
831     {
832         [item setLabel: @"Add to Queue"];
833         [item setPaletteLabel: @"Add to Queue"];
834         [item setToolTip: @"Add to Queue"];
835         [item setImage: [NSImage imageNamed: @"AddToQueue"]];
836         [item setTarget: self];
837         [item setAction: @selector(addToQueue:)];
838     }
839     else if ([itemIdent isEqualToString: PauseEncodingIdentifier])
840     {
841         [item setLabel: @"Pause"];
842         [item setPaletteLabel: @"Pause Encoding"];
843         [item setToolTip: @"Pause Encoding"];
844         [item setImage: [NSImage imageNamed: @"Pause"]];
845         [item setTarget: self];
846         [item setAction: @selector(Pause:)];
847     }
848     else if ([itemIdent isEqualToString: ShowActivityIdentifier]) {
849         [item setLabel: @"Activity Window"];
850         [item setPaletteLabel: @"Show Activity Window"];
851         [item setToolTip: @"Show Activity Window"];
852         [item setImage: [NSImage imageNamed: @"ActivityWindow"]];
853         [item setTarget: self];
854         [item setAction: @selector(showDebugOutputPanel:)];
855         [item setAutovalidates: NO];
856     }
857     else if ([itemIdent isEqualToString: ChooseSourceIdentifier])
858     {
859         [item setLabel: @"Source"];
860         [item setPaletteLabel: @"Source"];
861         [item setToolTip: @"Choose Video Source"];
862         [item setImage: [NSImage imageNamed: @"Source"]];
863         [item setTarget: self];
864         [item setAction: @selector(browseSources:)];
865     }
866     else
867     {
868         [item release];
869         return nil;
870     }
871
872     return item;
873 }
874
875 - (NSArray *) toolbarDefaultItemIdentifiers: (NSToolbar *) toolbar
876 {
877     return [NSArray arrayWithObjects: ChooseSourceIdentifier, NSToolbarSeparatorItemIdentifier, StartEncodingIdentifier,
878         PauseEncodingIdentifier, AddToQueueIdentifier, ShowQueueIdentifier, NSToolbarFlexibleSpaceItemIdentifier, 
879                 NSToolbarSpaceItemIdentifier, ShowActivityIdentifier, ToggleDrawerIdentifier, nil];
880 }
881
882 - (NSArray *) toolbarAllowedItemIdentifiers: (NSToolbar *) toolbar
883 {
884     return [NSArray arrayWithObjects:  StartEncodingIdentifier, PauseEncodingIdentifier, AddToQueueIdentifier,
885         ChooseSourceIdentifier, ShowQueueIdentifier, ShowActivityIdentifier, ToggleDrawerIdentifier,
886         NSToolbarCustomizeToolbarItemIdentifier, NSToolbarFlexibleSpaceItemIdentifier,
887         NSToolbarSpaceItemIdentifier, NSToolbarSeparatorItemIdentifier, nil];
888 }
889
890 - (BOOL) validateToolbarItem: (NSToolbarItem *) toolbarItem
891 {
892     NSString * ident = [toolbarItem itemIdentifier];
893         
894     if (fHandle)
895     {
896         hb_state_t s;
897         hb_get_state2( fHandle, &s );
898         
899         if (s.state == HB_STATE_WORKING || s.state == HB_STATE_MUXING)
900         {
901             if ([ident isEqualToString: StartEncodingIdentifier])
902             {
903                 [toolbarItem setImage: [NSImage imageNamed: @"Stop"]];
904                 [toolbarItem setLabel: @"Stop"];
905                 [toolbarItem setPaletteLabel: @"Stop"];
906                 [toolbarItem setToolTip: @"Stop Encoding"];
907                 return YES;
908             }
909             if ([ident isEqualToString: PauseEncodingIdentifier])
910             {
911                 [toolbarItem setImage: [NSImage imageNamed: @"Pause"]];
912                 [toolbarItem setLabel: @"Pause"];
913                 [toolbarItem setPaletteLabel: @"Pause Encoding"];
914                 [toolbarItem setToolTip: @"Pause Encoding"];
915                 return YES;
916             }
917             if (SuccessfulScan)
918                 if ([ident isEqualToString: AddToQueueIdentifier])
919                     return YES;
920         }
921         else if (s.state == HB_STATE_PAUSED)
922         {
923             if ([ident isEqualToString: PauseEncodingIdentifier])
924             {
925                 [toolbarItem setImage: [NSImage imageNamed: @"Play"]];
926                 [toolbarItem setLabel: @"Resume"];
927                 [toolbarItem setPaletteLabel: @"Resume Encoding"];
928                 [toolbarItem setToolTip: @"Resume Encoding"];
929                 return YES;
930             }
931             if ([ident isEqualToString: StartEncodingIdentifier])
932                 return YES;
933             if ([ident isEqualToString: AddToQueueIdentifier])
934                 return YES;
935         }
936         else if (s.state == HB_STATE_SCANNING)
937             return NO;
938         else if (s.state == HB_STATE_WORKDONE || s.state == HB_STATE_SCANDONE || SuccessfulScan)
939         {
940             if ([ident isEqualToString: StartEncodingIdentifier])
941             {
942                 [toolbarItem setImage: [NSImage imageNamed: @"Play"]];
943                 if (hb_count(fHandle) > 0)
944                     [toolbarItem setLabel: @"Start Queue"];
945                 else
946                     [toolbarItem setLabel: @"Start"];
947                 [toolbarItem setPaletteLabel: @"Start Encoding"];
948                 [toolbarItem setToolTip: @"Start Encoding"];
949                 return YES;
950             }
951             if ([ident isEqualToString: AddToQueueIdentifier])
952                 return YES;
953         }
954
955     }
956     
957     if ([ident isEqualToString: ShowQueueIdentifier])
958         return YES;
959     if ([ident isEqualToString: ToggleDrawerIdentifier])
960         return YES;
961     if ([ident isEqualToString: ChooseSourceIdentifier])
962         return YES;
963     if ([ident isEqualToString: ShowActivityIdentifier])
964         return YES;
965     
966     return NO;
967 }
968
969 - (BOOL) validateMenuItem: (NSMenuItem *) menuItem
970 {
971     SEL action = [menuItem action];
972     
973     hb_state_t s;
974     hb_get_state2( fHandle, &s );
975     
976     if (fHandle)
977     {
978         if (action == @selector(addToQueue:) || action == @selector(showPicturePanel:) || action == @selector(showAddPresetPanel:))
979             return SuccessfulScan && [fWindow attachedSheet] == nil;
980         
981         if (action == @selector(browseSources:))
982         {
983             if (s.state == HB_STATE_SCANNING)
984                 return NO;
985             else
986                 return [fWindow attachedSheet] == nil;
987         }
988         if (action == @selector(selectDefaultPreset:))
989             return [tableView selectedRow] >= 0 && [fWindow attachedSheet] == nil;
990         if (action == @selector(Pause:))
991         {
992             if (s.state == HB_STATE_WORKING)
993             {
994                 if(![[menuItem title] isEqualToString:@"Pause Encoding"])
995                     [menuItem setTitle:@"Pause Encoding"];
996                 return YES;
997             }
998             else if (s.state == HB_STATE_PAUSED)
999             {
1000                 if(![[menuItem title] isEqualToString:@"Resume Encoding"])
1001                     [menuItem setTitle:@"Resume Encoding"];
1002                 return YES;
1003             }
1004             else
1005                 return NO;
1006         }
1007         if (action == @selector(Rip:))
1008             if (s.state == HB_STATE_WORKING || s.state == HB_STATE_MUXING || s.state == HB_STATE_PAUSED)
1009             {
1010                 if(![[menuItem title] isEqualToString:@"Stop Encoding"])
1011                     [menuItem setTitle:@"Stop Encoding"];
1012                 return YES;
1013             }
1014             else if (SuccessfulScan)
1015             {
1016                 if(![[menuItem title] isEqualToString:@"Start Encoding"])
1017                     [menuItem setTitle:@"Start Encoding"];
1018                 return [fWindow attachedSheet] == nil;
1019             }
1020             else
1021                 return NO;
1022         }
1023     
1024     return YES;
1025 }
1026
1027 #pragma mark -
1028 #pragma mark Growl
1029 // register a test notification and make
1030 // it enabled by default
1031 #define SERVICE_NAME @"Encode Done"
1032 - (NSDictionary *)registrationDictionaryForGrowl 
1033
1034     NSDictionary *registrationDictionary = [NSDictionary dictionaryWithObjectsAndKeys: 
1035     [NSArray arrayWithObjects:SERVICE_NAME,nil], GROWL_NOTIFICATIONS_ALL, 
1036     [NSArray arrayWithObjects:SERVICE_NAME,nil], GROWL_NOTIFICATIONS_DEFAULT, 
1037     nil]; 
1038
1039     return registrationDictionary; 
1040
1041
1042 -(IBAction)showGrowlDoneNotification:(id)sender
1043 {
1044   [GrowlApplicationBridge 
1045             notifyWithTitle:@"Put down that cocktail..." 
1046                 description:@"your HandBrake encode is done!" 
1047            notificationName:SERVICE_NAME
1048                    iconData:nil 
1049                    priority:0 
1050                    isSticky:1 
1051                clickContext:nil];
1052 }
1053
1054 #pragma mark -
1055 #pragma mark Get New Source
1056
1057 /*Opens the source browse window, called from Open Source widgets */
1058 - (IBAction) browseSources: (id) sender
1059 {
1060     [self enableUI: NO];
1061     NSOpenPanel * panel;
1062         
1063     panel = [NSOpenPanel openPanel];
1064     [panel setAllowsMultipleSelection: NO];
1065     [panel setCanChooseFiles: YES];
1066     [panel setCanChooseDirectories: YES ];
1067     NSString * sourceDirectory;
1068         if ([[NSUserDefaults standardUserDefaults] stringForKey:@"LastSourceDirectory"])
1069         {
1070                 sourceDirectory = [[NSUserDefaults standardUserDefaults] stringForKey:@"LastSourceDirectory"];
1071         }
1072         else
1073         {
1074                 sourceDirectory = @"~/Desktop";
1075                 sourceDirectory = [sourceDirectory stringByExpandingTildeInPath];
1076         }
1077     /* we open up the browse sources sheet here and call for browseSourcesDone after the sheet is closed
1078         * to evaluate whether we want to specify a title, we pass the sender in the contextInfo variable
1079         */
1080     [panel beginSheetForDirectory: sourceDirectory file: nil types: nil
1081                    modalForWindow: fWindow modalDelegate: self
1082                    didEndSelector: @selector( browseSourcesDone:returnCode:contextInfo: )
1083                       contextInfo: sender]; 
1084 }
1085
1086 - (void) browseSourcesDone: (NSOpenPanel *) sheet
1087                 returnCode: (int) returnCode contextInfo: (void *) contextInfo
1088 {
1089     /* we convert the sender content of contextInfo back into a variable called sender
1090     * mostly just for consistency for evaluation later
1091     */
1092     id sender = (id)contextInfo;
1093     /* User selected a file to open */
1094         if( returnCode == NSOKButton )
1095     {
1096         
1097         NSString *scanPath = [[sheet filenames] objectAtIndex: 0];
1098         /* we set the last searched source directory in the prefs here */
1099         NSString *sourceDirectory = [scanPath stringByDeletingLastPathComponent];
1100         [[NSUserDefaults standardUserDefaults] setObject:sourceDirectory forKey:@"LastSourceDirectory"];
1101         /* we order out sheet, which is the browse window as we need to open
1102             * the title selection sheet right away
1103             */
1104         [sheet orderOut: self];
1105         
1106         if (sender == fOpenSourceTitleMMenu)
1107         {
1108             /* We put the chosen source path in the source display text field for the
1109             * source title selection sheet in which the user specifies the specific title to be
1110             * scanned  as well as the short source name in fSrcDsplyNameTitleScan just for display
1111             * purposes in the title panel
1112             */
1113             /* Full Path */
1114             [fScanSrcTitlePathField setStringValue: [NSString stringWithFormat:@"%@", scanPath]];
1115             NSString *displayTitlescanSourceName;
1116             
1117             if ([[scanPath lastPathComponent] isEqualToString: @"VIDEO_TS"])
1118             {
1119                 /* If VIDEO_TS Folder is chosen, choose its parent folder for the source display name 
1120                 we have to use the title->dvd value so we get the proper name of the volume if a physical dvd is the source*/
1121                 displayTitlescanSourceName = [NSString stringWithFormat:[[scanPath stringByDeletingLastPathComponent] lastPathComponent]];
1122             }
1123             else
1124             {
1125                 /* if not the VIDEO_TS Folder, we can assume the chosen folder is the source name */
1126                 displayTitlescanSourceName = [NSString stringWithFormat:[scanPath lastPathComponent]];
1127             }
1128             /* we set the source display name in the title selection dialogue */
1129             [fSrcDsplyNameTitleScan setStringValue: [NSString stringWithFormat:@"%@", displayTitlescanSourceName]];
1130             /* We show the actual sheet where the user specifies the title to be scanned 
1131                 * as we are going to do a title specific scan
1132                 */
1133             [self showSourceTitleScanPanel:NULL];
1134         }
1135         else
1136         {
1137             /* We are just doing a standard full source scan, so we specify "0" to libhb */
1138             NSString *path = [[sheet filenames] objectAtIndex: 0];
1139             [self performScan:path scanTitleNum:0];   
1140         }
1141         
1142     }
1143     else // User clicked Cancel in browse window
1144     {
1145         /* if we have a title loaded up */
1146         if ([[fSrcDVD2Field stringValue] length] > 0)
1147         {
1148             [self enableUI: YES];
1149         }
1150     }
1151 }
1152
1153 /* Here we open the title selection sheet where we can specify an exact title to be scanned */
1154 - (IBAction) showSourceTitleScanPanel: (id) sender
1155 {
1156     /* We default the title number to be scanned to "0" which results in a full source scan, unless the
1157     * user changes it
1158     */
1159     [fScanSrcTitleNumField setStringValue: @"0"];
1160         /* Show the panel */
1161         [NSApp beginSheet: fScanSrcTitlePanel modalForWindow: fWindow modalDelegate: NULL didEndSelector: NULL contextInfo: NULL];
1162 }
1163
1164 - (IBAction) closeSourceTitleScanPanel: (id) sender
1165 {
1166     [NSApp endSheet: fScanSrcTitlePanel];
1167     [fScanSrcTitlePanel orderOut: self];
1168     
1169     
1170     
1171     if(sender == fScanSrcTitleOpenButton)
1172     {
1173         /* We setup the scan status in the main window to indicate a source title scan */
1174         [fSrcDVD2Field setStringValue: _( @"Opening a new source title ..." )];
1175                 [fScanIndicator setHidden: NO];
1176             [fScanIndicator setIndeterminate: YES];
1177         [fScanIndicator startAnimation: nil];
1178                 
1179         /* We use the performScan method to actually perform the specified scan passing the path and the title
1180             * to be scanned
1181             */
1182         [self performScan:[fScanSrcTitlePathField stringValue] scanTitleNum:[fScanSrcTitleNumField intValue]];
1183     }
1184 }
1185
1186
1187 /* Here we actually tell hb_scan to perform the source scan, using the path to source and title number*/
1188 - (void) performScan:(NSString *) scanPath scanTitleNum: (int) scanTitleNum
1189 {
1190     NSString *path = scanPath;
1191     HBDVDDetector *detector = [HBDVDDetector detectorForPath:path];
1192     if( [detector isVideoDVD] )
1193     {
1194         // The chosen path was actually on a DVD, so use the raw block
1195         // device path instead.
1196         path = [detector devicePath];
1197     }
1198     /* If there is no title number passed to scan, we use "0"
1199         * which causes the default behavior of a full source scan
1200     */
1201     if (!scanTitleNum)
1202     {
1203         scanTitleNum = 0;
1204     }
1205     hb_scan( fHandle, [path UTF8String], scanTitleNum );
1206 }
1207
1208 - (IBAction) showNewScan:(id)sender
1209 {
1210         hb_list_t  * list;
1211         hb_title_t * title;
1212         int indxpri=0;    // Used to search the longuest title (default in combobox)
1213         int longuestpri=0; // Used to search the longuest title (default in combobox)
1214         
1215         list = hb_get_titles( fHandle );
1216         
1217         if( !hb_list_count( list ) )
1218         {
1219                 /* We display a message if a valid dvd source was not chosen */
1220                 [fSrcDVD2Field setStringValue: @"No Valid Title Found"];
1221         SuccessfulScan = NO;
1222         }
1223         else
1224         {
1225         /* We increment the successful scancount here by one,
1226         which we use at the end of this function to tell the gui
1227         if this is the first successful scan since launch and whether
1228         or not we should set all settings to the defaults */
1229                 
1230         currentSuccessfulScanCount++;
1231         
1232         [toolbar validateVisibleItems];
1233                 
1234                 [fSrcTitlePopUp removeAllItems];
1235                 for( int i = 0; i < hb_list_count( list ); i++ )
1236                 {
1237                         title = (hb_title_t *) hb_list_item( list, i );
1238                         
1239             currentSource = [NSString stringWithUTF8String: title->name];
1240             
1241             /* To get the source name as well as the default output name, first we check to see if
1242                 the selected directory is the VIDEO_TS Directory */
1243             if ([[currentSource lastPathComponent] isEqualToString: @"VIDEO_TS"])
1244             {
1245                 /* If VIDEO_TS Folder is chosen, choose its parent folder for the source display name 
1246                 we have to use the title->dvd value so we get the proper name of the volume if a physical dvd is the source*/
1247                 sourceDisplayName = [NSString stringWithFormat:[[[NSString stringWithUTF8String: title->dvd] stringByDeletingLastPathComponent] lastPathComponent]];
1248             }
1249             else
1250             {
1251                 /* if not the VIDEO_TS Folder, we can assume the chosen folder is the source name */
1252                 sourceDisplayName = [NSString stringWithFormat:[currentSource lastPathComponent]];
1253             }
1254                         /*Set DVD Name at top of window*/
1255                         [fSrcDVD2Field setStringValue:[NSString stringWithFormat: @"%@", sourceDisplayName]];
1256                         
1257                         /* Use the dvd name in the default output field here 
1258                                 May want to add code to remove blank spaces for some dvd names*/
1259                         /* Check to see if the last destination has been set,use if so, if not, use Desktop */
1260                         if ([[NSUserDefaults standardUserDefaults] stringForKey:@"LastDestinationDirectory"])
1261                         {
1262                                 [fDstFile2Field setStringValue: [NSString stringWithFormat:
1263                                         @"%@/%@.mp4", [[NSUserDefaults standardUserDefaults] stringForKey:@"LastDestinationDirectory"],sourceDisplayName]];
1264                         }
1265                         else
1266                         {
1267                                 [fDstFile2Field setStringValue: [NSString stringWithFormat:
1268                                         @"%@/Desktop/%@.mp4", NSHomeDirectory(),sourceDisplayName]];
1269                         }
1270                         
1271                         if (longuestpri < title->hours*60*60 + title->minutes *60 + title->seconds)
1272                         {
1273                                 longuestpri=title->hours*60*60 + title->minutes *60 + title->seconds;
1274                                 indxpri=i;
1275                         }
1276                         
1277                         [self formatPopUpChanged:NULL];
1278                         
1279             [fSrcTitlePopUp addItemWithTitle: [NSString
1280                 stringWithFormat: @"%d - %02dh%02dm%02ds",
1281                 title->index, title->hours, title->minutes,
1282                 title->seconds]];
1283                 }
1284         
1285                 // Select the longuest title
1286                 [fSrcTitlePopUp selectItemAtIndex: indxpri];
1287                 [self titlePopUpChanged: NULL];
1288                 
1289         SuccessfulScan = YES;
1290                 [self enableUI: YES];
1291                 
1292                 /* if its the initial successful scan after awakeFromNib */
1293         if (currentSuccessfulScanCount == 1)
1294         {
1295             [self selectDefaultPreset: NULL];
1296             /* if Deinterlace upon launch is specified in the prefs, then set to 1 for "Fast",
1297             if not, then set to 0 for none */
1298             if ([[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultDeinterlaceOn"] > 0)
1299                 [fPictureController setDeinterlace:1];
1300             else
1301                 [fPictureController setDeinterlace:0];
1302         }
1303         
1304         }
1305 }
1306
1307
1308 #pragma mark -
1309 #pragma mark New Output Destination
1310
1311 - (IBAction) browseFile: (id) sender
1312 {
1313     /* Open a panel to let the user choose and update the text field */
1314     NSSavePanel * panel = [NSSavePanel savePanel];
1315         /* We get the current file name and path from the destination field here */
1316         [panel beginSheetForDirectory: [[fDstFile2Field stringValue] stringByDeletingLastPathComponent] file: [[fDstFile2Field stringValue] lastPathComponent]
1317                                    modalForWindow: fWindow modalDelegate: self
1318                                    didEndSelector: @selector( browseFileDone:returnCode:contextInfo: )
1319                                           contextInfo: NULL];
1320 }
1321
1322 - (void) browseFileDone: (NSSavePanel *) sheet
1323     returnCode: (int) returnCode contextInfo: (void *) contextInfo
1324 {
1325     if( returnCode == NSOKButton )
1326     {
1327         [fDstFile2Field setStringValue: [sheet filename]];
1328     }
1329 }
1330
1331
1332 #pragma mark -
1333 #pragma mark Main Window Control
1334
1335 - (IBAction) openMainWindow: (id) sender
1336 {
1337     [fWindow  makeKeyAndOrderFront:nil];
1338 }
1339
1340 - (BOOL) windowShouldClose: (id) sender
1341 {
1342     return YES;
1343 }
1344
1345 - (BOOL)applicationShouldHandleReopen:(NSApplication *)theApplication hasVisibleWindows:(BOOL)flag
1346 {
1347     if( !flag ) {
1348         [fWindow  makeKeyAndOrderFront:nil];
1349                 
1350         return YES;
1351     }
1352     
1353     return NO;
1354 }
1355
1356 #pragma mark -
1357 #pragma mark Job Handling
1358
1359
1360 - (void) prepareJob
1361 {
1362     hb_list_t  * list  = hb_get_titles( fHandle );
1363     hb_title_t * title = (hb_title_t *) hb_list_item( list,
1364             [fSrcTitlePopUp indexOfSelectedItem] );
1365     hb_job_t * job = title->job;
1366     //int i;
1367
1368     /* Chapter selection */
1369     job->chapter_start = [fSrcChapterStartPopUp indexOfSelectedItem] + 1;
1370     job->chapter_end   = [fSrcChapterEndPopUp   indexOfSelectedItem] + 1;
1371         
1372     /* Format and codecs */
1373     int format = [fDstFormatPopUp indexOfSelectedItem];
1374     int codecs = [fDstCodecsPopUp indexOfSelectedItem];
1375     job->mux    = FormatSettings[format][codecs] & HB_MUX_MASK;
1376     job->vcodec = FormatSettings[format][codecs] & HB_VCODEC_MASK;
1377     job->acodec = FormatSettings[format][codecs] & HB_ACODEC_MASK;
1378     /* If mpeg-4, then set mpeg-4 specific options like chapters and > 4gb file sizes */
1379         if ([fDstFormatPopUp indexOfSelectedItem] == 0)
1380         {
1381         /* We set the largeFileSize (64 bit formatting) variable here to allow for > 4gb files based on the format being
1382                 mpeg4 and the checkbox being checked 
1383                 *Note: this will break compatibility with some target devices like iPod, etc.!!!!*/
1384                 if ([[NSUserDefaults standardUserDefaults] boolForKey:@"AllowLargeFiles"] > 0 && [fDstMpgLargeFileCheck state] == NSOnState)
1385                 {
1386                         job->largeFileSize = 1;
1387                 }
1388                 else
1389                 {
1390                         job->largeFileSize = 0;
1391                 }
1392         }
1393         if ([fDstFormatPopUp indexOfSelectedItem] == 0 || [fDstFormatPopUp indexOfSelectedItem] == 3)
1394         {
1395           /* We set the chapter marker extraction here based on the format being
1396                 mpeg4 or mkv and the checkbox being checked */
1397                 if ([fCreateChapterMarkers state] == NSOnState)
1398                 {
1399                         job->chapter_markers = 1;
1400                 }
1401                 else
1402                 {
1403                         job->chapter_markers = 0;
1404                 }
1405         }
1406         if( ( job->vcodec & HB_VCODEC_FFMPEG ) &&
1407         [fVidEncoderPopUp indexOfSelectedItem] > 0 )
1408     {
1409         job->vcodec = HB_VCODEC_XVID;
1410     }
1411     if( job->vcodec & HB_VCODEC_X264 )
1412     {
1413                 if ([fVidEncoderPopUp indexOfSelectedItem] > 0 )
1414             {
1415                         /* Just use new Baseline Level 3.0 
1416                         Lets Deprecate Baseline Level 1.3h264_level*/
1417                         job->h264_level = 30;
1418                         job->mux = HB_MUX_IPOD;
1419                         /* move sanity check for iPod Encoding here */
1420                         job->pixel_ratio = 0 ;
1421                         
1422                 }
1423                 
1424                 /* Set this flag to switch from Constant Quantizer(default) to Constant Rate Factor Thanks jbrjake
1425                 Currently only used with Constant Quality setting*/
1426                 if ([[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultCrf"] > 0 && [fVidQualityMatrix selectedRow] == 2)
1427                 {
1428                 job->crf = 1;
1429                 }
1430                 
1431                 /* Below Sends x264 options to the core library if x264 is selected*/
1432                 /* Lets use this as per Nyx, Thanks Nyx!*/
1433                 job->x264opts = (char *)calloc(1024, 1); /* Fixme, this just leaks */
1434                 /* Turbo first pass if two pass and Turbo First pass is selected */
1435                 if( [fVidTwoPassCheck state] == NSOnState && [fVidTurboPassCheck state] == NSOnState )
1436                 {
1437                         /* pass the "Turbo" string to be appended to the existing x264 opts string into a variable for the first pass */
1438                         NSString *firstPassOptStringTurbo = @":ref=1:subme=1:me=dia:analyse=none:trellis=0:no-fast-pskip=0:8x8dct=0";
1439                         /* append the "Turbo" string variable to the existing opts string.
1440                         Note: the "Turbo" string must be appended, not prepended to work properly*/
1441                         NSString *firstPassOptStringCombined = [[fAdvancedOptions optionsString] stringByAppendingString:firstPassOptStringTurbo];
1442                         strcpy(job->x264opts, [firstPassOptStringCombined UTF8String]);
1443                 }
1444                 else
1445                 {
1446                         strcpy(job->x264opts, [[fAdvancedOptions optionsString] UTF8String]);
1447                 }
1448                 
1449         job->h264_13 = [fVidEncoderPopUp indexOfSelectedItem];
1450     }
1451
1452     /* Video settings */
1453     if( [fVidRatePopUp indexOfSelectedItem] > 0 )
1454     {
1455         job->vrate      = 27000000;
1456         job->vrate_base = hb_video_rates[[fVidRatePopUp
1457             indexOfSelectedItem]-1].rate;
1458     }
1459     else
1460     {
1461         job->vrate      = title->rate;
1462         job->vrate_base = title->rate_base;
1463     }
1464
1465     switch( [fVidQualityMatrix selectedRow] )
1466     {
1467         case 0:
1468             /* Target size.
1469                Bitrate should already have been calculated and displayed
1470                in fVidBitrateField, so let's just use it */
1471         case 1:
1472             job->vquality = -1.0;
1473             job->vbitrate = [fVidBitrateField intValue];
1474             break;
1475         case 2:
1476             job->vquality = [fVidQualitySlider floatValue];
1477             job->vbitrate = 0;
1478             break;
1479     }
1480
1481     job->grayscale = ( [fVidGrayscaleCheck state] == NSOnState );
1482
1483     /* Subtitle settings */
1484     job->subtitle = [fSubPopUp indexOfSelectedItem] - 2;
1485
1486     /* Audio tracks and mixdowns */
1487     /* check for the condition where track 2 has an audio selected, but track 1 does not */
1488     /* we will use track 2 as track 1 in this scenario */
1489     if ([fAudLang1PopUp indexOfSelectedItem] > 0)
1490     {
1491         job->audios[0] = [fAudLang1PopUp indexOfSelectedItem] - 1;
1492         job->audios[1] = [fAudLang2PopUp indexOfSelectedItem] - 1; /* will be -1 if "none" is selected */
1493         job->audios[2] = -1;
1494         job->audio_mixdowns[0] = [[fAudTrack1MixPopUp selectedItem] tag];
1495         job->audio_mixdowns[1] = [[fAudTrack2MixPopUp selectedItem] tag];
1496     }
1497     else if ([fAudLang2PopUp indexOfSelectedItem] > 0)
1498     {
1499         job->audios[0] = [fAudLang2PopUp indexOfSelectedItem] - 1;
1500         job->audio_mixdowns[0] = [[fAudTrack2MixPopUp selectedItem] tag];
1501         job->audios[1] = -1;
1502     }
1503     else
1504     {
1505         job->audios[0] = -1;
1506     }
1507
1508     /* Audio settings */
1509     job->arate = hb_audio_rates[[fAudRatePopUp
1510                      indexOfSelectedItem]].rate;
1511     job->abitrate = [[fAudBitratePopUp selectedItem] tag];
1512     
1513     /* set vfr according to the Picture Window */
1514     if ([fPictureController vfr])
1515     {
1516     job->vfr = 1;
1517     }
1518     else
1519     {
1520     job->vfr = 0;
1521     }
1522     
1523     /* Filters */ 
1524     job->filters = hb_list_init();
1525    
1526         /* Detelecine */
1527     if ([fPictureController detelecine])
1528     {
1529         hb_list_add( job->filters, &hb_filter_detelecine );
1530     }
1531    
1532     /* Deinterlace */
1533     if ([fPictureController deinterlace] == 1)
1534     {
1535         /* Run old deinterlacer by default */
1536         hb_filter_deinterlace.settings = "-1"; 
1537         hb_list_add( job->filters, &hb_filter_deinterlace );
1538     }
1539     else if ([fPictureController deinterlace] == 2)
1540     {
1541         /* Yadif mode 0 (1-pass with spatial deinterlacing.) */
1542         hb_filter_deinterlace.settings = "0"; 
1543         hb_list_add( job->filters, &hb_filter_deinterlace );            
1544     }
1545     else if ([fPictureController deinterlace] == 3)
1546     {
1547         /* Yadif (1-pass w/o spatial deinterlacing) and Mcdeint */
1548         hb_filter_deinterlace.settings = "2:-1:1"; 
1549         hb_list_add( job->filters, &hb_filter_deinterlace );            
1550     }
1551     else if ([fPictureController deinterlace] == 4)
1552     {
1553         /* Yadif (2-pass w/ spatial deinterlacing) and Mcdeint*/
1554         hb_filter_deinterlace.settings = "1:-1:1"; 
1555         hb_list_add( job->filters, &hb_filter_deinterlace );            
1556     }
1557         
1558         /* Denoise */
1559         
1560         if ([fPictureController denoise] == 1) // Weak in popup
1561         {
1562                 hb_filter_denoise.settings = "2:1:2:3"; 
1563         hb_list_add( job->filters, &hb_filter_denoise );        
1564         }
1565         else if ([fPictureController denoise] == 2) // Medium in popup
1566         {
1567                 hb_filter_denoise.settings = "3:2:2:3"; 
1568         hb_list_add( job->filters, &hb_filter_denoise );        
1569         }
1570         else if ([fPictureController denoise] == 3) // Strong in popup
1571         {
1572                 hb_filter_denoise.settings = "7:7:5:5"; 
1573         hb_list_add( job->filters, &hb_filter_denoise );        
1574         }
1575     
1576     /* Deblock  (uses pp7 default) */
1577     if ([fPictureController deblock])
1578     {
1579         hb_list_add( job->filters, &hb_filter_deblock );
1580     }
1581
1582 }
1583
1584
1585
1586 /* addToQueue: puts up an alert before ultimately calling doAddToQueue
1587 */
1588 - (IBAction) addToQueue: (id) sender
1589 {
1590         /* We get the destination directory from the destination field here */
1591         NSString *destinationDirectory = [[fDstFile2Field stringValue] stringByDeletingLastPathComponent];
1592         /* We check for a valid destination here */
1593         if ([[NSFileManager defaultManager] fileExistsAtPath:destinationDirectory] == 0) 
1594         {
1595                 NSRunAlertPanel(@"Warning!", @"This is not a valid destination directory!", @"OK", nil, nil);
1596         return;
1597         }
1598
1599     /* We check for duplicate name here */
1600         if( [[NSFileManager defaultManager] fileExistsAtPath:
1601             [fDstFile2Field stringValue]] )
1602     {
1603         NSBeginCriticalAlertSheet( _( @"File already exists" ),
1604             _( @"Cancel" ), _( @"Overwrite" ), NULL, fWindow, self,
1605             @selector( overwriteAddToQueueAlertDone:returnCode:contextInfo: ),
1606             NULL, NULL, [NSString stringWithFormat:
1607             _( @"Do you want to overwrite %@?" ),
1608             [fDstFile2Field stringValue]] );
1609         // overwriteAddToQueueAlertDone: will be called when the alert is dismissed.
1610     }
1611     else
1612     {
1613         [self doAddToQueue];
1614     }
1615 }
1616
1617 /* overwriteAddToQueueAlertDone: called from the alert posted by addToQueue that asks
1618    the user if they want to overwrite an exiting movie file.
1619 */
1620 - (void) overwriteAddToQueueAlertDone: (NSWindow *) sheet
1621     returnCode: (int) returnCode contextInfo: (void *) contextInfo
1622 {
1623     if( returnCode == NSAlertAlternateReturn )
1624         [self doAddToQueue];
1625 }
1626
1627 - (void) doAddToQueue
1628 {
1629     hb_list_t  * list  = hb_get_titles( fHandle );
1630     hb_title_t * title = (hb_title_t *) hb_list_item( list, [fSrcTitlePopUp indexOfSelectedItem] );
1631     hb_job_t * job = title->job;
1632
1633     // Assign a sequence number, starting at zero, to each job added so they can
1634     // be lumped together in the UI.
1635     job->sequence_id = -1;
1636
1637     [self prepareJob];
1638
1639     /* Destination file */
1640     job->file = [[fDstFile2Field stringValue] UTF8String];
1641
1642     if( [fSubForcedCheck state] == NSOnState )
1643         job->subtitle_force = 1;
1644     else
1645         job->subtitle_force = 0;
1646
1647     /*
1648     * subtitle of -1 is a scan
1649     */
1650     if( job->subtitle == -1 )
1651     {
1652         char *x264opts_tmp;
1653
1654         /*
1655         * When subtitle scan is enabled do a fast pre-scan job
1656         * which will determine which subtitles to enable, if any.
1657         */
1658         job->pass = -1;
1659         x264opts_tmp = job->x264opts;
1660         job->subtitle = -1;
1661
1662         job->x264opts = NULL;
1663
1664         job->indepth_scan = 1;  
1665
1666         job->select_subtitle = (hb_subtitle_t**)malloc(sizeof(hb_subtitle_t*));
1667         *(job->select_subtitle) = NULL;
1668
1669         /*
1670         * Add the pre-scan job
1671         */
1672         job->sequence_id++; // for job grouping
1673         hb_add( fHandle, job );
1674
1675         job->x264opts = x264opts_tmp;
1676     }
1677     else
1678         job->select_subtitle = NULL;
1679
1680     /* No subtitle were selected, so reset the subtitle to -1 (which before
1681     * this point meant we were scanning
1682     */
1683     if( job->subtitle == -2 )
1684         job->subtitle = -1;
1685
1686     if( [fVidTwoPassCheck state] == NSOnState )
1687     {
1688         hb_subtitle_t **subtitle_tmp = job->select_subtitle;
1689         job->indepth_scan = 0;
1690
1691         /*
1692          * Do not autoselect subtitles on the first pass of a two pass
1693          */
1694         job->select_subtitle = NULL;
1695         
1696         job->pass = 1;
1697         job->sequence_id++; // for job grouping
1698         hb_add( fHandle, job );
1699
1700         job->pass = 2;
1701         job->sequence_id++; // for job grouping
1702
1703         job->x264opts = (char *)calloc(1024, 1); /* Fixme, this just leaks */  
1704         strcpy(job->x264opts, [[fAdvancedOptions optionsString] UTF8String]);
1705
1706         job->select_subtitle = subtitle_tmp;
1707
1708         hb_add( fHandle, job );
1709     }
1710     else
1711     {
1712         job->indepth_scan = 0;
1713         job->pass = 0;
1714         job->sequence_id++; // for job grouping
1715         hb_add( fHandle, job );
1716     }
1717         
1718     NSString *destinationDirectory = [[fDstFile2Field stringValue] stringByDeletingLastPathComponent];
1719         [[NSUserDefaults standardUserDefaults] setObject:destinationDirectory forKey:@"LastDestinationDirectory"];
1720         
1721     // Notify the queue
1722         [fQueueController hblibJobListChanged];
1723 }
1724
1725 /* Rip: puts up an alert before ultimately calling doRip
1726 */
1727 - (IBAction) Rip: (id) sender
1728 {
1729     /* Rip or Cancel ? */
1730     hb_state_t s;
1731     hb_get_state2( fHandle, &s );
1732
1733     if(s.state == HB_STATE_WORKING || s.state == HB_STATE_PAUSED)
1734         {
1735         [self Cancel: sender];
1736         return;
1737     }
1738     
1739     // If there are jobs in the queue, then this is a rip the queue
1740     
1741     if (hb_count( fHandle ) > 0)
1742     {
1743         [self doRip];
1744         return;
1745     }
1746
1747     // Before adding jobs to the queue, check for a valid destination.
1748
1749     NSString *destinationDirectory = [[fDstFile2Field stringValue] stringByDeletingLastPathComponent];
1750     if ([[NSFileManager defaultManager] fileExistsAtPath:destinationDirectory] == 0) 
1751     {
1752         NSRunAlertPanel(@"Warning!", @"This is not a valid destination directory!", @"OK", nil, nil);
1753         return;
1754     }
1755
1756     /* We check for duplicate name here */
1757     if( [[NSFileManager defaultManager] fileExistsAtPath:[fDstFile2Field stringValue]] )
1758     {
1759         NSBeginCriticalAlertSheet( _( @"File already exists" ),
1760             _( @"Cancel" ), _( @"Overwrite" ), NULL, fWindow, self,
1761             @selector( overWriteAlertDone:returnCode:contextInfo: ),
1762             NULL, NULL, [NSString stringWithFormat:
1763             _( @"Do you want to overwrite %@?" ),
1764             [fDstFile2Field stringValue]] );
1765             
1766         // overWriteAlertDone: will be called when the alert is dismissed. It will call doRip.
1767     }
1768     else
1769     {
1770         /* if there are no jobs in the queue, then add this one to the queue and rip 
1771         otherwise, just rip the queue */
1772         if( hb_count( fHandle ) == 0)
1773         {
1774             [self doAddToQueue];
1775         }
1776
1777         NSString *destinationDirectory = [[fDstFile2Field stringValue] stringByDeletingLastPathComponent];
1778         [[NSUserDefaults standardUserDefaults] setObject:destinationDirectory forKey:@"LastDestinationDirectory"];
1779         [self doRip];
1780     }
1781 }
1782
1783 /* overWriteAlertDone: called from the alert posted by Rip: that asks the user if they
1784    want to overwrite an exiting movie file.
1785 */
1786 - (void) overWriteAlertDone: (NSWindow *) sheet
1787     returnCode: (int) returnCode contextInfo: (void *) contextInfo
1788 {
1789     if( returnCode == NSAlertAlternateReturn )
1790     {
1791         /* if there are no jobs in the queue, then add this one to the queue and rip 
1792         otherwise, just rip the queue */
1793         if( hb_count( fHandle ) == 0 )
1794         {
1795             [self doAddToQueue];
1796         }
1797
1798         NSString *destinationDirectory = [[fDstFile2Field stringValue] stringByDeletingLastPathComponent];
1799         [[NSUserDefaults standardUserDefaults] setObject:destinationDirectory forKey:@"LastDestinationDirectory"];
1800         [self doRip];
1801     }
1802 }
1803
1804 - (void) remindUserOfSleepOrShutdown
1805 {
1806        if ([[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Put Computer To Sleep"])
1807        {
1808                /*Warn that computer will sleep after encoding*/
1809                int reminduser;
1810                NSBeep();
1811                reminduser = NSRunAlertPanel(@"The computer will sleep after encoding is done.",@"You have selected to sleep the computer after encoding. To turn off sleeping, go to the HandBrake preferences.", @"OK", @"Preferences...", nil);
1812                [NSApp requestUserAttention:NSCriticalRequest];
1813                if ( reminduser == NSAlertAlternateReturn ) 
1814                {
1815                        [self showPreferencesWindow:NULL];
1816                }
1817        } 
1818        else if ([[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Shut Down Computer"])
1819        {
1820                /*Warn that computer will shut down after encoding*/
1821                int reminduser;
1822                NSBeep();
1823                reminduser = NSRunAlertPanel(@"The computer will shut down after encoding is done.",@"You have selected to shut down the computer after encoding. To turn off shut down, go to the HandBrake preferences.", @"OK", @"Preferences...", nil);
1824                [NSApp requestUserAttention:NSCriticalRequest];
1825                if ( reminduser == NSAlertAlternateReturn ) 
1826                {
1827                        [self showPreferencesWindow:NULL];
1828                }
1829        }
1830
1831 }
1832
1833
1834 - (void) doRip
1835 {
1836     /* Let libhb do the job */
1837     hb_start( fHandle );
1838         /*set the fEncodeState State */
1839         fEncodeState = 1;
1840 }
1841
1842
1843
1844
1845 //------------------------------------------------------------------------------------
1846 // Removes all jobs from the queue. Does not cancel the current processing job.
1847 //------------------------------------------------------------------------------------
1848 - (void) doDeleteQueuedJobs
1849 {
1850     hb_job_t * job;
1851     while( ( job = hb_job( fHandle, 0 ) ) )
1852         hb_rem( fHandle, job );
1853 }
1854
1855 //------------------------------------------------------------------------------------
1856 // Cancels the current job and proceeds with the next one in the queue.
1857 //------------------------------------------------------------------------------------
1858 - (void) doCancelCurrentJob
1859 {
1860     // Stop the current job. hb_stop will only cancel the current pass and then set
1861     // its state to HB_STATE_WORKDONE. It also does this asynchronously. So when we
1862     // see the state has changed to HB_STATE_WORKDONE (in updateUI), we'll delete the
1863     // remaining passes of the job and then start the queue back up if there are any
1864     // remaining jobs.
1865      
1866     [fQueueController hblibWillStop];
1867     hb_stop( fHandle );
1868     fEncodeState = 2;   // don't alert at end of processing since this was a cancel
1869     
1870 }
1871
1872 //------------------------------------------------------------------------------------
1873 // Displays an alert asking user if the want to cancel encoding of current job.
1874 // Cancel: returns immediately after posting the alert. Later, when the user
1875 // acknowledges the alert, doCancelCurrentJob is called.
1876 //------------------------------------------------------------------------------------
1877 - (IBAction)Cancel: (id)sender
1878 {
1879     if (!fHandle) return;
1880     
1881     hb_job_t * job = hb_current_job(fHandle);
1882     if (!job) return;
1883
1884     NSString * alertTitle = [NSString stringWithFormat:NSLocalizedString(@"Do you want to stop encoding of %@?", nil),
1885             [NSString stringWithUTF8String:job->title->name]];
1886     
1887     // Which window to attach the sheet to?
1888     NSWindow * docWindow;
1889     if ([sender respondsToSelector: @selector(window)])
1890         docWindow = [sender window];
1891     else
1892         docWindow = fWindow;
1893         
1894     NSBeginCriticalAlertSheet(
1895             alertTitle,
1896             NSLocalizedString(@"Keep Encoding", nil),
1897             NSLocalizedString(@"Delete All", nil),
1898             NSLocalizedString(@"Stop Encoding", nil),
1899             docWindow, self,
1900             nil, @selector(didDimissCancelCurrentJob:returnCode:contextInfo:), nil,
1901             NSLocalizedString(@"Your movie will be lost if you don't continue encoding.", nil),
1902             [NSString stringWithUTF8String:job->title->name]);
1903     
1904     // didDimissCancelCurrentJob:returnCode:contextInfo: will be called when the dialog is dismissed
1905
1906     // N.B.: didDimissCancelCurrentJob:returnCode:contextInfo: is designated as the dismiss
1907     // selector to prevent a crash. As a dismiss selector, the alert window will
1908     // have already be dismissed. If we don't do it this way, the dismissing of
1909     // the alert window will cause the table view to be redrawn at a point where
1910     // current job has been deleted by hblib but we don't know about it yet. This
1911     // is a prime example of wy we need to NOT be relying on hb_current_job!!!!
1912 }
1913
1914 - (void) didDimissCancelCurrentJob: (NSWindow *)sheet returnCode: (int)returnCode contextInfo: (void *)contextInfo
1915 {
1916     if (returnCode == NSAlertOtherReturn)
1917         [self doCancelCurrentJob];
1918     else if (returnCode == NSAlertAlternateReturn)
1919     {
1920         [self doDeleteQueuedJobs];
1921         [self doCancelCurrentJob];
1922     }
1923 }
1924
1925
1926
1927
1928
1929 - (IBAction) Pause: (id) sender
1930 {
1931     hb_state_t s;
1932     hb_get_state2( fHandle, &s );
1933
1934     if( s.state == HB_STATE_PAUSED )
1935     {
1936         hb_resume( fHandle );
1937     }
1938     else
1939     {
1940         hb_pause( fHandle );
1941     }
1942 }
1943
1944 #pragma mark -
1945 #pragma mark GUI Controls Changed Methods
1946
1947 - (IBAction) titlePopUpChanged: (id) sender
1948 {
1949     hb_list_t  * list  = hb_get_titles( fHandle );
1950     hb_title_t * title = (hb_title_t*)
1951         hb_list_item( list, [fSrcTitlePopUp indexOfSelectedItem] );
1952                 
1953                 
1954     /* If Auto Naming is on. We create an output filename of dvd name - title number */
1955     if ([[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultAutoNaming"] > 0)
1956         {
1957                 [fDstFile2Field setStringValue: [NSString stringWithFormat:
1958                         @"%@/%@-%d.%@", [[fDstFile2Field stringValue] stringByDeletingLastPathComponent],
1959                         [NSString stringWithUTF8String: title->name],
1960                           title->index,
1961                         [[fDstFile2Field stringValue] pathExtension]]]; 
1962         }
1963
1964     /* Update chapter popups */
1965     [fSrcChapterStartPopUp removeAllItems];
1966     [fSrcChapterEndPopUp   removeAllItems];
1967     for( int i = 0; i < hb_list_count( title->list_chapter ); i++ )
1968     {
1969         [fSrcChapterStartPopUp addItemWithTitle: [NSString
1970             stringWithFormat: @"%d", i + 1]];
1971         [fSrcChapterEndPopUp addItemWithTitle: [NSString
1972             stringWithFormat: @"%d", i + 1]];
1973     }
1974     [fSrcChapterStartPopUp selectItemAtIndex: 0];
1975     [fSrcChapterEndPopUp   selectItemAtIndex:
1976         hb_list_count( title->list_chapter ) - 1];
1977     [self chapterPopUpChanged: NULL];
1978
1979 /* Start Get and set the initial pic size for display */
1980         hb_job_t * job = title->job;
1981         fTitle = title; 
1982         /* Turn Deinterlace on/off depending on the preference */
1983         if ([[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultDeinterlaceOn"] > 0)
1984         {
1985                 [fPictureController setDeinterlace:1];
1986         }
1987         else
1988         {
1989                 [fPictureController setDeinterlace:0];
1990         }
1991         
1992         /* Pixel Ratio Setting */
1993         if ([[NSUserDefaults standardUserDefaults] boolForKey:@"PixelRatio"])
1994     {
1995                 job->pixel_ratio = 1 ;
1996         }
1997         else
1998         {
1999                 job->pixel_ratio = 0 ;
2000         }
2001         /*Set Source Size Fields Here */
2002         [fPicSrcWidth setStringValue: [NSString stringWithFormat:
2003                                                          @"%d", fTitle->width]];
2004         [fPicSrcHeight setStringValue: [NSString stringWithFormat:
2005                                                          @"%d", fTitle->height]];
2006                                                          
2007         /* Set Auto Crop to on upon selecting a new title */
2008     [fPictureController setAutoCrop:YES];
2009     
2010         /* We get the originial output picture width and height and put them
2011         in variables for use with some presets later on */
2012         PicOrigOutputWidth = job->width;
2013         PicOrigOutputHeight = job->height;
2014         AutoCropTop = job->crop[0];
2015         AutoCropBottom = job->crop[1];
2016         AutoCropLeft = job->crop[2];
2017         AutoCropRight = job->crop[3];
2018         /* we test getting the max output value for pic sizing here to be used later*/
2019         [fPicSettingWidth setStringValue: [NSString stringWithFormat:
2020                 @"%d", PicOrigOutputWidth]];
2021         [fPicSettingHeight setStringValue: [NSString stringWithFormat:
2022                 @"%d", PicOrigOutputHeight]];
2023         /* we run the picture size values through
2024         calculatePictureSizing to get all picture size
2025         information*/
2026         [self calculatePictureSizing: NULL];
2027         /* Run Through encoderPopUpChanged to see if there
2028                 needs to be any pic value modifications based on encoder settings */
2029         //[self encoderPopUpChanged: NULL];
2030         /* END Get and set the initial pic size for display */ 
2031
2032     /* Update subtitle popups */
2033     hb_subtitle_t * subtitle;
2034     [fSubPopUp removeAllItems];
2035     [fSubPopUp addItemWithTitle: @"None"];
2036     [fSubPopUp addItemWithTitle: @"Autoselect"];
2037     for( int i = 0; i < hb_list_count( title->list_subtitle ); i++ )
2038     {
2039         subtitle = (hb_subtitle_t *) hb_list_item( title->list_subtitle, i );
2040
2041         /* We cannot use NSPopUpButton's addItemWithTitle because
2042            it checks for duplicate entries */
2043         [[fSubPopUp menu] addItemWithTitle: [NSString stringWithCString:
2044             subtitle->lang] action: NULL keyEquivalent: @""];
2045     }
2046     [fSubPopUp selectItemAtIndex: 0];
2047         
2048         [self subtitleSelectionChanged: NULL];
2049     
2050     /* Update chapter table */
2051     [fChapterTitlesDelegate resetWithTitle:title];
2052     [fChapterTable reloadData];
2053
2054     /* Update audio popups */
2055     [self addAllAudioTracksToPopUp: fAudLang1PopUp];
2056     [self addAllAudioTracksToPopUp: fAudLang2PopUp];
2057     /* search for the first instance of our prefs default language for track 1, and set track 2 to "none" */
2058         NSString * audioSearchPrefix = [[NSUserDefaults standardUserDefaults] stringForKey:@"DefaultLanguage"];
2059         [self selectAudioTrackInPopUp: fAudLang1PopUp searchPrefixString: audioSearchPrefix selectIndexIfNotFound: 1];
2060     [self selectAudioTrackInPopUp: fAudLang2PopUp searchPrefixString: NULL selectIndexIfNotFound: 0];
2061         
2062         /* changing the title may have changed the audio channels on offer, */
2063         /* so call audioTrackPopUpChanged for both audio tracks to update the mixdown popups */
2064         [self audioTrackPopUpChanged: fAudLang1PopUp];
2065         [self audioTrackPopUpChanged: fAudLang2PopUp];
2066     
2067     /* We repopulate the Video Framerate popup and show the detected framerate along with "Same as Source"*/
2068     [fVidRatePopUp removeAllItems];
2069     if (fTitle->rate_base == 1126125) // 23.976 NTSC Film
2070     {
2071         [fVidRatePopUp addItemWithTitle: @"Same as source (23.976)"];
2072     }
2073     else if (fTitle->rate_base == 1080000) // 25 PAL Film/Video
2074     {
2075         [fVidRatePopUp addItemWithTitle: @"Same as source (25)"];
2076     }
2077     else if (fTitle->rate_base == 900900) // 29.97 NTSC Video
2078     {
2079         [fVidRatePopUp addItemWithTitle: @"Same as source (29.97)"];
2080     }
2081     else
2082     {
2083         /* if none of the common dvd source framerates is detected, just use "Same as source" */
2084         [fVidRatePopUp addItemWithTitle: @"Same as source"];
2085     }
2086         for( int i = 0; i < hb_video_rates_count; i++ )
2087     {
2088         if ([[NSString stringWithCString: hb_video_rates[i].string] isEqualToString: [NSString stringWithFormat: @"%.3f",23.976]])
2089                 {
2090                         [fVidRatePopUp addItemWithTitle:[NSString stringWithFormat: @"%@%@",
2091                                 [NSString stringWithCString: hb_video_rates[i].string], @" (NTSC Film)"]];
2092                 }
2093                 else if ([[NSString stringWithCString: hb_video_rates[i].string] isEqualToString: [NSString stringWithFormat: @"%d",25]])
2094                 {
2095                         [fVidRatePopUp addItemWithTitle:[NSString stringWithFormat: @"%@%@",
2096                                 [NSString stringWithCString: hb_video_rates[i].string], @" (PAL Film/Video)"]];
2097                 }
2098                 else if ([[NSString stringWithCString: hb_video_rates[i].string] isEqualToString: [NSString stringWithFormat: @"%.2f",29.97]])
2099                 {
2100                         [fVidRatePopUp addItemWithTitle:[NSString stringWithFormat: @"%@%@",
2101                                 [NSString stringWithCString: hb_video_rates[i].string], @" (NTSC Video)"]];
2102                 }
2103                 else
2104                 {
2105                         [fVidRatePopUp addItemWithTitle:
2106                                 [NSString stringWithCString: hb_video_rates[i].string]];
2107                 }
2108     }   
2109     [fVidRatePopUp selectItemAtIndex: 0];
2110     
2111    /* lets call tableViewSelected to make sure that any preset we have selected is enforced after a title change */
2112         [self tableViewSelected:NULL]; 
2113         
2114 }
2115
2116 - (IBAction) chapterPopUpChanged: (id) sender
2117 {
2118     
2119         /* If start chapter popup is greater than end chapter popup,
2120         we set the end chapter popup to the same as start chapter popup */
2121         if ([fSrcChapterStartPopUp indexOfSelectedItem] > [fSrcChapterEndPopUp indexOfSelectedItem])
2122         {
2123                 [fSrcChapterEndPopUp selectItemAtIndex: [fSrcChapterStartPopUp indexOfSelectedItem]];
2124     }
2125
2126                 
2127         hb_list_t  * list  = hb_get_titles( fHandle );
2128     hb_title_t * title = (hb_title_t *)
2129         hb_list_item( list, [fSrcTitlePopUp indexOfSelectedItem] );
2130
2131     hb_chapter_t * chapter;
2132     int64_t        duration = 0;
2133     for( int i = [fSrcChapterStartPopUp indexOfSelectedItem];
2134          i <= [fSrcChapterEndPopUp indexOfSelectedItem]; i++ )
2135     {
2136         chapter = (hb_chapter_t *) hb_list_item( title->list_chapter, i );
2137         duration += chapter->duration;
2138     }
2139     
2140     duration /= 90000; /* pts -> seconds */
2141     [fSrcDuration2Field setStringValue: [NSString stringWithFormat:
2142         @"%02lld:%02lld:%02lld", duration / 3600, ( duration / 60 ) % 60,
2143         duration % 60]];
2144
2145     [self calculateBitrate: sender];
2146 }
2147
2148 - (IBAction) formatPopUpChanged: (id) sender
2149 {
2150     NSString * string = [fDstFile2Field stringValue];
2151     NSString * selectedCodecs = [fDstCodecsPopUp titleOfSelectedItem];
2152     int format = [fDstFormatPopUp indexOfSelectedItem];
2153     char * ext = NULL;
2154         /* Initially set the large file (64 bit formatting) output checkbox to hidden */
2155     [fDstMpgLargeFileCheck setHidden: YES];
2156     /* Update the codecs popup */
2157     [fDstCodecsPopUp removeAllItems];
2158     switch( format )
2159     {
2160         case 0:
2161                         /*Get Default MP4 File Extension*/
2162                         if ([[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultMpegName"] > 0)
2163                         {
2164                                 ext = "m4v";
2165                         }
2166                         else
2167                         {
2168                                 ext = "mp4";
2169                         }
2170             
2171             [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / AAC Audio" )];
2172             [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / AAC Audio" )];
2173             
2174                         /* We enable the create chapters checkbox here since we are .mp4*/
2175                         [fCreateChapterMarkers setEnabled: YES];
2176                         /* We show the Large File (64 bit formatting) checkbox since we are .mp4 
2177                         if we have enabled the option in the global preferences*/
2178                         if ([[NSUserDefaults standardUserDefaults] boolForKey:@"AllowLargeFiles"] > 0)
2179                         {
2180                                 [fDstMpgLargeFileCheck setHidden: NO];
2181                         }
2182                                 else
2183                                 {
2184                                         /* if not enable in global preferences, we additionaly sanity check that the
2185                                         hidden checkbox is set to off. */
2186                     [fDstMpgLargeFileCheck setState: NSOffState];
2187                                 }
2188             break;
2189             
2190         case 1:
2191             ext = "mkv";
2192             [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / AAC Audio" )];
2193             [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / AC-3 Audio" )];
2194                         [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / MP3 Audio" )];
2195                         [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / Vorbis Audio" )];
2196             
2197                         [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / AAC Audio" )];
2198                         [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / AC-3 Audio" )];
2199                         [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / MP3 Audio" )];
2200                         [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / Vorbis Audio" )];
2201             /* We enable the create chapters checkbox here */
2202                         [fCreateChapterMarkers setEnabled: YES];
2203                         break;
2204             
2205         case 2: 
2206             ext = "avi";
2207             [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / MP3 Audio" )];
2208             [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / AC-3 Audio" )];
2209             [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / MP3 Audio" )];
2210             [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / AC-3 Audio" )];
2211                         /* We disable the create chapters checkbox here and make sure it is unchecked*/
2212                         [fCreateChapterMarkers setEnabled: NO];
2213                         [fCreateChapterMarkers setState: NSOffState];
2214                         break;
2215             
2216         case 3:
2217             ext = "ogm";
2218             [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / Vorbis Audio" )];
2219             [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / MP3 Audio" )];
2220             /* We disable the create chapters checkbox here and make sure it is unchecked*/
2221                         [fCreateChapterMarkers setEnabled: NO];
2222                         [fCreateChapterMarkers setState: NSOffState];
2223                         break;
2224     }
2225     
2226     if ( SuccessfulScan ) {
2227         [fDstCodecsPopUp selectItemWithTitle:selectedCodecs];
2228         
2229         /* Add/replace to the correct extension */
2230         if( [string characterAtIndex: [string length] - 4] == '.' )
2231         {
2232             [fDstFile2Field setStringValue: [NSString stringWithFormat:
2233                 @"%@.%s", [string substringToIndex: [string length] - 4],
2234                 ext]];
2235         }
2236         else
2237         {
2238             [fDstFile2Field setStringValue: [NSString stringWithFormat:
2239                 @"%@.%s", string, ext]];
2240         }
2241         
2242         if ( [fDstCodecsPopUp selectedItem] == NULL )
2243         {
2244             [fDstCodecsPopUp selectItemAtIndex:0];
2245             [self codecsPopUpChanged: NULL];
2246             
2247             /* changing the format may mean that we can / can't offer mono or 6ch, */
2248             /* so call audioTrackPopUpChanged for both audio tracks to update the mixdown popups */
2249             [self audioTrackPopUpChanged: fAudLang1PopUp];
2250             [self audioTrackPopUpChanged: fAudLang2PopUp];
2251             /* We call the method to properly enable/disable turbo 2 pass */
2252             [self twoPassCheckboxChanged: sender];
2253             /* We call method method to change UI to reflect whether a preset is used or not*/
2254         }
2255     }
2256     
2257         [self customSettingUsed: sender];       
2258 }
2259
2260 - (IBAction) codecsPopUpChanged: (id) sender
2261 {
2262     int format = [fDstFormatPopUp indexOfSelectedItem];
2263     int codecs = [fDstCodecsPopUp indexOfSelectedItem];
2264         
2265     [fAdvancedOptions setHidden:YES];
2266
2267     /* Update the encoder popup*/
2268     if( ( FormatSettings[format][codecs] & HB_VCODEC_X264 ) )
2269     {
2270         /* MPEG-4 -> H.264 */
2271         [fVidEncoderPopUp removeAllItems];
2272                 [fVidEncoderPopUp addItemWithTitle: @"x264 (h.264 Main)"];
2273                 [fVidEncoderPopUp addItemWithTitle: @"x264 (h.264 iPod)"];
2274                 [fVidEncoderPopUp selectItemAtIndex: 0];
2275         [fAdvancedOptions setHidden:NO];
2276     }
2277     
2278     else if( ( FormatSettings[format][codecs] & HB_VCODEC_FFMPEG ) )
2279     {
2280         /* H.264 -> MPEG-4 */
2281         [fVidEncoderPopUp removeAllItems];
2282         [fVidEncoderPopUp addItemWithTitle: @"FFmpeg"];
2283         [fVidEncoderPopUp addItemWithTitle: @"XviD"];
2284         [fVidEncoderPopUp selectItemAtIndex: 0];
2285                                 
2286     }
2287
2288     if( FormatSettings[format][codecs] & HB_ACODEC_AC3 )
2289     {
2290         /* AC-3 pass-through: disable samplerate and bitrate */
2291         [fAudRatePopUp    setEnabled: NO];
2292         [fAudBitratePopUp setEnabled: NO];
2293     }
2294     else
2295     {
2296         [fAudRatePopUp    setEnabled: YES];
2297         [fAudBitratePopUp setEnabled: YES];
2298     }
2299     /* changing the codecs on offer may mean that we can / can't offer mono or 6ch, */
2300         /* so call audioTrackPopUpChanged for both audio tracks to update the mixdown popups */
2301         [self audioTrackPopUpChanged: fAudLang1PopUp];
2302         [self audioTrackPopUpChanged: fAudLang2PopUp];
2303
2304     [self calculateBitrate: sender];
2305     [self twoPassCheckboxChanged: sender];
2306 }
2307
2308 - (IBAction) encoderPopUpChanged: (id) sender
2309 {
2310     
2311         /* Check to see if we need to modify the job pic values based on x264 (iPod) encoder selection */
2312     if ([fDstFormatPopUp indexOfSelectedItem] == 0 && [fDstCodecsPopUp indexOfSelectedItem] == 1 && [fVidEncoderPopUp indexOfSelectedItem] == 1)
2313     {
2314                 hb_job_t * job = fTitle->job;
2315                 job->pixel_ratio = 0 ;
2316                 
2317                 if ([[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultPicSizeAutoiPod"] > 0)
2318                 {
2319                         
2320                         if (job->width > 640)
2321                         {
2322                                 job->width = 640;
2323                         }
2324                         job->keep_ratio = 1;
2325                         hb_fix_aspect( job, HB_KEEP_WIDTH );
2326                         
2327                 }
2328                 /* Make sure the 64bit formatting checkbox is off */
2329                 [fDstMpgLargeFileCheck setState: NSOffState];
2330         }
2331     
2332         [self calculatePictureSizing: sender];
2333         [self twoPassCheckboxChanged: sender];
2334 }
2335
2336 /* Method to determine if we should change the UI
2337 To reflect whether or not a Preset is being used or if
2338 the user is using "Custom" settings by determining the sender*/
2339 - (IBAction) customSettingUsed: (id) sender
2340 {
2341         if ([sender stringValue] != NULL)
2342         {
2343                 /* Deselect the currently selected Preset if there is one*/
2344                 [tableView deselectRow:[tableView selectedRow]];
2345                 [[fPresetsActionMenu itemAtIndex:0] setEnabled: NO];
2346                 /* Change UI to show "Custom" settings are being used */
2347                 [fPresetSelectedDisplay setStringValue: @"Custom"];
2348                 
2349                 curUserPresetChosenNum = nil;
2350         }
2351
2352 }
2353
2354
2355 #pragma mark -
2356 #pragma mark - Video
2357
2358 - (IBAction) twoPassCheckboxChanged: (id) sender
2359 {
2360         /* check to see if x264 is chosen */
2361         int format = [fDstFormatPopUp indexOfSelectedItem];
2362     int codecs = [fDstCodecsPopUp indexOfSelectedItem];
2363         if( ( FormatSettings[format][codecs] & HB_VCODEC_X264 ) )
2364     {
2365                 if( [fVidTwoPassCheck state] == NSOnState)
2366                 {
2367                         [fVidTurboPassCheck setHidden: NO];
2368                 }
2369                 else
2370                 {
2371                         [fVidTurboPassCheck setHidden: YES];
2372                         [fVidTurboPassCheck setState: NSOffState];
2373                 }
2374                 /* Make sure Two Pass is checked if Turbo is checked */
2375                 if( [fVidTurboPassCheck state] == NSOnState)
2376                 {
2377                         [fVidTwoPassCheck setState: NSOnState];
2378                 }
2379         }
2380         else
2381         {
2382                 [fVidTurboPassCheck setHidden: YES];
2383                 [fVidTurboPassCheck setState: NSOffState];
2384         }
2385         
2386         /* We call method method to change UI to reflect whether a preset is used or not*/
2387         [self customSettingUsed: sender];
2388 }
2389
2390 - (IBAction ) videoFrameRateChanged: (id) sender
2391 {
2392     /* We call method method to calculatePictureSizing to error check detelecine*/
2393     [self calculatePictureSizing: sender];
2394
2395     /* We call method method to change UI to reflect whether a preset is used or not*/
2396         [self customSettingUsed: sender];
2397 }
2398 - (IBAction) videoMatrixChanged: (id) sender;
2399 {
2400     bool target, bitrate, quality;
2401
2402     target = bitrate = quality = false;
2403     if( [fVidQualityMatrix isEnabled] )
2404     {
2405         switch( [fVidQualityMatrix selectedRow] )
2406         {
2407             case 0:
2408                 target = true;
2409                 break;
2410             case 1:
2411                 bitrate = true;
2412                 break;
2413             case 2:
2414                 quality = true;
2415                 break;
2416         }
2417     }
2418     [fVidTargetSizeField  setEnabled: target];
2419     [fVidBitrateField     setEnabled: bitrate];
2420     [fVidQualitySlider    setEnabled: quality];
2421     [fVidTwoPassCheck     setEnabled: !quality &&
2422         [fVidQualityMatrix isEnabled]];
2423     if( quality )
2424     {
2425         [fVidTwoPassCheck setState: NSOffState];
2426                 [fVidTurboPassCheck setHidden: YES];
2427                 [fVidTurboPassCheck setState: NSOffState];
2428     }
2429
2430     [self qualitySliderChanged: sender];
2431     [self calculateBitrate: sender];
2432         [self customSettingUsed: sender];
2433 }
2434
2435 - (IBAction) qualitySliderChanged: (id) sender
2436 {
2437     [fVidConstantCell setTitle: [NSString stringWithFormat:
2438         _( @"Constant quality: %.0f %%" ), 100.0 *
2439         [fVidQualitySlider floatValue]]];
2440                 [self customSettingUsed: sender];
2441 }
2442
2443 - (void) controlTextDidChange: (NSNotification *) notification
2444 {
2445     [self calculateBitrate: NULL];
2446 }
2447
2448 - (IBAction) calculateBitrate: (id) sender
2449 {
2450     if( !fHandle || [fVidQualityMatrix selectedRow] != 0 || !SuccessfulScan )
2451     {
2452         return;
2453     }
2454
2455     hb_list_t  * list  = hb_get_titles( fHandle );
2456     hb_title_t * title = (hb_title_t *) hb_list_item( list,
2457             [fSrcTitlePopUp indexOfSelectedItem] );
2458     hb_job_t * job = title->job;
2459
2460     [self prepareJob];
2461
2462     [fVidBitrateField setIntValue: hb_calc_bitrate( job,
2463             [fVidTargetSizeField intValue] )];
2464 }
2465
2466 #pragma mark -
2467 #pragma mark - Picture
2468
2469 /* lets set the picture size back to the max from right after title scan
2470    Lets use an IBAction here as down the road we could always use a checkbox
2471    in the gui to easily take the user back to max. Remember, the compiler
2472    resolves IBActions down to -(void) during compile anyway */
2473 - (IBAction) revertPictureSizeToMax: (id) sender
2474 {
2475         hb_job_t * job = fTitle->job;
2476         /* We use the output picture width and height
2477         as calculated from libhb right after title is set
2478         in TitlePopUpChanged */
2479         job->width = PicOrigOutputWidth;
2480         job->height = PicOrigOutputHeight;
2481     [fPictureController setAutoCrop:YES];
2482         /* Here we use the auto crop values determined right after scan */
2483         job->crop[0] = AutoCropTop;
2484         job->crop[1] = AutoCropBottom;
2485         job->crop[2] = AutoCropLeft;
2486         job->crop[3] = AutoCropRight;
2487                                 
2488                                 
2489                                 [self calculatePictureSizing: sender];
2490                                 /* We call method method to change UI to reflect whether a preset is used or not*/    
2491                                 [self customSettingUsed: sender];
2492 }
2493
2494 /**
2495  * Registers changes made in the Picture Settings Window.
2496  */
2497
2498 - (void)pictureSettingsDidChange {
2499         [self calculatePictureSizing: NULL];
2500 }
2501
2502 /* Get and Display Current Pic Settings in main window */
2503 - (IBAction) calculatePictureSizing: (id) sender
2504 {
2505         [fPicSettingWidth setStringValue: [NSString stringWithFormat:@"%d", fTitle->job->width]];
2506         [fPicSettingHeight setStringValue: [NSString stringWithFormat:@"%d", fTitle->job->height]];
2507                 
2508         if (fTitle->job->pixel_ratio == 1)
2509         {
2510         int titlewidth = fTitle->width-fTitle->job->crop[2]-fTitle->job->crop[3];
2511         int arpwidth = fTitle->job->pixel_aspect_width;
2512         int arpheight = fTitle->job->pixel_aspect_height;
2513         int displayparwidth = titlewidth * arpwidth / arpheight;
2514         int displayparheight = fTitle->height-fTitle->job->crop[0]-fTitle->job->crop[1];
2515         
2516         [fPicSettingWidth setStringValue: [NSString stringWithFormat:@"%d", titlewidth]];
2517         [fPicSettingHeight setStringValue: [NSString stringWithFormat:@"%d", displayparheight]];
2518         [fPicLabelPAROutputX setStringValue: @"x"];
2519         [fPicSettingPARWidth setStringValue: [NSString stringWithFormat:@"%d", displayparwidth]];
2520         [fPicSettingPARHeight setStringValue: [NSString stringWithFormat:@"%d", displayparheight]];
2521         
2522         fTitle->job->keep_ratio = 0;
2523         }
2524         else
2525         {
2526         [fPicLabelPAROutputX setStringValue: @""];
2527         [fPicSettingPARWidth setStringValue: @""];
2528         [fPicSettingPARHeight setStringValue:  @""];
2529         }
2530                                 
2531         /* Set ON/Off values for the deinterlace/keep aspect ratio according to boolean */      
2532         if (fTitle->job->keep_ratio > 0)
2533         {
2534                 [fPicSettingARkeep setStringValue: @"On"];
2535         }
2536         else
2537         {
2538                 [fPicSettingARkeep setStringValue: @"Off"];
2539         }       
2540     /* Detelecine */
2541     if ([fPictureController detelecine]) {
2542         [fPicSettingDetelecine setStringValue: @"Yes"];
2543     }
2544     else {
2545         [fPicSettingDetelecine setStringValue: @"No"];
2546     }
2547     
2548     /* VFR (Variable Frame Rate) */
2549     if ([fPictureController vfr]) {
2550         /* vfr has to set the framerate to 29.97 (ntsc video)
2551         and disable the framerate popup */
2552         [fVidRatePopUp selectItemAtIndex: 8];
2553         [fVidRatePopUp setEnabled: NO];
2554         /* We change the string of the fps popup to warn that vfr is on Framerate (FPS): */
2555         [fVidRateField setStringValue: @"Framerate (VFR On):"];  
2556         
2557     }
2558     else {
2559         /* vfr is off, make sure the framerate popup is enabled */
2560         [fVidRatePopUp setEnabled: YES];
2561         /* and make sure the label for framerate is set to its default */  
2562         [fVidRateField setStringValue: @"Framerate (FPS):"];
2563     }
2564
2565         /* Deinterlace */
2566         if ([fPictureController deinterlace] == 0)
2567         {
2568                 [fPicSettingDeinterlace setStringValue: @"Off"];
2569         }
2570         else if ([fPictureController deinterlace] == 1)
2571         {
2572                 [fPicSettingDeinterlace setStringValue: @"Fast"];
2573         }
2574         else if ([fPictureController deinterlace] == 2)
2575         {
2576                 [fPicSettingDeinterlace setStringValue: @"Slow"];
2577         }
2578         else if ([fPictureController deinterlace] == 3)
2579         {
2580                 [fPicSettingDeinterlace setStringValue: @"Slower"];
2581         }
2582         else if ([fPictureController deinterlace] ==4)
2583         {
2584                 [fPicSettingDeinterlace setStringValue: @"Slowest"];
2585         }
2586         /* Denoise */
2587         if ([fPictureController denoise] == 0)
2588         {
2589                 [fPicSettingDenoise setStringValue: @"Off"];
2590         }
2591         else if ([fPictureController denoise] == 1)
2592         {
2593                 [fPicSettingDenoise setStringValue: @"Weak"];
2594         }
2595         else if ([fPictureController denoise] == 2)
2596         {
2597                 [fPicSettingDenoise setStringValue: @"Medium"];
2598         }
2599         else if ([fPictureController denoise] == 3)
2600         {
2601                 [fPicSettingDenoise setStringValue: @"Strong"];
2602         }
2603
2604     /* Deblock */
2605     if ([fPictureController deblock]) {
2606         [fPicSettingDeblock setStringValue: @"Yes"];
2607     }
2608     else {
2609         [fPicSettingDeblock setStringValue: @"No"];
2610     }
2611         
2612         if (fTitle->job->pixel_ratio > 0)
2613         {
2614                 [fPicSettingPAR setStringValue: @""];
2615         }
2616         else
2617         {
2618                 [fPicSettingPAR setStringValue: @"Off"];
2619         }
2620         /* Set the display field for crop as per boolean */
2621         if (![fPictureController autoCrop])
2622         {
2623             [fPicSettingAutoCrop setStringValue: @"Custom"];
2624         }
2625         else
2626         {
2627                 [fPicSettingAutoCrop setStringValue: @"Auto"];
2628         }       
2629         
2630
2631 }
2632
2633
2634 #pragma mark -
2635 #pragma mark - Audio and Subtitles
2636
2637 - (IBAction) setEnabledStateOfAudioMixdownControls: (id) sender
2638 {
2639
2640     /* enable/disable the mixdown text and popupbutton for audio track 1 */
2641     [fAudTrack1MixPopUp setEnabled: ([fAudLang1PopUp indexOfSelectedItem] == 0) ? NO : YES];
2642     [fAudTrack1MixLabel setTextColor: ([fAudLang1PopUp indexOfSelectedItem] == 0) ?
2643         [NSColor disabledControlTextColor] : [NSColor controlTextColor]];
2644
2645     /* enable/disable the mixdown text and popupbutton for audio track 2 */
2646     [fAudTrack2MixPopUp setEnabled: ([fAudLang2PopUp indexOfSelectedItem] == 0) ? NO : YES];
2647     [fAudTrack2MixLabel setTextColor: ([fAudLang2PopUp indexOfSelectedItem] == 0) ?
2648         [NSColor disabledControlTextColor] : [NSColor controlTextColor]];
2649
2650 }
2651
2652 - (IBAction) addAllAudioTracksToPopUp: (id) sender
2653 {
2654
2655     hb_list_t  * list  = hb_get_titles( fHandle );
2656     hb_title_t * title = (hb_title_t*)
2657         hb_list_item( list, [fSrcTitlePopUp indexOfSelectedItem] );
2658
2659         hb_audio_t * audio;
2660
2661     [sender removeAllItems];
2662     [sender addItemWithTitle: _( @"None" )];
2663     for( int i = 0; i < hb_list_count( title->list_audio ); i++ )
2664     {
2665         audio = (hb_audio_t *) hb_list_item( title->list_audio, i );
2666         [[sender menu] addItemWithTitle:
2667             [NSString stringWithCString: audio->lang]
2668             action: NULL keyEquivalent: @""];
2669     }
2670     [sender selectItemAtIndex: 0];
2671
2672 }
2673
2674 - (IBAction) selectAudioTrackInPopUp: (id) sender searchPrefixString: (NSString *) searchPrefixString selectIndexIfNotFound: (int) selectIndexIfNotFound
2675 {
2676
2677     /* this method can be used to find a language, or a language-and-source-format combination, by passing in the appropriate string */
2678     /* e.g. to find the first French track, pass in an NSString * of "Francais" */
2679     /* e.g. to find the first English 5.1 AC3 track, pass in an NSString * of "English (AC3) (5.1 ch)" */
2680     /* if no matching track is found, then selectIndexIfNotFound is used to choose which track to select instead */
2681     
2682         if (searchPrefixString != NULL) 
2683         {
2684
2685         for( int i = 0; i < [sender numberOfItems]; i++ )
2686         {
2687             /* Try to find the desired search string */
2688             if ([[[sender itemAtIndex: i] title] hasPrefix:searchPrefixString])
2689             {
2690                 [sender selectItemAtIndex: i];
2691                 return;
2692             }
2693         }
2694         /* couldn't find the string, so select the requested "search string not found" item */
2695         /* index of 0 means select the "none" item */
2696         /* index of 1 means select the first audio track */
2697         [sender selectItemAtIndex: selectIndexIfNotFound];
2698         }
2699     else
2700     {
2701         /* if no search string is provided, then select the selectIndexIfNotFound item */
2702         [sender selectItemAtIndex: selectIndexIfNotFound];
2703     }
2704
2705 }
2706
2707 - (IBAction) audioTrackPopUpChanged: (id) sender
2708 {
2709     /* utility function to call audioTrackPopUpChanged without passing in a mixdown-to-use */
2710     [self audioTrackPopUpChanged: sender mixdownToUse: 0];
2711 }
2712
2713 - (IBAction) audioTrackPopUpChanged: (id) sender mixdownToUse: (int) mixdownToUse
2714 {
2715
2716     /* make sure we have a selected title before continuing */
2717     if (fTitle == NULL) return;
2718
2719     /* find out if audio track 1 or 2 was changed - this is passed to us in the tag of the sender */
2720     /* the sender will have been either fAudLang1PopUp (tag = 0) or fAudLang2PopUp (tag = 1) */
2721     int thisAudio = [sender tag];
2722
2723     /* get the index of the selected audio */
2724     int thisAudioIndex = [sender indexOfSelectedItem] - 1;
2725
2726     /* Handbrake can't currently cope with ripping the same source track twice */
2727     /* So, if this audio is also selected in the other audio track popup, set that popup's selection to "none" */
2728     /* get a reference to the two audio track popups */
2729     NSPopUpButton * thisAudioPopUp  = (thisAudio == 1 ? fAudLang2PopUp : fAudLang1PopUp);
2730     NSPopUpButton * otherAudioPopUp = (thisAudio == 1 ? fAudLang1PopUp : fAudLang2PopUp);
2731     /* if the same track is selected in the other audio popup, then select "none" in that popup */
2732     /* unless, of course, both are selected as "none!" */
2733     if ([thisAudioPopUp indexOfSelectedItem] != 0 && [thisAudioPopUp indexOfSelectedItem] == [otherAudioPopUp indexOfSelectedItem]) {
2734         [otherAudioPopUp selectItemAtIndex: 0];
2735         [self audioTrackPopUpChanged: otherAudioPopUp];
2736     }
2737
2738     /* pointer for the hb_audio_s struct we will use later on */
2739     hb_audio_t * audio;
2740
2741     /* find out what the currently-selected output audio codec is */
2742     int format = [fDstFormatPopUp indexOfSelectedItem];
2743     int codecs = [fDstCodecsPopUp indexOfSelectedItem];
2744     int acodec = FormatSettings[format][codecs] & HB_ACODEC_MASK;
2745
2746     /* pointer to this track's mixdown NSPopUpButton */
2747     NSTextField   * mixdownTextField;
2748     NSPopUpButton * mixdownPopUp;
2749
2750     /* find our mixdown NSTextField and NSPopUpButton */
2751     if (thisAudio == 0)
2752     {
2753         mixdownTextField = fAudTrack1MixLabel;
2754         mixdownPopUp = fAudTrack1MixPopUp;
2755     }
2756     else
2757     {
2758         mixdownTextField = fAudTrack2MixLabel;
2759         mixdownPopUp = fAudTrack2MixPopUp;
2760     }
2761
2762     /* delete the previous audio mixdown options */
2763     [mixdownPopUp removeAllItems];
2764
2765     /* check if the audio mixdown controls need their enabled state changing */
2766     [self setEnabledStateOfAudioMixdownControls: NULL];
2767
2768     if (thisAudioIndex != -1)
2769     {
2770
2771         /* get the audio */
2772         audio = (hb_audio_t *) hb_list_item( fTitle->list_audio, thisAudioIndex );
2773         if (audio != NULL)
2774         {
2775
2776             /* find out if our selected output audio codec supports mono and / or 6ch */
2777             /* we also check for an input codec of AC3 or DCA,
2778                as they are the only libraries able to do the mixdown to mono / conversion to 6-ch */
2779             /* audioCodecsSupportMono and audioCodecsSupport6Ch are the same for now,
2780                but this may change in the future, so they are separated for flexibility */
2781             int audioCodecsSupportMono = ((audio->codec == HB_ACODEC_AC3 ||
2782                 audio->codec == HB_ACODEC_DCA) && acodec == HB_ACODEC_FAAC);
2783             int audioCodecsSupport6Ch =  ((audio->codec == HB_ACODEC_AC3 ||
2784                 audio->codec == HB_ACODEC_DCA) && (acodec == HB_ACODEC_FAAC ||
2785                 acodec == HB_ACODEC_VORBIS));
2786
2787             /* check for AC-3 passthru */
2788             if (audio->codec == HB_ACODEC_AC3 && acodec == HB_ACODEC_AC3)
2789             {
2790                     [[mixdownPopUp menu] addItemWithTitle:
2791                         [NSString stringWithCString: "AC3 Passthru"]
2792                         action: NULL keyEquivalent: @""];
2793             }
2794             else
2795             {
2796
2797                 /* add the appropriate audio mixdown menuitems to the popupbutton */
2798                 /* in each case, we set the new menuitem's tag to be the amixdown value for that mixdown,
2799                    so that we can reference the mixdown later */
2800
2801                 /* keep a track of the min and max mixdowns we used, so we can select the best match later */
2802                 int minMixdownUsed = 0;
2803                 int maxMixdownUsed = 0;
2804                 
2805                 /* get the input channel layout without any lfe channels */
2806                 int layout = audio->input_channel_layout & HB_INPUT_CH_LAYOUT_DISCRETE_NO_LFE_MASK;
2807
2808                 /* do we want to add a mono option? */
2809                 if (audioCodecsSupportMono == 1) {
2810                     NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
2811                         [NSString stringWithCString: hb_audio_mixdowns[0].human_readable_name]
2812                         action: NULL keyEquivalent: @""];
2813                     [menuItem setTag: hb_audio_mixdowns[0].amixdown];
2814                     if (minMixdownUsed == 0) minMixdownUsed = hb_audio_mixdowns[0].amixdown;
2815                     maxMixdownUsed = MAX(maxMixdownUsed, hb_audio_mixdowns[0].amixdown);
2816                 }
2817
2818                 /* do we want to add a stereo option? */
2819                 /* offer stereo if we have a mono source and non-mono-supporting codecs, as otherwise we won't have a mixdown at all */
2820                 /* also offer stereo if we have a stereo-or-better source */
2821                 if ((layout == HB_INPUT_CH_LAYOUT_MONO && audioCodecsSupportMono == 0) || layout >= HB_INPUT_CH_LAYOUT_STEREO) {
2822                     NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
2823                         [NSString stringWithCString: hb_audio_mixdowns[1].human_readable_name]
2824                         action: NULL keyEquivalent: @""];
2825                     [menuItem setTag: hb_audio_mixdowns[1].amixdown];
2826                     if (minMixdownUsed == 0) minMixdownUsed = hb_audio_mixdowns[1].amixdown;
2827                     maxMixdownUsed = MAX(maxMixdownUsed, hb_audio_mixdowns[1].amixdown);
2828                 }
2829
2830                 /* do we want to add a dolby surround (DPL1) option? */
2831                 if (layout == HB_INPUT_CH_LAYOUT_3F1R || layout == HB_INPUT_CH_LAYOUT_3F2R || layout == HB_INPUT_CH_LAYOUT_DOLBY) {
2832                     NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
2833                         [NSString stringWithCString: hb_audio_mixdowns[2].human_readable_name]
2834                         action: NULL keyEquivalent: @""];
2835                     [menuItem setTag: hb_audio_mixdowns[2].amixdown];
2836                     if (minMixdownUsed == 0) minMixdownUsed = hb_audio_mixdowns[2].amixdown;
2837                     maxMixdownUsed = MAX(maxMixdownUsed, hb_audio_mixdowns[2].amixdown);
2838                 }
2839
2840                 /* do we want to add a dolby pro logic 2 (DPL2) option? */
2841                 if (layout == HB_INPUT_CH_LAYOUT_3F2R) {
2842                     NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
2843                         [NSString stringWithCString: hb_audio_mixdowns[3].human_readable_name]
2844                         action: NULL keyEquivalent: @""];
2845                     [menuItem setTag: hb_audio_mixdowns[3].amixdown];
2846                     if (minMixdownUsed == 0) minMixdownUsed = hb_audio_mixdowns[3].amixdown;
2847                     maxMixdownUsed = MAX(maxMixdownUsed, hb_audio_mixdowns[3].amixdown);
2848                 }
2849
2850                 /* do we want to add a 6-channel discrete option? */
2851                 if (audioCodecsSupport6Ch == 1 && layout == HB_INPUT_CH_LAYOUT_3F2R && (audio->input_channel_layout & HB_INPUT_CH_LAYOUT_HAS_LFE)) {
2852                     NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
2853                         [NSString stringWithCString: hb_audio_mixdowns[4].human_readable_name]
2854                         action: NULL keyEquivalent: @""];
2855                     [menuItem setTag: hb_audio_mixdowns[4].amixdown];
2856                     if (minMixdownUsed == 0) minMixdownUsed = hb_audio_mixdowns[4].amixdown;
2857                     maxMixdownUsed = MAX(maxMixdownUsed, hb_audio_mixdowns[4].amixdown);
2858                 }
2859
2860                 /* auto-select the best mixdown based on our saved mixdown preference */
2861                 
2862                 /* for now, this is hard-coded to a "best" mixdown of HB_AMIXDOWN_DOLBYPLII */
2863                 /* ultimately this should be a prefs option */
2864                 int useMixdown;
2865                 
2866                 /* if we passed in a mixdown to use - in order to load a preset - then try and use it */
2867                 if (mixdownToUse > 0)
2868                 {
2869                     useMixdown = mixdownToUse;
2870                 }
2871                 else
2872                 {
2873                     useMixdown = HB_AMIXDOWN_DOLBYPLII;
2874                 }
2875                 
2876                 /* if useMixdown > maxMixdownUsed, then use maxMixdownUsed */
2877                 if (useMixdown > maxMixdownUsed) useMixdown = maxMixdownUsed;
2878
2879                 /* if useMixdown < minMixdownUsed, then use minMixdownUsed */
2880                 if (useMixdown < minMixdownUsed) useMixdown = minMixdownUsed;
2881
2882                 /* select the (possibly-amended) preferred mixdown */
2883                 [mixdownPopUp selectItemWithTag: useMixdown];
2884                                 
2885                                 /* lets call the audioTrackMixdownChanged method here to determine appropriate bitrates, etc. */
2886                 [self audioTrackMixdownChanged: NULL];
2887             }
2888
2889         }
2890         
2891     }
2892
2893         /* see if the new audio track choice will change the bitrate we need */
2894     [self calculateBitrate: sender];    
2895
2896 }
2897 - (IBAction) audioTrackMixdownChanged: (id) sender
2898 {
2899
2900     /* find out what the currently-selected output audio codec is */
2901     int format = [fDstFormatPopUp indexOfSelectedItem];
2902     int codecs = [fDstCodecsPopUp indexOfSelectedItem];
2903     int acodec = FormatSettings[format][codecs] & HB_ACODEC_MASK;
2904     
2905     /* storage variable for the min and max bitrate allowed for this codec */
2906     int minbitrate;
2907     int maxbitrate;
2908     
2909     switch( acodec )
2910     {
2911         case HB_ACODEC_FAAC:
2912             /* check if we have a 6ch discrete conversion in either audio track */
2913             if ([[fAudTrack1MixPopUp selectedItem] tag] == HB_AMIXDOWN_6CH || [[fAudTrack2MixPopUp selectedItem] tag] == HB_AMIXDOWN_6CH)
2914             {
2915                 /* FAAC is happy using our min bitrate of 32 kbps, even for 6ch */
2916                 minbitrate = 32;
2917                 /* If either mixdown popup includes 6-channel discrete, then allow up to 384 kbps */
2918                 maxbitrate = 384;
2919                 break;
2920             }
2921             else
2922             {
2923                 /* FAAC is happy using our min bitrate of 32 kbps for stereo or mono */
2924                 minbitrate = 32;
2925                 /* FAAC won't honour anything more than 160 for stereo, so let's not offer it */
2926                 /* note: haven't dealt with mono separately here, FAAC will just use the max it can */
2927                 maxbitrate = 160;
2928                 break;
2929             }
2930
2931         case HB_ACODEC_LAME:
2932             /* Lame is happy using our min bitrate of 32 kbps */
2933             minbitrate = 32;
2934             /* Lame won't encode if the bitrate is higher than 320 kbps */
2935             maxbitrate = 320;
2936             break;
2937
2938         case HB_ACODEC_VORBIS:
2939         if ([[fAudTrack1MixPopUp selectedItem] tag] == HB_AMIXDOWN_6CH || [[fAudTrack2MixPopUp selectedItem] tag] == HB_AMIXDOWN_6CH)
2940             {
2941                 /* Vorbis causes a crash if we use a bitrate below 192 kbps with 6 channel */
2942                 minbitrate = 192;
2943                 /* If either mixdown popup includes 6-channel discrete, then allow up to 384 kbps */
2944                 maxbitrate = 384;
2945                 break;
2946             }
2947             else
2948             {
2949             /* Vorbis causes a crash if we use a bitrate below 48 kbps */
2950             minbitrate = 48;
2951             /* Vorbis can cope with 384 kbps quite happily, even for stereo */
2952             maxbitrate = 384;
2953             break;
2954             }
2955
2956         default:
2957             /* AC3 passthru disables the bitrate dropdown anyway, so we might as well just use the min and max bitrate */
2958             minbitrate = 32;
2959             maxbitrate = 384;
2960         
2961     }
2962
2963     [fAudBitratePopUp removeAllItems];
2964
2965     for( int i = 0; i < hb_audio_bitrates_count; i++ )
2966     {
2967         if (hb_audio_bitrates[i].rate >= minbitrate && hb_audio_bitrates[i].rate <= maxbitrate)
2968         {
2969             /* add a new menuitem for this bitrate */
2970             NSMenuItem *menuItem = [[fAudBitratePopUp menu] addItemWithTitle:
2971                 [NSString stringWithCString: hb_audio_bitrates[i].string]
2972                 action: NULL keyEquivalent: @""];
2973             /* set its tag to be the actual bitrate as an integer, so we can retrieve it later */
2974             [menuItem setTag: hb_audio_bitrates[i].rate];
2975         }
2976     }
2977
2978     /* select the default bitrate (but use 384 for 6-ch AAC) */
2979     if ([[fAudTrack1MixPopUp selectedItem] tag] == HB_AMIXDOWN_6CH || [[fAudTrack2MixPopUp selectedItem] tag] == HB_AMIXDOWN_6CH)
2980     {
2981         [fAudBitratePopUp selectItemWithTag: 384];
2982     }
2983     else
2984     {
2985         [fAudBitratePopUp selectItemWithTag: hb_audio_bitrates[hb_audio_bitrates_default].rate];
2986     }
2987
2988 }
2989
2990 - (IBAction) subtitleSelectionChanged: (id) sender
2991 {
2992         if ([fSubPopUp indexOfSelectedItem] == 0)
2993         {
2994         [fSubForcedCheck setState: NSOffState];
2995         [fSubForcedCheck setEnabled: NO];       
2996         }
2997         else
2998         {
2999         [fSubForcedCheck setEnabled: YES];      
3000         }
3001         
3002 }
3003
3004
3005
3006
3007 #pragma mark -
3008 #pragma mark Open New Windows
3009
3010 - (IBAction) openHomepage: (id) sender
3011 {
3012     [[NSWorkspace sharedWorkspace] openURL: [NSURL
3013         URLWithString:@"http://handbrake.m0k.org/"]];
3014 }
3015
3016 - (IBAction) openForums: (id) sender
3017 {
3018     [[NSWorkspace sharedWorkspace] openURL: [NSURL
3019         URLWithString:@"http://handbrake.m0k.org/forum/"]];
3020 }
3021 - (IBAction) openUserGuide: (id) sender
3022 {
3023     [[NSWorkspace sharedWorkspace] openURL: [NSURL
3024         URLWithString:@"http://handbrake.m0k.org/trac/wiki/HandBrakeGuide"]];
3025 }
3026
3027 /**
3028  * Shows debug output window.
3029  */
3030 - (IBAction)showDebugOutputPanel:(id)sender
3031 {
3032     [outputPanel showOutputPanel:sender];
3033 }
3034
3035 /**
3036  * Shows preferences window.
3037  */
3038 - (IBAction) showPreferencesWindow: (id) sender
3039 {
3040     NSWindow * window = [fPreferencesController window];
3041     if (![window isVisible])
3042         [window center];
3043
3044     [window makeKeyAndOrderFront: nil];
3045 }
3046
3047 /**
3048  * Shows queue window.
3049  */
3050 - (IBAction) showQueueWindow:(id)sender
3051 {
3052     [fQueueController showQueueWindow:sender];
3053 }
3054
3055
3056 - (IBAction) toggleDrawer:(id)sender {
3057     [fPresetDrawer toggle:self];
3058 }
3059
3060 /**
3061  * Shows Picture Settings Window.
3062  */
3063
3064 - (IBAction) showPicturePanel: (id) sender
3065 {
3066         hb_list_t  * list  = hb_get_titles( fHandle );
3067     hb_title_t * title = (hb_title_t *) hb_list_item( list,
3068             [fSrcTitlePopUp indexOfSelectedItem] );
3069     [fPictureController showPanelInWindow:fWindow forTitle:title];
3070 }
3071
3072 #pragma mark -
3073 #pragma mark Preset Table View Methods
3074
3075 - (IBAction)tableViewSelected:(id)sender
3076 {
3077     /* Since we cannot disable the presets tableView in terms of clickability
3078            we will use the enabled state of the add presets button to determine whether
3079            or not clicking on a preset will do anything */
3080         if ([fPresetsAdd isEnabled])
3081         {
3082                 if ([tableView selectedRow] >= 0)
3083                 {       
3084                         /* we get the chosen preset from the UserPresets array */
3085                         chosenPreset = [UserPresets objectAtIndex:[tableView selectedRow]];
3086                         curUserPresetChosenNum = [sender selectedRow];
3087                         /* we set the preset display field in main window here */
3088                         [fPresetSelectedDisplay setStringValue: [NSString stringWithFormat: @"%@",[chosenPreset valueForKey:@"PresetName"]]];
3089                         if ([[chosenPreset objectForKey:@"Default"] intValue] == 1)
3090                         {
3091                                 [fPresetSelectedDisplay setStringValue: [NSString stringWithFormat: @"%@ (Default)",[chosenPreset valueForKey:@"PresetName"]]];
3092                         }
3093                         else
3094                         {
3095                                 [fPresetSelectedDisplay setStringValue: [NSString stringWithFormat: @"%@",[chosenPreset valueForKey:@"PresetName"]]];
3096                         }
3097                         /* File Format */
3098                         [fDstFormatPopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"FileFormat"]]];
3099                         [self formatPopUpChanged: NULL];
3100                         
3101                         /* Chapter Markers*/
3102                         [fCreateChapterMarkers setState:[[chosenPreset objectForKey:@"ChapterMarkers"] intValue]];
3103                         /* Allow Mpeg4 64 bit formatting +4GB file sizes */
3104                         [fDstMpgLargeFileCheck setState:[[chosenPreset objectForKey:@"Mp4LargeFile"] intValue]];
3105                         /* Codecs */
3106                         [fDstCodecsPopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"FileCodecs"]]];
3107                         [self codecsPopUpChanged: NULL];
3108                         /* Video encoder */
3109                         [fVidEncoderPopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"VideoEncoder"]]];
3110                         
3111                         /* We can show the preset options here in the gui if we want to
3112                                 so we check to see it the user has specified it in the prefs */
3113                         [fAdvancedOptions setOptions: [NSString stringWithFormat:[chosenPreset valueForKey:@"x264Option"]]];
3114                         
3115                         /* Lets run through the following functions to get variables set there */
3116                         [self encoderPopUpChanged: NULL];
3117                         
3118                         [self calculateBitrate: NULL];
3119                         
3120                         /* Video quality */
3121                         [fVidQualityMatrix selectCellAtRow:[[chosenPreset objectForKey:@"VideoQualityType"] intValue] column:0];
3122                         
3123                         [fVidTargetSizeField setStringValue: [NSString stringWithFormat:[chosenPreset valueForKey:@"VideoTargetSize"]]];
3124                         [fVidBitrateField setStringValue: [NSString stringWithFormat:[chosenPreset valueForKey:@"VideoAvgBitrate"]]];
3125                         
3126                         [fVidQualitySlider setFloatValue: [[chosenPreset valueForKey:@"VideoQualitySlider"] floatValue]];
3127                         [self videoMatrixChanged: NULL];
3128                         
3129                         /* Video framerate */
3130                         /* For video preset video framerate, we want to make sure that Same as source does not conflict with the
3131                detected framerate in the fVidRatePopUp so we use index 0*/
3132                         if ([[NSString stringWithFormat:[chosenPreset valueForKey:@"VideoFramerate"]] isEqualToString: @"Same as source"])
3133             {
3134                 [fVidRatePopUp selectItemAtIndex: 0];
3135             }
3136             else
3137             {
3138                 [fVidRatePopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"VideoFramerate"]]];
3139             }
3140                         
3141                         /* GrayScale */
3142                         [fVidGrayscaleCheck setState:[[chosenPreset objectForKey:@"VideoGrayScale"] intValue]];
3143                         
3144                         /* 2 Pass Encoding */
3145                         [fVidTwoPassCheck setState:[[chosenPreset objectForKey:@"VideoTwoPass"] intValue]];
3146                         [self twoPassCheckboxChanged: NULL];
3147                         /* Turbo 1st pass for 2 Pass Encoding */
3148                         [fVidTurboPassCheck setState:[[chosenPreset objectForKey:@"VideoTurboTwoPass"] intValue]];
3149                         
3150                         /*Audio*/
3151                         
3152                         /* Audio Sample Rate*/
3153                         [fAudRatePopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"AudioSampleRate"]]];
3154                         /* Audio Bitrate Rate*/
3155                         [fAudBitratePopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"AudioBitRate"]]];
3156                         /*Subtitles*/
3157                         [fSubPopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"Subtitles"]]];
3158                         
3159                         /* Picture Settings */
3160                         /* Look to see if we apply these here in objectForKey:@"UsesPictureSettings"] */
3161                         if ([[chosenPreset objectForKey:@"UsesPictureSettings"]  intValue] > 0)
3162                         {
3163                                 hb_job_t * job = fTitle->job;
3164                                 /* Check to see if we should use the max picture setting for the current title*/
3165                                 if ([[chosenPreset objectForKey:@"UsesPictureSettings"]  intValue] == 2 || [[chosenPreset objectForKey:@"UsesMaxPictureSettings"]  intValue] == 1)
3166                                 {
3167                                         /* Use Max Picture settings for whatever the dvd is.*/
3168                                         [self revertPictureSizeToMax: NULL];
3169                                         job->keep_ratio = [[chosenPreset objectForKey:@"PictureKeepRatio"]  intValue];
3170                                         if (job->keep_ratio == 1)
3171                                         {
3172                                                 hb_fix_aspect( job, HB_KEEP_WIDTH );
3173                                                 if( job->height > fTitle->height )
3174                                                 {
3175                                                         job->height = fTitle->height;
3176                                                         hb_fix_aspect( job, HB_KEEP_HEIGHT );
3177                                                 }
3178                                         }
3179                                         job->pixel_ratio = [[chosenPreset objectForKey:@"PicturePAR"]  intValue];
3180                                 }
3181                                 else // Apply picture settings that were in effect at the time the preset was saved
3182                                 {
3183                                         job->width = [[chosenPreset objectForKey:@"PictureWidth"]  intValue];
3184                                         job->height = [[chosenPreset objectForKey:@"PictureHeight"]  intValue];
3185                                         job->keep_ratio = [[chosenPreset objectForKey:@"PictureKeepRatio"]  intValue];
3186                                         if (job->keep_ratio == 1)
3187                                         {
3188                                                 hb_fix_aspect( job, HB_KEEP_WIDTH );
3189                                                 if( job->height > fTitle->height )
3190                                                 {
3191                                                         job->height = fTitle->height;
3192                                                         hb_fix_aspect( job, HB_KEEP_HEIGHT );
3193                                                 }
3194                                         }
3195                                         job->pixel_ratio = [[chosenPreset objectForKey:@"PicturePAR"]  intValue];
3196                     
3197                     /* Filters */
3198                     [fPictureController setDeinterlace:[[chosenPreset objectForKey:@"PictureDeinterlace"] intValue]];
3199                                         
3200                                         if ([chosenPreset objectForKey:@"PictureDetelecine"])
3201                                         {
3202                         [fPictureController setDetelecine:[[chosenPreset objectForKey:@"PictureDetelecine"] intValue]];
3203                                         }
3204                                         if ([chosenPreset objectForKey:@"PictureDenoise"])
3205                                         {
3206                         [fPictureController setDenoise:[[chosenPreset objectForKey:@"PictureDenoise"] intValue]];
3207                                         }
3208                     if ([chosenPreset objectForKey:@"PictureDeblock"])
3209                                         {
3210                         [fPictureController setDeblock:[[chosenPreset objectForKey:@"PictureDeblock"] intValue]];
3211                                         }
3212                                         /* If Cropping is set to custom, then recall all four crop values from
3213                                                 when the preset was created and apply them */
3214                                         if ([[chosenPreset objectForKey:@"PictureAutoCrop"]  intValue] == 0)
3215                                         {
3216                         [fPictureController setAutoCrop:NO];
3217                                                 
3218                                                 /* Here we use the custom crop values saved at the time the preset was saved */
3219                                                 job->crop[0] = [[chosenPreset objectForKey:@"PictureTopCrop"]  intValue];
3220                                                 job->crop[1] = [[chosenPreset objectForKey:@"PictureBottomCrop"]  intValue];
3221                                                 job->crop[2] = [[chosenPreset objectForKey:@"PictureLeftCrop"]  intValue];
3222                                                 job->crop[3] = [[chosenPreset objectForKey:@"PictureRightCrop"]  intValue];
3223                                                 
3224                                         }
3225                                         else /* if auto crop has been saved in preset, set to auto and use post scan auto crop */
3226                                         {
3227                         [fPictureController setAutoCrop:YES];
3228                         /* Here we use the auto crop values determined right after scan */
3229                                                 job->crop[0] = AutoCropTop;
3230                                                 job->crop[1] = AutoCropBottom;
3231                                                 job->crop[2] = AutoCropLeft;
3232                                                 job->crop[3] = AutoCropRight;
3233                                                 
3234                                         }
3235                                 }
3236                                 [self calculatePictureSizing: NULL]; 
3237                         }
3238                         
3239                         
3240                         [[fPresetsActionMenu itemAtIndex:0] setEnabled: YES];
3241                         }
3242 }
3243 }
3244
3245
3246
3247 - (int)numberOfRowsInTableView:(NSTableView *)aTableView
3248 {
3249     return [UserPresets count];
3250 }
3251
3252 /* we use this to determine display characteristics for
3253 each table cell based on content currently only used to
3254 show the built in presets in a blue font. */
3255 - (void)tableView:(NSTableView *)aTableView
3256  willDisplayCell:(id)aCell 
3257  forTableColumn:(NSTableColumn *)aTableColumn row:(int)rowIndex
3258 {
3259     NSDictionary *userPresetDict = [UserPresets objectAtIndex:rowIndex];
3260         NSFont *txtFont;
3261         NSColor *fontColor;
3262         NSColor *shadowColor;
3263         txtFont = [NSFont systemFontOfSize: [NSFont smallSystemFontSize]];
3264         /* First, we check to see if its a selected row, if so, we use white since its highlighted in blue */
3265         if ([[aTableView selectedRowIndexes] containsIndex:rowIndex] && ([tableView editedRow] != rowIndex))
3266         {
3267                 
3268                 fontColor = [NSColor whiteColor];
3269                 shadowColor = [NSColor colorWithDeviceRed:(127.0/255.0) green:(140.0/255.0) blue:(160.0/255.0) alpha:1.0];
3270         }
3271         else
3272         {
3273                 /* We set the properties of unselected rows */
3274                 /* if built-in preset (defined by "type" == 0) we use a blue font */
3275                 if ([[userPresetDict objectForKey:@"Type"] intValue] == 0)
3276                 {
3277                         fontColor = [NSColor blueColor];
3278                 }
3279                 else // User created preset, use a black font
3280                 {
3281                         fontColor = [NSColor blackColor];
3282                 }
3283                 shadowColor = nil;
3284         }
3285         /* We check to see if this is the HB default, if so, color it appropriately */
3286         if (!presetUserDefault && presetHbDefault && rowIndex == presetHbDefault)
3287         {
3288         txtFont = [NSFont boldSystemFontOfSize: [NSFont smallSystemFontSize]];
3289         }
3290         /* We check to see if this is the User Specified default, if so, color it appropriately */
3291         if (presetUserDefault && rowIndex == presetUserDefault)
3292         {
3293         txtFont = [NSFont boldSystemFontOfSize: [NSFont smallSystemFontSize]];
3294         }
3295         
3296         [aCell setTextColor:fontColor];
3297         [aCell setFont:txtFont];
3298         /* this shadow stuff (like mail app) for some reason looks crappy, commented out
3299         temporarily in case we want to resurrect it */
3300         /*
3301         NSShadow *shadow = [[NSShadow alloc] init];
3302         NSSize shadowOffset = { width: 1.0, height: -1.5};
3303         [shadow setShadowOffset:shadowOffset];
3304         [shadow setShadowColor:shadowColor];
3305         [shadow set];
3306         */
3307         
3308 }
3309 /* Method to display tooltip with the description for each preset, if available */
3310 - (NSString *)tableView:(NSTableView *)aTableView toolTipForCell:(NSCell *)aCell 
3311                    rect:(NSRectPointer)aRect tableColumn:(NSTableColumn *)aTableColumn
3312                     row:(int)rowIndex mouseLocation:(NSPoint)aPos
3313 {
3314      /* initialize the tooltip contents variable */
3315          NSString *loc_tip;
3316      /* if there is a description for the preset, we show it in the tooltip */
3317          if ([[UserPresets objectAtIndex:rowIndex] valueForKey:@"PresetDescription"])
3318          {
3319         loc_tip = [NSString stringWithFormat: @"%@",[[UserPresets objectAtIndex:rowIndex] valueForKey:@"PresetDescription"]];
3320         return (loc_tip);
3321          }
3322          else
3323          {
3324         loc_tip = @"No description available";
3325          }
3326          return (loc_tip);
3327
3328 }
3329
3330 - (id)tableView:(NSTableView *)aTableView
3331       objectValueForTableColumn:(NSTableColumn *)aTableColumn
3332       row:(int)rowIndex
3333 {
3334 id theRecord, theValue;
3335     
3336     theRecord = [UserPresets objectAtIndex:rowIndex];
3337     theValue = [theRecord objectForKey:[aTableColumn identifier]];
3338     return theValue;
3339 }
3340
3341 // NSTableDataSource method that we implement to edit values directly in the table...
3342 - (void)tableView:(NSTableView *)aTableView
3343         setObjectValue:(id)anObject
3344         forTableColumn:(NSTableColumn *)aTableColumn
3345         row:(int)rowIndex
3346 {
3347     id theRecord;
3348     
3349     theRecord = [UserPresets objectAtIndex:rowIndex];
3350     [theRecord setObject:anObject forKey:@"PresetName"];
3351     /* We Sort the Presets By Factory or Custom */
3352         NSSortDescriptor * presetTypeDescriptor=[[[NSSortDescriptor alloc] initWithKey:@"Type" 
3353                                                     ascending:YES] autorelease];
3354                 /* We Sort the Presets Alphabetically by name */
3355         NSSortDescriptor * presetNameDescriptor=[[[NSSortDescriptor alloc] initWithKey:@"PresetName" 
3356                                                     ascending:YES selector:@selector(caseInsensitiveCompare:)] autorelease];
3357         NSArray *sortDescriptors=[NSArray arrayWithObjects:presetTypeDescriptor,presetNameDescriptor,nil];
3358     NSArray *sortedArray=[UserPresets sortedArrayUsingDescriptors:sortDescriptors];
3359         [UserPresets setArray:sortedArray];
3360         /* We Reload the New Table data for presets */
3361     [tableView reloadData];
3362    /* We save all of the preset data here */
3363     [self savePreset];
3364 }
3365
3366
3367
3368
3369 #pragma mark -
3370 #pragma mark Manage Presets
3371
3372 - (void) loadPresets {
3373         /* We declare the default NSFileManager into fileManager */
3374         NSFileManager * fileManager = [NSFileManager defaultManager];
3375         /*We define the location of the user presets file */
3376     UserPresetsFile = @"~/Library/Application Support/HandBrake/UserPresets.plist";
3377         UserPresetsFile = [[UserPresetsFile stringByExpandingTildeInPath]retain];
3378     /* We check for the presets.plist */
3379         if ([fileManager fileExistsAtPath:UserPresetsFile] == 0) 
3380         {
3381                 [fileManager createFileAtPath:UserPresetsFile contents:nil attributes:nil];
3382         }
3383                 
3384         UserPresets = [[NSMutableArray alloc] initWithContentsOfFile:UserPresetsFile];
3385         if (nil == UserPresets) 
3386         {
3387                 UserPresets = [[NSMutableArray alloc] init];
3388                 [self addFactoryPresets:NULL];
3389         }
3390         
3391 }
3392
3393
3394 - (IBAction) showAddPresetPanel: (id) sender
3395 {
3396     /* Deselect the currently selected Preset if there is one*/
3397     [tableView deselectRow:[tableView selectedRow]];
3398
3399     /* Populate the preset picture settings popup here */
3400     [fPresetNewPicSettingsPopUp removeAllItems];
3401     [fPresetNewPicSettingsPopUp addItemWithTitle:@"None"];
3402     [fPresetNewPicSettingsPopUp addItemWithTitle:@"Current"];
3403     [fPresetNewPicSettingsPopUp addItemWithTitle:@"Source Maximum (post source scan)"];
3404     [fPresetNewPicSettingsPopUp selectItemAtIndex: 0];  
3405         
3406     /* Erase info from the input fields fPresetNewDesc*/
3407         [fPresetNewName setStringValue: @""];
3408         [fPresetNewDesc setStringValue: @""];
3409         /* Show the panel */
3410         [NSApp beginSheet: fAddPresetPanel modalForWindow: fWindow modalDelegate: NULL didEndSelector: NULL contextInfo: NULL];
3411 }
3412
3413 - (IBAction) closeAddPresetPanel: (id) sender
3414 {
3415     [NSApp endSheet: fAddPresetPanel];
3416     [fAddPresetPanel orderOut: self];
3417 }
3418
3419 - (IBAction)addUserPreset:(id)sender
3420 {
3421     if (![[fPresetNewName stringValue] length])
3422             NSRunAlertPanel(@"Warning!", @"You need to insert a name for the preset.", @"OK", nil , nil);
3423     else
3424     {
3425         /* Here we create a custom user preset */
3426         [UserPresets addObject:[self createPreset]];
3427         [self addPreset];
3428         
3429         [self closeAddPresetPanel:NULL];
3430     }
3431 }
3432 - (void)addPreset
3433 {
3434
3435         
3436         /* We Sort the Presets By Factory or Custom */
3437         NSSortDescriptor * presetTypeDescriptor=[[[NSSortDescriptor alloc] initWithKey:@"Type" 
3438                                                     ascending:YES] autorelease];
3439         /* We Sort the Presets Alphabetically by name */
3440         NSSortDescriptor * presetNameDescriptor=[[[NSSortDescriptor alloc] initWithKey:@"PresetName" 
3441                                                     ascending:YES selector:@selector(caseInsensitiveCompare:)] autorelease];
3442         NSArray *sortDescriptors=[NSArray arrayWithObjects:presetTypeDescriptor,presetNameDescriptor,nil];
3443         NSArray *sortedArray=[UserPresets sortedArrayUsingDescriptors:sortDescriptors];
3444         [UserPresets setArray:sortedArray];
3445         
3446         
3447         /* We Reload the New Table data for presets */
3448     [tableView reloadData];
3449    /* We save all of the preset data here */
3450     [self savePreset];
3451 }
3452
3453 - (IBAction)insertPreset:(id)sender
3454 {
3455     int index = [tableView selectedRow];
3456     [UserPresets insertObject:[self createPreset] atIndex:index];
3457     [tableView reloadData];
3458     [self savePreset];
3459 }
3460
3461 - (NSDictionary *)createPreset
3462 {
3463     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
3464         /* Get the New Preset Name from the field in the AddPresetPanel */
3465     [preset setObject:[fPresetNewName stringValue] forKey:@"PresetName"];
3466         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
3467         [preset setObject:[NSNumber numberWithInt:1] forKey:@"Type"];
3468         /*Set whether or not this is default, at creation set to 0*/
3469         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
3470         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
3471         [preset setObject:[NSNumber numberWithInt:[fPresetNewPicSettingsPopUp indexOfSelectedItem]] forKey:@"UsesPictureSettings"];
3472         /* Get New Preset Description from the field in the AddPresetPanel*/
3473         [preset setObject:[fPresetNewDesc stringValue] forKey:@"PresetDescription"];
3474         /* File Format */
3475     [preset setObject:[fDstFormatPopUp titleOfSelectedItem] forKey:@"FileFormat"];
3476         /* Chapter Markers fCreateChapterMarkers*/
3477         [preset setObject:[NSNumber numberWithInt:[fCreateChapterMarkers state]] forKey:@"ChapterMarkers"];
3478         /* Allow Mpeg4 64 bit formatting +4GB file sizes */
3479         [preset setObject:[NSNumber numberWithInt:[fDstMpgLargeFileCheck state]] forKey:@"Mp4LargeFile"];
3480         /* Codecs */
3481         [preset setObject:[fDstCodecsPopUp titleOfSelectedItem] forKey:@"FileCodecs"];
3482         /* Video encoder */
3483         [preset setObject:[fVidEncoderPopUp titleOfSelectedItem] forKey:@"VideoEncoder"];
3484         /* x264 Option String */
3485         [preset setObject:[fAdvancedOptions optionsString] forKey:@"x264Option"];
3486         
3487         [preset setObject:[NSNumber numberWithInt:[fVidQualityMatrix selectedRow]] forKey:@"VideoQualityType"];
3488         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
3489         [preset setObject:[fVidBitrateField stringValue] forKey:@"VideoAvgBitrate"];
3490         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
3491         
3492         /* Video framerate */
3493     if ([fVidRatePopUp indexOfSelectedItem] == 0) // Same as source is selected
3494         {
3495     [preset setObject:[NSString stringWithFormat: @"Same as source"] forKey:@"VideoFramerate"];
3496     }
3497     else // we can record the actual titleOfSelectedItem
3498     {
3499     [preset setObject:[fVidRatePopUp titleOfSelectedItem] forKey:@"VideoFramerate"];
3500     }
3501         /* GrayScale */
3502         [preset setObject:[NSNumber numberWithInt:[fVidGrayscaleCheck state]] forKey:@"VideoGrayScale"];
3503         /* 2 Pass Encoding */
3504         [preset setObject:[NSNumber numberWithInt:[fVidTwoPassCheck state]] forKey:@"VideoTwoPass"];
3505         /* Turbo 2 pass Encoding fVidTurboPassCheck*/
3506         [preset setObject:[NSNumber numberWithInt:[fVidTurboPassCheck state]] forKey:@"VideoTurboTwoPass"];
3507         /*Picture Settings*/
3508         hb_job_t * job = fTitle->job;
3509         /* Basic Picture Settings */
3510         /* Use Max Picture settings for whatever the dvd is.*/
3511         [preset setObject:[NSNumber numberWithInt:0] forKey:@"UsesMaxPictureSettings"];
3512         [preset setObject:[NSNumber numberWithInt:fTitle->job->width] forKey:@"PictureWidth"];
3513         [preset setObject:[NSNumber numberWithInt:fTitle->job->height] forKey:@"PictureHeight"];
3514         [preset setObject:[NSNumber numberWithInt:fTitle->job->keep_ratio] forKey:@"PictureKeepRatio"];
3515         [preset setObject:[NSNumber numberWithInt:[fPictureController deinterlace]] forKey:@"PictureDeinterlace"];
3516         [preset setObject:[NSNumber numberWithInt:fTitle->job->pixel_ratio] forKey:@"PicturePAR"];
3517         [preset setObject:[NSNumber numberWithInt:[fPictureController detelecine]] forKey:@"PictureDetelecine"];
3518         [preset setObject:[NSNumber numberWithInt:[fPictureController denoise]] forKey:@"PictureDenoise"];
3519     [preset setObject:[NSNumber numberWithInt:[fPictureController deblock]] forKey:@"PictureDeblock"];
3520     
3521         /* Set crop settings here */
3522         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
3523         [preset setObject:[NSNumber numberWithInt:[fPictureController autoCrop]] forKey:@"PictureAutoCrop"];
3524
3525         [preset setObject:[NSNumber numberWithInt:job->crop[0]] forKey:@"PictureTopCrop"];
3526     [preset setObject:[NSNumber numberWithInt:job->crop[1]] forKey:@"PictureBottomCrop"];
3527         [preset setObject:[NSNumber numberWithInt:job->crop[2]] forKey:@"PictureLeftCrop"];
3528         [preset setObject:[NSNumber numberWithInt:job->crop[3]] forKey:@"PictureRightCrop"];
3529         
3530         /*Audio*/
3531         /* Audio Sample Rate*/
3532         [preset setObject:[fAudRatePopUp titleOfSelectedItem] forKey:@"AudioSampleRate"];
3533         /* Audio Bitrate Rate*/
3534         [preset setObject:[fAudBitratePopUp titleOfSelectedItem] forKey:@"AudioBitRate"];
3535         /* Subtitles*/
3536         [preset setObject:[fSubPopUp titleOfSelectedItem] forKey:@"Subtitles"];
3537         
3538
3539     [preset autorelease];
3540     return preset;
3541
3542 }
3543
3544 - (void)savePreset
3545 {
3546     [UserPresets writeToFile:UserPresetsFile atomically:YES];
3547         /* We get the default preset in case it changed */
3548         [self getDefaultPresets: NULL];
3549
3550 }
3551
3552 - (IBAction)deletePreset:(id)sender
3553 {
3554     int status;
3555     NSEnumerator *enumerator;
3556     NSNumber *index;
3557     NSMutableArray *tempArray;
3558     id tempObject;
3559     
3560     if ( [tableView numberOfSelectedRows] == 0 )
3561         return;
3562     /* Alert user before deleting preset */
3563         /* Comment out for now, tie to user pref eventually */
3564
3565     //NSBeep();
3566     status = NSRunAlertPanel(@"Warning!", @"Are you sure that you want to delete the selected preset?", @"OK", @"Cancel", nil);
3567     
3568     if ( status == NSAlertDefaultReturn ) {
3569         enumerator = [tableView selectedRowEnumerator];
3570         tempArray = [NSMutableArray array];
3571         
3572         while ( (index = [enumerator nextObject]) ) {
3573             tempObject = [UserPresets objectAtIndex:[index intValue]];
3574             [tempArray addObject:tempObject];
3575         }
3576         
3577         [UserPresets removeObjectsInArray:tempArray];
3578         [tableView reloadData];
3579         [self savePreset];   
3580     }
3581 }
3582
3583 #pragma mark -
3584 #pragma mark Manage Default Preset
3585
3586 - (IBAction)getDefaultPresets:(id)sender
3587 {
3588         int i = 0;
3589     NSEnumerator *enumerator = [UserPresets objectEnumerator];
3590         id tempObject;
3591         while (tempObject = [enumerator nextObject])
3592         {
3593                 NSDictionary *thisPresetDict = tempObject;
3594                 if ([[thisPresetDict objectForKey:@"Default"] intValue] == 1) // 1 is HB default
3595                 {
3596                         presetHbDefault = i;    
3597                 }
3598                 if ([[thisPresetDict objectForKey:@"Default"] intValue] == 2) // 2 is User specified default
3599                 {
3600                         presetUserDefault = i;  
3601                 }
3602                 i++;
3603         }
3604 }
3605
3606 - (IBAction)setDefaultPreset:(id)sender
3607 {
3608     int i = 0;
3609     NSEnumerator *enumerator = [UserPresets objectEnumerator];
3610         id tempObject;
3611         /* First make sure the old user specified default preset is removed */
3612         while (tempObject = [enumerator nextObject])
3613         {
3614                 /* make sure we are not removing the default HB preset */
3615                 if ([[[UserPresets objectAtIndex:i] objectForKey:@"Default"] intValue] != 1) // 1 is HB default
3616                 {
3617                         [[UserPresets objectAtIndex:i] setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
3618                 }
3619                 i++;
3620         }
3621         /* Second, go ahead and set the appropriate user specfied preset */
3622         /* we get the chosen preset from the UserPresets array */
3623         if ([[[UserPresets objectAtIndex:[tableView selectedRow]] objectForKey:@"Default"] intValue] != 1) // 1 is HB default
3624         {
3625                 [[UserPresets objectAtIndex:[tableView selectedRow]] setObject:[NSNumber numberWithInt:2] forKey:@"Default"];
3626         }
3627         presetUserDefault = [tableView selectedRow];
3628         
3629         /* We save all of the preset data here */
3630     [self savePreset];
3631         /* We Reload the New Table data for presets */
3632     [tableView reloadData];
3633 }
3634
3635 - (IBAction)selectDefaultPreset:(id)sender
3636 {
3637         /* if there is a user specified default, we use it */
3638         if (presetUserDefault)
3639         {
3640         [tableView selectRowIndexes:[NSIndexSet indexSetWithIndex:presetUserDefault] byExtendingSelection:NO];
3641         [self tableViewSelected:NULL];
3642         }
3643         else if (presetHbDefault) //else we use the built in default presetHbDefault
3644         {
3645         [tableView selectRowIndexes:[NSIndexSet indexSetWithIndex:presetHbDefault] byExtendingSelection:NO];
3646         [self tableViewSelected:NULL];
3647         }
3648 }
3649
3650
3651 #pragma mark -
3652 #pragma mark Manage Built In Presets
3653
3654
3655 - (IBAction)deleteFactoryPresets:(id)sender
3656 {
3657     //int status;
3658     NSEnumerator *enumerator = [UserPresets objectEnumerator];
3659         id tempObject;
3660     
3661         //NSNumber *index;
3662     NSMutableArray *tempArray;
3663
3664
3665         tempArray = [NSMutableArray array];
3666         /* we look here to see if the preset is we move on to the next one */
3667         while ( tempObject = [enumerator nextObject] )  
3668                 {
3669                         /* if the preset is "Factory" then we put it in the array of
3670                         presets to delete */
3671                         if ([[tempObject objectForKey:@"Type"] intValue] == 0)
3672                         {
3673                                 [tempArray addObject:tempObject];
3674                         }
3675         }
3676         
3677         [UserPresets removeObjectsInArray:tempArray];
3678         [tableView reloadData];
3679         [self savePreset];   
3680
3681 }
3682
3683    /* We use this method to recreate new, updated factory
3684    presets */
3685 - (IBAction)addFactoryPresets:(id)sender
3686 {
3687     /* First, we delete any existing built in presets */
3688     [self deleteFactoryPresets: sender];
3689     /* Then, we re-create new built in presets programmatically CreateIpodOnlyPreset*/
3690     [UserPresets addObject:[self createNormalPreset]];
3691     [UserPresets addObject:[self createClassicPreset]];
3692     [UserPresets addObject:[self createQuickTimePreset]];
3693         [UserPresets addObject:[self createIpodLowPreset]];
3694         [UserPresets addObject:[self createIpodHighPreset]];
3695         [UserPresets addObject:[self createAppleTVPreset]];
3696     [UserPresets addObject:[self createiPhonePreset]];
3697         [UserPresets addObject:[self createPSThreePreset]];
3698         [UserPresets addObject:[self createPSPPreset]];
3699         [UserPresets addObject:[self createFilmPreset]];
3700     [UserPresets addObject:[self createTelevisionPreset]];
3701     [UserPresets addObject:[self createAnimationPreset]];
3702     [UserPresets addObject:[self createBedlamPreset]];
3703     [UserPresets addObject:[self createDeuxSixQuatrePreset]];
3704     [UserPresets addObject:[self createBrokePreset]];
3705     [UserPresets addObject:[self createBlindPreset]];
3706     [UserPresets addObject:[self createCRFPreset]];
3707     
3708     [self addPreset];
3709 }
3710
3711 #pragma mark -
3712 #pragma mark Built In Preset Definitions
3713 /* These NSDictionary Buit In Preset definitions contain all of the settings for one built in preset */
3714 - (NSDictionary *)createIpodLowPreset
3715 {
3716     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
3717         /* Get the New Preset Name from the field in the AddPresetPanel */
3718     [preset setObject:@"iPod Low-Rez" forKey:@"PresetName"];
3719         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
3720         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
3721         /*Set whether or not this is default, at creation set to 0*/
3722         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
3723         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
3724         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
3725         /* Get the New Preset Description from the field in the AddPresetPanel */
3726     [preset setObject:@"HandBrake's low resolution settings for the iPod. Optimized for great playback on the iPod screen, with smaller file size." forKey:@"PresetDescription"];
3727         /* File Format */
3728     [preset setObject:@"MP4 file" forKey:@"FileFormat"];
3729         /* Chapter Markers*/
3730          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
3731     /* Codecs */
3732         [preset setObject:@"AVC/H.264 Video / AAC Audio" forKey:@"FileCodecs"];
3733         /* Video encoder */
3734         [preset setObject:@"x264 (h.264 iPod)" forKey:@"VideoEncoder"];
3735         /* x264 Option String */
3736         [preset setObject:@"keyint=300:keyint-min=30:bframes=0:cabac=0:ref=1:vbv-maxrate=768:vbv-bufsize=2000:analyse=all:me=umh:subme=6:no-fast-pskip=1" forKey:@"x264Option"];
3737         /* Video quality */
3738         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
3739         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
3740         [preset setObject:@"700" forKey:@"VideoAvgBitrate"];
3741         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
3742         
3743         /* Video framerate */
3744         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
3745         /* GrayScale */
3746         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
3747         /* 2 Pass Encoding */
3748         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoTwoPass"];
3749         
3750         /*Picture Settings*/
3751         //hb_job_t * job = fTitle->job;
3752         /* Basic Picture Settings */
3753         /* Use Max Picture settings for whatever the dvd is.*/
3754         [preset setObject:[NSNumber numberWithInt:0] forKey:@"UsesMaxPictureSettings"];
3755         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
3756         [preset setObject:[NSNumber numberWithInt:320] forKey:@"PictureWidth"];
3757         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
3758         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureKeepRatio"];
3759         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
3760         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PicturePAR"];
3761         /* Set crop settings here */
3762         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
3763         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
3764     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
3765         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
3766         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
3767         
3768         /*Audio*/
3769         /* Audio Sample Rate*/
3770         [preset setObject:@"48" forKey:@"AudioSampleRate"];
3771         /* Audio Bitrate Rate*/
3772         [preset setObject:@"160" forKey:@"AudioBitRate"];
3773         /* Subtitles*/
3774         [preset setObject:@"None" forKey:@"Subtitles"];
3775         
3776
3777     [preset autorelease];
3778     return preset;
3779
3780 }
3781
3782
3783 - (NSDictionary *)createIpodHighPreset
3784 {
3785     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
3786         /* Get the New Preset Name from the field in the AddPresetPanel */
3787     [preset setObject:@"iPod High-Rez" forKey:@"PresetName"];
3788         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
3789         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
3790         /*Set whether or not this is default, at creation set to 0*/
3791         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
3792         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
3793         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
3794         /* Get the New Preset Description from the field in the AddPresetPanel */
3795     [preset setObject:@"HandBrake's high resolution settings for the iPod. Good video quality, great for viewing on a TV using your iPod" forKey:@"PresetDescription"];
3796         /* File Format */
3797     [preset setObject:@"MP4 file" forKey:@"FileFormat"];
3798         /* Chapter Markers*/
3799          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
3800     /* Codecs */
3801         [preset setObject:@"AVC/H.264 Video / AAC Audio" forKey:@"FileCodecs"];
3802         /* Video encoder */
3803         [preset setObject:@"x264 (h.264 iPod)" forKey:@"VideoEncoder"];
3804         /* x264 Option String */
3805         [preset setObject:@"keyint=300:keyint-min=30:bframes=0:cabac=0:ref=1:vbv-maxrate=1500:vbv-bufsize=2000:analyse=all:me=umh:subme=6:no-fast-pskip=1" forKey:@"x264Option"];
3806         /* Video quality */
3807         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
3808         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
3809         [preset setObject:@"1500" forKey:@"VideoAvgBitrate"];
3810         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
3811         
3812         /* Video framerate */
3813         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
3814         /* GrayScale */
3815         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
3816         /* 2 Pass Encoding */
3817         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoTwoPass"];
3818         
3819         /*Picture Settings*/
3820         //hb_job_t * job = fTitle->job;
3821         /* Basic Picture Settings */
3822         /* Use Max Picture settings for whatever the dvd is.*/
3823         [preset setObject:[NSNumber numberWithInt:0] forKey:@"UsesMaxPictureSettings"];
3824         [preset setObject:[NSNumber numberWithInt:640] forKey:@"PictureWidth"];
3825         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
3826         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureKeepRatio"];
3827         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
3828         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PicturePAR"];
3829         /* Set crop settings here */
3830         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
3831         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
3832         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
3833     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
3834         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
3835         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
3836         
3837         /*Audio*/
3838         /* Audio Sample Rate*/
3839         [preset setObject:@"48" forKey:@"AudioSampleRate"];
3840         /* Audio Bitrate Rate*/
3841         [preset setObject:@"160" forKey:@"AudioBitRate"];
3842         /* Subtitles*/
3843         [preset setObject:@"None" forKey:@"Subtitles"];
3844         
3845
3846     [preset autorelease];
3847     return preset;
3848
3849 }
3850
3851 - (NSDictionary *)createAppleTVPreset
3852 {
3853     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
3854         /* Get the New Preset Name from the field in the AddPresetPanel */
3855     [preset setObject:@"AppleTV" forKey:@"PresetName"];
3856         /*Set whether or not this is a user preset where 0 is factory, 1 is user*/
3857         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
3858         /*Set whether or not this is default, at creation set to 0*/
3859         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
3860         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
3861         [preset setObject:[NSNumber numberWithInt:2] forKey:@"UsesPictureSettings"];
3862         /* Get the New Preset Description from the field in the AddPresetPanel */
3863     [preset setObject:@"HandBrake's settings for the AppleTV. Provides a good balance between quality and file size, and optimizes performance." forKey:@"PresetDescription"];
3864         /* File Format */
3865     [preset setObject:@"MP4 file" forKey:@"FileFormat"];
3866         /* Chapter Markers*/
3867          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
3868         /* Codecs */
3869         [preset setObject:@"AVC/H.264 Video / AAC Audio" forKey:@"FileCodecs"];
3870         /* Video encoder */
3871         [preset setObject:@"x264 (h.264 Main)" forKey:@"VideoEncoder"];
3872         /* x264 Option String (We can use this to tweak the appleTV output)*/
3873         [preset setObject:@"bframes=3:ref=1:subme=5:me=umh:no-fast-pskip=1:trellis=2:cabac=0" forKey:@"x264Option"];
3874         /* Video quality */
3875         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
3876         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
3877         [preset setObject:@"2500" forKey:@"VideoAvgBitrate"];
3878         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
3879         
3880         /* Video framerate */
3881         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
3882         /* GrayScale */
3883         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
3884         /* 2 Pass Encoding */
3885         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoTwoPass"];
3886         
3887         /*Picture Settings*/
3888         /* For AppleTV we only want to retain UsesMaxPictureSettings
3889         which depend on the source dvd picture settings, so we don't
3890         record the current dvd's picture info since it will vary from
3891         source to source*/
3892         //hb_job_t * job = fTitle->job;
3893         //hb_job_t * job = title->job;
3894         /* Basic Picture Settings */
3895         /* Use Max Picture settings for whatever the dvd is.*/
3896         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesMaxPictureSettings"];
3897         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureWidth"];
3898         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
3899         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureKeepRatio"];
3900         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
3901         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PicturePAR"];
3902         /* Set crop settings here */
3903         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
3904         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
3905     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
3906         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
3907         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
3908         
3909         /*Audio*/
3910         /* Audio Sample Rate*/
3911         [preset setObject:@"48" forKey:@"AudioSampleRate"];
3912         /* Audio Bitrate Rate*/
3913         [preset setObject:@"160" forKey:@"AudioBitRate"];
3914         /* Subtitles*/
3915         [preset setObject:@"None" forKey:@"Subtitles"];
3916         
3917
3918     [preset autorelease];
3919     return preset;
3920
3921 }
3922
3923 - (NSDictionary *)createPSThreePreset
3924 {
3925     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
3926         /* Get the New Preset Name from the field in the AddPresetPanel */
3927     [preset setObject:@"PS3" forKey:@"PresetName"];
3928         /*Set whether or not this is a user preset where 0 is factory, 1 is user*/
3929         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
3930         /*Set whether or not this is default, at creation set to 0*/
3931         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
3932         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
3933         [preset setObject:[NSNumber numberWithInt:2] forKey:@"UsesPictureSettings"];
3934         /* Get the New Preset Description from the field in the AddPresetPanel */
3935     [preset setObject:@"HandBrake's settings for the Sony PlayStation 3." forKey:@"PresetDescription"];
3936         /* File Format */
3937     [preset setObject:@"MP4 file" forKey:@"FileFormat"];
3938         /* Chapter Markers*/
3939          [preset setObject:[NSNumber numberWithInt:0] forKey:@"ChapterMarkers"];
3940         /* Codecs */
3941         [preset setObject:@"AVC/H.264 Video / AAC Audio" forKey:@"FileCodecs"];
3942         /* Video encoder */
3943         [preset setObject:@"x264 (h.264 Main)" forKey:@"VideoEncoder"];
3944         /* x264 Option String (We can use this to tweak the appleTV output)*/
3945         [preset setObject:@"level=41:subme=5:me=umh" forKey:@"x264Option"];
3946         /* Video quality */
3947         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
3948         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
3949         [preset setObject:@"2500" forKey:@"VideoAvgBitrate"];
3950         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
3951         
3952         /* Video framerate */
3953         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
3954         /* GrayScale */
3955         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
3956         /* 2 Pass Encoding */
3957         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoTwoPass"];
3958         
3959         /*Picture Settings*/
3960         /* For PS3 we only want to retain UsesMaxPictureSettings
3961         which depend on the source dvd picture settings, so we don't
3962         record the current dvd's picture info since it will vary from
3963         source to source*/
3964         /* Use Max Picture settings for whatever the dvd is.*/
3965         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesMaxPictureSettings"];
3966         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureWidth"];
3967         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
3968         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureKeepRatio"];
3969         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
3970         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PicturePAR"];
3971         /* Set crop settings here */
3972         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
3973         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
3974     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
3975         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
3976         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
3977         
3978         /*Audio*/
3979         /* Audio Sample Rate*/
3980         [preset setObject:@"48" forKey:@"AudioSampleRate"];
3981         /* Audio Bitrate Rate*/
3982         [preset setObject:@"160" forKey:@"AudioBitRate"];
3983         /* Subtitles*/
3984         [preset setObject:@"None" forKey:@"Subtitles"];
3985         
3986
3987     [preset autorelease];
3988     return preset;
3989
3990 }
3991 - (NSDictionary *)createPSPPreset
3992 {
3993     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
3994         /* Get the New Preset Name from the field in the AddPresetPanel */
3995     [preset setObject:@"PSP" forKey:@"PresetName"];
3996         /*Set whether or not this is a user preset where 0 is factory, 1 is user*/
3997         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
3998         /*Set whether or not this is default, at creation set to 0*/
3999         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
4000         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4001         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4002         /* Get the New Preset Description from the field in the AddPresetPanel */
4003     [preset setObject:@"HandBrake's settings for the Sony PlayStation Portable." forKey:@"PresetDescription"];
4004         /* File Format */
4005     [preset setObject:@"MP4 file" forKey:@"FileFormat"];
4006         /* Chapter Markers*/
4007          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
4008         /* Codecs */
4009         [preset setObject:@"MPEG-4 Video / AAC Audio" forKey:@"FileCodecs"];
4010         /* Video encoder */
4011         [preset setObject:@"FFmpeg" forKey:@"VideoEncoder"];
4012         /* x264 Option String (We can use this to tweak the appleTV output)*/
4013         [preset setObject:@"" forKey:@"x264Option"];
4014         /* Video quality */
4015         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
4016         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
4017         [preset setObject:@"1024" forKey:@"VideoAvgBitrate"];
4018         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
4019         
4020         /* Video framerate */
4021         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4022         /* GrayScale */
4023         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4024         /* 2 Pass Encoding */
4025         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoTwoPass"];
4026         
4027         /*Picture Settings*/
4028         /* For PS3 we only want to retain UsesMaxPictureSettings
4029         which depend on the source dvd picture settings, so we don't
4030         record the current dvd's picture info since it will vary from
4031         source to source*/
4032         /* Use Max Picture settings for whatever the dvd is.*/
4033         [preset setObject:[NSNumber numberWithInt:0] forKey:@"UsesMaxPictureSettings"];
4034         [preset setObject:@"368" forKey:@"PictureWidth"];
4035         [preset setObject:@"208" forKey:@"PictureHeight"];
4036         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureKeepRatio"];
4037         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
4038         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PicturePAR"];
4039         /* Set crop settings here */
4040         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4041         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4042         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4043     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4044         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4045         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4046         
4047         /*Audio*/
4048         /* Audio Sample Rate*/
4049         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4050         /* Audio Bitrate Rate*/
4051         [preset setObject:@"128" forKey:@"AudioBitRate"];
4052         /* Subtitles*/
4053         [preset setObject:@"None" forKey:@"Subtitles"];
4054         
4055
4056     [preset autorelease];
4057     return preset;
4058
4059 }
4060
4061 - (NSDictionary *)createNormalPreset
4062 {
4063     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
4064         /* Get the New Preset Name from the field in the AddPresetPanel */
4065     [preset setObject:@"Normal" forKey:@"PresetName"];
4066         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
4067         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
4068         /*Set whether or not this is default, at creation set to 0*/
4069         [preset setObject:[NSNumber numberWithInt:1] forKey:@"Default"];
4070         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4071         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4072         /* Get the New Preset Description from the field in the AddPresetPanel */
4073     [preset setObject:@"HandBrake's normal, default settings." forKey:@"PresetDescription"];
4074         /* File Format */
4075     [preset setObject:@"MP4 file" forKey:@"FileFormat"];
4076         /* Chapter Markers*/
4077          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
4078     /* Codecs */
4079         [preset setObject:@"AVC/H.264 Video / AAC Audio" forKey:@"FileCodecs"];
4080         /* Video encoder */
4081         [preset setObject:@"x264 (h.264 Main)" forKey:@"VideoEncoder"];
4082         /* x264 Option String */
4083         [preset setObject:@"ref=2:bframes=2:subme=5:me=umh" forKey:@"x264Option"];
4084         /* Video quality */
4085         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
4086         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
4087         [preset setObject:@"1500" forKey:@"VideoAvgBitrate"];
4088         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
4089         
4090         /* Video framerate */
4091         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4092         /* GrayScale */
4093         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4094         /* 2 Pass Encoding */
4095         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTwoPass"];
4096         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTurboTwoPass"];
4097         
4098         /*Picture Settings*/
4099         //hb_job_t * job = fTitle->job;
4100         /* Basic Picture Settings */
4101         /* Use Max Picture settings for whatever the dvd is.*/
4102         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesMaxPictureSettings"];
4103         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4104         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureWidth"];
4105         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
4106         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureKeepRatio"];
4107         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
4108         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PicturePAR"];
4109         /* Set crop settings here */
4110         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4111         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4112     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4113         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4114         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4115         
4116         /*Audio*/
4117         /* Audio Sample Rate*/
4118         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4119         /* Audio Bitrate Rate*/
4120         [preset setObject:@"160" forKey:@"AudioBitRate"];
4121         /* Subtitles*/
4122         [preset setObject:@"None" forKey:@"Subtitles"];
4123         
4124
4125     [preset autorelease];
4126     return preset;
4127
4128 }
4129
4130 - (NSDictionary *)createClassicPreset
4131 {
4132     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
4133         /* Get the New Preset Name from the field in the AddPresetPanel */
4134     [preset setObject:@"Classic" forKey:@"PresetName"];
4135         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
4136         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
4137         /*Set whether or not this is default, at creation set to 0*/
4138         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
4139         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4140         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4141         /* Get the New Preset Description from the field in the AddPresetPanel */
4142     [preset setObject:@"HandBrake's traditional, faster, lower-quality settings." forKey:@"PresetDescription"];
4143         /* File Format */
4144     [preset setObject:@"MP4 file" forKey:@"FileFormat"];
4145         /* Chapter Markers*/
4146          [preset setObject:[NSNumber numberWithInt:0] forKey:@"ChapterMarkers"];
4147     /* Codecs */
4148         [preset setObject:@"MPEG-4 Video / AAC Audio" forKey:@"FileCodecs"];
4149         /* Video encoder */
4150         [preset setObject:@"FFmpeg" forKey:@"VideoEncoder"];
4151         /* x264 Option String */
4152         [preset setObject:@"" forKey:@"x264Option"];
4153         /* Video quality */
4154         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
4155         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
4156         [preset setObject:@"1000" forKey:@"VideoAvgBitrate"];
4157         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
4158         
4159         /* Video framerate */
4160         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4161         /* GrayScale */
4162         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4163         /* 2 Pass Encoding */
4164         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoTwoPass"];
4165         
4166         /*Picture Settings*/
4167         //hb_job_t * job = fTitle->job;
4168         /* Basic Picture Settings */
4169         /* Use Max Picture settings for whatever the dvd is.*/
4170         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesMaxPictureSettings"];
4171         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4172         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureWidth"];
4173         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
4174         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureKeepRatio"];
4175         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
4176         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PicturePAR"];
4177         /* Set crop settings here */
4178         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4179         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4180     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4181         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4182         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4183         
4184         /*Audio*/
4185         /* Audio Sample Rate*/
4186         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4187         /* Audio Bitrate Rate*/
4188         [preset setObject:@"160" forKey:@"AudioBitRate"];
4189         /* Subtitles*/
4190         [preset setObject:@"None" forKey:@"Subtitles"];
4191         
4192
4193     [preset autorelease];
4194     return preset;
4195
4196 }
4197
4198 - (NSDictionary *)createFilmPreset
4199 {
4200     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
4201         /* Get the New Preset Name from the field in the AddPresetPanel */
4202     [preset setObject:@"Film" forKey:@"PresetName"];
4203         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
4204         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
4205         /*Set whether or not this is default, at creation set to 0*/
4206         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
4207         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4208         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4209         /* Get the New Preset Description from the field in the AddPresetPanel */
4210     [preset setObject:@"HandBrake's preset for feature films." forKey:@"PresetDescription"];
4211         /* File Format */
4212     [preset setObject:@"MKV file" forKey:@"FileFormat"];
4213         /* Chapter Markers*/
4214          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
4215     /* Codecs */
4216         [preset setObject:@"AVC/H.264 Video / AC-3 Audio" forKey:@"FileCodecs"];
4217         /* Video encoder */
4218         [preset setObject:@"x264 (h.264 Main)" forKey:@"VideoEncoder"];
4219         /* x264 Option String */
4220         [preset setObject:@"ref=3:mixed-refs:bframes=16:bime:weightb:b-rdo:direct=auto:b-pyramid:me=umh:subme=6:analyse=all:8x8dct:trellis=1:no-fast-pskip" forKey:@"x264Option"];
4221         /* Video quality */
4222         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
4223         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
4224         [preset setObject:@"1800" forKey:@"VideoAvgBitrate"];
4225         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
4226         
4227         /* Video framerate */
4228         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4229         /* GrayScale */
4230         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4231         /* 2 Pass Encoding */
4232         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTwoPass"];
4233         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTurboTwoPass"];
4234         
4235         /*Picture Settings*/
4236         //hb_job_t * job = fTitle->job;
4237         /* Basic Picture Settings */
4238         /* Use Max Picture settings for whatever the dvd is.*/
4239         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesMaxPictureSettings"];
4240         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4241         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureWidth"];
4242         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
4243         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureKeepRatio"];
4244         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
4245         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PicturePAR"];
4246         /* Set crop settings here */
4247         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4248         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4249     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4250         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4251         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4252         
4253         /*Audio*/
4254         /* Audio Sample Rate*/
4255         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4256         /* Audio Bitrate Rate*/
4257         [preset setObject:@"160" forKey:@"AudioBitRate"];
4258         /* Subtitles*/
4259         [preset setObject:@"None" forKey:@"Subtitles"];
4260         
4261
4262     [preset autorelease];
4263     return preset;
4264
4265 }
4266
4267 - (NSDictionary *)createTelevisionPreset
4268 {
4269     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
4270         /* Get the New Preset Name from the field in the AddPresetPanel */
4271     [preset setObject:@"Television" forKey:@"PresetName"];
4272         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
4273         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
4274         /*Set whether or not this is default, at creation set to 0*/
4275         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
4276         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4277         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4278         /* Get the New Preset Description from the field in the AddPresetPanel */
4279     [preset setObject:@"HandBrake's settings for video from television." forKey:@"PresetDescription"];
4280         /* File Format */
4281     [preset setObject:@"MKV file" forKey:@"FileFormat"];
4282         /* Chapter Markers*/
4283          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
4284     /* Codecs */
4285         [preset setObject:@"AVC/H.264 Video / AAC Audio" forKey:@"FileCodecs"];
4286         /* Video encoder */
4287         [preset setObject:@"x264 (h.264 Main)" forKey:@"VideoEncoder"];
4288         /* x264 Option String */
4289         [preset setObject:@"ref=3:mixed-refs:bframes=16:bime:weightb:direct=auto:b-pyramid:me=umh:subme=6:analyse=all:8x8dct:trellis=1:nr=150:no-fast-pskip" forKey:@"x264Option"];
4290         /* Video quality */
4291         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
4292         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
4293         [preset setObject:@"1300" forKey:@"VideoAvgBitrate"];
4294         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
4295         
4296         /* Video framerate */
4297         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4298         /* GrayScale */
4299         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4300         /* 2 Pass Encoding */
4301         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTwoPass"];
4302         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTurboTwoPass"];
4303         
4304         /*Picture Settings*/
4305         //hb_job_t * job = fTitle->job;
4306         /* Basic Picture Settings */
4307         /* Use Max Picture settings for whatever the dvd is.*/
4308         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesMaxPictureSettings"];
4309         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4310         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureWidth"];
4311         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
4312         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureKeepRatio"];
4313         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureDeinterlace"];
4314         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PicturePAR"];
4315         /* Set crop settings here */
4316         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4317         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4318     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4319         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4320         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4321         
4322         /*Audio*/
4323         /* Audio Sample Rate*/
4324         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4325         /* Audio Bitrate Rate*/
4326         [preset setObject:@"160" forKey:@"AudioBitRate"];
4327         /* Subtitles*/
4328         [preset setObject:@"None" forKey:@"Subtitles"];
4329         
4330
4331     [preset autorelease];
4332     return preset;
4333
4334 }
4335
4336 - (NSDictionary *)createAnimationPreset
4337 {
4338     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
4339         /* Get the New Preset Name from the field in the AddPresetPanel */
4340     [preset setObject:@"Animation" forKey:@"PresetName"];
4341         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
4342         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
4343         /*Set whether or not this is default, at creation set to 0*/
4344         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
4345         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4346         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4347         /* Get the New Preset Description from the field in the AddPresetPanel */
4348     [preset setObject:@"HandBrake's settings for cartoons, anime, and CGI." forKey:@"PresetDescription"];
4349         /* File Format */
4350     [preset setObject:@"MKV file" forKey:@"FileFormat"];
4351         /* Chapter Markers*/
4352          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
4353     /* Codecs */
4354         [preset setObject:@"AVC/H.264 Video / AAC Audio" forKey:@"FileCodecs"];
4355         /* Video encoder */
4356         [preset setObject:@"x264 (h.264 Main)" forKey:@"VideoEncoder"];
4357         /* x264 Option String */
4358         [preset setObject:@"ref=5:mixed-refs:bframes=16:bime:weightb:b-rdo:direct=auto:b-pyramid:me=umh:subme=5:analyse=all:8x8dct:trellis=1:nr=150:no-fast-pskip:filter=2,2" forKey:@"x264Option"];
4359         /* Video quality */
4360         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
4361         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
4362         [preset setObject:@"1000" forKey:@"VideoAvgBitrate"];
4363         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
4364         
4365         /* Video framerate */
4366         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4367         /* GrayScale */
4368         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4369         /* 2 Pass Encoding */
4370         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTwoPass"];
4371         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTurboTwoPass"];
4372         
4373         /*Picture Settings*/
4374         //hb_job_t * job = fTitle->job;
4375         /* Basic Picture Settings */
4376         /* Use Max Picture settings for whatever the dvd is.*/
4377         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesMaxPictureSettings"];
4378         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4379         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureWidth"];
4380         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
4381         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureKeepRatio"];
4382         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureDeinterlace"];
4383         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PicturePAR"];
4384         /* Set crop settings here */
4385         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4386         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4387     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4388         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4389         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4390         
4391         /*Audio*/
4392         /* Audio Sample Rate*/
4393         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4394         /* Audio Bitrate Rate*/
4395         [preset setObject:@"160" forKey:@"AudioBitRate"];
4396         /* Subtitles*/
4397         [preset setObject:@"None" forKey:@"Subtitles"];
4398         
4399
4400     [preset autorelease];
4401     return preset;
4402
4403 }
4404
4405 - (NSDictionary *)createQuickTimePreset
4406 {
4407     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
4408         /* Get the New Preset Name from the field in the AddPresetPanel */
4409     [preset setObject:@"QuickTime" forKey:@"PresetName"];
4410         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
4411         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
4412         /*Set whether or not this is default, at creation set to 0*/
4413         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
4414         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4415         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4416         /* Get the New Preset Description from the field in the AddPresetPanel */
4417     [preset setObject:@"HandBrake's high quality settings for use with QuickTime. It can be slow, so use it when the Normal preset doesn't look good enough." forKey:@"PresetDescription"];
4418         /* File Format */
4419     [preset setObject:@"MP4 file" forKey:@"FileFormat"];
4420         /* Chapter Markers*/
4421          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
4422     /* Codecs */
4423         [preset setObject:@"AVC/H.264 Video / AAC Audio" forKey:@"FileCodecs"];
4424         /* Video encoder */
4425         [preset setObject:@"x264 (h.264 Main)" forKey:@"VideoEncoder"];
4426         /* x264 Option String */
4427         [preset setObject:@"ref=3:mixed-refs:bframes=3:bime:weightb:b-rdo:direct=auto:me=umh:subme=5:analyse=all:trellis=1:no-fast-pskip" forKey:@"x264Option"];
4428         /* Video quality */
4429         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
4430         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
4431         [preset setObject:@"2000" forKey:@"VideoAvgBitrate"];
4432         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
4433         
4434         /* Video framerate */
4435         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4436         /* GrayScale */
4437         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4438         /* 2 Pass Encoding */
4439         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTwoPass"];
4440         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTurboTwoPass"];
4441         
4442         /*Picture Settings*/
4443         //hb_job_t * job = fTitle->job;
4444         /* Basic Picture Settings */
4445         /* Use Max Picture settings for whatever the dvd is.*/
4446         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesMaxPictureSettings"];
4447         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4448         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureWidth"];
4449         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
4450         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureKeepRatio"];
4451         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
4452         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PicturePAR"];
4453         /* Set crop settings here */
4454         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4455         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4456     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4457         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4458         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4459         
4460         /*Audio*/
4461         /* Audio Sample Rate*/
4462         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4463         /* Audio Bitrate Rate*/
4464         [preset setObject:@"160" forKey:@"AudioBitRate"];
4465         /* Subtitles*/
4466         [preset setObject:@"None" forKey:@"Subtitles"];
4467         
4468
4469     [preset autorelease];
4470     return preset;
4471
4472 }
4473
4474 - (NSDictionary *)createBedlamPreset
4475 {
4476     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
4477         /* Get the New Preset Name from the field in the AddPresetPanel */
4478     [preset setObject:@"Bedlam" forKey:@"PresetName"];
4479         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
4480         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
4481         /*Set whether or not this is default, at creation set to 0*/
4482         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
4483         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4484         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4485         /* Get the New Preset Description from the field in the AddPresetPanel */
4486     [preset setObject:@"HandBrake's settings maxed out for slowest encoding and highest quality. Use at your own risk. So slow it's not just insane...it's a trip to the looney bin." forKey:@"PresetDescription"];
4487         /* File Format */
4488     [preset setObject:@"MKV file" forKey:@"FileFormat"];
4489         /* Chapter Markers*/
4490          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
4491     /* Codecs */
4492         [preset setObject:@"AVC/H.264 Video / AC-3 Audio" forKey:@"FileCodecs"];
4493         /* Video encoder */
4494         [preset setObject:@"x264 (h.264 Main)" forKey:@"VideoEncoder"];
4495         /* x264 Option String */
4496         [preset setObject:@"ref=16:mixed-refs:bframes=16:bime:weightb:b-rdo:direct=auto:b-pyramid:me=umh:subme=7:me-range=64:analyse=all:8x8dct:trellis=2:no-fast-pskip:no-dct-decimate:filter=-2,-1" forKey:@"x264Option"];
4497         /* Video quality */
4498         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
4499         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
4500         [preset setObject:@"1800" forKey:@"VideoAvgBitrate"];
4501         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
4502         
4503         /* Video framerate */
4504         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4505         /* GrayScale */
4506         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4507         /* 2 Pass Encoding */
4508         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTwoPass"];
4509         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTurboTwoPass"];
4510         
4511         /*Picture Settings*/
4512         //hb_job_t * job = fTitle->job;
4513         /* Basic Picture Settings */
4514         /* Use Max Picture settings for whatever the dvd is.*/
4515         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesMaxPictureSettings"];
4516         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4517         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureWidth"];
4518         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
4519         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureKeepRatio"];
4520         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
4521         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PicturePAR"];
4522         /* Set crop settings here */
4523         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4524         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4525     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4526         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4527         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4528         
4529         /*Audio*/
4530         /* Audio Sample Rate*/
4531         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4532         /* Audio Bitrate Rate*/
4533         [preset setObject:@"160" forKey:@"AudioBitRate"];
4534         /* Subtitles*/
4535         [preset setObject:@"None" forKey:@"Subtitles"];
4536         
4537
4538     [preset autorelease];
4539     return preset;
4540
4541 }
4542
4543 - (NSDictionary *)createiPhonePreset
4544 {
4545     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
4546         /* Get the New Preset Name from the field in the AddPresetPanel */
4547     [preset setObject:@"iPhone / iPod Touch" forKey:@"PresetName"];
4548         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
4549         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
4550         /*Set whether or not this is default, at creation set to 0*/
4551         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
4552         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4553         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4554         /* Get the New Preset Description from the field in the AddPresetPanel */
4555     [preset setObject:@"HandBrake's settings for the iPhone." forKey:@"PresetDescription"];
4556         /* File Format */
4557     [preset setObject:@"MP4 file" forKey:@"FileFormat"];
4558         /* Chapter Markers*/
4559          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
4560     /* Codecs */
4561         [preset setObject:@"AVC/H.264 Video / AAC Audio" forKey:@"FileCodecs"];
4562         /* Video encoder */
4563         [preset setObject:@"x264 (h.264 iPod)" forKey:@"VideoEncoder"];
4564         /* x264 Option String */
4565         [preset setObject:@"cabac=0:ref=1:analyse=all:me=umh:subme=6:no-fast-pskip=1:trellis=1" forKey:@"x264Option"];
4566         /* Video quality */
4567         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
4568         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
4569         [preset setObject:@"960" forKey:@"VideoAvgBitrate"];
4570         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
4571         
4572         /* Video framerate */
4573         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4574         /* GrayScale */
4575         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4576         /* 2 Pass Encoding */
4577         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoTwoPass"];
4578         
4579         /*Picture Settings*/
4580         //hb_job_t * job = fTitle->job;
4581         /* Basic Picture Settings */
4582         /* Use Max Picture settings for whatever the dvd is.*/
4583         [preset setObject:[NSNumber numberWithInt:0] forKey:@"UsesMaxPictureSettings"];
4584         [preset setObject:[NSNumber numberWithInt:480] forKey:@"PictureWidth"];
4585         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
4586         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureKeepRatio"];
4587         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
4588         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PicturePAR"];
4589         /* Set crop settings here */
4590         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4591         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4592         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4593     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4594         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4595         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4596         
4597         /*Audio*/
4598         /* Audio Sample Rate*/
4599         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4600         /* Audio Bitrate Rate*/
4601         [preset setObject:@"128" forKey:@"AudioBitRate"];
4602         /* Subtitles*/
4603         [preset setObject:@"None" forKey:@"Subtitles"];
4604         
4605
4606     [preset autorelease];
4607     return preset;
4608
4609 }
4610
4611 - (NSDictionary *)createDeuxSixQuatrePreset
4612 {
4613     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
4614         /* Get the New Preset Name from the field in the AddPresetPanel */
4615     [preset setObject:@"Deux Six Quatre" forKey:@"PresetName"];
4616         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
4617         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
4618         /*Set whether or not this is default, at creation set to 0*/
4619         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
4620         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4621         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4622         /* Get the New Preset Description from the field in the AddPresetPanel */
4623     [preset setObject:@"HandBrake's preset for true high profile x264 quality. A good balance of quality and speed, based on community standards found in the wild. This preset will give you a much better sense of x264's capabilities than vanilla main profile." forKey:@"PresetDescription"];
4624         /* File Format */
4625     [preset setObject:@"MKV file" forKey:@"FileFormat"];
4626         /* Chapter Markers*/
4627          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
4628     /* Codecs */
4629         [preset setObject:@"AVC/H.264 Video / AC-3 Audio" forKey:@"FileCodecs"];
4630         /* Video encoder */
4631         [preset setObject:@"x264 (h.264 Main)" forKey:@"VideoEncoder"];
4632         /* x264 Option String */
4633         [preset setObject:@"ref=5:mixed-refs:bframes=3:bime:weightb:b-rdo:b-pyramid:me=umh:subme=7:trellis=1:analyse=all:8x8dct:no-fast-pskip" forKey:@"x264Option"];
4634         /* Video quality */
4635         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
4636         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
4637         [preset setObject:@"1600" forKey:@"VideoAvgBitrate"];
4638         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
4639         
4640         /* Video framerate */
4641         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4642         /* GrayScale */
4643         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4644         /* 2 Pass Encoding */
4645         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTwoPass"];
4646         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTurboTwoPass"];
4647         
4648         /*Picture Settings*/
4649         //hb_job_t * job = fTitle->job;
4650         /* Basic Picture Settings */
4651         /* Use Max Picture settings for whatever the dvd is.*/
4652         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesMaxPictureSettings"];
4653         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4654         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureWidth"];
4655         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
4656         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureKeepRatio"];
4657         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
4658         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PicturePAR"];
4659         /* Set crop settings here */
4660         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4661         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4662     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4663         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4664         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4665         
4666         /*Audio*/
4667         /* Audio Sample Rate*/
4668         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4669         /* Audio Bitrate Rate*/
4670         [preset setObject:@"160" forKey:@"AudioBitRate"];
4671         /* Subtitles*/
4672         [preset setObject:@"None" forKey:@"Subtitles"];
4673         
4674
4675     [preset autorelease];
4676     return preset;
4677
4678 }
4679
4680 - (NSDictionary *)createBrokePreset
4681 {
4682     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
4683         /* Get the New Preset Name from the field in the AddPresetPanel */
4684     [preset setObject:@"Broke" forKey:@"PresetName"];
4685         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
4686         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
4687         /*Set whether or not this is default, at creation set to 0*/
4688         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
4689         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4690         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4691         /* Get the New Preset Description from the field in the AddPresetPanel */
4692     [preset setObject:@"HandBrake's preset for people without a lot of money to waste on hard drives. Tries to maximize quality for burning to CDs, so you can party like it's 1999." forKey:@"PresetDescription"];
4693         /* File Format */
4694     [preset setObject:@"MP4 file" forKey:@"FileFormat"];
4695         /* Chapter Markers*/
4696          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
4697     /* Codecs */
4698         [preset setObject:@"AVC/H.264 Video / AAC Audio" forKey:@"FileCodecs"];
4699         /* Video encoder */
4700         [preset setObject:@"x264 (h.264 Main)" forKey:@"VideoEncoder"];
4701         /* x264 Option String */
4702         [preset setObject:@"ref=3:mixed-refs:bframes=16:bime:weightb:b-rdo:b-pyramid:direct=auto:me=umh:subme=6:trellis=1:analyse=all:8x8dct:no-fast-pskip" forKey:@"x264Option"];
4703         /* Video quality */
4704         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoQualityType"];
4705         [preset setObject:@"695" forKey:@"VideoTargetSize"];
4706         [preset setObject:@"1600" forKey:@"VideoAvgBitrate"];
4707         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
4708         
4709         /* Video framerate */
4710         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4711         /* GrayScale */
4712         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4713         /* 2 Pass Encoding */
4714         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTwoPass"];
4715         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoTurboTwoPass"];
4716         
4717         /*Picture Settings*/
4718         //hb_job_t * job = fTitle->job;
4719         /* Basic Picture Settings */
4720         /* Use Max Picture settings for whatever the dvd is.*/
4721         [preset setObject:[NSNumber numberWithInt:0] forKey:@"UsesMaxPictureSettings"];
4722         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4723         [preset setObject:[NSNumber numberWithInt:640] forKey:@"PictureWidth"];
4724         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
4725         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureKeepRatio"];
4726         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
4727         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PicturePAR"];
4728         /* Set crop settings here */
4729         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4730         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4731     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4732         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4733         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4734         
4735         /*Audio*/
4736         /* Audio Sample Rate*/
4737         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4738         /* Audio Bitrate Rate*/
4739         [preset setObject:@"128" forKey:@"AudioBitRate"];
4740         /* Subtitles*/
4741         [preset setObject:@"None" forKey:@"Subtitles"];
4742         
4743
4744     [preset autorelease];
4745     return preset;
4746
4747 }
4748
4749 - (NSDictionary *)createBlindPreset
4750 {
4751     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
4752         /* Get the New Preset Name from the field in the AddPresetPanel */
4753     [preset setObject:@"Blind" forKey:@"PresetName"];
4754         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
4755         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
4756         /*Set whether or not this is default, at creation set to 0*/
4757         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
4758         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4759         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4760         /* Get the New Preset Description from the field in the AddPresetPanel */
4761     [preset setObject:@"HandBrake's preset for impatient people who don't care about picture quality." forKey:@"PresetDescription"];
4762         /* File Format */
4763     [preset setObject:@"MP4 file" forKey:@"FileFormat"];
4764         /* Chapter Markers*/
4765          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
4766     /* Codecs */
4767         [preset setObject:@"MPEG-4 Video / AAC Audio" forKey:@"FileCodecs"];
4768         /* Video encoder */
4769         [preset setObject:@"FFmpeg" forKey:@"VideoEncoder"];
4770         /* x264 Option String */
4771         [preset setObject:@"" forKey:@"x264Option"];
4772         /* Video quality */
4773         [preset setObject:[NSNumber numberWithInt:1] forKey:@"VideoQualityType"];
4774         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
4775         [preset setObject:@"512" forKey:@"VideoAvgBitrate"];
4776         [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
4777         
4778         /* Video framerate */
4779         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4780         /* GrayScale */
4781         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4782         /* 2 Pass Encoding */
4783         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoTwoPass"];
4784         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoTurboTwoPass"];
4785         
4786         /*Picture Settings*/
4787         //hb_job_t * job = fTitle->job;
4788         /* Basic Picture Settings */
4789         /* Use Max Picture settings for whatever the dvd is.*/
4790         [preset setObject:[NSNumber numberWithInt:0] forKey:@"UsesMaxPictureSettings"];
4791         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4792         [preset setObject:[NSNumber numberWithInt:512] forKey:@"PictureWidth"];
4793         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
4794         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureKeepRatio"];
4795         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
4796         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PicturePAR"];
4797         /* Set crop settings here */
4798         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4799         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4800     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4801         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4802         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4803         
4804         /*Audio*/
4805         /* Audio Sample Rate*/
4806         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4807         /* Audio Bitrate Rate*/
4808         [preset setObject:@"128" forKey:@"AudioBitRate"];
4809         /* Subtitles*/
4810         [preset setObject:@"None" forKey:@"Subtitles"];
4811         
4812
4813     [preset autorelease];
4814     return preset;
4815
4816 }
4817
4818 - (NSDictionary *)createCRFPreset
4819 {
4820     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
4821         /* Get the New Preset Name from the field in the AddPresetPanel */
4822     [preset setObject:@"Constant Quality Rate" forKey:@"PresetName"];
4823         /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
4824         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Type"];
4825         /*Set whether or not this is default, at creation set to 0*/
4826         [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
4827         /*Get the whether or not to apply pic settings in the AddPresetPanel*/
4828         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesPictureSettings"];
4829         /* Get the New Preset Description from the field in the AddPresetPanel */
4830     [preset setObject:@"HandBrake's preset for consistently excellent quality in one pass, with the downside of entirely unpredictable file sizes and bitrates." forKey:@"PresetDescription"];
4831         /* File Format */
4832     [preset setObject:@"MKV file" forKey:@"FileFormat"];
4833         /* Chapter Markers*/
4834          [preset setObject:[NSNumber numberWithInt:1] forKey:@"ChapterMarkers"];
4835     /* Codecs */
4836         [preset setObject:@"AVC/H.264 Video / AC-3 Audio" forKey:@"FileCodecs"];
4837         /* Video encoder */
4838         [preset setObject:@"x264 (h.264 Main)" forKey:@"VideoEncoder"];
4839         /* x264 Option String */
4840         [preset setObject:@"ref=3:mixed-refs:bframes=3:b-pyramid:b-rdo:bime:weightb:filter=-2,-1:subme=6:trellis=1:analyse=all:8x8dct:me=umh" forKey:@"x264Option"];
4841         /* Video quality */
4842         [preset setObject:[NSNumber numberWithInt:2] forKey:@"VideoQualityType"];
4843         [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
4844         [preset setObject:@"2000" forKey:@"VideoAvgBitrate"];
4845         [preset setObject:[NSNumber numberWithFloat:0.6471] forKey:@"VideoQualitySlider"];
4846         
4847         /* Video framerate */
4848         [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
4849         /* GrayScale */
4850         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoGrayScale"];
4851         /* 2 Pass Encoding */
4852         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoTwoPass"];
4853         [preset setObject:[NSNumber numberWithInt:0] forKey:@"VideoTurboTwoPass"];
4854         
4855         /*Picture Settings*/
4856         //hb_job_t * job = fTitle->job;
4857         /* Basic Picture Settings */
4858         /* Use Max Picture settings for whatever the dvd is.*/
4859         [preset setObject:[NSNumber numberWithInt:1] forKey:@"UsesMaxPictureSettings"];
4860         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PictureAutoCrop"];
4861         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureWidth"];
4862         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureHeight"];
4863         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureKeepRatio"];
4864         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureDeinterlace"];
4865         [preset setObject:[NSNumber numberWithInt:1] forKey:@"PicturePAR"];
4866         /* Set crop settings here */
4867         /* The Auto Crop Matrix in the Picture Window autodetects differences in crop settings */
4868         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureTopCrop"];
4869     [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureBottomCrop"];
4870         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureLeftCrop"];
4871         [preset setObject:[NSNumber numberWithInt:0] forKey:@"PictureRightCrop"];
4872         
4873         /*Audio*/
4874         /* Audio Sample Rate*/
4875         [preset setObject:@"48" forKey:@"AudioSampleRate"];
4876         /* Audio Bitrate Rate*/
4877         [preset setObject:@"160" forKey:@"AudioBitRate"];
4878         /* Subtitles*/
4879         [preset setObject:@"None" forKey:@"Subtitles"];
4880         
4881
4882     [preset autorelease];
4883     return preset;
4884
4885 }
4886
4887
4888
4889
4890
4891 @end