int write_cc_buffer_as_smptett (struct eia608_screen *data, struct s_write *wb) { unsigned h1,m1,s1,ms1; unsigned h2,m2,s2,ms2; int wrote_something=0; LLONG startms = wb->data608->current_visible_start_ms; startms+=subs_delay; if (startms<0) // Drop screens that because of subs_delay start too early return 0; LLONG endms = get_visible_end()+subs_delay; endms--; // To prevent overlapping with next line. mstotime (startms,&h1,&m1,&s1,&ms1); mstotime (endms-1,&h2,&m2,&s2,&ms2); sprintf ((char *) str,"<p begin=\"%02u:%02u:%02u,%03u\" end=\"%02u:%02u:%02u,%03u\">\n",h1,m1,s1,ms1, h2,m2,s2,ms2); if (encoding!=ENC_UNICODE) { dbg_print(DMT_608, "\r%s\n", str); } enc_buffer_used=encode_line (enc_buffer,(unsigned char *) str); write (wb->fh, enc_buffer,enc_buffer_used); for (int i=0;i<15;i++) { if (data->row_used[i]) { int length = get_decoder_line_encoded (subline, i, data); if (encoding!=ENC_UNICODE) { dbg_print(DMT_608, "\r"); dbg_print(DMT_608, "%s\n",subline); } write (wb->fh, subline, length); wrote_something=1; //if (i!=14) //write (wb->fh, encoded_br, encoded_br_length); write (wb->fh,encoded_crlf, encoded_crlf_length); } } sprintf ((char *) str,"</p>\n"); if (encoding!=ENC_UNICODE) { dbg_print(DMT_608, "\r%s\n", str); } enc_buffer_used=encode_line (enc_buffer,(unsigned char *) str); write (wb->fh, enc_buffer,enc_buffer_used); if (encoding!=ENC_UNICODE) { dbg_print(DMT_608, "\r%s\n", str); } enc_buffer_used=encode_line (enc_buffer,(unsigned char *) str); //write (wb->fh, enc_buffer,enc_buffer_used); return wrote_something; }
int write_cc_buffer_as_sami(struct eia608_screen *data, struct encoder_ctx *context) { int used; LLONG startms, endms; int wrote_something=0; startms = data->start_time; startms+=context->subs_delay; if (startms<0) // Drop screens that because of subs_delay start too early return 0; endms = data->end_time; endms--; // To prevent overlapping with next line. sprintf ((char *) str, "<SYNC start=%llu><P class=\"UNKNOWNCC\">\r\n", (unsigned long long)startms); if (context->encoding != CCX_ENC_UNICODE) { dbg_print(CCX_DMT_DECODER_608, "\r%s\n", str); } used = encode_line(context->buffer,(unsigned char *) str); write (context->out->fh, context->buffer, used); for (int i=0;i<15;i++) { if (data->row_used[i]) { int length = get_decoder_line_encoded (context->subline, i, data); if (context->encoding != CCX_ENC_UNICODE) { dbg_print(CCX_DMT_DECODER_608, "\r"); dbg_print(CCX_DMT_DECODER_608, "%s\n",context->subline); } write (context->out->fh, context->subline, length); wrote_something = 1; if (i!=14) write (context->out->fh, encoded_br, encoded_br_length); write (context->out->fh, encoded_crlf, encoded_crlf_length); } } sprintf ((char *) str,"</P></SYNC>\r\n"); if (context->encoding != CCX_ENC_UNICODE) { dbg_print(CCX_DMT_DECODER_608, "\r%s\n", str); } used = encode_line(context->buffer,(unsigned char *) str); write (context->out->fh, context->buffer, used); sprintf ((char *) str, "<SYNC start=%llu><P class=\"UNKNOWNCC\"> </P></SYNC>\r\n\r\n", (unsigned long long)endms); if (context->encoding!=CCX_ENC_UNICODE) { dbg_print(CCX_DMT_DECODER_608, "\r%s\n", str); } used = encode_line(context->buffer,(unsigned char *) str); write (context->out->fh, context->buffer, used); return wrote_something; }
int write_cc_buffer_as_srt(struct eia608_screen *data, struct encoder_ctx *context) { int used; unsigned h1,m1,s1,ms1; unsigned h2,m2,s2,ms2; LLONG ms_start, ms_end; int wrote_something = 0; ms_start = data->start_time; int prev_line_start=-1, prev_line_end=-1; // Column in which the previous line started and ended, for autodash int prev_line_center1=-1, prev_line_center2=-1; // Center column of previous line text int empty_buf=1; for (int i=0;i<15;i++) { if (data->row_used[i]) { empty_buf=0; break; } } if (empty_buf) // Prevent writing empty screens. Not needed in .srt return 0; ms_start+=context->subs_delay; if (ms_start<0) // Drop screens that because of subs_delay start too early return 0; ms_end = data->end_time; mstotime (ms_start,&h1,&m1,&s1,&ms1); mstotime (ms_end-1,&h2,&m2,&s2,&ms2); // -1 To prevent overlapping with next line. char timeline[128]; context->srt_counter++; sprintf(timeline, "%u%s", context->srt_counter, context->encoded_crlf); used = encode_line(context, context->buffer,(unsigned char *) timeline); write(context->out->fh, context->buffer, used); sprintf (timeline, "%02u:%02u:%02u,%03u --> %02u:%02u:%02u,%03u%s", h1, m1, s1, ms1, h2, m2, s2, ms2, context->encoded_crlf); used = encode_line(context, context->buffer,(unsigned char *) timeline); dbg_print(CCX_DMT_DECODER_608, "\n- - - SRT caption ( %d) - - -\n", context->srt_counter); dbg_print(CCX_DMT_DECODER_608, "%s",timeline); write (context->out->fh, context->buffer, used); for (int i=0;i<15;i++) { if (data->row_used[i]) { if (context->sentence_cap) { capitalize (i,data); correct_case(i,data); } if (context->autodash && context->trim_subs) { int first=0, last=31, center1=-1, center2=-1; unsigned char *line = data->characters[i]; int do_dash=1, colon_pos=-1; find_limit_characters(line,&first,&last); if (first==-1 || last==-1) // Probably a bug somewhere though break; // Is there a speaker named, for example: TOM: What are you doing? for (int j=first;j<=last;j++) { if (line[j]==':') { colon_pos=j; break; } if (!isupper (line[j])) break; } if (prev_line_start==-1) do_dash=0; if (first==prev_line_start) // Case of left alignment do_dash=0; if (last==prev_line_end) // Right align do_dash=0; if (first>prev_line_start && last<prev_line_end) // Fully contained do_dash=0; if ((first>prev_line_start && first<prev_line_end) || // Overlap (last>prev_line_start && last<prev_line_end)) do_dash=0; center1=(first+last)/2; if (colon_pos!=-1) { while (colon_pos<CCX_DECODER_608_SCREEN_WIDTH && (line[colon_pos]==':' || line[colon_pos]==' ' || line[colon_pos]==0x89)) colon_pos++; // Find actual text center2=(colon_pos+last)/2; } else center2=center1; if (center1>=prev_line_center1-1 && center1<=prev_line_center1+1 && center1!=-1) // Center align do_dash=0; if (center2>=prev_line_center2-2 && center1<=prev_line_center2+2 && center1!=-1) // Center align do_dash=0; if (do_dash) write(context->out->fh, "- ", 2); prev_line_start=first; prev_line_end=last; prev_line_center1=center1; prev_line_center2=center2; } int length = get_decoder_line_encoded (context, context->subline, i, data); if (context->encoding!=CCX_ENC_UNICODE) { dbg_print(CCX_DMT_DECODER_608, "\r"); dbg_print(CCX_DMT_DECODER_608, "%s\n",context->subline); } write(context->out->fh, context->subline, length); write(context->out->fh, context->encoded_crlf, context->encoded_crlf_length); wrote_something=1; // fprintf (wb->fh,context->encoded_crlf); } } dbg_print(CCX_DMT_DECODER_608, "- - - - - - - - - - - -\r\n"); // fprintf (wb->fh, context->encoded_crlf); write (context->out->fh, context->encoded_crlf, context->encoded_crlf_length); return wrote_something; }
int write_cc_buffer_as_srt (struct eia608_screen *data, struct s_write *wb) { unsigned h1,m1,s1,ms1; unsigned h2,m2,s2,ms2; int wrote_something = 0; LLONG ms_start= wb->data608->current_visible_start_ms; int empty_buf=1; for (int i=0;i<15;i++) { if (data->row_used[i]) { empty_buf=0; break; } } if (empty_buf) // Prevent writing empty screens. Not needed in .srt return 0; ms_start+=subs_delay; if (ms_start<0) // Drop screens that because of subs_delay start too early return 0; LLONG ms_end = get_visible_end()+subs_delay; mstotime (ms_start,&h1,&m1,&s1,&ms1); mstotime (ms_end-1,&h2,&m2,&s2,&ms2); // -1 To prevent overlapping with next line. char timeline[128]; wb->data608->srt_counter++; sprintf (timeline,"%u\r\n",wb->data608->srt_counter); enc_buffer_used=encode_line (enc_buffer,(unsigned char *) timeline); write (wb->fh, enc_buffer,enc_buffer_used); sprintf (timeline, "%02u:%02u:%02u,%03u --> %02u:%02u:%02u,%03u\r\n", h1,m1,s1,ms1, h2,m2,s2,ms2); enc_buffer_used=encode_line (enc_buffer,(unsigned char *) timeline); dbg_print(DMT_608, "\n- - - SRT caption - - -\n"); dbg_print(DMT_608, "%s",timeline); write (wb->fh, enc_buffer,enc_buffer_used); for (int i=0;i<15;i++) { if (data->row_used[i]) { if (sentence_cap) { capitalize (i,data); correct_case(i,data); } int length = get_decoder_line_encoded (subline, i, data); if (encoding!=ENC_UNICODE) { dbg_print(DMT_608, "\r"); dbg_print(DMT_608, "%s\n",subline); } write (wb->fh, subline, length); write (wb->fh, encoded_crlf, encoded_crlf_length); wrote_something=1; // fprintf (wb->fh,encoded_crlf); } } dbg_print(DMT_608, "- - - - - - - - - - - -\r\n"); // fprintf (wb->fh, encoded_crlf); write (wb->fh, encoded_crlf, encoded_crlf_length); return wrote_something; }
int spupng_write_ccbuffer(struct spupng_t *sp, struct eia608_screen* data, struct encoder_ctx *context) { int row; int empty_buf = 1; char str[256] = ""; int str_len = 0; LLONG ms_start = data->start_time + context->subs_delay; if (ms_start < 0) { dbg_print(CCX_DMT_VERBOSE, "Negative start\n"); return 0; } for (row = 0; row < 15; row++) { if (data->row_used[row]) { empty_buf = 0; break; } } if (empty_buf) { dbg_print(CCX_DMT_VERBOSE, "Blank page\n"); return 0; } LLONG ms_end = data->end_time; sprintf(sp->pngfile, "%s/sub%04d.png", sp->dirname, sp->fileIndex++); if ((sp->fppng = fopen(sp->pngfile, "wb")) == NULL) { fatal(CCX_COMMON_EXIT_FILE_CREATION_FAILED, "Cannot open %s: %s\n", sp->pngfile, strerror(errno)); } if (!spupng_export_png(sp, data)) { fatal(CCX_COMMON_EXIT_FILE_CREATION_FAILED, "Cannot write %s: %s\n", sp->pngfile, strerror(errno)); } fclose(sp->fppng); write_sputag(sp,ms_start,ms_end); for (row = 0; row < ROWS; row++) { if (data->row_used[row]) { int len = get_decoder_line_encoded(context, context->subline, row, data); // Check for characters that spumux won't parse // null chars will be changed to space // pairs of dashes will be changed to underscores for (unsigned char* ptr = context->subline; ptr < context->subline+len; ptr++) { switch (*ptr) { case 0: *ptr = ' '; break; case '-': if (*(ptr+1) == '-') { *ptr++ = '_'; *ptr = '_'; } break; } } if (str_len + len + 3 > 256 ) { mprint("WARNING: Possible Loss of data\n"); break; } strncat(str, (const char*)context->subline, len); strncat(str,"\n",3); str_len = str_len + len + 2; } } write_spucomment(sp,str); return 1; }