OSDN Git Service

MacGui: Acivity Logs for individual encodes initial implementation
[handbrake-jp/handbrake-jp-git.git] / macosx / Controller.mm
index ba99155..5901249 100644 (file)
@@ -1,48 +1,16 @@
 /* $Id: Controller.mm,v 1.79 2005/11/04 19:41:32 titer Exp $
 
    This file is part of the HandBrake source code.
-   Homepage: <http://handbrake.m0k.org/>.
+   Homepage: <http://handbrake.fr/>.
    It may be used under the terms of the GNU General Public License. */
 
-#include "Controller.h"
-#include "a52dec/a52.h"
+#import "Controller.h"
 #import "HBOutputPanelController.h"
 #import "HBPreferencesController.h"
-/* Added to integrate scanning into HBController */
-#include <IOKit/IOKitLib.h>
-#include <IOKit/storage/IOMedia.h>
-#include <IOKit/storage/IODVDMedia.h>
-#include "HBDVDDetector.h"
-#include "dvdread/dvd_reader.h"
-#include "HBPresets.h"
-
-#define _(a) NSLocalizedString(a,NULL)
-
-static int FormatSettings[4][10] =
-  { { HB_MUX_MP4 | HB_VCODEC_FFMPEG | HB_ACODEC_FAAC,
-         HB_MUX_MP4 | HB_VCODEC_X264   | HB_ACODEC_FAAC,
-      HB_MUX_MP4 | HB_VCODEC_X264   | HB_ACODEC_FAAC,
-      HB_MUX_MP4 | HB_VCODEC_X264   | HB_ACODEC_AC3,
-      0,
-         0 },
-    { HB_MUX_MKV | HB_VCODEC_FFMPEG | HB_ACODEC_FAAC,
-         HB_MUX_MKV | HB_VCODEC_FFMPEG | HB_ACODEC_AC3,
-         HB_MUX_MKV | HB_VCODEC_FFMPEG | HB_ACODEC_LAME,
-         HB_MUX_MKV | HB_VCODEC_FFMPEG | HB_ACODEC_VORBIS,
-         HB_MUX_MKV | HB_VCODEC_X264   | HB_ACODEC_FAAC,
-         HB_MUX_MKV | HB_VCODEC_X264   | HB_ACODEC_AC3,
-         HB_MUX_MKV | HB_VCODEC_X264   | HB_ACODEC_LAME,
-         HB_MUX_MKV | HB_VCODEC_X264   | HB_ACODEC_VORBIS,
-         0,
-         0 },
-    { HB_MUX_AVI | HB_VCODEC_FFMPEG | HB_ACODEC_LAME,
-         HB_MUX_AVI | HB_VCODEC_FFMPEG | HB_ACODEC_AC3,
-         HB_MUX_AVI | HB_VCODEC_X264   | HB_ACODEC_LAME,
-         HB_MUX_AVI | HB_VCODEC_X264   | HB_ACODEC_AC3},
-    { HB_MUX_OGM | HB_VCODEC_FFMPEG | HB_ACODEC_VORBIS,
-         HB_MUX_OGM | HB_VCODEC_FFMPEG | HB_ACODEC_LAME,
-         0,
-         0 } };
+#import "HBDVDDetector.h"
+#import "HBPresets.h"
+
+#define DragDropSimplePboardType       @"MyCustomOutlineViewPboardType"
 
 /* We setup the toolbar values here */
 static NSString *        ToggleDrawerIdentifier             = @"Toggle Drawer Item Identifier";
@@ -59,26 +27,31 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
  *******************************/
 @implementation HBController
 
-- init
+- (id)init
 {
     self = [super init];
+    if( !self )
+    {
+        return nil;
+    }
+
     [HBPreferencesController registerUserDefaults];
     fHandle = NULL;
+    fQueueEncodeLibhb = NULL;
     /* Check for check for the app support directory here as
-        * outputPanel needs it right away, as may other future methods
-        */
-    /* We declare the default NSFileManager into fileManager */
-       NSFileManager * fileManager = [NSFileManager defaultManager];
-       /* we set the files and support paths here */
-       AppSupportDirectory = @"~/Library/Application Support/HandBrake";
-    AppSupportDirectory = [AppSupportDirectory stringByExpandingTildeInPath];
-    /* We check for the app support directory for handbrake */
-       if ([fileManager fileExistsAtPath:AppSupportDirectory] == 0) 
-       {
-               // If it doesnt exist yet, we create it here 
-               [fileManager createDirectoryAtPath:AppSupportDirectory attributes:nil];
-       }
-    
+     * outputPanel needs it right away, as may other future methods
+     */
+    NSString *libraryDir = [NSSearchPathForDirectoriesInDomains( NSLibraryDirectory,
+                                                                 NSUserDomainMask,
+                                                                 YES ) objectAtIndex:0];
+    AppSupportDirectory = [[libraryDir stringByAppendingPathComponent:@"Application Support"]
+                                       stringByAppendingPathComponent:@"HandBrake"];
+    if( ![[NSFileManager defaultManager] fileExistsAtPath:AppSupportDirectory] )
+    {
+        [[NSFileManager defaultManager] createDirectoryAtPath:AppSupportDirectory
+                                                   attributes:nil];
+    }
+
     outputPanel = [[HBOutputPanelController alloc] init];
     fPictureController = [[PictureController alloc] initWithDelegate:self];
     fQueueController = [[HBQueueController alloc] init];
@@ -89,70 +62,134 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     */
     fPresetsBuiltin = [[HBPresets alloc] init];
     fPreferencesController = [[HBPreferencesController alloc] init];
+    /* Lets report the HandBrake version number here to the activity log and text log file */
+    NSString *versionStringFull = [[NSString stringWithFormat: @"Handbrake Version: %@", [[[NSBundle mainBundle] infoDictionary] objectForKey:@"CFBundleGetInfoString"]] stringByAppendingString: [NSString stringWithFormat: @" (%@)", [[[NSBundle mainBundle] infoDictionary] objectForKey:@"CFBundleVersion"]]];
+    [self writeToActivityLog: "%s", [versionStringFull UTF8String]];    
+    
     return self;
 }
 
 
 - (void) applicationDidFinishLaunching: (NSNotification *) notification
 {
-    /* Variables from legacy update system, leave but commented out until Sparkle is compeletely vetted */
-    //int    build;
-    //char * version;
-    
-    // Init libhb
-       /* Old update method using hb_init, commented out but code left for a few revs til new sparkle updater is vetted */
-    //fHandle = hb_init(debugLevel, [[NSUserDefaults standardUserDefaults] boolForKey:@"CheckForUpdates"]);
-    /* New Init libhb with check for updates libhb style set to "0" so its ignored and lets sparkle take care of it */
-    fHandle = hb_init(HB_DEBUG_ALL, 0);
+    /* Init libhb with check for updates libhb style set to "0" so its ignored and lets sparkle take care of it */
+    int loggingLevel = [[[NSUserDefaults standardUserDefaults] objectForKey:@"LoggingLevel"] intValue];
+    fHandle = hb_init(loggingLevel, 0);
+    /* Init a separate instance of libhb for user scanning and setting up jobs */
+    fQueueEncodeLibhb = hb_init(loggingLevel, 0);
     
        // Set the Growl Delegate
-    [GrowlApplicationBridge setGrowlDelegate: self];    
+    [GrowlApplicationBridge setGrowlDelegate: self];
     /* Init others controllers */
     [fPictureController SetHandle: fHandle];
-    [fQueueController   setHandle: fHandle];
+    [fQueueController   setHandle: fQueueEncodeLibhb];
     [fQueueController   setHBController: self];
-       
+
     fChapterTitlesDelegate = [[ChapterTitles alloc] init];
     [fChapterTable setDataSource:fChapterTitlesDelegate];
-    
+    [fChapterTable setDelegate:fChapterTitlesDelegate];
+
     /* Call UpdateUI every 1/2 sec */
-    [[NSRunLoop currentRunLoop] addTimer: [NSTimer
-                                           scheduledTimerWithTimeInterval: 0.5 target: self
-                                           selector: @selector( updateUI: ) userInfo: NULL repeats: YES]
-                                 forMode: NSEventTrackingRunLoopMode];
-    
+    [[NSRunLoop currentRunLoop] addTimer:[NSTimer
+                                          scheduledTimerWithTimeInterval:0.5 target:self
+                                          selector:@selector(updateUI:) userInfo:nil repeats:YES]
+                                 forMode:NSEventTrackingRunLoopMode];
+
     // Open debug output window now if it was visible when HB was closed
     if ([[NSUserDefaults standardUserDefaults] boolForKey:@"OutputPanelIsOpen"])
         [self showDebugOutputPanel:nil];
-    
+
     // Open queue window now if it was visible when HB was closed
     if ([[NSUserDefaults standardUserDefaults] boolForKey:@"QueueWindowIsOpen"])
         [self showQueueWindow:nil];
-    
+
        [self openMainWindow:nil];
     
-    /* Show Browse Sources Window ASAP */
-    [self performSelectorOnMainThread: @selector(browseSources:)
-                           withObject: NULL waitUntilDone: NO];
+    /* We have to set the bool to tell hb what to do after a scan
+     * Initially we set it to NO until we start processing the queue
+     */
+     applyQueueToScan = NO;
+    
+    /* Now we re-check the queue array to see if there are
+     * any remaining encodes to be done in it and ask the
+     * user if they want to reload the queue */
+    if ([QueueFileArray count] > 0)
+       {
+        /* run  getQueueStats to see whats in the queue file */
+        [self getQueueStats];
+        /* this results in these values
+         * fEncodingQueueItem = 0;
+         * fPendingCount = 0;
+         * fCompletedCount = 0;
+         * fCanceledCount = 0;
+         * fWorkingCount = 0;
+         */
+        
+        /*On Screen Notification*/
+        NSString * alertTitle;
+        if (fWorkingCount > 0)
+        {
+            alertTitle = [NSString stringWithFormat:
+                         NSLocalizedString(@"HandBrake Has Detected %d Previously Encoding Item and %d Pending Item(s) In Your Queue.", @""),
+                         fWorkingCount,fPendingCount];
+        }
+        else
+        {
+            alertTitle = [NSString stringWithFormat:
+                         NSLocalizedString(@"HandBrake Has Detected %d Pending Item(s) In Your Queue.", @""),
+                         fPendingCount];
+        }
+        NSBeginCriticalAlertSheet(
+                                  alertTitle,
+                                  NSLocalizedString(@"Reload Queue", nil),
+                                  nil,
+                                  NSLocalizedString(@"Empty Queue", nil),
+                                  fWindow, self,
+                                  nil, @selector(didDimissReloadQueue:returnCode:contextInfo:), nil,
+                                  NSLocalizedString(@" Do you want to reload them ?", nil));
+        // call didDimissReloadQueue: (NSWindow *)sheet returnCode: (int)returnCode contextInfo: (void *)contextInfo
+        // right below to either clear the old queue or keep it loaded up.
+    }
+    else
+    {
+        
+        /* Show Browse Sources Window ASAP */
+        [self performSelectorOnMainThread:@selector(browseSources:)
+                               withObject:nil waitUntilDone:NO];
+    }
+}
+
+- (void) didDimissReloadQueue: (NSWindow *)sheet returnCode: (int)returnCode contextInfo: (void *)contextInfo
+{
+    if (returnCode == NSAlertOtherReturn)
+    {
+        [self clearQueueAllItems];
+        [self performSelectorOnMainThread:@selector(browseSources:)
+                           withObject:nil waitUntilDone:NO];
+    }
+    else
+    {
+    [self setQueueEncodingItemsAsPending];
+    [self showQueueWindow:NULL];
+    }
 }
 
 - (NSApplicationTerminateReply) applicationShouldTerminate: (NSApplication *) app
 {
+    
     // Warn if encoding a movie
     hb_state_t s;
-    hb_get_state( fHandle, &s );
-    HBJobGroup * jobGroup = [fQueueController currentJobGroup];
-    if ( jobGroup && ( s.state != HB_STATE_IDLE ) )
+    hb_get_state( fQueueEncodeLibhb, &s );
+    
+    if ( s.state != HB_STATE_IDLE )
     {
         int result = NSRunCriticalAlertPanel(
-                NSLocalizedString(@"Are you sure you want to quit HandBrake?", nil),
-                NSLocalizedString(@"%@ is currently encoding. If you quit HandBrake, your movie will be lost. Do you want to quit anyway?", nil),
-                NSLocalizedString(@"Quit", nil), NSLocalizedString(@"Don't Quit", nil), nil,
-                jobGroup ? [jobGroup name] : @"A movie" );
+                                             NSLocalizedString(@"Are you sure you want to quit HandBrake?", nil),
+                                             NSLocalizedString(@"If you quit HandBrake your current encode will be reloaded into your queue at next launch. Do you want to quit anyway?", nil),
+                                             NSLocalizedString(@"Quit", nil), NSLocalizedString(@"Don't Quit", nil), nil, @"A movie" );
         
         if (result == NSAlertDefaultReturn)
         {
-            [self doCancelCurrentJob];
             return NSTerminateNow;
         }
         else
@@ -160,12 +197,12 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     }
     
     // Warn if items still in the queue
-    else if ( hb_count( fHandle ) > 0 )
+    else if ( fPendingCount > 0 )
     {
         int result = NSRunCriticalAlertPanel(
-                NSLocalizedString(@"Are you sure you want to quit HandBrake?", nil),
-                NSLocalizedString(@"One or more encodes are queued for encoding. Do you want to quit anyway?", nil),
-                NSLocalizedString(@"Quit", nil), NSLocalizedString(@"Don't Quit", nil), nil);
+                                             NSLocalizedString(@"Are you sure you want to quit HandBrake?", nil),
+                                             NSLocalizedString(@"There are pending encodes in your queue. Do you want to quit anyway?",nil),
+                                             NSLocalizedString(@"Quit", nil), NSLocalizedString(@"Don't Quit", nil), nil);
         
         if ( result == NSAlertDefaultReturn )
             return NSTerminateNow;
@@ -182,6 +219,7 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     [outputPanel release];
        [fQueueController release];
        hb_close(&fHandle);
+    hb_close(&fQueueEncodeLibhb);
 }
 
 
@@ -191,15 +229,24 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     [fWindow setExcludedFromWindowsMenu:YES];
     [fAdvancedOptions setView:fAdvancedView];
 
+    /* lets setup our presets drawer for drag and drop here */
+    [fPresetsOutlineView registerForDraggedTypes: [NSArray arrayWithObject:DragDropSimplePboardType] ];
+    [fPresetsOutlineView setDraggingSourceOperationMask:NSDragOperationEvery forLocal:YES];
+    [fPresetsOutlineView setVerticalMotionCanBeginDrag: YES];
+
     /* Initialize currentScanCount so HB can use it to
                evaluate successive scans */
        currentScanCount = 0;
-       
+
+
     /* Init UserPresets .plist */
        [self loadPresets];
-               
-       fRipIndicatorShown = NO;  // initially out of view in the nib
+    
+    /* Init QueueFile .plist */
+    [self loadQueueFile];
        
+    fRipIndicatorShown = NO;  // initially out of view in the nib
+
        /* Show/Dont Show Presets drawer upon launch based
                on user preference DefaultPresetsDrawerShow*/
        if ([[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultPresetsDrawerShow"] > 0)
@@ -208,46 +255,56 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
        }
        
        
+    
     /* Destination box*/
+    NSMenuItem *menuItem;
     [fDstFormatPopUp removeAllItems];
-    [fDstFormatPopUp addItemWithTitle: _( @"MP4 file" )];
-       [fDstFormatPopUp addItemWithTitle: _( @"MKV file" )];
-    [fDstFormatPopUp addItemWithTitle: _( @"AVI file" )];
-    [fDstFormatPopUp addItemWithTitle: _( @"OGM file" )];
+    // MP4 file
+    menuItem = [[fDstFormatPopUp menu] addItemWithTitle:@"MP4 file" action: NULL keyEquivalent: @""];
+    [menuItem setTag: HB_MUX_MP4];
+       // MKV file
+    menuItem = [[fDstFormatPopUp menu] addItemWithTitle:@"MKV file" action: NULL keyEquivalent: @""];
+    [menuItem setTag: HB_MUX_MKV];
+    // AVI file
+    menuItem = [[fDstFormatPopUp menu] addItemWithTitle:@"AVI file" action: NULL keyEquivalent: @""];
+    [menuItem setTag: HB_MUX_AVI];
+    // OGM file
+    menuItem = [[fDstFormatPopUp menu] addItemWithTitle:@"OGM file" action: NULL keyEquivalent: @""];
+    [menuItem setTag: HB_MUX_OGM];
     [fDstFormatPopUp selectItemAtIndex: 0];
-       
-    [self formatPopUpChanged: NULL];
-    
-       /* We enable the create chapters checkbox here since we are .mp4 */     
+
+    [self formatPopUpChanged:nil];
+
+       /* We enable the create chapters checkbox here since we are .mp4 */
        [fCreateChapterMarkers setEnabled: YES];
        if ([fDstFormatPopUp indexOfSelectedItem] == 0 && [[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultChapterMarkers"] > 0)
        {
                [fCreateChapterMarkers setState: NSOnState];
        }
-       
-       
-       
-       
+
+
+
+
     [fDstFile2Field setStringValue: [NSString stringWithFormat:
         @"%@/Desktop/Movie.mp4", NSHomeDirectory()]];
-       
+
     /* Video encoder */
     [fVidEncoderPopUp removeAllItems];
     [fVidEncoderPopUp addItemWithTitle: @"FFmpeg"];
     [fVidEncoderPopUp addItemWithTitle: @"XviD"];
-       
-    
-       
+
+
+
     /* Video quality */
     [fVidTargetSizeField setIntValue: 700];
        [fVidBitrateField    setIntValue: 1000];
-       
+
     [fVidQualityMatrix   selectCell: fVidBitrateCell];
-    [self videoMatrixChanged: NULL];
-       
+    [self videoMatrixChanged:nil];
+
     /* Video framerate */
     [fVidRatePopUp removeAllItems];
-       [fVidRatePopUp addItemWithTitle: _( @"Same as source" )];
+       [fVidRatePopUp addItemWithTitle: NSLocalizedString( @"Same as source", @"" )];
     for( int i = 0; i < hb_video_rates_count; i++ )
     {
         if ([[NSString stringWithCString: hb_video_rates[i].string] isEqualToString: [NSString stringWithFormat: @"%.3f",23.976]])
@@ -277,84 +334,69 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     [fPictureController setAutoCrop:YES];
        
        /* Audio bitrate */
-    [fAudBitratePopUp removeAllItems];
+    [fAudTrack1BitratePopUp removeAllItems];
     for( int i = 0; i < hb_audio_bitrates_count; i++ )
     {
-        [fAudBitratePopUp addItemWithTitle:
+        [fAudTrack1BitratePopUp addItemWithTitle:
                                [NSString stringWithCString: hb_audio_bitrates[i].string]];
 
     }
-    [fAudBitratePopUp selectItemAtIndex: hb_audio_bitrates_default];
+    [fAudTrack1BitratePopUp selectItemAtIndex: hb_audio_bitrates_default];
        
     /* Audio samplerate */
-    [fAudRatePopUp removeAllItems];
+    [fAudTrack1RatePopUp removeAllItems];
     for( int i = 0; i < hb_audio_rates_count; i++ )
     {
-        [fAudRatePopUp addItemWithTitle:
+        [fAudTrack1RatePopUp addItemWithTitle:
             [NSString stringWithCString: hb_audio_rates[i].string]];
     }
-    [fAudRatePopUp selectItemAtIndex: hb_audio_rates_default];
+    [fAudTrack1RatePopUp selectItemAtIndex: hb_audio_rates_default];
        
     /* Bottom */
     [fStatusField setStringValue: @""];
-       
+
     [self enableUI: NO];
        [self setupToolbar];
-       
-       [fPresetsActionButton setMenu:fPresetsActionMenu];
-       
+
        /* We disable the Turbo 1st pass checkbox since we are not x264 */
        [fVidTurboPassCheck setEnabled: NO];
        [fVidTurboPassCheck setState: NSOffState];
-       
-       
+
+
        /* lets get our default prefs here */
-       [self getDefaultPresets: NULL];
+       [self getDefaultPresets:nil];
        /* lets initialize the current successful scancount here to 0 */
        currentSuccessfulScanCount = 0;
-    
-}
 
-- (void) TranslateStrings
-{
-    [fSrcTitleField     setStringValue: _( @"Title:" )];
-    [fSrcChapterField   setStringValue: _( @"Chapters:" )];
-    [fSrcChapterToField setStringValue: _( @"to" )];
-    [fSrcDuration1Field setStringValue: _( @"Duration:" )];
-
-    [fDstFormatField    setStringValue: _( @"Format:" )];
-    [fDstCodecsField    setStringValue: _( @"Codecs:" )];
-    [fDstFile1Field     setStringValue: _( @"File:" )];
-    [fDstBrowseButton   setTitle:       _( @"Browse" )];
 
-    [fVidRateField      setStringValue: _( @"Framerate (fps):" )];
-    [fVidEncoderField   setStringValue: _( @"Encoder:" )];
-    [fVidQualityField   setStringValue: _( @"Quality:" )];
 }
 
-
 - (void) enableUI: (bool) b
 {
     NSControl * controls[] =
       { fSrcTitleField, fSrcTitlePopUp,
         fSrcChapterField, fSrcChapterStartPopUp, fSrcChapterToField,
         fSrcChapterEndPopUp, fSrcDuration1Field, fSrcDuration2Field,
-        fDstFormatField, fDstFormatPopUp, fDstCodecsField,
-        fDstCodecsPopUp, fDstFile1Field, fDstFile2Field,
+        fDstFormatField, fDstFormatPopUp, fDstFile1Field, fDstFile2Field,
         fDstBrowseButton, fVidRateField, fVidRatePopUp,
         fVidEncoderField, fVidEncoderPopUp, fVidQualityField,
         fVidQualityMatrix, fVidGrayscaleCheck, fSubField, fSubPopUp,
-        fAudLang1Field, fAudLang1PopUp, fAudLang2Field, fAudLang2PopUp,
-        fAudTrack1MixLabel, fAudTrack1MixPopUp, fAudTrack2MixLabel, fAudTrack2MixPopUp,
-        fAudRateField, fAudRatePopUp, fAudBitrateField,
-        fAudBitratePopUp, fPictureButton,fQueueStatus,fPicSettingARkeep,
-               fPicSettingDeinterlace,fPicLabelSettings,fPicLabelSrc,fPicLabelOutp,fPicSettingsSrc,fPicSettingsOutp,fPicSettingsAnamorphic,
+        fAudSourceLabel, fAudCodecLabel, fAudMixdownLabel, fAudSamplerateLabel, fAudBitrateLabel,
+        fAudTrack1Label, fAudTrack2Label, fAudTrack3Label, fAudTrack4Label,
+        fAudLang1PopUp, fAudLang2PopUp, fAudLang3PopUp, fAudLang4PopUp,
+        fAudTrack1CodecPopUp, fAudTrack2CodecPopUp, fAudTrack3CodecPopUp, fAudTrack4CodecPopUp,
+        fAudTrack1MixPopUp, fAudTrack2MixPopUp, fAudTrack3MixPopUp, fAudTrack4MixPopUp,
+        fAudTrack1RatePopUp, fAudTrack2RatePopUp, fAudTrack3RatePopUp, fAudTrack4RatePopUp,
+        fAudTrack1BitratePopUp, fAudTrack2BitratePopUp, fAudTrack3BitratePopUp, fAudTrack4BitratePopUp,
+        fAudDrcLabel, fAudTrack1DrcSlider, fAudTrack1DrcField, fAudTrack2DrcSlider,
+        fAudTrack2DrcField, fAudTrack3DrcSlider, fAudTrack3DrcField, fAudTrack4DrcSlider,fAudTrack4DrcField,
+        fPictureButton,fQueueStatus,fPicSettingARkeep, fPicSettingDeinterlace,fPicLabelSettings,fPicLabelSrc,
+        fPicLabelOutp,fPicSettingsSrc,fPicSettingsOutp,fPicSettingsAnamorphic,
                fPicLabelAr,fPicLabelDeinterlace,fPicSettingPAR,fPicLabelAnamorphic,fPresetsAdd,fPresetsDelete,
                fCreateChapterMarkers,fVidTurboPassCheck,fDstMp4LargeFileCheck,fPicLabelAutoCrop,
                fPicSettingAutoCrop,fPicSettingDetelecine,fPicLabelDetelecine,fPicLabelDenoise,fPicSettingDenoise,
-        fSubForcedCheck,fPicSettingDeblock,fPicLabelDeblock,fPresetsOutlineView,fAudDrcSlider,
-        fAudDrcField,fAudDrcLabel,fDstMp4HttpOptFileCheck,fAudDrcDescLabel1,fAudDrcDescLabel2,fAudDrcDescLabel3,
-        fAudDrcDescLabel4,fDstMp4iPodFileCheck};
+        fSubForcedCheck,fPicSettingDeblock,fPicLabelDeblock,fPicLabelDecomb,fPicSettingDecomb,fPresetsOutlineView,
+        fAudDrcLabel,fDstMp4HttpOptFileCheck,fDstMp4iPodFileCheck};
 
     for( unsigned i = 0;
          i < sizeof( controls ) / sizeof( NSControl * ); i++ )
@@ -372,22 +414,23 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
         [controls[i] setEnabled: b];
 
     }
-       
+
        if (b) {
 
         /* if we're enabling the interface, check if the audio mixdown controls need to be enabled or not */
         /* these will have been enabled by the mass control enablement above anyway, so we're sense-checking it here */
-        [self setEnabledStateOfAudioMixdownControls: NULL];
+        [self setEnabledStateOfAudioMixdownControls:nil];
         /* we also call calculatePictureSizing here to sense check if we already have vfr selected */
-        [self calculatePictureSizing: NULL];
-       
+        [self calculatePictureSizing:nil];
+        [self shouldEnableHttpMp4CheckBox: nil];
+
        } else {
 
                [fPresetsOutlineView setEnabled: NO];
-       
+
        }
 
-    [self videoMatrixChanged: NULL];
+    [self videoMatrixChanged:nil];
     [fAdvancedOptions enableUI:b];
 }
 
@@ -478,252 +521,302 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
 
 - (void) updateUI: (NSTimer *) timer
 {
-
+    
+    /* Update UI for fHandle (user scanning instance of libhb ) */
+    
     hb_list_t  * list;
-    list = hb_get_titles( fHandle );   
+    list = hb_get_titles( fHandle );
     /* check to see if there has been a new scan done
-       this bypasses the constraints of HB_STATE_WORKING
-       not allowing setting a newly scanned source */
+     this bypasses the constraints of HB_STATE_WORKING
+     not allowing setting a newly scanned source */
        int checkScanCount = hb_get_scancount( fHandle );
-       if (checkScanCount > currentScanCount)
+       if( checkScanCount > currentScanCount )
        {
-               
                currentScanCount = checkScanCount;
         [fScanIndicator setIndeterminate: NO];
         [fScanIndicator setDoubleValue: 0.0];
         [fScanIndicator setHidden: YES];
-               [self showNewScan: NULL];
+               [self showNewScan:nil];
        }
-       
+    
     hb_state_t s;
     hb_get_state( fHandle, &s );
-       
-       
+    
     switch( s.state )
     {
         case HB_STATE_IDLE:
-               break;
-#define p s.param.scanning                     
+            break;
+#define p s.param.scanning
         case HB_STATE_SCANNING:
                {
             [fSrcDVD2Field setStringValue: [NSString stringWithFormat:
-                                            _( @"Scanning title %d of %d..." ),
+                                            NSLocalizedString( @"Scanning title %d of %d...", @"" ),
                                             p.title_cur, p.title_count]];
             [fScanIndicator setHidden: NO];
             [fScanIndicator setDoubleValue: 100.0 * ( p.title_cur - 1 ) / p.title_count];
             break;
                }
 #undef p
-       
+            
 #define p s.param.scandone
         case HB_STATE_SCANDONE:
         {
             [fScanIndicator setIndeterminate: NO];
             [fScanIndicator setDoubleValue: 0.0];
             [fScanIndicator setHidden: YES];
-                       [self showNewScan: NULL];
-            [toolbar validateVisibleItems];
+                       [self writeToActivityLog:"ScanDone state received from fHandle"];
+            [self showNewScan:nil];
+            [[fWindow toolbar] validateVisibleItems];
+            
+                       break;
+        }
+#undef p
+            
+#define p s.param.working
+        case HB_STATE_WORKING:
+        {
+            
+            break;
+        }
+#undef p
+            
+#define p s.param.muxing
+        case HB_STATE_MUXING:
+        {
+            
+            break;
+        }
+#undef p
+            
+        case HB_STATE_PAUSED:
+            break;
+            
+        case HB_STATE_WORKDONE:
+        {
+            break;
+        }
+    }
+    
+    
+    /* Update UI for fQueueEncodeLibhb */
+    // hb_list_t  * list;
+    // list = hb_get_titles( fQueueEncodeLibhb ); //fQueueEncodeLibhb
+    /* check to see if there has been a new scan done
+     this bypasses the constraints of HB_STATE_WORKING
+     not allowing setting a newly scanned source */
+       
+    checkScanCount = hb_get_scancount( fQueueEncodeLibhb );
+       if( checkScanCount > currentScanCount )
+       {
+               currentScanCount = checkScanCount;
+        [self writeToActivityLog:"currentScanCount received from fQueueEncodeLibhb"];
+       }
+    
+    //hb_state_t s;
+    hb_get_state( fQueueEncodeLibhb, &s );
+    
+    switch( s.state )
+    {
+        case HB_STATE_IDLE:
+            break;
+#define p s.param.scanning
+        case HB_STATE_SCANNING:
+               {
+            [fStatusField setStringValue: [NSString stringWithFormat:
+                                           NSLocalizedString( @"Queue Scanning title %d of %d...", @"" ),
+                                           p.title_cur, p.title_count]];
+            
+            /* Set the status string in fQueueController as well */                               
+            [fQueueController setQueueStatusString: [NSString stringWithFormat:
+                                                     NSLocalizedString( @"Queue Scanning title %d of %d...", @"" ),
+                                                     p.title_cur, p.title_count]];
+            
+            [fRipIndicator setHidden: NO];
+            [fRipIndicator setDoubleValue: 100.0 * ( p.title_cur - 1 ) / p.title_count];
+            break;
+               }
+#undef p
+            
+#define p s.param.scandone
+        case HB_STATE_SCANDONE:
+        {
+            [fRipIndicator setIndeterminate: NO];
+            [fRipIndicator setDoubleValue: 0.0];
+            
+                       [self writeToActivityLog:"ScanDone state received from fQueueEncodeLibhb"];
+            [self processNewQueueEncode];
+            [[fWindow toolbar] validateVisibleItems];
+            
                        break;
         }
 #undef p
-                       
+            
 #define p s.param.working
         case HB_STATE_WORKING:
         {
             float progress_total;
             NSMutableString * string;
-                       /* Currently, p.job_cur and p.job_count get screwed up when adding
-                               jobs during encoding, if they cannot be fixed in libhb, will implement a
-                               nasty but working cocoa solution */
                        /* Update text field */
-                       string = [NSMutableString stringWithFormat: _( @"Encoding: task %d of %d, %.2f %%" ), p.job_cur, p.job_count, 100.0 * p.progress];
+                       string = [NSMutableString stringWithFormat: NSLocalizedString( @"Encoding: pass %d of %d, %.2f %%", @"" ), p.job_cur, p.job_count, 100.0 * p.progress];
             
                        if( p.seconds > -1 )
             {
                 [string appendFormat:
-                    _( @" (%.2f fps, avg %.2f fps, ETA %02dh%02dm%02ds)" ),
-                    p.rate_cur, p.rate_avg, p.hours, p.minutes, p.seconds];
+                 NSLocalizedString( @" (%.2f fps, avg %.2f fps, ETA %02dh%02dm%02ds)", @"" ),
+                 p.rate_cur, p.rate_avg, p.hours, p.minutes, p.seconds];
             }
+            
             [fStatusField setStringValue: string];
-                       
+            /* Set the status string in fQueueController as well */
+            [fQueueController setQueueStatusString: string];
             /* Update slider */
                        progress_total = ( p.progress + p.job_cur - 1 ) / p.job_count;
             [fRipIndicator setIndeterminate: NO];
             [fRipIndicator setDoubleValue: 100.0 * progress_total];
-                       
+            
             // If progress bar hasn't been revealed at the bottom of the window, do
             // that now. This code used to be in doRip. I moved it to here to handle
             // the case where hb_start is called by HBQueueController and not from
             // HBController.
-            if (!fRipIndicatorShown)
+            if( !fRipIndicatorShown )
             {
                 NSRect frame = [fWindow frame];
-                if (frame.size.width <= 591)
+                if( frame.size.width <= 591 )
                     frame.size.width = 591;
                 frame.size.height += 36;
                 frame.origin.y -= 36;
                 [fWindow setFrame:frame display:YES animate:YES];
                 fRipIndicatorShown = YES;
-                /* We check to see if we need to warn the user that the computer will go to sleep
-                   or shut down when encoding is finished */
-                [self remindUserOfSleepOrShutdown];
+                
             }
-
+            
             /* Update dock icon */
             [self UpdateDockIcon: progress_total];
-                       
-            // Has current job changed? That means the queue has probably changed as
-                       // well so update it
-            [fQueueController libhbStateChanged: s];
             
             break;
         }
 #undef p
-                       
+            
 #define p s.param.muxing
         case HB_STATE_MUXING:
         {
-            NSMutableString * string;
-                       
             /* Update text field */
-            string = [NSMutableString stringWithFormat:
-                _( @"Muxing..." )];
-            [fStatusField setStringValue: string];
-                       
+            [fStatusField setStringValue: NSLocalizedString( @"Muxing...", @"" )];
+            /* Set the status string in fQueueController as well */
+            [fQueueController setQueueStatusString: NSLocalizedString( @"Muxing...", @"" )];
             /* Update slider */
             [fRipIndicator setIndeterminate: YES];
             [fRipIndicator startAnimation: nil];
-                       
+            
             /* Update dock icon */
             [self UpdateDockIcon: 1.0];
-                       
-                       // Pass along the info to HBQueueController
-            [fQueueController libhbStateChanged: s];
-                       
-            break;
+            
+                       break;
         }
 #undef p
-                       
+            
         case HB_STATE_PAUSED:
-                   [fStatusField setStringValue: _( @"Paused" )];
+                   [fStatusField setStringValue: NSLocalizedString( @"Paused", @"" )];
+            [fQueueController setQueueStatusString: NSLocalizedString( @"Paused", @"" )];
+            
+                       break;
             
-                       // Pass along the info to HBQueueController
-            [fQueueController libhbStateChanged: s];
-
-            break;
-                       
         case HB_STATE_WORKDONE:
         {
             // HB_STATE_WORKDONE happpens as a result of libhb finishing all its jobs
             // or someone calling hb_stop. In the latter case, hb_stop does not clear
             // out the remaining passes/jobs in the queue. We'll do that here.
-                        
+            
             // Delete all remaining jobs of this encode.
-            hb_job_t * job;
-            while( ( job = hb_job( fHandle, 0 ) ) && ( !IsFirstPass(job->sequence_id) ) )
-                hb_rem( fHandle, job );
-
-            [fStatusField setStringValue: _( @"Done." )];
+            [fStatusField setStringValue: NSLocalizedString( @"Encode Finished.", @"" )];
+            /* Set the status string in fQueueController as well */
+            [fQueueController setQueueStatusString: NSLocalizedString( @"Encode Finished.", @"" )];
             [fRipIndicator setIndeterminate: NO];
             [fRipIndicator setDoubleValue: 0.0];
-            [toolbar validateVisibleItems];
-
+            [[fWindow toolbar] validateVisibleItems];
+            
             /* Restore dock icon */
             [self UpdateDockIcon: -1.0];
-
-            if (fRipIndicatorShown)
+            
+            if( fRipIndicatorShown )
             {
                 NSRect frame = [fWindow frame];
-                if (frame.size.width <= 591)
+                if( frame.size.width <= 591 )
                                    frame.size.width = 591;
                 frame.size.height += -36;
                 frame.origin.y -= -36;
                 [fWindow setFrame:frame display:YES animate:YES];
                                fRipIndicatorShown = NO;
                        }
-                       
-                       // Pass along the info to HBQueueController
-            [fQueueController libhbStateChanged: s];
-                       
+            /* Since we are done with this encode, tell output to stop writing to the
+             * individual encode log
+             */
+                       [outputPanel endEncodeLog];
             /* Check to see if the encode state has not been cancelled
-                               to determine if we should check for encode done notifications */
-                       if (fEncodeState != 2)                  {
-                               /* If Growl Notification or Window and Growl has been selected */
-                               if ([[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Growl Notification"] || 
-                                       [[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Alert Window And Growl"])
-                {
-                                       /*Growl Notification*/
-                                       [self showGrowlDoneNotification: NULL];
-                }
-                /* If Alert Window or Window and Growl has been selected */
-                               if ([[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Alert Window"] || 
-                                       [[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Alert Window And Growl"])
-                {
-                                       /*On Screen Notification*/
-                                       int status;
-                                       NSBeep();
-                                       status = NSRunAlertPanel(@"Put down that cocktail...",@"Your HandBrake encode is done!", @"OK", nil, nil);
-                                       [NSApp requestUserAttention:NSCriticalRequest];
-                                       if ( status == NSAlertDefaultReturn ) 
-                                       {
-                                               [self enableUI: YES];
-                                       }
-                }
-                               else
-                               {
-                                       [self enableUI: YES];
-                               }
-                                  /* If sleep has been selected */ 
-            if ([[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Put Computer To Sleep"]) 
-                { 
-               /* Sleep */ 
-               NSDictionary* errorDict; 
-               NSAppleEventDescriptor* returnDescriptor = NULL; 
-               NSAppleScript* scriptObject = [[NSAppleScript alloc] initWithSource: 
-                        @"tell application \"Finder\" to sleep"]; 
-               returnDescriptor = [scriptObject executeAndReturnError: &errorDict]; 
-               [scriptObject release]; 
-               [self enableUI: YES]; 
-                } 
-            /* If Shutdown has been selected */ 
-            if ([[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Shut Down Computer"]) 
-                { 
-               /* Shut Down */ 
-               NSDictionary* errorDict; 
-               NSAppleEventDescriptor* returnDescriptor = NULL; 
-               NSAppleScript* scriptObject = [[NSAppleScript alloc] initWithSource: 
-                        @"tell application \"Finder\" to shut down"]; 
-               returnDescriptor = [scriptObject executeAndReturnError: &errorDict]; 
-               [scriptObject release]; 
-               [self enableUI: YES]; 
-                }
-                       
-                                               // MetaX insertion via AppleScript
-                       if([[NSUserDefaults standardUserDefaults] boolForKey: @"sendToMetaX"] == YES)
-                       {
-                       NSAppleScript *myScript = [[NSAppleScript alloc] initWithSource: [NSString stringWithFormat: @"%@%@%@", @"tell application \"MetaX\" to open (POSIX file \"", [fDstFile2Field stringValue], @"\")"]];
-                       [myScript executeAndReturnError: nil];
-                       [myScript release];
-                       }
-                       
-                       
-                       }
-                       else
-                       {
-                               [self enableUI: YES];
-                       }
+             to determine if we should check for encode done notifications */
+                       if( fEncodeState != 2 )
+            {
+                NSString *pathOfFinishedEncode;
+                /* Get the output file name for the finished encode */
+                pathOfFinishedEncode = [[QueueFileArray objectAtIndex:currentQueueEncodeIndex] objectForKey:@"DestinationPath"];
+                
+                /* Both the Growl Alert and Sending to MetaX can be done as encodes roll off the queue */
+                /* Growl alert */
+                [self showGrowlDoneNotification:pathOfFinishedEncode];
+                /* Send to MetaX */
+                [self sendToMetaX:pathOfFinishedEncode];
+                
+                /* since we have successfully completed an encode, we increment the queue counter */
+                [self incrementQueueItemDone:nil]; 
+                
+                /* all end of queue actions below need to be done after all queue encodes have finished 
+                 * and there are no pending jobs left to process
+                 */
+                if (fPendingCount == 0)
+                {
+                    /* If Alert Window or Window and Growl has been selected */
+                    if( [[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Alert Window"] ||
+                       [[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Alert Window And Growl"] )
+                    {
+                        /*On Screen Notification*/
+                        int status;
+                        NSBeep();
+                        status = NSRunAlertPanel(@"Put down that cocktail...",@"Your HandBrake queue is done!", @"OK", nil, nil);
+                        [NSApp requestUserAttention:NSCriticalRequest];
+                    }
+                    
+                    /* If sleep has been selected */
+                    if( [[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Put Computer To Sleep"] )
+                    {
+                        /* Sleep */
+                        NSDictionary* errorDict;
+                        NSAppleEventDescriptor* returnDescriptor = nil;
+                        NSAppleScript* scriptObject = [[NSAppleScript alloc] initWithSource:
+                                                       @"tell application \"Finder\" to sleep"];
+                        returnDescriptor = [scriptObject executeAndReturnError: &errorDict];
+                        [scriptObject release];
+                    }
+                    /* If Shutdown has been selected */
+                    if( [[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Shut Down Computer"] )
+                    {
+                        /* Shut Down */
+                        NSDictionary* errorDict;
+                        NSAppleEventDescriptor* returnDescriptor = nil;
+                        NSAppleScript* scriptObject = [[NSAppleScript alloc] initWithSource:
+                                                       @"tell application \"Finder\" to shut down"];
+                        returnDescriptor = [scriptObject executeAndReturnError: &errorDict];
+                        [scriptObject release];
+                    }
+                    
+                }
+                
+                
+            }
+            
             break;
         }
     }
-       
-    /* Lets show the queue status here in the main window */
-       int queue_count = [fQueueController pendingCount];
-       if( queue_count == 1)
-               [fQueueStatus setStringValue: _( @"1 encode queued") ];
-    else if (queue_count > 1)
-               [fQueueStatus setStringValue: [NSString stringWithFormat: _( @"%d encodes queued" ), queue_count]];
-       else
-               [fQueueStatus setStringValue: @""];
+    
 }
 
 /* We use this to write messages to stderr from the macgui which show up in the activity window and log*/
@@ -750,21 +843,21 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
 // ============================================================
 
 - (void) setupToolbar {
-    toolbar = [[[NSToolbar alloc] initWithIdentifier: @"HandBrake Toolbar"] autorelease];
-    
+    NSToolbar *toolbar = [[[NSToolbar alloc] initWithIdentifier: @"HandBrake Toolbar"] autorelease];
+
     [toolbar setAllowsUserCustomization: YES];
     [toolbar setAutosavesConfiguration: YES];
     [toolbar setDisplayMode: NSToolbarDisplayModeIconAndLabel];
-    
+
     [toolbar setDelegate: self];
-    
+
     [fWindow setToolbar: toolbar];
 }
 
 - (NSToolbarItem *) toolbar: (NSToolbar *)toolbar itemForItemIdentifier:
     (NSString *) itemIdent willBeInsertedIntoToolbar:(BOOL) willBeInserted {
-    NSToolbarItem * item = [[NSToolbarItem alloc] initWithItemIdentifier: itemIdent];
-    
+    NSToolbarItem * item = [[[NSToolbarItem alloc] initWithItemIdentifier: itemIdent] autorelease];
+
     if ([itemIdent isEqualToString: ToggleDrawerIdentifier])
     {
         [item setLabel: @"Toggle Presets"];
@@ -832,7 +925,6 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     }
     else
     {
-        [item release];
         return nil;
     }
 
@@ -861,7 +953,7 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     if (fHandle)
     {
         hb_state_t s;
-        hb_get_state2( fHandle, &s );
+        hb_get_state2( fQueueEncodeLibhb, &s );
         
         if (s.state == HB_STATE_WORKING || s.state == HB_STATE_MUXING)
         {
@@ -920,7 +1012,9 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
         }
 
     }
-    
+    /* If there are any pending queue items, make sure the start/stop button is active */
+    if ([ident isEqualToString: StartEncodingIdentifier] && fPendingCount > 0)
+        return YES;
     if ([ident isEqualToString: ShowQueueIdentifier])
         return YES;
     if ([ident isEqualToString: ToggleDrawerIdentifier])
@@ -972,6 +1066,7 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
                 return NO;
         }
         if (action == @selector(Rip:))
+        {
             if (s.state == HB_STATE_WORKING || s.state == HB_STATE_MUXING || s.state == HB_STATE_PAUSED)
             {
                 if(![[menuItem title] isEqualToString:@"Stop Encoding"])
@@ -987,12 +1082,17 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
             else
                 return NO;
         }
-    
+    }
+    if( action == @selector(setDefaultPreset:) )
+    {
+        return [fPresetsOutlineView selectedRow] != -1;
+    }
+
     return YES;
 }
 
 #pragma mark -
-#pragma mark Growl
+#pragma mark Encode Done Actions
 // register a test notification and make
 // it enabled by default
 #define SERVICE_NAME @"Encode Done"
@@ -1006,25 +1106,43 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     return registrationDictionary; 
 } 
 
--(IBAction)showGrowlDoneNotification:(id)sender
+-(void)showGrowlDoneNotification:(NSString *) filePath
+{
+    /* This end of encode action is called as each encode rolls off of the queue */
+    NSString * finishedEncode = filePath;
+    /* strip off the path to just show the file name */
+    finishedEncode = [finishedEncode lastPathComponent];
+    if ([[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Growl Notification"] || 
+        [[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Alert Window And Growl"])
+    {
+        NSString * growlMssg = [NSString stringWithFormat: @"your HandBrake encode %@ is done!",finishedEncode];
+        [GrowlApplicationBridge 
+         notifyWithTitle:@"Put down that cocktail..." 
+         description:growlMssg 
+         notificationName:SERVICE_NAME
+         iconData:nil 
+         priority:0 
+         isSticky:1 
+         clickContext:nil];
+    }
+    
+}
+-(void)sendToMetaX:(NSString *) filePath
 {
-  [GrowlApplicationBridge 
-            notifyWithTitle:@"Put down that cocktail..." 
-                description:@"your HandBrake encode is done!" 
-           notificationName:SERVICE_NAME
-                   iconData:nil 
-                   priority:0 
-                   isSticky:1 
-               clickContext:nil];
+    /* This end of encode action is called as each encode rolls off of the queue */
+    if([[NSUserDefaults standardUserDefaults] boolForKey: @"sendToMetaX"] == YES)
+    {
+        NSAppleScript *myScript = [[NSAppleScript alloc] initWithSource: [NSString stringWithFormat: @"%@%@%@", @"tell application \"MetaX\" to open (POSIX file \"", filePath, @"\")"]];
+        [myScript executeAndReturnError: nil];
+        [myScript release];
+    }
 }
-
 #pragma mark -
 #pragma mark Get New Source
 
 /*Opens the source browse window, called from Open Source widgets */
 - (IBAction) browseSources: (id) sender
 {
-    [self enableUI: NO];
     NSOpenPanel * panel;
        
     panel = [NSOpenPanel openPanel];
@@ -1053,8 +1171,6 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
 - (void) browseSourcesDone: (NSOpenPanel *) sheet
                 returnCode: (int) returnCode contextInfo: (void *) contextInfo
 {
-    [browsedSourceDisplayName release];
-    
     /* we convert the sender content of contextInfo back into a variable called sender
      * mostly just for consistency for evaluation later
      */
@@ -1062,6 +1178,8 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     /* User selected a file to open */
        if( returnCode == NSOKButton )
     {
+            /* Free display name allocated previously by this code */
+        [browsedSourceDisplayName release];
        
         NSString *scanPath = [[sheet filenames] objectAtIndex: 0];
         /* we set the last searched source directory in the prefs here */
@@ -1080,28 +1198,28 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
              * purposes in the title panel
              */
             /* Full Path */
-            [fScanSrcTitlePathField setStringValue: [NSString stringWithFormat:@"%@", scanPath]];
+            [fScanSrcTitlePathField setStringValue:scanPath];
             NSString *displayTitlescanSourceName;
-            
+
             if ([[scanPath lastPathComponent] isEqualToString: @"VIDEO_TS"])
             {
-                /* If VIDEO_TS Folder is chosen, choose its parent folder for the source display name 
+                /* If VIDEO_TS Folder is chosen, choose its parent folder for the source display name
                  we have to use the title->dvd value so we get the proper name of the volume if a physical dvd is the source*/
-                displayTitlescanSourceName = [NSString stringWithFormat:[[scanPath stringByDeletingLastPathComponent] lastPathComponent]];
+                displayTitlescanSourceName = [[scanPath stringByDeletingLastPathComponent] lastPathComponent];
             }
             else
             {
                 /* if not the VIDEO_TS Folder, we can assume the chosen folder is the source name */
-                displayTitlescanSourceName = [NSString stringWithFormat:[scanPath lastPathComponent]];
+                displayTitlescanSourceName = [scanPath lastPathComponent];
             }
             /* we set the source display name in the title selection dialogue */
-            [fSrcDsplyNameTitleScan setStringValue: [NSString stringWithFormat:@"%@", displayTitlescanSourceName]];
+            [fSrcDsplyNameTitleScan setStringValue:displayTitlescanSourceName];
             /* we set the attempted scans display name for main window to displayTitlescanSourceName*/
             browsedSourceDisplayName = [displayTitlescanSourceName retain];
-            /* We show the actual sheet where the user specifies the title to be scanned 
+            /* We show the actual sheet where the user specifies the title to be scanned
              * as we are going to do a title specific scan
              */
-            [self showSourceTitleScanPanel:NULL];
+            [self showSourceTitleScanPanel:nil];
         }
         else
         {
@@ -1118,7 +1236,7 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
                     [self writeToActivityLog:"trying to open eyetv package"];
                     /* We're looking at an EyeTV package - try to open its enclosed
                      .mpg media file */
-                     browsedSourceDisplayName = [[NSString stringWithFormat:@"%@",[[path stringByDeletingPathExtension] lastPathComponent]] retain];
+                     browsedSourceDisplayName = [[[path stringByDeletingPathExtension] lastPathComponent] retain];
                     NSString *mpgname;
                     int n = [[path stringByAppendingString: @"/"]
                              completePathIntoString: &mpgname caseSensitive: NO
@@ -1142,44 +1260,37 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
                 else if ([[path pathExtension] isEqualToString: @"dvdmedia"])
                 {
                     /* path IS a package - but dvdmedia packages can be treaded like normal directories */
-                    browsedSourceDisplayName = [[NSString stringWithFormat:@"%@",[[path stringByDeletingPathExtension] lastPathComponent]] retain];
+                    browsedSourceDisplayName = [[[path stringByDeletingPathExtension] lastPathComponent] retain];
                     [self writeToActivityLog:"trying to open dvdmedia package"];
                     [self performScan:path scanTitleNum:0];
                 }
-                else 
+                else
                 {
                     /* The package is not an eyetv package, so we do not call performScan */
                     [self writeToActivityLog:"unable to open package"];
                 }
             }
-            else // path is not a package, so we treat it as a dvd parent folder or VIDEO_TS folder 
+            else // path is not a package, so we treat it as a dvd parent folder or VIDEO_TS folder
             {
                 /* path is not a package, so we call perform scan directly on our file */
                 if ([[path lastPathComponent] isEqualToString: @"VIDEO_TS"])
                 {
                     [self writeToActivityLog:"trying to open video_ts folder (video_ts folder chosen)"];
                     /* If VIDEO_TS Folder is chosen, choose its parent folder for the source display name*/
-                    browsedSourceDisplayName = [[NSString stringWithFormat:@"%@",[[path stringByDeletingLastPathComponent] lastPathComponent]] retain];
+                    browsedSourceDisplayName = [[[path stringByDeletingLastPathComponent] lastPathComponent] retain];
                 }
                 else
                 {
                     [self writeToActivityLog:"trying to open video_ts folder (parent directory chosen)"];
                     /* if not the VIDEO_TS Folder, we can assume the chosen folder is the source name */
-                    browsedSourceDisplayName = [[NSString stringWithFormat:@"%@",[path lastPathComponent]] retain];
+                    /* make sure we remove any path extension as this can also be an '.mpg' file */
+                    browsedSourceDisplayName = [[path lastPathComponent] retain];
                 }
                 [self performScan:path scanTitleNum:0];
             }
-            
-        }
-        
-    }
-    else // User clicked Cancel in browse window
-    {
-        /* if we have a title loaded up */
-        if ([[fSrcDVD2Field stringValue] length] > 0)
-        {
-            [self enableUI: YES];
+
         }
+
     }
 }
 
@@ -1191,16 +1302,14 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     */
     [fScanSrcTitleNumField setStringValue: @"0"];
        /* Show the panel */
-       [NSApp beginSheet: fScanSrcTitlePanel modalForWindow: fWindow modalDelegate: NULL didEndSelector: NULL contextInfo: NULL];
+       [NSApp beginSheet:fScanSrcTitlePanel modalForWindow:fWindow modalDelegate:nil didEndSelector:NULL contextInfo:NULL];
 }
 
 - (IBAction) closeSourceTitleScanPanel: (id) sender
 {
     [NSApp endSheet: fScanSrcTitlePanel];
     [fScanSrcTitlePanel orderOut: self];
-    
-    
-    
+
     if(sender == fScanSrcTitleOpenButton)
     {
         /* We setup the scan status in the main window to indicate a source title scan */
@@ -1216,34 +1325,84 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     }
 }
 
-
 /* Here we actually tell hb_scan to perform the source scan, using the path to source and title number*/
 - (void) performScan:(NSString *) scanPath scanTitleNum: (int) scanTitleNum
 {
+    /* set the bool applyQueueToScan so that we dont apply a queue setting to the final scan */
+    applyQueueToScan = NO;
+    /* use a bool to determine whether or not we can decrypt using vlc */
+    BOOL cancelScanDecrypt = 0;
     NSString *path = scanPath;
     HBDVDDetector *detector = [HBDVDDetector detectorForPath:path];
+
+    // Notify ChapterTitles that there's no title
+    [fChapterTitlesDelegate resetWithTitle:nil];
+    [fChapterTable reloadData];
+
+    [self enableUI: NO];
+
     if( [detector isVideoDVD] )
     {
         // The chosen path was actually on a DVD, so use the raw block
         // device path instead.
         path = [detector devicePath];
         [self writeToActivityLog: "trying to open a physical dvd at: %s", [scanPath UTF8String]];
+
+        /* lets check for vlc here to make sure we have a dylib available to use for decrypting */
+        NSString *vlcPath = @"/Applications/VLC.app";
+        NSFileManager * fileManager = [NSFileManager defaultManager];
+           if ([fileManager fileExistsAtPath:vlcPath] == 0) 
+           {
+            /*vlc not found in /Applications so we set the bool to cancel scanning to 1 */
+            cancelScanDecrypt = 1;
+            [self writeToActivityLog: "VLC app not found for decrypting physical dvd"];
+            int status;
+            status = NSRunAlertPanel(@"HandBrake could not find VLC.",@"Please download and install VLC media player in your /Applications folder if you wish to read encrypted DVDs.", @"Get VLC", @"Cancel Scan", @"Attempt Scan Anyway");
+            [NSApp requestUserAttention:NSCriticalRequest];
+            
+            if (status == NSAlertDefaultReturn)
+            {
+                /* User chose to go download vlc (as they rightfully should) so we send them to the vlc site */
+                [[NSWorkspace sharedWorkspace] openURL:[NSURL URLWithString:@"http://www.videolan.org/"]];
+            }
+            else if (status == NSAlertAlternateReturn)
+            {
+            /* User chose to cancel the scan */
+            [self writeToActivityLog: "cannot open physical dvd , scan cancelled"];
+            }
+            else
+            {
+            /* User chose to override our warning and scan the physical dvd anyway, at their own peril. on an encrypted dvd this produces massive log files and fails */
+            cancelScanDecrypt = 0;
+            [self writeToActivityLog: "user overrode vlc warning -trying to open physical dvd without decryption"];
+            }
+
+        }
+        else
+        {
+            /* VLC was found in /Applications so all is well, we can carry on using vlc's libdvdcss.dylib for decrypting if needed */
+            [self writeToActivityLog: "VLC app found for decrypting physical dvd"];
+        }
     }
-    /* If there is no title number passed to scan, we use "0"
-        * which causes the default behavior of a full source scan
-    */
-    if (!scanTitleNum)
-    {
-        scanTitleNum = 0;
-    }
-    if (scanTitleNum > 0)
+
+    if (cancelScanDecrypt == 0)
     {
-    [self writeToActivityLog: "scanning specifically for title: %d", scanTitleNum];
+        /* we actually pass the scan off to libhb here */
+        /* If there is no title number passed to scan, we use "0"
+         * which causes the default behavior of a full source scan
+         */
+        if (!scanTitleNum)
+        {
+            scanTitleNum = 0;
+        }
+        if (scanTitleNum > 0)
+        {
+            [self writeToActivityLog: "scanning specifically for title: %d", scanTitleNum];
+        }
+
+        hb_scan( fHandle, [path UTF8String], scanTitleNum );
+        [fSrcDVD2Field setStringValue:@"Scanning new source ..."];
     }
-    [fSrcDVD2Field setStringValue: [NSString stringWithFormat: @"Scanning new source ..."]];
-    /* we actually pass the scan off to libhb here */
-    hb_scan( fHandle, [path UTF8String], scanTitleNum );
-    
 }
 
 - (IBAction) showNewScan:(id)sender
@@ -1252,96 +1411,90 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
        hb_title_t * title;
        int indxpri=0;    // Used to search the longuest title (default in combobox)
        int longuestpri=0; // Used to search the longuest title (default in combobox)
-       
-       list = hb_get_titles( fHandle );
-       
-       if( !hb_list_count( list ) )
-       {
-               /* We display a message if a valid dvd source was not chosen */
-               [fSrcDVD2Field setStringValue: @"No Valid Source Found"];
-        SuccessfulScan = NO;
-        
-        // Notify ChapterTitles that there's no title
-        [fChapterTitlesDelegate resetWithTitle:nil];
-        [fChapterTable reloadData];
-       }
-       else
-       {
-        /* We increment the successful scancount here by one,
-        which we use at the end of this function to tell the gui
-        if this is the first successful scan since launch and whether
-        or not we should set all settings to the defaults */
-               
-        currentSuccessfulScanCount++;
+    
+
+        list = hb_get_titles( fHandle );
         
-        [toolbar validateVisibleItems];
-               
-               [fSrcTitlePopUp removeAllItems];
-               for( int i = 0; i < hb_list_count( list ); i++ )
-               {
-                       title = (hb_title_t *) hb_list_item( list, i );
-                       
-            currentSource = [NSString stringWithUTF8String: title->name];
+        if( !hb_list_count( list ) )
+        {
+            /* We display a message if a valid dvd source was not chosen */
+            [fSrcDVD2Field setStringValue: @"No Valid Source Found"];
+            SuccessfulScan = NO;
             
-            /*Set DVD Name at top of window with the browsedSourceDisplayName grokked right before -performScan */
-                       [fSrcDVD2Field setStringValue: [NSString stringWithFormat: @"%@",browsedSourceDisplayName]];
-                       
-                       /* Use the dvd name in the default output field here 
-                               May want to add code to remove blank spaces for some dvd names*/
-                       /* Check to see if the last destination has been set,use if so, if not, use Desktop */
-                       if ([[NSUserDefaults standardUserDefaults] stringForKey:@"LastDestinationDirectory"])
-                       {
-                               [fDstFile2Field setStringValue: [NSString stringWithFormat:
-                                       @"%@/%@.mp4", [[NSUserDefaults standardUserDefaults] stringForKey:@"LastDestinationDirectory"],browsedSourceDisplayName]];
-                       }
-                       else
-                       {
-                               [fDstFile2Field setStringValue: [NSString stringWithFormat:
-                                       @"%@/Desktop/%@.mp4", NSHomeDirectory(),browsedSourceDisplayName]];
-                       }
-                       
-                       if (longuestpri < title->hours*60*60 + title->minutes *60 + title->seconds)
-                       {
-                               longuestpri=title->hours*60*60 + title->minutes *60 + title->seconds;
-                               indxpri=i;
-                       }
-                       
-                       [self formatPopUpChanged:NULL];
-                       
-            [fSrcTitlePopUp addItemWithTitle: [NSString
-                stringWithFormat: @"%d - %02dh%02dm%02ds",
-                title->index, title->hours, title->minutes,
-                title->seconds]];
-               }
-        
-               // Select the longuest title
-               [fSrcTitlePopUp selectItemAtIndex: indxpri];
-               [self titlePopUpChanged: NULL];
-               
-        SuccessfulScan = YES;
-               [self enableUI: YES];
-               
-               /* if its the initial successful scan after awakeFromNib */
-        if (currentSuccessfulScanCount == 1)
+            // Notify ChapterTitles that there's no title
+            [fChapterTitlesDelegate resetWithTitle:nil];
+            [fChapterTable reloadData];
+        }
+        else
         {
-            [self selectDefaultPreset: NULL];
-            /* if Deinterlace upon launch is specified in the prefs, then set to 1 for "Fast",
-             if not, then set to 0 for none */
-            if ([[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultDeinterlaceOn"] > 0)
-            {
-                [fPictureController setDeinterlace:1];
-            }
-            else
+            /* We increment the successful scancount here by one,
+             which we use at the end of this function to tell the gui
+             if this is the first successful scan since launch and whether
+             or not we should set all settings to the defaults */
+            
+            currentSuccessfulScanCount++;
+            
+            [[fWindow toolbar] validateVisibleItems];
+            
+            [fSrcTitlePopUp removeAllItems];
+            for( int i = 0; i < hb_list_count( list ); i++ )
             {
-                [fPictureController setDeinterlace:0];
+                title = (hb_title_t *) hb_list_item( list, i );
+                
+                currentSource = [NSString stringWithUTF8String: title->name];
+                /*Set DVD Name at top of window with the browsedSourceDisplayName grokked right before -performScan */
+                [fSrcDVD2Field setStringValue:browsedSourceDisplayName];
+                
+                /* Use the dvd name in the default output field here
+                 May want to add code to remove blank spaces for some dvd names*/
+                /* Check to see if the last destination has been set,use if so, if not, use Desktop */
+                if ([[NSUserDefaults standardUserDefaults] stringForKey:@"LastDestinationDirectory"])
+                {
+                    [fDstFile2Field setStringValue: [NSString stringWithFormat:
+                                                     @"%@/%@.mp4", [[NSUserDefaults standardUserDefaults] stringForKey:@"LastDestinationDirectory"],[browsedSourceDisplayName stringByDeletingPathExtension]]];
+                }
+                else
+                {
+                    [fDstFile2Field setStringValue: [NSString stringWithFormat:
+                                                     @"%@/Desktop/%@.mp4", NSHomeDirectory(),[browsedSourceDisplayName stringByDeletingPathExtension]]];
+                }
+                
+                
+                if (longuestpri < title->hours*60*60 + title->minutes *60 + title->seconds)
+                {
+                    longuestpri=title->hours*60*60 + title->minutes *60 + title->seconds;
+                    indxpri=i;
+                }
+                
+                [fSrcTitlePopUp addItemWithTitle: [NSString
+                                                   stringWithFormat: @"%d - %02dh%02dm%02ds",
+                                                   title->index, title->hours, title->minutes,
+                                                   title->seconds]];
             }
-            /* lets set Denoise to index 0 or "None" since this is the first scan */
-            [fPictureController setDenoise:0];
             
-            [fPictureController setInitialPictureFilters];
+            // Select the longuest title
+            [fSrcTitlePopUp selectItemAtIndex: indxpri];
+            [self titlePopUpChanged:nil];
+            
+            SuccessfulScan = YES;
+            [self enableUI: YES];
+
+                /* if its the initial successful scan after awakeFromNib */
+                if (currentSuccessfulScanCount == 1)
+                {
+                    [self selectDefaultPreset:nil];
+                    /* initially set deinterlace to 0, will be overridden reset by the default preset anyway */
+                    //[fPictureController setDeinterlace:0];
+                    
+                    /* lets set Denoise to index 0 or "None" since this is the first scan */
+                    //[fPictureController setDenoise:0];
+                    
+                    [fPictureController setInitialPictureFilters];
+                }
+
+            
         }
-        
-       }
+
 }
 
 
@@ -1393,267 +1546,1326 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     return NO;
 }
 
+
 #pragma mark -
-#pragma mark Job Handling
+#pragma mark Queue File
+
+- (void) loadQueueFile {
+       /* We declare the default NSFileManager into fileManager */
+       NSFileManager * fileManager = [NSFileManager defaultManager];
+       /*We define the location of the user presets file */
+    QueueFile = @"~/Library/Application Support/HandBrake/Queue.plist";
+       QueueFile = [[QueueFile stringByExpandingTildeInPath]retain];
+    /* We check for the presets.plist */
+       if ([fileManager fileExistsAtPath:QueueFile] == 0)
+       {
+               [fileManager createFileAtPath:QueueFile contents:nil attributes:nil];
+       }
 
+       QueueFileArray = [[NSMutableArray alloc] initWithContentsOfFile:QueueFile];
+       /* lets check to see if there is anything in the queue file .plist */
+    if (nil == QueueFileArray)
+       {
+        /* if not, then lets initialize an empty array */
+               QueueFileArray = [[NSMutableArray alloc] init];
+        
+     /* Initialize our curQueueEncodeIndex to 0
+     * so we can use it to track which queue
+     * item is to be used to track our encodes */
+     /* NOTE: this should be changed if and when we
+      * are able to get the last unfinished encode
+      * in the case of a crash or shutdown */
+    
+       }
+    else
+    {
+    [self clearQueueEncodedItems];
+    }
+    currentQueueEncodeIndex = 0;
+}
 
-- (void) prepareJob
+- (void)addQueueFileItem
 {
-    hb_list_t  * list  = hb_get_titles( fHandle );
-    hb_title_t * title = (hb_title_t *) hb_list_item( list,
-            [fSrcTitlePopUp indexOfSelectedItem] );
-    hb_job_t * job = title->job;
-    //int i;
+        [QueueFileArray addObject:[self createQueueFileItem]];
+        [self saveQueueFileItem];
 
-    /* Chapter selection */
-    job->chapter_start = [fSrcChapterStartPopUp indexOfSelectedItem] + 1;
-    job->chapter_end   = [fSrcChapterEndPopUp   indexOfSelectedItem] + 1;
-       
-    /* Format and codecs */
-    int format = [fDstFormatPopUp indexOfSelectedItem];
-    int codecs = [fDstCodecsPopUp indexOfSelectedItem];
-    job->mux    = FormatSettings[format][codecs] & HB_MUX_MASK;
-    job->vcodec = FormatSettings[format][codecs] & HB_VCODEC_MASK;
-    job->acodec = FormatSettings[format][codecs] & HB_ACODEC_MASK;
-    /* If mpeg-4, then set mpeg-4 specific options like chapters and > 4gb file sizes */
-       if ([fDstFormatPopUp indexOfSelectedItem] == 0)
-       {
-        /* We set the largeFileSize (64 bit formatting) variable here to allow for > 4gb files based on the format being
-               mpeg4 and the checkbox being checked 
-               *Note: this will break compatibility with some target devices like iPod, etc.!!!!*/
-               if ([[NSUserDefaults standardUserDefaults] boolForKey:@"AllowLargeFiles"] > 0 && [fDstMp4LargeFileCheck state] == NSOnState)
-               {
-                       job->largeFileSize = 1;
-               }
-               else
-               {
-                       job->largeFileSize = 0;
-               }
-        /* We set http optimized mp4 here */
-        if ([fDstMp4HttpOptFileCheck state] == NSOnState)
-               {
-        job->mp4_optimize = 1;
-        }
-        else
-        {
-        job->mp4_optimize = 0;
-        }
+}
+
+- (void) removeQueueFileItem:(int) queueItemToRemove
+{
+   
+   /* Find out if the item we are removing is a cancelled (3) or a finished (0) item*/
+   if ([[[QueueFileArray objectAtIndex:queueItemToRemove] objectForKey:@"Status"] intValue] == 3 || [[[QueueFileArray objectAtIndex:queueItemToRemove] objectForKey:@"Status"] intValue] == 0)
+    {
+    /* Since we are removing a cancelled or finished item, WE need to decrement the currentQueueEncodeIndex
+     * by one to keep in sync with the queue array
+     */
+    currentQueueEncodeIndex--;
+    [self writeToActivityLog: "removeQueueFileItem: Removing a cancelled/finished encode, decrement currentQueueEncodeIndex to %d", currentQueueEncodeIndex];
     }
-       if ([fDstFormatPopUp indexOfSelectedItem] == 0 || [fDstFormatPopUp indexOfSelectedItem] == 3)
+    [QueueFileArray removeObjectAtIndex:queueItemToRemove];
+    [self saveQueueFileItem];
+
+}
+
+- (void)saveQueueFileItem
+{
+    [QueueFileArray writeToFile:QueueFile atomically:YES];
+    [fQueueController setQueueArray: QueueFileArray];
+    [self getQueueStats];
+}
+
+- (void)getQueueStats
+{
+/* lets get the stats on the status of the queue array */
+
+fEncodingQueueItem = 0;
+fPendingCount = 0;
+fCompletedCount = 0;
+fCanceledCount = 0;
+fWorkingCount = 0;
+
+    /* We use a number system to set the encode status of the queue item
+     * in controller.mm
+     * 0 == already encoded
+     * 1 == is being encoded
+     * 2 == is yet to be encoded
+     * 3 == cancelled
+     */
+
+       int i = 0;
+    NSEnumerator *enumerator = [QueueFileArray objectEnumerator];
+       id tempObject;
+       while (tempObject = [enumerator nextObject])
        {
-         /* We set the chapter marker extraction here based on the format being
-               mpeg4 or mkv and the checkbox being checked */
-               if ([fCreateChapterMarkers state] == NSOnState)
+               NSDictionary *thisQueueDict = tempObject;
+               if ([[thisQueueDict objectForKey:@"Status"] intValue] == 0) // Completed
                {
-                       job->chapter_markers = 1;
+                       fCompletedCount++;      
                }
-               else
+               if ([[thisQueueDict objectForKey:@"Status"] intValue] == 1) // being encoded
                {
-                       job->chapter_markers = 0;
-               }
-       }
-       if( ( job->vcodec & HB_VCODEC_FFMPEG ) &&
-        [fVidEncoderPopUp indexOfSelectedItem] > 0 )
-    {
-        job->vcodec = HB_VCODEC_XVID;
-    }
-    if( job->vcodec & HB_VCODEC_X264 )
-    {
-               if ([fDstMp4iPodFileCheck state] == NSOnState)
-           {
-            job->ipod_atom = 1;
+                       fWorkingCount++;
+            fEncodingQueueItem = i;    
                }
-        else
+        if ([[thisQueueDict objectForKey:@"Status"] intValue] == 2) // pending         
         {
-        job->ipod_atom = 0;
-        }
-               
-               /* Set this flag to switch from Constant Quantizer(default) to Constant Rate Factor Thanks jbrjake
-         Currently only used with Constant Quality setting*/
-               if ([[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultCrf"] > 0 && [fVidQualityMatrix selectedRow] == 2)
-               {
-               job->crf = 1;
-               }
-               
-               /* Below Sends x264 options to the core library if x264 is selected*/
-               /* Lets use this as per Nyx, Thanks Nyx!*/
-               job->x264opts = (char *)calloc(1024, 1); /* Fixme, this just leaks */
-               /* Turbo first pass if two pass and Turbo First pass is selected */
-               if( [fVidTwoPassCheck state] == NSOnState && [fVidTurboPassCheck state] == NSOnState )
-               {
-                       /* pass the "Turbo" string to be appended to the existing x264 opts string into a variable for the first pass */
-                       NSString *firstPassOptStringTurbo = @":ref=1:subme=1:me=dia:analyse=none:trellis=0:no-fast-pskip=0:8x8dct=0:weightb=0";
-                       /* append the "Turbo" string variable to the existing opts string.
-             Note: the "Turbo" string must be appended, not prepended to work properly*/
-                       NSString *firstPassOptStringCombined = [[fAdvancedOptions optionsString] stringByAppendingString:firstPassOptStringTurbo];
-                       strcpy(job->x264opts, [firstPassOptStringCombined UTF8String]);
+                       fPendingCount++;
                }
-               else
-               {
-                       strcpy(job->x264opts, [[fAdvancedOptions optionsString] UTF8String]);
+        if ([[thisQueueDict objectForKey:@"Status"] intValue] == 3) // cancelled               
+        {
+                       fCanceledCount++;
                }
-        
-    }
+               i++;
+       }
 
-    /* Video settings */
-    if( [fVidRatePopUp indexOfSelectedItem] > 0 )
+    /* Set the queue status field in the main window */
+    NSMutableString * string;
+    if (fPendingCount == 1)
     {
-        job->vrate      = 27000000;
-        job->vrate_base = hb_video_rates[[fVidRatePopUp
-            indexOfSelectedItem]-1].rate;
+        string = [NSMutableString stringWithFormat: NSLocalizedString( @"%d encode pending in the queue", @"" ), fPendingCount];
     }
     else
     {
-        job->vrate      = title->rate;
-        job->vrate_base = title->rate_base;
+        string = [NSMutableString stringWithFormat: NSLocalizedString( @"%d encode(s) pending in the queue", @"" ), fPendingCount];
     }
+    [fQueueStatus setStringValue:string];
+}
 
-    switch( [fVidQualityMatrix selectedRow] )
+/* This method will set any item marked as encoding back to pending
+ * currently used right after a queue reload
+ */
+- (void) setQueueEncodingItemsAsPending
+{
+    NSEnumerator *enumerator = [QueueFileArray objectEnumerator];
+       id tempObject;
+    NSMutableArray *tempArray;
+    tempArray = [NSMutableArray array];
+    /* we look here to see if the preset is we move on to the next one */
+    while ( tempObject = [enumerator nextObject] )  
     {
-        case 0:
-            /* Target size.
-               Bitrate should already have been calculated and displayed
-               in fVidBitrateField, so let's just use it */
-        case 1:
-            job->vquality = -1.0;
-            job->vbitrate = [fVidBitrateField intValue];
-            break;
-        case 2:
-            job->vquality = [fVidQualitySlider floatValue];
-            job->vbitrate = 0;
-            break;
+        /* If the queue item is marked as "encoding" (1)
+         * then change its status back to pending (2) which effectively
+         * puts it back into the queue to be encoded
+         */
+        if ([[tempObject objectForKey:@"Status"] intValue] == 1)
+        {
+            [tempObject setObject:[NSNumber numberWithInt: 2] forKey:@"Status"];
+        }
+        [tempArray addObject:tempObject];
     }
+    
+    [QueueFileArray setArray:tempArray];
+    [self saveQueueFileItem];
+}
 
-    job->grayscale = ( [fVidGrayscaleCheck state] == NSOnState );
-
-    /* Subtitle settings */
-    job->subtitle = [fSubPopUp indexOfSelectedItem] - 2;
-
-    /* Audio tracks and mixdowns */
-    /* check for the condition where track 2 has an audio selected, but track 1 does not */
-    /* we will use track 2 as track 1 in this scenario */
-    if ([fAudLang1PopUp indexOfSelectedItem] > 0)
-    {
-        job->audios[0] = [fAudLang1PopUp indexOfSelectedItem] - 1;
-        job->audios[1] = [fAudLang2PopUp indexOfSelectedItem] - 1; /* will be -1 if "none" is selected */
-        job->audios[2] = -1;
-        job->audio_mixdowns[0] = [[fAudTrack1MixPopUp selectedItem] tag];
-        job->audio_mixdowns[1] = [[fAudTrack2MixPopUp selectedItem] tag];
-    }
-    else if ([fAudLang2PopUp indexOfSelectedItem] > 0)
-    {
-        job->audios[0] = [fAudLang2PopUp indexOfSelectedItem] - 1;
-        job->audio_mixdowns[0] = [[fAudTrack2MixPopUp selectedItem] tag];
-        job->audios[1] = -1;
-    }
-    else
-    {
-        job->audios[0] = -1;
-    }
 
-    /*
-     * Where one or more of the audio tracks has a mixdown of DPLII+AC3 we need to create an extra
-     * track for each.
-     */
-    if (job->audio_mixdowns[0] == HB_AMIXDOWN_DOLBYPLII_AC3)
+/* This method will clear the queue of any encodes that are not still pending
+ * this includes both successfully completed encodes as well as cancelled encodes */
+- (void) clearQueueEncodedItems
+{
+    NSEnumerator *enumerator = [QueueFileArray objectEnumerator];
+       id tempObject;
+    NSMutableArray *tempArray;
+    tempArray = [NSMutableArray array];
+    /* we look here to see if the preset is we move on to the next one */
+    while ( tempObject = [enumerator nextObject] )  
     {
-        /*
-         * Make space for the AC3 track by moving 1 to 2
+        /* If the queue item is either completed (0) or cancelled (3) from the
+         * last session, then we put it in tempArray to be deleted from QueueFileArray.
+         * NOTE: this means we retain pending (2) and also an item that is marked as
+         * still encoding (1). If the queue has an item that is still marked as encoding
+         * from a previous session, we can conlude that HB was either shutdown, or crashed
+         * during the encodes so we keep it and tell the user in the "Load Queue Alert"
          */
-        job->audios[2] = job->audios[1];
-        job->audio_mixdowns[2] = job->audio_mixdowns[1];
-        job->audios[1] = job->audios[0];
-        job->audio_mixdowns[0] = HB_AMIXDOWN_DOLBYPLII;
-        job->audio_mixdowns[1] = HB_AMIXDOWN_AC3;
-    }
-
-    if (job->audio_mixdowns[1] == HB_AMIXDOWN_DOLBYPLII_AC3)
-    {
-        job->audios[2] = job->audios[1];
-        job->audio_mixdowns[1] = HB_AMIXDOWN_DOLBYPLII;
-        job->audio_mixdowns[2] = HB_AMIXDOWN_AC3;
-        job->audios[3] = -1;
+        if ([[tempObject objectForKey:@"Status"] intValue] == 0 || [[tempObject objectForKey:@"Status"] intValue] == 3)
+        {
+            [tempArray addObject:tempObject];
+        }
     }
+    
+    [QueueFileArray removeObjectsInArray:tempArray];
+    [self saveQueueFileItem];
+}
 
-    if (job->audio_mixdowns[2] == HB_AMIXDOWN_DOLBYPLII_AC3)
+/* This method will clear the queue of all encodes. effectively creating an empty queue */
+- (void) clearQueueAllItems
+{
+    NSEnumerator *enumerator = [QueueFileArray objectEnumerator];
+       id tempObject;
+    NSMutableArray *tempArray;
+    tempArray = [NSMutableArray array];
+    /* we look here to see if the preset is we move on to the next one */
+    while ( tempObject = [enumerator nextObject] )  
     {
-        job->audios[3] = job->audios[2];
-        job->audio_mixdowns[2] = HB_AMIXDOWN_DOLBYPLII;
-        job->audio_mixdowns[3] = HB_AMIXDOWN_AC3;
-        job->audios[4] = -1;
+        [tempArray addObject:tempObject];
     }
+    
+    [QueueFileArray removeObjectsInArray:tempArray];
+    [self saveQueueFileItem];
+}
 
-    /* Audio settings */
-    job->arate = hb_audio_rates[[fAudRatePopUp
-                     indexOfSelectedItem]].rate;
-    job->abitrate = [[fAudBitratePopUp selectedItem] tag];
+/* This method will duplicate prepareJob however into the
+ * queue .plist instead of into the job structure so it can
+ * be recalled later */
+- (NSDictionary *)createQueueFileItem
+{
+    NSMutableDictionary *queueFileJob = [[NSMutableDictionary alloc] init];
     
-    /* Dynamic Range Compression */
-    job->dynamic_range_compression = [fAudDrcField floatValue];
+       hb_list_t  * list  = hb_get_titles( fHandle );
+    hb_title_t * title = (hb_title_t *) hb_list_item( list,
+            [fSrcTitlePopUp indexOfSelectedItem] );
+    hb_job_t * job = title->job;
     
-    /* set vfr according to the Picture Window */
-    if ([fPictureController vfr])
-    {
-    job->vfr = 1;
-    }
-    else
-    {
-    job->vfr = 0;
-    }
     
-    /* Filters */ 
+    
+    /* We use a number system to set the encode status of the queue item
+     * 0 == already encoded
+     * 1 == is being encoded
+     * 2 == is yet to be encoded
+     * 3 == cancelled
+     */
+    [queueFileJob setObject:[NSNumber numberWithInt:2] forKey:@"Status"];
+    /* Source and Destination Information */
+    
+    [queueFileJob setObject:[NSString stringWithUTF8String: title->dvd] forKey:@"SourcePath"];
+    [queueFileJob setObject:[fSrcDVD2Field stringValue] forKey:@"SourceName"];
+    [queueFileJob setObject:[NSNumber numberWithInt:title->index] forKey:@"TitleNumber"];
+    [queueFileJob setObject:[NSNumber numberWithInt:[fSrcChapterStartPopUp indexOfSelectedItem] + 1] forKey:@"ChapterStart"];
+    
+    [queueFileJob setObject:[NSNumber numberWithInt:[fSrcChapterEndPopUp indexOfSelectedItem] + 1] forKey:@"ChapterEnd"];
+    
+    [queueFileJob setObject:[fDstFile2Field stringValue] forKey:@"DestinationPath"];
+    
+    /* Lets get the preset info if there is any */
+    [queueFileJob setObject:[fPresetSelectedDisplay stringValue] forKey:@"PresetName"];
+    [queueFileJob setObject:[NSNumber numberWithInt:[fPresetsOutlineView selectedRow]] forKey:@"PresetIndexNum"];
+    
+    [queueFileJob setObject:[fDstFormatPopUp titleOfSelectedItem] forKey:@"FileFormat"];
+       /* Chapter Markers fCreateChapterMarkers*/
+       [queueFileJob setObject:[NSNumber numberWithInt:[fCreateChapterMarkers state]] forKey:@"ChapterMarkers"];
+       
+    /* We need to get the list of chapter names to put into an array and store 
+     * in our queue, so they can be reapplied in prepareJob when this queue
+     * item comes up if Chapter Markers is set to on.
+     */
+     int i;
+     NSMutableArray *ChapterNamesArray = [[NSMutableArray alloc] init];
+     int chaptercount = hb_list_count( fTitle->list_chapter );
+     for( i = 0; i < chaptercount; i++ )
+    {
+        hb_chapter_t *chapter = (hb_chapter_t *) hb_list_item( fTitle->list_chapter, i );
+        if( chapter != NULL )
+        {
+         [ChapterNamesArray addObject:[NSString stringWithFormat:@"%s",chapter->title]];
+        }
+    }
+    [queueFileJob setObject:[NSMutableArray arrayWithArray: ChapterNamesArray] forKey:@"ChapterNames"];
+    [ChapterNamesArray autorelease];
+    
+    /* Allow Mpeg4 64 bit formatting +4GB file sizes */
+       [queueFileJob setObject:[NSNumber numberWithInt:[fDstMp4LargeFileCheck state]] forKey:@"Mp4LargeFile"];
+    /* Mux mp4 with http optimization */
+    [queueFileJob setObject:[NSNumber numberWithInt:[fDstMp4HttpOptFileCheck state]] forKey:@"Mp4HttpOptimize"];
+    /* Add iPod uuid atom */
+    [queueFileJob setObject:[NSNumber numberWithInt:[fDstMp4iPodFileCheck state]] forKey:@"Mp4iPodCompatible"];
+    
+    /* Codecs */
+       /* Video encoder */
+       [queueFileJob setObject:[fVidEncoderPopUp titleOfSelectedItem] forKey:@"VideoEncoder"];
+       /* x264 Option String */
+       [queueFileJob setObject:[fAdvancedOptions optionsString] forKey:@"x264Option"];
+
+       [queueFileJob setObject:[NSNumber numberWithInt:[fVidQualityMatrix selectedRow]] forKey:@"VideoQualityType"];
+       [queueFileJob setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
+       [queueFileJob setObject:[fVidBitrateField stringValue] forKey:@"VideoAvgBitrate"];
+       [queueFileJob setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
+    /* Framerate */
+    [queueFileJob setObject:[fVidRatePopUp titleOfSelectedItem] forKey:@"VideoFramerate"];
+    
+    /* GrayScale */
+       [queueFileJob setObject:[NSNumber numberWithInt:[fVidGrayscaleCheck state]] forKey:@"VideoGrayScale"];
+       /* 2 Pass Encoding */
+       [queueFileJob setObject:[NSNumber numberWithInt:[fVidTwoPassCheck state]] forKey:@"VideoTwoPass"];
+       /* Turbo 2 pass Encoding fVidTurboPassCheck*/
+       [queueFileJob setObject:[NSNumber numberWithInt:[fVidTurboPassCheck state]] forKey:@"VideoTurboTwoPass"];
+    
+       /* Picture Sizing */
+       /* Use Max Picture settings for whatever the dvd is.*/
+       [queueFileJob setObject:[NSNumber numberWithInt:0] forKey:@"UsesMaxPictureSettings"];
+       [queueFileJob setObject:[NSNumber numberWithInt:fTitle->job->width] forKey:@"PictureWidth"];
+       [queueFileJob setObject:[NSNumber numberWithInt:fTitle->job->height] forKey:@"PictureHeight"];
+       [queueFileJob setObject:[NSNumber numberWithInt:fTitle->job->keep_ratio] forKey:@"PictureKeepRatio"];
+       [queueFileJob setObject:[NSNumber numberWithInt:fTitle->job->pixel_ratio] forKey:@"PicturePAR"];
+    NSString * pictureSummary;
+    pictureSummary = [NSString stringWithFormat:@"Source: %@ Output: %@ Anamorphic: %@", 
+                     [fPicSettingsSrc stringValue], 
+                     [fPicSettingsOutp stringValue], 
+                     [fPicSettingsAnamorphic stringValue]];
+    [queueFileJob setObject:pictureSummary forKey:@"PictureSizingSummary"];                 
+    /* Set crop settings here */
+       [queueFileJob setObject:[NSNumber numberWithInt:[fPictureController autoCrop]] forKey:@"PictureAutoCrop"];
+    [queueFileJob setObject:[NSNumber numberWithInt:job->crop[0]] forKey:@"PictureTopCrop"];
+    [queueFileJob setObject:[NSNumber numberWithInt:job->crop[1]] forKey:@"PictureBottomCrop"];
+       [queueFileJob setObject:[NSNumber numberWithInt:job->crop[2]] forKey:@"PictureLeftCrop"];
+       [queueFileJob setObject:[NSNumber numberWithInt:job->crop[3]] forKey:@"PictureRightCrop"];
+    
+    /* Picture Filters */
+    [queueFileJob setObject:[NSNumber numberWithInt:[fPictureController deinterlace]] forKey:@"PictureDeinterlace"];
+       [queueFileJob setObject:[NSNumber numberWithInt:[fPictureController detelecine]] forKey:@"PictureDetelecine"];
+    [queueFileJob setObject:[NSNumber numberWithInt:[fPictureController denoise]] forKey:@"PictureDenoise"];
+    [queueFileJob setObject:[NSString stringWithFormat:@"%d",[fPictureController deblock]] forKey:@"PictureDeblock"]; 
+    [queueFileJob setObject:[NSNumber numberWithInt:[fPictureController decomb]] forKey:@"PictureDecomb"];
+    
+    /*Audio*/
+    if ([fAudLang1PopUp indexOfSelectedItem] > 0)
+    {
+        [queueFileJob setObject:[NSNumber numberWithInt:[fAudLang1PopUp indexOfSelectedItem]] forKey:@"Audio1Track"];
+        [queueFileJob setObject:[fAudLang1PopUp titleOfSelectedItem] forKey:@"Audio1TrackDescription"];
+        [queueFileJob setObject:[fAudTrack1CodecPopUp titleOfSelectedItem] forKey:@"Audio1Encoder"];
+        [queueFileJob setObject:[fAudTrack1MixPopUp titleOfSelectedItem] forKey:@"Audio1Mixdown"];
+        [queueFileJob setObject:[fAudTrack1RatePopUp titleOfSelectedItem] forKey:@"Audio1Samplerate"];
+        [queueFileJob setObject:[fAudTrack1BitratePopUp titleOfSelectedItem] forKey:@"Audio1Bitrate"];
+        [queueFileJob setObject:[NSNumber numberWithFloat:[fAudTrack1DrcSlider floatValue]] forKey:@"Audio1TrackDRCSlider"];
+    }
+    if ([fAudLang2PopUp indexOfSelectedItem] > 0)
+    {
+        [queueFileJob setObject:[NSNumber numberWithInt:[fAudLang2PopUp indexOfSelectedItem]] forKey:@"Audio2Track"];
+        [queueFileJob setObject:[fAudLang2PopUp titleOfSelectedItem] forKey:@"Audio2TrackDescription"];
+        [queueFileJob setObject:[fAudTrack2CodecPopUp titleOfSelectedItem] forKey:@"Audio2Encoder"];
+        [queueFileJob setObject:[fAudTrack2MixPopUp titleOfSelectedItem] forKey:@"Audio2Mixdown"];
+        [queueFileJob setObject:[fAudTrack2RatePopUp titleOfSelectedItem] forKey:@"Audio2Samplerate"];
+        [queueFileJob setObject:[fAudTrack2BitratePopUp titleOfSelectedItem] forKey:@"Audio2Bitrate"];
+        [queueFileJob setObject:[NSNumber numberWithFloat:[fAudTrack2DrcSlider floatValue]] forKey:@"Audio2TrackDRCSlider"];
+    }
+    if ([fAudLang3PopUp indexOfSelectedItem] > 0)
+    {
+        [queueFileJob setObject:[NSNumber numberWithInt:[fAudLang3PopUp indexOfSelectedItem]] forKey:@"Audio3Track"];
+        [queueFileJob setObject:[fAudLang3PopUp titleOfSelectedItem] forKey:@"Audio3TrackDescription"];
+        [queueFileJob setObject:[fAudTrack3CodecPopUp titleOfSelectedItem] forKey:@"Audio3Encoder"];
+        [queueFileJob setObject:[fAudTrack3MixPopUp titleOfSelectedItem] forKey:@"Audio3Mixdown"];
+        [queueFileJob setObject:[fAudTrack3RatePopUp titleOfSelectedItem] forKey:@"Audio3Samplerate"];
+        [queueFileJob setObject:[fAudTrack3BitratePopUp titleOfSelectedItem] forKey:@"Audio3Bitrate"];
+        [queueFileJob setObject:[NSNumber numberWithFloat:[fAudTrack3DrcSlider floatValue]] forKey:@"Audio3TrackDRCSlider"];
+    }
+    if ([fAudLang4PopUp indexOfSelectedItem] > 0)
+    {
+        [queueFileJob setObject:[NSNumber numberWithInt:[fAudLang4PopUp indexOfSelectedItem]] forKey:@"Audio4Track"];
+        [queueFileJob setObject:[fAudLang4PopUp titleOfSelectedItem] forKey:@"Audio4TrackDescription"];
+        [queueFileJob setObject:[fAudTrack4CodecPopUp titleOfSelectedItem] forKey:@"Audio4Encoder"];
+        [queueFileJob setObject:[fAudTrack4MixPopUp titleOfSelectedItem] forKey:@"Audio4Mixdown"];
+        [queueFileJob setObject:[fAudTrack4RatePopUp titleOfSelectedItem] forKey:@"Audio4Samplerate"];
+        [queueFileJob setObject:[fAudTrack4BitratePopUp titleOfSelectedItem] forKey:@"Audio4Bitrate"];
+        [queueFileJob setObject:[NSNumber numberWithFloat:[fAudTrack4DrcSlider floatValue]] forKey:@"Audio4TrackDRCSlider"];
+    }
+    
+       /* Subtitles*/
+       [queueFileJob setObject:[fSubPopUp titleOfSelectedItem] forKey:@"Subtitles"];
+    [queueFileJob setObject:[NSNumber numberWithInt:[fSubPopUp indexOfSelectedItem]] forKey:@"JobSubtitlesIndex"];
+    /* Forced Subtitles */
+       [queueFileJob setObject:[NSNumber numberWithInt:[fSubForcedCheck state]] forKey:@"SubtitlesForced"];
+    
+    
+    
+    /* Now we go ahead and set the "job->values in the plist for passing right to fQueueEncodeLibhb */
+     
+    [queueFileJob setObject:[NSNumber numberWithInt:[fSrcChapterStartPopUp indexOfSelectedItem] + 1] forKey:@"JobChapterStart"];
+    
+    [queueFileJob setObject:[NSNumber numberWithInt:[fSrcChapterEndPopUp indexOfSelectedItem] + 1] forKey:@"JobChapterEnd"];
+    
+    
+    [queueFileJob setObject:[NSNumber numberWithInt:[[fDstFormatPopUp selectedItem] tag]] forKey:@"JobFileFormatMux"];
+    
+    /* Codecs */
+       /* Video encoder */
+       [queueFileJob setObject:[NSNumber numberWithInt:[[fVidEncoderPopUp selectedItem] tag]] forKey:@"JobVideoEncoderVcodec"];
+       
+    /* Framerate */
+    [queueFileJob setObject:[NSNumber numberWithInt:[fVidRatePopUp indexOfSelectedItem]] forKey:@"JobIndexVideoFramerate"];
+    [queueFileJob setObject:[NSNumber numberWithInt:title->rate] forKey:@"JobVrate"];
+    [queueFileJob setObject:[NSNumber numberWithInt:title->rate_base] forKey:@"JobVrateBase"];
+       
+    /* Picture Sizing */
+       /* Use Max Picture settings for whatever the dvd is.*/
+       [queueFileJob setObject:[NSNumber numberWithInt:0] forKey:@"UsesMaxPictureSettings"];
+       [queueFileJob setObject:[NSNumber numberWithInt:fTitle->job->width] forKey:@"PictureWidth"];
+       [queueFileJob setObject:[NSNumber numberWithInt:fTitle->job->height] forKey:@"PictureHeight"];
+       [queueFileJob setObject:[NSNumber numberWithInt:fTitle->job->keep_ratio] forKey:@"PictureKeepRatio"];
+       [queueFileJob setObject:[NSNumber numberWithInt:fTitle->job->pixel_ratio] forKey:@"PicturePAR"];
+    
+    /* Set crop settings here */
+       [queueFileJob setObject:[NSNumber numberWithInt:[fPictureController autoCrop]] forKey:@"PictureAutoCrop"];
+    [queueFileJob setObject:[NSNumber numberWithInt:job->crop[0]] forKey:@"PictureTopCrop"];
+    [queueFileJob setObject:[NSNumber numberWithInt:job->crop[1]] forKey:@"PictureBottomCrop"];
+       [queueFileJob setObject:[NSNumber numberWithInt:job->crop[2]] forKey:@"PictureLeftCrop"];
+       [queueFileJob setObject:[NSNumber numberWithInt:job->crop[3]] forKey:@"PictureRightCrop"];
+    
+    /* Picture Filters */
+    [queueFileJob setObject:[fPicSettingDecomb stringValue] forKey:@"JobPictureDecomb"];
+    
+    /*Audio*/
+    if ([fAudLang1PopUp indexOfSelectedItem] > 0)
+    {
+        //[queueFileJob setObject:[fAudTrack1CodecPopUp indexOfSelectedItem] forKey:@"JobAudio1Encoder"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack1CodecPopUp selectedItem] tag]] forKey:@"JobAudio1Encoder"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack1MixPopUp selectedItem] tag]] forKey:@"JobAudio1Mixdown"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack1RatePopUp selectedItem] tag]] forKey:@"JobAudio1Samplerate"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack1BitratePopUp selectedItem] tag]] forKey:@"JobAudio1Bitrate"];
+     }
+    if ([fAudLang2PopUp indexOfSelectedItem] > 0)
+    {
+        //[queueFileJob setObject:[fAudTrack1CodecPopUp indexOfSelectedItem] forKey:@"JobAudio2Encoder"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack2CodecPopUp selectedItem] tag]] forKey:@"JobAudio2Encoder"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack2MixPopUp selectedItem] tag]] forKey:@"JobAudio2Mixdown"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack2RatePopUp selectedItem] tag]] forKey:@"JobAudio2Samplerate"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack2BitratePopUp selectedItem] tag]] forKey:@"JobAudio2Bitrate"];
+    }
+    if ([fAudLang3PopUp indexOfSelectedItem] > 0)
+    {
+        //[queueFileJob setObject:[fAudTrack1CodecPopUp indexOfSelectedItem] forKey:@"JobAudio3Encoder"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack3CodecPopUp selectedItem] tag]] forKey:@"JobAudio3Encoder"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack3MixPopUp selectedItem] tag]] forKey:@"JobAudio3Mixdown"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack3RatePopUp selectedItem] tag]] forKey:@"JobAudio3Samplerate"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack3BitratePopUp selectedItem] tag]] forKey:@"JobAudio3Bitrate"];
+    }
+    if ([fAudLang4PopUp indexOfSelectedItem] > 0)
+    {
+        //[queueFileJob setObject:[fAudTrack1CodecPopUp indexOfSelectedItem] forKey:@"JobAudio4Encoder"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack4CodecPopUp selectedItem] tag]] forKey:@"JobAudio4Encoder"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack4MixPopUp selectedItem] tag]] forKey:@"JobAudio4Mixdown"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack4RatePopUp selectedItem] tag]] forKey:@"JobAudio4Samplerate"];
+        [queueFileJob setObject:[NSNumber numberWithInt:[[fAudTrack4BitratePopUp selectedItem] tag]] forKey:@"JobAudio4Bitrate"];
+    }
+       /* Subtitles*/
+       [queueFileJob setObject:[fSubPopUp titleOfSelectedItem] forKey:@"Subtitles"];
+    /* Forced Subtitles */
+       [queueFileJob setObject:[NSNumber numberWithInt:[fSubForcedCheck state]] forKey:@"SubtitlesForced"];
+    /* we need to auto relase the queueFileJob and return it */
+    [queueFileJob autorelease];
+    return queueFileJob;
+
+}
+
+/* this is actually called from the queue controller to modify the queue array and return it back to the queue controller */
+- (void)moveObjectsInQueueArray:(NSMutableArray *)array fromIndexes:(NSIndexSet *)indexSet toIndex:(unsigned)insertIndex
+{
+    unsigned index = [indexSet lastIndex];
+    unsigned aboveInsertIndexCount = 0;
+    
+    while (index != NSNotFound)
+    {
+        unsigned removeIndex;
+        
+        if (index >= insertIndex)
+        {
+            removeIndex = index + aboveInsertIndexCount;
+            aboveInsertIndexCount++;
+        }
+        else
+        {
+            removeIndex = index;
+            insertIndex--;
+        }
+        
+        id object = [[QueueFileArray objectAtIndex:removeIndex] retain];
+        [QueueFileArray removeObjectAtIndex:removeIndex];
+        [QueueFileArray insertObject:object atIndex:insertIndex];
+        [object release];
+        
+        index = [indexSet indexLessThanIndex:index];
+    }
+   /* We save all of the Queue data here 
+    * and it also gets sent back to the queue controller*/
+    [self saveQueueFileItem]; 
+    
+}
+
+
+#pragma mark -
+#pragma mark Queue Job Processing
+
+- (void) incrementQueueItemDone:(int) queueItemDoneIndexNum
+{
+    int i = currentQueueEncodeIndex;
+    [[QueueFileArray objectAtIndex:i] setObject:[NSNumber numberWithInt:0] forKey:@"Status"];
+       
+    /* We save all of the Queue data here */
+    [self saveQueueFileItem];
+       /* We Reload the New Table data for presets */
+    //[fPresetsOutlineView reloadData];
+
+    /* Since we have now marked a queue item as done
+     * we can go ahead and increment currentQueueEncodeIndex 
+     * so that if there is anything left in the queue we can
+     * go ahead and move to the next item if we want to */
+    currentQueueEncodeIndex++ ;
+    [self writeToActivityLog: "incrementQueueItemDone currentQueueEncodeIndex is incremented to: %d", currentQueueEncodeIndex];
+    int queueItems = [QueueFileArray count];
+    /* If we still have more items in our queue, lets go to the next one */
+    if (currentQueueEncodeIndex < queueItems)
+    {
+    [self writeToActivityLog: "incrementQueueItemDone currentQueueEncodeIndex is incremented to: %d", currentQueueEncodeIndex];
+    [self performNewQueueScan:[[QueueFileArray objectAtIndex:currentQueueEncodeIndex] objectForKey:@"SourcePath"] scanTitleNum:[[[QueueFileArray objectAtIndex:currentQueueEncodeIndex] objectForKey:@"TitleNumber"]intValue]];
+    }
+    else
+    {
+        [self writeToActivityLog: "incrementQueueItemDone the %d item queue is complete", currentQueueEncodeIndex - 1];
+    }
+}
+
+/* Here we actually tell hb_scan to perform the source scan, using the path to source and title number*/
+- (void) performNewQueueScan:(NSString *) scanPath scanTitleNum: (int) scanTitleNum
+{
+   /* Tell HB to output a new activity log file for this encode */
+    [outputPanel startEncodeLog:[[QueueFileArray objectAtIndex:currentQueueEncodeIndex] objectForKey:@"DestinationPath"]];
+    
+    
+     /* use a bool to determine whether or not we can decrypt using vlc */
+    BOOL cancelScanDecrypt = 0;
+    /* set the bool so that showNewScan knows to apply the appropriate queue
+    * settings as this is a queue rescan
+    */
+    applyQueueToScan = YES;
+    NSString *path = scanPath;
+    HBDVDDetector *detector = [HBDVDDetector detectorForPath:path];
+
+        /*On Screen Notification*/
+        //int status;
+        //status = NSRunAlertPanel(@"HandBrake is now loading up a new queue item...",@"Would You Like to wait until you add another encode?", @"Cancel", @"Okay", nil);
+        //[NSApp requestUserAttention:NSCriticalRequest];
+
+    // Notify ChapterTitles that there's no title
+    [fChapterTitlesDelegate resetWithTitle:nil];
+    [fChapterTable reloadData];
+
+    //[self enableUI: NO];
+
+    if( [detector isVideoDVD] )
+    {
+        // The chosen path was actually on a DVD, so use the raw block
+        // device path instead.
+        path = [detector devicePath];
+        [self writeToActivityLog: "trying to open a physical dvd at: %s", [scanPath UTF8String]];
+
+        /* lets check for vlc here to make sure we have a dylib available to use for decrypting */
+        NSString *vlcPath = @"/Applications/VLC.app";
+        NSFileManager * fileManager = [NSFileManager defaultManager];
+           if ([fileManager fileExistsAtPath:vlcPath] == 0) 
+           {
+            /*vlc not found in /Applications so we set the bool to cancel scanning to 1 */
+            cancelScanDecrypt = 1;
+            [self writeToActivityLog: "VLC app not found for decrypting physical dvd"];
+            int status;
+            status = NSRunAlertPanel(@"HandBrake could not find VLC.",@"Please download and install VLC media player in your /Applications folder if you wish to read encrypted DVDs.", @"Get VLC", @"Cancel Scan", @"Attempt Scan Anyway");
+            [NSApp requestUserAttention:NSCriticalRequest];
+            
+            if (status == NSAlertDefaultReturn)
+            {
+                /* User chose to go download vlc (as they rightfully should) so we send them to the vlc site */
+                [[NSWorkspace sharedWorkspace] openURL:[NSURL URLWithString:@"http://www.videolan.org/"]];
+            }
+            else if (status == NSAlertAlternateReturn)
+            {
+            /* User chose to cancel the scan */
+            [self writeToActivityLog: "cannot open physical dvd , scan cancelled"];
+            }
+            else
+            {
+            /* User chose to override our warning and scan the physical dvd anyway, at their own peril. on an encrypted dvd this produces massive log files and fails */
+            cancelScanDecrypt = 0;
+            [self writeToActivityLog: "user overrode vlc warning -trying to open physical dvd without decryption"];
+            }
+
+        }
+        else
+        {
+            /* VLC was found in /Applications so all is well, we can carry on using vlc's libdvdcss.dylib for decrypting if needed */
+            [self writeToActivityLog: "VLC app found for decrypting physical dvd"];
+        }
+    }
+
+    if (cancelScanDecrypt == 0)
+    {
+        /* we actually pass the scan off to libhb here */
+        /* If there is no title number passed to scan, we use "0"
+         * which causes the default behavior of a full source scan
+         */
+        if (!scanTitleNum)
+        {
+            scanTitleNum = 0;
+        }
+        if (scanTitleNum > 0)
+        {
+            [self writeToActivityLog: "scanning specifically for title: %d", scanTitleNum];
+        }
+        [self writeToActivityLog: "performNewQueueScan currentQueueEncodeIndex is: %d", currentQueueEncodeIndex];
+        hb_scan( fQueueEncodeLibhb, [path UTF8String], scanTitleNum );
+    }
+}
+
+/* This method was originally used to load up a new queue item in the gui and
+ * then start processing it. However we now have modified -prepareJob and use a second
+ * instance of libhb to do our actual encoding, therefor right now it is not required. 
+ * Nonetheless I want to leave this in here
+ * because basically its everything we need to be able to actually modify a pending queue
+ * item in the gui and resave it. At least for now - dynaflash
+ */
+
+- (IBAction)applyQueueSettings:(id)sender
+{
+    NSMutableDictionary * queueToApply = [QueueFileArray objectAtIndex:currentQueueEncodeIndex];
+    hb_job_t * job = fTitle->job;
+    
+    /* Set title number and chapters */
+    /* since the queue only scans a single title, we really don't need to pick a title */
+    //[fSrcTitlePopUp selectItemAtIndex: [[queueToApply objectForKey:@"TitleNumber"] intValue] - 1];
+    
+    [fSrcChapterStartPopUp selectItemAtIndex: [[queueToApply objectForKey:@"ChapterStart"] intValue] - 1];
+    [fSrcChapterEndPopUp selectItemAtIndex: [[queueToApply objectForKey:@"ChapterEnd"] intValue] - 1];
+    
+    /* File Format */
+    [fDstFormatPopUp selectItemWithTitle:[queueToApply objectForKey:@"FileFormat"]];
+    [self formatPopUpChanged:nil];
+    
+    /* Chapter Markers*/
+    [fCreateChapterMarkers setState:[[queueToApply objectForKey:@"ChapterMarkers"] intValue]];
+    /* Allow Mpeg4 64 bit formatting +4GB file sizes */
+    [fDstMp4LargeFileCheck setState:[[queueToApply objectForKey:@"Mp4LargeFile"] intValue]];
+    /* Mux mp4 with http optimization */
+    [fDstMp4HttpOptFileCheck setState:[[queueToApply objectForKey:@"Mp4HttpOptimize"] intValue]];
+    
+    /* Video encoder */
+    /* We set the advanced opt string here if applicable*/
+    [fVidEncoderPopUp selectItemWithTitle:[queueToApply objectForKey:@"VideoEncoder"]];
+    [fAdvancedOptions setOptions:[queueToApply objectForKey:@"x264Option"]];
+    
+    /* Lets run through the following functions to get variables set there */
+    [self videoEncoderPopUpChanged:nil];
+    /* Set the state of ipod compatible with Mp4iPodCompatible. Only for x264*/
+    [fDstMp4iPodFileCheck setState:[[queueToApply objectForKey:@"Mp4iPodCompatible"] intValue]];
+    [self calculateBitrate:nil];
+    
+    /* Video quality */
+    [fVidQualityMatrix selectCellAtRow:[[queueToApply objectForKey:@"VideoQualityType"] intValue] column:0];
+    
+    [fVidTargetSizeField setStringValue:[queueToApply objectForKey:@"VideoTargetSize"]];
+    [fVidBitrateField setStringValue:[queueToApply objectForKey:@"VideoAvgBitrate"]];
+    [fVidQualitySlider setFloatValue:[[queueToApply objectForKey:@"VideoQualitySlider"] floatValue]];
+    
+    [self videoMatrixChanged:nil];
+    
+    /* Video framerate */
+    /* For video preset video framerate, we want to make sure that Same as source does not conflict with the
+     detected framerate in the fVidRatePopUp so we use index 0*/
+    if ([[queueToApply objectForKey:@"VideoFramerate"] isEqualToString:@"Same as source"])
+    {
+        [fVidRatePopUp selectItemAtIndex: 0];
+    }
+    else
+    {
+        [fVidRatePopUp selectItemWithTitle:[queueToApply objectForKey:@"VideoFramerate"]];
+    }
+    
+    /* GrayScale */
+    [fVidGrayscaleCheck setState:[[queueToApply objectForKey:@"VideoGrayScale"] intValue]];
+    
+    /* 2 Pass Encoding */
+    [fVidTwoPassCheck setState:[[queueToApply objectForKey:@"VideoTwoPass"] intValue]];
+    [self twoPassCheckboxChanged:nil];
+    /* Turbo 1st pass for 2 Pass Encoding */
+    [fVidTurboPassCheck setState:[[queueToApply objectForKey:@"VideoTurboTwoPass"] intValue]];
+    
+    /*Audio*/
+    if ([queueToApply objectForKey:@"Audio1Track"] > 0)
+    {
+        if ([fAudLang1PopUp indexOfSelectedItem] == 0)
+        {
+            [fAudLang1PopUp selectItemAtIndex: 1];
+        }
+        [self audioTrackPopUpChanged: fAudLang1PopUp];
+        [fAudTrack1CodecPopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio1Encoder"]];
+        [self audioTrackPopUpChanged: fAudTrack1CodecPopUp];
+        [fAudTrack1MixPopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio1Mixdown"]];
+        /* check to see if the selections was available, if not, rerun audioTrackPopUpChanged using the codec to just set the default
+         * mixdown*/
+        if  ([fAudTrack1MixPopUp selectedItem] == nil)
+        {
+            [self audioTrackPopUpChanged: fAudTrack1CodecPopUp];
+        }
+        [fAudTrack1RatePopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio1Samplerate"]];
+        /* We set the presets bitrate if it is *not* an AC3 track since that uses the input bitrate */
+        if (![[queueToApply objectForKey:@"Audio1Encoder"] isEqualToString:@"AC3 Passthru"])
+        {
+            [fAudTrack1BitratePopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio1Bitrate"]];
+        }
+        [fAudTrack1DrcSlider setFloatValue:[[queueToApply objectForKey:@"Audio1TrackDRCSlider"] floatValue]];
+        [self audioDRCSliderChanged: fAudTrack1DrcSlider];
+    }
+    if ([queueToApply objectForKey:@"Audio2Track"] > 0)
+    {
+        if ([fAudLang2PopUp indexOfSelectedItem] == 0)
+        {
+            [fAudLang2PopUp selectItemAtIndex: 1];
+        }
+        [self audioTrackPopUpChanged: fAudLang2PopUp];
+        [fAudTrack2CodecPopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio2Encoder"]];
+        [self audioTrackPopUpChanged: fAudTrack2CodecPopUp];
+        [fAudTrack2MixPopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio2Mixdown"]];
+        /* check to see if the selections was available, if not, rerun audioTrackPopUpChanged using the codec to just set the default
+         * mixdown*/
+        if  ([fAudTrack2MixPopUp selectedItem] == nil)
+        {
+            [self audioTrackPopUpChanged: fAudTrack2CodecPopUp];
+        }
+        [fAudTrack2RatePopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio2Samplerate"]];
+        /* We set the presets bitrate if it is *not* an AC3 track since that uses the input bitrate */
+        if (![[queueToApply objectForKey:@"Audio2Encoder"] isEqualToString:@"AC3 Passthru"])
+        {
+            [fAudTrack2BitratePopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio2Bitrate"]];
+        }
+        [fAudTrack2DrcSlider setFloatValue:[[queueToApply objectForKey:@"Audio2TrackDRCSlider"] floatValue]];
+        [self audioDRCSliderChanged: fAudTrack2DrcSlider];
+    }
+    if ([queueToApply objectForKey:@"Audio3Track"] > 0)
+    {
+        if ([fAudLang3PopUp indexOfSelectedItem] == 0)
+        {
+            [fAudLang3PopUp selectItemAtIndex: 1];
+        }
+        [self audioTrackPopUpChanged: fAudLang3PopUp];
+        [fAudTrack3CodecPopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio3Encoder"]];
+        [self audioTrackPopUpChanged: fAudTrack3CodecPopUp];
+        [fAudTrack3MixPopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio3Mixdown"]];
+        /* check to see if the selections was available, if not, rerun audioTrackPopUpChanged using the codec to just set the default
+         * mixdown*/
+        if  ([fAudTrack3MixPopUp selectedItem] == nil)
+        {
+            [self audioTrackPopUpChanged: fAudTrack3CodecPopUp];
+        }
+        [fAudTrack3RatePopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio3Samplerate"]];
+        /* We set the presets bitrate if it is *not* an AC3 track since that uses the input bitrate */
+        if (![[queueToApply objectForKey:@"Audio3Encoder"] isEqualToString: @"AC3 Passthru"])
+        {
+            [fAudTrack3BitratePopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio3Bitrate"]];
+        }
+        [fAudTrack3DrcSlider setFloatValue:[[queueToApply objectForKey:@"Audio3TrackDRCSlider"] floatValue]];
+        [self audioDRCSliderChanged: fAudTrack3DrcSlider];
+    }
+    if ([queueToApply objectForKey:@"Audio4Track"] > 0)
+    {
+        if ([fAudLang4PopUp indexOfSelectedItem] == 0)
+        {
+            [fAudLang4PopUp selectItemAtIndex: 1];
+        }
+        [self audioTrackPopUpChanged: fAudLang4PopUp];
+        [fAudTrack4CodecPopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio4Encoder"]];
+        [self audioTrackPopUpChanged: fAudTrack4CodecPopUp];
+        [fAudTrack4MixPopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio4Mixdown"]];
+        /* check to see if the selections was available, if not, rerun audioTrackPopUpChanged using the codec to just set the default
+         * mixdown*/
+        if  ([fAudTrack4MixPopUp selectedItem] == nil)
+        {
+            [self audioTrackPopUpChanged: fAudTrack4CodecPopUp];
+        }
+        [fAudTrack4RatePopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio4Samplerate"]];
+        /* We set the presets bitrate if it is *not* an AC3 track since that uses the input bitrate */
+        if (![[chosenPreset objectForKey:@"Audio4Encoder"] isEqualToString:@"AC3 Passthru"])
+        {
+            [fAudTrack4BitratePopUp selectItemWithTitle:[queueToApply objectForKey:@"Audio4Bitrate"]];
+        }
+        [fAudTrack4DrcSlider setFloatValue:[[queueToApply objectForKey:@"Audio4TrackDRCSlider"] floatValue]];
+        [self audioDRCSliderChanged: fAudTrack4DrcSlider];
+    }
+    
+    
+    /*Subtitles*/
+    [fSubPopUp selectItemWithTitle:[queueToApply objectForKey:@"Subtitles"]];
+    /* Forced Subtitles */
+    [fSubForcedCheck setState:[[queueToApply objectForKey:@"SubtitlesForced"] intValue]];
+    
+    /* Picture Settings */
+    /* we check to make sure the presets width/height does not exceed the sources width/height */
+    if (fTitle->width < [[queueToApply objectForKey:@"PictureWidth"]  intValue] || fTitle->height < [[queueToApply objectForKey:@"PictureHeight"]  intValue])
+    {
+        /* if so, then we use the sources height and width to avoid scaling up */
+        job->width = fTitle->width;
+        job->height = fTitle->height;
+    }
+    else // source width/height is >= the preset height/width
+    {
+        /* we can go ahead and use the presets values for height and width */
+        job->width = [[queueToApply objectForKey:@"PictureWidth"]  intValue];
+        job->height = [[queueToApply objectForKey:@"PictureHeight"]  intValue];
+    }
+    job->keep_ratio = [[queueToApply objectForKey:@"PictureKeepRatio"]  intValue];
+    if (job->keep_ratio == 1)
+    {
+        hb_fix_aspect( job, HB_KEEP_WIDTH );
+        if( job->height > fTitle->height )
+        {
+            job->height = fTitle->height;
+            hb_fix_aspect( job, HB_KEEP_HEIGHT );
+        }
+    }
+    job->pixel_ratio = [[queueToApply objectForKey:@"PicturePAR"]  intValue];
+    
+    
+    /* If Cropping is set to custom, then recall all four crop values from
+     when the preset was created and apply them */
+    if ([[queueToApply objectForKey:@"PictureAutoCrop"]  intValue] == 0)
+    {
+        [fPictureController setAutoCrop:NO];
+        
+        /* Here we use the custom crop values saved at the time the preset was saved */
+        job->crop[0] = [[queueToApply objectForKey:@"PictureTopCrop"]  intValue];
+        job->crop[1] = [[queueToApply objectForKey:@"PictureBottomCrop"]  intValue];
+        job->crop[2] = [[queueToApply objectForKey:@"PictureLeftCrop"]  intValue];
+        job->crop[3] = [[queueToApply objectForKey:@"PictureRightCrop"]  intValue];
+        
+    }
+    else /* if auto crop has been saved in preset, set to auto and use post scan auto crop */
+    {
+        [fPictureController setAutoCrop:YES];
+        /* Here we use the auto crop values determined right after scan */
+        job->crop[0] = AutoCropTop;
+        job->crop[1] = AutoCropBottom;
+        job->crop[2] = AutoCropLeft;
+        job->crop[3] = AutoCropRight;
+        
+    }
+    
+    /* Filters */
+    /* Deinterlace */
+    [fPictureController setDeinterlace:[[queueToApply objectForKey:@"PictureDeinterlace"] intValue]];
+    
+    /* Detelecine */
+    [fPictureController setDetelecine:[[queueToApply objectForKey:@"PictureDetelecine"] intValue]];
+    /* Denoise */
+    [fPictureController setDenoise:[[queueToApply objectForKey:@"PictureDenoise"] intValue]];
+    /* Deblock */
+    [fPictureController setDeblock:[[queueToApply objectForKey:@"PictureDeblock"] intValue]];
+    /* Decomb */
+    [fPictureController setDecomb:[[queueToApply objectForKey:@"PictureDecomb"] intValue]];
+    
+    [self calculatePictureSizing:nil];
+    
+    
+    /* somehow we need to figure out a way to tie the queue item to a preset if it used one */
+    //[queueFileJob setObject:[fPresetSelectedDisplay stringValue] forKey:@"PresetName"];
+    //    [queueFileJob setObject:[NSNumber numberWithInt:[fPresetsOutlineView selectedRow]] forKey:@"PresetIndexNum"];
+    if ([queueToApply objectForKey:@"PresetIndexNum"]) // This item used a preset so insert that info
+       {
+               /* Deselect the currently selected Preset if there is one*/
+        //[fPresetsOutlineView selectRowIndexes:[NSIndexSet indexSetWithIndex:[[queueToApply objectForKey:@"PresetIndexNum"] intValue]] byExtendingSelection:NO];
+        //[self selectPreset:nil];
+               
+        //[fPresetsOutlineView selectRow:[[queueToApply objectForKey:@"PresetIndexNum"] intValue]];
+               /* Change UI to show "Custom" settings are being used */
+               //[fPresetSelectedDisplay setStringValue: [[queueToApply objectForKey:@"PresetName"] stringValue]];
+        
+               curUserPresetChosenNum = nil;
+       }
+    else
+    {
+        /* Deselect the currently selected Preset if there is one*/
+               [fPresetsOutlineView deselectRow:[fPresetsOutlineView selectedRow]];
+               /* Change UI to show "Custom" settings are being used */
+               [fPresetSelectedDisplay setStringValue: @"Custom"];
+        
+               //curUserPresetChosenNum = nil;
+    }
+    
+    /* We need to set this bool back to NO, in case the user wants to do a scan */
+    //applyQueueToScan = NO;
+    
+    /* so now we go ahead and process the new settings */
+    [self processNewQueueEncode];
+}
+
+
+
+/* This assumes that we have re-scanned and loaded up a new queue item to send to libhb as fQueueEncodeLibhb */
+- (void) processNewQueueEncode
+{
+    hb_list_t  * list  = hb_get_titles( fQueueEncodeLibhb );
+    hb_title_t * title = (hb_title_t *) hb_list_item( list,0 ); // is always zero since now its a single title scan
+    hb_job_t * job = title->job;
+    
+    if( !hb_list_count( list ) )
+    {
+        [self writeToActivityLog: "processNewQueueEncode WARNING nothing found in the title list"];
+    }
+    else
+    {
+        [self writeToActivityLog: "processNewQueueEncode title list is: %d", hb_list_count( list )];
+    }
+    
+    NSMutableDictionary * queueToApply = [QueueFileArray objectAtIndex:currentQueueEncodeIndex];
+    //[self writeToActivityLog: "processNewQueueEncode currentQueueEncodeIndex is: %d", currentQueueEncodeIndex];
+    [self writeToActivityLog: "processNewQueueEncode number of passes expected is: %d", ([[queueToApply objectForKey:@"VideoTwoPass"] intValue] + 1)];
+    job->file = [[queueToApply objectForKey:@"DestinationPath"] UTF8String];
+    //[self writeToActivityLog: "processNewQueueEncode sending to prepareJob"];
+    [self prepareJob];
+    if( [[queueToApply objectForKey:@"SubtitlesForced"] intValue] == 1 )
+        job->subtitle_force = 1;
+    else
+        job->subtitle_force = 0;
+    
+    /*
+     * subtitle of -1 is a scan
+     */
+    if( job->subtitle == -1 )
+    {
+        char *x264opts_tmp;
+        
+        /*
+         * When subtitle scan is enabled do a fast pre-scan job
+         * which will determine which subtitles to enable, if any.
+         */
+        job->pass = -1;
+        x264opts_tmp = job->x264opts;
+        job->subtitle = -1;
+        
+        job->x264opts = NULL;
+        
+        job->indepth_scan = 1;  
+        
+        job->select_subtitle = (hb_subtitle_t**)malloc(sizeof(hb_subtitle_t*));
+        *(job->select_subtitle) = NULL;
+        
+        /*
+         * Add the pre-scan job
+         */
+        hb_add( fQueueEncodeLibhb, job );
+        job->x264opts = x264opts_tmp;
+    }
+    else
+        job->select_subtitle = NULL;
+    
+    /* No subtitle were selected, so reset the subtitle to -1 (which before
+     * this point meant we were scanning
+     */
+    if( job->subtitle == -2 )
+        job->subtitle = -1;
+    
+    if( [[queueToApply objectForKey:@"VideoTwoPass"] intValue] == 1 )
+    {
+        hb_subtitle_t **subtitle_tmp = job->select_subtitle;
+        job->indepth_scan = 0;
+        
+        /*
+         * Do not autoselect subtitles on the first pass of a two pass
+         */
+        job->select_subtitle = NULL;
+        
+        job->pass = 1;
+        
+        hb_add( fQueueEncodeLibhb, job );
+        
+        job->pass = 2;
+        
+        job->x264opts = (char *)calloc(1024, 1); /* Fixme, this just leaks */  
+        strcpy(job->x264opts, [[queueToApply objectForKey:@"x264Option"] UTF8String]);
+        
+        job->select_subtitle = subtitle_tmp;
+        
+        hb_add( fQueueEncodeLibhb, job );
+        
+    }
+    else
+    {
+        job->indepth_scan = 0;
+        job->pass = 0;
+        
+        hb_add( fQueueEncodeLibhb, job );
+    }
+       
+    NSString *destinationDirectory = [[queueToApply objectForKey:@"DestinationPath"] stringByDeletingLastPathComponent];
+       [[NSUserDefaults standardUserDefaults] setObject:destinationDirectory forKey:@"LastDestinationDirectory"];
+       /* Lets mark our new encode as 1 or "Encoding" */
+    [queueToApply setObject:[NSNumber numberWithInt:1] forKey:@"Status"];
+    [self saveQueueFileItem];
+    /* We should be all setup so let 'er rip */   
+    [self doRip];
+}
+
+
+#pragma mark -
+#pragma mark Job Handling
+
+
+- (void) prepareJob
+{
+    
+    NSMutableDictionary * queueToApply = [QueueFileArray objectAtIndex:currentQueueEncodeIndex];
+    hb_list_t  * list  = hb_get_titles( fQueueEncodeLibhb );
+    hb_title_t * title = (hb_title_t *) hb_list_item( list,0 ); // is always zero since now its a single title scan
+    hb_job_t * job = title->job;
+    hb_audio_config_t * audio;
+    /* Chapter selection */
+    job->chapter_start = [[queueToApply objectForKey:@"JobChapterStart"] intValue];
+    job->chapter_end   = [[queueToApply objectForKey:@"JobChapterEnd"] intValue];
+       
+    /* Format (Muxer) and Video Encoder */
+    job->mux = [[queueToApply objectForKey:@"JobFileFormatMux"] intValue];
+    job->vcodec = [[queueToApply objectForKey:@"JobVideoEncoderVcodec"] intValue];
+    
+    
+    /* If mpeg-4, then set mpeg-4 specific options like chapters and > 4gb file sizes */
+       //if( [fDstFormatPopUp indexOfSelectedItem] == 0 )
+       //{
+    /* We set the largeFileSize (64 bit formatting) variable here to allow for > 4gb files based on the format being
+     mpeg4 and the checkbox being checked 
+     *Note: this will break compatibility with some target devices like iPod, etc.!!!!*/
+    if( [[queueToApply objectForKey:@"Mp4LargeFile"] intValue] == 1)
+    {
+        job->largeFileSize = 1;
+    }
+    else
+    {
+        job->largeFileSize = 0;
+    }
+    /* We set http optimized mp4 here */
+    if( [[queueToApply objectForKey:@"Mp4HttpOptimize"] intValue] == 1 )
+    {
+        job->mp4_optimize = 1;
+    }
+    else
+    {
+        job->mp4_optimize = 0;
+    }
+    
+    //}
+       
+    /* We set the chapter marker extraction here based on the format being
+     mpeg4 or mkv and the checkbox being checked */
+    if ([[queueToApply objectForKey:@"ChapterMarkers"] intValue] == 1)
+    {
+        job->chapter_markers = 1;
+        
+        /* now lets get our saved chapter names out the array in the queue file
+         * and insert them back into the title chapter list. We have it here,
+         * because unless we are inserting chapter markers there is no need to
+         * spend the overhead of iterating through the chapter names array imo
+         * Also, note that if for some reason we don't apply chapter names, the
+         * chapters just come out 001, 002, etc. etc.
+         */
+         
+        NSMutableArray *ChapterNamesArray = [queueToApply objectForKey:@"ChapterNames"];
+        int i = 0;
+        NSEnumerator *enumerator = [ChapterNamesArray objectEnumerator];
+        id tempObject;
+        while (tempObject = [enumerator nextObject])
+        {
+            hb_chapter_t *chapter = (hb_chapter_t *) hb_list_item( title->list_chapter, i );
+            if( chapter != NULL )
+            {
+                strncpy( chapter->title, [tempObject UTF8String], 1023);
+                chapter->title[1023] = '\0';
+            }
+            i++;
+        }
+    }
+    else
+    {
+        job->chapter_markers = 0;
+    }
+    
+
+    
+    
+    
+    if( job->vcodec & HB_VCODEC_X264 )
+    {
+               if ([[queueToApply objectForKey:@"Mp4iPodCompatible"] intValue] == 1)
+           {
+            job->ipod_atom = 1;
+               }
+        else
+        {
+            job->ipod_atom = 0;
+        }
+               
+               /* Set this flag to switch from Constant Quantizer(default) to Constant Rate Factor Thanks jbrjake
+         Currently only used with Constant Quality setting*/
+               if ([[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultCrf"] > 0 && [[queueToApply objectForKey:@"VideoQualityType"] intValue] == 2)
+               {
+               job->crf = 1;
+               }
+               /* Below Sends x264 options to the core library if x264 is selected*/
+               /* Lets use this as per Nyx, Thanks Nyx!*/
+               job->x264opts = (char *)calloc(1024, 1); /* Fixme, this just leaks */
+               /* Turbo first pass if two pass and Turbo First pass is selected */
+               if( [[queueToApply objectForKey:@"VideoTwoPass"] intValue] == 1 && [[queueToApply objectForKey:@"VideoTurboTwoPass"] intValue] == 1 )
+               {
+                       /* pass the "Turbo" string to be appended to the existing x264 opts string into a variable for the first pass */
+                       NSString *firstPassOptStringTurbo = @":ref=1:subme=1:me=dia:analyse=none:trellis=0:no-fast-pskip=0:8x8dct=0:weightb=0";
+                       /* append the "Turbo" string variable to the existing opts string.
+             Note: the "Turbo" string must be appended, not prepended to work properly*/
+                       NSString *firstPassOptStringCombined = [[queueToApply objectForKey:@"x264Option"] stringByAppendingString:firstPassOptStringTurbo];
+                       strcpy(job->x264opts, [firstPassOptStringCombined UTF8String]);
+               }
+               else
+               {
+                       strcpy(job->x264opts, [[queueToApply objectForKey:@"x264Option"] UTF8String]);
+               }
+        
+    }
+    
+    
+    /* Picture Size Settings */
+    job->width = [[queueToApply objectForKey:@"PictureWidth"]  intValue];
+    job->height = [[queueToApply objectForKey:@"PictureHeight"]  intValue];
+    
+    job->keep_ratio = [[queueToApply objectForKey:@"PictureKeepRatio"]  intValue];
+    job->pixel_ratio = [[queueToApply objectForKey:@"PicturePAR"]  intValue];
+    
+    
+    /* Here we use the crop values saved at the time the preset was saved */
+    job->crop[0] = [[queueToApply objectForKey:@"PictureTopCrop"]  intValue];
+    job->crop[1] = [[queueToApply objectForKey:@"PictureBottomCrop"]  intValue];
+    job->crop[2] = [[queueToApply objectForKey:@"PictureLeftCrop"]  intValue];
+    job->crop[3] = [[queueToApply objectForKey:@"PictureRightCrop"]  intValue];
+    
+    /* Video settings */
+    /* Framerate */
+    
+    /* Set vfr to 0 as it's only on if using same as source in the framerate popup
+     * and detelecine is on, so we handle that in the logic below
+     */
+    job->vfr = 0;
+    if( [[queueToApply objectForKey:@"JobIndexVideoFramerate"] intValue] > 0 )
+    {
+        /* a specific framerate has been chosen */
+        job->vrate      = 27000000;
+        job->vrate_base = hb_video_rates[[[queueToApply objectForKey:@"JobIndexVideoFramerate"] intValue]-1].rate;
+        /* We are not same as source so we set job->cfr to 1 
+         * to enable constant frame rate since user has specified
+         * a specific framerate*/
+        job->cfr = 1;
+    }
+    else
+    {
+        /* We are same as source (variable) */
+        job->vrate      = [[queueToApply objectForKey:@"JobVrate"] intValue];
+        job->vrate_base = [[queueToApply objectForKey:@"JobVrateBase"] intValue];
+        /* We are same as source so we set job->cfr to 0 
+         * to enable true same as source framerate */
+        job->cfr = 0;
+        /* If we are same as source and we have detelecine on, we need to turn on
+         * job->vfr
+         */
+        if ([[queueToApply objectForKey:@"PictureDetelecine"] intValue] == 1)
+        {
+            job->vfr = 1;
+        }
+    }
+    if ( [[queueToApply objectForKey:@"VideoQualityType"] intValue] != 2 )
+    {
+        /* Target size.
+         Bitrate should already have been calculated and displayed
+         in fVidBitrateField, so let's just use it same as abr*/
+        job->vquality = -1.0;
+        job->vbitrate = [[queueToApply objectForKey:@"VideoAvgBitrate"] intValue];
+    }
+    if ( [[queueToApply objectForKey:@"VideoQualityType"] intValue] == 2 )
+    {
+        job->vquality = [[queueToApply objectForKey:@"VideoQualitySlider"] floatValue];
+        job->vbitrate = 0;
+        
+    }
+    
+    job->grayscale = [[queueToApply objectForKey:@"VideoGrayScale"] intValue];
+    /* Subtitle settings */
+    job->subtitle = [[queueToApply objectForKey:@"JobSubtitlesIndex"] intValue] - 2;
+    
+    /* Audio tracks and mixdowns */
+    /* Lets make sure there arent any erroneous audio tracks in the job list, so lets make sure its empty*/
+    int audiotrack_count = hb_list_count(job->list_audio);
+    for( int i = 0; i < audiotrack_count;i++)
+    {
+        hb_audio_t * temp_audio = (hb_audio_t*) hb_list_item( job->list_audio, 0 );
+        hb_list_rem(job->list_audio, temp_audio);
+    }
+    /* Now lets add our new tracks to the audio list here */
+    if ([[queueToApply objectForKey:@"Audio1Track"] intValue] > 0)
+    {
+        audio = (hb_audio_config_t *) calloc(1, sizeof(*audio));
+        hb_audio_config_init(audio);
+        audio->in.track = [[queueToApply objectForKey:@"Audio1Track"] intValue] - 1;
+        /* We go ahead and assign values to our audio->out.<properties> */
+        audio->out.track = [[queueToApply objectForKey:@"Audio1Track"] intValue] - 1;
+        audio->out.codec = [[queueToApply objectForKey:@"JobAudio1Encoder"] intValue];
+        audio->out.mixdown = [[queueToApply objectForKey:@"JobAudio1Mixdown"] intValue];
+        audio->out.bitrate = [[queueToApply objectForKey:@"JobAudio1Bitrate"] intValue];
+        audio->out.samplerate = [[queueToApply objectForKey:@"JobAudio1Samplerate"] intValue];
+        audio->out.dynamic_range_compression = [[queueToApply objectForKey:@"Audio1TrackDRCSlider"] floatValue];
+        
+        hb_audio_add( job, audio );
+        free(audio);
+    }  
+    if ([[queueToApply objectForKey:@"Audio2Track"] intValue] > 0)
+    {
+        
+        audio = (hb_audio_config_t *) calloc(1, sizeof(*audio));
+        hb_audio_config_init(audio);
+        audio->in.track = [[queueToApply objectForKey:@"Audio2Track"] intValue] - 1;
+        [self writeToActivityLog: "prepareJob audiotrack 2 is: %d", audio->in.track];
+        /* We go ahead and assign values to our audio->out.<properties> */
+        audio->out.track = [[queueToApply objectForKey:@"Audio2Track"] intValue] - 1;
+        audio->out.codec = [[queueToApply objectForKey:@"JobAudio2Encoder"] intValue];
+        audio->out.mixdown = [[queueToApply objectForKey:@"JobAudio2Mixdown"] intValue];
+        audio->out.bitrate = [[queueToApply objectForKey:@"JobAudio2Bitrate"] intValue];
+        audio->out.samplerate = [[queueToApply objectForKey:@"JobAudio2Samplerate"] intValue];
+        audio->out.dynamic_range_compression = [[queueToApply objectForKey:@"Audio2TrackDRCSlider"] floatValue];
+        
+        hb_audio_add( job, audio );
+        free(audio);
+    }
+    
+    if ([[queueToApply objectForKey:@"Audio3Track"] intValue] > 0)
+    {
+        audio = (hb_audio_config_t *) calloc(1, sizeof(*audio));
+        hb_audio_config_init(audio);
+        audio->in.track = [[queueToApply objectForKey:@"Audio3Track"] intValue] - 1;
+        /* We go ahead and assign values to our audio->out.<properties> */
+        audio->out.track = [[queueToApply objectForKey:@"Audio3Track"] intValue] - 1;
+        audio->out.codec = [[queueToApply objectForKey:@"JobAudio3Encoder"] intValue];
+        audio->out.mixdown = [[queueToApply objectForKey:@"JobAudio3Mixdown"] intValue];
+        audio->out.bitrate = [[queueToApply objectForKey:@"JobAudio3Bitrate"] intValue];
+        audio->out.samplerate = [[queueToApply objectForKey:@"JobAudio3Samplerate"] intValue];
+        audio->out.dynamic_range_compression = [[queueToApply objectForKey:@"Audio3TrackDRCSlider"] floatValue];
+        
+        hb_audio_add( job, audio );
+        free(audio);        
+    }
+    
+    if ([[queueToApply objectForKey:@"Audio4Track"] intValue] > 0)
+    {
+        audio = (hb_audio_config_t *) calloc(1, sizeof(*audio));
+        hb_audio_config_init(audio);
+        audio->in.track = [[queueToApply objectForKey:@"Audio4Track"] intValue] - 1;
+        /* We go ahead and assign values to our audio->out.<properties> */
+        audio->out.track = [[queueToApply objectForKey:@"Audio4Track"] intValue] - 1;
+        audio->out.codec = [[queueToApply objectForKey:@"JobAudio4Encoder"] intValue];
+        audio->out.mixdown = [[queueToApply objectForKey:@"JobAudio4Mixdown"] intValue];
+        audio->out.bitrate = [[queueToApply objectForKey:@"JobAudio4Bitrate"] intValue];
+        audio->out.samplerate = [[queueToApply objectForKey:@"JobAudio4Samplerate"] intValue];
+        audio->out.dynamic_range_compression = [[queueToApply objectForKey:@"Audio4TrackDRCSlider"] floatValue];
+        
+        hb_audio_add( job, audio );
+        free(audio);
+    }
+    
+    /* Filters */ 
     job->filters = hb_list_init();
-   
-       /* Detelecine */
-    if ([fPictureController detelecine])
+    
+    /* Now lets call the filters if applicable.
+     * The order of the filters is critical
+     */
+    /* Detelecine */
+    if ([[queueToApply objectForKey:@"PictureDetelecine"] intValue] == 1)
     {
         hb_list_add( job->filters, &hb_filter_detelecine );
     }
-   
+    
+    /* Decomb */
+    if ([[queueToApply objectForKey:@"PictureDecomb"] intValue] == 1)
+    {
+        /* Run old deinterlacer fd by default */
+        hb_filter_decomb.settings = (char *) [[queueToApply objectForKey:@"JobPictureDecomb"] UTF8String];
+        hb_list_add( job->filters, &hb_filter_decomb );
+    }
+    
     /* Deinterlace */
-    if ([fPictureController deinterlace] == 1)
+    if ([[queueToApply objectForKey:@"PictureDeinterlace"] intValue] == 1)
     {
         /* Run old deinterlacer fd by default */
         hb_filter_deinterlace.settings = "-1"; 
         hb_list_add( job->filters, &hb_filter_deinterlace );
     }
-    else if ([fPictureController deinterlace] == 2)
+    else if ([[queueToApply objectForKey:@"PictureDeinterlace"] intValue] == 2)
     {
         /* Yadif mode 0 (without spatial deinterlacing.) */
         hb_filter_deinterlace.settings = "2"; 
         hb_list_add( job->filters, &hb_filter_deinterlace );            
     }
-    else if ([fPictureController deinterlace] == 3)
+    else if ([[queueToApply objectForKey:@"PictureDeinterlace"] intValue] == 3)
     {
         /* Yadif (with spatial deinterlacing) */
         hb_filter_deinterlace.settings = "0"; 
         hb_list_add( job->filters, &hb_filter_deinterlace );            
     }
        
-       /* Denoise */
-       
-       if ([fPictureController denoise] == 1) // Weak in popup
+    /* Denoise */
+       if ([[queueToApply objectForKey:@"PictureDenoise"] intValue] == 1) // Weak in popup
        {
                hb_filter_denoise.settings = "2:1:2:3"; 
         hb_list_add( job->filters, &hb_filter_denoise );       
        }
-       else if ([fPictureController denoise] == 2) // Medium in popup
+       else if ([[queueToApply objectForKey:@"PictureDenoise"] intValue] == 2) // Medium in popup
        {
                hb_filter_denoise.settings = "3:2:2:3"; 
         hb_list_add( job->filters, &hb_filter_denoise );       
        }
-       else if ([fPictureController denoise] == 3) // Strong in popup
+       else if ([[queueToApply objectForKey:@"PictureDenoise"] intValue] == 3) // Strong in popup
        {
                hb_filter_denoise.settings = "7:7:5:5"; 
         hb_list_add( job->filters, &hb_filter_denoise );       
        }
     
     /* Deblock  (uses pp7 default) */
-    if ([fPictureController deblock])
+    /* NOTE: even though there is a valid deblock setting of 0 for the filter, for 
+     * the macgui's purposes a value of 0 actually means to not even use the filter
+     * current hb_filter_deblock.settings valid ranges are from 5 - 15 
+     */
+    if ([[queueToApply objectForKey:@"PictureDeblock"] intValue] != 0)
     {
+        hb_filter_deblock.settings = (char *) [[queueToApply objectForKey:@"PictureDeblock"] UTF8String];
         hb_list_add( job->filters, &hb_filter_deblock );
     }
-
+[self writeToActivityLog: "prepareJob exiting"];    
 }
 
 
@@ -1675,28 +2887,14 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
        if( [[NSFileManager defaultManager] fileExistsAtPath:
             [fDstFile2Field stringValue]] )
     {
-        NSBeginCriticalAlertSheet( _( @"File already exists" ),
-            _( @"Cancel" ), _( @"Overwrite" ), NULL, fWindow, self,
-            @selector( overwriteAddToQueueAlertDone:returnCode:contextInfo: ),
-            NULL, NULL, [NSString stringWithFormat:
-            _( @"Do you want to overwrite %@?" ),
-            [fDstFile2Field stringValue]] );
-        // overwriteAddToQueueAlertDone: will be called when the alert is dismissed.
-    }
-    
-    // Warn if another pending job in the queue has the same destination path
-    else if ( ([fQueueController pendingJobGroupWithDestinationPath:[fDstFile2Field stringValue]] != nil)
-            || ([[[fQueueController currentJobGroup] destinationPath] isEqualToString: [fDstFile2Field stringValue]]) )
-    {
-        NSBeginCriticalAlertSheet( _( @"Another queued encode has specified the same destination." ),
-            _( @"Cancel" ), _( @"Overwrite" ), NULL, fWindow, self,
+        NSBeginCriticalAlertSheet( NSLocalizedString( @"File already exists", @"" ),
+            NSLocalizedString( @"Cancel", @"" ), NSLocalizedString( @"Overwrite", @"" ), nil, fWindow, self,
             @selector( overwriteAddToQueueAlertDone:returnCode:contextInfo: ),
             NULL, NULL, [NSString stringWithFormat:
-            _( @"Do you want to overwrite %@?" ),
+            NSLocalizedString( @"Do you want to overwrite %@?", @"" ),
             [fDstFile2Field stringValue]] );
         // overwriteAddToQueueAlertDone: will be called when the alert is dismissed.
     }
-    
     else
     {
         [self doAddToQueue];
@@ -1715,174 +2913,76 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
 
 - (void) doAddToQueue
 {
-    hb_list_t  * list  = hb_get_titles( fHandle );
-    hb_title_t * title = (hb_title_t *) hb_list_item( list, [fSrcTitlePopUp indexOfSelectedItem] );
-    hb_job_t * job = title->job;
-
-    // Create a Queue Controller job group. Each job that we submit to libhb will also
-    // get added to the job group so that the queue can track the jobs.
-    HBJobGroup * jobGroup = [HBJobGroup jobGroup];
-    // The job group can maintain meta data that libhb can not...
-    [jobGroup setPresetName: [fPresetSelectedDisplay stringValue]];
-
-    // Job groups require that each job within the group be assigned a unique id so
-    // that the queue can xref between itself and the private jobs that libhb
-    // maintains. The ID is composed a group id number and a "sequence" number. libhb
-    // does not use this id.
-    static int jobGroupID = 0;
-    jobGroupID++;
-    
-    // A sequence number, starting at zero, is used to identifiy to each pass. This is
-    // used by the queue UI to determine if a pass if the first pass of an encode.
-    int sequenceNum = -1;
-    
-    [self prepareJob];
-
-    /* Destination file */
-    job->file = [[fDstFile2Field stringValue] UTF8String];
-
-    if( [fSubForcedCheck state] == NSOnState )
-        job->subtitle_force = 1;
-    else
-        job->subtitle_force = 0;
-
-    /*
-    * subtitle of -1 is a scan
-    */
-    if( job->subtitle == -1 )
-    {
-        char *x264opts_tmp;
-
-        /*
-        * When subtitle scan is enabled do a fast pre-scan job
-        * which will determine which subtitles to enable, if any.
-        */
-        job->pass = -1;
-        x264opts_tmp = job->x264opts;
-        job->subtitle = -1;
-
-        job->x264opts = NULL;
-
-        job->indepth_scan = 1;  
-
-        job->select_subtitle = (hb_subtitle_t**)malloc(sizeof(hb_subtitle_t*));
-        *(job->select_subtitle) = NULL;
-
-        /*
-        * Add the pre-scan job
-        */
-        job->sequence_id = MakeJobID(jobGroupID, ++sequenceNum);
-        hb_add( fHandle, job );
-        [jobGroup addJob:[HBJob jobWithLibhbJob:job]];     // add this pass to the job group
-
-        job->x264opts = x264opts_tmp;
-    }
-    else
-        job->select_subtitle = NULL;
-
-    /* No subtitle were selected, so reset the subtitle to -1 (which before
-    * this point meant we were scanning
-    */
-    if( job->subtitle == -2 )
-        job->subtitle = -1;
-
-    if( [fVidTwoPassCheck state] == NSOnState )
-    {
-        hb_subtitle_t **subtitle_tmp = job->select_subtitle;
-        job->indepth_scan = 0;
-
-        /*
-         * Do not autoselect subtitles on the first pass of a two pass
-         */
-        job->select_subtitle = NULL;
-        
-        job->pass = 1;
-        job->sequence_id = MakeJobID(jobGroupID, ++sequenceNum);
-        hb_add( fHandle, job );
-        [jobGroup addJob:[HBJob jobWithLibhbJob:job]];     // add this pass to the job group
-
-        job->pass = 2;
-        job->sequence_id = MakeJobID(jobGroupID, ++sequenceNum);
-
-        job->x264opts = (char *)calloc(1024, 1); /* Fixme, this just leaks */  
-        strcpy(job->x264opts, [[fAdvancedOptions optionsString] UTF8String]);
+    [self addQueueFileItem ];
+}
 
-        job->select_subtitle = subtitle_tmp;
 
-        hb_add( fHandle, job );
-        [jobGroup addJob:[HBJob jobWithLibhbJob:job]];     // add this pass to the job group
-    }
-    else
-    {
-        job->indepth_scan = 0;
-        job->pass = 0;
-        job->sequence_id = MakeJobID(jobGroupID, ++sequenceNum);
-        hb_add( fHandle, job );
-        [jobGroup addJob:[HBJob jobWithLibhbJob:job]];     // add this pass to the job group
-    }
-       
-    NSString *destinationDirectory = [[fDstFile2Field stringValue] stringByDeletingLastPathComponent];
-       [[NSUserDefaults standardUserDefaults] setObject:destinationDirectory forKey:@"LastDestinationDirectory"];
-       
-    // Let the queue controller know about the job group
-    [fQueueController addJobGroup:jobGroup];
-}
 
 /* Rip: puts up an alert before ultimately calling doRip
 */
 - (IBAction) Rip: (id) sender
 {
+    [self writeToActivityLog: "Rip: Pending queue count is %d", fPendingCount];
     /* Rip or Cancel ? */
     hb_state_t s;
-    hb_get_state2( fHandle, &s );
-
+    hb_get_state2( fQueueEncodeLibhb, &s );
+    
     if(s.state == HB_STATE_WORKING || s.state == HB_STATE_PAUSED)
        {
         [self Cancel: sender];
         return;
     }
     
-    // If there are jobs in the queue, then this is a rip the queue
+    /* We check to see if we need to warn the user that the computer will go to sleep
+                 or shut down when encoding is finished */
+                [self remindUserOfSleepOrShutdown];
     
-    if (hb_count( fHandle ) > 0)
+    // If there are pending jobs in the queue, then this is a rip the queue
+    if (fPendingCount > 0)
     {
-        [self doRip];
+        /* here lets start the queue with the first pending item */
+        [self performNewQueueScan:[[QueueFileArray objectAtIndex:currentQueueEncodeIndex] objectForKey:@"SourcePath"] scanTitleNum:[[[QueueFileArray objectAtIndex:currentQueueEncodeIndex] objectForKey:@"TitleNumber"]intValue]]; 
+        
         return;
     }
-
+    
     // Before adding jobs to the queue, check for a valid destination.
-
+    
     NSString *destinationDirectory = [[fDstFile2Field stringValue] stringByDeletingLastPathComponent];
     if ([[NSFileManager defaultManager] fileExistsAtPath:destinationDirectory] == 0) 
     {
         NSRunAlertPanel(@"Warning!", @"This is not a valid destination directory!", @"OK", nil, nil);
         return;
     }
-
+    
     /* We check for duplicate name here */
     if( [[NSFileManager defaultManager] fileExistsAtPath:[fDstFile2Field stringValue]] )
     {
-        NSBeginCriticalAlertSheet( _( @"File already exists" ),
-            _( @"Cancel" ), _( @"Overwrite" ), NULL, fWindow, self,
-            @selector( overWriteAlertDone:returnCode:contextInfo: ),
-            NULL, NULL, [NSString stringWithFormat:
-            _( @"Do you want to overwrite %@?" ),
-            [fDstFile2Field stringValue]] );
-            
+        NSBeginCriticalAlertSheet( NSLocalizedString( @"File already exists", @"" ),
+                                  NSLocalizedString( @"Cancel", "" ), NSLocalizedString( @"Overwrite", @"" ), nil, fWindow, self,
+                                  @selector( overWriteAlertDone:returnCode:contextInfo: ),
+                                  NULL, NULL, [NSString stringWithFormat:
+                                               NSLocalizedString( @"Do you want to overwrite %@?", @"" ),
+                                               [fDstFile2Field stringValue]] );
+        
         // overWriteAlertDone: will be called when the alert is dismissed. It will call doRip.
     }
     else
     {
-        /* if there are no jobs in the queue, then add this one to the queue and rip 
-        otherwise, just rip the queue */
-        if( hb_count( fHandle ) == 0)
+        /* if there are no pending jobs in the queue, then add this one to the queue and rip
+         otherwise, just rip the queue */
+        if(fPendingCount == 0)
         {
-            [self doAddToQueue];
+         [self writeToActivityLog: "Rip: No pending jobs, so sending this one to doAddToQueue"];
+               [self doAddToQueue];
         }
-
+        
         NSString *destinationDirectory = [[fDstFile2Field stringValue] stringByDeletingLastPathComponent];
         [[NSUserDefaults standardUserDefaults] setObject:destinationDirectory forKey:@"LastDestinationDirectory"];
-        [self doRip];
+        /* go right to processing the new queue encode */
+       [self writeToActivityLog: "Rip: Going right to performNewQueueScan"];
+         [self performNewQueueScan:[[QueueFileArray objectAtIndex:currentQueueEncodeIndex] objectForKey:@"SourcePath"] scanTitleNum:[[[QueueFileArray objectAtIndex:currentQueueEncodeIndex] objectForKey:@"TitleNumber"]intValue]]; 
+        
     }
 }
 
@@ -1896,14 +2996,15 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     {
         /* if there are no jobs in the queue, then add this one to the queue and rip 
         otherwise, just rip the queue */
-        if( hb_count( fHandle ) == 0 )
+        if( fPendingCount == 0 )
         {
             [self doAddToQueue];
         }
 
         NSString *destinationDirectory = [[fDstFile2Field stringValue] stringByDeletingLastPathComponent];
         [[NSUserDefaults standardUserDefaults] setObject:destinationDirectory forKey:@"LastDestinationDirectory"];
-        [self doRip];
+        [self performNewQueueScan:[[QueueFileArray objectAtIndex:currentQueueEncodeIndex] objectForKey:@"SourcePath"] scanTitleNum:[[[QueueFileArray objectAtIndex:currentQueueEncodeIndex] objectForKey:@"TitleNumber"]intValue]]; 
+      
     }
 }
 
@@ -1916,11 +3017,11 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
                NSBeep();
                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);
                [NSApp requestUserAttention:NSCriticalRequest];
-               if ( reminduser == NSAlertAlternateReturn ) 
+               if ( reminduser == NSAlertAlternateReturn )
                {
-                       [self showPreferencesWindow:NULL];
+                       [self showPreferencesWindow:nil];
                }
-       } 
+       }
        else if ([[[NSUserDefaults standardUserDefaults] stringForKey:@"AlertWhenDone"] isEqualToString: @"Shut Down Computer"])
        {
                /*Warn that computer will shut down after encoding*/
@@ -1928,9 +3029,9 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
                NSBeep();
                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);
                [NSApp requestUserAttention:NSCriticalRequest];
-               if ( reminduser == NSAlertAlternateReturn ) 
+               if ( reminduser == NSAlertAlternateReturn )
                {
-                       [self showPreferencesWindow:NULL];
+                       [self showPreferencesWindow:nil];
                }
        }
 
@@ -1940,24 +3041,12 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
 - (void) doRip
 {
     /* Let libhb do the job */
-    hb_start( fHandle );
-       /*set the fEncodeState State */
+    hb_start( fQueueEncodeLibhb );
+    /*set the fEncodeState State */
        fEncodeState = 1;
 }
 
 
-
-
-//------------------------------------------------------------------------------------
-// Removes all jobs from the queue. Does not cancel the current processing job.
-//------------------------------------------------------------------------------------
-- (void) doDeleteQueuedJobs
-{
-    hb_job_t * job;
-    while( ( job = hb_job( fHandle, 0 ) ) )
-        hb_rem( fHandle, job );
-}
-
 //------------------------------------------------------------------------------------
 // Cancels and deletes the current job and stops libhb from processing the remaining
 // encodes.
@@ -1970,10 +3059,32 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     // remaining passes of the job and then start the queue back up if there are any
     // remaining jobs.
      
-    [fQueueController libhbWillStop];
-    hb_stop( fHandle );
+    
+    hb_stop( fQueueEncodeLibhb );
     fEncodeState = 2;   // don't alert at end of processing since this was a cancel
     
+    // now that we've stopped the currently encoding job, lets mark it as cancelled
+    [[QueueFileArray objectAtIndex:currentQueueEncodeIndex] setObject:[NSNumber numberWithInt:3] forKey:@"Status"];
+    // and as always, save it in the queue .plist...
+    /* We save all of the Queue data here */
+    [self saveQueueFileItem];
+    // so now lets move to 
+    currentQueueEncodeIndex++ ;
+    // ... and see if there are more items left in our queue
+    int queueItems = [QueueFileArray count];
+    /* If we still have more items in our queue, lets go to the next one */
+    if (currentQueueEncodeIndex < queueItems)
+    {
+    [self writeToActivityLog: "doCancelCurrentJob currentQueueEncodeIndex is incremented to: %d", currentQueueEncodeIndex];
+    [self writeToActivityLog: "doCancelCurrentJob moving to the next job"];
+    
+    [self performNewQueueScan:[[QueueFileArray objectAtIndex:currentQueueEncodeIndex] objectForKey:@"SourcePath"] scanTitleNum:[[[QueueFileArray objectAtIndex:currentQueueEncodeIndex] objectForKey:@"TitleNumber"]intValue]];
+    }
+    else
+    {
+        [self writeToActivityLog: "doCancelCurrentJob the item queue is complete"];
+    }
+
 }
 
 //------------------------------------------------------------------------------------
@@ -1983,14 +3094,11 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
 //------------------------------------------------------------------------------------
 - (IBAction)Cancel: (id)sender
 {
-    if (!fHandle) return;
-    
-    HBJobGroup * jobGroup = [fQueueController currentJobGroup];
-    if (!jobGroup) return;
-
-    NSString * alertTitle = [NSString stringWithFormat:NSLocalizedString(@"Stop encoding %@?", nil),
-            [jobGroup name]];
+    if (!fQueueController) return;
     
+  hb_pause( fQueueEncodeLibhb );
+    NSString * alertTitle = [NSString stringWithFormat:NSLocalizedString(@"You are currently encoding. What would you like to do ?", nil)];
+   
     // Which window to attach the sheet to?
     NSWindow * docWindow;
     if ([sender respondsToSelector: @selector(window)])
@@ -2000,38 +3108,55 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
         
     NSBeginCriticalAlertSheet(
             alertTitle,
-            NSLocalizedString(@"Keep Encoding", nil),
-            nil,
-            NSLocalizedString(@"Stop Encoding", nil),
+            NSLocalizedString(@"Continue Encoding", nil),
+            NSLocalizedString(@"Cancel Current and Stop", nil),
+            NSLocalizedString(@"Cancel Current and Continue", nil),
             docWindow, self,
-            nil, @selector(didDimissCancelCurrentJob:returnCode:contextInfo:), nil,
-            NSLocalizedString(@"Your movie will be lost if you don't continue encoding.", nil));
+            nil, @selector(didDimissCancel:returnCode:contextInfo:), nil,
+            NSLocalizedString(@"Your encode will be cancelled if you don't continue encoding.", nil));
     
     // didDimissCancelCurrentJob:returnCode:contextInfo: will be called when the dialog is dismissed
 }
 
-- (void) didDimissCancelCurrentJob: (NSWindow *)sheet returnCode: (int)returnCode contextInfo: (void *)contextInfo
+- (void) didDimissCancel: (NSWindow *)sheet returnCode: (int)returnCode contextInfo: (void *)contextInfo
 {
-    if (returnCode == NSAlertOtherReturn)
+   hb_resume( fQueueEncodeLibhb );
+     if (returnCode == NSAlertOtherReturn)
+    {
         [self doCancelCurrentJob];  // <- this also stops libhb
+    }
+    if (returnCode == NSAlertAlternateReturn)
+    {
+    [self doCancelCurrentJobAndStop];
+    }
 }
 
-
-
-
-
+- (void) doCancelCurrentJobAndStop
+{
+    hb_stop( fQueueEncodeLibhb );
+    fEncodeState = 2;   // don't alert at end of processing since this was a cancel
+    
+    // now that we've stopped the currently encoding job, lets mark it as cancelled
+    [[QueueFileArray objectAtIndex:currentQueueEncodeIndex] setObject:[NSNumber numberWithInt:3] forKey:@"Status"];
+    // and as always, save it in the queue .plist...
+    /* We save all of the Queue data here */
+    [self saveQueueFileItem];
+    // so now lets move to 
+    currentQueueEncodeIndex++ ;
+    [self writeToActivityLog: "cancelling current job and stopping the queue"];
+}
 - (IBAction) Pause: (id) sender
 {
     hb_state_t s;
-    hb_get_state2( fHandle, &s );
+    hb_get_state2( fQueueEncodeLibhb, &s );
 
     if( s.state == HB_STATE_PAUSED )
     {
-        hb_resume( fHandle );
+        hb_resume( fQueueEncodeLibhb );
     }
     else
     {
-        hb_pause( fHandle );
+        hb_pause( fQueueEncodeLibhb );
     }
 }
 
@@ -2043,15 +3168,14 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     hb_list_t  * list  = hb_get_titles( fHandle );
     hb_title_t * title = (hb_title_t*)
         hb_list_item( list, [fSrcTitlePopUp indexOfSelectedItem] );
-               
-               
+
     /* If Auto Naming is on. We create an output filename of dvd name - title number */
-    if ([[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultAutoNaming"] > 0)
+    if( [[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultAutoNaming"] > 0 && ( hb_list_count( list ) > 1 ) )
        {
                [fDstFile2Field setStringValue: [NSString stringWithFormat:
                        @"%@/%@-%d.%@", [[fDstFile2Field stringValue] stringByDeletingLastPathComponent],
-                       browsedSourceDisplayName,
-                         title->index,
+                       [browsedSourceDisplayName stringByDeletingPathExtension],
+            title->index,
                        [[fDstFile2Field stringValue] pathExtension]]]; 
        }
 
@@ -2065,24 +3189,16 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
         [fSrcChapterEndPopUp addItemWithTitle: [NSString
             stringWithFormat: @"%d", i + 1]];
     }
+
     [fSrcChapterStartPopUp selectItemAtIndex: 0];
     [fSrcChapterEndPopUp   selectItemAtIndex:
         hb_list_count( title->list_chapter ) - 1];
-    [self chapterPopUpChanged: NULL];
+    [self chapterPopUpChanged:nil];
 
-/* Start Get and set the initial pic size for display */
+    /* Start Get and set the initial pic size for display */
        hb_job_t * job = title->job;
-       fTitle = title; 
+       fTitle = title;
 
-       /* Pixel Ratio Setting */
-       if ([[NSUserDefaults standardUserDefaults] boolForKey:@"PixelRatio"])
-    {
-               job->pixel_ratio = 1 ;
-       }
-       else
-       {
-               job->pixel_ratio = 0 ;
-       }
        /*Set Source Size Field Here */
     [fPicSettingsSrc setStringValue: [NSString stringWithFormat: @"%d x %d", fTitle->width, fTitle->height]];
        
@@ -2118,81 +3234,52 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
             subtitle->lang] action: NULL keyEquivalent: @""];
     }
     [fSubPopUp selectItemAtIndex: 0];
-       
-       [self subtitleSelectionChanged: NULL];
-    
+
+       [self subtitleSelectionChanged:nil];
+
     /* Update chapter table */
     [fChapterTitlesDelegate resetWithTitle:title];
     [fChapterTable reloadData];
 
+   /* Lets make sure there arent any erroneous audio tracks in the job list, so lets make sure its empty*/
+    int audiotrack_count = hb_list_count(job->list_audio);
+    for( int i = 0; i < audiotrack_count;i++)
+    {
+        hb_audio_t * temp_audio = (hb_audio_t*) hb_list_item( job->list_audio, 0 );
+        hb_list_rem(job->list_audio, temp_audio);
+    }
+
     /* Update audio popups */
     [self addAllAudioTracksToPopUp: fAudLang1PopUp];
     [self addAllAudioTracksToPopUp: fAudLang2PopUp];
+    [self addAllAudioTracksToPopUp: fAudLang3PopUp];
+    [self addAllAudioTracksToPopUp: fAudLang4PopUp];
     /* search for the first instance of our prefs default language for track 1, and set track 2 to "none" */
        NSString * audioSearchPrefix = [[NSUserDefaults standardUserDefaults] stringForKey:@"DefaultLanguage"];
         [self selectAudioTrackInPopUp: fAudLang1PopUp searchPrefixString: audioSearchPrefix selectIndexIfNotFound: 1];
-    [self selectAudioTrackInPopUp: fAudLang2PopUp searchPrefixString: NULL selectIndexIfNotFound: 0];
-       
+    [self selectAudioTrackInPopUp:fAudLang2PopUp searchPrefixString:nil selectIndexIfNotFound:0];
+    [self selectAudioTrackInPopUp:fAudLang3PopUp searchPrefixString:nil selectIndexIfNotFound:0];
+    [self selectAudioTrackInPopUp:fAudLang4PopUp searchPrefixString:nil selectIndexIfNotFound:0];
+
        /* changing the title may have changed the audio channels on offer, */
        /* so call audioTrackPopUpChanged for both audio tracks to update the mixdown popups */
        [self audioTrackPopUpChanged: fAudLang1PopUp];
        [self audioTrackPopUpChanged: fAudLang2PopUp];
-    
-    /* We repopulate the Video Framerate popup and show the detected framerate along with "Same as Source"*/
-    [fVidRatePopUp removeAllItems];
-    if (fTitle->rate_base == 1126125) // 23.976 NTSC Film
-    {
-        [fVidRatePopUp addItemWithTitle: @"Same as source (23.976)"];
-    }
-    else if (fTitle->rate_base == 1080000) // 25 PAL Film/Video
-    {
-        [fVidRatePopUp addItemWithTitle: @"Same as source (25)"];
-    }
-    else if (fTitle->rate_base == 900900) // 29.97 NTSC Video
-    {
-        [fVidRatePopUp addItemWithTitle: @"Same as source (29.97)"];
-    }
-    else
-    {
-        /* if none of the common dvd source framerates is detected, just use "Same as source" */
-        [fVidRatePopUp addItemWithTitle: @"Same as source"];
-    }
-       for( int i = 0; i < hb_video_rates_count; i++ )
-    {
-        if ([[NSString stringWithCString: hb_video_rates[i].string] isEqualToString: [NSString stringWithFormat: @"%.3f",23.976]])
-               {
-                       [fVidRatePopUp addItemWithTitle:[NSString stringWithFormat: @"%@%@",
-                               [NSString stringWithCString: hb_video_rates[i].string], @" (NTSC Film)"]];
-               }
-               else if ([[NSString stringWithCString: hb_video_rates[i].string] isEqualToString: [NSString stringWithFormat: @"%d",25]])
-               {
-                       [fVidRatePopUp addItemWithTitle:[NSString stringWithFormat: @"%@%@",
-                               [NSString stringWithCString: hb_video_rates[i].string], @" (PAL Film/Video)"]];
-               }
-               else if ([[NSString stringWithCString: hb_video_rates[i].string] isEqualToString: [NSString stringWithFormat: @"%.2f",29.97]])
-               {
-                       [fVidRatePopUp addItemWithTitle:[NSString stringWithFormat: @"%@%@",
-                               [NSString stringWithCString: hb_video_rates[i].string], @" (NTSC Video)"]];
-               }
-               else
-               {
-                       [fVidRatePopUp addItemWithTitle:
-                               [NSString stringWithCString: hb_video_rates[i].string]];
-               }
-    }   
+    [self audioTrackPopUpChanged: fAudLang3PopUp];
+    [self audioTrackPopUpChanged: fAudLang4PopUp];
+
     [fVidRatePopUp selectItemAtIndex: 0];
-    
+
     /* we run the picture size values through calculatePictureSizing to get all picture setting        information*/
-       [self calculatePictureSizing: NULL];
-    
+       [self calculatePictureSizing:nil];
+
    /* lets call tableViewSelected to make sure that any preset we have selected is enforced after a title change */
-       [self selectPreset:NULL]; 
-       
+       [self selectPreset:nil];
 }
 
 - (IBAction) chapterPopUpChanged: (id) sender
 {
-    
+
        /* If start chapter popup is greater than end chapter popup,
        we set the end chapter popup to the same as start chapter popup */
        if ([fSrcChapterStartPopUp indexOfSelectedItem] > [fSrcChapterEndPopUp indexOfSelectedItem])
@@ -2225,7 +3312,6 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
 - (IBAction) formatPopUpChanged: (id) sender
 {
     NSString * string = [fDstFile2Field stringValue];
-    NSString * selectedCodecs = [fDstCodecsPopUp titleOfSelectedItem];
     int format = [fDstFormatPopUp indexOfSelectedItem];
     char * ext = NULL;
        /* Initially set the large file (64 bit formatting) output checkbox to hidden */
@@ -2233,8 +3319,16 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
     [fDstMp4HttpOptFileCheck setHidden: YES];
     [fDstMp4iPodFileCheck setHidden: YES];
     
-    /* Update the codecs popup */
-    [fDstCodecsPopUp removeAllItems];
+    /* Update the Video Codec PopUp */
+    /* Note: we now store the video encoder int values from common.c in the tags of each popup for easy retrieval later */
+    [fVidEncoderPopUp removeAllItems];
+    NSMenuItem *menuItem;
+    /* These video encoders are available to all of our current muxers, so lets list them once here */
+    menuItem = [[fVidEncoderPopUp menu] addItemWithTitle:@"MPEG-4 (FFmpeg)" action: NULL keyEquivalent: @""];
+    [menuItem setTag: HB_VCODEC_FFMPEG];
+    
+    menuItem = [[fVidEncoderPopUp menu] addItemWithTitle:@"MPEG-4 (XviD)" action: NULL keyEquivalent: @""];
+    [menuItem setTag: HB_VCODEC_XVID];
     switch( format )
     {
         case 0:
@@ -2247,165 +3341,156 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
                        {
                                ext = "mp4";
                        }
-            
-            [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / AAC Audio" )];
-            [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / AAC Audio" )];
-            /* We add a new codecs entry which will allow the new aac/ ac3 hybrid */
-            [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / AAC + AC3 Audio" )];
-            [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / AC3 Audio" )];
-                       /* We enable the create chapters checkbox here since we are .mp4*/
-                       [fCreateChapterMarkers setEnabled: YES];
-                       /* We show the Large File (64 bit formatting) checkbox since we are .mp4 
-             if we have enabled the option in the global preferences*/
-                       if ([[NSUserDefaults standardUserDefaults] boolForKey:@"AllowLargeFiles"] > 0)
-                       {
-                               [fDstMp4LargeFileCheck setHidden: NO];
-                       }
-            else
-            {
-                /* if not enable in global preferences, we additionaly sanity check that the
-                 hidden checkbox is set to off. */
-                [fDstMp4LargeFileCheck setState: NSOffState];
-            }
-            /* We show the HTTP Optimized checkbox here since we are mp4 */
-            [fDstMp4HttpOptFileCheck setHidden: NO];
+            /* Add additional video encoders here */
+            menuItem = [[fVidEncoderPopUp menu] addItemWithTitle:@"H.264 (x264)" action: NULL keyEquivalent: @""];
+            [menuItem setTag: HB_VCODEC_X264];
+            /* We show the mp4 option checkboxes here since we are mp4 */
+            [fCreateChapterMarkers setEnabled: YES];
+                       [fDstMp4LargeFileCheck setHidden: NO];
+                       [fDstMp4HttpOptFileCheck setHidden: NO];
             [fDstMp4iPodFileCheck setHidden: NO];
             break;
             
-        case 1:
+            case 1:
             ext = "mkv";
-            [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / AAC Audio" )];
-            [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / AC-3 Audio" )];
-                       [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / MP3 Audio" )];
-                       [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / Vorbis Audio" )];
-            
-                       [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / AAC Audio" )];
-                       [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / AC-3 Audio" )];
-                       [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / MP3 Audio" )];
-                       [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / Vorbis Audio" )];
+            /* Add additional video encoders here */
+            menuItem = [[fVidEncoderPopUp menu] addItemWithTitle:@"H.264 (x264)" action: NULL keyEquivalent: @""];
+            [menuItem setTag: HB_VCODEC_X264];
+            menuItem = [[fVidEncoderPopUp menu] addItemWithTitle:@"VP3 (Theora)" action: NULL keyEquivalent: @""];
+            [menuItem setTag: HB_VCODEC_THEORA];
             /* We enable the create chapters checkbox here */
                        [fCreateChapterMarkers setEnabled: YES];
                        break;
             
-        case 2: 
+            case 2: 
             ext = "avi";
-            [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / MP3 Audio" )];
-            [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / AC-3 Audio" )];
-            [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / MP3 Audio" )];
-            [fDstCodecsPopUp addItemWithTitle:_( @"AVC/H.264 Video / AC-3 Audio" )];
-                       /* We disable the create chapters checkbox here and make sure it is unchecked*/
+            /* Add additional video encoders here */
+            menuItem = [[fVidEncoderPopUp menu] addItemWithTitle:@"H.264 (x264)" action: NULL keyEquivalent: @""];
+            [menuItem setTag: HB_VCODEC_X264];
+            /* We disable the create chapters checkbox here and make sure it is unchecked*/
                        [fCreateChapterMarkers setEnabled: NO];
                        [fCreateChapterMarkers setState: NSOffState];
                        break;
             
-        case 3:
+            case 3:
             ext = "ogm";
-            [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / Vorbis Audio" )];
-            [fDstCodecsPopUp addItemWithTitle:_( @"MPEG-4 Video / MP3 Audio" )];
+            /* Add additional video encoders here */
+            menuItem = [[fVidEncoderPopUp menu] addItemWithTitle:@"VP3 (Theora)" action: NULL keyEquivalent: @""];
+            [menuItem setTag: HB_VCODEC_THEORA];
             /* We disable the create chapters checkbox here and make sure it is unchecked*/
                        [fCreateChapterMarkers setEnabled: NO];
                        [fCreateChapterMarkers setState: NSOffState];
                        break;
     }
-    
-    if ( SuccessfulScan ) {
-        [fDstCodecsPopUp selectItemWithTitle:selectedCodecs];
-        
+    [fVidEncoderPopUp selectItemAtIndex: 0];
+
+    [self audioAddAudioTrackCodecs: fAudTrack1CodecPopUp];
+    [self audioAddAudioTrackCodecs: fAudTrack2CodecPopUp];
+    [self audioAddAudioTrackCodecs: fAudTrack3CodecPopUp];
+    [self audioAddAudioTrackCodecs: fAudTrack4CodecPopUp];
+
+    if( format == 0 )
+        [self autoSetM4vExtension: sender];
+    else
+        [fDstFile2Field setStringValue: [NSString stringWithFormat:@"%@.%s", [string stringByDeletingPathExtension], ext]];
+
+    if( SuccessfulScan )
+    {
         /* Add/replace to the correct extension */
-        if( [string characterAtIndex: [string length] - 4] == '.' )
-        {
-            [fDstFile2Field setStringValue: [NSString stringWithFormat:
-                @"%@.%s", [string substringToIndex: [string length] - 4],
-                ext]];
-        }
-        else
-        {
-            [fDstFile2Field setStringValue: [NSString stringWithFormat:
-                @"%@.%s", string, ext]];
-        }
-        
-        if ( [fDstCodecsPopUp selectedItem] == NULL )
+        [self audioTrackPopUpChanged: fAudLang1PopUp];
+        [self audioTrackPopUpChanged: fAudLang2PopUp];
+        [self audioTrackPopUpChanged: fAudLang3PopUp];
+        [self audioTrackPopUpChanged: fAudLang4PopUp];
+
+        if( [fVidEncoderPopUp selectedItem] == nil )
         {
-            [fDstCodecsPopUp selectItemAtIndex:0];
-            [self codecsPopUpChanged: NULL];
-            
+
+            [fVidEncoderPopUp selectItemAtIndex:0];
+            [self videoEncoderPopUpChanged:nil];
+
             /* changing the format may mean that we can / can't offer mono or 6ch, */
             /* so call audioTrackPopUpChanged for both audio tracks to update the mixdown popups */
-            [self audioTrackPopUpChanged: fAudLang1PopUp];
-            [self audioTrackPopUpChanged: fAudLang2PopUp];
+
             /* We call the method to properly enable/disable turbo 2 pass */
             [self twoPassCheckboxChanged: sender];
             /* We call method method to change UI to reflect whether a preset is used or not*/
         }
     }
-    
-       [self customSettingUsed: sender];       
+       [self customSettingUsed: sender];
 }
 
-- (IBAction) codecsPopUpChanged: (id) sender
+- (IBAction) autoSetM4vExtension: (id) sender
 {
-    int format = [fDstFormatPopUp indexOfSelectedItem];
-    int codecs = [fDstCodecsPopUp indexOfSelectedItem];
-       
-    [fAdvancedOptions setHidden:YES];
+    if ( [fDstFormatPopUp indexOfSelectedItem] )
+        return;
 
-    /* Update the encoder popup*/
-    if( ( FormatSettings[format][codecs] & HB_VCODEC_X264 ) )
-    {
-        /* MPEG-4 -> H.264 */
-        [fVidEncoderPopUp removeAllItems];
-               [fVidEncoderPopUp addItemWithTitle: @"x264"];
-               [fVidEncoderPopUp selectItemAtIndex: 0];
-        [fAdvancedOptions setHidden:NO];
-        /* if MP4 format and [fDstCodecsPopUp indexOfSelectedItem] > 1 we know that the audio is going to be
-         * either aac + ac3 passthru, or just ac3 passthru so we need to make sure the output file extension is m4v
-         * otherwise Quicktime will not play it at all */
-        if ([fDstFormatPopUp indexOfSelectedItem] == 0 && [fDstCodecsPopUp indexOfSelectedItem] > 1)
-        {
-            NSString *newpath = [[[fDstFile2Field stringValue] stringByDeletingPathExtension] stringByAppendingPathExtension: @"m4v"];
-            [fDstFile2Field setStringValue: [NSString stringWithFormat:
-                                             @"%@", newpath]];
-        }
-    }
-    
-    else if( ( FormatSettings[format][codecs] & HB_VCODEC_FFMPEG ) )
-    {
-        /* H.264 -> MPEG-4 */
-        [fVidEncoderPopUp removeAllItems];
-        [fVidEncoderPopUp addItemWithTitle: @"FFmpeg"];
-        [fVidEncoderPopUp addItemWithTitle: @"XviD"];
-        [fVidEncoderPopUp selectItemAtIndex: 0];
-                               
-    }
+    NSString * extension = @"mp4";
 
-    if( FormatSettings[format][codecs] & HB_ACODEC_AC3 )
+    if( [[fAudTrack1CodecPopUp selectedItem] tag] == HB_ACODEC_AC3 || [[fAudTrack2CodecPopUp selectedItem] tag] == HB_ACODEC_AC3 ||
+                                                        [[fAudTrack3CodecPopUp selectedItem] tag] == HB_ACODEC_AC3 ||
+                                                        [[fAudTrack4CodecPopUp selectedItem] tag] == HB_ACODEC_AC3 ||
+                                                        [fCreateChapterMarkers state] == NSOnState ||
+                                                        [[NSUserDefaults standardUserDefaults] boolForKey:@"DefaultMpegName"] > 0 )
     {
-        /* AC-3 pass-through: disable samplerate and bitrate */
-        [fAudRatePopUp    setEnabled: NO];
-        [fAudBitratePopUp setEnabled: NO];
+        extension = @"m4v";
     }
+
+    if( [extension isEqualTo: [[fDstFile2Field stringValue] pathExtension]] )
+        return;
     else
-    {
-        [fAudRatePopUp    setEnabled: YES];
-        [fAudBitratePopUp setEnabled: YES];
-    }
-    /* changing the codecs on offer may mean that we can / can't offer mono or 6ch, */
-       /* so call audioTrackPopUpChanged for both audio tracks to update the mixdown popups */
-       [self audioTrackPopUpChanged: fAudLang1PopUp];
-       [self audioTrackPopUpChanged: fAudLang2PopUp];
-       [self encoderPopUpChanged: sender];
+        [fDstFile2Field setStringValue: [NSString stringWithFormat:@"%@.%@",
+                                    [[fDstFile2Field stringValue] stringByDeletingPathExtension], extension]];
+}
+
+- (void) shouldEnableHttpMp4CheckBox: (id) sender
+{
+    if( [[fAudTrack1CodecPopUp selectedItem] tag] == HB_ACODEC_AC3 || [[fAudTrack2CodecPopUp selectedItem] tag] == HB_ACODEC_AC3 ||
+                                                        [[fAudTrack3CodecPopUp selectedItem] tag] == HB_ACODEC_AC3 ||
+                                                        [[fAudTrack4CodecPopUp selectedItem] tag] == HB_ACODEC_AC3 )
+        [fDstMp4HttpOptFileCheck setEnabled: NO];
+    else
+        [fDstMp4HttpOptFileCheck setEnabled: YES];
+}
+        
+/* Method to determine if we should change the UI
+To reflect whether or not a Preset is being used or if
+the user is using "Custom" settings by determining the sender*/
+- (IBAction) customSettingUsed: (id) sender
+{
+       if ([sender stringValue])
+       {
+               /* Deselect the currently selected Preset if there is one*/
+               [fPresetsOutlineView deselectRow:[fPresetsOutlineView selectedRow]];
+               /* Change UI to show "Custom" settings are being used */
+               [fPresetSelectedDisplay setStringValue: @"Custom"];
 
+               curUserPresetChosenNum = nil;
+       }
+[self calculateBitrate:nil];
 }
 
-- (IBAction) encoderPopUpChanged: (id) sender
+
+#pragma mark -
+#pragma mark - Video
+
+- (IBAction) videoEncoderPopUpChanged: (id) sender
 {
     hb_job_t * job = fTitle->job;
+    int videoEncoder = [[fVidEncoderPopUp selectedItem] tag];
+    
+    [fAdvancedOptions setHidden:YES];
+    /* If we are using x264 then show the x264 advanced panel*/
+    if (videoEncoder == HB_VCODEC_X264)
+    {
+        [fAdvancedOptions setHidden:NO];
+        [self autoSetM4vExtension: sender];
+    }
     
     /* We need to set loose anamorphic as available depending on whether or not the ffmpeg encoder
     is being used as it borks up loose anamorphic .
     For convenience lets use the titleOfSelected index. Probably should revisit whether or not we want
     to use the index itself but this is easier */
-    if ([fVidEncoderPopUp titleOfSelectedItem] == @"FFmpeg")
+    if (videoEncoder == HB_VCODEC_FFMPEG)
     {
         if (job->pixel_ratio == 2)
         {
@@ -2429,34 +3514,11 @@ static NSString *        ChooseSourceIdentifier             = @"Choose Source It
        [self twoPassCheckboxChanged: sender];
 }
 
-/* Method to determine if we should change the UI
-To reflect whether or not a Preset is being used or if
-the user is using "Custom" settings by determining the sender*/
-- (IBAction) customSettingUsed: (id) sender
-{
-       if ([sender stringValue] != NULL)
-       {
-               /* Deselect the currently selected Preset if there is one*/
-               [fPresetsOutlineView deselectRow:[fPresetsOutlineView selectedRow]];
-               [[fPresetsActionMenu itemAtIndex:0] setEnabled: NO];
-               /* Change UI to show "Custom" settings are being used */
-               [fPresetSelectedDisplay setStringValue: @"Custom"];
-               
-               curUserPresetChosenNum = nil;
-       }
-
-}
-
-
-#pragma mark -
-#pragma mark - Video
 
 - (IBAction) twoPassCheckboxChanged: (id) sender
 {
        /* check to see if x264 is chosen */
-       int format = [fDstFormatPopUp indexOfSelectedItem];
-    int codecs = [fDstCodecsPopUp indexOfSelectedItem];
-       if( ( FormatSettings[format][codecs] & HB_VCODEC_X264 ) )
+       if([[fVidEncoderPopUp selectedItem] tag] == HB_VCODEC_X264)
     {
                if( [fVidTwoPassCheck state] == NSOnState)
                {
@@ -2531,14 +3593,14 @@ the user is using "Custom" settings by determining the sender*/
 - (IBAction) qualitySliderChanged: (id) sender
 {
     [fVidConstantCell setTitle: [NSString stringWithFormat:
-        _( @"Constant quality: %.0f %%" ), 100.0 *
+        NSLocalizedString( @"Constant quality: %.0f %%", @"" ), 100.0 *
         [fVidQualitySlider floatValue]]];
                [self customSettingUsed: sender];
 }
 
 - (void) controlTextDidChange: (NSNotification *) notification
 {
-    [self calculateBitrate: NULL];
+    [self calculateBitrate:nil];
 }
 
 - (IBAction) calculateBitrate: (id) sender
@@ -2552,11 +3614,98 @@ the user is using "Custom" settings by determining the sender*/
     hb_title_t * title = (hb_title_t *) hb_list_item( list,
             [fSrcTitlePopUp indexOfSelectedItem] );
     hb_job_t * job = title->job;
+    hb_audio_config_t * audio;
+    /* For  hb_calc_bitrate in addition to the Target Size in MB out of the
+     * Target Size Field, we also need the job info for the Muxer, the Chapters
+     * as well as all of the audio track info.
+     * This used to be accomplished by simply calling prepareJob here, however
+     * since the resilient queue sets the queue array values instead of the job
+     * values directly, we duplicate the old prepareJob code here for the variables
+     * needed
+     */
+    job->chapter_start = [fSrcChapterStartPopUp indexOfSelectedItem] + 1;
+    job->chapter_end = [fSrcChapterEndPopUp indexOfSelectedItem] + 1; 
+    job->mux = [[fDstFormatPopUp selectedItem] tag];
+    
+    /* Audio goes here */
+    int audiotrack_count = hb_list_count(job->list_audio);
+    for( int i = 0; i < audiotrack_count;i++)
+    {
+        hb_audio_t * temp_audio = (hb_audio_t*) hb_list_item( job->list_audio, 0 );
+        hb_list_rem(job->list_audio, temp_audio);
+    }
+    /* Now we need our audio info here for each track if applicable */
+    if ([fAudLang1PopUp indexOfSelectedItem] > 0)
+    {
+        audio = (hb_audio_config_t *) calloc(1, sizeof(*audio));
+        hb_audio_config_init(audio);
+        audio->in.track = [fAudLang1PopUp indexOfSelectedItem] - 1;
+        /* We go ahead and assign values to our audio->out.<properties> */
+        audio->out.track = [fAudLang1PopUp indexOfSelectedItem] - 1;
+        audio->out.codec = [[fAudTrack1CodecPopUp selectedItem] tag];
+        audio->out.mixdown = [[fAudTrack1MixPopUp selectedItem] tag];
+        audio->out.bitrate = [[fAudTrack1BitratePopUp selectedItem] tag];
+        audio->out.samplerate = [[fAudTrack1RatePopUp selectedItem] tag];
+        audio->out.dynamic_range_compression = [fAudTrack1DrcField floatValue];
+        
+        hb_audio_add( job, audio );
+        free(audio);
+    }  
+    if ([fAudLang2PopUp indexOfSelectedItem] > 0)
+    {
+        audio = (hb_audio_config_t *) calloc(1, sizeof(*audio));
+        hb_audio_config_init(audio);
+        audio->in.track = [fAudLang2PopUp indexOfSelectedItem] - 1;
+        /* We go ahead and assign values to our audio->out.<properties> */
+        audio->out.track = [fAudLang2PopUp indexOfSelectedItem] - 1;
+        audio->out.codec = [[fAudTrack2CodecPopUp selectedItem] tag];
+        audio->out.mixdown = [[fAudTrack2MixPopUp selectedItem] tag];
+        audio->out.bitrate = [[fAudTrack2BitratePopUp selectedItem] tag];
+        audio->out.samplerate = [[fAudTrack2RatePopUp selectedItem] tag];
+        audio->out.dynamic_range_compression = [fAudTrack2DrcField floatValue];
+        
+        hb_audio_add( job, audio );
+        free(audio);
+        
+    }
+    
+    if ([fAudLang3PopUp indexOfSelectedItem] > 0)
+    {
+        audio = (hb_audio_config_t *) calloc(1, sizeof(*audio));
+        hb_audio_config_init(audio);
+        audio->in.track = [fAudLang3PopUp indexOfSelectedItem] - 1;
+        /* We go ahead and assign values to our audio->out.<properties> */
+        audio->out.track = [fAudLang3PopUp indexOfSelectedItem] - 1;
+        audio->out.codec = [[fAudTrack3CodecPopUp selectedItem] tag];
+        audio->out.mixdown = [[fAudTrack3MixPopUp selectedItem] tag];
+        audio->out.bitrate = [[fAudTrack3BitratePopUp selectedItem] tag];
+        audio->out.samplerate = [[fAudTrack3RatePopUp selectedItem] tag];
+        audio->out.dynamic_range_compression = [fAudTrack3DrcField floatValue];
+        
+        hb_audio_add( job, audio );
+        free(audio);
+        
+    }
 
-    [self prepareJob];
-
-    [fVidBitrateField setIntValue: hb_calc_bitrate( job,
-            [fVidTargetSizeField intValue] )];
+    if ([fAudLang4PopUp indexOfSelectedItem] > 0)
+    {
+        audio = (hb_audio_config_t *) calloc(1, sizeof(*audio));
+        hb_audio_config_init(audio);
+        audio->in.track = [fAudLang4PopUp indexOfSelectedItem] - 1;
+        /* We go ahead and assign values to our audio->out.<properties> */
+        audio->out.track = [fAudLang4PopUp indexOfSelectedItem] - 1;
+        audio->out.codec = [[fAudTrack4CodecPopUp selectedItem] tag];
+        audio->out.mixdown = [[fAudTrack4MixPopUp selectedItem] tag];
+        audio->out.bitrate = [[fAudTrack4BitratePopUp selectedItem] tag];
+        audio->out.samplerate = [[fAudTrack4RatePopUp selectedItem] tag];
+        audio->out.dynamic_range_compression = [fAudTrack4DrcField floatValue];
+        
+        hb_audio_add( job, audio );
+        free(audio);
+        
+    }
+       
+[fVidBitrateField setIntValue: hb_calc_bitrate( job, [fVidTargetSizeField intValue] )];
 }
 
 #pragma mark -
@@ -2569,18 +3718,9 @@ the user is using "Custom" settings by determining the sender*/
 - (IBAction) revertPictureSizeToMax: (id) sender
 {
        hb_job_t * job = fTitle->job;
-       /* We use the output picture width and height
-     as calculated from libhb right after title is set
-     in TitlePopUpChanged */
-       job->width = PicOrigOutputWidth;
-       job->height = PicOrigOutputHeight;
-    [fPictureController setAutoCrop:YES];
-       /* Here we use the auto crop values determined right after scan */
-       job->crop[0] = AutoCropTop;
-       job->crop[1] = AutoCropBottom;
-       job->crop[2] = AutoCropLeft;
-       job->crop[3] = AutoCropRight;
-    
+       /* Here we apply the max source storage width and height */
+    job->width = fTitle->width-fTitle->job->crop[2]-fTitle->job->crop[3];
+    job->height = fTitle->height-fTitle->job->crop[0]-fTitle->job->crop[1];
     
     [self calculatePictureSizing: sender];
     /* We call method to change UI to reflect whether a preset is used or not*/    
@@ -2592,7 +3732,7 @@ the user is using "Custom" settings by determining the sender*/
  */
 
 - (void)pictureSettingsDidChange {
-       [self calculatePictureSizing: NULL];
+       [self calculatePictureSizing:nil];
 }
 
 /* Get and Display Current Pic Settings in main window */
@@ -2618,18 +3758,18 @@ the user is using "Custom" settings by determining the sender*/
         hb_set_anamorphic_size(job, &output_width, &output_height, &output_par_width, &output_par_height);
         int display_width;
         display_width = output_width * output_par_width / output_par_height;
-        
+
         [fPicSettingsOutp setStringValue: [NSString stringWithFormat:@"%d x %d", output_width, output_height]];
         [fPicSettingsAnamorphic setStringValue: [NSString stringWithFormat:@"%d x %d Loose", display_width, output_height]];
-        
+
         fTitle->job->keep_ratio = 0;
     }
        else
        {
-        [fPicSettingsAnamorphic setStringValue: [NSString stringWithFormat:@"Off"]];
+        [fPicSettingsAnamorphic setStringValue:@"Off"];
        }
-    
-       /* Set ON/Off values for the deinterlace/keep aspect ratio according to boolean */      
+
+       /* Set ON/Off values for the deinterlace/keep aspect ratio according to boolean */
        if (fTitle->job->keep_ratio > 0)
        {
                [fPicSettingARkeep setStringValue: @"On"];
@@ -2638,6 +3778,7 @@ the user is using "Custom" settings by determining the sender*/
        {
                [fPicSettingARkeep setStringValue: @"Off"];
        }       
+    
     /* Detelecine */
     if ([fPictureController detelecine]) {
         [fPicSettingDetelecine setStringValue: @"Yes"];
@@ -2646,16 +3787,22 @@ the user is using "Custom" settings by determining the sender*/
         [fPicSettingDetelecine setStringValue: @"No"];
     }
     
-    /* VFR (Variable Frame Rate) */
-    if ([fPictureController vfr]) {
-        /* We change the string of the fps popup to warn that vfr is on Framerate (FPS): */
-        [fVidRateField setStringValue: @"Framerate (VFR On):"];  
-        
-    }
-    else {
-        /* make sure the label for framerate is set to its default */  
-        [fVidRateField setStringValue: @"Framerate (FPS):"];
+    /* Decomb */
+       if ([fPictureController decomb] == 0)
+       {
+               [fPicSettingDecomb setStringValue: @"Off"];
+       }
+       else if ([fPictureController decomb] == 1)
+       {
+               [fPicSettingDecomb setStringValue: @"1:2:6:9:80:16:16"];
+       }
+    else if ([fPictureController decomb] == 2)
+    {
+        [fPicSettingDecomb setStringValue:[[NSUserDefaults standardUserDefaults] stringForKey:@"DecombCustomString"]];
     }
+
+    /* VFR (Variable Frame Rate) */
+    
     
        /* Deinterlace */
        if ([fPictureController deinterlace] == 0)
@@ -2674,7 +3821,8 @@ the user is using "Custom" settings by determining the sender*/
        {
                [fPicSettingDeinterlace setStringValue: @"Slower"];
        }
-       /* Denoise */
+               
+    /* Denoise */
        if ([fPictureController denoise] == 0)
        {
                [fPicSettingDenoise setStringValue: @"Off"];
@@ -2693,11 +3841,13 @@ the user is using "Custom" settings by determining the sender*/
        }
     
     /* Deblock */
-    if ([fPictureController deblock]) {
-        [fPicSettingDeblock setStringValue: @"Yes"];
+    if ([fPictureController deblock] == 0) 
+    {
+        [fPicSettingDeblock setStringValue: @"Off"];
     }
-    else {
-        [fPicSettingDeblock setStringValue: @"No"];
+    else 
+    {
+        [fPicSettingDeblock setStringValue: [NSString stringWithFormat:@"%d",[fPictureController deblock]]];
     }
        
        if (fTitle->job->pixel_ratio > 0)
@@ -2708,7 +3858,8 @@ the user is using "Custom" settings by determining the sender*/
        {
                [fPicSettingPAR setStringValue: @"Off"];
        }
-       /* Set the display field for crop as per boolean */
+       
+    /* Set the display field for crop as per boolean */
        if (![fPictureController autoCrop])
        {
            [fPicSettingAutoCrop setStringValue: @"Custom"];
@@ -2721,23 +3872,185 @@ the user is using "Custom" settings by determining the sender*/
     
 }
 
-
-#pragma mark -
-#pragma mark - Audio and Subtitles
-
+
+#pragma mark -
+#pragma mark - Audio and Subtitles
+- (IBAction) audioCodecsPopUpChanged: (id) sender
+{
+    
+    NSPopUpButton * audiotrackPopUp;
+    NSPopUpButton * sampleratePopUp;
+    NSPopUpButton * bitratePopUp;
+    NSPopUpButton * audiocodecPopUp;
+    if (sender == fAudTrack1CodecPopUp)
+    {
+        audiotrackPopUp = fAudLang1PopUp;
+        audiocodecPopUp = fAudTrack1CodecPopUp;
+        sampleratePopUp = fAudTrack1RatePopUp;
+        bitratePopUp = fAudTrack1BitratePopUp;
+    }
+    else if (sender == fAudTrack2CodecPopUp)
+    {
+        audiotrackPopUp = fAudLang2PopUp;
+        audiocodecPopUp = fAudTrack2CodecPopUp;
+        sampleratePopUp = fAudTrack2RatePopUp;
+        bitratePopUp = fAudTrack2BitratePopUp;
+    }
+    else if (sender == fAudTrack3CodecPopUp)
+    {
+        audiotrackPopUp = fAudLang3PopUp;
+        audiocodecPopUp = fAudTrack3CodecPopUp;
+        sampleratePopUp = fAudTrack3RatePopUp;
+        bitratePopUp = fAudTrack3BitratePopUp;
+    }
+    else
+    {
+        audiotrackPopUp = fAudLang4PopUp;
+        audiocodecPopUp = fAudTrack4CodecPopUp;
+        sampleratePopUp = fAudTrack4RatePopUp;
+        bitratePopUp = fAudTrack4BitratePopUp;
+    }
+       
+    /* changing the codecs on offer may mean that we can / can't offer mono or 6ch, */
+       /* so call audioTrackPopUpChanged for both audio tracks to update the mixdown popups */
+    [self audioTrackPopUpChanged: audiotrackPopUp];
+    
+}
+
 - (IBAction) setEnabledStateOfAudioMixdownControls: (id) sender
 {
-
+    /* We will be setting the enabled/disabled state of each tracks audio controls based on
+     * the settings of the source audio for that track. We leave the samplerate and bitrate
+     * to audiotrackMixdownChanged
+     */
+    
+    /* We will first verify that a lower track number has been selected before enabling each track
+     * for example, make sure a track is selected for track 1 before enabling track 2, etc.
+     */
+    if ([fAudLang1PopUp indexOfSelectedItem] == 0)
+    {
+        [fAudLang2PopUp setEnabled: NO];
+        [fAudLang2PopUp selectItemAtIndex: 0];
+    }
+    else
+    {
+        [fAudLang2PopUp setEnabled: YES];
+    }
+    
+    if ([fAudLang2PopUp indexOfSelectedItem] == 0)
+    {
+        [fAudLang3PopUp setEnabled: NO];
+        [fAudLang3PopUp selectItemAtIndex: 0];
+    }
+    else
+    {
+        [fAudLang3PopUp setEnabled: YES];
+    }
+    if ([fAudLang3PopUp indexOfSelectedItem] == 0)
+    {
+        [fAudLang4PopUp setEnabled: NO];
+        [fAudLang4PopUp selectItemAtIndex: 0];
+    }
+    else
+    {
+        [fAudLang4PopUp setEnabled: YES];
+    }
     /* enable/disable the mixdown text and popupbutton for audio track 1 */
+    [fAudTrack1CodecPopUp setEnabled: ([fAudLang1PopUp indexOfSelectedItem] == 0) ? NO : YES];
     [fAudTrack1MixPopUp setEnabled: ([fAudLang1PopUp indexOfSelectedItem] == 0) ? NO : YES];
-    [fAudTrack1MixLabel setTextColor: ([fAudLang1PopUp indexOfSelectedItem] == 0) ?
-        [NSColor disabledControlTextColor] : [NSColor controlTextColor]];
-
+    [fAudTrack1RatePopUp setEnabled: ([fAudLang1PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack1BitratePopUp setEnabled: ([fAudLang1PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack1DrcSlider setEnabled: ([fAudLang1PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack1DrcField setEnabled: ([fAudLang1PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    if ([fAudLang1PopUp indexOfSelectedItem] == 0)
+    {
+        [fAudTrack1CodecPopUp removeAllItems];
+        [fAudTrack1MixPopUp removeAllItems];
+        [fAudTrack1RatePopUp removeAllItems];
+        [fAudTrack1BitratePopUp removeAllItems];
+        [fAudTrack1DrcSlider setFloatValue: 1.00];
+        [self audioDRCSliderChanged: fAudTrack1DrcSlider];
+    }
+    else if ([[fAudTrack1MixPopUp selectedItem] tag] == HB_ACODEC_AC3)
+    {
+        [fAudTrack1RatePopUp setEnabled: NO];
+        [fAudTrack1BitratePopUp setEnabled: NO];
+        [fAudTrack1DrcSlider setEnabled: NO];
+        [fAudTrack1DrcField setEnabled: NO];
+    }
+    
     /* enable/disable the mixdown text and popupbutton for audio track 2 */
+    [fAudTrack2CodecPopUp setEnabled: ([fAudLang2PopUp indexOfSelectedItem] == 0) ? NO : YES];
     [fAudTrack2MixPopUp setEnabled: ([fAudLang2PopUp indexOfSelectedItem] == 0) ? NO : YES];
-    [fAudTrack2MixLabel setTextColor: ([fAudLang2PopUp indexOfSelectedItem] == 0) ?
-        [NSColor disabledControlTextColor] : [NSColor controlTextColor]];
-
+    [fAudTrack2RatePopUp setEnabled: ([fAudLang2PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack2BitratePopUp setEnabled: ([fAudLang2PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack2DrcSlider setEnabled: ([fAudLang2PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack2DrcField setEnabled: ([fAudLang2PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    if ([fAudLang2PopUp indexOfSelectedItem] == 0)
+    {
+        [fAudTrack2CodecPopUp removeAllItems];
+        [fAudTrack2MixPopUp removeAllItems];
+        [fAudTrack2RatePopUp removeAllItems];
+        [fAudTrack2BitratePopUp removeAllItems];
+        [fAudTrack2DrcSlider setFloatValue: 1.00];
+        [self audioDRCSliderChanged: fAudTrack2DrcSlider];
+    }
+    else if ([[fAudTrack2MixPopUp selectedItem] tag] == HB_ACODEC_AC3)
+    {
+        [fAudTrack2RatePopUp setEnabled: NO];
+        [fAudTrack2BitratePopUp setEnabled: NO];
+        [fAudTrack2DrcSlider setEnabled: NO];
+        [fAudTrack2DrcField setEnabled: NO];
+    }
+    
+    /* enable/disable the mixdown text and popupbutton for audio track 3 */
+    [fAudTrack3CodecPopUp setEnabled: ([fAudLang3PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack3MixPopUp setEnabled: ([fAudLang3PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack3RatePopUp setEnabled: ([fAudLang3PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack3BitratePopUp setEnabled: ([fAudLang3PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack3DrcSlider setEnabled: ([fAudLang3PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack3DrcField setEnabled: ([fAudLang3PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    if ([fAudLang3PopUp indexOfSelectedItem] == 0)
+    {
+        [fAudTrack3CodecPopUp removeAllItems];
+        [fAudTrack3MixPopUp removeAllItems];
+        [fAudTrack3RatePopUp removeAllItems];
+        [fAudTrack3BitratePopUp removeAllItems];
+        [fAudTrack3DrcSlider setFloatValue: 1.00];
+        [self audioDRCSliderChanged: fAudTrack3DrcSlider];
+    }
+    else if ([[fAudTrack3MixPopUp selectedItem] tag] == HB_ACODEC_AC3)
+    {
+        [fAudTrack3RatePopUp setEnabled: NO];
+        [fAudTrack3BitratePopUp setEnabled: NO];
+        [fAudTrack3DrcSlider setEnabled: NO];
+        [fAudTrack3DrcField setEnabled: NO];
+    }
+    
+    /* enable/disable the mixdown text and popupbutton for audio track 4 */
+    [fAudTrack4CodecPopUp setEnabled: ([fAudLang4PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack4MixPopUp setEnabled: ([fAudLang4PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack4RatePopUp setEnabled: ([fAudLang4PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack4BitratePopUp setEnabled: ([fAudLang4PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack4DrcSlider setEnabled: ([fAudLang4PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    [fAudTrack4DrcField setEnabled: ([fAudLang4PopUp indexOfSelectedItem] == 0) ? NO : YES];
+    if ([fAudLang4PopUp indexOfSelectedItem] == 0)
+    {
+        [fAudTrack4CodecPopUp removeAllItems];
+        [fAudTrack4MixPopUp removeAllItems];
+        [fAudTrack4RatePopUp removeAllItems];
+        [fAudTrack4BitratePopUp removeAllItems];
+        [fAudTrack4DrcSlider setFloatValue: 1.00];
+        [self audioDRCSliderChanged: fAudTrack4DrcSlider];
+    }
+    else if ([[fAudTrack4MixPopUp selectedItem] tag] == HB_ACODEC_AC3)
+    {
+        [fAudTrack4RatePopUp setEnabled: NO];
+        [fAudTrack4BitratePopUp setEnabled: NO];
+        [fAudTrack4DrcSlider setEnabled: NO];
+        [fAudTrack4DrcField setEnabled: NO];
+    }
+    
 }
 
 - (IBAction) addAllAudioTracksToPopUp: (id) sender
@@ -2747,15 +4060,15 @@ the user is using "Custom" settings by determining the sender*/
     hb_title_t * title = (hb_title_t*)
         hb_list_item( list, [fSrcTitlePopUp indexOfSelectedItem] );
 
-       hb_audio_t * audio;
+       hb_audio_config_t * audio;
 
     [sender removeAllItems];
-    [sender addItemWithTitle: _( @"None" )];
+    [sender addItemWithTitle: NSLocalizedString( @"None", @"" )];
     for( int i = 0; i < hb_list_count( title->list_audio ); i++ )
     {
-        audio = (hb_audio_t *) hb_list_item( title->list_audio, i );
+        audio = (hb_audio_config_t *) hb_list_audio_config_item( title->list_audio, i );
         [[sender menu] addItemWithTitle:
-            [NSString stringWithCString: audio->lang]
+            [NSString stringWithCString: audio->lang.description]
             action: NULL keyEquivalent: @""];
     }
     [sender selectItemAtIndex: 0];
@@ -2769,8 +4082,8 @@ the user is using "Custom" settings by determining the sender*/
     /* e.g. to find the first French track, pass in an NSString * of "Francais" */
     /* e.g. to find the first English 5.1 AC3 track, pass in an NSString * of "English (AC3) (5.1 ch)" */
     /* if no matching track is found, then selectIndexIfNotFound is used to choose which track to select instead */
-    
-       if (searchPrefixString != NULL) 
+
+       if (searchPrefixString)
        {
 
         for( int i = 0; i < [sender numberOfItems]; i++ )
@@ -2794,6 +4107,97 @@ the user is using "Custom" settings by determining the sender*/
     }
 
 }
+- (IBAction) audioAddAudioTrackCodecs: (id)sender
+{
+    int format = [fDstFormatPopUp indexOfSelectedItem];
+    
+    /* setup pointers to the appropriate popups for the correct track */
+    NSPopUpButton * audiocodecPopUp;
+    NSPopUpButton * audiotrackPopUp;
+    if (sender == fAudTrack1CodecPopUp)
+    {
+        audiotrackPopUp = fAudLang1PopUp;
+        audiocodecPopUp = fAudTrack1CodecPopUp;
+    }
+    else if (sender == fAudTrack2CodecPopUp)
+    {
+        audiotrackPopUp = fAudLang2PopUp;
+        audiocodecPopUp = fAudTrack2CodecPopUp;
+    }
+    else if (sender == fAudTrack3CodecPopUp)
+    {
+        audiotrackPopUp = fAudLang3PopUp;
+        audiocodecPopUp = fAudTrack3CodecPopUp;
+    }
+    else
+    {
+        audiotrackPopUp = fAudLang4PopUp;
+        audiocodecPopUp = fAudTrack4CodecPopUp;
+    }
+    
+    [audiocodecPopUp removeAllItems];
+    /* Make sure "None" isnt selected in the source track */
+    if ([audiotrackPopUp indexOfSelectedItem] > 0)
+    {
+        [audiocodecPopUp setEnabled:YES];
+        NSMenuItem *menuItem;
+        /* We setup our appropriate popups for codecs and put the int value in the popup tag for easy retrieval */
+        switch( format )
+        {
+            case 0:
+                /* MP4 */
+                // AAC
+                menuItem = [[audiocodecPopUp menu] addItemWithTitle:@"AAC (faac)" action: NULL keyEquivalent: @""];
+                [menuItem setTag: HB_ACODEC_FAAC];
+                
+                // AC3 Passthru
+                menuItem = [[audiocodecPopUp menu] addItemWithTitle:@"AC3 Passthru" action: NULL keyEquivalent: @""];
+                [menuItem setTag: HB_ACODEC_AC3];
+                break;
+                
+            case 1:
+                /* MKV */
+                // AAC
+                menuItem = [[audiocodecPopUp menu] addItemWithTitle:@"AAC (faac)" action: NULL keyEquivalent: @""];
+                [menuItem setTag: HB_ACODEC_FAAC];
+                // AC3 Passthru
+                menuItem = [[audiocodecPopUp menu] addItemWithTitle:@"AC3 Passthru" action: NULL keyEquivalent: @""];
+                [menuItem setTag: HB_ACODEC_AC3];
+                // MP3
+                menuItem = [[audiocodecPopUp menu] addItemWithTitle:@"MP3 (lame)" action: NULL keyEquivalent: @""];
+                [menuItem setTag: HB_ACODEC_LAME];
+                // Vorbis
+                menuItem = [[audiocodecPopUp menu] addItemWithTitle:@"Vorbis (vorbis)" action: NULL keyEquivalent: @""];
+                [menuItem setTag: HB_ACODEC_VORBIS];
+                break;
+                
+            case 2: 
+                /* AVI */
+                // MP3
+                menuItem = [[audiocodecPopUp menu] addItemWithTitle:@"MP3 (lame)" action: NULL keyEquivalent: @""];
+                [menuItem setTag: HB_ACODEC_LAME];
+                // AC3 Passthru
+                menuItem = [[audiocodecPopUp menu] addItemWithTitle:@"AC3 Passthru" action: NULL keyEquivalent: @""];
+                [menuItem setTag: HB_ACODEC_AC3];
+                break;
+                
+            case 3:
+                /* OGM */
+                // Vorbis
+                menuItem = [[audiocodecPopUp menu] addItemWithTitle:@"Vorbis (vorbis)" action: NULL keyEquivalent: @""];
+                [menuItem setTag: HB_ACODEC_VORBIS];
+                // MP3
+                menuItem = [[audiocodecPopUp menu] addItemWithTitle:@"MP3 (lame)" action: NULL keyEquivalent: @""];
+                [menuItem setTag: HB_ACODEC_LAME];
+                break;
+        }
+        [audiocodecPopUp selectItemAtIndex:0];
+    }
+    else
+    {
+        [audiocodecPopUp setEnabled:NO];
+    }
+}
 
 - (IBAction) audioTrackPopUpChanged: (id) sender
 {
@@ -2803,184 +4207,209 @@ the user is using "Custom" settings by determining the sender*/
 
 - (IBAction) audioTrackPopUpChanged: (id) sender mixdownToUse: (int) mixdownToUse
 {
-
+    
     /* make sure we have a selected title before continuing */
     if (fTitle == NULL) return;
-
-    /* find out if audio track 1 or 2 was changed - this is passed to us in the tag of the sender */
-    /* the sender will have been either fAudLang1PopUp (tag = 0) or fAudLang2PopUp (tag = 1) */
-    int thisAudio = [sender tag];
-
-    /* get the index of the selected audio */
-    int thisAudioIndex = [sender indexOfSelectedItem] - 1;
-
-#if 0
-    /* Handbrake can't currently cope with ripping the same source track twice */
-    /* So, if this audio is also selected in the other audio track popup, set that popup's selection to "none" */
-    /* get a reference to the two audio track popups */
-    NSPopUpButton * thisAudioPopUp  = (thisAudio == 1 ? fAudLang2PopUp : fAudLang1PopUp);
-    NSPopUpButton * otherAudioPopUp = (thisAudio == 1 ? fAudLang1PopUp : fAudLang2PopUp);
-    /* if the same track is selected in the other audio popup, then select "none" in that popup */
-    /* unless, of course, both are selected as "none!" */
-    if ([thisAudioPopUp indexOfSelectedItem] != 0 && [thisAudioPopUp indexOfSelectedItem] == [otherAudioPopUp indexOfSelectedItem]) {
-        [otherAudioPopUp selectItemAtIndex: 0];
-        [self audioTrackPopUpChanged: otherAudioPopUp];
+    /* if the sender is the lanaguage popup and there is nothing in the codec popup, lets call
+    * audioAddAudioTrackCodecs on the codec popup to populate it properly before moving on
+    */
+    if (sender == fAudLang1PopUp && [[fAudTrack1CodecPopUp menu] numberOfItems] == 0)
+    {
+        [self audioAddAudioTrackCodecs: fAudTrack1CodecPopUp];
+    }
+    if (sender == fAudLang2PopUp && [[fAudTrack2CodecPopUp menu] numberOfItems] == 0)
+    {
+        [self audioAddAudioTrackCodecs: fAudTrack2CodecPopUp];
+    }
+    if (sender == fAudLang3PopUp && [[fAudTrack3CodecPopUp menu] numberOfItems] == 0)
+    {
+        [self audioAddAudioTrackCodecs: fAudTrack3CodecPopUp];
+    }
+    if (sender == fAudLang4PopUp && [[fAudTrack4CodecPopUp menu] numberOfItems] == 0)
+    {
+        [self audioAddAudioTrackCodecs: fAudTrack4CodecPopUp];
     }
-#endif
-
-    /* pointer for the hb_audio_s struct we will use later on */
-    hb_audio_t * audio;
-
-    /* find out what the currently-selected output audio codec is */
-    int format = [fDstFormatPopUp indexOfSelectedItem];
-    int codecs = [fDstCodecsPopUp indexOfSelectedItem];
-    int acodec = FormatSettings[format][codecs] & HB_ACODEC_MASK;
     
-    /*HACK: Lets setup a convenience variable to decide whether or not to allow aac hybrid (aac + ac3 passthru )*/
-    bool mp4AacAc3;
-    if (format == 0 && codecs == 2) // if mp4 and aac + ac3
+    /* Now lets make the sender the appropriate Audio Track popup from this point on */
+    if (sender == fAudTrack1CodecPopUp || sender == fAudTrack1MixPopUp)
     {
-    mp4AacAc3 = 1;
+        sender = fAudLang1PopUp;
     }
-    else
+    if (sender == fAudTrack2CodecPopUp || sender == fAudTrack2MixPopUp)
     {
-    mp4AacAc3 = 0;
+        sender = fAudLang2PopUp;
     }
-
-    /* pointer to this track's mixdown NSPopUpButton */
-    NSTextField   * mixdownTextField;
+    if (sender == fAudTrack3CodecPopUp || sender == fAudTrack3MixPopUp)
+    {
+        sender = fAudLang3PopUp;
+    }
+    if (sender == fAudTrack4CodecPopUp || sender == fAudTrack4MixPopUp)
+    {
+        sender = fAudLang4PopUp;
+    }
+    
+    /* pointer to this track's mixdown, codec, sample rate and bitrate NSPopUpButton's */
     NSPopUpButton * mixdownPopUp;
-
-    /* find our mixdown NSTextField and NSPopUpButton */
-    if (thisAudio == 0)
+    NSPopUpButton * audiocodecPopUp;
+    NSPopUpButton * sampleratePopUp;
+    NSPopUpButton * bitratePopUp;
+    if (sender == fAudLang1PopUp)
     {
-        mixdownTextField = fAudTrack1MixLabel;
         mixdownPopUp = fAudTrack1MixPopUp;
+        audiocodecPopUp = fAudTrack1CodecPopUp;
+        sampleratePopUp = fAudTrack1RatePopUp;
+        bitratePopUp = fAudTrack1BitratePopUp;
     }
-    else
+    else if (sender == fAudLang2PopUp)
     {
-        mixdownTextField = fAudTrack2MixLabel;
         mixdownPopUp = fAudTrack2MixPopUp;
+        audiocodecPopUp = fAudTrack2CodecPopUp;
+        sampleratePopUp = fAudTrack2RatePopUp;
+        bitratePopUp = fAudTrack2BitratePopUp;
     }
+    else if (sender == fAudLang3PopUp)
+    {
+        mixdownPopUp = fAudTrack3MixPopUp;
+        audiocodecPopUp = fAudTrack3CodecPopUp;
+        sampleratePopUp = fAudTrack3RatePopUp;
+        bitratePopUp = fAudTrack3BitratePopUp;
+    }
+    else
+    {
+        mixdownPopUp = fAudTrack4MixPopUp;
+        audiocodecPopUp = fAudTrack4CodecPopUp;
+        sampleratePopUp = fAudTrack4RatePopUp;
+        bitratePopUp = fAudTrack4BitratePopUp;
+    }
+
+    /* get the index of the selected audio Track*/
+    int thisAudioIndex = [sender indexOfSelectedItem] - 1;
 
-    /* delete the previous audio mixdown options */
-    [mixdownPopUp removeAllItems];
+    /* pointer for the hb_audio_s struct we will use later on */
+    hb_audio_config_t * audio;
 
+    int acodec;
     /* check if the audio mixdown controls need their enabled state changing */
-    [self setEnabledStateOfAudioMixdownControls: NULL];
+    [self setEnabledStateOfAudioMixdownControls:nil];
 
     if (thisAudioIndex != -1)
     {
 
         /* get the audio */
-        audio = (hb_audio_t *) hb_list_item( fTitle->list_audio, thisAudioIndex );
+        audio = (hb_audio_config_t *) hb_list_audio_config_item( fTitle->list_audio, thisAudioIndex );// Should "fTitle" be title and be setup ?
+
+        /* actually manipulate the proper mixdowns here */
+        /* delete the previous audio mixdown options */
+        [mixdownPopUp removeAllItems];
+
+        acodec = [[audiocodecPopUp selectedItem] tag];
+
         if (audio != NULL)
         {
 
             /* find out if our selected output audio codec supports mono and / or 6ch */
             /* we also check for an input codec of AC3 or DCA,
-               as they are the only libraries able to do the mixdown to mono / conversion to 6-ch */
+             as they are the only libraries able to do the mixdown to mono / conversion to 6-ch */
             /* audioCodecsSupportMono and audioCodecsSupport6Ch are the same for now,
-               but this may change in the future, so they are separated for flexibility */
-            int audioCodecsSupportMono = ((audio->codec == HB_ACODEC_AC3 ||
-                audio->codec == HB_ACODEC_DCA) && acodec == HB_ACODEC_FAAC);
-            int audioCodecsSupport6Ch =  ((audio->codec == HB_ACODEC_AC3 ||
-                audio->codec == HB_ACODEC_DCA) && (acodec == HB_ACODEC_FAAC ||
-                acodec == HB_ACODEC_VORBIS));
-
+             but this may change in the future, so they are separated for flexibility */
+            int audioCodecsSupportMono =
+                    (audio->in.codec & (HB_ACODEC_AC3|HB_ACODEC_DCA)) &&
+                    (acodec != HB_ACODEC_LAME);
+            int audioCodecsSupport6Ch =
+                    (audio->in.codec & (HB_ACODEC_AC3|HB_ACODEC_DCA)) &&
+                    (acodec != HB_ACODEC_LAME);
+            
             /* check for AC-3 passthru */
-            if (audio->codec == HB_ACODEC_AC3 && acodec == HB_ACODEC_AC3)
+            if (audio->in.codec == HB_ACODEC_AC3 && acodec == HB_ACODEC_AC3)
             {
-            
-                    [[mixdownPopUp menu] addItemWithTitle:
-                        [NSString stringWithCString: "AC3 Passthru"]
-                        action: NULL keyEquivalent: @""];
+                
+            NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
+                 [NSString stringWithCString: "AC3 Passthru"]
+                                               action: NULL keyEquivalent: @""];
+             [menuItem setTag: HB_ACODEC_AC3];   
             }
             else
             {
-
+                
                 /* add the appropriate audio mixdown menuitems to the popupbutton */
                 /* in each case, we set the new menuitem's tag to be the amixdown value for that mixdown,
-                   so that we can reference the mixdown later */
-
+                 so that we can reference the mixdown later */
+                
                 /* keep a track of the min and max mixdowns we used, so we can select the best match later */
                 int minMixdownUsed = 0;
                 int maxMixdownUsed = 0;
                 
                 /* get the input channel layout without any lfe channels */
-                int layout = audio->input_channel_layout & HB_INPUT_CH_LAYOUT_DISCRETE_NO_LFE_MASK;
-
+                int layout = audio->in.channel_layout & HB_INPUT_CH_LAYOUT_DISCRETE_NO_LFE_MASK;
+                
                 /* do we want to add a mono option? */
-                if (!mp4AacAc3 && audioCodecsSupportMono == 1) {
+                if (audioCodecsSupportMono == 1)
+                {
                     NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
-                        [NSString stringWithCString: hb_audio_mixdowns[0].human_readable_name]
-                        action: NULL keyEquivalent: @""];
+                                            [NSString stringWithCString: hb_audio_mixdowns[0].human_readable_name]
+                                                                          action: NULL keyEquivalent: @""];
                     [menuItem setTag: hb_audio_mixdowns[0].amixdown];
                     if (minMixdownUsed == 0) minMixdownUsed = hb_audio_mixdowns[0].amixdown;
                     maxMixdownUsed = MAX(maxMixdownUsed, hb_audio_mixdowns[0].amixdown);
                 }
-
+                
                 /* do we want to add a stereo option? */
                 /* offer stereo if we have a mono source and non-mono-supporting codecs, as otherwise we won't have a mixdown at all */
                 /* also offer stereo if we have a stereo-or-better source */
-                if (((!mp4AacAc3 || audio->codec == HB_ACODEC_MPGA ||  audio->codec == HB_ACODEC_LPCM || audio->codec == HB_ACODEC_DCA) && ((layout == HB_INPUT_CH_LAYOUT_MONO && audioCodecsSupportMono == 0) || layout >= HB_INPUT_CH_LAYOUT_STEREO))) {
+                if ((layout == HB_INPUT_CH_LAYOUT_MONO && audioCodecsSupportMono == 0) || layout >= HB_INPUT_CH_LAYOUT_STEREO)
+                {
                     NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
-                        [NSString stringWithCString: hb_audio_mixdowns[1].human_readable_name]
-                        action: NULL keyEquivalent: @""];
+                                            [NSString stringWithCString: hb_audio_mixdowns[1].human_readable_name]
+                                                                          action: NULL keyEquivalent: @""];
                     [menuItem setTag: hb_audio_mixdowns[1].amixdown];
                     if (minMixdownUsed == 0) minMixdownUsed = hb_audio_mixdowns[1].amixdown;
                     maxMixdownUsed = MAX(maxMixdownUsed, hb_audio_mixdowns[1].amixdown);
                 }
-
+                
                 /* do we want to add a dolby surround (DPL1) option? */
-                if (!mp4AacAc3 && (layout == HB_INPUT_CH_LAYOUT_3F1R || layout == HB_INPUT_CH_LAYOUT_3F2R || layout == HB_INPUT_CH_LAYOUT_DOLBY)) {
+                if (layout == HB_INPUT_CH_LAYOUT_3F1R || layout == HB_INPUT_CH_LAYOUT_3F2R || layout == HB_INPUT_CH_LAYOUT_DOLBY)
+                {
                     NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
-                        [NSString stringWithCString: hb_audio_mixdowns[2].human_readable_name]
-                        action: NULL keyEquivalent: @""];
+                                            [NSString stringWithCString: hb_audio_mixdowns[2].human_readable_name]
+                                                                          action: NULL keyEquivalent: @""];
                     [menuItem setTag: hb_audio_mixdowns[2].amixdown];
                     if (minMixdownUsed == 0) minMixdownUsed = hb_audio_mixdowns[2].amixdown;
                     maxMixdownUsed = MAX(maxMixdownUsed, hb_audio_mixdowns[2].amixdown);
                 }
-
+                
                 /* do we want to add a dolby pro logic 2 (DPL2) option? */
-                if ((!mp4AacAc3 || audio->codec == HB_ACODEC_DCA) && layout == HB_INPUT_CH_LAYOUT_3F2R) {
+                if (layout == HB_INPUT_CH_LAYOUT_3F2R)
+                {
                     NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
-                        [NSString stringWithCString: hb_audio_mixdowns[3].human_readable_name]
-                        action: NULL keyEquivalent: @""];
+                                            [NSString stringWithCString: hb_audio_mixdowns[3].human_readable_name]
+                                                                          action: NULL keyEquivalent: @""];
                     [menuItem setTag: hb_audio_mixdowns[3].amixdown];
                     if (minMixdownUsed == 0) minMixdownUsed = hb_audio_mixdowns[3].amixdown;
                     maxMixdownUsed = MAX(maxMixdownUsed, hb_audio_mixdowns[3].amixdown);
                 }
-
+                
                 /* do we want to add a 6-channel discrete option? */
-                if (!mp4AacAc3 && (audioCodecsSupport6Ch == 1 && layout == HB_INPUT_CH_LAYOUT_3F2R && (audio->input_channel_layout & HB_INPUT_CH_LAYOUT_HAS_LFE))) {
+                if (audioCodecsSupport6Ch == 1 && layout == HB_INPUT_CH_LAYOUT_3F2R && (audio->in.channel_layout & HB_INPUT_CH_LAYOUT_HAS_LFE))
+                {
                     NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
-                        [NSString stringWithCString: hb_audio_mixdowns[4].human_readable_name]
-                        action: NULL keyEquivalent: @""];
+                                            [NSString stringWithCString: hb_audio_mixdowns[4].human_readable_name]
+                                                                          action: NULL keyEquivalent: @""];
                     [menuItem setTag: hb_audio_mixdowns[4].amixdown];
                     if (minMixdownUsed == 0) minMixdownUsed = hb_audio_mixdowns[4].amixdown;
                     maxMixdownUsed = MAX(maxMixdownUsed, hb_audio_mixdowns[4].amixdown);
                 }
-
+                
                 /* do we want to add an AC-3 passthrough option? */
-                if (audio->codec == HB_ACODEC_AC3 && acodec == HB_ACODEC_AC3) {
+                if (audio->in.codec == HB_ACODEC_AC3 && acodec == HB_ACODEC_AC3) 
+                {
                     NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
-                        [NSString stringWithCString: hb_audio_mixdowns[5].human_readable_name]
-                        action: NULL keyEquivalent: @""];
-                    [menuItem setTag: hb_audio_mixdowns[5].amixdown];
+                                            [NSString stringWithCString: hb_audio_mixdowns[5].human_readable_name]
+                                                                          action: NULL keyEquivalent: @""];
+                    [menuItem setTag: HB_ACODEC_AC3];
                     if (minMixdownUsed == 0) minMixdownUsed = hb_audio_mixdowns[5].amixdown;
                     maxMixdownUsed = MAX(maxMixdownUsed, hb_audio_mixdowns[5].amixdown);
                 }
-
-                /* do we want to add the DPLII+AC3 passthrough option? */
-                if (mp4AacAc3 && audio->codec == HB_ACODEC_AC3) {
-                    NSMenuItem *menuItem = [[mixdownPopUp menu] addItemWithTitle:
-                        [NSString stringWithCString: hb_audio_mixdowns[6].human_readable_name]
-                        action: NULL keyEquivalent: @""];
-                    [menuItem setTag: hb_audio_mixdowns[6].amixdown];
-                    if (minMixdownUsed == 0) minMixdownUsed = hb_audio_mixdowns[6].amixdown;
-                    maxMixdownUsed = MAX(maxMixdownUsed, hb_audio_mixdowns[6].amixdown);
-                }
+                
                 /* auto-select the best mixdown based on our saved mixdown preference */
                 
                 /* for now, this is hard-coded to a "best" mixdown of HB_AMIXDOWN_DOLBYPLII */
@@ -2998,34 +4427,104 @@ the user is using "Custom" settings by determining the sender*/
                 }
                 
                 /* if useMixdown > maxMixdownUsed, then use maxMixdownUsed */
-                if (useMixdown > maxMixdownUsed) useMixdown = maxMixdownUsed;
-
+                if (useMixdown > maxMixdownUsed)
+                { 
+                    useMixdown = maxMixdownUsed;
+                }
+                
                 /* if useMixdown < minMixdownUsed, then use minMixdownUsed */
-                if (useMixdown < minMixdownUsed) useMixdown = minMixdownUsed;
-
+                if (useMixdown < minMixdownUsed)
+                { 
+                    useMixdown = minMixdownUsed;
+                }
+                
                 /* select the (possibly-amended) preferred mixdown */
                 [mixdownPopUp selectItemWithTag: useMixdown];
-                               
-                               /* lets call the audioTrackMixdownChanged method here to determine appropriate bitrates, etc. */
-                [self audioTrackMixdownChanged: NULL];
-            }
 
+            }
+            /* In the case of a source track that is not AC3 and the user tries to use AC3 Passthru (which does not work)
+             * we force the Audio Codec choice back to a workable codec. We use MP3 for avi and aac for all
+             * other containers.
+             */
+            if (audio->in.codec != HB_ACODEC_AC3 && [[audiocodecPopUp selectedItem] tag] == HB_ACODEC_AC3)
+            {
+                /* If we are using the avi container, we select MP3 as there is no aac available*/
+                if ([[fDstFormatPopUp selectedItem] tag] == HB_MUX_AVI)
+                {
+                    [audiocodecPopUp selectItemWithTag: HB_ACODEC_LAME];
+                }
+                else
+                {
+                    [audiocodecPopUp selectItemWithTag: HB_ACODEC_FAAC];
+                }
+            }
+            /* Setup our samplerate and bitrate popups we will need based on mixdown */
+            [self audioTrackMixdownChanged: mixdownPopUp];            
         }
-        
+    
+    }
+    if( [fDstFormatPopUp indexOfSelectedItem] == 0 )
+    {
+        [self autoSetM4vExtension: sender];
+        [self shouldEnableHttpMp4CheckBox: sender];
     }
-
-       /* see if the new audio track choice will change the bitrate we need */
-    [self calculateBitrate: sender];   
-
 }
+
 - (IBAction) audioTrackMixdownChanged: (id) sender
 {
-
-    /* find out what the currently-selected output audio codec is */
-    int format = [fDstFormatPopUp indexOfSelectedItem];
-    int codecs = [fDstCodecsPopUp indexOfSelectedItem];
-    int acodec = FormatSettings[format][codecs] & HB_ACODEC_MASK;
     
+    int acodec;
+    /* setup pointers to all of the other audio track controls
+    * we will need later
+    */
+    NSPopUpButton * mixdownPopUp;
+    NSPopUpButton * sampleratePopUp;
+    NSPopUpButton * bitratePopUp;
+    NSPopUpButton * audiocodecPopUp;
+    NSPopUpButton * audiotrackPopUp;
+    NSSlider * drcSlider;
+    NSTextField * drcField;
+    if (sender == fAudTrack1MixPopUp)
+    {
+        audiotrackPopUp = fAudLang1PopUp;
+        audiocodecPopUp = fAudTrack1CodecPopUp;
+        mixdownPopUp = fAudTrack1MixPopUp;
+        sampleratePopUp = fAudTrack1RatePopUp;
+        bitratePopUp = fAudTrack1BitratePopUp;
+        drcSlider = fAudTrack1DrcSlider;
+        drcField = fAudTrack1DrcField;
+    }
+    else if (sender == fAudTrack2MixPopUp)
+    {
+        audiotrackPopUp = fAudLang2PopUp;
+        audiocodecPopUp = fAudTrack2CodecPopUp;
+        mixdownPopUp = fAudTrack2MixPopUp;
+        sampleratePopUp = fAudTrack2RatePopUp;
+        bitratePopUp = fAudTrack2BitratePopUp;
+        drcSlider = fAudTrack2DrcSlider;
+        drcField = fAudTrack2DrcField;
+    }
+    else if (sender == fAudTrack3MixPopUp)
+    {
+        audiotrackPopUp = fAudLang3PopUp;
+        audiocodecPopUp = fAudTrack3CodecPopUp;
+        mixdownPopUp = fAudTrack3MixPopUp;
+        sampleratePopUp = fAudTrack3RatePopUp;
+        bitratePopUp = fAudTrack3BitratePopUp;
+        drcSlider = fAudTrack3DrcSlider;
+        drcField = fAudTrack3DrcField;
+    }
+    else
+    {
+        audiotrackPopUp = fAudLang4PopUp;
+        audiocodecPopUp = fAudTrack4CodecPopUp;
+        mixdownPopUp = fAudTrack4MixPopUp;
+        sampleratePopUp = fAudTrack4RatePopUp;
+        bitratePopUp = fAudTrack4BitratePopUp;
+        drcSlider = fAudTrack4DrcSlider;
+        drcField = fAudTrack4DrcField;
+    }
+    acodec = [[audiocodecPopUp selectedItem] tag];
     /* storage variable for the min and max bitrate allowed for this codec */
     int minbitrate;
     int maxbitrate;
@@ -3034,10 +4533,7 @@ the user is using "Custom" settings by determining the sender*/
     {
         case HB_ACODEC_FAAC:
             /* check if we have a 6ch discrete conversion in either audio track */
-            if ([[fAudTrack1MixPopUp selectedItem] tag] == HB_AMIXDOWN_6CH || 
-                [[fAudTrack2MixPopUp selectedItem] tag] == HB_AMIXDOWN_6CH || 
-                [[fAudTrack1MixPopUp selectedItem] tag] == HB_AMIXDOWN_AC3 || 
-                [[fAudTrack2MixPopUp selectedItem] tag] == HB_AMIXDOWN_AC3)
+            if ([[mixdownPopUp selectedItem] tag] == HB_AMIXDOWN_6CH)
             {
                 /* FAAC is happy using our min bitrate of 32 kbps, even for 6ch */
                 minbitrate = 32;
@@ -3054,16 +4550,16 @@ the user is using "Custom" settings by determining the sender*/
                 maxbitrate = 160;
                 break;
             }
-
-        case HB_ACODEC_LAME:
+            
+            case HB_ACODEC_LAME:
             /* Lame is happy using our min bitrate of 32 kbps */
             minbitrate = 32;
             /* Lame won't encode if the bitrate is higher than 320 kbps */
             maxbitrate = 320;
             break;
-
-        case HB_ACODEC_VORBIS:
-        if ([[fAudTrack1MixPopUp selectedItem] tag] == HB_AMIXDOWN_6CH || [[fAudTrack2MixPopUp selectedItem] tag] == HB_AMIXDOWN_6CH)
+            
+            case HB_ACODEC_VORBIS:
+            if ([[mixdownPopUp selectedItem] tag] == HB_AMIXDOWN_6CH)
             {
                 /* Vorbis causes a crash if we use a bitrate below 192 kbps with 6 channel */
                 minbitrate = 192;
@@ -3073,54 +4569,137 @@ the user is using "Custom" settings by determining the sender*/
             }
             else
             {
-            /* Vorbis causes a crash if we use a bitrate below 48 kbps */
-            minbitrate = 48;
-            /* Vorbis can cope with 384 kbps quite happily, even for stereo */
-            maxbitrate = 384;
-            break;
+                /* Vorbis causes a crash if we use a bitrate below 48 kbps */
+                minbitrate = 48;
+                /* Vorbis can cope with 384 kbps quite happily, even for stereo */
+                maxbitrate = 384;
+                break;
             }
-
-        default:
+            
+            default:
             /* AC3 passthru disables the bitrate dropdown anyway, so we might as well just use the min and max bitrate */
             minbitrate = 32;
             maxbitrate = 384;
-        
+            
     }
-
-    [fAudBitratePopUp removeAllItems];
-
-    for( int i = 0; i < hb_audio_bitrates_count; i++ )
+    
+    /* make sure we have a selected title before continuing */
+    if (fTitle == NULL) return;
+    /* get the audio so we can find out what input rates are*/
+    hb_audio_config_t * audio;
+    audio = (hb_audio_config_t *) hb_list_audio_config_item( fTitle->list_audio, [audiotrackPopUp indexOfSelectedItem] - 1 );
+    int inputbitrate = audio->in.bitrate / 1000;
+    int inputsamplerate = audio->in.samplerate;
+    
+    if ([[mixdownPopUp selectedItem] tag] != HB_ACODEC_AC3)
     {
-        if (hb_audio_bitrates[i].rate >= minbitrate && hb_audio_bitrates[i].rate <= maxbitrate)
+        [bitratePopUp removeAllItems];
+        
+        for( int i = 0; i < hb_audio_bitrates_count; i++ )
+        {
+            if (hb_audio_bitrates[i].rate >= minbitrate && hb_audio_bitrates[i].rate <= maxbitrate)
+            {
+                /* add a new menuitem for this bitrate */
+                NSMenuItem *menuItem = [[bitratePopUp menu] addItemWithTitle:
+                                        [NSString stringWithCString: hb_audio_bitrates[i].string]
+                                                                      action: NULL keyEquivalent: @""];
+                /* set its tag to be the actual bitrate as an integer, so we can retrieve it later */
+                [menuItem setTag: hb_audio_bitrates[i].rate];
+            }
+        }
+        
+        /* select the default bitrate (but use 384 for 6-ch AAC) */
+        if ([[mixdownPopUp selectedItem] tag] == HB_AMIXDOWN_6CH)
+        {
+            [bitratePopUp selectItemWithTag: 384];
+        }
+        else
         {
-            /* add a new menuitem for this bitrate */
-            NSMenuItem *menuItem = [[fAudBitratePopUp menu] addItemWithTitle:
-                [NSString stringWithCString: hb_audio_bitrates[i].string]
-                action: NULL keyEquivalent: @""];
-            /* set its tag to be the actual bitrate as an integer, so we can retrieve it later */
-            [menuItem setTag: hb_audio_bitrates[i].rate];
+            [bitratePopUp selectItemWithTag: hb_audio_bitrates[hb_audio_bitrates_default].rate];
         }
     }
-
-    /* select the default bitrate (but use 384 for 6-ch AAC) */
-    if ([[fAudTrack1MixPopUp selectedItem] tag] == HB_AMIXDOWN_6CH || 
-        [[fAudTrack2MixPopUp selectedItem] tag] == HB_AMIXDOWN_6CH ||
-        [[fAudTrack1MixPopUp selectedItem] tag] == HB_AMIXDOWN_AC3 || 
-        [[fAudTrack2MixPopUp selectedItem] tag] == HB_AMIXDOWN_AC3)
+    /* populate and set the sample rate popup */
+    /* Audio samplerate */
+    [sampleratePopUp removeAllItems];
+    /* we create a same as source selection (Auto) so that we can choose to use the input sample rate */
+    NSMenuItem *menuItem = [[sampleratePopUp menu] addItemWithTitle: @"Auto" action: NULL keyEquivalent: @""];
+    [menuItem setTag: inputsamplerate];
+    
+    for( int i = 0; i < hb_audio_rates_count; i++ )
+    {
+        NSMenuItem *menuItem = [[sampleratePopUp menu] addItemWithTitle:
+                                [NSString stringWithCString: hb_audio_rates[i].string]
+                                                                 action: NULL keyEquivalent: @""];
+        [menuItem setTag: hb_audio_rates[i].rate];
+    }
+    /* We use the input sample rate as the default sample rate as downsampling just makes audio worse
+    * and there is no compelling reason to use anything else as default, though the users default
+    * preset will likely override any setting chosen here.
+    */
+    [sampleratePopUp selectItemWithTag: inputsamplerate];
+    
+    
+    /* Since AC3 Pass Thru uses the input ac3 bitrate and sample rate, we get the input tracks
+    * bitrate and dispay it in the bitrate popup even though libhb happily ignores any bitrate input from
+    * the gui. We do this for better user feedback in the audio tab as well as the queue for the most part
+    */
+    if ([[mixdownPopUp selectedItem] tag] == HB_ACODEC_AC3)
     {
-        [fAudBitratePopUp selectItemWithTag: 384];
+        
+        /* lets also set the bitrate popup to the input bitrate as thats what passthru will use */
+        [bitratePopUp removeAllItems];
+        NSMenuItem *menuItem = [[bitratePopUp menu] addItemWithTitle:
+                                [NSString stringWithFormat:@"%d", inputbitrate]
+                                                              action: NULL keyEquivalent: @""];
+        [menuItem setTag: inputbitrate];
+        /* For ac3 passthru we disable the sample rate and bitrate popups as well as the drc slider*/
+        [bitratePopUp setEnabled: NO];
+        [sampleratePopUp setEnabled: NO];
+        
+        [drcSlider setFloatValue: 1.00];
+        [self audioDRCSliderChanged: drcSlider];
+        [drcSlider setEnabled: NO];
+        [drcField setEnabled: NO];
     }
     else
     {
-        [fAudBitratePopUp selectItemWithTag: hb_audio_bitrates[hb_audio_bitrates_default].rate];
+        [sampleratePopUp setEnabled: YES];
+        [bitratePopUp setEnabled: YES];
+        [drcSlider setEnabled: YES];
+        [drcField setEnabled: YES];
     }
-
+[self calculateBitrate:nil];    
 }
 
 - (IBAction) audioDRCSliderChanged: (id) sender
 {
-    [fAudDrcField setStringValue: [NSString stringWithFormat: @"%.2f", [fAudDrcSlider floatValue]]];
-    [self customSettingUsed: sender];
+    NSSlider * drcSlider;
+    NSTextField * drcField;
+    if (sender == fAudTrack1DrcSlider)
+    {
+        drcSlider = fAudTrack1DrcSlider;
+        drcField = fAudTrack1DrcField;
+    }
+    else if (sender == fAudTrack2DrcSlider)
+    {
+        drcSlider = fAudTrack2DrcSlider;
+        drcField = fAudTrack2DrcField;
+    }
+    else if (sender == fAudTrack3DrcSlider)
+    {
+        drcSlider = fAudTrack3DrcSlider;
+        drcField = fAudTrack3DrcField;
+    }
+    else
+    {
+        drcSlider = fAudTrack4DrcSlider;
+        drcField = fAudTrack4DrcField;
+    }
+    [drcField setStringValue: [NSString stringWithFormat: @"%.2f", [drcSlider floatValue]]];
+    /* For now, do not call this until we have an intelligent way to determine audio track selections
+    * compared to presets
+    */
+    //[self customSettingUsed: sender];
 }
 
 - (IBAction) subtitleSelectionChanged: (id) sender
@@ -3146,18 +4725,18 @@ the user is using "Custom" settings by determining the sender*/
 - (IBAction) openHomepage: (id) sender
 {
     [[NSWorkspace sharedWorkspace] openURL: [NSURL
-        URLWithString:@"http://handbrake.m0k.org/"]];
+        URLWithString:@"http://handbrake.fr/"]];
 }
 
 - (IBAction) openForums: (id) sender
 {
     [[NSWorkspace sharedWorkspace] openURL: [NSURL
-        URLWithString:@"http://handbrake.m0k.org/forum/"]];
+        URLWithString:@"http://handbrake.fr/forum/"]];
 }
 - (IBAction) openUserGuide: (id) sender
 {
     [[NSWorkspace sharedWorkspace] openURL: [NSURL
-        URLWithString:@"http://handbrake.m0k.org/trac/wiki/HandBrakeGuide"]];
+        URLWithString:@"http://handbrake.fr/trac/wiki/HandBrakeGuide"]];
 }
 
 /**
@@ -3205,39 +4784,116 @@ the user is using "Custom" settings by determining the sender*/
     [fPictureController showPanelInWindow:fWindow forTitle:title];
 }
 
-#pragma mark -
-#pragma mark Preset Outline View Methods
-#pragma mark - Required
-/* These are required by the NSOutlineView Datasource Delegate */
+#pragma mark -
+#pragma mark Preset Outline View Methods
+#pragma mark - Required
+/* These are required by the NSOutlineView Datasource Delegate */
+
+
+/* used to specify the number of levels to show for each item */
+- (int)outlineView:(NSOutlineView *)fPresetsOutlineView numberOfChildrenOfItem:(id)item
+{
+    /* currently use no levels to test outline view viability */
+    if (item == nil) // for an outline view the root level of the hierarchy is always nil
+    {
+        return [UserPresets count];
+    }
+    else
+    {
+        /* we need to return the count of the array in ChildrenArray for this folder */
+        NSArray *children = nil;
+        children = [item objectForKey:@"ChildrenArray"];
+        if ([children count] > 0)
+        {
+            return [children count];
+        }
+        else
+        {
+            return 0;
+        }
+    }
+}
+
 /* We use this to deterimine children of an item */
-- (id)outlineView:(NSOutlineView *)fPresetsOutlineView child:(NSInteger)index ofItem:(id)item
+- (id)outlineView:(NSOutlineView *)fPresetsOutlineView child:(int)index ofItem:(id)item
 {
-if (item == nil)
-        return [UserPresets objectAtIndex:index];
+    
+    /* we need to return the count of the array in ChildrenArray for this folder */
+    NSArray *children = nil;
+    if (item == nil)
+    {
+        children = UserPresets;
+    }
+    else
+    {
+        if ([item objectForKey:@"ChildrenArray"])
+        {
+            children = [item objectForKey:@"ChildrenArray"];
+        }
+    }   
+    if ((children == nil) || ([children count] <= index))
+    {
+        return nil;
+    }
+    else
+    {
+        return [children objectAtIndex:index];
+    }
+    
     
     // We are only one level deep, so we can't be asked about children
-    NSAssert (NO, @"Presets View outlineView:child:ofItem: currently can't handle nested items.");
-    return nil;
+    //NSAssert (NO, @"Presets View outlineView:child:ofItem: currently can't handle nested items.");
+    //return nil;
 }
+
 /* We use this to determine if an item should be expandable */
 - (BOOL)outlineView:(NSOutlineView *)fPresetsOutlineView isItemExpandable:(id)item
 {
-
-    /* For now, we maintain one level, so set to no
-    * when nested, we set to yes for any preset "folders"
-    */
-    return NO;
-
-}
-/* used to specify the number of levels to show for each item */
-- (int)outlineView:(NSOutlineView *)fPresetsOutlineView numberOfChildrenOfItem:(id)item
-{
-    /* currently use no levels to test outline view viability */
+    
+    /* we need to return the count of the array in ChildrenArray for this folder */
+    NSArray *children= nil;
     if (item == nil)
-        return [UserPresets count];
+    {
+        children = UserPresets;
+    }
+    else
+    {
+        if ([item objectForKey:@"ChildrenArray"])
+        {
+            children = [item objectForKey:@"ChildrenArray"];
+        }
+    }   
+    
+    /* To deterimine if an item should show a disclosure triangle
+     * we could do it by the children count as so:
+     * if ([children count] < 1)
+     * However, lets leave the triangle show even if there are no
+     * children to help indicate a folder, just like folder in the
+     * finder can show a disclosure triangle even when empty
+     */
+    
+    /* We need to determine if the item is a folder */
+   if ([[item objectForKey:@"Folder"] intValue] == 1)
+   {
+        return YES;
+    }
     else
-        return 0;
+    {
+        return NO;
+    }
+    
+}
+
+- (BOOL)outlineView:(NSOutlineView *)outlineView shouldExpandItem:(id)item
+{
+    // Our outline view has no levels, but we can still expand every item. Doing so
+    // just makes the row taller. See heightOfRowByItem below.
+//return ![(HBQueueOutlineView*)outlineView isDragging];
+
+return YES;
 }
+
+
 /* Used to tell the outline view which information is to be displayed per item */
 - (id)outlineView:(NSOutlineView *)fPresetsOutlineView objectValueForTableColumn:(NSTableColumn *)tableColumn byItem:(id)item
 {
@@ -3249,7 +4905,8 @@ if (item == nil)
     }
     else
     {
-        return @"something";
+        //return @"";
+        return nil;
     }
 }
 
@@ -3259,7 +4916,6 @@ if (item == nil)
 {
     if ([[tableColumn identifier] isEqualToString:@"PresetName"])
     {
-        NSDictionary *userPresetDict = item;
         NSFont *txtFont;
         NSColor *fontColor;
         NSColor *shadowColor;
@@ -3268,12 +4924,12 @@ if (item == nil)
         if ([fPresetsOutlineView selectedRow] == [fPresetsOutlineView rowForItem:item])
         {
             
-            fontColor = [NSColor whiteColor];
+            fontColor = [NSColor blackColor];
             shadowColor = [NSColor colorWithDeviceRed:(127.0/255.0) green:(140.0/255.0) blue:(160.0/255.0) alpha:1.0];
         }
         else
         {
-            if ([[userPresetDict objectForKey:@"Type"] intValue] == 0)
+            if ([[item objectForKey:@"Type"] intValue] == 0)
             {
                 fontColor = [NSColor blueColor];
             }
@@ -3281,15 +4937,21 @@ if (item == nil)
             {
                 fontColor = [NSColor blackColor];
             }
-            shadowColor = nil;
+            /* check to see if its a folder */
+            //if ([[item objectForKey:@"Folder"] intValue] == 1)
+            //{
+            //fontColor = [NSColor greenColor];
+            //}
+            
+            
         }
         /* We use Bold Text for the HB Default */
-        if ([[userPresetDict objectForKey:@"Default"] intValue] == 1)// 1 is HB default
+        if ([[item objectForKey:@"Default"] intValue] == 1)// 1 is HB default
         {
             txtFont = [NSFont boldSystemFontOfSize: [NSFont smallSystemFontSize]];
         }
         /* We use Bold Text for the User Specified Default */
-        if ([[userPresetDict objectForKey:@"Default"] intValue] == 2)// 2 is User default
+        if ([[item objectForKey:@"Default"] intValue] == 2)// 2 is User default
         {
             txtFont = [NSFont boldSystemFontOfSize: [NSFont smallSystemFontSize]];
         }
@@ -3302,7 +4964,7 @@ if (item == nil)
 }
 
 /* We use this to edit the name field in the outline view */
-- (void)outlineView:(NSOutlineView *)fPresetsOutlineView setObjectValue:(id)object forTableColumn:(NSTableColumn *)tableColumn byItem:(id)item
+- (void)outlineView:(NSOutlineView *)outlineView setObjectValue:(id)object forTableColumn:(NSTableColumn *)tableColumn byItem:(id)item
 {
     if ([[tableColumn identifier] isEqualToString:@"PresetName"])
     {
@@ -3310,17 +4972,10 @@ if (item == nil)
         
         theRecord = item;
         [theRecord setObject:object forKey:@"PresetName"];
-        /* We Sort the Presets By Factory or Custom */
-        NSSortDescriptor * presetTypeDescriptor=[[[NSSortDescriptor alloc] initWithKey:@"Type" 
-                                                                             ascending:YES] autorelease];
-               /* We Sort the Presets Alphabetically by name */
-        NSSortDescriptor * presetNameDescriptor=[[[NSSortDescriptor alloc] initWithKey:@"PresetName" 
-                                                                             ascending:YES selector:@selector(caseInsensitiveCompare:)] autorelease];
-        NSArray *sortDescriptors=[NSArray arrayWithObjects:presetTypeDescriptor,presetNameDescriptor,nil];
-        NSArray *sortedArray=[UserPresets sortedArrayUsingDescriptors:sortDescriptors];
-        [UserPresets setArray:sortedArray];
-        /* We Reload the New Table data for presets */
-        //[fPresetsOutlineView reloadData];
+        
+        [self sortPresets];
+        
+        [fPresetsOutlineView reloadData];
         /* We save all of the preset data here */
         [self savePreset];
     }
@@ -3333,9 +4988,9 @@ if (item == nil)
         /* initialize the tooltip contents variable */
         NSString *loc_tip;
         /* if there is a description for the preset, we show it in the tooltip */
-        if ([item valueForKey:@"PresetDescription"])
+        if ([item objectForKey:@"PresetDescription"])
         {
-            loc_tip = [NSString stringWithFormat: @"%@",[item valueForKey:@"PresetDescription"]];
+            loc_tip = [item objectForKey:@"PresetDescription"];
             return (loc_tip);
         }
         else
@@ -3346,28 +5001,140 @@ if (item == nil)
     //}
 }
 
+#pragma mark -
+#pragma mark Preset Outline View Methods (dragging related)
+
+
+- (BOOL)outlineView:(NSOutlineView *)outlineView writeItems:(NSArray *)items toPasteboard:(NSPasteboard *)pboard
+{
+       // Dragging is only allowed for custom presets.
+    //[[[fPresetsOutlineView itemAtRow:[fPresetsOutlineView selectedRow]] objectForKey:@"Default"] intValue] != 1
+       if ([[[fPresetsOutlineView itemAtRow:[fPresetsOutlineView selectedRow]] objectForKey:@"Type"] intValue] == 0) // 0 is built in preset
+    {
+        return NO;
+    }
+    // Don't retain since this is just holding temporaral drag information, and it is
+    //only used during a drag!  We could put this in the pboard actually.
+    fDraggedNodes = items;
+    // Provide data for our custom type, and simple NSStrings.
+    [pboard declareTypes:[NSArray arrayWithObjects: DragDropSimplePboardType, nil] owner:self];
+    
+    // the actual data doesn't matter since DragDropSimplePboardType drags aren't recognized by anyone but us!.
+    [pboard setData:[NSData data] forType:DragDropSimplePboardType]; 
+    
+    return YES;
+}
+
+- (NSDragOperation)outlineView:(NSOutlineView *)outlineView validateDrop:(id <NSDraggingInfo>)info proposedItem:(id)item proposedChildIndex:(int)index
+{
+       
+       // Don't allow dropping ONTO an item since they can't really contain any children.
+    
+    BOOL isOnDropTypeProposal = index == NSOutlineViewDropOnItemIndex;
+    if (isOnDropTypeProposal)
+        return NSDragOperationNone;
+    
+    // Don't allow dropping INTO an item since they can't really contain any children as of yet.
+       if (item != nil)
+       {
+               index = [fPresetsOutlineView rowForItem: item] + 1;
+               item = nil;
+       }
+    
+    // Don't allow dropping into the Built In Presets.
+    if (index < presetCurrentBuiltInCount)
+    {
+        return NSDragOperationNone;
+        index = MAX (index, presetCurrentBuiltInCount);
+       }    
+       
+    [outlineView setDropItem:item dropChildIndex:index];
+    return NSDragOperationGeneric;
+}
+
+
+
+- (BOOL)outlineView:(NSOutlineView *)outlineView acceptDrop:(id <NSDraggingInfo>)info item:(id)item childIndex:(int)index
+{
+    /* first, lets see if we are dropping into a folder */
+    if ([[fPresetsOutlineView itemAtRow:index] objectForKey:@"Folder"] && [[[fPresetsOutlineView itemAtRow:index] objectForKey:@"Folder"] intValue] == 1) // if its a folder
+       {
+    NSMutableArray *childrenArray = [[NSMutableArray alloc] init];
+    childrenArray = [[fPresetsOutlineView itemAtRow:index] objectForKey:@"ChildrenArray"];
+    [childrenArray addObject:item];
+    [[fPresetsOutlineView itemAtRow:index] setObject:[NSMutableArray arrayWithArray: childrenArray] forKey:@"ChildrenArray"];
+    [childrenArray autorelease];
+    }
+    else // We are not, so we just move the preset into the existing array 
+    {
+        NSMutableIndexSet *moveItems = [NSMutableIndexSet indexSet];
+        id obj;
+        NSEnumerator *enumerator = [fDraggedNodes objectEnumerator];
+        while (obj = [enumerator nextObject])
+        {
+            [moveItems addIndex:[UserPresets indexOfObject:obj]];
+        }
+        // Successful drop, lets rearrange the view and save it all
+        [self moveObjectsInPresetsArray:UserPresets fromIndexes:moveItems toIndex: index];
+    }
+    [fPresetsOutlineView reloadData];
+    [self savePreset];
+    return YES;
+}
+
+- (void)moveObjectsInPresetsArray:(NSMutableArray *)array fromIndexes:(NSIndexSet *)indexSet toIndex:(unsigned)insertIndex
+{
+    unsigned index = [indexSet lastIndex];
+    unsigned aboveInsertIndexCount = 0;
+    
+    while (index != NSNotFound)
+    {
+        unsigned removeIndex;
+        
+        if (index >= insertIndex)
+        {
+            removeIndex = index + aboveInsertIndexCount;
+            aboveInsertIndexCount++;
+        }
+        else
+        {
+            removeIndex = index;
+            insertIndex--;
+        }
+        
+        id object = [[array objectAtIndex:removeIndex] retain];
+        [array removeObjectAtIndex:removeIndex];
+        [array insertObject:object atIndex:insertIndex];
+        [object release];
+        
+        index = [indexSet indexLessThanIndex:index];
+    }
+}
+
+
 
 #pragma mark - Functional Preset NSOutlineView Methods
 
 - (IBAction)selectPreset:(id)sender
 {
     
-    if ([fPresetsOutlineView selectedRow] >= 0)
+    if ([fPresetsOutlineView selectedRow] >= 0 && [[[fPresetsOutlineView itemAtRow:[fPresetsOutlineView selectedRow]] objectForKey:@"Folder"] intValue] != 1)
     {
         chosenPreset = [fPresetsOutlineView itemAtRow:[fPresetsOutlineView selectedRow]];
-        /* we set the preset display field in main window here */
-        [fPresetSelectedDisplay setStringValue: [NSString stringWithFormat: @"%@",[chosenPreset valueForKey:@"PresetName"]]];
+        [fPresetSelectedDisplay setStringValue:[chosenPreset objectForKey:@"PresetName"]];
+        
         if ([[chosenPreset objectForKey:@"Default"] intValue] == 1)
         {
-            [fPresetSelectedDisplay setStringValue: [NSString stringWithFormat: @"%@ (Default)",[chosenPreset valueForKey:@"PresetName"]]];
+            [fPresetSelectedDisplay setStringValue:[NSString stringWithFormat:@"%@ (Default)", [chosenPreset objectForKey:@"PresetName"]]];
         }
         else
         {
-            [fPresetSelectedDisplay setStringValue: [NSString stringWithFormat: @"%@",[chosenPreset valueForKey:@"PresetName"]]];
+            [fPresetSelectedDisplay setStringValue:[chosenPreset objectForKey:@"PresetName"]];
         }
+        
         /* File Format */
-        [fDstFormatPopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"FileFormat"]]];
-        [self formatPopUpChanged: NULL];
+        [fDstFormatPopUp selectItemWithTitle:[chosenPreset objectForKey:@"FileFormat"]];
+        [self formatPopUpChanged:nil];
         
         /* Chapter Markers*/
         [fCreateChapterMarkers setState:[[chosenPreset objectForKey:@"ChapterMarkers"] intValue]];
@@ -3375,61 +5142,67 @@ if (item == nil)
         [fDstMp4LargeFileCheck setState:[[chosenPreset objectForKey:@"Mp4LargeFile"] intValue]];
         /* Mux mp4 with http optimization */
         [fDstMp4HttpOptFileCheck setState:[[chosenPreset objectForKey:@"Mp4HttpOptimize"] intValue]];
-        /* Set the state of ipod compatible with Mp4iPodCompatible */
-        [fDstMp4iPodFileCheck setState:[[chosenPreset objectForKey:@"Mp4iPodCompatible"] intValue]];
-        /* Codecs */
-        [fDstCodecsPopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"FileCodecs"]]];
-        [self codecsPopUpChanged: NULL];
         
         /* Video encoder */
         /* We set the advanced opt string here if applicable*/
-        [fAdvancedOptions setOptions: [NSString stringWithFormat:[chosenPreset valueForKey:@"x264Option"]]];
+        [fAdvancedOptions setOptions:[chosenPreset objectForKey:@"x264Option"]];
         /* We use a conditional to account for the new x264 encoder dropdown as well as presets made using legacy x264 settings*/
-        if ([[NSString stringWithFormat:[chosenPreset valueForKey:@"VideoEncoder"]] isEqualToString: @"x264 (h.264 Main)"] || [[NSString stringWithFormat:[chosenPreset valueForKey:@"VideoEncoder"]] isEqualToString: @"x264 (h.264 iPod)"])
+        if ([[chosenPreset objectForKey:@"VideoEncoder"] isEqualToString:@"x264 (h.264 Main)"] ||
+            [[chosenPreset objectForKey:@"VideoEncoder"] isEqualToString:@"x264 (h.264 iPod)"] ||
+            [[chosenPreset objectForKey:@"VideoEncoder"] isEqualToString:@"x264"])
         {
-            [fVidEncoderPopUp selectItemWithTitle: [NSString stringWithFormat:@"x264"]];
+            [fVidEncoderPopUp selectItemWithTitle:@"H.264 (x264)"];
             /* special case for legacy preset to check the new fDstMp4HttpOptFileCheck checkbox to set the ipod atom */
-            if ([[NSString stringWithFormat:[chosenPreset valueForKey:@"VideoEncoder"]] isEqualToString: @"x264 (h.264 iPod)"])
+            if ([[chosenPreset objectForKey:@"VideoEncoder"] isEqualToString:@"x264 (h.264 iPod)"])
             {
                 [fDstMp4iPodFileCheck setState:NSOnState];
                 /* We also need to add "level=30:" to the advanced opts string to set the correct level for the iPod when
                  encountering a legacy preset as it used to be handled separately from the opt string*/
-                [fAdvancedOptions setOptions: [NSString stringWithFormat:[@"level=30:" stringByAppendingString:[fAdvancedOptions optionsString]]]];
+                [fAdvancedOptions setOptions:[@"level=30:" stringByAppendingString:[fAdvancedOptions optionsString]]];
             }
             else
             {
                 [fDstMp4iPodFileCheck setState:NSOffState];
             }
         }
+        else if ([[chosenPreset objectForKey:@"VideoEncoder"] isEqualToString:@"FFmpeg"])
+        {
+            [fVidEncoderPopUp selectItemWithTitle:@"MPEG-4 (FFmpeg)"];
+        }
+        else if ([[chosenPreset objectForKey:@"VideoEncoder"] isEqualToString:@"XviD"])
+        {
+            [fVidEncoderPopUp selectItemWithTitle:@"MPEG-4 (XviD)"];
+        }
         else
         {
-            [fVidEncoderPopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"VideoEncoder"]]];
+            [fVidEncoderPopUp selectItemWithTitle:[chosenPreset objectForKey:@"VideoEncoder"]];
         }
         
         /* Lets run through the following functions to get variables set there */
-        [self encoderPopUpChanged: NULL];
-        
-        [self calculateBitrate: NULL];
+        [self videoEncoderPopUpChanged:nil];
+        /* Set the state of ipod compatible with Mp4iPodCompatible. Only for x264*/
+        [fDstMp4iPodFileCheck setState:[[chosenPreset objectForKey:@"Mp4iPodCompatible"] intValue]];
+        [self calculateBitrate:nil];
         
         /* Video quality */
         [fVidQualityMatrix selectCellAtRow:[[chosenPreset objectForKey:@"VideoQualityType"] intValue] column:0];
         
-        [fVidTargetSizeField setStringValue: [NSString stringWithFormat:[chosenPreset valueForKey:@"VideoTargetSize"]]];
-        [fVidBitrateField setStringValue: [NSString stringWithFormat:[chosenPreset valueForKey:@"VideoAvgBitrate"]]];
-        [fVidQualitySlider setFloatValue: [[chosenPreset valueForKey:@"VideoQualitySlider"] floatValue]];
+        [fVidTargetSizeField setStringValue:[chosenPreset objectForKey:@"VideoTargetSize"]];
+        [fVidBitrateField setStringValue:[chosenPreset objectForKey:@"VideoAvgBitrate"]];
+        [fVidQualitySlider setFloatValue:[[chosenPreset objectForKey:@"VideoQualitySlider"] floatValue]];
         
-        [self videoMatrixChanged: NULL];
+        [self videoMatrixChanged:nil];
         
         /* Video framerate */
         /* For video preset video framerate, we want to make sure that Same as source does not conflict with the
          detected framerate in the fVidRatePopUp so we use index 0*/
-        if ([[NSString stringWithFormat:[chosenPreset valueForKey:@"VideoFramerate"]] isEqualToString: @"Same as source"])
+        if ([[chosenPreset objectForKey:@"VideoFramerate"] isEqualToString:@"Same as source"])
         {
             [fVidRatePopUp selectItemAtIndex: 0];
         }
         else
         {
-            [fVidRatePopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"VideoFramerate"]]];
+            [fVidRatePopUp selectItemWithTitle:[chosenPreset objectForKey:@"VideoFramerate"]];
         }
         
         /* GrayScale */
@@ -3437,24 +5210,316 @@ if (item == nil)
         
         /* 2 Pass Encoding */
         [fVidTwoPassCheck setState:[[chosenPreset objectForKey:@"VideoTwoPass"] intValue]];
-        [self twoPassCheckboxChanged: NULL];
+        [self twoPassCheckboxChanged:nil];
         /* Turbo 1st pass for 2 Pass Encoding */
         [fVidTurboPassCheck setState:[[chosenPreset objectForKey:@"VideoTurboTwoPass"] intValue]];
         
         /*Audio*/
+        if ([chosenPreset objectForKey:@"FileCodecs"])
+        {
+            /* We need to handle the audio codec popup by determining what was chosen from the deprecated Codecs PopUp for past presets*/
+            if ([[chosenPreset objectForKey:@"FileCodecs"] isEqualToString: @"AVC/H.264 Video / AAC + AC3 Audio"])
+            {
+                /* We need to address setting languages etc. here in the new multi track audio panel */
+                /* Track One set here */
+                /*for track one though a track should be selected but lets check here anyway and use track one if its not.*/
+                if ([fAudLang1PopUp indexOfSelectedItem] == 0)
+                {
+                    [fAudLang1PopUp selectItemAtIndex: 1];
+                    [self audioTrackPopUpChanged: fAudLang1PopUp];
+                }
+                [fAudTrack1CodecPopUp selectItemWithTitle: @"AAC (faac)"];
+                [self audioTrackPopUpChanged: fAudTrack1CodecPopUp];
+                /* Track Two, set source same as track one */
+                [fAudLang2PopUp selectItemAtIndex: [fAudLang1PopUp indexOfSelectedItem]];
+                [self audioTrackPopUpChanged: fAudLang2PopUp];
+                [fAudTrack2CodecPopUp selectItemWithTitle: @"AC3 Passthru"];
+                [self audioTrackPopUpChanged: fAudTrack2CodecPopUp];
+            }
+            else if ([[chosenPreset objectForKey:@"FileCodecs"] isEqualToString:@"MPEG-4 Video / AAC Audio"] ||
+                     [[chosenPreset objectForKey:@"FileCodecs"] isEqualToString:@"AVC/H.264 Video / AAC Audio"])
+            {
+                if ([fAudLang1PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack1CodecPopUp selectItemWithTitle: @"AAC (faac)"];
+                    [self audioTrackPopUpChanged: fAudTrack1CodecPopUp];
+                }
+                if ([fAudLang2PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack2CodecPopUp selectItemWithTitle: @"AAC (faac)"];
+                    [self audioTrackPopUpChanged: fAudTrack2CodecPopUp];
+                }
+                if ([fAudLang3PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack3CodecPopUp selectItemWithTitle: @"AAC (faac)"];
+                    [self audioTrackPopUpChanged: fAudTrack3CodecPopUp];
+                }
+                if ([fAudLang4PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack4CodecPopUp selectItemWithTitle: @"AAC (faac)"];
+                    [self audioTrackPopUpChanged: fAudTrack4CodecPopUp];
+                }
+            }
+            else if ([[chosenPreset objectForKey:@"FileCodecs"] isEqualToString:@"MPEG-4 Video / AC-3 Audio"] ||
+                     [[chosenPreset objectForKey:@"FileCodecs"] isEqualToString:@"AVC/H.264 Video / AC-3 Audio"])
+            {
+                if ([fAudLang1PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack1CodecPopUp selectItemWithTitle: @"AC3 Passthru"];
+                    [self audioTrackPopUpChanged: fAudTrack1CodecPopUp];
+                }
+                if ([fAudLang2PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack2CodecPopUp selectItemWithTitle: @"AC3 Passthru"];
+                    [self audioTrackPopUpChanged: fAudTrack2CodecPopUp];
+                }
+                if ([fAudLang3PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack3CodecPopUp selectItemWithTitle: @"AC3 Passthru"];
+                    [self audioTrackPopUpChanged: fAudTrack3CodecPopUp];
+                }
+                if ([fAudLang4PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack4CodecPopUp selectItemWithTitle: @"AC3 Passthru"];
+                    [self audioTrackPopUpChanged: fAudTrack4CodecPopUp];
+                }
+            }
+            else if ([[chosenPreset objectForKey:@"FileCodecs"] isEqualToString:@"MPEG-4 Video / MP3 Audio"] ||
+                     [[chosenPreset objectForKey:@"FileCodecs"] isEqualToString:@"AVC/H.264 Video / MP3 Audio"])
+            {
+                if ([fAudLang1PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack1CodecPopUp selectItemWithTitle: @"MP3 (lame)"];
+                    [self audioTrackPopUpChanged: fAudTrack1CodecPopUp];
+                }
+                if ([fAudLang2PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack2CodecPopUp selectItemWithTitle: @"MP3 (lame)"];
+                    [self audioTrackPopUpChanged: fAudTrack2CodecPopUp];
+                }
+                if ([fAudLang3PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack3CodecPopUp selectItemWithTitle: @"MP3 (lame)"];
+                    [self audioTrackPopUpChanged: fAudTrack3CodecPopUp];
+                }
+                if ([fAudLang4PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack4CodecPopUp selectItemWithTitle: @"MP3 (lame)"];
+                    [self audioTrackPopUpChanged: fAudTrack4CodecPopUp];
+                }
+            }
+            else if ([[chosenPreset objectForKey:@"FileCodecs"] isEqualToString:@"MPEG-4 Video / Vorbis Audio"])
+            {
+                if ([fAudLang1PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack1CodecPopUp selectItemWithTitle: @"Vorbis (vorbis)"];
+                    [self audioTrackPopUpChanged: fAudTrack1CodecPopUp];
+                }
+                if ([fAudLang2PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack2CodecPopUp selectItemWithTitle: @"Vorbis (vorbis)"];
+                    [self audioTrackPopUpChanged: fAudTrack2CodecPopUp];
+                }
+                if ([fAudLang3PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack3CodecPopUp selectItemWithTitle: @"Vorbis (vorbis)"];
+                    [self audioTrackPopUpChanged: fAudTrack3CodecPopUp];
+                }
+                if ([fAudLang4PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack4CodecPopUp selectItemWithTitle: @"Vorbis (vorbis)"];
+                    [self audioTrackPopUpChanged: fAudTrack4CodecPopUp];
+                }
+            }
+            /* We detect here if we have the old audio sample rate and if so we apply samplerate and bitrate to the existing four tracks if chosen
+             * UNLESS the CodecPopUp is AC3 in which case the preset values are ignored in favor of rates set in audioTrackMixdownChanged*/
+            if ([chosenPreset objectForKey:@"AudioSampleRate"])
+            {
+                if ([fAudLang1PopUp indexOfSelectedItem] > 0 && [fAudTrack1CodecPopUp titleOfSelectedItem] != @"AC3 Passthru")
+                {
+                    [fAudTrack1RatePopUp selectItemWithTitle:[chosenPreset objectForKey:@"AudioSampleRate"]];
+                    [fAudTrack1BitratePopUp selectItemWithTitle:[chosenPreset objectForKey:@"AudioBitRate"]];
+                }
+                if ([fAudLang2PopUp indexOfSelectedItem] > 0 && [fAudTrack2CodecPopUp titleOfSelectedItem] != @"AC3 Passthru")
+                {
+                    [fAudTrack2RatePopUp selectItemWithTitle:[chosenPreset objectForKey:@"AudioSampleRate"]];
+                    [fAudTrack2BitratePopUp selectItemWithTitle:[chosenPreset objectForKey:@"AudioBitRate"]];
+                }
+                if ([fAudLang3PopUp indexOfSelectedItem] > 0 && [fAudTrack3CodecPopUp titleOfSelectedItem] != @"AC3 Passthru")
+                {
+                    [fAudTrack3RatePopUp selectItemWithTitle:[chosenPreset objectForKey:@"AudioSampleRate"]];
+                    [fAudTrack3BitratePopUp selectItemWithTitle:[chosenPreset objectForKey:@"AudioBitRate"]];
+                }
+                if ([fAudLang4PopUp indexOfSelectedItem] > 0 && [fAudTrack4CodecPopUp titleOfSelectedItem] != @"AC3 Passthru")
+                {
+                    [fAudTrack4RatePopUp selectItemWithTitle:[chosenPreset objectForKey:@"AudioSampleRate"]];
+                    [fAudTrack4BitratePopUp selectItemWithTitle:[chosenPreset objectForKey:@"AudioBitRate"]];
+                }
+            }
+            /* We detect here if we have the old DRC Slider and if so we apply it to the existing four tracks if chosen */
+            if ([chosenPreset objectForKey:@"AudioDRCSlider"])
+            {
+                if ([fAudLang1PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack1DrcSlider setFloatValue:[[chosenPreset objectForKey:@"AudioDRCSlider"] floatValue]];
+                    [self audioDRCSliderChanged: fAudTrack1DrcSlider];
+                }
+                if ([fAudLang2PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack2DrcSlider setFloatValue:[[chosenPreset objectForKey:@"AudioDRCSlider"] floatValue]];
+                    [self audioDRCSliderChanged: fAudTrack2DrcSlider];
+                }
+                if ([fAudLang3PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack3DrcSlider setFloatValue:[[chosenPreset objectForKey:@"AudioDRCSlider"] floatValue]];
+                    [self audioDRCSliderChanged: fAudTrack3DrcSlider];
+                }
+                if ([fAudLang4PopUp indexOfSelectedItem] > 0)
+                {
+                    [fAudTrack4DrcSlider setFloatValue:[[chosenPreset objectForKey:@"AudioDRCSlider"] floatValue]];
+                    [self audioDRCSliderChanged: fAudTrack4DrcSlider];
+                }
+            }
+        }
+        else // since there was no codecs key in the preset we know we can use new multi-audio track presets
+        {
+            if ([chosenPreset objectForKey:@"Audio1Track"] > 0)
+            {
+                if ([fAudLang1PopUp indexOfSelectedItem] == 0)
+                {
+                    [fAudLang1PopUp selectItemAtIndex: 1];
+                }
+                [self audioTrackPopUpChanged: fAudLang1PopUp];
+                [fAudTrack1CodecPopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio1Encoder"]];
+                [self audioTrackPopUpChanged: fAudTrack1CodecPopUp];
+                [fAudTrack1MixPopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio1Mixdown"]];
+                /* check to see if the selections was available, if not, rerun audioTrackPopUpChanged using the codec to just set the default
+                 * mixdown*/
+                if  ([fAudTrack1MixPopUp selectedItem] == nil)
+                {
+                    [self audioTrackPopUpChanged: fAudTrack1CodecPopUp];
+                }
+                [fAudTrack1RatePopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio1Samplerate"]];
+                /* We set the presets bitrate if it is *not* an AC3 track since that uses the input bitrate */
+                if (![[chosenPreset objectForKey:@"Audio1Encoder"] isEqualToString:@"AC3 Passthru"])
+                {
+                    [fAudTrack1BitratePopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio1Bitrate"]];
+                }
+                [fAudTrack1DrcSlider setFloatValue:[[chosenPreset objectForKey:@"Audio1TrackDRCSlider"] floatValue]];
+                [self audioDRCSliderChanged: fAudTrack1DrcSlider];
+            }
+            if ([chosenPreset objectForKey:@"Audio2Track"] > 0)
+            {
+                if ([fAudLang2PopUp indexOfSelectedItem] == 0)
+                {
+                    [fAudLang2PopUp selectItemAtIndex: 1];
+                }
+                [self audioTrackPopUpChanged: fAudLang2PopUp];
+                [fAudTrack2CodecPopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio2Encoder"]];
+                [self audioTrackPopUpChanged: fAudTrack2CodecPopUp];
+                [fAudTrack2MixPopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio2Mixdown"]];
+                /* check to see if the selections was available, if not, rerun audioTrackPopUpChanged using the codec to just set the default
+                 * mixdown*/
+                if  ([fAudTrack2MixPopUp selectedItem] == nil)
+                {
+                    [self audioTrackPopUpChanged: fAudTrack2CodecPopUp];
+                }
+                [fAudTrack2RatePopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio2Samplerate"]];
+                /* We set the presets bitrate if it is *not* an AC3 track since that uses the input bitrate */
+                if (![[chosenPreset objectForKey:@"Audio2Encoder"] isEqualToString:@"AC3 Passthru"])
+                {
+                    [fAudTrack2BitratePopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio2Bitrate"]];
+                }
+                [fAudTrack2DrcSlider setFloatValue:[[chosenPreset objectForKey:@"Audio2TrackDRCSlider"] floatValue]];
+                [self audioDRCSliderChanged: fAudTrack2DrcSlider];
+            }
+            if ([chosenPreset objectForKey:@"Audio3Track"] > 0)
+            {
+                if ([fAudLang3PopUp indexOfSelectedItem] == 0)
+                {
+                    [fAudLang3PopUp selectItemAtIndex: 1];
+                }
+                [self audioTrackPopUpChanged: fAudLang3PopUp];
+                [fAudTrack3CodecPopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio3Encoder"]];
+                [self audioTrackPopUpChanged: fAudTrack3CodecPopUp];
+                [fAudTrack3MixPopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio3Mixdown"]];
+                /* check to see if the selections was available, if not, rerun audioTrackPopUpChanged using the codec to just set the default
+                 * mixdown*/
+                if  ([fAudTrack3MixPopUp selectedItem] == nil)
+                {
+                    [self audioTrackPopUpChanged: fAudTrack3CodecPopUp];
+                }
+                [fAudTrack3RatePopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio3Samplerate"]];
+                /* We set the presets bitrate if it is *not* an AC3 track since that uses the input bitrate */
+                if (![[chosenPreset objectForKey:@"Audio3Encoder"] isEqualToString: @"AC3 Passthru"])
+                {
+                    [fAudTrack3BitratePopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio3Bitrate"]];
+                }
+                [fAudTrack3DrcSlider setFloatValue:[[chosenPreset objectForKey:@"Audio3TrackDRCSlider"] floatValue]];
+                [self audioDRCSliderChanged: fAudTrack3DrcSlider];
+            }
+            if ([chosenPreset objectForKey:@"Audio4Track"] > 0)
+            {
+                if ([fAudLang4PopUp indexOfSelectedItem] == 0)
+                {
+                    [fAudLang4PopUp selectItemAtIndex: 1];
+                }
+                [self audioTrackPopUpChanged: fAudLang4PopUp];
+                [fAudTrack4CodecPopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio4Encoder"]];
+                [self audioTrackPopUpChanged: fAudTrack4CodecPopUp];
+                [fAudTrack4MixPopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio4Mixdown"]];
+                /* check to see if the selections was available, if not, rerun audioTrackPopUpChanged using the codec to just set the default
+                 * mixdown*/
+                if  ([fAudTrack4MixPopUp selectedItem] == nil)
+                {
+                    [self audioTrackPopUpChanged: fAudTrack4CodecPopUp];
+                }
+                [fAudTrack4RatePopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio4Samplerate"]];
+                /* We set the presets bitrate if it is *not* an AC3 track since that uses the input bitrate */
+                if (![[chosenPreset objectForKey:@"Audio4Encoder"] isEqualToString:@"AC3 Passthru"])
+                {
+                    [fAudTrack4BitratePopUp selectItemWithTitle:[chosenPreset objectForKey:@"Audio4Bitrate"]];
+                }
+                [fAudTrack4DrcSlider setFloatValue:[[chosenPreset objectForKey:@"Audio4TrackDRCSlider"] floatValue]];
+                [self audioDRCSliderChanged: fAudTrack4DrcSlider];
+            }
+            
+            
+        }
+        
+        /* We now cleanup any extra audio tracks that may be previously set if we need to, we do it here so we don't have to
+         * duplicate any code for legacy presets.*/
+        /* First we handle the legacy Codecs crazy AVC/H.264 Video / AAC + AC3 Audio atv hybrid */
+        if ([chosenPreset objectForKey:@"FileCodecs"] && [[chosenPreset objectForKey:@"FileCodecs"] isEqualToString:@"AVC/H.264 Video / AAC + AC3 Audio"])
+        {
+            [fAudLang3PopUp selectItemAtIndex: 0];
+            [self audioTrackPopUpChanged: fAudLang3PopUp];
+            [fAudLang4PopUp selectItemAtIndex: 0];
+            [self audioTrackPopUpChanged: fAudLang4PopUp];
+        }
+        else
+        {
+            if (![chosenPreset objectForKey:@"Audio2Track"] || [chosenPreset objectForKey:@"Audio2Track"] == 0)
+            {
+                [fAudLang2PopUp selectItemAtIndex: 0];
+                [self audioTrackPopUpChanged: fAudLang2PopUp];
+            }
+            if (![chosenPreset objectForKey:@"Audio3Track"] || [chosenPreset objectForKey:@"Audio3Track"] > 0)
+            {
+                [fAudLang3PopUp selectItemAtIndex: 0];
+                [self audioTrackPopUpChanged: fAudLang3PopUp];
+            }
+            if (![chosenPreset objectForKey:@"Audio4Track"] || [chosenPreset objectForKey:@"Audio4Track"] > 0)
+            {
+                [fAudLang4PopUp selectItemAtIndex: 0];
+                [self audioTrackPopUpChanged: fAudLang4PopUp];
+            }
+        }
         
-        /* Audio Sample Rate*/
-        [fAudRatePopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"AudioSampleRate"]]];
-        /* Audio Bitrate Rate*/
-        [fAudBitratePopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"AudioBitRate"]]];
         /*Subtitles*/
-        [fSubPopUp selectItemWithTitle: [NSString stringWithFormat:[chosenPreset valueForKey:@"Subtitles"]]];
+        [fSubPopUp selectItemWithTitle:[chosenPreset objectForKey:@"Subtitles"]];
         /* Forced Subtitles */
         [fSubForcedCheck setState:[[chosenPreset objectForKey:@"SubtitlesForced"] intValue]];
-           
-        /* Dynamic Range Control Slider */
-        [fAudDrcSlider setFloatValue: [[chosenPreset valueForKey:@"AudioDRCSlider"] floatValue]];
-        [self audioDRCSliderChanged: NULL];
         
         /* Picture Settings */
         /* Note: objectForKey:@"UsesPictureSettings" now refers to picture size, this encompasses:
@@ -3469,11 +5534,37 @@ if (item == nil)
         if ([[chosenPreset objectForKey:@"UsesPictureSettings"]  intValue] > 0)
         {
             hb_job_t * job = fTitle->job;
+            
+            /* If Cropping is set to custom, then recall all four crop values from
+                 when the preset was created and apply them */
+                if ([[chosenPreset objectForKey:@"PictureAutoCrop"]  intValue] == 0)
+                {
+                    [fPictureController setAutoCrop:NO];
+                    
+                    /* Here we use the custom crop values saved at the time the preset was saved */
+                    job->crop[0] = [[chosenPreset objectForKey:@"PictureTopCrop"]  intValue];
+                    job->crop[1] = [[chosenPreset objectForKey:@"PictureBottomCrop"]  intValue];
+                    job->crop[2] = [[chosenPreset objectForKey:@"PictureLeftCrop"]  intValue];
+                    job->crop[3] = [[chosenPreset objectForKey:@"PictureRightCrop"]  intValue];
+                    
+                }
+                else /* if auto crop has been saved in preset, set to auto and use post scan auto crop */
+                {
+                    [fPictureController setAutoCrop:YES];
+                    /* Here we use the auto crop values determined right after scan */
+                    job->crop[0] = AutoCropTop;
+                    job->crop[1] = AutoCropBottom;
+                    job->crop[2] = AutoCropLeft;
+                    job->crop[3] = AutoCropRight;
+                    
+                }
+
+            
             /* Check to see if the objectForKey:@"UsesPictureSettings is 2 which is "Use Max for the source */
             if ([[chosenPreset objectForKey:@"UsesPictureSettings"]  intValue] == 2 || [[chosenPreset objectForKey:@"UsesMaxPictureSettings"]  intValue] == 1)
             {
                 /* Use Max Picture settings for whatever the dvd is.*/
-                [self revertPictureSizeToMax: NULL];
+                [self revertPictureSizeToMax:nil];
                 job->keep_ratio = [[chosenPreset objectForKey:@"PictureKeepRatio"]  intValue];
                 if (job->keep_ratio == 1)
                 {
@@ -3514,30 +5605,7 @@ if (item == nil)
                 job->pixel_ratio = [[chosenPreset objectForKey:@"PicturePAR"]  intValue];
                 
                 
-                /* If Cropping is set to custom, then recall all four crop values from
-                 when the preset was created and apply them */
-                if ([[chosenPreset objectForKey:@"PictureAutoCrop"]  intValue] == 0)
-                {
-                    [fPictureController setAutoCrop:NO];
-                    
-                    /* Here we use the custom crop values saved at the time the preset was saved */
-                    job->crop[0] = [[chosenPreset objectForKey:@"PictureTopCrop"]  intValue];
-                    job->crop[1] = [[chosenPreset objectForKey:@"PictureBottomCrop"]  intValue];
-                    job->crop[2] = [[chosenPreset objectForKey:@"PictureLeftCrop"]  intValue];
-                    job->crop[3] = [[chosenPreset objectForKey:@"PictureRightCrop"]  intValue];
-                    
-                }
-                else /* if auto crop has been saved in preset, set to auto and use post scan auto crop */
-                {
-                    [fPictureController setAutoCrop:YES];
-                    /* Here we use the auto crop values determined right after scan */
-                    job->crop[0] = AutoCropTop;
-                    job->crop[1] = AutoCropBottom;
-                    job->crop[2] = AutoCropLeft;
-                    job->crop[3] = AutoCropRight;
-                    
-                }
-                /* If the preset has no objectForKey:@"UsesPictureFilters", then we know it is a legacy preset
+                                /* If the preset has no objectForKey:@"UsesPictureFilters", then we know it is a legacy preset
                  * and handle the filters here as before.
                  * NOTE: This should be removed when the update presets code is done as we can be assured that legacy
                  * presets are updated to work properly with new keys.
@@ -3549,14 +5617,14 @@ if (item == nil)
                     if ([chosenPreset objectForKey:@"PictureDeinterlace"])
                     {
                         /* We check to see if the preset used the past fourth "Slowest" deinterlaceing and set that to "Slower
-                        * since we no longer have a fourth "Slowest" deinterlacing due to the mcdeint bug */
+                         * since we no longer have a fourth "Slowest" deinterlacing due to the mcdeint bug */
                         if ([[chosenPreset objectForKey:@"PictureDeinterlace"] intValue] == 4)
                         {
                             [fPictureController setDeinterlace:3];
                         }
                         else
                         {
-
+                            
                             [fPictureController setDeinterlace:[[chosenPreset objectForKey:@"PictureDeinterlace"] intValue]];
                         }
                     }
@@ -3567,12 +5635,11 @@ if (item == nil)
                     /* VFR */
                     if ([[chosenPreset objectForKey:@"VFR"] intValue] == 1)
                     {
-                        [fPictureController setVFR:[[chosenPreset objectForKey:@"VFR"] intValue]];
-                    }
-                    else
-                    {
-                        [fPictureController setVFR:0];
+                        // We make sure that framerate is set to Same as source variable
+                        // detelecine will take care of itself right below
+                        //[fPictureController setVFR:[[chosenPreset objectForKey:@"VFR"] intValue]];
                     }
+                    
                     /* Detelecine */
                     if ([[chosenPreset objectForKey:@"PictureDetelecine"] intValue] == 1)
                     {
@@ -3594,13 +5661,16 @@ if (item == nil)
                     /* Deblock */
                     if ([[chosenPreset objectForKey:@"PictureDeblock"] intValue] == 1)
                     {
-                        [fPictureController setDeblock:[[chosenPreset objectForKey:@"PictureDeblock"] intValue]];
+                        /* since we used to use 1 to turn on deblock, we now use a 5 in our sliding scale */
+                        [fPictureController setDeblock:5];
                     }
                     else
                     {
                         [fPictureController setDeblock:0];
-                    }             
-                    [self calculatePictureSizing: NULL];
+                        
+                    }
+                    
+                    [self calculatePictureSizing:nil];
                 }
                 
             }
@@ -3631,15 +5701,7 @@ if (item == nil)
             {
                 [fPictureController setDeinterlace:0];
             }
-            /* VFR */
-            if ([[chosenPreset objectForKey:@"VFR"] intValue] == 1)
-            {
-                [fPictureController setVFR:[[chosenPreset objectForKey:@"VFR"] intValue]];
-            }
-            else
-            {
-                [fPictureController setVFR:0];
-            }
+            
             /* Detelecine */
             if ([[chosenPreset objectForKey:@"PictureDetelecine"] intValue] == 1)
             {
@@ -3661,15 +5723,27 @@ if (item == nil)
             /* Deblock */
             if ([[chosenPreset objectForKey:@"PictureDeblock"] intValue] == 1)
             {
+                /* if its a one, then its the old on/off deblock, set on to 5*/
+                [fPictureController setDeblock:5];
+            }
+            else
+            {
+                /* use the settings intValue */
                 [fPictureController setDeblock:[[chosenPreset objectForKey:@"PictureDeblock"] intValue]];
             }
+            /* Decomb */
+            /* Even though we currently allow for a custom setting for decomb, ultimately it will only have Off and
+             * Default so we just pay attention to anything greater than 0 as 1 (Default). 0 is Off. */
+            if ([[chosenPreset objectForKey:@"PictureDecomb"] intValue] > 0)
+            {
+                [fPictureController setDecomb:1];
+            }
             else
             {
-                [fPictureController setDeblock:0];
-            }             
+                [fPictureController setDecomb:0];
+            }
         }
-        [self calculatePictureSizing: NULL];
-        [[fPresetsActionMenu itemAtIndex:0] setEnabled: YES];
+        [self calculatePictureSizing:nil];
     }
 }
 
@@ -3684,16 +5758,16 @@ if (item == nil)
     UserPresetsFile = @"~/Library/Application Support/HandBrake/UserPresets.plist";
        UserPresetsFile = [[UserPresetsFile stringByExpandingTildeInPath]retain];
     /* We check for the presets.plist */
-       if ([fileManager fileExistsAtPath:UserPresetsFile] == 0) 
+       if ([fileManager fileExistsAtPath:UserPresetsFile] == 0)
        {
                [fileManager createFileAtPath:UserPresetsFile contents:nil attributes:nil];
        }
-               
+
        UserPresets = [[NSMutableArray alloc] initWithContentsOfFile:UserPresetsFile];
-       if (nil == UserPresets) 
+       if (nil == UserPresets)
        {
                UserPresets = [[NSMutableArray alloc] init];
-               [self addFactoryPresets:NULL];
+               [self addFactoryPresets:nil];
        }
        [fPresetsOutlineView reloadData];
 }
@@ -3712,11 +5786,13 @@ if (item == nil)
     [fPresetNewPicSettingsPopUp selectItemAtIndex: 0]; 
     /* Uncheck the preset use filters checkbox */
     [fPresetNewPicFiltersCheck setState:NSOffState];
+    // fPresetNewFolderCheck
+    [fPresetNewFolderCheck setState:NSOffState];
     /* Erase info from the input fields*/
        [fPresetNewName setStringValue: @""];
        [fPresetNewDesc setStringValue: @""];
        /* Show the panel */
-       [NSApp beginSheet: fAddPresetPanel modalForWindow: fWindow modalDelegate: NULL didEndSelector: NULL contextInfo: NULL];
+       [NSApp beginSheet:fAddPresetPanel modalForWindow:fWindow modalDelegate:nil didEndSelector:NULL contextInfo:NULL];
 }
 
 - (IBAction) closeAddPresetPanel: (id) sender
@@ -3734,29 +5810,40 @@ if (item == nil)
         /* Here we create a custom user preset */
         [UserPresets addObject:[self createPreset]];
         [self addPreset];
-        
-        [self closeAddPresetPanel:NULL];
+
+        [self closeAddPresetPanel:nil];
     }
 }
 - (void)addPreset
 {
 
        
+       /* We Reload the New Table data for presets */
+    [fPresetsOutlineView reloadData];
+   /* We save all of the preset data here */
+    [self savePreset];
+}
+
+- (void)sortPresets
+{
+
+       
        /* We Sort the Presets By Factory or Custom */
        NSSortDescriptor * presetTypeDescriptor=[[[NSSortDescriptor alloc] initWithKey:@"Type" 
                                                     ascending:YES] autorelease];
-       /* We Sort the Presets Alphabetically by name */
-       NSSortDescriptor * presetNameDescriptor=[[[NSSortDescriptor alloc] initWithKey:@"PresetName" 
+       /* We Sort the Presets Alphabetically by name  We do not use this now as we have drag and drop*/
+       /*
+    NSSortDescriptor * presetNameDescriptor=[[[NSSortDescriptor alloc] initWithKey:@"PresetName" 
                                                     ascending:YES selector:@selector(caseInsensitiveCompare:)] autorelease];
-       NSArray *sortDescriptors=[NSArray arrayWithObjects:presetTypeDescriptor,presetNameDescriptor,nil];
+       //NSArray *sortDescriptors=[NSArray arrayWithObjects:presetTypeDescriptor,presetNameDescriptor,nil];
+    
+    */
+    /* Since we can drag and drop our custom presets, lets just sort by type and not name */
+    NSArray *sortDescriptors=[NSArray arrayWithObjects:presetTypeDescriptor,nil];
        NSArray *sortedArray=[UserPresets sortedArrayUsingDescriptors:sortDescriptors];
        [UserPresets setArray:sortedArray];
        
-       
-       /* We Reload the New Table data for presets */
-    [fPresetsOutlineView reloadData];
-   /* We save all of the preset data here */
-    [self savePreset];
+
 }
 
 - (IBAction)insertPreset:(id)sender
@@ -3772,133 +5859,196 @@ if (item == nil)
     NSMutableDictionary *preset = [[NSMutableDictionary alloc] init];
        /* Get the New Preset Name from the field in the AddPresetPanel */
     [preset setObject:[fPresetNewName stringValue] forKey:@"PresetName"];
+    /* Set whether or not this is to be a folder fPresetNewFolderCheck*/
+    [preset setObject:[NSNumber numberWithBool:[fPresetNewFolderCheck state]] forKey:@"Folder"];
        /*Set whether or not this is a user preset or factory 0 is factory, 1 is user*/
        [preset setObject:[NSNumber numberWithInt:1] forKey:@"Type"];
        /*Set whether or not this is default, at creation set to 0*/
        [preset setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
-       /*Get the whether or not to apply pic Size and Cropping (includes Anamorphic)*/
-       [preset setObject:[NSNumber numberWithInt:[fPresetNewPicSettingsPopUp indexOfSelectedItem]] forKey:@"UsesPictureSettings"];
-    /* Get whether or not to use the current Picture Filter settings for the preset */
-    [preset setObject:[NSNumber numberWithInt:[fPresetNewPicFiltersCheck state]] forKey:@"UsesPictureFilters"];
-    /* Get New Preset Description from the field in the AddPresetPanel*/
-       [preset setObject:[fPresetNewDesc stringValue] forKey:@"PresetDescription"];
-       /* File Format */
-    [preset setObject:[fDstFormatPopUp titleOfSelectedItem] forKey:@"FileFormat"];
-       /* Chapter Markers fCreateChapterMarkers*/
-       [preset setObject:[NSNumber numberWithInt:[fCreateChapterMarkers state]] forKey:@"ChapterMarkers"];
-       /* Allow Mpeg4 64 bit formatting +4GB file sizes */
-       [preset setObject:[NSNumber numberWithInt:[fDstMp4LargeFileCheck state]] forKey:@"Mp4LargeFile"];
-    /* Mux mp4 with http optimization */
-    [preset setObject:[NSNumber numberWithInt:[fDstMp4HttpOptFileCheck state]] forKey:@"Mp4HttpOptimize"];
-    /* Add iPod uuid atom */
-    [preset setObject:[NSNumber numberWithInt:[fDstMp4iPodFileCheck state]] forKey:@"Mp4iPodCompatible"];
-    
-    /* Codecs */
-       [preset setObject:[fDstCodecsPopUp titleOfSelectedItem] forKey:@"FileCodecs"];
-       /* Video encoder */
-       [preset setObject:[fVidEncoderPopUp titleOfSelectedItem] forKey:@"VideoEncoder"];
-       /* x264 Option String */
-       [preset setObject:[fAdvancedOptions optionsString] forKey:@"x264Option"];
-       
-       [preset setObject:[NSNumber numberWithInt:[fVidQualityMatrix selectedRow]] forKey:@"VideoQualityType"];
-       [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
-       [preset setObject:[fVidBitrateField stringValue] forKey:@"VideoAvgBitrate"];
-       [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
-       
-       /* Video framerate */
-    if ([fVidRatePopUp indexOfSelectedItem] == 0) // Same as source is selected
-       {
-    [preset setObject:[NSString stringWithFormat: @"Same as source"] forKey:@"VideoFramerate"];
+    if ([fPresetNewFolderCheck state] == YES)
+    {
+        /* initialize and set an empty array for children here since we are a new folder */
+        NSMutableArray *childrenArray = [[NSMutableArray alloc] init];
+        [preset setObject:[NSMutableArray arrayWithArray: childrenArray] forKey:@"ChildrenArray"];
+        [childrenArray autorelease];
     }
-    else // we can record the actual titleOfSelectedItem
+    else // we are not creating a preset folder, so we go ahead with the rest of the preset info
     {
-    [preset setObject:[fVidRatePopUp titleOfSelectedItem] forKey:@"VideoFramerate"];
+        /*Get the whether or not to apply pic Size and Cropping (includes Anamorphic)*/
+        [preset setObject:[NSNumber numberWithInt:[fPresetNewPicSettingsPopUp indexOfSelectedItem]] forKey:@"UsesPictureSettings"];
+        /* Get whether or not to use the current Picture Filter settings for the preset */
+        [preset setObject:[NSNumber numberWithInt:[fPresetNewPicFiltersCheck state]] forKey:@"UsesPictureFilters"];
+        
+        /* Get New Preset Description from the field in the AddPresetPanel*/
+        [preset setObject:[fPresetNewDesc stringValue] forKey:@"PresetDescription"];
+        /* File Format */
+        [preset setObject:[fDstFormatPopUp titleOfSelectedItem] forKey:@"FileFormat"];
+        /* Chapter Markers fCreateChapterMarkers*/
+        [preset setObject:[NSNumber numberWithInt:[fCreateChapterMarkers state]] forKey:@"ChapterMarkers"];
+        /* Allow Mpeg4 64 bit formatting +4GB file sizes */
+        [preset setObject:[NSNumber numberWithInt:[fDstMp4LargeFileCheck state]] forKey:@"Mp4LargeFile"];
+        /* Mux mp4 with http optimization */
+        [preset setObject:[NSNumber numberWithInt:[fDstMp4HttpOptFileCheck state]] forKey:@"Mp4HttpOptimize"];
+        /* Add iPod uuid atom */
+        [preset setObject:[NSNumber numberWithInt:[fDstMp4iPodFileCheck state]] forKey:@"Mp4iPodCompatible"];
+        
+        /* Codecs */
+        /* Video encoder */
+        [preset setObject:[fVidEncoderPopUp titleOfSelectedItem] forKey:@"VideoEncoder"];
+        /* x264 Option String */
+        [preset setObject:[fAdvancedOptions optionsString] forKey:@"x264Option"];
+        
+        [preset setObject:[NSNumber numberWithInt:[fVidQualityMatrix selectedRow]] forKey:@"VideoQualityType"];
+        [preset setObject:[fVidTargetSizeField stringValue] forKey:@"VideoTargetSize"];
+        [preset setObject:[fVidBitrateField stringValue] forKey:@"VideoAvgBitrate"];
+        [preset setObject:[NSNumber numberWithFloat:[fVidQualitySlider floatValue]] forKey:@"VideoQualitySlider"];
+        
+        /* Video framerate */
+        if ([fVidRatePopUp indexOfSelectedItem] == 0) // Same as source is selected
+        {
+            [preset setObject:@"Same as source" forKey:@"VideoFramerate"];
+        }
+        else // we can record the actual titleOfSelectedItem
+        {
+            [preset setObject:[fVidRatePopUp titleOfSelectedItem] forKey:@"VideoFramerate"];
+        }
+        /* GrayScale */
+        [preset setObject:[NSNumber numberWithInt:[fVidGrayscaleCheck state]] forKey:@"VideoGrayScale"];
+        /* 2 Pass Encoding */
+        [preset setObject:[NSNumber numberWithInt:[fVidTwoPassCheck state]] forKey:@"VideoTwoPass"];
+        /* Turbo 2 pass Encoding fVidTurboPassCheck*/
+        [preset setObject:[NSNumber numberWithInt:[fVidTurboPassCheck state]] forKey:@"VideoTurboTwoPass"];
+        /*Picture Settings*/
+        hb_job_t * job = fTitle->job;
+        /* Picture Sizing */
+        /* Use Max Picture settings for whatever the dvd is.*/
+        [preset setObject:[NSNumber numberWithInt:0] forKey:@"UsesMaxPictureSettings"];
+        [preset setObject:[NSNumber numberWithInt:fTitle->job->width] forKey:@"PictureWidth"];
+        [preset setObject:[NSNumber numberWithInt:fTitle->job->height] forKey:@"PictureHeight"];
+        [preset setObject:[NSNumber numberWithInt:fTitle->job->keep_ratio] forKey:@"PictureKeepRatio"];
+        [preset setObject:[NSNumber numberWithInt:fTitle->job->pixel_ratio] forKey:@"PicturePAR"];
+        
+        /* Set crop settings here */
+        [preset setObject:[NSNumber numberWithInt:[fPictureController autoCrop]] forKey:@"PictureAutoCrop"];
+        [preset setObject:[NSNumber numberWithInt:job->crop[0]] forKey:@"PictureTopCrop"];
+        [preset setObject:[NSNumber numberWithInt:job->crop[1]] forKey:@"PictureBottomCrop"];
+        [preset setObject:[NSNumber numberWithInt:job->crop[2]] forKey:@"PictureLeftCrop"];
+        [preset setObject:[NSNumber numberWithInt:job->crop[3]] forKey:@"PictureRightCrop"];
+        
+        /* Picture Filters */
+        [preset setObject:[NSNumber numberWithInt:[fPictureController deinterlace]] forKey:@"PictureDeinterlace"];
+        [preset setObject:[NSNumber numberWithInt:[fPictureController detelecine]] forKey:@"PictureDetelecine"];
+        //[preset setObject:[NSNumber numberWithInt:[fPictureController vfr]] forKey:@"VFR"];
+        [preset setObject:[NSNumber numberWithInt:[fPictureController denoise]] forKey:@"PictureDenoise"];
+        [preset setObject:[NSNumber numberWithInt:[fPictureController deblock]] forKey:@"PictureDeblock"]; 
+        [preset setObject:[NSNumber numberWithInt:[fPictureController decomb]] forKey:@"PictureDecomb"];
+        
+        
+        /*Audio*/
+        if ([fAudLang1PopUp indexOfSelectedItem] > 0)
+        {
+            [preset setObject:[NSNumber numberWithInt:[fAudLang1PopUp indexOfSelectedItem]] forKey:@"Audio1Track"];
+            [preset setObject:[fAudLang1PopUp titleOfSelectedItem] forKey:@"Audio1TrackDescription"];
+            [preset setObject:[fAudTrack1CodecPopUp titleOfSelectedItem] forKey:@"Audio1Encoder"];
+            [preset setObject:[fAudTrack1MixPopUp titleOfSelectedItem] forKey:@"Audio1Mixdown"];
+            [preset setObject:[fAudTrack1RatePopUp titleOfSelectedItem] forKey:@"Audio1Samplerate"];
+            [preset setObject:[fAudTrack1BitratePopUp titleOfSelectedItem] forKey:@"Audio1Bitrate"];
+            [preset setObject:[NSNumber numberWithFloat:[fAudTrack1DrcSlider floatValue]] forKey:@"Audio1TrackDRCSlider"];
+        }
+        if ([fAudLang2PopUp indexOfSelectedItem] > 0)
+        {
+            [preset setObject:[NSNumber numberWithInt:[fAudLang2PopUp indexOfSelectedItem]] forKey:@"Audio2Track"];
+            [preset setObject:[fAudLang2PopUp titleOfSelectedItem] forKey:@"Audio2TrackDescription"];
+            [preset setObject:[fAudTrack2CodecPopUp titleOfSelectedItem] forKey:@"Audio2Encoder"];
+            [preset setObject:[fAudTrack2MixPopUp titleOfSelectedItem] forKey:@"Audio2Mixdown"];
+            [preset setObject:[fAudTrack2RatePopUp titleOfSelectedItem] forKey:@"Audio2Samplerate"];
+            [preset setObject:[fAudTrack2BitratePopUp titleOfSelectedItem] forKey:@"Audio2Bitrate"];
+            [preset setObject:[NSNumber numberWithFloat:[fAudTrack2DrcSlider floatValue]] forKey:@"Audio2TrackDRCSlider"];
+        }
+        if ([fAudLang3PopUp indexOfSelectedItem] > 0)
+        {
+            [preset setObject:[NSNumber numberWithInt:[fAudLang3PopUp indexOfSelectedItem]] forKey:@"Audio3Track"];
+            [preset setObject:[fAudLang3PopUp titleOfSelectedItem] forKey:@"Audio3TrackDescription"];
+            [preset setObject:[fAudTrack3CodecPopUp titleOfSelectedItem] forKey:@"Audio3Encoder"];
+            [preset setObject:[fAudTrack3MixPopUp titleOfSelectedItem] forKey:@"Audio3Mixdown"];
+            [preset setObject:[fAudTrack3RatePopUp titleOfSelectedItem] forKey:@"Audio3Samplerate"];
+            [preset setObject:[fAudTrack3BitratePopUp titleOfSelectedItem] forKey:@"Audio3Bitrate"];
+            [preset setObject:[NSNumber numberWithFloat:[fAudTrack3DrcSlider floatValue]] forKey:@"Audio3TrackDRCSlider"];
+        }
+        if ([fAudLang4PopUp indexOfSelectedItem] > 0)
+        {
+            [preset setObject:[NSNumber numberWithInt:[fAudLang4PopUp indexOfSelectedItem]] forKey:@"Audio4Track"];
+            [preset setObject:[fAudLang4PopUp titleOfSelectedItem] forKey:@"Audio4TrackDescription"];
+            [preset setObject:[fAudTrack4CodecPopUp titleOfSelectedItem] forKey:@"Audio4Encoder"];
+            [preset setObject:[fAudTrack4MixPopUp titleOfSelectedItem] forKey:@"Audio4Mixdown"];
+            [preset setObject:[fAudTrack4RatePopUp titleOfSelectedItem] forKey:@"Audio4Samplerate"];
+            [preset setObject:[fAudTrack4BitratePopUp titleOfSelectedItem] forKey:@"Audio4Bitrate"];
+            [preset setObject:[NSNumber numberWithFloat:[fAudTrack4DrcSlider floatValue]] forKey:@"Audio4TrackDRCSlider"];
+        }
+        
+        /* Subtitles*/
+        [preset setObject:[fSubPopUp titleOfSelectedItem] forKey:@"Subtitles"];
+        /* Forced Subtitles */
+        [preset setObject:[NSNumber numberWithInt:[fSubForcedCheck state]] forKey:@"SubtitlesForced"];
     }
-       /* GrayScale */
-       [preset setObject:[NSNumber numberWithInt:[fVidGrayscaleCheck state]] forKey:@"VideoGrayScale"];
-       /* 2 Pass Encoding */
-       [preset setObject:[NSNumber numberWithInt:[fVidTwoPassCheck state]] forKey:@"VideoTwoPass"];
-       /* Turbo 2 pass Encoding fVidTurboPassCheck*/
-       [preset setObject:[NSNumber numberWithInt:[fVidTurboPassCheck state]] forKey:@"VideoTurboTwoPass"];
-       /*Picture Settings*/
-       hb_job_t * job = fTitle->job;
-       /* Picture Sizing */
-       /* Use Max Picture settings for whatever the dvd is.*/
-       [preset setObject:[NSNumber numberWithInt:0] forKey:@"UsesMaxPictureSettings"];
-       [preset setObject:[NSNumber numberWithInt:fTitle->job->width] forKey:@"PictureWidth"];
-       [preset setObject:[NSNumber numberWithInt:fTitle->job->height] forKey:@"PictureHeight"];
-       [preset setObject:[NSNumber numberWithInt:fTitle->job->keep_ratio] forKey:@"PictureKeepRatio"];
-       [preset setObject:[NSNumber numberWithInt:fTitle->job->pixel_ratio] forKey:@"PicturePAR"];
-    
-    /* Set crop settings here */
-       [preset setObject:[NSNumber numberWithInt:[fPictureController autoCrop]] forKey:@"PictureAutoCrop"];
-    [preset setObject:[NSNumber numberWithInt:job->crop[0]] forKey:@"PictureTopCrop"];
-    [preset setObject:[NSNumber numberWithInt:job->crop[1]] forKey:@"PictureBottomCrop"];
-       [preset setObject:[NSNumber numberWithInt:job->crop[2]] forKey:@"PictureLeftCrop"];
-       [preset setObject:[NSNumber numberWithInt:job->crop[3]] forKey:@"PictureRightCrop"];
-    
-    /* Picture Filters */
-    [preset setObject:[NSNumber numberWithInt:[fPictureController deinterlace]] forKey:@"PictureDeinterlace"];
-       [preset setObject:[NSNumber numberWithInt:[fPictureController detelecine]] forKey:@"PictureDetelecine"];
-    [preset setObject:[NSNumber numberWithInt:[fPictureController vfr]] forKey:@"VFR"];
-       [preset setObject:[NSNumber numberWithInt:[fPictureController denoise]] forKey:@"PictureDenoise"];
-    [preset setObject:[NSNumber numberWithInt:[fPictureController deblock]] forKey:@"PictureDeblock"];
-    
-
-       
-       /*Audio*/
-       /* Audio Sample Rate*/
-       [preset setObject:[fAudRatePopUp titleOfSelectedItem] forKey:@"AudioSampleRate"];
-       /* Audio Bitrate Rate*/
-       [preset setObject:[fAudBitratePopUp titleOfSelectedItem] forKey:@"AudioBitRate"];
-       /* Subtitles*/
-       [preset setObject:[fSubPopUp titleOfSelectedItem] forKey:@"Subtitles"];
-    /* Forced Subtitles */
-       [preset setObject:[NSNumber numberWithInt:[fSubForcedCheck state]] forKey:@"SubtitlesForced"];
-    /* Dynamic Range Control Slider */
-    [preset setObject:[NSNumber numberWithFloat:[fAudDrcSlider floatValue]] forKey:@"AudioDRCSlider"];
-       
-
     [preset autorelease];
     return preset;
-
+    
 }
 
 - (void)savePreset
 {
     [UserPresets writeToFile:UserPresetsFile atomically:YES];
        /* We get the default preset in case it changed */
-       [self getDefaultPresets: NULL];
+       [self getDefaultPresets:nil];
 
 }
 
 - (IBAction)deletePreset:(id)sender
 {
-    int status;
-    NSEnumerator *enumerator;
-    NSNumber *index;
-    NSMutableArray *tempArray;
-    id tempObject;
+    
     
     if ( [fPresetsOutlineView numberOfSelectedRows] == 0 )
+    {
         return;
+    }
     /* Alert user before deleting preset */
-       /* Comment out for now, tie to user pref eventually */
-
-    //NSBeep();
+       int status;
     status = NSRunAlertPanel(@"Warning!", @"Are you sure that you want to delete the selected preset?", @"OK", @"Cancel", nil);
     
-    if ( status == NSAlertDefaultReturn ) {
-        enumerator = [fPresetsOutlineView selectedRowEnumerator];
+    if ( status == NSAlertDefaultReturn ) 
+    {
+        int presetToModLevel = [fPresetsOutlineView levelForItem: [fPresetsOutlineView itemAtRow:[fPresetsOutlineView selectedRow]]];
+        NSDictionary *presetToMod = [fPresetsOutlineView itemAtRow:[fPresetsOutlineView selectedRow]];
+        NSDictionary *presetToModParent = [fPresetsOutlineView parentForItem: presetToMod];
+        
+        NSEnumerator *enumerator;
+        NSMutableArray *presetsArrayToMod;
+        NSMutableArray *tempArray;
+        id tempObject;
+        /* If we are a root level preset, we are modding the UserPresets array */
+        if (presetToModLevel == 0)
+        {
+            presetsArrayToMod = UserPresets;
+        }
+        else // We have a parent preset, so we modify the chidren array object for key
+        {
+            presetsArrayToMod = [presetToModParent objectForKey:@"ChildrenArray"]; 
+        }
+        
+        enumerator = [presetsArrayToMod objectEnumerator];
         tempArray = [NSMutableArray array];
         
-        while ( (index = [enumerator nextObject]) ) {
-            tempObject = [UserPresets objectAtIndex:[index intValue]];
-            [tempArray addObject:tempObject];
+        while (tempObject = [enumerator nextObject]) 
+        {
+            NSDictionary *thisPresetDict = tempObject;
+            if (thisPresetDict == presetToMod)
+            {
+                [tempArray addObject:tempObject];
+            }
         }
         
-        [UserPresets removeObjectsInArray:tempArray];
+        [presetsArrayToMod removeObjectsInArray:tempArray];
         [fPresetsOutlineView reloadData];
         [self savePreset];   
     }
@@ -3909,67 +6059,224 @@ if (item == nil)
 
 - (IBAction)getDefaultPresets:(id)sender
 {
-       int i = 0;
+       presetHbDefault = nil;
+    presetUserDefault = nil;
+    presetUserDefaultParent = nil;
+    presetUserDefaultParentParent = nil;
+    NSMutableDictionary *presetHbDefaultParent = nil;
+    NSMutableDictionary *presetHbDefaultParentParent = nil;
+    
+    int i = 0;
+    BOOL userDefaultFound = NO;
+    presetCurrentBuiltInCount = 0;
+    /* First we iterate through the root UserPresets array to check for defaults */
     NSEnumerator *enumerator = [UserPresets objectEnumerator];
        id tempObject;
        while (tempObject = [enumerator nextObject])
        {
-               NSDictionary *thisPresetDict = tempObject;
+               NSMutableDictionary *thisPresetDict = tempObject;
                if ([[thisPresetDict objectForKey:@"Default"] intValue] == 1) // 1 is HB default
                {
-                       presetHbDefault = i;    
+                       presetHbDefault = thisPresetDict;       
                }
                if ([[thisPresetDict objectForKey:@"Default"] intValue] == 2) // 2 is User specified default
                {
-                       presetUserDefault = i;  
+                       presetUserDefault = thisPresetDict;
+            userDefaultFound = YES;
+        }
+        if ([[thisPresetDict objectForKey:@"Type"] intValue] == 0) // Type 0 is a built in preset              
+        {
+                       presetCurrentBuiltInCount++; // <--increment the current number of built in presets     
                }
                i++;
+        
+        /* if we run into a folder, go to level 1 and iterate through the children arrays for the default */
+        if ([thisPresetDict objectForKey:@"ChildrenArray"])
+        {
+            NSMutableDictionary *thisPresetDictParent = thisPresetDict;
+            NSEnumerator *enumerator = [[thisPresetDict objectForKey:@"ChildrenArray"] objectEnumerator];
+            id tempObject;
+            while (tempObject = [enumerator nextObject])
+            {
+                NSMutableDictionary *thisPresetDict = tempObject;
+                if ([[thisPresetDict objectForKey:@"Default"] intValue] == 1) // 1 is HB default
+                {
+                    presetHbDefault = thisPresetDict;
+                    presetHbDefaultParent = thisPresetDictParent;
+                }
+                if ([[thisPresetDict objectForKey:@"Default"] intValue] == 2) // 2 is User specified default
+                {
+                    presetUserDefault = thisPresetDict;
+                    presetUserDefaultParent = thisPresetDictParent;
+                    userDefaultFound = YES;
+                }
+                
+                /* if we run into a folder, go to level 2 and iterate through the children arrays for the default */
+                if ([thisPresetDict objectForKey:@"ChildrenArray"])
+                {
+                    NSMutableDictionary *thisPresetDictParentParent = thisPresetDict;
+                    NSEnumerator *enumerator = [[thisPresetDict objectForKey:@"ChildrenArray"] objectEnumerator];
+                    id tempObject;
+                    while (tempObject = [enumerator nextObject])
+                    {
+                        NSMutableDictionary *thisPresetDict = tempObject;
+                        if ([[thisPresetDict objectForKey:@"Default"] intValue] == 1) // 1 is HB default
+                        {
+                            presetHbDefault = thisPresetDict;
+                            presetHbDefaultParent = thisPresetDictParent;
+                            presetHbDefaultParentParent = thisPresetDictParentParent;  
+                        }
+                        if ([[thisPresetDict objectForKey:@"Default"] intValue] == 2) // 2 is User specified default
+                        {
+                            presetUserDefault = thisPresetDict;
+                            presetUserDefaultParent = thisPresetDictParent;
+                            presetUserDefaultParentParent = thisPresetDictParentParent;
+                            userDefaultFound = YES;    
+                        }
+                        
+                    }
+                }
+            }
+        }
+        
        }
+    /* check to see if a user specified preset was found, if not then assign the parents for
+     * the presetHbDefault so that we can open the parents for the nested presets
+     */
+    if (userDefaultFound == NO)
+    {
+        presetUserDefaultParent = presetHbDefaultParent;
+        presetUserDefaultParentParent = presetHbDefaultParentParent;
+    }
 }
 
 - (IBAction)setDefaultPreset:(id)sender
 {
+/* We need to determine if the item is a folder */
+   if ([[[fPresetsOutlineView itemAtRow:[fPresetsOutlineView selectedRow]] objectForKey:@"Folder"] intValue] == 1)
+   {
+   return;
+   }
+
     int i = 0;
     NSEnumerator *enumerator = [UserPresets objectEnumerator];
        id tempObject;
        /* First make sure the old user specified default preset is removed */
-       while (tempObject = [enumerator nextObject])
+    while (tempObject = [enumerator nextObject])
        {
-               /* make sure we are not removing the default HB preset */
-               if ([[[UserPresets objectAtIndex:i] objectForKey:@"Default"] intValue] != 1) // 1 is HB default
+               NSMutableDictionary *thisPresetDict = tempObject;
+               if ([[tempObject objectForKey:@"Default"] intValue] != 1) // if not the default HB Preset, set to 0
                {
-                       [[UserPresets objectAtIndex:i] setObject:[NSNumber numberWithInt:0] forKey:@"Default"];
+                       [[UserPresets objectAtIndex:i] setObject:[NSNumber numberWithInt:0] forKey:@"Default"]; 
                }
-               i++;
-       }
-       /* Second, go ahead and set the appropriate user specfied preset */
-       /* we get the chosen preset from the UserPresets array */
-       if ([[[UserPresets objectAtIndex:[fPresetsOutlineView selectedRow]] objectForKey:@"Default"] intValue] != 1) // 1 is HB default
-       {
-               [[UserPresets objectAtIndex:[fPresetsOutlineView selectedRow]] setObject:[NSNumber numberWithInt:2] forKey:@"Default"];
+               
+               /* if we run into a folder, go to level 1 and iterate through the children arrays for the default */
+        if ([thisPresetDict objectForKey:@"ChildrenArray"])
+        {
+            NSEnumerator *enumerator = [[thisPresetDict objectForKey:@"ChildrenArray"] objectEnumerator];
+            id tempObject;
+            int ii = 0;
+            while (tempObject = [enumerator nextObject])
+            {
+                NSMutableDictionary *thisPresetDict1 = tempObject;
+                if ([[tempObject objectForKey:@"Default"] intValue] != 1) // if not the default HB Preset, set to 0
+                {
+                    [[[thisPresetDict objectForKey:@"ChildrenArray"] objectAtIndex:ii] setObject:[NSNumber numberWithInt:0] forKey:@"Default"];        
+                }
+                /* if we run into a folder, go to level 2 and iterate through the children arrays for the default */
+                if ([thisPresetDict1 objectForKey:@"ChildrenArray"])
+                {
+                    NSEnumerator *enumerator = [[thisPresetDict1 objectForKey:@"ChildrenArray"] objectEnumerator];
+                    id tempObject;
+                    int iii = 0;
+                    while (tempObject = [enumerator nextObject])
+                    {
+                        if ([[tempObject objectForKey:@"Default"] intValue] != 1) // if not the default HB Preset, set to 0
+                        {
+                            [[[thisPresetDict1 objectForKey:@"ChildrenArray"] objectAtIndex:iii] setObject:[NSNumber numberWithInt:0] forKey:@"Default"];      
+                        }
+                        iii++;
+                    }
+                }
+                ii++;
+            }
+            
+        }
+        i++; 
        }
-       /*FIX ME: I think we now need to use the items not rows in NSOutlineView */
-    presetUserDefault = [fPresetsOutlineView selectedRow];
-       
-       /* We save all of the preset data here */
+    
+    
+    int presetToModLevel = [fPresetsOutlineView levelForItem: [fPresetsOutlineView itemAtRow:[fPresetsOutlineView selectedRow]]];
+    NSDictionary *presetToMod = [fPresetsOutlineView itemAtRow:[fPresetsOutlineView selectedRow]];
+    NSDictionary *presetToModParent = [fPresetsOutlineView parentForItem: presetToMod];
+    
+    
+    NSMutableArray *presetsArrayToMod;
+    NSMutableArray *tempArray;
+    
+    /* If we are a root level preset, we are modding the UserPresets array */
+    if (presetToModLevel == 0)
+    {
+        presetsArrayToMod = UserPresets;
+    }
+    else // We have a parent preset, so we modify the chidren array object for key
+    {
+        presetsArrayToMod = [presetToModParent objectForKey:@"ChildrenArray"]; 
+    }
+    
+    enumerator = [presetsArrayToMod objectEnumerator];
+    tempArray = [NSMutableArray array];
+    int iiii = 0;
+    while (tempObject = [enumerator nextObject]) 
+    {
+        NSDictionary *thisPresetDict = tempObject;
+        if (thisPresetDict == presetToMod)
+        {
+            if ([[tempObject objectForKey:@"Default"] intValue] != 1) // if not the default HB Preset, set to 2
+            {
+                [[presetsArrayToMod objectAtIndex:iiii] setObject:[NSNumber numberWithInt:2] forKey:@"Default"];       
+            }
+        }
+     iiii++;
+     }
+    
+    
+    /* We save all of the preset data here */
     [self savePreset];
-       /* We Reload the New Table data for presets */
+    /* We Reload the New Table data for presets */
     [fPresetsOutlineView reloadData];
 }
 
 - (IBAction)selectDefaultPreset:(id)sender
 {
-       /* if there is a user specified default, we use it */
+       NSMutableDictionary *presetToMod;
+    /* if there is a user specified default, we use it */
        if (presetUserDefault)
        {
-       [fPresetsOutlineView selectRowIndexes:[NSIndexSet indexSetWithIndex:presetUserDefault] byExtendingSelection:NO];
-       [self selectPreset:NULL];
-       }
+        presetToMod = presetUserDefault;
+    }
        else if (presetHbDefault) //else we use the built in default presetHbDefault
        {
-       [fPresetsOutlineView selectRowIndexes:[NSIndexSet indexSetWithIndex:presetHbDefault] byExtendingSelection:NO];
-       [self selectPreset:NULL];
+        presetToMod = presetHbDefault;
        }
+    else
+    {
+    return;
+    }
+    
+    if (presetUserDefaultParent != nil)
+    {
+        [fPresetsOutlineView expandItem:presetUserDefaultParent];
+        
+    }
+    if (presetUserDefaultParentParent != nil)
+    {
+        [fPresetsOutlineView expandItem:presetUserDefaultParentParent];
+        
+    }
+    
+    [fPresetsOutlineView selectRowIndexes:[NSIndexSet indexSetWithIndex:[fPresetsOutlineView rowForItem: presetToMod]] byExtendingSelection:NO];
+       [self selectPreset:nil];
 }
 
 
@@ -4015,15 +6322,47 @@ if (item == nil)
     /* Then we generate new built in presets programmatically with fPresetsBuiltin
     * which is all setup in HBPresets.h and  HBPresets.m*/
     [fPresetsBuiltin generateBuiltinPresets:UserPresets];
-
+    [self sortPresets];
     [self addPreset];
+    
 }
 
 
 
 
 
+@end
+
+/*******************************
+ * Subclass of the HBPresetsOutlineView *
+ *******************************/
+
+@implementation HBPresetsOutlineView
+- (NSImage *)dragImageForRowsWithIndexes:(NSIndexSet *)dragRows tableColumns:(NSArray *)tableColumns event:(NSEvent*)dragEvent offset:(NSPointPointer)dragImageOffset
+{
+    fIsDragging = YES;
+
+    // By default, NSTableView only drags an image of the first column. Change this to
+    // drag an image of the queue's icon and PresetName columns.
+    NSArray * cols = [NSArray arrayWithObjects: [self tableColumnWithIdentifier:@"PresetName"], nil];
+    return [super dragImageForRowsWithIndexes:dragRows tableColumns:cols event:dragEvent offset:dragImageOffset];
+}
+
+
 
+- (void) mouseDown:(NSEvent *)theEvent
+{
+    [super mouseDown:theEvent];
+       fIsDragging = NO;
+}
 
 
+
+- (BOOL) isDragging;
+{
+    return fIsDragging;
+}
 @end
+
+
+