]> granicus.if.org Git - handbrake/commitdiff
MacGui: improvement to the HBCore class, use it in HBPreviewGenerator. Added some...
authorritsuka <damiog@gmail.com>
Sat, 29 Nov 2014 09:42:33 +0000 (09:42 +0000)
committerritsuka <damiog@gmail.com>
Sat, 29 Nov 2014 09:42:33 +0000 (09:42 +0000)
git-svn-id: svn://svn.handbrake.fr/HandBrake/trunk@6566 b64f7644-9d1e-0410-96f1-a4d463321fa5

macosx/HBCore.h
macosx/HBCore.m
macosx/HBJob.h
macosx/HBJob.m
macosx/HBPreviewGenerator.m
macosx/HandBrake.xcodeproj/project.pbxproj
macosx/HandBrake.xcodeproj/xcshareddata/xcschemes/HandBrake [DEBUG].xcscheme

index 435d5f799d992a172eabd33f0c2d67b90a2621b8..ba10addbec33f6e05e539ddb4820643d2183a58e 100644 (file)
@@ -1,18 +1,23 @@
-/**
- * @file
- * Interface of class HBCore.
- */
+/*  HBCore.h $
+
+ This file is part of the HandBrake source code.
+ Homepage: <http://handbrake.fr/>.
+ It may be used under the terms of the GNU General Public License. */
 
 #import <Cocoa/Cocoa.h>
+#include "hb.h"
 
-extern const NSString *HBStateIdle;
-extern const NSString *HBStateScanning;
-extern const NSString *HBStateScanDone;
-extern const NSString *HBStateWorking;
-extern const NSString *HBStatePaused;
-extern const NSString *HBStateWorkDone;
-extern const NSString *HBStateMuxing;
-extern const NSString *HBStateAll;
+// These constants specify the current state of HBCore.
+typedef NS_ENUM(NSUInteger, HBState) {
+    HBStateIdle      = HB_STATE_IDLE,        ///< HB is doing nothing
+    HBStateScanning  = HB_STATE_SCANNING,    ///< HB is scanning
+    HBStateScanDone  = HB_STATE_SCANDONE,    ///< Scanning has been completed
+    HBStateWorking   = HB_STATE_WORKING,     ///< HB is encoding
+    HBStatePaused    = HB_STATE_PAUSED,      ///< Encoding is paused
+    HBStateWorkDone  = HB_STATE_WORKDONE,    ///< Encoding has been completed
+    HBStateMuxing    = HB_STATE_MUXING,      ///< HB is muxing
+    HBStateSearching = HB_STATE_SEARCHING    ///< HB is searching
+};
 
 extern NSString *HBCoreScanningNotification;
 extern NSString *HBCoreScanDoneNotification;
@@ -28,25 +33,71 @@ extern NSString *HBCoreMuxingNotification;
  * to implement properties that can be directly bound to elements of the gui.
  */
 @interface HBCore : NSObject
-{
-    /// Pointer to libhb handle.
-    struct hb_handle_s *hb_handle;
-    
-    /// Pointer to latest state information returned by libhb.
-    struct hb_state_s *hb_state;
-    
-    /// Timer used to poll libhb for state changes.
-    NSTimer *updateTimer;
-
-    /// Current state of HBCore; one of the HBState* constants.
-    const NSString *state;  
-}
-
-- (id)init;
-- (BOOL)openInDebugMode:(BOOL)debugMode checkForUpdates:(BOOL)checkForUpdates;
-- (BOOL)close;
-- (NSString *)state;
-- (struct hb_handle_s *)hb_handle;
-- (const struct hb_state_s *)hb_state;
+
+/**
+ * Set the status of libdvdnav in low level HandBrake library.
+ * This should be called once before other functions HBCore are used.
+ *
+ * @param enabled         whether libdvdnav is enabled or not.
+ */
++ (void)setDVDNav:(BOOL)enabled;
+
+/**
+ * Opens low level HandBrake library. This should be called once before other
+ * functions HBCore are used.
+ *
+ * @param loggingLevel         the desired libhb logging level.
+ *
+ * @return YES if libhb was opened, NO if there was an error.
+ */
+- (instancetype)initWithLoggingLevel:(int)loggingLevel;
+
+/**
+ * Current state of HBCore.
+ */
+@property (nonatomic, readonly) HBState state;
+
+/**
+ * Pointer to a hb_state_s struct containing state information of libhb.
+ */
+@property (nonatomic, readonly) hb_state_t *hb_state;
+
+/**
+ * Pointer to a libhb handle used by this HBCore instance.
+ */
+@property (nonatomic, readonly) hb_handle_t *hb_handle;
+
+
+/**
+ *  Determines whether the scan operation can scan a particural URL or whether an additional decription lib is needed..
+ *
+ *  @param url   the URL of the input file.
+ *  @param error an error containing additional info.
+ *
+ *  @return YES is the file at URL is scannable.
+ */
+- (BOOL)canScan:(NSURL *)url error:(NSError **)error;
+
+/**
+ *  Starts the asynchronous execution of a scan.
+ *
+ *  @param url              the URL of the input file.
+ *  @param titleNum         the number of the desired title. Use 0 to scan every title.
+ *  @param previewsNum      the number of previews image to generate.
+ *  @param minTitleDuration the minimum duration of the wanted titles in seconds.
+ */
+- (void)scan:(NSURL *)url titleNum:(NSUInteger)titleNum previewsNum:(NSUInteger)previewsNum minTitleDuration:(NSUInteger)minTitleDuration;
+
+/**
+ * Starts the libhb encoding session.
+ *
+ *     This method must be called after all jobs have been added.
+ */
+- (void)start;
+
+/**
+ * Stops encoding session and releases resources.
+ */
+- (void)stop;
 
 @end
