]> git.sesse.net Git - vlc/blobdiff - modules/codec/schroedinger.c
MP4: fix a typo
[vlc] / modules / codec / schroedinger.c
index 58fe20749456daefaf253ffd55876ec8f5f57eea..bc1e1c259ded3ee5de58a5c888102ef7851004c1 100644 (file)
@@ -3,8 +3,7 @@
  *          (http://www.bbc.co.uk/rd/projects/dirac/index.shtml)
  *          (http://diracvideo.org)
  *****************************************************************************
- * Copyright (C) 2008 the VideoLAN team
- * $Id$
+ * Copyright (C) 2008-2011 the VideoLAN team
  *
  * Authors: Jonathan Rosser <jonathan.rosser@gmail.com>
  *          David Flynn <davidf at rd dot bbc.co.uk>
@@ -28,6 +27,7 @@
 /*****************************************************************************
  * Preamble
  *****************************************************************************/
+
 #ifdef HAVE_CONFIG_H
 # include "config.h"
 #endif
@@ -36,8 +36,7 @@
 
 #include <vlc_common.h>
 #include <vlc_plugin.h>
-#include <vlc_codec.h>
-#include <vlc_sout.h>
+#include <vlc_codec.h>                              /* decoder_DeletePicture */
 
 #include <schroedinger/schro.h>
 
@@ -51,7 +50,7 @@ static void       CloseEncoder ( vlc_object_t * );
 
 #define ENC_CFG_PREFIX "sout-schro-"
 
-#define ENC_CHROMAFMT "chroma_fmt"
+#define ENC_CHROMAFMT "chroma-fmt"
 #define ENC_CHROMAFMT_TEXT N_("Chroma format")
 #define ENC_CHROMAFMT_LONGTEXT N_("Picking chroma format will force a " \
                                   "conversion of the video into that format")
@@ -60,13 +59,302 @@ static const char *const enc_chromafmt_list[] =
 static const char *const enc_chromafmt_list_text[] =
   { N_("4:2:0"), N_("4:2:2"), N_("4:4:4") };
 
+#define ENC_RATE_CONTROL "rate-control"
+#define ENC_RATE_CONTROL_TEXT N_("Rate control method")
+#define ENC_RATE_CONTROL_LONGTEXT N_("Method used to encode the video sequence")
+
+static const char *enc_rate_control_list[] = {
+  "constant_noise_threshold",
+  "constant_bitrate",
+  "low_delay",
+  "lossless",
+  "constant_lambda",
+  "constant_error",
+  "constant_quality"
+};
+
+static const char *enc_rate_control_list_text[] = {
+  N_("Constant noise threshold mode"),
+  N_("Constant bitrate mode (CBR)"),
+  N_("Low Delay mode"),
+  N_("Lossless mode"),
+  N_("Constant lambda mode"),
+  N_("Constant error mode"),
+  N_("Constant quality mode")
+};
+
+#define ENC_GOP_STRUCTURE "gop-structure"
+#define ENC_GOP_STRUCTURE_TEXT N_("GOP structure")
+#define ENC_GOP_STRUCTURE_LONGTEXT N_("GOP structure used to encode the video sequence")
+
+static const char *enc_gop_structure_list[] = {
+  "adaptive",
+  "intra_only",
+  "backref",
+  "chained_backref",
+  "biref",
+  "chained_biref"
+};
+
+static const char *enc_gop_structure_list_text[] = {
+  N_("No fixed gop structure. A picture can be intra or inter and refer to previous or future pictures."),
+  N_("I-frame only sequence"),
+  N_("Inter pictures refere to previous pictures only"),
+  N_("Inter pictures refere to previous pictures only"),
+  N_("Inter pictures can refer to previous or future pictures"),
+  N_("Inter pictures can refer to previous or future pictures")
+};
+
+#define ENC_QUALITY "quality"
+#define ENC_QUALITY_TEXT N_("Constant quality factor")
+#define ENC_QUALITY_LONGTEXT N_("Quality factor to use in constant quality mode")
+
+#define ENC_NOISE_THRESHOLD "noise-threshold"
+#define ENC_NOISE_THRESHOLD_TEXT N_("Noise Threshold")
+#define ENC_NOISE_THRESHOLD_LONGTEXT N_("Noise threshold to use in constant noise threshold mode")
+
+#define ENC_BITRATE "bitrate"
+#define ENC_BITRATE_TEXT N_("CBR bitrate (kbps)")
+#define ENC_BITRATE_LONGTEXT N_("Target bitrate in kbps when encoding in constant bitrate mode")
+
+#define ENC_MAX_BITRATE "max-bitrate"
+#define ENC_MAX_BITRATE_TEXT N_("Maximum bitrate (kbps)")
+#define ENC_MAX_BITRATE_LONGTEXT N_("Maximum bitrate in kbps when encoding in constant bitrate mode")
 
-#define ENC_CODINGMODE "auto_coding_mode"
-#define ENC_CODINGMODE_TEXT N_("Automate picture coding mode")
-#define ENC_CODINGMODE_LONGTEXT N_("Use the input picture to determine how to" \
-                                   " code it - interlaced or progressive")
+#define ENC_MIN_BITRATE "min-bitrate"
+#define ENC_MIN_BITRATE_TEXT N_("Minimum bitrate (kbps)")
+#define ENC_MIN_BITRATE_LONGTEXT N_("Minimum bitrate in kbps when encoding in constant bitrate mode")
 
