mirror of
https://github.com/mpv-player/mpv.git
synced 2025-12-28 05:33:14 +00:00
dvdnav: make MP_NAV_EVENT_RESET_ALL handled properly
dvdnav.c did not handle event in regular sequence. Usually this does not make any trouble except around MP_NAV_EVENT_RESET_ALL. Those events should be handled in regular sequence. If they're mixed, it can make wrong result. For instance, MP_NAV_EVENT_HIGHLIGHT right after MP_NAV_EVENT_RESET_ALL should not be ignored but it might be because MP_NAV_EVENT_RESET_ALL makes the demuxer reloaded and osd hidden.
This commit is contained in:
@@ -145,7 +145,9 @@ void mp_handle_nav(struct MPContext *mpctx)
|
|||||||
case MP_NAV_EVENT_RESET_ALL: {
|
case MP_NAV_EVENT_RESET_ALL: {
|
||||||
mpctx->stop_play = PT_RELOAD_DEMUXER;
|
mpctx->stop_play = PT_RELOAD_DEMUXER;
|
||||||
MP_VERBOSE(nav, "reload\n");
|
MP_VERBOSE(nav, "reload\n");
|
||||||
break;
|
// return immediately.
|
||||||
|
// other events should be handled after reloaded.
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
case MP_NAV_EVENT_RESET: {
|
case MP_NAV_EVENT_RESET: {
|
||||||
nav->nav_still_frame = 0;
|
nav->nav_still_frame = 0;
|
||||||
|
|||||||
@@ -305,42 +305,47 @@ static void handle_cmd(stream_t *s, struct mp_nav_cmd *ev)
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static inline bool set_event_type(struct priv *priv, int type,
|
||||||
|
struct mp_nav_event *event)
|
||||||
|
{
|
||||||
|
if (!(priv->next_event & (1 << type)))
|
||||||
|
return false;
|
||||||
|
priv->next_event &= ~(1 << type);
|
||||||
|
event->event = type;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
static void fill_next_event(stream_t *s, struct mp_nav_event **ret)
|
static void fill_next_event(stream_t *s, struct mp_nav_event **ret)
|
||||||
{
|
{
|
||||||
struct priv *priv = s->priv;
|
struct priv *priv = s->priv;
|
||||||
struct mp_nav_event e = {0};
|
struct mp_nav_event e = {0};
|
||||||
for (int n = 0; n < 30; n++) {
|
if (!set_event_type(priv, MP_NAV_EVENT_RESET_ALL, &e))
|
||||||
if (priv->next_event & (1 << n)) {
|
for (int n = 0; n < 30 && !set_event_type(priv, n, &e); n++) ;
|
||||||
priv->next_event &= ~(1 << n);
|
switch (e.event) {
|
||||||
e.event = n;
|
case MP_NAV_EVENT_NONE:
|
||||||
switch (e.event) {
|
return;
|
||||||
case MP_NAV_EVENT_HIGHLIGHT: {
|
case MP_NAV_EVENT_HIGHLIGHT: {
|
||||||
dvdnav_highlight_event_t hlev = priv->hlev;
|
dvdnav_highlight_event_t hlev = priv->hlev;
|
||||||
e.u.highlight.display = hlev.display;
|
e.u.highlight.display = hlev.display;
|
||||||
e.u.highlight.sx = hlev.sx;
|
e.u.highlight.sx = hlev.sx;
|
||||||
e.u.highlight.sy = hlev.sy;
|
e.u.highlight.sy = hlev.sy;
|
||||||
e.u.highlight.ex = hlev.ex;
|
e.u.highlight.ex = hlev.ex;
|
||||||
e.u.highlight.ey = hlev.ey;
|
e.u.highlight.ey = hlev.ey;
|
||||||
e.u.highlight.palette = hlev.palette;
|
e.u.highlight.palette = hlev.palette;
|
||||||
break;
|
break;
|
||||||
}
|
|
||||||
case MP_NAV_EVENT_MENU_MODE:
|
|
||||||
e.u.menu_mode.enable = !dvdnav_is_domain_vts(priv->dvdnav);
|
|
||||||
break;
|
|
||||||
case MP_NAV_EVENT_STILL_FRAME:
|
|
||||||
e.u.still_frame.seconds = priv->still_length;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
if (e.event) {
|
case MP_NAV_EVENT_MENU_MODE:
|
||||||
*ret = talloc(NULL, struct mp_nav_event);
|
e.u.menu_mode.enable = !dvdnav_is_domain_vts(priv->dvdnav);
|
||||||
**ret = e;
|
break;
|
||||||
|
case MP_NAV_EVENT_STILL_FRAME:
|
||||||
|
e.u.still_frame.seconds = priv->still_length;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
*ret = talloc(NULL, struct mp_nav_event);
|
||||||
|
**ret = e;
|
||||||
|
|
||||||
MP_VERBOSE(s, "DVDNAV: player event '%s'\n",
|
MP_VERBOSE(s, "DVDNAV: player event '%s'\n",
|
||||||
LOOKUP_NAME(mp_nav_event_types, e.event));
|
LOOKUP_NAME(mp_nav_event_types, e.event));
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static int fill_buffer(stream_t *s, char *buf, int max_len)
|
static int fill_buffer(stream_t *s, char *buf, int max_len)
|
||||||
@@ -421,6 +426,8 @@ static int fill_buffer(stream_t *s, char *buf, int max_len)
|
|||||||
priv->had_initial_vts = true;
|
priv->had_initial_vts = true;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
// clear all previous events
|
||||||
|
priv->next_event = 0;
|
||||||
priv->next_event |= 1 << MP_NAV_EVENT_RESET;
|
priv->next_event |= 1 << MP_NAV_EVENT_RESET;
|
||||||
priv->next_event |= 1 << MP_NAV_EVENT_RESET_ALL;
|
priv->next_event |= 1 << MP_NAV_EVENT_RESET_ALL;
|
||||||
if (dvdnav_current_title_info(dvdnav, &tit, &part) == DVDNAV_STATUS_OK)
|
if (dvdnav_current_title_info(dvdnav, &tit, &part) == DVDNAV_STATUS_OK)
|
||||||
|
|||||||
Reference in New Issue
Block a user