Add another .srt test; remove checking of .srt subtitle indices as the strict sequenc...
[dcpomatic.git] / test / subrip_test.cc
1 /*
2     Copyright (C) 2014 Carl Hetherington <cth@carlh.net>
3
4     This program is free software; you can redistribute it and/or modify
5     it under the terms of the GNU General Public License as published by
6     the Free Software Foundation; either version 2 of the License, or
7     (at your option) any later version.
8
9     This program is distributed in the hope that it will be useful,
10     but WITHOUT ANY WARRANTY; without even the implied warranty of
11     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12     GNU General Public License for more details.
13
14     You should have received a copy of the GNU General Public License
15     along with this program; if not, write to the Free Software
16     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
17
18 */
19
20 /** @file  test/subrip_test.cc
21  *  @brief Various tests of the subrip code.
22  */
23
24 #include <boost/test/unit_test.hpp>
25 #include <dcp/subtitle_content.h>
26 #include "lib/subrip.h"
27 #include "lib/subrip_content.h"
28 #include "lib/subrip_decoder.h"
29 #include "lib/render_subtitles.h"
30 #include "test.h"
31
32 using std::list;
33 using std::vector;
34 using std::string;
35 using boost::shared_ptr;
36 using boost::dynamic_pointer_cast;
37
38 /** Test SubRip::convert_time */
39 BOOST_AUTO_TEST_CASE (subrip_time_test)
40 {
41         BOOST_CHECK_EQUAL (SubRip::convert_time ("00:03:10,500"), ContentTime::from_seconds ((3 * 60) + 10 + 0.5));
42         BOOST_CHECK_EQUAL (SubRip::convert_time ("04:19:51,782"), ContentTime::from_seconds ((4 * 3600) + (19 * 60) + 51 + 0.782));
43 }
44
45 /** Test SubRip::convert_coordinate */
46 BOOST_AUTO_TEST_CASE (subrip_coordinate_test)
47 {
48         BOOST_CHECK_EQUAL (SubRip::convert_coordinate ("foo:42"), 42);
49         BOOST_CHECK_EQUAL (SubRip::convert_coordinate ("X1:999"), 999);
50 }
51
52 /** Test SubRip::convert_content */
53 BOOST_AUTO_TEST_CASE (subrip_content_test)
54 {
55         list<string> c;
56         list<SubRipSubtitlePiece> p;
57         
58         c.push_back ("Hello world");
59         p = SubRip::convert_content (c);
60         BOOST_CHECK_EQUAL (p.size(), 1);
61         BOOST_CHECK_EQUAL (p.front().text, "Hello world");
62         c.clear ();
63
64         c.push_back ("<b>Hello world</b>");
65         p = SubRip::convert_content (c);
66         BOOST_CHECK_EQUAL (p.size(), 1);
67         BOOST_CHECK_EQUAL (p.front().text, "Hello world");
68         BOOST_CHECK_EQUAL (p.front().bold, true);
69         c.clear ();
70
71         c.push_back ("<i>Hello world</i>");
72         p = SubRip::convert_content (c);
73         BOOST_CHECK_EQUAL (p.size(), 1);
74         BOOST_CHECK_EQUAL (p.front().text, "Hello world");
75         BOOST_CHECK_EQUAL (p.front().italic, true);
76         c.clear ();
77
78         c.push_back ("<u>Hello world</u>");
79         p = SubRip::convert_content (c);
80         BOOST_CHECK_EQUAL (p.size(), 1);
81         BOOST_CHECK_EQUAL (p.front().text, "Hello world");
82         BOOST_CHECK_EQUAL (p.front().underline, true);
83         c.clear ();
84
85         c.push_back ("{b}Hello world{/b}");
86         p = SubRip::convert_content (c);
87         BOOST_CHECK_EQUAL (p.size(), 1);
88         BOOST_CHECK_EQUAL (p.front().text, "Hello world");
89         BOOST_CHECK_EQUAL (p.front().bold, true);
90         c.clear ();
91
92         c.push_back ("{i}Hello world{/i}");
93         p = SubRip::convert_content (c);
94         BOOST_CHECK_EQUAL (p.size(), 1);
95         BOOST_CHECK_EQUAL (p.front().text, "Hello world");
96         BOOST_CHECK_EQUAL (p.front().italic, true);
97         c.clear ();
98
99         c.push_back ("{u}Hello world{/u}");
100         p = SubRip::convert_content (c);
101         BOOST_CHECK_EQUAL (p.size(), 1);
102         BOOST_CHECK_EQUAL (p.front().text, "Hello world");
103         BOOST_CHECK_EQUAL (p.front().underline, true);
104         c.clear ();
105
106         c.push_back ("<b>This is <i>nesting</i> of subtitles</b>");
107         p = SubRip::convert_content (c);
108         BOOST_CHECK_EQUAL (p.size(), 3);
109         list<SubRipSubtitlePiece>::iterator i = p.begin ();     
110         BOOST_CHECK_EQUAL (i->text, "This is ");
111         BOOST_CHECK_EQUAL (i->bold, true);
112         BOOST_CHECK_EQUAL (i->italic, false);
113         ++i;
114         BOOST_CHECK_EQUAL (i->text, "nesting");
115         BOOST_CHECK_EQUAL (i->bold, true);
116         BOOST_CHECK_EQUAL (i->italic, true);
117         ++i;
118         BOOST_CHECK_EQUAL (i->text, " of subtitles");
119         BOOST_CHECK_EQUAL (i->bold, true);
120         BOOST_CHECK_EQUAL (i->italic, false);
121         ++i;
122         c.clear ();
123 }
124
125 /** Test parsing of full SubRip file content */
126 BOOST_AUTO_TEST_CASE (subrip_parse_test)
127 {
128         shared_ptr<Film> film = new_test_film ("subrip_parse_test");
129         shared_ptr<SubRipContent> content (new SubRipContent (film, "test/data/subrip.srt"));
130         content->examine (shared_ptr<Job> ());
131         BOOST_CHECK_EQUAL (content->full_length(), DCPTime::from_seconds ((3 * 60) + 56.471));
132
133         SubRip s (content);
134
135         vector<SubRipSubtitle>::const_iterator i = s._subtitles.begin();
136
137         BOOST_CHECK (i != s._subtitles.end ());
138         BOOST_CHECK_EQUAL (i->period.from, ContentTime::from_seconds ((1 * 60) + 49.200));
139         BOOST_CHECK_EQUAL (i->period.to, ContentTime::from_seconds ((1 * 60) + 52.351));
140         BOOST_CHECK_EQUAL (i->pieces.size(), 1);
141         BOOST_CHECK_EQUAL (i->pieces.front().text, "This is a subtitle, and it goes over two lines.");
142
143         ++i;
144         BOOST_CHECK (i != s._subtitles.end ());
145         BOOST_CHECK_EQUAL (i->period.from, ContentTime::from_seconds ((1 * 60) + 52.440));
146         BOOST_CHECK_EQUAL (i->period.to, ContentTime::from_seconds ((1 * 60) + 54.351));
147         BOOST_CHECK_EQUAL (i->pieces.size(), 1);
148         BOOST_CHECK_EQUAL (i->pieces.front().text, "We have emboldened this");
149         BOOST_CHECK_EQUAL (i->pieces.front().bold, true);
150
151         ++i;
152         BOOST_CHECK (i != s._subtitles.end ());
153         BOOST_CHECK_EQUAL (i->period.from, ContentTime::from_seconds ((1 * 60) + 54.440));
154         BOOST_CHECK_EQUAL (i->period.to, ContentTime::from_seconds ((1 * 60) + 56.590));
155         BOOST_CHECK_EQUAL (i->pieces.size(), 1);
156         BOOST_CHECK_EQUAL (i->pieces.front().text, "And italicised this.");
157         BOOST_CHECK_EQUAL (i->pieces.front().italic, true);
158
159         ++i;
160         BOOST_CHECK (i != s._subtitles.end ());
161         BOOST_CHECK_EQUAL (i->period.from, ContentTime::from_seconds ((1 * 60) + 56.680));
162         BOOST_CHECK_EQUAL (i->period.to, ContentTime::from_seconds ((1 * 60) + 58.955));
163         BOOST_CHECK_EQUAL (i->pieces.size(), 1);
164         BOOST_CHECK_EQUAL (i->pieces.front().text, "Shall I compare thee to a summers' day?");
165
166         ++i;
167         BOOST_CHECK (i != s._subtitles.end ());
168         BOOST_CHECK_EQUAL (i->period.from, ContentTime::from_seconds ((2 * 60) + 0.840));
169         BOOST_CHECK_EQUAL (i->period.to, ContentTime::from_seconds ((2 * 60) + 3.400));
170         BOOST_CHECK_EQUAL (i->pieces.size(), 1);
171         BOOST_CHECK_EQUAL (i->pieces.front().text, "Is this a dagger I see before me?");
172
173         ++i;
174         BOOST_CHECK (i != s._subtitles.end ());
175         BOOST_CHECK_EQUAL (i->period.from, ContentTime::from_seconds ((3 * 60) + 54.560));
176         BOOST_CHECK_EQUAL (i->period.to, ContentTime::from_seconds ((3 * 60) + 56.471));
177         BOOST_CHECK_EQUAL (i->pieces.size(), 1);
178         BOOST_CHECK_EQUAL (i->pieces.front().text, "Hello world.");
179
180         ++i;
181         BOOST_CHECK (i == s._subtitles.end ());
182 }
183
184 /** Test rendering of a SubRip subtitle */
185 BOOST_AUTO_TEST_CASE (subrip_render_test)
186 {
187         shared_ptr<Film> film = new_test_film ("subrip_render_test");
188         shared_ptr<SubRipContent> content (new SubRipContent (film, "test/data/subrip.srt"));
189         content->examine (shared_ptr<Job> ());
190         BOOST_CHECK_EQUAL (content->full_length(), DCPTime::from_seconds ((3 * 60) + 56.471));
191
192         shared_ptr<SubRipDecoder> decoder (new SubRipDecoder (content));
193         list<ContentTextSubtitle> cts = decoder->get_text_subtitles (
194                 ContentTimePeriod (
195                         ContentTime::from_seconds (109), ContentTime::from_seconds (110)
196                         ), false
197                 );
198         BOOST_CHECK_EQUAL (cts.size(), 1);
199
200         PositionImage image = render_subtitles (cts.front().subs, dcp::Size (1998, 1080));
201         write_image (image.image, "build/test/subrip_render_test.png");
202         check_file ("build/test/subrip_render_test.png", "test/data/subrip_render_test.png");
203 }
204
205 static void
206 test (boost::filesystem::path p)
207 {
208         shared_ptr<Film> film = new_test_film ("subrip_read_test_" + p.string ());
209         boost::filesystem::path t = private_data / p;
210         shared_ptr<SubRipContent> s (new SubRipContent (film, t));
211         s->examine (shared_ptr<Job> ());
212 }
213
214 /** Test of reading some typical .srt files */
215 BOOST_AUTO_TEST_CASE (subrip_read_test)
216 {
217         test ("sintel_en.srt");
218         test ("Fight.Club.1999.720p.BRRip.x264-x0r.srt");
219 }