-static const char **ppsz_enc_options = NULL;
+#define ENC_AU_DISTANCE "gop-length"
+#define ENC_AU_DISTANCE_TEXT N_("GOP length")
+#define ENC_AU_DISTANCE_LONGTEXT N_("Number of pictures between successive sequenence headers i.e. length of the group of pictures")
+
+
+#define ENC_PREFILTER "filtering"
+#define ENC_PREFILTER_TEXT N_("Prefilter")
+#define ENC_PREFILTER_LONGTEXT N_("Enable adaptive prefiltering")
+
+static const char *enc_filtering_list[] = {
+  "none",
+  "center_weighted_median",
+  "gaussian",
+  "add_noise",
+  "adaptive_gaussian",
+  "lowpass"
+};
+
+static const char *enc_filtering_list_text[] = {
+  N_("No pre-filtering"),
+  N_("Centre Weighted Median"),
+  N_("Gaussian Low Pass Filter"),
+  N_("Add Noise"),
+  N_("Gaussian Adaptive Low Pass Filter"),
+  N_("Low Pass Ffilter"),
+};
+
+#define ENC_PREFILTER_STRENGTH "filter-value"
+#define ENC_PREFILTER_STRENGTH_TEXT N_("Amount of prefiltering")
+#define ENC_PREFILTER_STRENGTH_LONGTEXT N_("Higher value implies more prefiltering")
+
+#define ENC_CODINGMODE "coding-mode"
+#define ENC_CODINGMODE_TEXT N_("Picture coding mode")
+#define ENC_CODINGMODE_LONGTEXT N_("Field coding is where interlaced fields are coded" \
+                                   " separately as opposed to a pseudo-progressive frame")
+static const char *const enc_codingmode_list[] =
+  { "auto", "progressive", "field" };
+static const char *const enc_codingmode_list_text[] =
+  { N_("auto - let encoder decide based upon input (Best)"),
+    N_("force coding frame as single picture"),
+    N_("force coding frame as separate interlaced fields"),
+  };
+
+/* advanced option only */
+#define ENC_MCBLK_SIZE "motion-block-size"
+#define ENC_MCBLK_SIZE_TEXT N_("Size of motion compensation blocks")
+
+static const char *enc_block_size_list[] = {
+  "automatic",
+  "small",
+  "medium",
+  "large"
+};
+static const char *const enc_block_size_list_text[] =
+  { N_("automatic - let encoder decide based upon input (Best)"),
+    N_("small - use small motion compensation blocks"),
+    N_("medium - use medium motion compensation blocks"),
+    N_("large - use large motion compensation blocks"),
+  };
+
+/* advanced option only */
+#define ENC_MCBLK_OVERLAP "motion-block-overlap"
+#define ENC_MCBLK_OVERLAP_TEXT N_("Overlap of motion compensation blocks")
+
+static const char *enc_block_overlap_list[] = {
+  "automatic",
+  "none",
+  "partial",
+  "full"
+};
+static const char *const enc_block_overlap_list_text[] =
+  { N_("automatic - let encoder decide based upon input (Best)"),
+    N_("none - Motion compensation blocks do not overlap"),
+    N_("partial - Motion compensation blocks only partially overlap"),
+    N_("full - Motion compensation blocks fully overlap"),
+  };
+
+
+#define ENC_MVPREC "mv-precision"
+#define ENC_MVPREC_TEXT N_("Motion Vector precision")
+#define ENC_MVPREC_LONGTEXT N_("Motion Vector precision in pels")
+static const char *const enc_mvprec_list[] =
+  { "1", "1/2", "1/4", "1/8" };
+
+/* advanced option only */
+#define ENC_ME_COMBINED "me-combined"
+#define ENC_ME_COMBINED_TEXT N_("Three component motion estimation")
+#define ENC_ME_COMBINED_LONGTEXT N_("Use chroma as part of the motion estimation process")
+
+#define ENC_DWTINTRA "intra-wavelet"
+#define ENC_DWTINTRA_TEXT N_("Intra picture DWT filter")
+
+#define ENC_DWTINTER "inter-wavelet"
+#define ENC_DWTINTER_TEXT N_("Inter picture DWT filter")
+
+static const char *enc_wavelet_list[] = {
+  "desl_dubuc_9_7",
+  "le_gall_5_3",
+  "desl_dubuc_13_7",
+  "haar_0",
+  "haar_1",
+  "fidelity",
+  "daub_9_7"
+};
+
+static const char *enc_wavelet_list_text[] = {
+  "Deslauriers-Dubuc (9,7)",
+  "LeGall (5,3)",
+  "Deslauriers-Dubuc (13,7)",
+  "Haar with no shift",
+  "Haar with single shift per level",
+  "Fidelity filter",
+  "Daubechies (9,7) integer approximation"
+};
+
+#define ENC_DWTDEPTH "transform-depth"
+#define ENC_DWTDEPTH_TEXT N_("Number of DWT iterations")
+#define ENC_DWTDEPTH_LONGTEXT N_("Also known as DWT levels")
+
+
+/* advanced option only */
+#define ENC_MULTIQUANT "enable-multiquant"
+#define ENC_MULTIQUANT_TEXT N_("Enable multiple quantizers")
+#define ENC_MULTIQUANT_LONGTEXT N_("Enable multiple quantizers per subband (one per codeblock)")
+
+/* advanced option only */
+#define ENC_NOAC "enable-noarith"
+#define ENC_NOAC_TEXT N_("Disable arithmetic coding")
+#define ENC_NOAC_LONGTEXT N_("Use variable length codes instead, useful for very high bitrates")
+
+/* visual modelling */
+/* advanced option only */
+#define ENC_PWT "perceptual-weighting"
+#define ENC_PWT_TEXT N_("perceptual weighting method")
+
+static const char *enc_perceptual_weighting_list[] = {
+  "none",
+  "ccir959",
+  "moo",
+  "manos_sakrison"
+};
+
+/* advanced option only */
+#define ENC_PDIST "perceptual-distance"
+#define ENC_PDIST_TEXT N_("perceptual distance")
+#define ENC_PDIST_LONGTEXT N_("perceptual distance to calculate perceptual weight")
+
+/* advanced option only */
+#define ENC_HSLICES "horiz-slices"
+#define ENC_HSLICES_TEXT N_("Horizontal slices per frame")
+#define ENC_HSLICES_LONGTEXT N_("Number of horizontal slices per frame in low delay mode")
+
+/* advanced option only */
+#define ENC_VSLICES "vert-slices"
+#define ENC_VSLICES_TEXT N_("Vertical slices per frame")
+#define ENC_VSLICES_LONGTEXT N_("Number of vertical slices per frame in low delay mode")
+
+/* advanced option only */
+#define ENC_SCBLK_SIZE "codeblock-size"
+#define ENC_SCBLK_SIZE_TEXT N_("Size of code blocks in each subband")
+
+static const char *enc_codeblock_size_list[] = {
+  "automatic",
+  "small",
+  "medium",
+  "large",
+  "full"
+};
+static const char *const enc_codeblock_size_list_text[] =
+  { N_("automatic - let encoder decide based upon input (Best)"),
+    N_("small - use small code blocks"),
+    N_("medium - use medium sized code blocks"),
+    N_("large - use large code blocks"),
+    N_("full - One code block per subband"),
+  };
+
+/* advanced option only */
+#define ENC_ME_HIERARCHICAL "enable-hierarchical-me"
+#define ENC_ME_HIERARCHICAL_TEXT N_("Enable hierarchical Motion Estimation")
+
+/* advanced option only */
+#define ENC_ME_DOWNSAMPLE_LEVELS "downsample-levels"
+#define ENC_ME_DOWNSAMPLE_LEVELS_TEXT N_("Number of levels of downsampling")
+#define ENC_ME_DOWNSAMPLE_LEVELS_LONGTEXT N_("Number of levels of downsampling in hierarchical motion estimation mode")
+
+/* advanced option only */
+#define ENC_ME_GLOBAL_MOTION "enable-global-me"
+#define ENC_ME_GLOBAL_MOTION_TEXT N_("Enable Global Motion Estimation")
+
+/* advanced option only */
+#define ENC_ME_PHASECORR "enable-phasecorr-me"
+#define ENC_ME_PHASECORR_TEXT N_("Enable Phase Correlation Estimation")
+
+/* advanced option only */
+#define ENC_SCD "enable-scd"
+#define ENC_SCD_TEXT N_("Enable Scene Change Detection")
+
+/* advanced option only */
+#define ENC_FORCE_PROFILE "force-profile"
+#define ENC_FORCE_PROFILE_TEXT N_("Force Profile")
+
+static const char *enc_profile_list[] = {
+  "auto",
+  "vc2_low_delay",
+  "vc2_simple",
+  "vc2_main",
+  "main"
+};
+
+static const char *const enc_profile_list_text[] =
+  { N_("automatic - let encoder decide based upon input (Best)"),
+    N_("VC2 Low Delay Profile"),
+    N_("VC2 Simple Profile"),
+    N_("VC2 Main Profile"),
+    N_("Main Profile"),
+  };
+
+static const char *const const ppsz_enc_options[] = {
+    ENC_RATE_CONTROL, ENC_GOP_STRUCTURE, ENC_QUALITY, ENC_NOISE_THRESHOLD, ENC_BITRATE,
+    ENC_MIN_BITRATE, ENC_MAX_BITRATE, ENC_AU_DISTANCE, ENC_CHROMAFMT,
+    ENC_PREFILTER, ENC_PREFILTER_STRENGTH, ENC_CODINGMODE, ENC_MCBLK_SIZE,
+    ENC_MCBLK_OVERLAP, ENC_MVPREC, ENC_ME_COMBINED, ENC_DWTINTRA, ENC_DWTINTER,
+    ENC_DWTDEPTH, ENC_MULTIQUANT, ENC_NOAC, ENC_PWT, ENC_PDIST, ENC_HSLICES,
+    ENC_VSLICES, ENC_SCBLK_SIZE, ENC_ME_HIERARCHICAL, ENC_ME_DOWNSAMPLE_LEVELS,
+    ENC_ME_GLOBAL_MOTION, ENC_ME_PHASECORR, ENC_SCD, ENC_FORCE_PROFILE,
+    NULL
+};
+
+
+/* Module declaration */
 
 vlc_module_begin ()
     set_category( CAT_INPUT )
