From e4601ac655a03103f548b089735b2c5f794f0733 Mon Sep 17 00:00:00 2001 From: Palana Date: Thu, 12 Jun 2014 02:30:06 +0200 Subject: [PATCH] Show unsupported selected presets for mac-avcapture Configured presets that are unsupported are now preserved in the user config, but listed as disabled --- plugins/mac-avcapture/av-capture.m | 112 ++++++++++++++++++++++++----- 1 file changed, 93 insertions(+), 19 deletions(-) diff --git a/plugins/mac-avcapture/av-capture.m b/plugins/mac-avcapture/av-capture.m index a86391583..89fedf969 100644 --- a/plugins/mac-avcapture/av-capture.m +++ b/plugins/mac-avcapture/av-capture.m @@ -509,7 +509,10 @@ static NSString *preset_names(NSString *preset) AVCaptureSessionPreset960x540:@"960x540", AVCaptureSessionPreset1280x720:@"1280x720", }; - return preset_names[preset]; + NSString *name = preset_names[preset]; + if (name) + return name; + return [NSString stringWithFormat:@"Unknown (%@)", preset]; } @@ -536,6 +539,66 @@ static void av_capture_defaults(obs_data_t settings) obs_data_set_default_string(settings, "preset", highest.UTF8String); } +static void fill_presets(AVCaptureDevice *dev, obs_property_t list, + NSString *current_preset) +{ + obs_property_list_clear(list); + + bool preset_found = false; + for (NSString *preset in presets()) { + bool supported = [dev supportsAVCaptureSessionPreset:preset]; + bool is_current = [preset isEqualToString:current_preset]; + + if (is_current) + preset_found = true; + + if (!supported && !is_current) + continue; + + size_t idx = obs_property_list_add_string(list, + preset_names(preset).UTF8String, + preset.UTF8String); + obs_property_list_item_disable(list, idx, !supported); + } + + if (preset_found) + return; + + size_t idx = obs_property_list_add_string(list, + preset_names(current_preset).UTF8String, + current_preset.UTF8String); + obs_property_list_item_disable(list, idx, true); +} + +static bool check_preset(AVCaptureDevice *dev, + obs_property_t list, obs_data_t settings) +{ + NSString *current_preset = get_string(settings, "preset"); + + size_t size = obs_property_list_item_count(list); + NSMutableSet *listed = [NSMutableSet setWithCapacity:size]; + + for (size_t i = 0; i < size; i++) + [listed addObject:@(obs_property_list_item_string(list, i))]; + + bool presets_changed = false; + for (NSString *preset in presets()) { + bool is_listed = [listed member:preset] != nil; + bool supported = [dev supportsAVCaptureSessionPreset:preset]; + + if (supported == is_listed) + continue; + + presets_changed = true; + } + + if (!presets_changed && [listed member:current_preset] != nil) + return false; + + fill_presets(dev, list, current_preset); + return true; +} + static bool properties_device_changed(obs_properties_t props, obs_property_t p, obs_data_t settings) { @@ -547,25 +610,21 @@ static bool properties_device_changed(obs_properties_t props, obs_property_t p, if (!dev) return false; - obs_property_t preset_list = obs_properties_get(props, "preset"); - obs_property_list_clear(preset_list); + return check_preset(dev, obs_properties_get(props, "preset"), settings); +} - for (NSString *preset in presets()) { - if (![dev supportsAVCaptureSessionPreset:preset]) - continue; +static bool properties_preset_changed(obs_properties_t props, obs_property_t p, + obs_data_t settings) +{ + UNUSED_PARAMETER(props); - obs_property_list_add_string(preset_list, - preset_names(preset).UTF8String, - preset.UTF8String); + NSString *uid = get_string(settings, "device"); + AVCaptureDevice *dev = [AVCaptureDevice deviceWithUniqueID:uid]; - } + if (!dev) + return false; - NSString *preset = get_string(settings, "preset"); - if (![dev supportsAVCaptureSessionPreset:preset]) - obs_data_setstring(settings, "preset", - select_preset(dev, preset).UTF8String); - - return true; + return check_preset(dev, p, settings); } static obs_properties_t av_capture_properties(void) @@ -591,8 +650,15 @@ static obs_properties_t av_capture_properties(void) // TODO: implement manual configuration obs_property_set_enabled(use_preset, false); - obs_properties_add_list(props, "preset", "Preset", OBS_COMBO_TYPE_LIST, - OBS_COMBO_FORMAT_STRING); + obs_property_t preset_list = obs_properties_add_list(props, "preset", + "Preset", OBS_COMBO_TYPE_LIST, OBS_COMBO_FORMAT_STRING); + for (NSString *preset in presets()) + obs_property_list_add_string(preset_list, + preset_names(preset).UTF8String, + preset.UTF8String); + + obs_property_set_modified_callback(preset_list, + properties_preset_changed); return props; } @@ -628,7 +694,15 @@ static void av_capture_update(void *data, obs_data_t settings) if (!capture->device || ![capture->device.uniqueID isEqualToString:uid]) return switch_device(capture, uid, settings); - capture->session.sessionPreset = get_string(settings, "preset"); + NSString *preset = get_string(settings, "preset"); + NSLog(@"%@", preset); + if (![capture->device supportsAVCaptureSessionPreset:preset]) { + AVLOG(LOG_ERROR, "Preset %s not available", preset.UTF8String); + preset = select_preset(capture->device, preset); + } + + capture->session.sessionPreset = preset; + AVLOG(LOG_INFO, "Selected preset %s", preset.UTF8String); } struct obs_source_info av_capture_info = {