captionbob docs

Version 1.0.0
Contents ↓

Python: captionbob.effects

captionbob.effects.swift

Swift effect: slanted bold white words that appear one by one.

Each caption shows a few words as spoken, with their end marks, in bold white letters that lean to the right. A soft dark shadow spreads out around the letters. The words stand in rows of a few words, one row under the other, and each row has its middle in the middle of the video.

The captions take their turns from an order of turns, which starts again when it ends. A caption has one of two turns:

  • rise: the caption starts below its place and rises into it, fast at first and slower at the end. Each word fades in when it starts, at its own place in its row.
  • type: the caption stands in its place. The letters of each word appear one after the other in the time in which the word is spoken, and each row keeps its middle in the middle of the video as it grows.

The letters are those of the font, leaned to the right and made taller by the letter height, with an outline in their own color, which makes them heavier. So the widths of the words stay the widths that libass gives for the font, and the caption measure gives them. The rows of a caption are apart by the row spacing, which is less than the room that libass gives two lines of the font. So each row is an event of its own. The caption measure gives the rows of each line of words: a line that is too wide for the room between the side margins breaks into more rows.

ASS moves a text only in a straight line at one speed. So the rise of a caption is cut into short events, and each event is one straight move from one place of the curve to the next. A caption that types is one event for each look of each row.

The shadow of each event is the same text in the shadow color on the layer below it, with an outline that is wider by the shadow radius, and blurred.

The effect draws nothing itself. It builds the text of an ASS script, and ffmpeg draws it on the video. The common part of the effects is in effect_common.py.

The defaults are the look of the source video of the effect, measured on its frames and scaled to a video of 1080x1920.

Source file: captionbob/effects/swift.py

Settings

The command line and the HTTP API call this effect the style swift. Its settings class is SwiftSettings. Each setting has the default below.

Setting Type Default Description
most_words integer 4 The most words that one caption shows.
fewest_words integer 1 The fewest words that one caption shows, when its sentence is long enough for that.
font_name string "DejaVu Sans" Name of the font of the text.
font_size integer 67 Height of the font in pixels.
bold boolean true True for bold text.
primary_color string "#FFFFFF" Color of the text, as "#RRGGBB".
stroke_color string "#FFFFFF" Color of the outline of the text, as "#RRGGBB".
stroke_width number 2.0 Width of the outline in pixels. 0 gives no outline.
bottom_position number 0.665 Where the bottom of the caption sits, as a part of the video height from the top. 0.75 is three quarters of the way down.
side_margin integer 54 Room in pixels that stays free on the left and on the right of the caption. A caption that is too wide for the room between the margins breaks into lines.
slant number 0.25 How far the top of a letter is to the right of its bottom, as a part of the height of the letter. 0 gives upright letters.
letter_height number 1.22 The height of the letters as a part of the height that the font gives them.
words_per_line integer 3 The most words of one line of a caption. A line that is too wide for the room between the side margins breaks into more rows.
row_spacing number 70.0 Room in pixels from the bottom of one row of a caption to the bottom of the next row.
shadow_color string "#000000" Color of the shadow, as "#RRGGBB".
shadow_radius number 8.0 How far the shadow reaches out from the outline, in pixels, and how much it is blurred. 0 gives no shadow.
shadow_opacity number 0.5 Strength of the shadow, from 0 for no shadow to 1.
rise_height number 60.0 How far below its place a caption that rises starts, in pixels. 0 gives no rise.
rise_seconds number 2.4 The time in which a caption rises into its place. A caption that ends earlier ends before it is in its place. 0 gives no rise.
fade_seconds number 0.1 The time in which a word of a caption that rises fades in. 0 shows each word at once.
turns list ["type", "rise", "rise", "rise", "type"] The turn of each caption in order, each RISE_TURN or TYPE_TURN. The order starts again when it ends.
hold_seconds number 0.1 The longest time that a caption stays after its last word ends. The caption goes earlier when the next caption starts.

SwiftSettings

@dataclass(frozen=True)
class SwiftSettings(CaptionSettings)

The look and the timing of the swift effect.

The settings of CaptionSettings come first: the word counts, the font, the colors, the stroke, the bottom position and the side margin. These settings follow them. The bottom position is the place of the bottom of the first row of a caption, when the caption is in its place. The stroke is the outline of the letters.

Args:

  • slant: How far the top of a letter is to the right of its bottom, as a part of the height of the letter. 0 gives upright letters.
  • letter_height: The height of the letters as a part of the height that the font gives them.
  • words_per_line: The most words of one line of a caption. A line that is too wide for the room between the side margins breaks into more rows.
  • row_spacing: Room in pixels from the bottom of one row of a caption to the bottom of the next row.
  • shadow_color: Color of the shadow, as "#RRGGBB".
  • shadow_radius: How far the shadow reaches out from the outline, in pixels, and how much it is blurred. 0 gives no shadow.
  • shadow_opacity: Strength of the shadow, from 0 for no shadow to 1.
  • rise_height: How far below its place a caption that rises starts, in pixels. 0 gives no rise.
  • rise_seconds: The time in which a caption rises into its place. A caption that ends earlier ends before it is in its place. 0 gives no rise.
  • fade_seconds: The time in which a word of a caption that rises fades in. 0 shows each word at once.
  • turns: The turn of each caption in order, each RISE_TURN or TYPE_TURN. The order starts again when it ends.
  • hold_seconds: The longest time that a caption stays after its last word ends. The caption goes earlier when the next caption starts.

Raises:

  • TypeError: When a word count is not a whole number.
  • ValueError: When a value is outside its range, when a color is not in the form "#RRGGBB", when the font name is empty or holds a comma, or when the turns are not a tuple of one turn or more.

SwiftSettings.has_shadow

@property
def has_shadow(self) -> bool

True when the settings give a shadow that can be seen.

SwiftSettings.shadow_style_line

def shadow_style_line(self, margin_vertical: int) -> str

Write the ASS style line of the shadow of these settings.

The shadow is the text in the shadow color, with an outline that is wider than the stroke by the shadow radius. The event of the shadow blurs this outline.

Args:

  • margin_vertical: Room in pixels between the bottom of the caption and the bottom edge of the video.

Returns:

The style line of the shadow of the captions.

Raises:

  • ValueError: When the font name, the font size, the shadow color, the outline width or a margin is outside its range.

SwiftEffect

class SwiftEffect
    def __init__(
            self, settings: SwiftSettings,
            caption_measure: PlaceMeasure) -> None

Builds the ASS script of slanted bold white words that appear one by one.

Args:

  • settings: The look and the timing of the effect.
  • caption_measure: The measure that says where libass draws each word of a caption. It runs ffmpeg once for all the captions of a video.

SwiftEffect.build_ass_text

def build_ass_text(self, words: Sequence[Word], video: VideoInfo) -> str

Build the ASS script of the effect for the words of one video.

Each row of each caption is one event or more on the text layer, and each of them has its shadow event with the same times on the shadow layer when the shadow can be seen. The shadows come first. The events of a caption start with its first word. They end when the next caption starts, and at the latest the hold time after its last word and at the end of the video.

Args:

  • words: The words of the video in time order, each with its times.
  • video: The frame size and the duration of the video.

Returns:

The text of the ASS script. It has no event when there are no words.

Raises:

  • ValueError: When the side margins leave no room for the caption in the width of the video, or when libass draws no pixel for a word.
  • RuntimeError: When the ffmpeg of the caption measure fails.