/* Copyright (C) 2012-2020 Carl Hetherington This program 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. This program 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 this program; if not, write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "util.h" #include #include "reader.h" #include "subtitle.h" #include "collect.h" #include #include #include #include #include using std::string; using std::getline; using std::ostream; using std::map; using std::list; using boost::optional; using boost::shared_ptr; using namespace sub; /** @param s A string. * @return true if the string contains only space, newline or tab characters, or is empty. */ bool sub::empty_or_white_space (string s) { for (size_t i = 0; i < s.length(); ++i) { if (s[i] != ' ' && s[i] != '\n' && s[i] != '\t') { return false; } } return true; } optional sub::get_line_stringstream (locked_stringstream* str) { if (!str->good ()) { return optional (); } string s; getline (*str, s); return s; } optional sub::get_line_file (FILE* f) { char buffer[256]; char* r = fgets (buffer, sizeof (buffer), f); if (r == 0) { return optional (); } return string (buffer); } void sub::remove_unicode_bom (optional& line) { if ( line->length() >= 3 && static_cast (line.get()[0]) == 0xef && static_cast (line.get()[1]) == 0xbb && static_cast (line.get()[2]) == 0xbf ) { /* Skip Unicode byte order mark */ line = line->substr (3); } } void sub::dump (shared_ptr reader, ostream& os) { map metadata = reader->metadata (); for (map::const_iterator i = metadata.begin(); i != metadata.end(); ++i) { os << i->first << ": " << i->second << "\n"; } list subs = collect > (reader->subtitles ()); int n = 0; for (list::const_iterator i = subs.begin(); i != subs.end(); ++i) { os << "Subtitle " << n << " at " << i->from << " -> " << i->to << "\n"; for (list::const_iterator j = i->lines.begin(); j != i->lines.end(); ++j) { os << "\t"; if (j->vertical_position.proportional) { os << j->vertical_position.proportional.get() << " of screen"; } else if (j->vertical_position.line && j->vertical_position.lines) { os << j->vertical_position.line.get() << " lines of " << j->vertical_position.lines.get(); } if (j->vertical_position.reference) { os << " from "; switch (j->vertical_position.reference.get()) { case TOP_OF_SCREEN: os << "top"; break; case VERTICAL_CENTRE_OF_SCREEN: os << "centre"; break; case BOTTOM_OF_SCREEN: os << "bottom"; break; case TOP_OF_SUBTITLE: os << "top of subtitle"; break; } } os << "\t"; bool italic = false; bool underline = false; for (list::const_iterator k = j->blocks.begin(); k != j->blocks.end(); ++k) { if (k->italic && !italic) { os << ""; } else if (italic && !k->italic) { os << ""; } if (k->underline && !underline) { os << ""; } else if (underline && !k->underline) { os << ""; } italic = k->italic; underline = k->underline; os << k->text; } if (italic) { os << ""; } if (underline) { os << ""; } os << "\n"; } ++n; } }