Esempio n. 1
0
    def subtitles(
            self,
            comments: Comments) -> Generator[Tuple[str, Comment], None, None]:
        """
        Subtitle generator
        :param comments: Comments to turn into subtitles
        :return: Generator with subtitles and subtitle data
        """
        for index, comment in enumerate(comments):
            # Stat and stop timestamps. Add a millisecond for timedelta to include millisecond digits
            start = datetime.timedelta(seconds=comment.content_offset_seconds)
            stop: datetime.timedelta = start + datetime.timedelta(
                milliseconds=self.format_dictionary['duration'])

            # Format message
            message: str = Pipe(self.format_dictionary['comments']).comment(
                comment.data)

            # Subtitle variables
            # Subtract the last three milliseconds form timestamp (required by SRT)
            subtitle: dict = {
                'index': index + 1,
                'start': SRT.format_timestamp(start),
                'stop': SRT.format_timestamp(stop),
                'message': message
            }

            yield '{index}\n{start} --> {stop}\n{message}\n'.format_map(
                SafeDict(subtitle)), comment
Esempio n. 2
0
 def use(self) -> Tuple[Generator[Tuple[str, Comment], None, None], str]:
     """
     Use SRT format
     :return: Comment generator and output string
     """
     return self.subtitles(self.video.comments), Pipe(
         self.format_dictionary['output']).output(self.video.data)
Esempio n. 3
0
    def use(self) -> Tuple[Generator[Tuple[str, Comment], None, None], str]:
        """
        Use SSA format
        :return:
        """
        output: str = Pipe(self.format_dictionary['output']).output(
            self.video.data)

        return self.generator(), output
Esempio n. 4
0
    def use(self) -> Tuple[Generator[Tuple[str, twitch.v5.Comment], None, None], str]:
        """
        Use this format
        :return: tuple(formatted comment, comment), output format
        """
        # Format comments
        comments = self.comment_generator(self.video.comments())

        # Format output
        output: str = Pipe(self.format_dictionary['output']).output(self.video.data)

        return comments, output
Esempio n. 5
0
 def comment_generator(
         self,
         comments: Comments) -> Generator[Tuple[str, Comment], None, None]:
     for comment in comments:
         yield Pipe(self.format_dictionary['comments']).comment(
             comment.data), comment
Esempio n. 6
0
    def dialogues(
            self,
            comments: Comments) -> Generator[Tuple[str, Comments], None, None]:
        """
        Format comments as SSA dialogues
        :param comments: Comment to format
        :return: tuple(formatted comment, comment)
        """
        for comment in comments:
            start: datetime.timedelta = datetime.timedelta(
                seconds=comment.content_offset_seconds)
            end: datetime.timedelta = start + datetime.timedelta(
                milliseconds=self.format_dictionary['duration'])

            # Avoid SSA variable conflicts with Python string formatting
            # This is done by temporarily removing opening and closing curly brackets used by SSA.
            #
            # The main problem is detecting these curly brackets. We want to differentiate brackets that
            # should be used by the Python string formatter, and those used by SSA.
            #
            # Opening curly brackets for SSA can easily be found by looking for "{\", however,
            # closing curly brackets are used in the same way (just a "}") for both and requires a bit more effort.
            #
            # By incrementing a counter for opening brackets meant for Python formatting and decrementing for every
            # closing bracket meant for Python formatting, we can define every closing bracket to belong to SSA whenever
            # the counter is at zero.

            ssa_closing_brackets_indices: list = []
            open_bracket_counter: int = 0

            # Loop through every character in formatting string
            for index in range(
                    len(self.format_dictionary['comments']['format'])):
                letter: str = self.format_dictionary['comments']['format'][
                    index]

                # Check if SSA bracket first, before altering the counter.
                if letter is '}' and open_bracket_counter is 0:
                    ssa_closing_brackets_indices.append(index)
                    continue

                # Update counter
                open_bracket_counter += {
                    '{': 1,  # Bracket is opened
                    '\\': -1,  # Bracket was meant for SSA, not for Python
                    '}': -1  # Closing bracket
                }.get(letter, 0)

                # Multiple SSA commands within a curly brackets could make it negative
                # Example: {\\c&#000000&\\b1} will count 1, 0, -1, -2
                open_bracket_counter = max(0, open_bracket_counter)

            # Add a temporary special character for SSA closing curly brackets
            for index in ssa_closing_brackets_indices:
                self.format_dictionary['comments']['format'] = self.format_dictionary['comments']['format'][
                                                               :index] + SSA.SPECIAL + \
                                                               self.format_dictionary['comments']['format'][index + 1:]

            self.format_dictionary['comments'][
                'format'] = self.format_dictionary['comments'][
                    'format'].replace('{\\', SSA.OPEN).replace(
                        SSA.SPECIAL, SSA.CLOSE)

            # Format comment
            comment_text = Pipe(self.format_dictionary['comments']).comment(
                comment.data)

            # Insert opening and closing curly brackets for SSA
            comment_text = comment_text.replace(SSA.OPEN,
                                                '{\\').replace(SSA.CLOSE, '}')

            # Convert color code into SSA color code.
            comment_text = comment_text.replace('\\c&#', '\\c&H').replace(
                '\\c&H#', '\\c&H')

            dialogue: dict = {
                'start': SSA.format_timestamp(start),
                'end': SSA.format_timestamp(end),
                'comment': comment_text
            }
            dialogue.update(comment.data)

            yield self.format_dictionary['events']['dialogue'].format_map(
                SafeDict(dialogue)), comment