summaryrefslogtreecommitdiff
path: root/test
diff options
context:
space:
mode:
authorCarl Hetherington <cth@carlh.net>2022-11-18 10:56:42 +0100
committerCarl Hetherington <cth@carlh.net>2022-11-21 20:09:28 +0100
commit323b8cbb0b95297fbd027ffdc4ea5003b59ef25f (patch)
tree9d558917b9a6ad488fc127293fba2b903c329d2b /test
parentb9f949d688b6e9563f6350286bbbc3f169b1b9fe (diff)
Fix subtitle vertical position (#2367).
Previously we would not account for the differences in what vertical position means between Interop and SMPTE. For interop, vertical position is the distance from the reference point to the text baseline, whereas for SMPTE it is the distance from the reference point to the top/middle/bottom of the subtitle (depending on the reference). This caused differences between the preview and the DCP for some cases (notably, using SRT/SSA and making Interop DCPs, or converting Interop DCP subs to SMPTE, or vice versa).
Diffstat (limited to 'test')
m---------test/data0
-rw-r--r--test/subtitle_position_test.cc164
-rw-r--r--test/wscript1
3 files changed, 165 insertions, 0 deletions
diff --git a/test/data b/test/data
-Subproject 92d2787d602701d5faf53f0ab7430f62bec0916
+Subproject ef2374f03fbd715883da46bb3cb011befa11615
diff --git a/test/subtitle_position_test.cc b/test/subtitle_position_test.cc
new file mode 100644
index 000000000..0237a417c
--- /dev/null
+++ b/test/subtitle_position_test.cc
@@ -0,0 +1,164 @@
+/*
+ Copyright (C) 2022 Carl Hetherington <cth@carlh.net>
+
+ This file is part of DCP-o-matic.
+
+ DCP-o-matic is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
+
+ DCP-o-matic is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with DCP-o-matic. If not, see <http://www.gnu.org/licenses/>.
+
+*/
+
+
+#include "lib/content.h"
+#include "lib/content_factory.h"
+#include "lib/film.h"
+#include "lib/make_dcp.h"
+#include "lib/text_content.h"
+#include "test.h"
+#include <dcp/interop_subtitle_asset.h>
+#include <dcp/smpte_subtitle_asset.h>
+#include <dcp/language_tag.h>
+#include <boost/test/unit_test.hpp>
+#include <vector>
+
+
+using std::string;
+using std::vector;
+using std::shared_ptr;
+
+
+BOOST_AUTO_TEST_CASE(interop_correctly_placed_in_interop)
+{
+ string const name = "interop_in_interop_position_test";
+ auto fr = content_factory("test/data/dcp_sub.xml");
+ auto film = new_test_film2(name, fr);
+
+ film->set_interop(true);
+
+ make_and_verify_dcp (
+ film,
+ {
+ dcp::VerificationNote::Code::INVALID_STANDARD,
+ dcp::VerificationNote::Code::INVALID_SUBTITLE_SPACING,
+ dcp::VerificationNote::Code::INVALID_SUBTITLE_DURATION
+ });
+
+ auto output = subtitle_file(film);
+ dcp::InteropSubtitleAsset asset(output);
+ auto output_subs = asset.subtitles();
+ BOOST_REQUIRE_EQUAL(output_subs.size(), 1U);
+
+ /* The input subtitle should have been left alone */
+ BOOST_CHECK(output_subs[0]->v_align() == dcp::VAlign::BOTTOM);
+ BOOST_CHECK_CLOSE(output_subs[0]->v_position(), 0.08, 1e-3);
+}
+
+
+BOOST_AUTO_TEST_CASE(interop_correctly_placed_in_smpte)
+{
+ string const name = "interop_in_smpte_position_test";
+ auto fr = content_factory("test/data/dcp_sub.xml");
+ auto film = new_test_film2(name, fr);
+
+ film->set_interop(false);
+
+ make_and_verify_dcp (
+ film,
+ {
+ dcp::VerificationNote::Code::INVALID_SUBTITLE_SPACING,
+ dcp::VerificationNote::Code::MISSING_SUBTITLE_LANGUAGE,
+ dcp::VerificationNote::Code::MISSING_CPL_METADATA,
+ dcp::VerificationNote::Code::INVALID_SUBTITLE_FIRST_TEXT_TIME
+ });
+
+ auto output = subtitle_file(film);
+ dcp::SMPTESubtitleAsset asset(output);
+ auto output_subs = asset.subtitles();
+ BOOST_REQUIRE_EQUAL(output_subs.size(), 1U);
+
+ BOOST_CHECK(output_subs[0]->v_align() == dcp::VAlign::BOTTOM);
+ BOOST_CHECK_CLOSE(output_subs[0]->v_position(), 0.07074, 1e-3);
+}
+
+
+BOOST_AUTO_TEST_CASE(smpte_correctly_placed_in_interop)
+{
+ string const name = "smpte_in_interop_position_test";
+ auto fr = content_factory("test/data/short.srt");
+ auto film = new_test_film2(name, fr);
+
+ film->set_interop(true);
+
+ make_and_verify_dcp (
+ film,
+ {
+ dcp::VerificationNote::Code::INVALID_STANDARD,
+ dcp::VerificationNote::Code::INVALID_SUBTITLE_SPACING,
+ dcp::VerificationNote::Code::INVALID_SUBTITLE_FIRST_TEXT_TIME
+ });
+
+ auto output = subtitle_file(film);
+ dcp::InteropSubtitleAsset asset(output);
+ auto output_subs = asset.subtitles();
+ BOOST_REQUIRE_EQUAL(output_subs.size(), 1U);
+
+ BOOST_CHECK(output_subs[0]->v_align() == dcp::VAlign::TOP);
+ BOOST_CHECK_CLOSE(output_subs[0]->v_position(), 0.87079, 1e-3);
+}
+
+
+static
+void
+vpos_test(dcp::VAlign reference, float position, dcp::Standard from, dcp::Standard to)
+{
+ string standard = from == dcp::Standard::INTEROP ? "interop" : "smpte";
+ auto name = String::compose("vpos_test_%1_%2", standard, valign_to_string(reference));
+ auto in = content_factory(String::compose("test/data/%1.xml", name));
+ auto film = new_test_film2(name, in);
+
+ film->set_interop(to == dcp::Standard::INTEROP);
+
+ film->write_metadata();
+ make_dcp(film, TranscodeJob::ChangedBehaviour::IGNORE);
+ BOOST_REQUIRE(!wait_for_jobs());
+
+ auto out = subtitle_file(film);
+ vector<shared_ptr<const dcp::Subtitle>> subtitles;
+ if (to == dcp::Standard::INTEROP) {
+ dcp::InteropSubtitleAsset asset(out);
+ subtitles = asset.subtitles();
+ } else {
+ dcp::SMPTESubtitleAsset asset(out);
+ subtitles = asset.subtitles();
+ }
+
+ BOOST_REQUIRE_EQUAL(subtitles.size(), 1U);
+
+ BOOST_CHECK(subtitles[0]->v_align() == reference);
+ BOOST_CHECK_CLOSE(subtitles[0]->v_position(), position, 1e-3);
+}
+
+
+BOOST_AUTO_TEST_CASE(subtitles_correctly_placed_with_all_references)
+{
+ constexpr auto baseline_to_bottom = 0.00925926;
+ constexpr auto height = 0.0462963;
+
+ vpos_test(dcp::VAlign::TOP, 0.2 - height + baseline_to_bottom, dcp::Standard::INTEROP, dcp::Standard::SMPTE);
+ vpos_test(dcp::VAlign::CENTER, 0.11 - (height / 2) + baseline_to_bottom, dcp::Standard::INTEROP, dcp::Standard::SMPTE);
+ vpos_test(dcp::VAlign::BOTTOM, 0.08 - baseline_to_bottom, dcp::Standard::INTEROP, dcp::Standard::SMPTE);
+ vpos_test(dcp::VAlign::TOP, 0.1 + height - baseline_to_bottom, dcp::Standard::SMPTE, dcp::Standard::INTEROP);
+ vpos_test(dcp::VAlign::CENTER, 0.15 + (height / 2) - baseline_to_bottom, dcp::Standard::SMPTE, dcp::Standard::INTEROP);
+ vpos_test(dcp::VAlign::BOTTOM, 0.10 + baseline_to_bottom, dcp::Standard::SMPTE, dcp::Standard::INTEROP);
+}
+
diff --git a/test/wscript b/test/wscript
index fc63aac1e..e54d5c985 100644
--- a/test/wscript
+++ b/test/wscript
@@ -141,6 +141,7 @@ def build(bld):
subtitle_font_id_change_test.cc
subtitle_language_test.cc
subtitle_metadata_test.cc
+ subtitle_position_test.cc
subtitle_reel_test.cc
subtitle_reel_number_test.cc
subtitle_timing_test.cc