2 Copyright (C) 2013-2020 Carl Hetherington <cth@carlh.net>
4 This file is part of DCP-o-matic.
6 DCP-o-matic is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
11 DCP-o-matic is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with DCP-o-matic. If not, see <http://www.gnu.org/licenses/>.
22 #include "audio_stream.h"
25 #include <boost/foreach.hpp>
30 using boost::shared_ptr;
33 Piece::Piece (shared_ptr<Content> c, shared_ptr<Decoder> d, FrameRateChange f)
37 _content.push_back (c);
38 _decoder.push_back (d);
41 BOOST_FOREACH (AudioStreamPtr i, c->audio->streams()) {
42 _stream_last_push_end[i] = c->position();
49 Piece::update_pull_to (DCPTime& pull_to) const
55 for (map<AudioStreamPtr, DCPTime>::const_iterator i = _stream_last_push_end.begin(); i != _stream_last_push_end.end(); ++i) {
56 if (i->second < pull_to) {
64 Piece::set_last_push_end (AudioStreamPtr stream, DCPTime end)
66 DCPOMATIC_ASSERT (_stream_last_push_end.find(stream) != _stream_last_push_end.end());
67 _stream_last_push_end[stream] = end;
72 Piece::position () const
74 return _content[0]->position();
79 Piece::end (shared_ptr<const Film> film) const
81 return _content[0]->end(film);
86 Piece::content_video_to_dcp (Frame f) const
88 /* It might seem more logical here to convert s to a ContentTime (using the FrameRateChange)
89 then convert that ContentTime to frames at the content's rate. However this fails for
90 situations like content at 29.9978733fps, DCP at 30fps. The accuracy of the Time type is not
91 enough to distinguish between the two with low values of time (e.g. 3200 in Time units).
93 Instead we convert the DCPTime using the DCP video rate then account for any skip/repeat.
96 DCPTime const d = DCPTime::from_frames(f * _frc.factor(), _frc.dcp) - DCPTime(_content[0]->trim_start(), _frc);
97 return d + position();
102 Piece::resampled_audio_to_dcp (shared_ptr<const Film> film, Frame f) const
104 /* See comment in dcp_to_content_video */
105 return DCPTime::from_frames(f, film->audio_frame_rate()) - DCPTime(_content[0]->trim_start(), frc) + position();
110 Piece::dcp_to_content_time (shared_ptr<const Film> film, DCPTime t) const
112 DCPTime s = t - position();
113 s = min (_content[0]->length_after_trim(_film), s);
114 return max (ContentTime(), ContentTime(s, _frc) + _content[0]->trim_start());
119 Piece::content_time_to_dcp (ContentTime t) const
121 return max (DCPTime(), DCPTime(t - _content[0]->trim_start(), _frc) + position());
126 Piece::add_fonts (list<shared_ptr<Font> >& fonts) const
128 BOOST_FOREACH (shared_ptr<Content> i, _content) {
129 BOOST_FOREACH (shared_ptr<TextContent> j, i->text) {
130 /* XXX: things may go wrong if there are duplicate font IDs
131 with different font files.
133 list<shared_ptr<Font> > f = j->fonts ();
134 copy (f.begin(), f.end(), back_inserter(fonts));
141 Piece::position (shared_ptr<const Film> film)
144 return optional<DCPTime>();
147 DCPTime const t = content_time_to_dcp (max(_decoder[0]->position(), _content[0]->trim_start()));
150 return optional<DCPTime>();
158 Piece::has_text () const
160 return !_decoder[0].text.empty();
167 _done = _decoder[0]->pass();