@@ -77,6 +365,7 @@ vlc_module_begin ()
     set_callbacks( OpenDecoder, CloseDecoder )
     add_shortcut( "schroedinger" )
 
+    /* encoder */
     add_submodule()
     set_section( N_("Encoding") , NULL )
     set_description( N_("Dirac video encoder using libschroedinger") )
@@ -84,61 +373,154 @@ vlc_module_begin ()
     set_callbacks( OpenEncoder, CloseEncoder )
     add_shortcut( "schroedinger", "schro" )
 
-    int i_numopts =  schro_encoder_get_n_settings();
-    /* Allocate for schro encoder options + chroma format + coding mode
-       + null */
-    ppsz_enc_options = (const char **)malloc( sizeof( char * )*( i_numopts + 3 ) );
-    if( unlikely( ppsz_enc_options == NULL ) )
-        return VLC_ENOMEM;
+    add_string( ENC_CFG_PREFIX ENC_RATE_CONTROL, NULL,
+                 ENC_RATE_CONTROL_TEXT, ENC_RATE_CONTROL_LONGTEXT, false )
+    change_string_list( enc_rate_control_list, enc_rate_control_list_text, 0 );
 
-    for( int i = 0; i < i_numopts; ++i ) {
-        const SchroEncoderSetting *p_setting = schro_encoder_get_setting_info( i );
-        bool b_advanced = ( strlen( p_setting->name ) > 6 && !strncmp( p_setting->name, "magic_ ", 6 ) );
-        char *p_cfg_setting_name = malloc( strlen( ENC_CFG_PREFIX ) + strlen( p_setting->name ) + 1 );
+    add_float( ENC_CFG_PREFIX ENC_QUALITY, -1.,
+               ENC_QUALITY_TEXT, ENC_QUALITY_LONGTEXT, false )
+    change_float_range(-1., 10.);
 
-        if( unlikely( p_cfg_setting_name == NULL ) )
-            return VLC_ENOMEM;
+    add_float( ENC_CFG_PREFIX ENC_NOISE_THRESHOLD, -1.,
+               ENC_NOISE_THRESHOLD_TEXT, ENC_NOISE_THRESHOLD_LONGTEXT, false )
+    change_float_range(-1., 100.);
 
-        strcpy( p_cfg_setting_name, ENC_CFG_PREFIX );
-        strcat( p_cfg_setting_name, p_setting->name );
+    add_integer( ENC_CFG_PREFIX ENC_BITRATE, -1,
+                 ENC_BITRATE_TEXT, ENC_BITRATE_LONGTEXT, false )
+    change_integer_range(-1, INT_MAX);
 
-        ppsz_enc_options[i] = strdup( p_setting->name );
-        switch( p_setting->type ) {
-            case SCHRO_ENCODER_SETTING_TYPE_BOOLEAN:
-                add_bool( p_cfg_setting_name, p_setting->default_value, p_setting->name, p_setting->name, b_advanced );
-                break;
-            case SCHRO_ENCODER_SETTING_TYPE_INT:
-                add_integer( p_cfg_setting_name, p_setting->default_value, p_setting->name, p_setting->name, b_advanced );
-                change_integer_range( p_setting->min, p_setting->max );
-                break;
-            case SCHRO_ENCODER_SETTING_TYPE_DOUBLE:
-                add_float( p_cfg_setting_name, p_setting->default_value, p_setting->name, p_setting->name, b_advanced );
-                change_float_range( p_setting->min, p_setting->max );
-                break;
-            case SCHRO_ENCODER_SETTING_TYPE_ENUM:
-                add_string( p_cfg_setting_name, p_setting->enum_list[(int)p_setting->default_value], p_setting->name, p_setting->name, b_advanced );
-                vlc_config_set( p_config, VLC_CONFIG_LIST, (int)(p_setting->max-p_setting->min+1), p_setting->enum_list, p_setting->enum_list, 0 );
-                break;
-            default:
-                break;
-        }
-        free( p_cfg_setting_name );
-    }
+    add_integer( ENC_CFG_PREFIX ENC_MAX_BITRATE, -1,
+                 ENC_MAX_BITRATE_TEXT, ENC_MAX_BITRATE_LONGTEXT, false )
+    change_integer_range(-1, INT_MAX);
+
+    add_integer( ENC_CFG_PREFIX ENC_MIN_BITRATE, -1,
+                 ENC_MIN_BITRATE_TEXT, ENC_MIN_BITRATE_LONGTEXT, false )
+    change_integer_range(-1, INT_MAX);
+
+    add_string( ENC_CFG_PREFIX ENC_GOP_STRUCTURE, NULL,
+                 ENC_GOP_STRUCTURE_TEXT, ENC_GOP_STRUCTURE_LONGTEXT, false )
+    change_string_list( enc_gop_structure_list, enc_gop_structure_list_text, 0 );
+
+    add_integer( ENC_CFG_PREFIX ENC_AU_DISTANCE, -1,
+                 ENC_AU_DISTANCE_TEXT, ENC_AU_DISTANCE_LONGTEXT, false )
+    change_integer_range(-1, INT_MAX);
 
