Remove in-place translations support.
[dcpomatic.git] / src / lib / dcp_decoder.cc
index 85c5d3297d0d6a8acb704f523bf70d01524446e4..165b5bfb55a2b3ee70521f55fd3a15815722cc65 100644 (file)
@@ -23,6 +23,7 @@
 #include "audio_content.h"
 #include "audio_decoder.h"
 #include "config.h"
+#include "constants.h"
 #include "dcp_content.h"
 #include "dcp_decoder.h"
 #include "digester.h"
@@ -44,6 +45,7 @@
 #include <dcp/reel_picture_asset.h>
 #include <dcp/reel_sound_asset.h>
 #include <dcp/reel_subtitle_asset.h>
+#include <dcp/search.h>
 #include <dcp/sound_asset_reader.h>
 #include <dcp/sound_frame.h>
 #include <dcp/stereo_picture_asset.h>
@@ -68,8 +70,8 @@ using namespace dcpomatic;
 
 
 DCPDecoder::DCPDecoder (shared_ptr<const Film> film, shared_ptr<const DCPContent> content, bool fast, bool tolerant, shared_ptr<DCPDecoder> old)
-       : DCP (content, tolerant)
-       , Decoder (film)
+       : Decoder (film)
+       , _dcp_content (content)
 {
        if (content->can_be_played()) {
                if (content->video) {
@@ -79,8 +81,11 @@ DCPDecoder::DCPDecoder (shared_ptr<const Film> film, shared_ptr<const DCPContent
                        audio = make_shared<AudioDecoder>(this, content->audio, fast);
                }
                for (auto i: content->text) {
-                       /* XXX: this time here should be the time of the first subtitle, not 0 */
-                       text.push_back (make_shared<TextDecoder>(this, i, ContentTime()));
+                       text.push_back (make_shared<TextDecoder>(this, i));
+                       /* We should really call maybe_set_position() on this TextDecoder to set the time
+                        * of the first subtitle, but it probably doesn't matter since we'll always
+                        * have regularly occurring video (and maybe audio) content.
+                        */
                }
                if (content->atmos) {
                        atmos = make_shared<AtmosDecoder>(this, content);
@@ -100,8 +105,7 @@ DCPDecoder::DCPDecoder (shared_ptr<const Film> film, shared_ptr<const DCPContent
        if (old && old->lazy_digest() == _lazy_digest) {
                _reels = old->_reels;
        } else {
-
-               auto cpl_list = cpls ();
+               auto cpl_list = dcp::find_and_resolve_cpls(content->directories(), tolerant);
 
                if (cpl_list.empty()) {
                        throw DCPError (_("No CPLs found in DCP."));
@@ -118,7 +122,11 @@ DCPDecoder::DCPDecoder (shared_ptr<const Film> film, shared_ptr<const DCPContent
                        /* No CPL found; probably an old file that doesn't specify it;
                           just use the first one.
                        */
-                       cpl = cpls().front ();
+                       cpl = cpl_list.front();
+               }
+
+               if (content->kdm()) {
+                       cpl->add (decrypt_kdm_with_helpful_error(content->kdm().get()));
                }
 
                _reels = cpl->reels ();
@@ -128,6 +136,9 @@ DCPDecoder::DCPDecoder (shared_ptr<const Film> film, shared_ptr<const DCPContent
 
        _reel = _reels.begin ();
        get_readers ();
+
+       _font_id_allocator.add_fonts_from_reels(_reels);
+       _font_id_allocator.allocate();
 }
 
 
@@ -283,7 +294,7 @@ DCPDecoder::pass_texts (
                        true
                        );
 
-               list<dcp::SubtitleString> strings;
+               vector<dcp::SubtitleString> strings;
 
                for (auto i: subs) {
                        auto is = dynamic_pointer_cast<const dcp::SubtitleString>(i);
@@ -295,12 +306,19 @@ DCPDecoder::pass_texts (
                                                        ContentTime::from_frames(_offset - entry_point, vfr) + ContentTime::from_seconds(b.in().as_seconds()),
                                                        ContentTime::from_frames(_offset - entry_point, vfr) + ContentTime::from_seconds(b.out().as_seconds())
                                                        ),
-                                               strings
+                                               strings,
+                                               asset->subtitle_standard()
                                                );
                                        strings.clear ();
                                }
 
-                               strings.push_back (*is);
+                               dcp::SubtitleString is_copy = *is;
+                               if (is_copy.font()) {
+                                       is_copy.set_font(_font_id_allocator.font_id(_reel - _reels.begin(), asset->id(), is_copy.font().get()));
+                               } else {
+                                       is_copy.set_font(_font_id_allocator.default_font_id());
+                               }
+                               strings.push_back(is_copy);
                        }
 
                        /* XXX: perhaps these image subs should also be collected together like the string ones are;
@@ -328,7 +346,8 @@ DCPDecoder::pass_texts (
                                        ContentTime::from_frames(_offset - entry_point, vfr) + ContentTime::from_seconds(b.in().as_seconds()),
                                        ContentTime::from_frames(_offset - entry_point, vfr) + ContentTime::from_seconds(b.out().as_seconds())
                                        ),
-                               strings
+                               strings,
+                               asset->subtitle_standard()
                                );
                        strings.clear ();
                }
@@ -356,7 +375,7 @@ DCPDecoder::get_readers ()
                return;
        }
 
-       if ((*_reel)->main_picture()) {
+       if (video && !video->ignore() && (*_reel)->main_picture()) {
                auto asset = (*_reel)->main_picture()->asset ();
                auto mono = dynamic_pointer_cast<dcp::MonoPictureAsset> (asset);
                auto stereo = dynamic_pointer_cast<dcp::StereoPictureAsset> (asset);
@@ -375,7 +394,7 @@ DCPDecoder::get_readers ()
                _stereo_reader.reset ();
        }
 
-       if ((*_reel)->main_sound()) {
+       if (audio && !audio->ignore() && (*_reel)->main_sound()) {
                _sound_reader = (*_reel)->main_sound()->asset()->start_read ();
                _sound_reader->set_check_hmac (false);
        } else {
@@ -431,10 +450,12 @@ DCPDecoder::seek (ContentTime t, bool accurate)
 
        /* Pass texts in the pre-roll */
 
-       auto const vfr = _dcp_content->active_video_frame_rate (film());
-       for (int i = 0; i < pre_roll_seconds * vfr; ++i) {
-               pass_texts (pre, (*_reel)->main_picture()->asset()->size());
-               pre += ContentTime::from_frames (1, vfr);
+       if (_reel != _reels.end()) {
+               auto const vfr = _dcp_content->active_video_frame_rate (film());
+               for (int i = 0; i < pre_roll_seconds * vfr; ++i) {
+                       pass_texts (pre, (*_reel)->main_picture()->asset()->size());
+                       pre += ContentTime::from_frames (1, vfr);
+               }
        }
 
        /* Seek to correct position */
@@ -497,18 +518,3 @@ DCPDecoder::position () const
        return ContentTime::from_frames(_offset, _dcp_content->active_video_frame_rate(film())) + _next;
 }
 
-
-vector<FontData>
-DCPDecoder::fonts () const
-{
-       vector<FontData> data;
-       for (auto i: _reels) {
-               if (i->main_subtitle() && i->main_subtitle()->asset()) {
-                       for (auto const& j: i->main_subtitle()->asset()->font_data()) {
-                               data.push_back (FontData(j.first, j.second));
-                       }
-               }
-       }
-       return data;
-}
-