index 0702d5d8e820f1ca1db501167e1041f8b96ea4ba..fb3184ba5b8d4f84764286c1ab4c23c9694ea717 100644 (file)
@@ -1,21 +1,14 @@
-/**
- * @file
- * Implementation of class HBCore.
- */
-
-#import "HBCore.h"
-#include "hb.h"
+/*  HBCore.m $
 
-// These constants specify the current state of HBCore.
+ This file is part of the HandBrake source code.
+ Homepage: <http://handbrake.fr/>.
+ It may be used under the terms of the GNU General Public License. */
 
-const NSString *HBStateIdle = @"HBStateIdle";           ///< HB is doing nothing (HB_STATE_IDLE)
-const NSString *HBStateScanning = @"HBStateScanning";   ///< HB is scanning (HB_STATE_SCANNING)
-const NSString *HBStateScanDone = @"HBStateScanDone";   ///< Scanning has been completed (HB_STATE_SCANDONE)
-const NSString *HBStateWorking = @"HBStateWorking";     ///< HB is encoding (HB_STATE_WORKING)
-const NSString *HBStatePaused = @"HBStatePaused";       ///< Encoding is paused (HB_STATE_PAUSED)
-const NSString *HBStateWorkDone = @"HBStateWorkDone";   ///< Encoding has been completed (HB_STATE_WORKDONE)
-const NSString *HBStateMuxing = @"HBStateMuxing";       ///< HB is muxing (HB_STATE_MUXING)
+#import "HBCore.h"
+#import "HBDVDDetector.h"
+#import "HBUtilities.h"
 
+#include <dlfcn.h>
 
 // These constants specify various status notifications sent by HBCore
 
@@ -40,12 +33,25 @@ NSString *HBCoreMuxingNotification = @"HBCoreMuxingNotification";
 /**
  * Private methods of HBCore.
  */
-@interface HBCore (Private)
-- (NSString *)stateAsString:(int)stateValue;
+@interface HBCore ()
+
+/// Current state of HBCore.
+@property (nonatomic, readwrite) HBState state;
+
+/// Timer used to poll libhb for state changes.
+@property (nonatomic, readwrite, retain) NSTimer *updateTimer;
+
+- (void)stateUpdateTimer:(NSTimer *)timer;
+
 @end
 
 @implementation HBCore
 
++ (void)setDVDNav:(BOOL)enabled
+{
+    hb_dvd_set_dvdnav(enabled);
+}
+
 /**
  * Initializes HBCore.
  */
@@ -53,8 +59,8 @@ NSString *HBCoreMuxingNotification = @"HBCoreMuxingNotification";
 {
     if (self = [super init])
     {
-        state = HBStateIdle;    
-        hb_state = malloc(sizeof(struct hb_state_s));   
+        _state = HBStateIdle;
+        _hb_state = malloc(sizeof(struct hb_state_s));
     }
     return self;
 }
@@ -64,7 +70,11 @@ NSString *HBCoreMuxingNotification = @"HBCoreMuxingNotification";
  */
 - (void)dealloc
 {
-    free(hb_state);    
+    [self stopUpdateTimer];
+    hb_close(&_hb_handle);
+    _hb_handle = NULL;
+
+    free(_hb_state);
     [super dealloc];
 }
 
@@ -73,107 +83,189 @@ NSString *HBCoreMuxingNotification = @"HBCoreMuxingNotification";
  * functions HBCore are used.
  *
  * @param debugMode         If set to YES, libhb will print verbose debug output.
- * @param checkForUpdates   If set to YES, libhb checks for updated versions.
  *
  * @return YES if libhb was opened, NO if there was an error.
  */