-    ppsz_enc_options[i_numopts] = strdup( ENC_CHROMAFMT );
     add_string( ENC_CFG_PREFIX ENC_CHROMAFMT, "420",
                 ENC_CHROMAFMT_TEXT, ENC_CHROMAFMT_LONGTEXT, false )
     change_string_list( enc_chromafmt_list, enc_chromafmt_list_text, 0 );
 
-    ppsz_enc_options[i_numopts+1] = strdup( ENC_CODINGMODE );
-    add_bool( ENC_CFG_PREFIX ENC_CODINGMODE, true,
+    add_string( ENC_CFG_PREFIX ENC_CODINGMODE, "auto",
                 ENC_CODINGMODE_TEXT, ENC_CODINGMODE_LONGTEXT, false )
-
-    ppsz_enc_options[i_numopts+2] = NULL;
-
+    change_string_list( enc_codingmode_list, enc_codingmode_list_text, 0 );
+
+    add_string( ENC_CFG_PREFIX ENC_MVPREC, NULL,
+                ENC_MVPREC_TEXT, ENC_MVPREC_LONGTEXT, false )
+    change_string_list( enc_mvprec_list, enc_mvprec_list, 0 );
+
+    /* advanced option only */
+    add_string( ENC_CFG_PREFIX ENC_MCBLK_SIZE, NULL,
+                ENC_MCBLK_SIZE_TEXT, ENC_MCBLK_SIZE_TEXT, true )
+    change_string_list( enc_block_size_list, enc_block_size_list_text, 0 );
+
+
+    /* advanced option only */
+    add_string( ENC_CFG_PREFIX ENC_MCBLK_OVERLAP, NULL,
+                ENC_MCBLK_OVERLAP_TEXT, ENC_MCBLK_OVERLAP_TEXT, true )
+    change_string_list( enc_block_overlap_list, enc_block_overlap_list_text, 0 );
+
+    /* advanced option only */
+    add_integer( ENC_CFG_PREFIX ENC_ME_COMBINED, -1,
+              ENC_ME_COMBINED_TEXT, ENC_ME_COMBINED_LONGTEXT, true )
+    change_integer_range(-1, 1 );
+
+    /* advanced option only */
+    add_integer( ENC_CFG_PREFIX ENC_ME_HIERARCHICAL, -1,
+                 ENC_ME_HIERARCHICAL_TEXT, ENC_ME_HIERARCHICAL_TEXT, true )
+    change_integer_range(-1, 1 );
+
+    /* advanced option only */
+    add_integer( ENC_CFG_PREFIX ENC_ME_DOWNSAMPLE_LEVELS, -1,
+                 ENC_ME_DOWNSAMPLE_LEVELS_TEXT, ENC_ME_DOWNSAMPLE_LEVELS_LONGTEXT, true )
+    change_integer_range(-1, 8 );
+
+    /* advanced option only */
+    add_integer( ENC_CFG_PREFIX ENC_ME_GLOBAL_MOTION, -1,
+                 ENC_ME_GLOBAL_MOTION_TEXT, ENC_ME_GLOBAL_MOTION_TEXT, true )
+    change_integer_range(-1, 1 );
+
+    /* advanced option only */
+    add_integer( ENC_CFG_PREFIX ENC_ME_PHASECORR, -1,
+                 ENC_ME_PHASECORR_TEXT, ENC_ME_PHASECORR_TEXT, true )
+    change_integer_range(-1, 1 );
+
+    add_string( ENC_CFG_PREFIX ENC_DWTINTRA, NULL,
+                ENC_DWTINTRA_TEXT, ENC_DWTINTRA_TEXT, false )
+    change_string_list( enc_wavelet_list, enc_wavelet_list_text, 0 );
+
+    add_string( ENC_CFG_PREFIX ENC_DWTINTER, NULL,
+                ENC_DWTINTER_TEXT, ENC_DWTINTER_TEXT, false )
+    change_string_list( enc_wavelet_list, enc_wavelet_list_text, 0 );
+
+    add_integer( ENC_CFG_PREFIX ENC_DWTDEPTH, -1,
+                 ENC_DWTDEPTH_TEXT, ENC_DWTDEPTH_LONGTEXT, false )
+    change_integer_range(-1, SCHRO_LIMIT_ENCODER_TRANSFORM_DEPTH );
+
+    /* advanced option only */
+    add_integer( ENC_CFG_PREFIX ENC_MULTIQUANT, -1,
+                 ENC_MULTIQUANT_TEXT, ENC_MULTIQUANT_LONGTEXT, true )
+    change_integer_range(-1, 1 );
+
+    /* advanced option only */
+    add_string( ENC_CFG_PREFIX ENC_SCBLK_SIZE, NULL,
+                ENC_SCBLK_SIZE_TEXT, ENC_SCBLK_SIZE_TEXT, true )
+    change_string_list( enc_codeblock_size_list, enc_codeblock_size_list_text, 0 );
+
+    add_string( ENC_CFG_PREFIX ENC_PREFILTER, NULL,
+                ENC_PREFILTER_TEXT, ENC_PREFILTER_LONGTEXT, false )
+    change_string_list( enc_filtering_list, enc_filtering_list_text, 0 );
+
+    add_float( ENC_CFG_PREFIX ENC_PREFILTER_STRENGTH, -1.,
+                 ENC_PREFILTER_STRENGTH_TEXT, ENC_PREFILTER_STRENGTH_LONGTEXT, false )
+    change_float_range(-1., 100.0);
+
+    /* advanced option only */
+    add_integer( ENC_CFG_PREFIX ENC_SCD, -1,
+                 ENC_SCD_TEXT, ENC_SCD_TEXT, true )
+    change_integer_range(-1, 1 );
+
+    /* advanced option only */
+    add_string( ENC_CFG_PREFIX ENC_PWT, NULL,
+                ENC_PWT_TEXT, ENC_PWT_TEXT, true )
+    change_string_list( enc_perceptual_weighting_list, enc_perceptual_weighting_list, 0 );
+
+    /* advanced option only */
+    add_float( ENC_CFG_PREFIX ENC_PDIST, -1,
+               ENC_PDIST_TEXT, ENC_PDIST_LONGTEXT, true )
+    change_float_range(-1., 100.);
+
+    /* advanced option only */
+    add_integer( ENC_CFG_PREFIX ENC_NOAC, -1,
+              ENC_NOAC_TEXT, ENC_NOAC_LONGTEXT, true )
+    change_integer_range(-1, 1 );
+
+    /* advanced option only */
+    add_integer( ENC_CFG_PREFIX ENC_HSLICES, -1,
+                 ENC_HSLICES_TEXT, ENC_HSLICES_LONGTEXT, true )
+    change_integer_range(-1, INT_MAX );
+
+    /* advanced option only */
+    add_integer( ENC_CFG_PREFIX ENC_VSLICES, -1,
+                 ENC_VSLICES_TEXT, ENC_VSLICES_LONGTEXT, true )
+    change_integer_range(-1, INT_MAX );
+
+    /* advanced option only */
+    add_string( ENC_CFG_PREFIX ENC_FORCE_PROFILE, NULL,
+                ENC_FORCE_PROFILE_TEXT, ENC_FORCE_PROFILE_TEXT, true )
+    change_string_list( enc_profile_list, enc_profile_list_text, 0 );
 
 vlc_module_end ()
 
+
 /*****************************************************************************
  * Local prototypes
  *****************************************************************************/
@@ -491,9 +873,9 @@ static block_t *Encode( encoder_t *p_enc, picture_t *p_pict );
  *****************************************************************************/
 struct picture_pts_t
 {
-   bool b_empty;      /* entry is invalid */
-   uint32_t u_pnum;  /* dirac picture number */
    mtime_t i_pts;    /* associated pts */
+   uint32_t u_pnum;  /* dirac picture number */
+   bool b_empty;     /* entry is invalid */
 };
 
 /*****************************************************************************
@@ -556,7 +938,7 @@ static struct
 static void ResetPTStlb( encoder_t *p_enc )
 {
     encoder_sys_t *p_sys = p_enc->p_sys;
-    for( int i=0; i<SCHRO_PTS_TLB_SIZE; i++ )
+    for( int i = 0; i < SCHRO_PTS_TLB_SIZE; i++ )
     {
         p_sys->pts_tlb[i].b_empty = true;
     }
@@ -570,7 +952,7 @@ static void StorePicturePTS( encoder_t *p_enc, uint32_t u_pnum, mtime_t i_pts )
 {
     encoder_sys_t *p_sys = p_enc->p_sys;
 
-    for( int i=0; i<SCHRO_PTS_TLB_SIZE; i++ )
+    for( int i = 0; i<SCHRO_PTS_TLB_SIZE; i++ )
     {
         if( p_sys->pts_tlb[i].b_empty )
         {
@@ -592,7 +974,7 @@ static mtime_t GetPicturePTS( encoder_t *p_enc, uint32_t u_pnum )
 {
     encoder_sys_t *p_sys = p_enc->p_sys;
 
-    for( int i=0; i<SCHRO_PTS_TLB_SIZE; i++ )
+    for( int i = 0; i < SCHRO_PTS_TLB_SIZE; i++ )
     {
         if( !p_sys->pts_tlb[i].b_empty &&
             p_sys->pts_tlb[i].u_pnum == u_pnum )
@@ -606,21 +988,18 @@ static mtime_t GetPicturePTS( encoder_t *p_enc, uint32_t u_pnum )
     return 0;
 }
 
-static inline bool SchroSetEnum( const encoder_t *p_enc, const SchroEncoderSetting *p_setting, const char *psz_value ) {
+static inline bool SchroSetEnum( const encoder_t *p_enc, int i_list_size, const char *list[],
+                  const char *psz_name,  const char *psz_name_text,  const char *psz_value)
+{
     encoder_sys_t *p_sys = p_enc->p_sys;
-    if( psz_value && p_setting && p_setting->type == SCHRO_ENCODER_SETTING_TYPE_ENUM ) {
-        int i_index = -1;
-        int i_list_size = p_setting->max - p_setting->min + 1;
+    if( list && psz_name_text && psz_name && psz_value ) {
         for( int i = 0; i < i_list_size; ++i ) {
-            if( strcmp( p_setting->enum_list[i], psz_value ) )
+            if( strcmp( list[i], psz_value ) )
                 continue;
-            i_index = p_setting->min + i;
-            schro_encoder_setting_set_double( p_sys->p_schro, p_setting->name, i_index );
+            schro_encoder_setting_set_double( p_sys->p_schro, psz_name, i );
             return true;
         }
-        if( i_index == -1 ) {
-            msg_Err( p_enc, "Invalid %s: %s", p_setting->name, psz_value );
-        }
+        msg_Err( p_enc, "Invalid %s: %s", psz_name_text, psz_value );
     }
     return false;
 }
@@ -652,6 +1031,28 @@ static bool SetEncChromaFormat( encoder_t *p_enc, uint32_t i_codec )
     return true;
 }
 
+#define SCHRO_SET_FLOAT(psz_name, pschro_name) \
+    f_tmp = var_GetFloat( p_enc, ENC_CFG_PREFIX psz_name ); \
+    if( f_tmp >= 0.0 ) \
+        schro_encoder_setting_set_double( p_sys->p_schro, pschro_name, f_tmp );
+
+#define SCHRO_SET_INTEGER(psz_name, pschro_name, ignore_val) \
+    i_tmp = var_GetInteger( p_enc, ENC_CFG_PREFIX psz_name ); \
+    if( i_tmp > ignore_val ) \
+        schro_encoder_setting_set_double( p_sys->p_schro, pschro_name, i_tmp );
+
+#define SCHRO_SET_ENUM(list, psz_name, psz_name_text, pschro_name) \
+    psz_tmp = var_GetString( p_enc, ENC_CFG_PREFIX psz_name ); \
+    if( !psz_tmp ) \
+        goto error; \
+    else if ( *psz_tmp != '\0' ) { \
+        int i_list_size = ARRAY_SIZE(list); \
+        if( !SchroSetEnum( p_enc, i_list_size, list, pschro_name, psz_name_text, psz_tmp ) ) { \
+            free( psz_tmp ); \
+            goto error; \
+        } \
+    } \
+    free( psz_tmp );
 
 /*****************************************************************************
  * OpenEncoder: probe the encoder and return score
@@ -662,7 +1063,6 @@ static int OpenEncoder( vlc_object_t *p_this )
     encoder_sys_t *p_sys = p_enc->p_sys;
     int i_tmp;
     float f_tmp;
-    bool b_tmp;
     char *psz_tmp;
 
     if( p_enc->fmt_out.i_codec != VLC_CODEC_DIRAC &&
@@ -751,53 +1151,9 @@ static int OpenEncoder( vlc_object_t *p_this )
 
     config_ChainParse( p_enc, ENC_CFG_PREFIX, ppsz_enc_options, p_enc->p_cfg );
 
-    int i_numopts =  schro_encoder_get_n_settings();
-
-    for( int i = 0; i < i_numopts; ++i ) {
-        const SchroEncoderSetting *p_setting = schro_encoder_get_setting_info( i );
-        char *p_cfg_setting_name = malloc( strlen( ENC_CFG_PREFIX ) + strlen( p_setting->name ) + 1 );
-        if( unlikely( p_cfg_setting_name == NULL ) )
-            return VLC_ENOMEM;
+    SCHRO_SET_ENUM(enc_rate_control_list, ENC_RATE_CONTROL, ENC_RATE_CONTROL_TEXT, "rate_control")
 
-        strcpy( p_cfg_setting_name, ENC_CFG_PREFIX );
-        strcat( p_cfg_setting_name, p_setting->name );
-
-        switch( p_setting->type ) {
-            case SCHRO_ENCODER_SETTING_TYPE_BOOLEAN:
-                schro_encoder_setting_set_double ( p_sys->p_schro, p_setting->name, var_GetBool( p_enc, p_cfg_setting_name ) );
-                break;
-            case SCHRO_ENCODER_SETTING_TYPE_INT:
-                i_tmp = var_GetInteger( p_enc, p_cfg_setting_name );
-                schro_encoder_setting_set_double( p_sys->p_schro, p_setting->name, i_tmp );
-                /* A kludge to set bitrate to the value in sout-transcode-vb */
-                if( !strcmp( p_setting->name, "bitrate" ) ) {
-                    if( i_tmp == p_setting->default_value )
-                        schro_encoder_setting_set_double( p_sys->p_schro, p_setting->name, p_enc->fmt_out.i_bitrate );
-                       p_enc->fmt_out.i_bitrate = schro_encoder_setting_get_double( p_sys->p_schro, p_setting->name );
-                }
-                break;
-            case SCHRO_ENCODER_SETTING_TYPE_DOUBLE:
-                f_tmp = var_GetFloat( p_enc, p_cfg_setting_name );
-                if( f_tmp >= 0.0 )
-                    schro_encoder_setting_set_double( p_sys->p_schro, p_setting->name, f_tmp );
-                break;
-            case SCHRO_ENCODER_SETTING_TYPE_ENUM:
-                psz_tmp = var_GetString( p_enc, p_cfg_setting_name );
-                if( !psz_tmp )
-                    goto error;
-                else if( *psz_tmp != '\0' ) {
-                    if( !SchroSetEnum( p_enc, p_setting, psz_tmp ) ) {
-                        free( psz_tmp );
-                        goto error;
-                    }
-                }
-                free( psz_tmp );
-                break;
-            default:
-                break;
-        }
-        free( p_cfg_setting_name );
-    }
+    SCHRO_SET_ENUM(enc_gop_structure_list, ENC_GOP_STRUCTURE, ENC_GOP_STRUCTURE_TEXT, "gop_structure")
 
     psz_tmp = var_GetString( p_enc, ENC_CFG_PREFIX ENC_CHROMAFMT );
     if( !psz_tmp )
