[vlc-devel] [PATCH 01/14] Enable secondary SPU ES and selection from the GUI

Roland Bewick roland.bewick at gmail.com
Sat May 11 08:37:58 CEST 2019


On 11/05/2019 1:32 PM, Roland Bewick wrote:

> ---
>   include/vlc_player.h                 | 13 ++++++++++
>   modules/gui/qt/util/input_models.cpp |  6 +++++
>   src/input/es_out.c                   | 47 ++++++++++++++++++++++++++++++++++--
>   src/input/es_out.h                   |  5 +++-
>   src/input/input.c                    |  5 ++++
>   src/input/input_internal.h           |  1 +
>   src/input/player.c                   | 11 +++++++++
>   src/libvlccore.sym                   |  1 +
>   8 files changed, 86 insertions(+), 3 deletions(-)
>
> diff --git a/include/vlc_player.h b/include/vlc_player.h
> index 1aa5f8e687..077b3883ad 100644
> --- a/include/vlc_player.h
> +++ b/include/vlc_player.h
> @@ -2428,6 +2428,19 @@ VLC_API unsigned
>   vlc_player_GetSubtitleTextScale(vlc_player_t *player);
>   
>   /**
> + * Allow secondary subtitle track(s) to be selected when
> + * the primary subtitle track is already selected.
> + *
> + * @note This must be returned to false immediately after
> + * selection of the subtitle.
> + *
> + * @param player locked player instance
> + * @param select true to allow selection of multiple subtitles
> + */
> +VLC_API void
> +vlc_player_SetSubtitleMultipleSelection(vlc_player_t *player, bool multiple);
> +
> +/**
>    * Get the signal quality and strength of the current media
>    *
>    * @param player locked player instance
> diff --git a/modules/gui/qt/util/input_models.cpp b/modules/gui/qt/util/input_models.cpp
> index e381fbb917..34fefa3960 100644
> --- a/modules/gui/qt/util/input_models.cpp
> +++ b/modules/gui/qt/util/input_models.cpp
> @@ -62,7 +62,13 @@ bool TrackListModel::setData(const QModelIndex &index, const QVariant &value, in
>       vlc_player_locker lock{ m_player };
>   
>       if (select)
> +    {
> +        /* Only allow secondary subtitles to be manually selected
> +        by the user through the GUI. */
> +        vlc_player_SetSubtitleMultipleSelection(m_player, true);
>           vlc_player_SelectTrack(m_player, m_data[row].m_id.get());
> +        vlc_player_SetSubtitleMultipleSelection(m_player, false);
> +    }
>       else
>           vlc_player_UnselectTrack(m_player, m_data[row].m_id.get());
>       return true;
> diff --git a/src/input/es_out.c b/src/input/es_out.c
> index 2026fb8c22..54245aed4e 100644
> --- a/src/input/es_out.c
> +++ b/src/input/es_out.c
> @@ -209,6 +209,9 @@ typedef struct
>       /* Used only to limit debugging output */
>       int         i_prev_stream_level;
>   
> +    /* Used to temporarily allow subtitle selection of multiple sub tracks */
> +    bool        b_multiple_subtitle_selection;
> +
>       es_out_t out;
>   } es_out_sys_t;
>   
> @@ -2037,6 +2040,24 @@ static void EsOutUnselectEs( es_out_t *out, es_out_id_t *es, bool b_update )
>   }
>   
>   /**
> + * Count the number of selected ES of the given category
> + * \param i_cat the ES category (e.g. SPU_ES)
> + * \return count
> + */
> +static int EsOutCountSelected( es_out_sys_t *p_sys,
> +                               enum es_format_category_e i_cat )
> +{
> +    int i_selected_count = 0;
> +    es_out_id_t *other;
> +    foreach_es_then_es_slaves(other)
> +        if( other->fmt.i_cat == i_cat && EsIsSelected( other ) )
> +        {
> +            ++i_selected_count;
> +        }
> +    return i_selected_count;
> +}
> +
> +/**
>    * Select an ES given the current mode
>    * XXX: you need to take a the lock before (stream.stream_lock)
>    *
> @@ -2056,9 +2077,24 @@ static void EsOutSelect( es_out_t *out, es_out_id_t *es, bool b_force )
>           return;
>       }
>   
> +    /* Select secondary if the user has already selected a primary sub track */
> +    bool b_select_secondary_subtitle = es->fmt.i_cat == SPU_ES &&
> +                               p_sys->b_multiple_subtitle_selection &&
> +                               p_esprops->p_main_es != NULL &&
> +                               EsIsSelected(p_esprops->p_main_es);
> +
> +    if ( b_select_secondary_subtitle &&
> +         EsOutCountSelected( p_sys, es->fmt.i_cat ) > 1 )
> +    {
> +        /* Don't allow more than one secondary SPU ES selected at a time. */
> +        EsOutSendEsEvent(out, es, VLC_INPUT_ES_UNSELECTED);
> +        return;
> +    }
> +
>       bool b_auto_unselect = p_esprops && p_sys->i_mode == ES_OUT_MODE_AUTO &&
>                              p_esprops->e_policy == ES_OUT_ES_POLICY_EXCLUSIVE &&
> -                           p_esprops->p_main_es && p_esprops->p_main_es != es;
> +                           p_esprops->p_main_es && p_esprops->p_main_es != es &&
> +                           !b_select_secondary_subtitle;
>   
>       if( p_sys->i_mode == ES_OUT_MODE_ALL || b_force )
>       {
> @@ -2178,7 +2214,8 @@ static void EsOutSelect( es_out_t *out, es_out_id_t *es, bool b_force )
>       }
>   
>       /* FIXME TODO handle priority here */
> -    if( p_esprops && p_sys->i_mode == ES_OUT_MODE_AUTO && EsIsSelected( es ) )
> +    if( p_esprops && p_sys->i_mode == ES_OUT_MODE_AUTO && EsIsSelected( es ) &&
> +        !b_select_secondary_subtitle )
>           p_esprops->p_main_es = es;
>   }
>   
> @@ -3187,6 +3224,12 @@ static int EsOutVaControlLocked( es_out_t *out, int i_query, va_list args )
>           }
>           return ret;
>       }
> +    case ES_OUT_SET_MULTIPLE_SUBTITLE_SELECTION:
> +    {
> +        es_out_sys_t *p_sys = container_of(out, es_out_sys_t, out);
> +        p_sys->b_multiple_subtitle_selection = va_arg( args, int );
> +        return VLC_SUCCESS;
> +    }
>       default:
>           msg_Err( p_sys->p_input, "unknown query 0x%x in %s", i_query,
>                    __func__  );
> diff --git a/src/input/es_out.h b/src/input/es_out.h
> index 7cbea71728..3f37d73b68 100644
> --- a/src/input/es_out.h
> +++ b/src/input/es_out.h
> @@ -89,7 +89,10 @@ enum es_out_query_private_e
>       ES_OUT_SET_VBI_PAGE,                            /* arg1=unsigned res=can fail */
>   
>       /* Set VBI/Teletext menu transparent */
> -    ES_OUT_SET_VBI_TRANSPARENCY                     /* arg1=bool res=can fail */
> +    ES_OUT_SET_VBI_TRANSPARENCY,                    /* arg1=bool res=can fail */
> +
> +    /* Allow selection of a secondary SPU ES if primary is already selected */
> +    ES_OUT_SET_MULTIPLE_SUBTITLE_SELECTION,         /* arg1=bool res=cannot fail */
>   };
>   
>   static inline void es_out_SetMode( es_out_t *p_out, int i_mode )
> diff --git a/src/input/input.c b/src/input/input.c
> index 381b85a9fd..821a18ff2c 100644
> --- a/src/input/input.c
> +++ b/src/input/input.c
> @@ -2396,6 +2396,11 @@ static bool Control( input_thread_t *p_input,
>                               param.vbi_transparency.id,
>                               param.vbi_transparency.enabled );
>               break;
> +        case INPUT_CONTROL_SET_MULTIPLE_SUBTITLE_SELECTION:
> +             es_out_Control( priv->p_es_out_display,
> +                             ES_OUT_SET_MULTIPLE_SUBTITLE_SELECTION,
> +                             param.val.b_bool );
> +             break;
>   
>           case INPUT_CONTROL_NAV_ACTIVATE:
>           case INPUT_CONTROL_NAV_UP:
> diff --git a/src/input/input_internal.h b/src/input/input_internal.h
> index 18495881c2..914cebe7d4 100644
> --- a/src/input/input_internal.h
> +++ b/src/input/input_internal.h
> @@ -268,6 +268,7 @@ enum input_control_e
>   
>       INPUT_CONTROL_SET_VBI_PAGE,
>       INPUT_CONTROL_SET_VBI_TRANSPARENCY,
> +    INPUT_CONTROL_SET_MULTIPLE_SUBTITLE_SELECTION,
>   };
>   
>   /* Internal helpers */
> diff --git a/src/input/player.c b/src/input/player.c
> index da02375a66..843f86000c 100644
> --- a/src/input/player.c
> +++ b/src/input/player.c
> @@ -2888,6 +2888,17 @@ vlc_player_SetSubtitleSync(vlc_player_t *player,
>       }
>   }
>   
> +void
> +vlc_player_SetSubtitleMultipleSelection(vlc_player_t *player, bool multiple)
> +{
> +    struct vlc_player_input *input = vlc_player_get_input_locked(player);
> +    if (!input)
> +        return;
> +    input_ControlPushHelper(input->thread,
> +                            INPUT_CONTROL_SET_MULTIPLE_SUBTITLE_SELECTION,
> +                            &(vlc_value_t){ .b_bool = multiple });
> +}
> +
>   vlc_tick_t
>   vlc_player_GetSubtitleDelay(vlc_player_t *player)
>   {
> diff --git a/src/libvlccore.sym b/src/libvlccore.sym
> index 1cbbfe72f6..d0070d42b8 100644
> --- a/src/libvlccore.sym
> +++ b/src/libvlccore.sym
> @@ -868,6 +868,7 @@ vlc_player_SetStartPaused
>   vlc_player_SetSubtitleDelay
>   vlc_player_SetSubtitleSync
>   vlc_player_SetSubtitleTextScale
> +vlc_player_SetSubtitleMultipleSelection
>   vlc_player_SetTeletextEnabled
>   vlc_player_SetTeletextTransparency
>   vlc_player_SetTrackCategoryEnabled

Hello again,

This updated patch set focuses on the possibility of supporting N 
selected subtitle tracks in the future rather than just two.

Other improvements:
- Toggle dual subtitles in the dropdown subtitle menu rather than going 
into the config
- Secondary subtitle control hotkey will automatically enable dual subtitles
- Subtitle message OSD now has text for secondary subtitles
- Subtitle promotion: Deselect the primary subtitle will promote the 
secondary subtitle to primary
- Fixed OSD text not showing once a SPU clock has been added

Roland



More information about the vlc-devel mailing list