-- (BOOL)openInDebugMode:(BOOL)debugMode checkForUpdates:(BOOL)checkForUpdates;
+- (instancetype)initWithLoggingLevel:(int)loggingLevel
 {
-    NSAssert(!hb_handle, @"[HBCore openInDebugMode:checkForUpdates:] libhb is already open");
-    if (hb_handle)
+    self = [self init];
+    if (self)
+    {
+        _hb_handle = hb_init(loggingLevel, 0);
+        if (!_hb_handle)
+        {
+            [self release];
+            return nil;
+        }
+    }
+
+    return self;
+}
+
+#pragma mark - Scan
+
+- (BOOL)canScan:(NSURL *)url error:(NSError **)error
+{
+    if (!_hb_handle)
+    {
+        // Libhb is not open so we cannot do anything.
         return NO;
+    }
 
-    state = HBStateIdle;
+    if (![[NSFileManager defaultManager] fileExistsAtPath:url.path]) {
+        if (*error) {
+            *error = [NSError errorWithDomain:@"HBErrorDomain"
+                                         code:100
+                                     userInfo:@{ NSLocalizedDescriptionKey: @"Unable to find the file at the specified URL" }];
+        }
 
-    hb_handle = hb_init(debugMode ? HB_DEBUG_ALL : HB_DEBUG_NONE, checkForUpdates);
-    if (!hb_handle)
         return NO;
+    }
 
-    updateTimer = [[NSTimer scheduledTimerWithTimeInterval:0.5
-                                                    target:self
-                                                  selector:@selector(stateUpdateTimer:) 
-                                                  userInfo:NULL 
-                                                   repeats:YES] retain];
+    HBDVDDetector *detector = [HBDVDDetector detectorForPath:url.path];
+
+    if (detector.isVideoDVD)
+    {
+        // The chosen path was actually on a DVD, so use the raw block
+        // device path instead.
+
+        [HBUtilities writeToActivityLog: "trying to open a physical dvd at: %s", [url.path UTF8String]];
+
+        // Notify the user that we don't support removal of copy protection.
+        void *dvdcss = dlopen("libdvdcss.2.dylib", RTLD_LAZY);
+        if (dvdcss)
+        {
+            // libdvdcss was found so all is well
+            [HBUtilities writeToActivityLog: "libdvdcss.2.dylib found for decrypting physical dvd"];
+            dlclose(dvdcss);
+        }
+        else
+        {
+            // compatible libdvdcss not found
+            [HBUtilities writeToActivityLog: "libdvdcss.2.dylib not found for decrypting physical dvd"];
+
+            if (*error) {
+                *error = [NSError errorWithDomain:@"HBErrorDomain" code:101 userInfo:@{ NSLocalizedDescriptionKey: @"libdvdcss.2.dylib not found for decrypting physical dvd" }];
+            }
+        }
+    }
 
-    [[NSRunLoop currentRunLoop] addTimer:updateTimer forMode:NSModalPanelRunLoopMode];        
     return YES;
 }
 
-/**
- * Closes low level HandBrake library and releases resources.
- *
- * @return YES if libhb was closed successfully, NO if there was an error.
- */
-- (BOOL)close
+- (void)scan:(NSURL *)url titleNum:(NSUInteger)titleNum previewsNum:(NSUInteger)previewsNum minTitleDuration:(NSUInteger)minTitleDuration;
 {
-    NSAssert(hb_handle, @"[HBCore close] libhb is not open");
-    if (!hb_handle)
-        return NO;
+    NSAssert(_hb_handle, @"[HBCore scan:] libhb is not open");
 
-    [updateTimer invalidate];
-    [updateTimer release];
-    updateTimer = nil;
-    hb_close(&hb_handle);
-    hb_handle = NULL;
-    return YES;
+    // Start the timer to handle libhb state changes
+    [self startUpdateTimer];
+
+    NSString *path = url.path;
+    HBDVDDetector *detector = [HBDVDDetector detectorForPath:path];
+
+    if (detector.isVideoDVD)
+    {
+        // The chosen path was actually on a DVD, so use the raw block
+        // device path instead.
+        path = detector.devicePath;
+    }
+
+    // convert minTitleDuration from seconds to the internal HB time
+    uint64_t min_title_duration_ticks = 90000LL * minTitleDuration;
+
+    // If there is no title number passed to scan, we use 0
+    // which causes the default behavior of a full source scan
+    if (titleNum > 0)
+    {
+        [HBUtilities writeToActivityLog: "scanning specifically for title: %d", titleNum];
+    }
+    else
+    {
+        // minimum title duration doesn't apply to title-specific scan
+        // it doesn't apply to batch scan either, but we can't tell it apart from DVD & BD folders here
+        [HBUtilities writeToActivityLog: "scanning titles with a duration of %d seconds or more", minTitleDuration];
+    }
+
+    hb_system_sleep_prevent(_hb_handle);
+
+    hb_scan(_hb_handle, path.fileSystemRepresentation,
+            (int)titleNum, (int)previewsNum,
+            1, min_title_duration_ticks);
 }
 
-/**
- * Returns libhb handle used by this HBCore instance.
- */ 
-- (struct hb_handle_s *)hb_handle
+#pragma mark - Encodes
+
+- (void)start
 {
-    return hb_handle;
+    NSAssert(_hb_handle, @"[HBCore start] libhb is not open");
+
+    // Start the timer to handle libhb state changes
+    [self startUpdateTimer];
+
+    hb_system_sleep_prevent(_hb_handle);
+    hb_start(_hb_handle);
 }
 
+- (void)stop
+{
+    NSAssert(_hb_handle, @"[HBCore stop] libhb is not open");
+
+    hb_stop(_hb_handle);
+    hb_system_sleep_allow(_hb_handle);
+}
+
+#pragma mark - State updates
+
 /**
- * Returns current state of HBCore.
- *
- * @return One of the HBState* string constants.
+ * Starts the timer used to polls libhb for state changes.
  */