@@ -822,12 +1178,116 @@ static int OpenEncoder( vlc_object_t *p_this )
     }
     free( psz_tmp );
 
+    SCHRO_SET_FLOAT(ENC_QUALITY, "quality")
 
-    b_tmp = var_GetBool( p_enc, ENC_CFG_PREFIX ENC_CODINGMODE );
-    if( b_tmp == true )
-        p_sys->b_auto_field_coding = true;
+    SCHRO_SET_FLOAT(ENC_NOISE_THRESHOLD, "noise_threshold")
+
+    /* use bitrate from sout-transcode-vb in kbps */
+    i_tmp = var_GetInteger( p_enc, ENC_CFG_PREFIX ENC_BITRATE );
+    if( i_tmp > -1 )
+        schro_encoder_setting_set_double( p_sys->p_schro, "bitrate", i_tmp * 1000 );
     else
+        schro_encoder_setting_set_double( p_sys->p_schro, "bitrate", p_enc->fmt_out.i_bitrate );
+
+       p_enc->fmt_out.i_bitrate = schro_encoder_setting_get_double( p_sys->p_schro, "bitrate" );
+
+    i_tmp = var_GetInteger( p_enc, ENC_CFG_PREFIX ENC_MIN_BITRATE );
+    if( i_tmp > -1 )
+        schro_encoder_setting_set_double( p_sys->p_schro, "min_bitrate", i_tmp * 1000 );
+
+    i_tmp = var_GetInteger( p_enc, ENC_CFG_PREFIX ENC_MAX_BITRATE );
+    if( i_tmp > -1 )
+        schro_encoder_setting_set_double( p_sys->p_schro, "max_bitrate", i_tmp * 1000 );
+
+    SCHRO_SET_INTEGER(ENC_AU_DISTANCE, "au_distance", -1)
+
+    SCHRO_SET_ENUM(enc_filtering_list, ENC_PREFILTER, ENC_PREFILTER_TEXT, "filtering")
+
+    SCHRO_SET_FLOAT(ENC_PREFILTER_STRENGTH, "filter_value")
+
+
+    psz_tmp = var_GetString( p_enc, ENC_CFG_PREFIX ENC_CODINGMODE );
+    if( !psz_tmp )
+        goto error;
+    else if( !strcmp( psz_tmp, "auto" ) ) {
+        p_sys->b_auto_field_coding = true;
+    }
+    else if( !strcmp( psz_tmp, "progressive" ) ) {
+        p_sys->b_auto_field_coding = false;
+        schro_encoder_setting_set_double( p_sys->p_schro, "interlaced_coding", false);
+    }
+    else if( !strcmp( psz_tmp, "field" ) ) {
         p_sys->b_auto_field_coding = false;
+        schro_encoder_setting_set_double( p_sys->p_schro, "interlaced_coding", true);
+    }
+    else {
+        msg_Err( p_enc, "Invalid codingmode: %s", psz_tmp );
+        free( psz_tmp );
+        goto error;
+    }
+    free( psz_tmp );
+
+    SCHRO_SET_ENUM(enc_block_size_list, ENC_MCBLK_SIZE, ENC_MCBLK_SIZE_TEXT, "motion_block_size")
+
+    SCHRO_SET_ENUM(enc_block_overlap_list, ENC_MCBLK_OVERLAP, ENC_MCBLK_OVERLAP_TEXT, "motion_block_overlap")
+
+    psz_tmp = var_GetString( p_enc, ENC_CFG_PREFIX ENC_MVPREC );
+    if( !psz_tmp )
+        goto error;
+    else if( *psz_tmp != '\0') {
+        if( !strcmp( psz_tmp, "1" ) ) {
+            schro_encoder_setting_set_double( p_sys->p_schro, "mv_precision", 0 );
+        }
+        else if( !strcmp( psz_tmp, "1/2" ) ) {
+            schro_encoder_setting_set_double( p_sys->p_schro, "mv_precision", 1 );
+        }
+        else if( !strcmp( psz_tmp, "1/4" ) ) {
+            schro_encoder_setting_set_double( p_sys->p_schro, "mv_precision", 2 );
+        }
+        else if( !strcmp( psz_tmp, "1/8" ) ) {
+            schro_encoder_setting_set_double( p_sys->p_schro, "mv_precision", 3 );
+        }
+        else {
+            msg_Err( p_enc, "Invalid mv_precision: %s", psz_tmp );
+            free( psz_tmp );
+            goto error;
+        }
+    }
+    free( psz_tmp );
+
+    SCHRO_SET_INTEGER(ENC_ME_COMBINED, "enable_chroma_me", -1)
+
+    SCHRO_SET_ENUM(enc_wavelet_list, ENC_DWTINTRA, ENC_DWTINTRA_TEXT, "intra_wavelet")
+
+    SCHRO_SET_ENUM(enc_wavelet_list, ENC_DWTINTER, ENC_DWTINTER_TEXT, "inter_wavelet")
+
+    SCHRO_SET_INTEGER(ENC_DWTDEPTH, "transform_depth", -1)
+
+    SCHRO_SET_INTEGER(ENC_MULTIQUANT, "enable_multiquant", -1)
+
+    SCHRO_SET_INTEGER(ENC_NOAC, "enable_noarith", -1)
+
+    SCHRO_SET_ENUM(enc_perceptual_weighting_list, ENC_PWT, ENC_PWT_TEXT, "perceptual_weighting")
+
+    SCHRO_SET_FLOAT(ENC_PDIST, "perceptual_distance")
+
+    SCHRO_SET_INTEGER(ENC_HSLICES, "horiz_slices", -1)
+
+    SCHRO_SET_INTEGER(ENC_VSLICES, "vert_slices", -1)
+
+    SCHRO_SET_ENUM(enc_codeblock_size_list, ENC_SCBLK_SIZE, ENC_SCBLK_SIZE_TEXT, "codeblock_size")
+
+    SCHRO_SET_INTEGER(ENC_ME_HIERARCHICAL, "enable_hierarchical_estimation", -1)
+
+    SCHRO_SET_INTEGER(ENC_ME_DOWNSAMPLE_LEVELS, "downsample_levels", 1)
+
+    SCHRO_SET_INTEGER(ENC_ME_GLOBAL_MOTION, "enable_global_motion", -1)
+
+    SCHRO_SET_INTEGER(ENC_ME_PHASECORR, "enable_phasecorr_estimation", -1)
+
+    SCHRO_SET_INTEGER(ENC_SCD, "enable_scene_change_detection", -1)
+
+    SCHRO_SET_ENUM(enc_profile_list, ENC_FORCE_PROFILE, ENC_FORCE_PROFILE_TEXT, "force_profile")
 
     p_sys->started = 0;