+
+/* Get a 2 char code */
+static char *LanguageGetCode( const char *psz_lang )
+{
+ const iso639_lang_t *pl;
+
+ if( psz_lang == NULL || *psz_lang == '\0' )
+ return strdup("??");
+
+ for( pl = p_languages; pl->psz_iso639_1 != NULL; pl++ )
+ {
+ if( !strcasecmp( pl->psz_eng_name, psz_lang ) ||
+ !strcasecmp( pl->psz_native_name, psz_lang ) ||
+ !strcasecmp( pl->psz_iso639_1, psz_lang ) ||
+ !strcasecmp( pl->psz_iso639_2T, psz_lang ) ||
+ !strcasecmp( pl->psz_iso639_2B, psz_lang ) )
+ break;
+ }
+
+ if( pl->psz_iso639_1 != NULL )
+ return strdup( pl->psz_iso639_1 );
+
+ return strdup("??");
+}
+
+static char **LanguageSplit( const char *psz_langs )
+{
+ char *psz_dup;
+ char *psz_parser;
+ char **ppsz = NULL;
+ int i_psz = 0;
+
+ if( psz_langs == NULL ) return NULL;
+
+ psz_parser = psz_dup = strdup(psz_langs);
+
+ while( psz_parser && *psz_parser )
+ {
+ char *psz;
+ char *psz_code;
+
+ psz = strchr(psz_parser, ',' );
+ if( psz ) *psz++ = '\0';
+
+ psz_code = LanguageGetCode( psz_parser );
+ if( strcmp( psz_code, "??" ) )
+ {
+ TAB_APPEND( i_psz, ppsz, psz_code );
+ }
+
+ psz_parser = psz;
+ }
+
+ if( i_psz )
+ {
+ TAB_APPEND( i_psz, ppsz, NULL );
+ }
+
+ free( psz_dup );
+ return ppsz;
+}
+
+static int LanguageArrayIndex( char **ppsz_langs, char *psz_lang )
+{
+ int i;
+
+ if( !ppsz_langs || !psz_lang ) return -1;
+
+ for( i = 0; ppsz_langs[i]; i++ )
+ if( !strcasecmp( ppsz_langs[i], psz_lang ) ) return i;
+
+ return -1;
+}
+
+/****************************************************************************
+ * EsOutAddInfo:
+ * - add meta info to the playlist item
+ ****************************************************************************/
+static void EsOutAddInfo( es_out_t *out, es_out_id_t *es )
+{
+ es_out_sys_t *p_sys = out->p_sys;
+ input_thread_t *p_input = p_sys->p_input;
+ es_format_t *fmt = &es->fmt;
+ char *psz_cat;
+ lldiv_t div;
+
+ /* Add stream info */
+ asprintf( &psz_cat, _("Stream %d"), out->p_sys->i_id - 1 );
+
+ input_Control( p_input, INPUT_ADD_INFO, psz_cat, _("Codec"),
+ "%.4s", (char*)&fmt->i_codec );
+
+ input_Control( p_input, INPUT_ADD_INFO, psz_cat, _("Language"),
+ "%s", es->psz_language );
+
+ /* Add information */
+ switch( fmt->i_cat )
+ {
+ case AUDIO_ES:
+ input_Control( p_input, INPUT_ADD_INFO, psz_cat,
+ _("Type"), _("Audio") );
+
+ if( fmt->audio.i_channels > 0 )
+ input_Control( p_input, INPUT_ADD_INFO, psz_cat, _("Channels"),
+ "%u", fmt->audio.i_channels );
+
+ if( fmt->audio.i_rate > 0 )
+ {
+ input_Control( p_input, INPUT_ADD_INFO, psz_cat, _("Sample rate"),
+ _("%u Hz"), fmt->audio.i_rate );
+ var_SetInteger( p_input, "sample-rate", fmt->audio.i_rate );
+ }
+
+ if( fmt->audio.i_bitspersample > 0 )
+ input_Control( p_input, INPUT_ADD_INFO, psz_cat,
+ _("Bits per sample"), "%u",
+ fmt->audio.i_bitspersample );
+
+ if( fmt->i_bitrate > 0 )
+ {
+ input_Control( p_input, INPUT_ADD_INFO, psz_cat, _("Bitrate"),
+ _("%u kb/s"), fmt->i_bitrate / 1000 );
+ var_SetInteger( p_input, "bit-rate", fmt->i_bitrate );
+ }
+ break;
+
+ case VIDEO_ES:
+ input_Control( p_input, INPUT_ADD_INFO, psz_cat,
+ _("Type"), _("Video") );
+
+ if( fmt->video.i_width > 0 && fmt->video.i_height > 0 )
+ input_Control( p_input, INPUT_ADD_INFO, psz_cat,
+ _("Resolution"), "%ux%u",
+ fmt->video.i_width, fmt->video.i_height );
+
+ if( fmt->video.i_visible_width > 0 &&
+ fmt->video.i_visible_height > 0 )
+ input_Control( p_input, INPUT_ADD_INFO, psz_cat,
+ _("Display resolution"), "%ux%u",
+ fmt->video.i_visible_width,
+ fmt->video.i_visible_height);
+ if( fmt->video.i_frame_rate > 0 &&
+ fmt->video.i_frame_rate_base > 0 )
+ {
+ div = lldiv( (float)fmt->video.i_frame_rate /
+ fmt->video.i_frame_rate_base * 1000000,
+ 1000000 );
+ input_Control( p_input, INPUT_ADD_INFO, psz_cat,
+ _("Frame rate"), I64Fd".%06u",
+ div.quot, (unsigned int )div.rem );
+ }
+ break;
+
+ case SPU_ES:
+ input_Control( p_input, INPUT_ADD_INFO, psz_cat,
+ _("Type"), _("Subtitle") );
+ break;
+
+ default:
+ break;
+ }
+
+ free( psz_cat );
+}