-- (const NSString *)state
+- (void)startUpdateTimer
 {
-    return state;
+    if (!self.updateTimer)
+    {
+        self.updateTimer = [NSTimer scheduledTimerWithTimeInterval:0.5
+                                                            target:self
+                                                          selector:@selector(stateUpdateTimer:)
+                                                          userInfo:NULL
+                                                           repeats:YES];
+
+        [[NSRunLoop currentRunLoop] addTimer:self.updateTimer forMode:NSEventTrackingRunLoopMode];
+    }
 }
 
 /**
- * Returns latest hb_state_s information struct returned by libhb.
- *
- * @return Pointer to a hb_state_s struct containing state information of libhb.
+ * Stops the update timer.
  */
-- (const struct hb_state_s *)hb_state
+- (void)stopUpdateTimer
 {
-    return hb_state;
+    [self.updateTimer invalidate];
+    self.updateTimer = nil;
 }
 
-@end 
-
-@implementation HBCore (Private)
-
 /**
- * Transforms a libhb state constant to a matching HBCore state constant.
+ * Transforms a libhb state constant to a matching HBCore selector.
  */
-- (const NSString *)stateAsString:(int)stateValue
+- (const SEL)selectorForState:(HBState)stateValue
 {
     switch (stateValue)
     {
-        case HB_STATE_IDLE:
-            return HBStateIdle;        
-        case HB_STATE_SCANNING:
-            return HBStateScanning;
-        case HB_STATE_SCANDONE:
-            return HBStateScanDone;
         case HB_STATE_WORKING:
-            return HBStateWorking;
+            return @selector(handleHBStateWorking);
+        case HB_STATE_SCANNING:
+            return @selector(handleHBStateScanning);
+        case HB_STATE_MUXING:
+            return @selector(handleHBStateMuxing);
         case HB_STATE_PAUSED:
-            return HBStatePaused;
+            return @selector(handleHBStatePaused);
+        case HB_STATE_SEARCHING:
+            return @selector(handleHBStateSearching);
+        case HB_STATE_SCANDONE:
+            return @selector(handleHBStateScanDone);
         case HB_STATE_WORKDONE:
-            return HBStateWorkDone;
-        case HB_STATE_MUXING:
-            return HBStateMuxing;        
+            return @selector(handleHBStateWorkDone);
         default:
-            NSAssert1(NO, @"[HBCore stateAsString:] unknown state %d", stateValue);
-            return nil;
+            NSAssert1(NO, @"[HBCore selectorForState:] unknown state %lu", stateValue);
+            return NULL;
     }
 }
 
@@ -184,35 +276,40 @@ NSString *HBCoreMuxingNotification = @"HBCoreMuxingNotification";
  */
 - (void)stateUpdateTimer:(NSTimer *)timer
 {
-    if (!hb_handle)
+    if (!_hb_handle)
     {
         // Libhb is not open so we cannot do anything.
         return;
     }
-    hb_get_state(hb_handle, hb_state);
+    hb_get_state(_hb_handle, _hb_state);
 
-    if (hb_state->state == HB_STATE_IDLE)
+    if (_hb_state->state == HB_STATE_IDLE)
     {
         // Libhb reported HB_STATE_IDLE, so nothing interesting has happened.
         return;
     }
-        
+
     // Update HBCore state to reflect the current state of libhb
-    NSString *newState = [self stateAsString:hb_state->state];
-    if (newState != state)
-    {
-        [self willChangeValueForKey:@"state"];
-        state = newState;
-        [self didChangeValueForKey:@"state"];
-    }
+    self.state = _hb_state->state;
 
     // Determine name of the method that does further processing for this state
     // and call it. 
-    SEL sel = NSSelectorFromString([NSString stringWithFormat:@"handle%@", state]);
-    if ([self respondsToSelector:sel])
-        [self performSelector:sel];
+    SEL sel = [self selectorForState:self.state];
+    [self performSelector:sel];
+
+    if (_hb_state->state == HB_STATE_WORKDONE || _hb_state->state == HB_STATE_SCANDONE)
+    {
+        // Libhb reported HB_STATE_WORKDONE or HB_STATE_SCANDONE,
+        // so nothing interesting will happen after this point, stop the timer.
+        [self stopUpdateTimer];
+
+        self.state = HBStateIdle;
+        hb_system_sleep_allow(_hb_handle);
+    }
 }
 
+#pragma mark - Notifications
+
 /**
  * Processes HBStateScanning state information. Current implementation just
  * sends HBCoreScanningNotification.
@@ -267,4 +364,13 @@ NSString *HBCoreMuxingNotification = @"HBCoreMuxingNotification";
     [[NSNotificationCenter defaultCenter] postNotificationName:HBCoreMuxingNotification object:self];    
 }
 
+/**
+ * Processes HBStateSearching state information. Current implementation just
+ * sends HBCoreSearchingNotification.
+ */
+- (void)handleHBStateSearching
+{
+    [[NSNotificationCenter defaultCenter] postNotificationName:HBCoreMuxingNotification object:self];
+}
+
 @end
index 3521d464582e98c2c18607da013574d3e3a7755f..ebc6a8cbde68353898db5f3658c346df3077dfab 100644 (file)
@@ -14,8 +14,8 @@
 @class HBPicture;
 @class HBFilters;
 
