Index: libhb/muxmp4.c =================================================================== --- libhb/muxmp4.c (revision 2844) +++ libhb/muxmp4.c (working copy) @@ -534,6 +534,7 @@ enum style_s {ITALIC, BOLD, UNDERLINE} style; uint16_t start; uint16_t stop; + uint16_t utf8_count; struct stylerecord_s *next; } stylerecord; @@ -599,10 +600,28 @@ uint8_t *reader = input; uint8_t *writer = output; uint8_t stylecount = 0; + uint16_t utf8_count = 0; // utf8 count from start of subtitle stylerecord *stylestack = NULL; stylerecord *oldrecord = NULL; while(*reader != '\0') { + if( ( *reader & 0xc0 ) == 0x80 ) + { + /* + * Track the utf8_count when doing markup so that we get the tx3g stops + * based on UTF8 chr counts rather than bytes. + */ + utf8_count++; + if( stylestack ) + { + stylestack->utf8_count++; + hb_deep_log( 3, "MuxMP4: Counted %d UTF-8 chrs within style", + stylestack->utf8_count, + utf8_count); + } + hb_deep_log( 3, "MuxMP4: Counted %d UTF-8 chrs within subtitle so far", + utf8_count); + } if (*reader == '<') { /* * possible markup, peek at the next chr @@ -611,7 +630,7 @@ case 'i': if (*(reader+2) == '>') { reader += 3; - hb_makestylerecord(&stylestack, ITALIC, writer-output); + hb_makestylerecord(&stylestack, ITALIC, (writer - output - utf8_count)); } else { *writer++ = *reader++; } @@ -619,7 +638,7 @@ case 'b': if (*(reader+2) == '>') { reader += 3; - hb_makestylerecord(&stylestack, BOLD, writer-output); + hb_makestylerecord(&stylestack, BOLD, (writer - output - utf8_count)); } else { *writer++ = *reader++; } @@ -627,7 +646,7 @@ case 'u': if (*(reader+2) == '>') { reader += 3; - hb_makestylerecord(&stylestack, UNDERLINE, writer-output); + hb_makestylerecord(&stylestack, UNDERLINE, (writer - output - utf8_count)); } else { *writer++ = *reader++; } @@ -638,7 +657,7 @@ if (*(reader+3) == '>') { if (stylestack && stylestack->style == ITALIC) { uint8_t style_record[12]; - stylestack->stop = writer - output; + stylestack->stop = writer - output - stylestack->utf8_count; hb_makestyleatom(stylestack, style_record); memcpy(style + 10 + (12 * stylecount), style_record, 12); @@ -646,6 +665,13 @@ oldrecord = stylestack; stylestack = stylestack->next; + /* + * Embedded utf8 chrs must be maintained up the stack. + */ + if( stylestack ) + { + stylestack->utf8_count += oldrecord->utf8_count; + } free(oldrecord); } else { hb_error("Mismatched Subtitle markup '%s'", input); @@ -659,13 +685,20 @@ if (*(reader+3) == '>') { if (stylestack && stylestack->style == BOLD) { uint8_t style_record[12]; - stylestack->stop = writer - output; + stylestack->stop = writer - output - stylestack->utf8_count; hb_makestyleatom(stylestack, style_record); memcpy(style + 10 + (12 * stylecount), style_record, 12); stylecount++; oldrecord = stylestack; stylestack = stylestack->next; + /* + * Embedded utf8 chrs must be maintained up the stack. + */ + if( stylestack ) + { + stylestack->utf8_count += oldrecord->utf8_count; + } free(oldrecord); } else { hb_error("Mismatched Subtitle markup '%s'", input); @@ -680,7 +713,7 @@ if (*(reader+3) == '>') { if (stylestack && stylestack->style == UNDERLINE) { uint8_t style_record[12]; - stylestack->stop = writer - output; + stylestack->stop = writer - output - stylestack->utf8_count; hb_makestyleatom(stylestack, style_record); memcpy(style + 10 + (12 * stylecount), style_record, 12); @@ -688,6 +721,13 @@ oldrecord = stylestack; stylestack = stylestack->next; + /* + * Embedded utf8 chrs must be maintained up the stack. + */ + if( stylestack ) + { + stylestack->utf8_count += oldrecord->utf8_count; + } free(oldrecord); } else { hb_error("Mismatched Subtitle markup '%s'", input); @@ -928,7 +968,6 @@ } mux_data->sum_dur += (buf->stop - buf->start); - hb_deep_log(3, "MuxMP4:Total time elapsed:%"PRId64, mux_data->sum_dur); } } else