PROJECT NAME
AssParser
WHAT IT IS
ass_parser is a Rust crate I built to make working with .ass subtitle files a lot easier. If you've ever messed around with subtitles that need fancy formatting, precise positioning, or anime-style effects, you've probably seen this file type. With AssParser, you can read, write, and tweak these files however you like no fuss. It's designed to be clean, straightforward, and Rustacean-friendly.
WHY I BUILT IT
I have worked with .ass
files before in Rust and found that there aren't many libraries that did what I wanted (Read and Modify .ass files), Convert a .srt
(SubRip Subtitle File) to a .ass
file. Plus most of them are not maintained. So I decided to build my own parser in Rust that makes it easy to create, modify, convert and understand these files without the headacheIt was a fun way to dive deep into parsing world and also contributing to the community.
HOW IT WORKS
Under the hood, AssParser breaks down an .ass
subtitle file into clearly defined parts using Rust structs like ScriptInfo for metadata, V4Style for styles, and Events for dialogue lines to_know_more. These sections are all wrapped neatly inside an AssFile struct, making it easy to build or modify subtitles programmatically. You don’t need to worry about formatting rules or file structure just work with the fields you care about, and AssParser handles the rest.
SUBTITLING RAP GOD - BECAUSE WHY NOT
I wanted to test my parser with a fast changing subtitles, So I taught why not style subtitles with one of the fastest rap songs out there? Using AssParser. I created .ass subtitle file synced to Rap God by Eminem complete with timed lyrics and random colors.
⚠️ Note: This is just a demo to showcase what AssParser can do. All rights to the song and lyrics belong to Eminem and his copyright holders.
Here is a demo where I subtitled Rap God by Eminem with Random Colors!Here is the sample code that I used to generate the random colored subtitles.
use ass_parser::{AssFile, Events, Dialogue, V4Format, ScriptInfo};
use hex_color::HexColor;
fn main() {
let srt_file = AssFile::from_srt("./Rap-God.srt");
let output_path = "./Rap-God.ass";
let mut ass_file = AssFile::new();
let mut event = Events::new();
let mut srt_iter = srt_file.iter();
let next = srt_iter.next().unwrap();
let dialogue = Dialogue::default()
.set_start(&next.start)
.set_colour(HexColor::RED)
.set_end(&next.end)
.set_text(&next.text)
.set_colour(HexColor::random_rgb());
event.add_dialogue(dialogue);
println!("Generating subtitles...");
for srt_seg in srt_iter {
let dialogue = Dialogue::default()
.set_start(&srt_seg.start)
.set_end(&srt_seg.end)
.set_text(&srt_seg.text)
.set_colour(HexColor::random_rgb());
event.add_dialogue(dialogue);
}
event.create();
ass_file.components.v4.set_v4(V4Format::default());
ass_file.components.script.set_script(ScriptInfo::default());
ass_file.components.events.set_events(event);
AssFile::save_file(&ass_file, output_path);
println!("Generated and saved .ass file to {}", output_path);
}
Here are the files that I used to create this:
Rap-God.srt
The final
.ass
file
Rap-God.ass
INSTALLATION
ass_parser is a Rust crate which you can use to create, read and modify .ass
files.
To download the rust crate you can add this crate using cargo
package manager.
cargo add ass_parser
This adds ass_parser
as a dependency to your rust project
EXAMPLE - DEFAULT VALUES
Creating a simple Advanced SubStation Alpha (.ass) file with default values!
Imports
use ass_parser::{AssFile, ScriptInfo, V4Format, Events, AssFileOptions};
use hex_color::HexColor;
Set Default values
let mut ass_file = AssFile::new();
let hexcolor = AssFileOptions::get_ass_color(HexColor::YELLOW);
ass_file.components.script
.set_script(ScriptInfo::default());
ass_file.components.v4
.set_v4(V4Format::default())
.set_primarycolour(&hexcolor);
ass_file.components.events
.set_events(Events::default());
Save the file
AssFile::save_file(&ass_file, "new_subtitles.ass")
EXAMPLE - ADD DIALOGUES
Add Dialogues
Imports
use ass_parser::{AssFile, ScriptInfo, V4Format, Events, AssFileOptions, Dialogue};
use hex_color::HexColor;
Add the dialogues
let mut ass_file = AssFile::new();
let hexcolor = AssFileOptions::get_ass_color(HexColor::YELLOW);
let first_dialogue = Dialogue::default()
.set_text("Hello There!")
.set_start("0:00:00.10")
.set_end("0:00:00.50");
let second_dialogue = Dialogue::default()
.set_text("Hello Friend!")
.set_start("00:00.50")
.set_end("00:00.58");
let third_dialogue = Dialogue::default()
.set_text("Hello World!!")
.set_start("0:00:00.58")
.set_end("0:00:01.01");
let events = Events::new()
.add_first_dialogue(first_dialogue)?
.add_dialogue(second_dialogue)
.add_dialogue(third_dialogue)
.create();
ass_file.components.script
.set_script(ScriptInfo::default())
.set_scripttype("FFMPEG");
ass_file.components.v4
.set_v4(V4Format::default())
.set_primarycolour(&hexcolor);
ass_file.components.events
.set_events(events);
AssFile::save_file(&ass_file, "new_subtitles.ass");
Ok(())
}
Save the file
AssFile::save_file(&ass_file, "new_subtitles.ass");
EXAMPLE - ADD COLORS TO SUBTITLES
Add Colors to Subtitles.
Description
you need to make sure to set this feature flag to have random rgb generation working
hex_color = {version = "3.0.0", features = ["rand", "std"]}
set the hex_color crate to the latest available version.
Imports
use hex_color::HexColor;
use ass_parser::Dialogue;
use ass_parser::Events;
let random_color: HexColor = HexColor::random_rgb();
let dialogue = Dialogue::default()
.set_text("Hello Friend!")
.set_start("0:00:00.50")
.set_end("0:00:00.58")
.set_colour(random_color);
let events = Events::new()
.add_first_dialogue(dialogue).expect("Unable to add Dialogue");
EXAMPLE - SRT TO ASS CONVERSION
Added Support for SubRip files.
Description
Now you can load .srt files and convert them to .ass files and even modify them during the process. This example loads a SubRip file (RapGod.srt), adds random colors to each subtitle, then converts and saves the result as an .ass file.
Imports
use hex_color::HexColor;
use ass_parser::{AssFile, AssFileOptions};
use ass_parser::{ScriptInfo, V4Format, Events, Dialogue};
fn main() {
let hexcolor = AssFileOptions::get_ass_color(HexColor::YELLOW);
let srt_file = AssFile::from_srt("examples/RapGod.srt");
let mut ass_file = AssFile::new();
let mut event = Events::default();
for srt_seg in srt_file.iter() {
let start = &srt_seg.start;
let end = &srt_seg.end;
let text = &srt_seg.text;
let random_color: HexColor = HexColor::random_rgb();
let dialogue = Dialogue::default()
.set_start(&start)
.set_end(&end)
.set_text(&text)
.set_colour(random_color);
event.add_dialogue(dialogue);
}
ass_file.components.script
.set_script(ScriptInfo::default());
ass_file.components.v4
.set_v4(V4Format::default())
.set_primarycolour(&hexcolor);
ass_file.components.events
.set_events(event);
AssFile::save_file(&ass_file, "new_subtitle.ass");
}
Save the file
AssFile::save_file(&ass_file, "new_subtitle.ass");
WHAT IT IS
Open Source & Community Driven
ass_parser is fully open source and packed with documentation and examples. Whether you're just exploring or want to contribute, you're welcome!
🤝 Want to contribute? Check out our contribution guidelines.