-@class HBAudioSettings;
-@class HBSubtitlesSettings;
+@class HBAudioDefaults;
+@class HBSubtitlesDefaults;
 
 /**
  * HBJob
@@ -45,8 +45,8 @@
 @property (nonatomic, readonly) HBFilters *filters;
 
 // Defaults settings
-@property (nonatomic, readonly) HBAudioSettings *audioSettings;
-@property (nonatomic, readonly) HBSubtitlesSettings *subtitlesSettings;
+@property (nonatomic, readonly) HBAudioDefaults *audioDefaults;
+@property (nonatomic, readonly) HBSubtitlesDefaults *subtitlesDefaults;
 
 // File resources
 @property (nonatomic, readonly) NSMutableArray *audioTracks;
index 78e6a317be15d9009411f19bb908e3019c845436..a7943f3c06237071a312c80063c101897e7080b4 100644 (file)
@@ -5,8 +5,8 @@
  It may be used under the terms of the GNU General Public License. */
 
 #import "HBJob.h"
-#import "HBAudioSettings.h"
-#import "HBSubtitlesSettings.h"
+#import "HBAudioDefaults.h"
+#import "HBSubtitlesDefaults.h"
 #import "HBPreset.h"
 
 #include "lang.h"
@@ -47,8 +47,8 @@ extern NSString *keySubTrackSrtCharCode;
         _subtitlesTracks = [[NSMutableArray alloc] init];
         _chapters = [[NSMutableArray alloc] init];
 
-        _audioSettings = [[HBAudioSettings alloc] init];
-        _subtitlesSettings = [[HBSubtitlesSettings alloc] init];
+        _audioDefaults = [[HBAudioDefaults alloc] init];
+        _subtitlesDefaults = [[HBSubtitlesDefaults alloc] init];
 
         [self loadAudioTracks];
         [self loadSubtitlesTracks];
@@ -59,8 +59,8 @@ extern NSString *keySubTrackSrtCharCode;
 
 - (void)applyPreset:(HBPreset *)preset
 {
-    [self.audioSettings applySettingsFromPreset:preset.content];
-    [self.subtitlesSettings applySettingsFromPreset:preset.content];
+    [self.audioDefaults applySettingsFromPreset:preset.content];
+    [self.subtitlesDefaults applySettingsFromPreset:preset.content];
 }
 
 #pragma mark - initialization
index dce77e1aaa3abbc92ea76a41e6f817a95d19b733..ccbe7473c960f80083731ccad418438b6701f7bc 100644 (file)
@@ -7,6 +7,7 @@
 
 #import "HBPreviewGenerator.h"
 #import "HBUtilities.h"
