#include "settings.h"
#include "callbacks.h"
#include "subtitlehandler.h"
+#include "x264handler.h"
#include "preview.h"
#include "values.h"
#include "lang.h"
d_logging_opts
};
+static options_map_t d_appcast_update_opts[] =
+{
+ {"Never", "never", 0, "never"},
+ {"Daily", "daily", 1, "daily"},
+ {"Weekly", "weekly", 2, "weekly"},
+ {"Monthly", "monthly", 3, "monthly"},
+};
+combo_opts_t appcast_update_opts =
+{
+ sizeof(d_appcast_update_opts)/sizeof(options_map_t),
+ d_appcast_update_opts
+};
+
static options_map_t d_vqual_granularity_opts[] =
{
{"0.2", "0.2", 0.2, "0.2"},
{"PicturePAR", &par_opts},
{"PictureModulus", &alignment_opts},
{"LoggingLevel", &logging_opts},
+ {"check_updates", &appcast_update_opts},
{"VideoQualityGranularity", &vqual_granularity_opts},
{"FileFormat", &container_opts},
{"PictureDeinterlace", &deint_opts},
return titleindex;
}
+gchar*
+ghb_get_source_audio_lang(gint titleindex, gint track)
+{
+ hb_list_t * list;
+ hb_title_t * title;
+ hb_audio_config_t * audio;
+ gchar *lang = NULL;
+
+ g_debug("ghb_lookup_1st_audio_lang ()\n");
+ if (h_scan == NULL)
+ return NULL;
+ list = hb_get_titles( h_scan );
+ title = (hb_title_t*)hb_list_item( list, titleindex );
+ if (title == NULL)
+ return NULL;
+ if (hb_list_count( title->list_audio ) <= track)
+ return NULL;
+
+ audio = hb_list_audio_config_item(title->list_audio, track);
+ if (audio == NULL)
+ return NULL;
+
+ lang = g_strdup(audio->lang.iso639_2);
+ return lang;
+}
+
gint
ghb_find_audio_track(
gint titleindex,
return lookup_video_rate_int(gval);
else if (strcmp(name, "AudioMixdown") == 0)
return lookup_mix_int(gval);
- else if (strcmp(name, "SourceAudioLang") == 0)
+ else if (strcmp(name, "PreferredLanguage") == 0)
return lookup_audio_lang_int(gval);
else
{
return lookup_video_rate_int(gval);
else if (strcmp(name, "AudioMixdown") == 0)
return lookup_mix_int(gval);
- else if (strcmp(name, "SourceAudioLang") == 0)
+ else if (strcmp(name, "PreferredLanguage") == 0)
return lookup_audio_lang_int(gval);
else
{
return lookup_video_rate_option(gval);
else if (strcmp(name, "AudioMixdown") == 0)
return lookup_mix_option(gval);
- else if (strcmp(name, "SourceAudioLang") == 0)
+ else if (strcmp(name, "PreferredLanguage") == 0)
return lookup_audio_lang_option(gval);
else
{
return lookup_video_rate_option(gval);
else if (strcmp(name, "AudioMixdown") == 0)
return lookup_mix_option(gval);
- else if (strcmp(name, "SourceAudioLang") == 0)
+ else if (strcmp(name, "PreferredLanguage") == 0)
return lookup_audio_lang_option(gval);
else
{
audio_samplerate_opts_set(ud->builder, "AudioSamplerate", hb_audio_rates, hb_audio_rates_count);
video_rate_opts_set(ud->builder, "VideoFramerate", hb_video_rates, hb_video_rates_count);
mix_opts_set(ud->builder, "AudioMixdown");
- language_opts_set(ud->builder, "SourceAudioLang");
+ language_opts_set(ud->builder, "PreferredLanguage");
title_opts_set(ud->builder, "title");
audio_track_opts_set(ud->builder, "AudioTrack", user_data);
subtitle_track_opts_set(ud->builder, "SubtitleTrack", user_data);
generic_opts_set(ud->builder, "PicturePAR", &par_opts);
generic_opts_set(ud->builder, "PictureModulus", &alignment_opts);
generic_opts_set(ud->builder, "LoggingLevel", &logging_opts);
+ generic_opts_set(ud->builder, "check_updates", &appcast_update_opts);
generic_opts_set(ud->builder, "FileFormat", &container_opts);
generic_opts_set(ud->builder, "PictureDeinterlace", &deint_opts);
generic_opts_set(ud->builder, "PictureDetelecine", &detel_opts);
video_rate_opts_set(ud->builder, "VideoFramerate", hb_video_rates, hb_video_rates_count);
else if (strcmp(name, "AudioMixdown") == 0)
mix_opts_set(ud->builder, "AudioMixdown");
- else if (strcmp(name, "SourceAudioLang") == 0)
- language_opts_set(ud->builder, "SourceAudioLang");
+ else if (strcmp(name, "PreferredLanguage") == 0)
+ language_opts_set(ud->builder, "PreferredLanguage");
else if (strcmp(name, "title") == 0)
title_opts_set(ud->builder, "title");
else if (strcmp(name, "SubtitleTrack") == 0)
init_combo_box(builder, "AudioSamplerate");
init_combo_box(builder, "VideoFramerate");
init_combo_box(builder, "AudioMixdown");
- init_combo_box(builder, "SourceAudioLang");
+ init_combo_box(builder, "PreferredLanguage");
init_combo_box(builder, "title");
init_combo_box(builder, "AudioTrack");
for (ii = 0; combo_name_map[ii].name != NULL; ii++)
static const char * turbo_opts =
"ref=1:subme=1:me=dia:analyse=none:trellis=0:"
- "no-fast-pskip=0:8x8dct=0:weightb=0";
+ "no-fast-pskip=0:8x8dct=0";
// Construct the x264 options string
// The result is allocated, so someone must free it at some point.
asettings = ghb_array_get_nth(audio_list, ii);
acodec = ghb_settings_combo_int(asettings, "AudioEncoder");
- if (acodec == HB_ACODEC_AC3)
+ if (acodec & HB_ACODEC_AC3)
return TRUE;
}
return FALSE;
{
gboolean autoscale, keep_aspect, enable_keep_aspect;
gboolean enable_scale_width, enable_scale_height;
- gboolean enable_disp_width, enable_disp_height;
+ gboolean enable_disp_width, enable_disp_height, enable_par;
gint pic_par;
GtkWidget *widget;
enable_scale_width = !autoscale && (pic_par != 1);
enable_scale_height = !autoscale && (pic_par != 1);
enable_disp_width = (pic_par == 3) && !keep_aspect;
+ enable_par = (pic_par == 3) && !keep_aspect;
enable_disp_height = FALSE;
widget = GHB_WIDGET(ud->builder, "PictureModulus");
gtk_widget_set_sensitive(widget, enable_disp_width);
widget = GHB_WIDGET(ud->builder, "PictureDisplayHeight");
gtk_widget_set_sensitive(widget, enable_disp_height);
+ widget = GHB_WIDGET(ud->builder, "PicturePARWidth");
+ gtk_widget_set_sensitive(widget, enable_par);
+ widget = GHB_WIDGET(ud->builder, "PicturePARHeight");
+ gtk_widget_set_sensitive(widget, enable_par);
widget = GHB_WIDGET(ud->builder, "PictureKeepRatio");
gtk_widget_set_sensitive(widget, enable_keep_aspect);
widget = GHB_WIDGET(ud->builder, "autoscale");
// The scaler crashes if the dimensions are not divisible by 2
// Align mod 2. And so does something in x264_encoder_headers()
job->anamorphic.modulus = mod;
+ job->anamorphic.par_width = title->pixel_aspect_width;
+ job->anamorphic.par_height = title->pixel_aspect_height;
+ job->anamorphic.dar_width = 0;
+ job->anamorphic.dar_height = 0;
+
if (keep_height && pic_par == 2)
width = ((double)height * crop_width / crop_height) + 0.5;
job->width = width;
job->crop[2] = crop[2]; job->crop[3] = crop[3];
if (job->anamorphic.mode == 3 && !keep_aspect)
{
- gint dar_width, dar_height;
+ job->anamorphic.keep_display_aspect = 0;
if (mode & GHB_PIC_KEEP_PAR)
{
- par_width = ghb_settings_get_int(ud->settings,
- "PicturePARWidth");
- par_height = ghb_settings_get_int(ud->settings,
- "PicturePARHeight");
- dar_width = ((gdouble)width * par_width / par_height) + 0.5;
- dar_height = height;
+ job->anamorphic.par_width =
+ ghb_settings_get_int(ud->settings, "PicturePARWidth");
+ job->anamorphic.par_height =
+ ghb_settings_get_int(ud->settings, "PicturePARHeight");
}
else
{
- dar_width = ghb_settings_get_int(ud->settings,
- "PictureDisplayWidth");
- dar_height = ghb_settings_get_int(ud->settings,
- "PictureDisplayHeight");
+ job->anamorphic.dar_width =
+ ghb_settings_get_int(ud->settings,
+ "PictureDisplayWidth");
+ job->anamorphic.dar_height =
+ ghb_settings_get_int(ud->settings,
+ "PictureDisplayHeight");
}
- job->anamorphic.dar_width = dar_width;
- job->anamorphic.dar_height = dar_height;
- job->anamorphic.keep_display_aspect = 0;
}
else
{
- job->anamorphic.dar_width = 0;
- job->anamorphic.dar_height = 0;
job->anamorphic.keep_display_aspect = 1;
}
hb_set_anamorphic_size( job, &width, &height,
&par_width, &par_height );
+ if (job->anamorphic.mode == 3 && !keep_aspect &&
+ mode & GHB_PIC_KEEP_PAR)
+ {
+ // hb_set_anamorphic_size reduces the par, which we
+ // don't want in this case because the user is
+ // explicitely specifying it.
+ par_width = ghb_settings_get_int(ud->settings,
+ "PicturePARWidth");
+ par_height = ghb_settings_get_int(ud->settings,
+ "PicturePARHeight");
+ }
}
else
{
}
ghb_ui_update(ud, "display_aspect", ghb_string_value(str));
g_free(str);
- ghb_ui_update(ud, "par_width", ghb_int64_value(par_width));
- ghb_ui_update(ud, "par_height", ghb_int64_value(par_height));
+ ghb_ui_update(ud, "PicturePARWidth", ghb_int64_value(par_width));
+ ghb_ui_update(ud, "PicturePARHeight", ghb_int64_value(par_height));
ghb_ui_update(ud, "PictureDisplayWidth", ghb_int64_value(disp_width));
ghb_ui_update(ud, "PictureDisplayHeight", ghb_int64_value(height));
busy = FALSE;
gboolean keep_aspect;
keep_aspect = ghb_settings_get_boolean(settings, "PictureKeepRatio");
- if (job->anamorphic.mode == 3 && !keep_aspect)
+ if (job->anamorphic.mode)
{
- gint disp_width, disp_height;
- disp_width = ghb_settings_get_int(settings, "PictureDisplayWidth");
- disp_height = ghb_settings_get_int(settings, "PictureDisplayHeight");
- job->anamorphic.dar_width = disp_width;
- job->anamorphic.dar_height = disp_height;
- job->anamorphic.keep_display_aspect = 0;
- }
- else
- {
- job->anamorphic.keep_display_aspect = 1;
+ job->anamorphic.par_width = job->title->pixel_aspect_width;
+ job->anamorphic.par_height = job->title->pixel_aspect_height;
job->anamorphic.dar_width = 0;
job->anamorphic.dar_height = 0;
+
+ if (job->anamorphic.mode == 3 && !keep_aspect)
+ {
+ job->anamorphic.keep_display_aspect = 0;
+ job->anamorphic.par_width =
+ ghb_settings_get_int(settings, "PicturePARWidth");
+ job->anamorphic.par_height =
+ ghb_settings_get_int(settings, "PicturePARHeight");
+ }
+ else
+ {
+ job->anamorphic.keep_display_aspect = 1;
+ }
}
}
job->deinterlace = 0;
job->grayscale = ghb_settings_get_boolean(js, "VideoGrayScale");
+ gboolean keep_aspect;
+ keep_aspect = ghb_settings_get_boolean(js, "PictureKeepRatio");
job->anamorphic.mode = ghb_settings_combo_int(js, "PicturePAR");
job->anamorphic.modulus = ghb_settings_combo_int(js, "PictureModulus");
+ if (job->anamorphic.mode)
+ {
+ job->anamorphic.par_width = title->pixel_aspect_width;
+ job->anamorphic.par_height = title->pixel_aspect_height;
+ job->anamorphic.dar_width = 0;
+ job->anamorphic.dar_height = 0;
+
+ if (job->anamorphic.mode == 3 && !keep_aspect)
+ {
+ job->anamorphic.keep_display_aspect = 0;
+ job->anamorphic.par_width =
+ ghb_settings_get_int(js, "PicturePARWidth");
+ job->anamorphic.par_height =
+ ghb_settings_get_int(js, "PicturePARHeight");
+ }
+ else
+ {
+ job->anamorphic.keep_display_aspect = 1;
+ }
+ }
/* Add selected filters */
job->filters = hb_list_init();
dest_str = ghb_settings_get_string(js, "destination");
job->file = dest_str;
job->crf = ghb_settings_get_boolean(js, "constant_rate_factor");
- // TODO: libhb holds onto a reference to the x264opts and is not
- // finished with it until encoding the job is done. But I can't
- // find a way to get at the job before it is removed in order to
- // free up the memory I am allocating here.
- // The short story is THIS LEAKS.
- x264opts = ghb_build_x264opts_string(js);
-
- if( x264opts != NULL && *x264opts != '\0' )
- {
- job->x264opts = x264opts;
- }
- else /*avoids a bus error crash when options aren't specified*/
- {
- job->x264opts = NULL;
- }
const GValue *subtitle_list;
gint subtitle;
gboolean force, burned, def, one_burned = FALSE;
- job->select_subtitle = NULL;
subtitle_list = ghb_settings_get_value(js, "subtitle_list");
count = ghb_array_len(subtitle_list);
for (ii = 0; ii < count; ii++)
// Only allow one subtitle to be burned into the video
if (one_burned)
continue;
+ job->select_subtitle_config.dest = RENDERSUB;
one_burned = TRUE;
}
job->select_subtitle_config.force = force;
job->select_subtitle_config.default_track = def;
job->indepth_scan = 1;
- job->select_subtitle = malloc(sizeof(hb_subtitle_t*));
- *job->select_subtitle = NULL;
}
else if (subtitle >= 0)
{
}
}
+ // TODO: libhb holds onto a reference to the x264opts and is not
+ // finished with it until encoding the job is done. But I can't
+ // find a way to get at the job before it is removed in order to
+ // free up the memory I am allocating here.
+ // The short story is THIS LEAKS.
+ x264opts = ghb_build_x264opts_string(js);
+
+ if( *x264opts == '\0' )
+ {
+ g_free(x264opts);
+ x264opts = NULL;
+ }
+
if (job->indepth_scan == 1)
{
// Subtitle scan. Look for subtitle matching audio language
- char *x264opts_tmp;
/*
* When subtitle scan is enabled do a fast pre-scan job
*/
job->pass = -1;
job->indepth_scan = 1;
-
- x264opts_tmp = job->x264opts;
job->x264opts = NULL;
-
/*
* Add the pre-scan job
*/
job->sequence_id = (unique_id & 0xFFFFFF) | (sub_id++ << 24);
hb_add( h, job );
- //if (job->x264opts != NULL)
- // g_free(job->x264opts);
-
- job->x264opts = x264opts_tmp;
}
if( ghb_settings_get_boolean(js, "VideoTwoPass") &&
* for the second pass and then off again for the
* second.
*/
- hb_subtitle_t **subtitle_tmp = job->select_subtitle;
- job->select_subtitle = NULL;
job->pass = 1;
job->indepth_scan = 0;
- gchar *x264opts2 = NULL;
- if (x264opts)
- {
- x264opts2 = g_strdup(x264opts);
- }
+
/*
* If turbo options have been selected then append them
* to the x264opts now (size includes one ':' and the '\0')
*/
if( ghb_settings_get_boolean(js, "VideoTurboTwoPass") )
{
- char *tmp_x264opts;
+ gchar *tmp_x264opts;
+ gchar *extra_opts;
+ gint badapt;
+ badapt = ghb_lookup_badapt(x264opts);
+ if (badapt == 2)
+ {
+ extra_opts = g_strdup_printf("%s", turbo_opts);
+ }
+ else
+ {
+ extra_opts = g_strdup_printf("%s:weightb=0", turbo_opts);
+ }
+
if ( x264opts )
{
- tmp_x264opts = g_strdup_printf("%s:%s", x264opts, turbo_opts);
- g_free(x264opts);
+ tmp_x264opts = g_strdup_printf("%s:%s", x264opts, extra_opts);
}
else
{
* No x264opts to modify, but apply the turbo options
* anyway as they may be modifying defaults
*/
- tmp_x264opts = g_strdup_printf("%s", turbo_opts);
+ tmp_x264opts = g_strdup_printf("%s", extra_opts);
}
- x264opts = tmp_x264opts;
+ g_free(extra_opts);
+ job->x264opts = tmp_x264opts;
+ }
+ else
+ {
job->x264opts = x264opts;
}
job->sequence_id = (unique_id & 0xFFFFFF) | (sub_id++ << 24);
//if (job->x264opts != NULL)
// g_free(job->x264opts);
- job->select_subtitle = subtitle_tmp;
job->pass = 2;
/*
* On the second pass we turn off subtitle scan so that we
* attribute of the job).
*/
job->indepth_scan = 0;
- job->x264opts = x264opts2;
+ job->x264opts = x264opts;
job->sequence_id = (unique_id & 0xFFFFFF) | (sub_id++ << 24);
hb_add( h, job );
//if (job->x264opts != NULL)
}
else
{
+ job->x264opts = x264opts;
job->indepth_scan = 0;
job->pass = 0;
job->sequence_id = (unique_id & 0xFFFFFF) | (sub_id++ << 24);