示例#1
0
void media_input::open(const std::vector<std::string> &urls, const device_request &dev_request)
{
    assert(urls.size() > 0);

    // Open media objects
    _is_device = dev_request.is_device();
    _media_objects.resize(urls.size());
    for (size_t i = 0; i < urls.size(); i++)
    {
        _media_objects[i].open(urls[i], dev_request);
    }

    // Construct id for this input
    _id = basename(_media_objects[0].url());
    for (size_t i = 1; i < _media_objects.size(); i++)
    {
        _id += '/';
        _id += basename(_media_objects[i].url());
    }

    // Gather metadata
    for (size_t i = 0; i < _media_objects.size(); i++)
    {
        // Note that we may have multiple identical tag names in our metadata
        for (size_t j = 0; j < _media_objects[i].tags(); j++)
        {
            _tag_names.push_back(_media_objects[i].tag_name(j));
            _tag_values.push_back(_media_objects[i].tag_value(j));
        }
    }

    // Gather streams and stream names
    for (size_t i = 0; i < _media_objects.size(); i++)
    {
        for (int j = 0; j < _media_objects[i].video_streams(); j++)
        {
            _video_stream_names.push_back(_media_objects[i].video_frame_template(j).format_info());
        }
    }
    if (_video_stream_names.size() > 1)
    {
        for (size_t i = 0; i < _video_stream_names.size(); i++)
        {
            _video_stream_names[i].insert(0,
                    std::string(1, '#') + str::from(i + 1) + '/'
                    + str::from(_video_stream_names.size()) + ": ");
        }
    }
    for (size_t i = 0; i < _media_objects.size(); i++)
    {
        for (int j = 0; j < _media_objects[i].audio_streams(); j++)
        {
            _audio_stream_names.push_back(_media_objects[i].audio_blob_template(j).format_info());
        }
    }
    if (_audio_stream_names.size() > 1)
    {
        for (size_t i = 0; i < _audio_stream_names.size(); i++)
        {
            _audio_stream_names[i].insert(0,
                    std::string(1, '#') + str::from(i + 1) + '/'
                    + str::from(_audio_stream_names.size()) + ": ");
        }
    }
    for (size_t i = 0; i < _media_objects.size(); i++)
    {
        for (int j = 0; j < _media_objects[i].subtitle_streams(); j++)
        {
            _subtitle_stream_names.push_back(_media_objects[i].subtitle_box_template(j).format_info());
        }
    }
    if (_subtitle_stream_names.size() > 1)
    {
        for (size_t i = 0; i < _subtitle_stream_names.size(); i++)
        {
            _subtitle_stream_names[i].insert(0,
                    std::string(1, '#') + str::from(i + 1) + '/'
                    + str::from(_subtitle_stream_names.size()) + ": ");
        }
    }

    // Set duration information
    _duration = std::numeric_limits<int64_t>::max();
    for (size_t i = 0; i < _media_objects.size(); i++)
    {
        for (int j = 0; j < _media_objects[i].video_streams(); j++)
        {
            int64_t d = _media_objects[i].video_duration(j);
            if (d < _duration)
            {
                _duration = d;
            }
        }
        for (int j = 0; j < _media_objects[i].audio_streams(); j++)
        {
            int64_t d = _media_objects[i].audio_duration(j);
            if (d < _duration)
            {
                _duration = d;
            }
        }
        // Ignore subtitle stream duration; it seems unreliable and is not important anyway.
    }

    // Skip advertisement in 3dtv.at movies. Only works for single media objects.
    try { _initial_skip = str::to<int64_t>(tag_value("StereoscopicSkip")); } catch (...) { }

    // Find stereo layout and set active video stream(s)
    _supports_stereo_layout_separate = false;
    if (video_streams() == 2)
    {
        int o0, o1, v0, v1;
        get_video_stream(0, o0, v0);
        get_video_stream(1, o1, v1);
        video_frame t0 = _media_objects[o0].video_frame_template(v0);
        video_frame t1 = _media_objects[o1].video_frame_template(v1);
        if (t0.width == t1.width
                && t0.height == t1.height
                && (t0.aspect_ratio <= t1.aspect_ratio && t0.aspect_ratio >= t1.aspect_ratio)
                && t0.layout == t1.layout
                && t0.color_space == t1.color_space
                && t0.value_range == t1.value_range
                && t0.chroma_location == t1.chroma_location)
        {
            _supports_stereo_layout_separate = true;
        }
    }
    if (_supports_stereo_layout_separate)
    {
        _active_video_stream = 0;
        int o, s;
        get_video_stream(_active_video_stream, o, s);
        _video_frame = _media_objects[o].video_frame_template(s);
        _video_frame.stereo_layout = parameters::layout_separate;
    }
    else if (video_streams() > 0)
    {
        _active_video_stream = 0;
        int o, s;
        get_video_stream(_active_video_stream, o, s);
        _video_frame = _media_objects[o].video_frame_template(s);
    }
    else
    {
        _active_video_stream = -1;
    }
    if (_active_video_stream >= 0)
    {
        select_video_stream(_active_video_stream);
    }

    // Set active audio stream
    _active_audio_stream = (audio_streams() > 0 ? 0 : -1);
    if (_active_audio_stream >= 0)
    {
        int o, s;
        get_audio_stream(_active_audio_stream, o, s);
        _audio_blob = _media_objects[o].audio_blob_template(s);
        select_audio_stream(_active_audio_stream);
    }

    // Set active subtitle stream
    _active_subtitle_stream = -1;       // no subtitles by default

    // Print summary
    msg::inf(_("Input:"));
    for (int i = 0; i < video_streams(); i++)
    {
        int o, s;
        get_video_stream(i, o, s);
        msg::inf(4, _("Video %s: %s"), video_stream_name(i).c_str(),
                _media_objects[o].video_frame_template(s).format_name().c_str());
    }
    if (video_streams() == 0)
    {
        msg::inf(4, _("No video."));
    }
    for (int i = 0; i < audio_streams(); i++)
    {
        int o, s;
        get_audio_stream(i, o, s);
        msg::inf(4, _("Audio %s: %s"), audio_stream_name(i).c_str(),
                _media_objects[o].audio_blob_template(s).format_name().c_str());
    }
    if (audio_streams() == 0)
    {
        msg::inf(4, _("No audio."));
    }
    for (int i = 0; i < subtitle_streams(); i++)
    {
        int o, s;
        get_subtitle_stream(i, o, s);
        msg::inf(4, _("Subtitle %s: %s"), subtitle_stream_name(i).c_str(),
                _media_objects[o].subtitle_box_template(s).format_name().c_str());
    }
    if (subtitle_streams() == 0)
    {
        msg::inf(4, _("No subtitle."));
    }
    msg::inf(4, _("Duration: %g seconds"), duration() / 1e6f);
    if (video_streams() > 0)
    {
        msg::inf(4, _("Stereo layout: %s"), parameters::stereo_layout_to_string(
                    video_frame_template().stereo_layout, video_frame_template().stereo_layout_swap).c_str());
    }
}
示例#2
0
void media_input::open(const std::vector<std::string> &urls)
{
    assert(urls.size() > 0);

    // Open media objects
    _media_objects.resize(urls.size());
    for (size_t i = 0; i < urls.size(); i++)
    {
        _media_objects[i].open(urls[i]);
    }

    // Construct id for this input
    _id = basename(_media_objects[0].url());
    for (size_t i = 1; i < _media_objects.size(); i++)
    {
        _id += '/';
        _id += basename(_media_objects[i].url());
    }

    // Gather metadata
    for (size_t i = 0; i < _media_objects.size(); i++)
    {
        std::string pfx = (_media_objects.size() == 1 ? "" : str::from(i + 1) + " - ");
        for (size_t j = 0; j < _media_objects[i].tags(); j++)
        {
            _tag_names.push_back(pfx + _media_objects[i].tag_name(j));
            _tag_values.push_back(pfx + _media_objects[i].tag_value(j));
        }
    }

    // Gather streams and stream names
    for (size_t i = 0; i < _media_objects.size(); i++)
    {
        std::string pfx = (_media_objects.size() == 1 ? "" : str::from(i + 1) + " - ");
        for (int j = 0; j < _media_objects[i].video_streams(); j++)
        {
            std::string pfx2 = (_media_objects[i].video_streams() == 1 ? "" : str::from(j + 1) + " - ");
            _video_stream_names.push_back(pfx + pfx2
                    + _media_objects[i].video_frame_template(j).format_info());
        }
    }
    for (size_t i = 0; i < _media_objects.size(); i++)
    {
        std::string pfx = (_media_objects.size() == 1 ? "" : str::from(i + 1) + " - ");
        for (int j = 0; j < _media_objects[i].audio_streams(); j++)
        {
            std::string pfx2 = (_media_objects[i].audio_streams() == 1 ? "" : str::from(j + 1) + " - ");
            _audio_stream_names.push_back(pfx + pfx2
                    + _media_objects[i].audio_blob_template(j).format_info());
        }
    }
    for (size_t i = 0; i < _media_objects.size(); i++)
    {
        std::string pfx = (_media_objects.size() == 1 ? "" : str::from(i + 1) + " - ");
        for (int j = 0; j < _media_objects[i].subtitle_streams(); j++)
        {
            std::string pfx2 = (_media_objects[i].subtitle_streams() == 1 ? "" : str::from(j + 1) + " - ");
            _subtitle_stream_names.push_back(pfx + pfx2
                    + _media_objects[i].subtitle_box_template(j).format_info());
        }
    }

    // Set duration information
    _duration = std::numeric_limits<int64_t>::max();
    for (size_t i = 0; i < _media_objects.size(); i++)
    {
        for (int j = 0; j < _media_objects[i].video_streams(); j++)
        {
            int64_t d = _media_objects[i].video_duration(j);
            if (d < _duration)
            {
                _duration = d;
            }
        }
        for (int j = 0; j < _media_objects[i].audio_streams(); j++)
        {
            int64_t d = _media_objects[i].audio_duration(j);
            if (d < _duration)
            {
                _duration = d;
            }
        }
        for (int j = 0; j < _media_objects[i].subtitle_streams(); j++)
        {
//             int64_t d = _media_objects[i].subtitle_duration(j);
//             if (d < _duration)
//             {
//                 _duration = d;
//             }
        }
    }
 
    // Skip advertisement in 3dtv.at movies. Only works for single media objects.
    try { _initial_skip = str::to<int64_t>(tag_value("StereoscopicSkip")); } catch (...) { }

    // Find stereo layout and set active video stream(s)
    _supports_stereo_layout_separate = false;
    if (video_streams() == 2)
    {
        int o0, o1, v0, v1;
        get_video_stream(0, o0, v0);
        get_video_stream(1, o1, v1);
        video_frame t0 = _media_objects[o0].video_frame_template(v0);
        video_frame t1 = _media_objects[o1].video_frame_template(v1);
        if (t0.width == t1.width
                && t0.height == t1.height
                && (t0.aspect_ratio <= t1.aspect_ratio && t0.aspect_ratio >= t1.aspect_ratio)
                && t0.layout == t1.layout
                && t0.color_space == t1.color_space
                && t0.value_range == t1.value_range
                && t0.chroma_location == t1.chroma_location)
        {
            _supports_stereo_layout_separate = true;
        }
    }
    if (_supports_stereo_layout_separate)
    {
        _active_video_stream = 0;
        int o, s;
        get_video_stream(_active_video_stream, o, s);
        _video_frame = _media_objects[o].video_frame_template(s);
        _video_frame.stereo_layout = video_frame::separate;
    }
    else if (video_streams() > 0)
    {
        _active_video_stream = 0;
        int o, s;
        get_video_stream(_active_video_stream, o, s);
        _video_frame = _media_objects[o].video_frame_template(s);
    }
    else
    {
        _active_video_stream = -1;
    }
    if (_active_video_stream >= 0)
    {
        select_video_stream(_active_video_stream);
    }

    // Set active audio stream
    _active_audio_stream = (audio_streams() > 0 ? 0 : -1);
    if (_active_audio_stream >= 0)
    {
        int o, s;
        get_audio_stream(_active_audio_stream, o, s);
        _audio_blob = _media_objects[o].audio_blob_template(s);
        select_audio_stream(_active_audio_stream);
    }

    // Set active subtitle stream
    _active_subtitle_stream = -1;       // no subtitles by default

    // Print summary
    msg::inf("Input:");
    for (int i = 0; i < video_streams(); i++)
    {
        int o, s;
        get_video_stream(i, o, s);
        msg::inf("    Video %s: %s", video_stream_name(i).c_str(),
                _media_objects[o].video_frame_template(s).format_name().c_str());
    }
    if (video_streams() == 0)
    {
        msg::inf("    No video.");
    }
    for (int i = 0; i < audio_streams(); i++)
    {
        int o, s;
        get_audio_stream(i, o, s);
        msg::inf("    Audio %s: %s", audio_stream_name(i).c_str(), 
                _media_objects[o].audio_blob_template(s).format_name().c_str());
    }
    if (audio_streams() == 0)
    {
        msg::inf("    No audio.");
    }
    for (int i = 0; i < subtitle_streams(); i++)
    {
        int o, s;
        get_subtitle_stream(i, o, s);
        msg::inf("    Subtitle %s: %s", subtitle_stream_name(i).c_str(), 
                _media_objects[o].subtitle_box_template(s).format_name().c_str());
    }
    if (subtitle_streams() == 0)
    {
        msg::inf("    No subtitles.");
    }
    msg::inf("    Duration: %g seconds", duration() / 1e6f);
    if (video_streams() > 0)
    {
        msg::inf("    Stereo layout: %s", video_frame::stereo_layout_to_string(
                    video_frame_template().stereo_layout, video_frame_template().stereo_layout_swap).c_str());
    }
}