+#import "HBCore.h"
 #import "Controller.h"
 
 typedef enum EncodeState : NSUInteger {
@@ -22,9 +23,9 @@ typedef enum EncodeState : NSUInteger {
 @property (nonatomic, readonly) hb_handle_t *handle;
 @property (nonatomic, readonly) hb_title_t *title;
 
-@property (nonatomic) hb_handle_t *privateHandle;
-@property (nonatomic) NSTimer *timer;
-@property (nonatomic) EncodeState encodeState;
+@property (nonatomic) HBCore *core;
+@property (nonatomic, getter=isCancelled) BOOL cancelled;
+
 
 @property (nonatomic, retain) NSURL *fileURL;
 
@@ -191,7 +192,7 @@ typedef enum EncodeState : NSUInteger {
 - (BOOL) createMovieAsyncWithImageIndex: (NSUInteger) index andDuration: (NSUInteger) duration;
 {
     /* return if an encoding if already started */
-    if (self.encodeState || index >= self.imagesCount)
+    if (self.core || index >= self.imagesCount)
         return NO;
 
     hb_job_t *job = self.title->job;
@@ -232,7 +233,7 @@ typedef enum EncodeState : NSUInteger {
      */
 
     int loggingLevel = [[[NSUserDefaults standardUserDefaults] objectForKey:@"LoggingLevel"] intValue];
-    self.privateHandle = hb_init(loggingLevel, 0);
+    self.core = [[[HBCore alloc] initWithLoggingLevel:loggingLevel] autorelease];
 
     /*
      * If scanning we need to do some extra setup of the job.
@@ -254,7 +255,7 @@ typedef enum EncodeState : NSUInteger {
         hb_job_set_encoder_profile(job, NULL);
         hb_job_set_encoder_level  (job, NULL);
         job->pass = -1;
-        hb_add(self.privateHandle, job);
+        hb_add(self.core.hb_handle, job);
         /*
          * reset the advanced settings
          */
@@ -274,18 +275,16 @@ typedef enum EncodeState : NSUInteger {
     job->indepth_scan = 0;
     job->pass = 0;
 
-    hb_add(self.privateHandle, job);
+    hb_add(self.core.hb_handle, job);
 
     /* we need to clean up the various lists after the job(s) have been set  */
     hb_job_reset(job);
 
-    /* start the actual encode */
-    self.encodeState = EncodeStateWorking;
-    hb_system_sleep_prevent(self.privateHandle);
-
-    [self startHBTimer];
+    [self registerCoreNotifications];
+    self.cancelled = NO;
 
-    hb_start(self.privateHandle);
+    /* start the actual encode */
+    [self.core start];
 
     return YES;
 }
@@ -295,126 +294,68 @@ typedef enum EncodeState : NSUInteger {
  */
 - (void) cancel
 {
-    if (self.privateHandle)
+    if (self.core)
     {
-        hb_state_t s;
-        hb_get_state2(self.privateHandle, &s);
-
-        if (self.encodeState && (s.state == HB_STATE_WORKING ||
-                                  s.state == HB_STATE_PAUSED))
+        if (self.core.state == HBStateWorking || self.core.state == HBStatePaused)
         {
-            self.encodeState = EncodeStateCancelled;
-            hb_stop(self.privateHandle);
-            hb_system_sleep_allow(self.privateHandle);
+            [self.core stop];
+            self.cancelled = YES;
         }
     }
 }
 
-- (void) startHBTimer
-{
-    if (!self.timer)
-    {
-        self.timer = [NSTimer scheduledTimerWithTimeInterval:0.5
-                                                      target:self
-                                                    selector:@selector(updateState)
-                                                    userInfo:nil
-                                                     repeats:YES];
-    }
-}
-
-- (void) stopHBTimer
+/**
+ *  Registers for notifications from HBCore.
+ */
+- (void) registerCoreNotifications
 {
-    [self.timer invalidate];
-    self.timer = nil;
-}
+    NSOperationQueue *mainQueue = [NSOperationQueue mainQueue];
 
-- (void) updateState
-{
-    hb_state_t s;
-    hb_get_state(self.privateHandle, &s);
+    [[NSNotificationCenter defaultCenter] addObserverForName:HBCoreWorkingNotification object:self.core queue:mainQueue usingBlock:^(NSNotification *note) {
+        hb_state_t s = *(self.core.hb_state);
 
-    switch( s.state )
-    {
-        case HB_STATE_IDLE:
-        case HB_STATE_SCANNING:
-        case HB_STATE_SCANDONE:
-            break;
+        NSMutableString *info = [NSMutableString stringWithFormat: @"Encoding preview:  %.2f %%", 100.0 * s.param.working.progress];
 
-        case HB_STATE_WORKING:
+        if (s.param.working.seconds > -1)
         {
-                       NSMutableString *info = [NSMutableString stringWithFormat: @"Encoding preview:  %.2f %%", 100.0 * s.param.working.progress];
+            [info appendFormat:@" (%.2f fps, avg %.2f fps, ETA %02dh%02dm%02ds)",
+             s.param.working.rate_cur, s.param.working.rate_avg, s.param.working.hours,
+             s.param.working.minutes, s.param.working.seconds];
+        }
 
-                       if( s.param.working.seconds > -1 )
-            {
-                [info appendFormat:@" (%.2f fps, avg %.2f fps, ETA %02dh%02dm%02ds)",
-                 s.param.working.rate_cur, s.param.working.rate_avg, s.param.working.hours,
-                 s.param.working.minutes, s.param.working.seconds];
-            }
+        double progress = 100.0 * s.param.working.progress;
 
-            double progress = 100.0 * s.param.working.progress;
+        [self.delegate updateProgress:progress info:info];
+    }];
 
-            [self.delegate updateProgress:progress info:info];
+    [[NSNotificationCenter defaultCenter] addObserverForName:HBCoreMuxingNotification object:self.core queue:mainQueue usingBlock:^(NSNotification *note) {
+        [self.delegate updateProgress:100.0 info:@"Muxing Preview…"];
+    }];
 
-            break;
-        }
+    [[NSNotificationCenter defaultCenter] addObserverForName:HBCoreWorkDoneNotification object:self.core queue:mainQueue usingBlock:^(NSNotification *note) {
+        [self.core stop];
+        self.core = nil;
 
-        case HB_STATE_MUXING:
+        /* Encode done, call the delegate and close libhb handle */
+        if (!self.isCancelled)
         {
-            NSString *info = @"Muxing Preview…";
-            double progress = 100.0;
-
-            [self.delegate updateProgress:progress info:info];
-
-            break;
+            [self.delegate didCreateMovieAtURL:self.fileURL];
         }
-
-        case HB_STATE_PAUSED:
-            break;
-
-        case HB_STATE_WORKDONE:
+        else
         {
-            [self stopHBTimer];
-
-            // Delete all remaining jobs since libhb doesn't do this on its own.
-            hb_job_t * job;
-            while( ( job = hb_job(self.privateHandle, 0) ) )
-                hb_rem( self.handle, job );
-
-            hb_system_sleep_allow(self.privateHandle);
-            hb_stop(self.privateHandle);
-            hb_close(&_privateHandle);
-            self.privateHandle = NULL;
-
-            /* Encode done, call the delegate and close libhb handle */
-            if (self.encodeState != EncodeStateCancelled)
-            {
-                [self.delegate didCreateMovieAtURL:self.fileURL];
-            }
-            else
-            {
-                [self.delegate didCancelMovieCreation];
-            }
-
-            self.encodeState = EncodeStateIdle;
-
-            break;
+            [self.delegate didCancelMovieCreation];
         }
-    }
+
+        [[NSNotificationCenter defaultCenter] removeObserver:self];
+    }];
 }
 
 #pragma mark -
 
 - (void) dealloc
 {
-    [_timer invalidate];
-    [_timer release];
-    _timer = nil;
-
-    if (_privateHandle) {
-        hb_system_sleep_allow(self.privateHandle);
-        hb_stop(_privateHandle);
-        hb_close(&_privateHandle);
-    }
+    [self.core stop];
+    self.core = nil;
 
     [_fileURL release];
     _fileURL = nil;
index fc05ebfd5b6fcd89ce9091da90edc060b9afca45..1a4bf405f52a062ffdcd7d8812c4ad6678678402 100644 (file)
                A9D488A51996270300E9B1BA /* HBTreeNode.m in Sources */ = {isa = PBXBuildFile; fileRef = A9D488A41996270300E9B1BA /* HBTreeNode.m */; };
                A9DC6C52196F04F6002AE6B4 /* HBSubtitlesController.m in Sources */ = {isa = PBXBuildFile; fileRef = A9DC6C50196F04F6002AE6B4 /* HBSubtitlesController.m */; };
                A9DC6C56196F0517002AE6B4 /* Subtitles.xib in Resources */ = {isa = PBXBuildFile; fileRef = A9DC6C54196F0517002AE6B4 /* Subtitles.xib */; };
+               A9DEC8741A23C87500C79B48 /* HBCore.m in Sources */ = {isa = PBXBuildFile; fileRef = A9DEC8731A23C87500C79B48 /* HBCore.m */; };
+               A9DEC8771A23C88D00C79B48 /* HBVideo.m in Sources */ = {isa = PBXBuildFile; fileRef = A9DEC8761A23C88D00C79B48 /* HBVideo.m */; };
+               A9DEC87A1A23C89E00C79B48 /* HBPicture.m in Sources */ = {isa = PBXBuildFile; fileRef = A9DEC8791A23C89E00C79B48 /* HBPicture.m */; };
+               A9DEC87F1A23DF6F00C79B48 /* HBJob.m in Sources */ = {isa = PBXBuildFile; fileRef = A9DEC87E1A23DF6F00C79B48 /* HBJob.m */; };
                A9E1467B16BC2ABD00C307BC /* QuartzCore.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = A9E1467A16BC2ABD00C307BC /* QuartzCore.framework */; };
                A9E1468016BC2AD800C307BC /* next-p.pdf in Resources */ = {isa = PBXBuildFile; fileRef = A9E1467C16BC2AD800C307BC /* next-p.pdf */; };
                A9E1468116BC2AD800C307BC /* pause-p.pdf in Resources */ = {isa = PBXBuildFile; fileRef = A9E1467D16BC2AD800C307BC /* pause-p.pdf */; };
                A9DC6C4F196F04F6002AE6B4 /* HBSubtitlesController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = HBSubtitlesController.h; sourceTree = SOURCE_ROOT; };
                A9DC6C50196F04F6002AE6B4 /* HBSubtitlesController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = HBSubtitlesController.m; sourceTree = SOURCE_ROOT; };
                A9DC6C55196F0517002AE6B4 /* English */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = English; path = Subtitles.xib; sourceTree = "<group>"; };
+               A9DEC8721A23C87500C79B48 /* HBCore.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = HBCore.h; sourceTree = "<group>"; };
+               A9DEC8731A23C87500C79B48 /* HBCore.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = HBCore.m; sourceTree = "<group>"; };
+               A9DEC8751A23C88D00C79B48 /* HBVideo.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = HBVideo.h; sourceTree = "<group>"; };
+               A9DEC8761A23C88D00C79B48 /* HBVideo.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = HBVideo.m; sourceTree = "<group>"; };
+               A9DEC8781A23C89E00C79B48 /* HBPicture.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = HBPicture.h; sourceTree = "<group>"; };
+               A9DEC8791A23C89E00C79B48 /* HBPicture.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = HBPicture.m; sourceTree = "<group>"; };
+               A9DEC87D1A23DF6F00C79B48 /* HBJob.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = HBJob.h; sourceTree = "<group>"; };
+               A9DEC87E1A23DF6F00C79B48 /* HBJob.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = HBJob.m; sourceTree = "<group>"; };
                A9E1467A16BC2ABD00C307BC /* QuartzCore.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = QuartzCore.framework; path = /System/Library/Frameworks/QuartzCore.framework; sourceTree = "<absolute>"; };
                A9E1467C16BC2AD800C307BC /* next-p.pdf */ = {isa = PBXFileReference; lastKnownFileType = image.pdf; path = "next-p.pdf"; sourceTree = "<group>"; };
                A9E1467D16BC2AD800C307BC /* pause-p.pdf */ = {isa = PBXFileReference; lastKnownFileType = image.pdf; path = "pause-p.pdf"; sourceTree = "<group>"; };
                                A9B34D6F197683FE00871B7D /* Controllers */,
                                A98C29C51977C00000AF5DED /* Core */,
                                A952392E199A647F00588AEF /* Presets */,
-                               A9AA447D1970729300D7DEFC /* HBPreviewGenerator.h */,
-                               A9D1E41618262364002F6424 /* HBPreviewGenerator.m */,
                                A9AA44781970664A00D7DEFC /* HBUtilities.h */,
                                A9AA44791970664A00D7DEFC /* HBUtilities.m */,
-                               273F209714ADBE670021BE6D /* HBDVDDetector.h */,
-                               273F209814ADBE670021BE6D /* HBDVDDetector.m */,
                                273F209D14ADBE670021BE6D /* HBOutputRedirect.h */,
                                273F209E14ADBE670021BE6D /* HBOutputRedirect.m */,
                                A98C29C21977B10600AF5DED /* HBLanguagesSelection.h */,
                A98C29C51977C00000AF5DED /* Core */ = {
                        isa = PBXGroup;
                        children = (
+                               A9DEC8721A23C87500C79B48 /* HBCore.h */,
+                               A9DEC8731A23C87500C79B48 /* HBCore.m */,
+                               A9DEC87D1A23DF6F00C79B48 /* HBJob.h */,
+                               A9DEC87E1A23DF6F00C79B48 /* HBJob.m */,
+                               A9DEC8751A23C88D00C79B48 /* HBVideo.h */,
+                               A9DEC8761A23C88D00C79B48 /* HBVideo.m */,
+                               A9DEC8781A23C89E00C79B48 /* HBPicture.h */,
+                               A9DEC8791A23C89E00C79B48 /* HBPicture.m */,
                                A932E271198834130047D13E /* HBAudioDefaults.h */,
                                A932E272198834130047D13E /* HBAudioDefaults.m */,
                                A9F4728B1976BAA70009EC65 /* HBSubtitlesDefaults.h */,
                                A90A0CAE1988D57200DA65CE /* HBAudioTrackPreset.m */,
                                A9523935199A6AAE00588AEF /* HBFilters.h */,
                                A9523936199A6AAE00588AEF /* HBFilters.m */,
+                               A9AA447D1970729300D7DEFC /* HBPreviewGenerator.h */,
+                               A9D1E41618262364002F6424 /* HBPreviewGenerator.m */,
+                               273F209714ADBE670021BE6D /* HBDVDDetector.h */,
+                               273F209814ADBE670021BE6D /* HBDVDDetector.m */,
                        );
                        name = Core;
                        sourceTree = "<group>";
                                A98C29C41977B10600AF5DED /* HBLanguagesSelection.m in Sources */,
                                A9BB0F2719A0ECE40079F1C1 /* HBHUDButtonCell.m in Sources */,
                                A932E273198834130047D13E /* HBAudioDefaults.m in Sources */,
+                               A9DEC8771A23C88D00C79B48 /* HBVideo.m in Sources */,
                                A9523937199A6AAE00588AEF /* HBFilters.m in Sources */,
                                A9AA447A1970664A00D7DEFC /* HBUtilities.m in Sources */,
                                273F20AC14ADBE670021BE6D /* Controller.m in Sources */,
                                273F20AD14ADBE670021BE6D /* HBAdvancedController.m in Sources */,
                                273F20AE14ADBE670021BE6D /* HBAudio.m in Sources */,
+                               A9DEC87A1A23C89E00C79B48 /* HBPicture.m in Sources */,
                                273F20AF14ADBE670021BE6D /* HBAudioController.m in Sources */,
                                273F20B114ADBE670021BE6D /* HBDVDDetector.m in Sources */,
                                273F20B214ADBE670021BE6D /* HBImageAndTextCell.m in Sources */,
                                A9DC6C52196F04F6002AE6B4 /* HBSubtitlesController.m in Sources */,
                                A9F472891976B7F30009EC65 /* HBSubtitlesDefaultsController.m in Sources */,
                                A9CF25F41990D64E0023F727 /* HBPreset.m in Sources */,
+                               A9DEC8741A23C87500C79B48 /* HBCore.m in Sources */,
                                A9F4728D1976BAA70009EC65 /* HBSubtitlesDefaults.m in Sources */,
                                A93E0ED31972957000FD67FB /* HBVideoController.m in Sources */,
                                273F20B614ADBE670021BE6D /* HBPresetsManager.m in Sources */,
                                A9C9F88919A733FE00DC8923 /* HBHUDView.m in Sources */,
                                A932E26F198833920047D13E /* HBAudioDefaultsController.m in Sources */,
                                46AB433515F98A2B009C0961 /* DockTextField.m in Sources */,
+                               A9DEC87F1A23DF6F00C79B48 /* HBJob.m in Sources */,
                                A9E2FD271A21BC4A000E8D3F /* HBAddPresetController.m in Sources */,
                                A9D488A51996270300E9B1BA /* HBTreeNode.m in Sources */,
                        );
index ffb7335809a82d96cc199d8cd4e50238161e683d..9dc1fa481b4d4f24077a2e8d7cce058338e20a15 100644 (file)
@@ -55,7 +55,7 @@
    </TestAction>
    <LaunchAction
       selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
-      selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.GDB"
+      selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
       launchStyle = "0"
       useCustomWorkingDirectory = "NO"
       buildConfiguration = "debug"
          </BuildableReference>
       </BuildableProductRunnable>
       <AdditionalOptions>
+         <AdditionalOption
+            key = "NSZombieEnabled"
+            value = "YES"
+            isEnabled = "YES">
+         </AdditionalOption>
       </AdditionalOptions>
    </LaunchAction>
    <ProfileAction