Go to the documentation of this file.
   60       .offset        = offsetof(
ASS, script_info),
 
   69     { .section       = 
"V4+ Styles",
 
   70       .format_header = 
"Format",
 
   71       .fields_header = 
"Style",
 
   74       .offset_count  = offsetof(
ASS, styles_count),
 
  101     { .section       = 
"V4 Styles",
 
  102       .format_header = 
"Format",
 
  103       .fields_header = 
"Style",
 
  106       .offset_count  = offsetof(
ASS, styles_count),
 
  128     { .section       = 
"Events",
 
  129       .format_header = 
"Format",
 
  130       .fields_header = 
"Dialogue",
 
  133       .offset_count  = offsetof(
ASS, dialogs_count),
 
  156         memcpy(str, buf, 
len);
 
  160         *(
char **)dest = str;
 
  166     return sscanf(buf, 
"%d", (
int *)dest) == 1;
 
  170     return sscanf(buf, 
"%f", (
float *)dest) == 1;
 
  174     return sscanf(buf, 
"&H%8x", (
int *)dest) == 1 ||
 
  175            sscanf(buf, 
"%d",    (
int *)dest) == 1;
 
  180     if ((
c = sscanf(buf, 
"%d:%02d:%02d.%02d", &
h, &m, &
s, &cs)) == 4)
 
  181         *(
int *)dest = 360000*
h + 6000*m + 100*
s + cs;
 
  187     if (sscanf(buf, 
"%d", &
a) == 1) {
 
  189         *(
int *)dest = 
a + ((
a&4) >> 1) - 5*!!(
a&8);
 
  217     void **section_ptr = (
void **)((uint8_t *)&
ctx->ass + section->
offset);
 
  230     return buf == 
'\r' || buf == 
'\n' || buf == 0;
 
  258     int *number = &
ctx->field_number[
ctx->current_section];
 
  259     int *order = 
ctx->field_order[
ctx->current_section];
 
  262     while (buf && *buf) {
 
  264             ctx->current_section = -1;
 
  267         if (buf[0] == 
';' || (buf[0] == 
'!' && buf[1] == 
':'))
 
  270         len = strcspn(buf, 
":\r\n");
 
  271         if (buf[
len] == 
':' &&
 
  276                     ctx->current_section = 
i;
 
  278                     number = &
ctx->field_number[
ctx->current_section];
 
  279                     order = 
ctx->field_order[
ctx->current_section];
 
  290                     len = strcspn(buf, 
", \r\n");
 
  303                 ctx->field_order[
ctx->current_section] = order;
 
  311                 if (!struct_ptr)  
return NULL;
 
  318                     ctx->field_order[
ctx->current_section] = order;
 
  322                 for (
i=0; !
is_eol(*buf) && 
i < *number; 
i++) {
 
  323                     int last = 
i == *number - 1;
 
  325                     len = strcspn(buf, last ? 
"\r\n" : 
",\r\n");
 
  332                     if (!last && *buf) buf++;
 
  337             len = strcspn(buf, 
":\r\n");
 
  338             if (buf[
len] == 
':') {
 
  342                         uint8_t *ptr = (uint8_t *)&
ctx->ass + section->
offset;
 
  351         buf += strcspn(buf, 
"\n");
 
  362     if (
ctx->current_section >= 0)
 
  365     while (buf && *buf) {
 
  366         if (sscanf(buf, 
"[%15[0-9A-Za-z+ ]]%c", section, &
c) == 2) {
 
  367             buf += strcspn(buf, 
"\n");
 
  371                     ctx->current_section = 
i;
 
  375             buf += strcspn(buf, 
"\n");
 
  387     if (buf && !strncmp(buf, 
"\xef\xbb\xbf", 3)) 
 
  389     ctx->current_section = -1;
 
  399     uint8_t *ptr = (uint8_t *)&
ctx->ass + section->
offset;
 
  400     int i, j, *count, 
c = 1;
 
  409         for (
i=0; 
i<*count; 
i++, ptr += section->
size)
 
  458         len = last ? strlen(buf) : strcspn(buf, 
",");
 
  459         if (
len >= INT_MAX) {
 
  486     const char *text = 
NULL;
 
  490     while (buf && *buf) {
 
  492             (sscanf(buf, 
"\\%1[nN]", new_line) == 1 ||
 
  493              !strncmp(buf, 
"{\\", 2))) {
 
  497         if (sscanf(buf, 
"\\%1[nN]", new_line) == 1) {
 
  499                 callbacks->new_line(priv, new_line[0] == 
'N');
 
  501         } 
else if (!strncmp(buf, 
"{\\", 2)) {
 
  503             while (*buf == 
'\\') {
 
  504                 char style[2], 
c[2], sep[2], c_num[2] = 
"0", 
tmp[128] = {0};
 
  505                 unsigned int color = 0xFFFFFFFF;
 
  507                 int x1, y1, x2, y2, t1 = -1, t2 = -1;
 
  508                 if (sscanf(buf, 
"\\%1[bisu]%1[01\\}]%n", style, 
c, &
len) > 1) {
 
  509                     int close = 
c[0] == 
'0' ? 1 : 
c[0] == 
'1' ? 0 : -1;
 
  513                 } 
else if (sscanf(buf, 
"\\c%1[\\}]%n", sep, &
len) > 0 ||
 
  514                            sscanf(buf, 
"\\c&H%X&%1[\\}]%n", &
color, sep, &
len) > 1 ||
 
  515                            sscanf(buf, 
"\\%1[1234]c%1[\\}]%n", c_num, sep, &
len) > 1 ||
 
  516                            sscanf(buf, 
"\\%1[1234]c&H%X&%1[\\}]%n", c_num, &
color, sep, &
len) > 2) {
 
  519                 } 
else if (sscanf(buf, 
"\\alpha%1[\\}]%n", sep, &
len) > 0 ||
 
  520                            sscanf(buf, 
"\\alpha&H%2X&%1[\\}]%n", &
alpha, sep, &
len) > 1 ||
 
  521                            sscanf(buf, 
"\\%1[1234]a%1[\\}]%n", c_num, sep, &
len) > 1 ||
 
  522                            sscanf(buf, 
"\\%1[1234]a&H%2X&%1[\\}]%n", c_num, &
alpha, sep, &
len) > 2) {
 
  525                 } 
else if (sscanf(buf, 
"\\fn%1[\\}]%n", sep, &
len) > 0 ||
 
  526                            sscanf(buf, 
"\\fn%127[^\\}]%1[\\}]%n", 
tmp, sep, &
len) > 1) {
 
  529                 } 
else if (sscanf(buf, 
"\\fs%1[\\}]%n", sep, &
len) > 0 ||
 
  530                            sscanf(buf, 
"\\fs%u%1[\\}]%n", &
size, sep, &
len) > 1) {
 
  533                 } 
else if (sscanf(buf, 
"\\a%1[\\}]%n", sep, &
len) > 0 ||
 
  534                            sscanf(buf, 
"\\a%2u%1[\\}]%n", &an, sep, &
len) > 1 ||
 
  535                            sscanf(buf, 
"\\an%1[\\}]%n", sep, &
len) > 0 ||
 
  536                            sscanf(buf, 
"\\an%1u%1[\\}]%n", &an, sep, &
len) > 1) {
 
  537                     if (an != -1 && buf[2] != 
'n')
 
  538                         an = (an&3) + (an&4 ? 6 : an&8 ? 3 : 0);
 
  541                 } 
else if (sscanf(buf, 
"\\r%1[\\}]%n", sep, &
len) > 0 ||
 
  542                            sscanf(buf, 
"\\r%127[^\\}]%1[\\}]%n", 
tmp, sep, &
len) > 1) {
 
  545                 } 
else if (sscanf(buf, 
"\\move(%d,%d,%d,%d)%1[\\}]%n", &x1, &y1, &x2, &y2, sep, &
len) > 4 ||
 
  546                            sscanf(buf, 
"\\move(%d,%d,%d,%d,%d,%d)%1[\\}]%n", &x1, &y1, &x2, &y2, &t1, &t2, sep, &
len) > 6) {
 
  548                         callbacks->move(priv, x1, y1, x2, y2, t1, t2);
 
  549                 } 
else if (sscanf(buf, 
"\\pos(%d,%d)%1[\\}]%n", &x1, &y1, sep, &
len) > 2) {
 
  551                         callbacks->move(priv, x1, y1, x1, y1, -1, -1);
 
  552                 } 
else if (sscanf(buf, 
"\\org(%d,%d)%1[\\}]%n", &x1, &y1, sep, &
len) > 2) {
 
  556                     len = strcspn(buf+1, 
"\\}") + 2;  
 
  583     if (!style || !*style)
 
  
it s the only field you need to keep assuming you have a context There is some magic you don t need to care about around this just let it vf default minimum maximum flags name is the option name
Set of callback functions corresponding to each override codes that can be encountered in a "Dialogue...
static int convert_str(void *dest, const char *buf, int len)
static int is_eol(char buf)
static const ASSConvertFunc convert_func[]
static const OMX_CALLBACKTYPE callbacks
ASSDialog * ff_ass_split_dialog(ASSSplitContext *ctx, const char *buf)
Split one ASS Dialogue line from a string buffer.
static int convert_flt(void *dest, const char *buf, int len)
ASSStyle * styles
array of split out styles
char * style
name of the ASSStyle to use with this dialog
static const char * ass_split_section(ASSSplitContext *ctx, const char *buf)
static void free_section(ASSSplitContext *ctx, const ASSSection *section)
static av_cold void close(AVCodecParserContext *s)
av_cold void ff_ass_split_free(ASSSplitContext *ctx)
Free all the memory allocated for an ASSSplitContext.
it s the only field you need to keep assuming you have a context There is some magic you don t need to care about around this just let it vf type
static int convert_color(void *dest, const char *buf, int len)
void ff_ass_free_dialog(ASSDialog **dialogp)
Free a dialogue obtained from ff_ass_split_dialog().
#define FF_ARRAY_ELEMS(a)
static int convert_alignment(void *dest, const char *buf, int len)
const char * fields_header
void * av_realloc_array(void *ptr, size_t nmemb, size_t size)
static uint8_t * realloc_section_array(ASSSplitContext *ctx)
static const ASSSection ass_sections[]
it s the only field you need to keep assuming you have a context There is some magic you don t need to care about around this field
the definition of that something depends on the semantic of the filter The callback must examine the status of the filter s links and proceed accordingly The status of output links is stored in the status_in and status_out fields and tested by the then the processing requires a frame on this link and the filter is expected to make efforts in that direction The status of input links is stored by the fifo and status_out fields
structure containing the whole split ASS data
fields extracted from the [Script Info] section
static int convert_timestamp(void *dest, const char *buf, int len)
This struct can be casted to ASS to access to the split data.
int(* ASSConvertFunc)(void *dest, const char *buf, int len)
Undefined Behavior In the C some operations are like signed integer dereferencing freed accessing outside allocated Undefined Behavior must not occur in a C it is not safe even if the output of undefined operations is unused The unsafety may seem nit picking but Optimizing compilers have in fact optimized code on the assumption that no undefined Behavior occurs Optimizing code based on wrong assumptions can and has in some cases lead to effects beyond the output of computations The signed integer overflow problem in speed critical code Code which is highly optimized and works with signed integers sometimes has the problem that often the output of the computation does not c
fields extracted from the [V4(+) Styles] section
char * text
actual text which will be displayed as a subtitle, can include style override control codes (see ff_a...
char * name
name of the tyle (case sensitive)
The reader does not expect b to be semantically here and if the code is changed by maybe adding a a division or other the signedness will almost certainly be mistaken To avoid this confusion a new type was SUINT is the C unsigned type but it holds a signed int to use the same example SUINT a
int av_reallocp_array(void *ptr, size_t nmemb, size_t size)
Allocate, reallocate an array through a pointer to a pointer.
it s the only field you need to keep assuming you have a context There is some magic you don t need to care about around this just let it vf offset
ASSStyle * ff_ass_style_get(ASSSplitContext *ctx, const char *style)
Find an ASSStyle structure by its name.
#define i(width, name, range_min, range_max)
#define av_malloc_array(a, b)
void * av_mallocz(size_t size)
Allocate a memory block with alignment suitable for all memory accesses (including vectors if availab...
int styles_count
number of ASSStyle in the styles array
static int convert_int(void *dest, const char *buf, int len)
fields extracted from the [Events] section
static int ass_split(ASSSplitContext *ctx, const char *buf)
static const int16_t alpha[]
#define AVERROR_INVALIDDATA
Invalid data found when processing input.
int ff_ass_split_override_codes(const ASSCodesCallbacks *callbacks, void *priv, const char *buf)
Split override codes out of a ASS "Dialogue" Text field.
const char * format_header
av_cold ASSSplitContext * ff_ass_split(const char *buf)
Split a full ASS file or a ASS header from a string buffer and store the split structure in a newly a...
static const char * skip_space(const char *buf)
int * field_order[FF_ARRAY_ELEMS(ass_sections)]
int field_number[FF_ARRAY_ELEMS(ass_sections)]
static int * get_default_field_orders(const ASSSection *section, int *number)