static int control(stream_t *stream, int cmd, void* arg) { dvdnav_priv_t* priv=stream->priv; int tit, part; switch(cmd) { case STREAM_CTRL_SEEK_TO_CHAPTER: { int chap = *(unsigned int *)arg+1; if(chap < 1 || dvdnav_current_title_info(priv->dvdnav, &tit, &part) != DVDNAV_STATUS_OK) break; if(dvdnav_part_play(priv->dvdnav, tit, chap) != DVDNAV_STATUS_OK) break; return 1; } case STREAM_CTRL_GET_NUM_CHAPTERS: { if(dvdnav_current_title_info(priv->dvdnav, &tit, &part) != DVDNAV_STATUS_OK) break; if(dvdnav_get_number_of_parts(priv->dvdnav, tit, &part) != DVDNAV_STATUS_OK) break; if(!part) break; *(unsigned int *)arg = part; return 1; } case STREAM_CTRL_GET_CURRENT_CHAPTER: { if(dvdnav_current_title_info(priv->dvdnav, &tit, &part) != DVDNAV_STATUS_OK) break; *(unsigned int *)arg = part - 1; return 1; } case STREAM_CTRL_GET_TIME_LENGTH: { if(priv->duration || priv->still_length) { *(double *)arg = (double)priv->duration / 1000.0; return 1; } break; } case STREAM_CTRL_GET_ASPECT_RATIO: { uint8_t ar = dvdnav_get_video_aspect(priv->dvdnav); *(double *)arg = !ar ? 4.0/3.0 : 16.0/9.0; return 1; } case STREAM_CTRL_GET_CURRENT_TIME: { double tm; tm = dvdnav_get_current_time(priv->dvdnav)/90000.0f; if(tm != -1) { *(double *)arg = tm; return 1; } break; } case STREAM_CTRL_SEEK_TO_TIME: { uint64_t tm = *(double *)arg * 90000; if(dvdnav_time_search(priv->dvdnav, tm) == DVDNAV_STATUS_OK) return 1; break; } case STREAM_CTRL_GET_NUM_ANGLES: { uint32_t curr, angles; if(dvdnav_get_angle_info(priv->dvdnav, &curr, &angles) != DVDNAV_STATUS_OK) break; *(int *)arg = angles; return 1; } case STREAM_CTRL_GET_ANGLE: { uint32_t curr, angles; if(dvdnav_get_angle_info(priv->dvdnav, &curr, &angles) != DVDNAV_STATUS_OK) break; *(int *)arg = curr; return 1; } case STREAM_CTRL_SET_ANGLE: { uint32_t curr, angles; int new_angle = *(int *)arg; if(dvdnav_get_angle_info(priv->dvdnav, &curr, &angles) != DVDNAV_STATUS_OK) break; if(new_angle>angles || new_angle<1) break; if(dvdnav_angle_change(priv->dvdnav, new_angle) != DVDNAV_STATUS_OK) return 1; } case STREAM_CTRL_GET_LANG: { struct stream_lang_req *req = arg; int lang = 0; switch(req->type) { case stream_ctrl_audio: lang = mp_dvdnav_lang_from_aid(stream, req->id); break; case stream_ctrl_sub: lang = mp_dvdnav_lang_from_sid(stream, req->id); break; } if (!lang) break; req->buf[0] = lang >> 8; req->buf[1] = lang; req->buf[2] = 0; return STREAM_OK; } } return STREAM_UNSUPPORTED; }
static int control(stream_t *stream, int cmd, void* arg) { dvdnav_priv_t* priv=stream->priv; int tit, part; switch(cmd) { case STREAM_CTRL_SEEK_TO_CHAPTER: { int chap = *((unsigned int *)arg)+1; if(chap < 1 || dvdnav_current_title_info(priv->dvdnav, &tit, &part) != DVDNAV_STATUS_OK) break; if(dvdnav_part_play(priv->dvdnav, tit, chap) != DVDNAV_STATUS_OK) break; return 1; } case STREAM_CTRL_GET_NUM_CHAPTERS: { if(dvdnav_current_title_info(priv->dvdnav, &tit, &part) != DVDNAV_STATUS_OK) break; if(dvdnav_get_number_of_parts(priv->dvdnav, tit, &part) != DVDNAV_STATUS_OK) break; if(!part) break; *((unsigned int *)arg) = part; return 1; } case STREAM_CTRL_GET_CURRENT_CHAPTER: { if(dvdnav_current_title_info(priv->dvdnav, &tit, &part) != DVDNAV_STATUS_OK) break; *((unsigned int *)arg) = part - 1; return 1; } case STREAM_CTRL_GET_TIME_LENGTH: { if(priv->duration) { *((double *)arg) = (double)priv->duration / 1000.0; return 1; } break; } case STREAM_CTRL_GET_ASPECT_RATIO: { uint8_t ar = dvdnav_get_video_aspect(priv->dvdnav); *((double *)arg) = !ar ? 4.0/3.0 : 16.0/9.0; return 1; } case STREAM_CTRL_GET_CURRENT_TIME: { double tm; tm = dvdnav_get_current_time(priv->dvdnav)/90000.0f; if(tm != -1) { *((double *)arg) = tm; return 1; } break; } case STREAM_CTRL_SEEK_TO_TIME: { uint64_t tm = (uint64_t) (*((double*)arg) * 90000); if(dvdnav_time_search(priv->dvdnav, tm) == DVDNAV_STATUS_OK) return 1; break; } } return STREAM_UNSUPPORTED; }