You've already forked FFmpeg
							
							
				mirror of
				https://github.com/FFmpeg/FFmpeg.git
				synced 2025-10-30 23:18:11 +02:00 
			
		
		
		
	avcodec: Remove deprecated ASS with inline timing
Deprecated in 22ebbda637.
Signed-off-by: Andreas Rheinhardt <andreas.rheinhardt@gmail.com>
Signed-off-by: James Almer <jamrial@gmail.com>
			
			
This commit is contained in:
		
				
					committed by
					
						 James Almer
						James Almer
					
				
			
			
				
	
			
			
			
						parent
						
							cb172ae9ab
						
					
				
				
					commit
					1f63665ca5
				
			| @@ -27,10 +27,6 @@ | ||||
| #include "libavutil/internal.h" | ||||
| #include "libavutil/mem.h" | ||||
|  | ||||
| typedef struct { | ||||
|     int id; ///< current event id, ReadOrder field | ||||
| } ASSEncodeContext; | ||||
|  | ||||
| static av_cold int ass_encode_init(AVCodecContext *avctx) | ||||
| { | ||||
|     avctx->extradata = av_malloc(avctx->subtitle_header_size + 1); | ||||
| @@ -46,49 +42,16 @@ static int ass_encode_frame(AVCodecContext *avctx, | ||||
|                             unsigned char *buf, int bufsize, | ||||
|                             const AVSubtitle *sub) | ||||
| { | ||||
|     ASSEncodeContext *s = avctx->priv_data; | ||||
|     int i, len, total_len = 0; | ||||
|  | ||||
|     for (i=0; i<sub->num_rects; i++) { | ||||
|         char ass_line[2048]; | ||||
|         const char *ass = sub->rects[i]->ass; | ||||
|         long int layer; | ||||
|         char *p; | ||||
|  | ||||
|         if (sub->rects[i]->type != SUBTITLE_ASS) { | ||||
|             av_log(avctx, AV_LOG_ERROR, "Only SUBTITLE_ASS type supported.\n"); | ||||
|             return AVERROR(EINVAL); | ||||
|         } | ||||
|  | ||||
| #if FF_API_ASS_TIMING | ||||
|         if (!strncmp(ass, "Dialogue: ", 10)) { | ||||
|             if (i > 0) { | ||||
|                 av_log(avctx, AV_LOG_ERROR, "ASS encoder supports only one " | ||||
|                        "ASS rectangle field.\n"); | ||||
|                 return AVERROR_INVALIDDATA; | ||||
|             } | ||||
|  | ||||
|             ass += 10; // skip "Dialogue: " | ||||
|             /* parse Layer field. If it's a Marked field, the content | ||||
|              * will be "Marked=N" instead of the layer num, so we will | ||||
|              * have layer=0, which is fine. */ | ||||
|             layer = strtol(ass, &p, 10); | ||||
|  | ||||
| #define SKIP_ENTRY(ptr) do {        \ | ||||
|     char *sep = strchr(ptr, ',');   \ | ||||
|     if (sep)                        \ | ||||
|         ptr = sep + 1;              \ | ||||
| } while (0) | ||||
|  | ||||
|             SKIP_ENTRY(p); // skip layer or marked | ||||
|             SKIP_ENTRY(p); // skip start timestamp | ||||
|             SKIP_ENTRY(p); // skip end timestamp | ||||
|             snprintf(ass_line, sizeof(ass_line), "%d,%ld,%s", ++s->id, layer, p); | ||||
|             ass_line[strcspn(ass_line, "\r\n")] = 0; | ||||
|             ass = ass_line; | ||||
|         } | ||||
| #endif | ||||
|  | ||||
|         len = av_strlcpy(buf+total_len, ass, bufsize-total_len); | ||||
|  | ||||
|         if (len > bufsize-total_len-1) { | ||||
| @@ -110,7 +73,6 @@ AVCodec ff_ssa_encoder = { | ||||
|     .id           = AV_CODEC_ID_ASS, | ||||
|     .init         = ass_encode_init, | ||||
|     .encode_sub   = ass_encode_frame, | ||||
|     .priv_data_size = sizeof(ASSEncodeContext), | ||||
| }; | ||||
| #endif | ||||
|  | ||||
| @@ -122,6 +84,5 @@ AVCodec ff_ass_encoder = { | ||||
|     .id           = AV_CODEC_ID_ASS, | ||||
|     .init         = ass_encode_init, | ||||
|     .encode_sub   = ass_encode_frame, | ||||
|     .priv_data_size = sizeof(ASSEncodeContext), | ||||
| }; | ||||
| #endif | ||||
|   | ||||
| @@ -2047,9 +2047,6 @@ typedef struct AVCodecContext { | ||||
|      */ | ||||
|     int sub_text_format; | ||||
| #define FF_SUB_TEXT_FMT_ASS              0 | ||||
| #if FF_API_ASS_TIMING | ||||
| #define FF_SUB_TEXT_FMT_ASS_WITH_TIMINGS 1 | ||||
| #endif | ||||
|  | ||||
|     /** | ||||
|      * Audio only. The amount of padding (in samples) appended by the encoder to | ||||
|   | ||||
| @@ -949,79 +949,6 @@ static int utf8_check(const uint8_t *str) | ||||
|     return 1; | ||||
| } | ||||
|  | ||||
| #if FF_API_ASS_TIMING | ||||
| static void insert_ts(AVBPrint *buf, int ts) | ||||
| { | ||||
|     if (ts == -1) { | ||||
|         av_bprintf(buf, "9:59:59.99,"); | ||||
|     } else { | ||||
|         int h, m, s; | ||||
|  | ||||
|         h = ts/360000;  ts -= 360000*h; | ||||
|         m = ts/  6000;  ts -=   6000*m; | ||||
|         s = ts/   100;  ts -=    100*s; | ||||
|         av_bprintf(buf, "%d:%02d:%02d.%02d,", h, m, s, ts); | ||||
|     } | ||||
| } | ||||
|  | ||||
| static int convert_sub_to_old_ass_form(AVSubtitle *sub, const AVPacket *pkt, AVRational tb) | ||||
| { | ||||
|     int i; | ||||
|     AVBPrint buf; | ||||
|  | ||||
|     av_bprint_init(&buf, 0, AV_BPRINT_SIZE_UNLIMITED); | ||||
|  | ||||
|     for (i = 0; i < sub->num_rects; i++) { | ||||
|         char *final_dialog; | ||||
|         const char *dialog; | ||||
|         AVSubtitleRect *rect = sub->rects[i]; | ||||
|         int ts_start, ts_duration = -1; | ||||
|         long int layer; | ||||
|  | ||||
|         if (rect->type != SUBTITLE_ASS || !strncmp(rect->ass, "Dialogue: ", 10)) | ||||
|             continue; | ||||
|  | ||||
|         av_bprint_clear(&buf); | ||||
|  | ||||
|         /* skip ReadOrder */ | ||||
|         dialog = strchr(rect->ass, ','); | ||||
|         if (!dialog) | ||||
|             continue; | ||||
|         dialog++; | ||||
|  | ||||
|         /* extract Layer or Marked */ | ||||
|         layer = strtol(dialog, (char**)&dialog, 10); | ||||
|         if (*dialog != ',') | ||||
|             continue; | ||||
|         dialog++; | ||||
|  | ||||
|         /* rescale timing to ASS time base (ms) */ | ||||
|         ts_start = av_rescale_q(pkt->pts, tb, av_make_q(1, 100)); | ||||
|         if (pkt->duration != -1) | ||||
|             ts_duration = av_rescale_q(pkt->duration, tb, av_make_q(1, 100)); | ||||
|         sub->end_display_time = FFMAX(sub->end_display_time, 10 * ts_duration); | ||||
|  | ||||
|         /* construct ASS (standalone file form with timestamps) string */ | ||||
|         av_bprintf(&buf, "Dialogue: %ld,", layer); | ||||
|         insert_ts(&buf, ts_start); | ||||
|         insert_ts(&buf, ts_duration == -1 ? -1 : ts_start + ts_duration); | ||||
|         av_bprintf(&buf, "%s\r\n", dialog); | ||||
|  | ||||
|         final_dialog = av_strdup(buf.str); | ||||
|         if (!av_bprint_is_complete(&buf) || !final_dialog) { | ||||
|             av_freep(&final_dialog); | ||||
|             av_bprint_finalize(&buf, NULL); | ||||
|             return AVERROR(ENOMEM); | ||||
|         } | ||||
|         av_freep(&rect->ass); | ||||
|         rect->ass = final_dialog; | ||||
|     } | ||||
|  | ||||
|     av_bprint_finalize(&buf, NULL); | ||||
|     return 0; | ||||
| } | ||||
| #endif | ||||
|  | ||||
| int avcodec_decode_subtitle2(AVCodecContext *avctx, AVSubtitle *sub, | ||||
|                              int *got_sub_ptr, | ||||
|                              AVPacket *avpkt) | ||||
| @@ -1057,17 +984,6 @@ int avcodec_decode_subtitle2(AVCodecContext *avctx, AVSubtitle *sub, | ||||
|         av_assert1((ret >= 0) >= !!*got_sub_ptr && | ||||
|                    !!*got_sub_ptr >= !!sub->num_rects); | ||||
|  | ||||
| #if FF_API_ASS_TIMING | ||||
|         if (avctx->sub_text_format == FF_SUB_TEXT_FMT_ASS_WITH_TIMINGS | ||||
|             && *got_sub_ptr && sub->num_rects) { | ||||
|             const AVRational tb = avctx->pkt_timebase.num ? avctx->pkt_timebase | ||||
|                                   : avctx->time_base; | ||||
|             int err = convert_sub_to_old_ass_form(sub, avpkt, tb); | ||||
|             if (err < 0) | ||||
|                 ret = err; | ||||
|         } | ||||
| #endif | ||||
|  | ||||
|         if (sub->num_rects && !sub->end_display_time && avpkt->duration && | ||||
|             avctx->pkt_timebase.num) { | ||||
|             AVRational ms = { 1, 1000 }; | ||||
|   | ||||
| @@ -655,25 +655,12 @@ static int mov_text_encode_frame(AVCodecContext *avctx, unsigned char *buf, | ||||
|             return AVERROR(EINVAL); | ||||
|         } | ||||
|  | ||||
| #if FF_API_ASS_TIMING | ||||
|         if (!strncmp(ass, "Dialogue: ", 10)) { | ||||
|             int num; | ||||
|             dialog = ff_ass_split_dialog(s->ass_ctx, ass, 0, &num); | ||||
|             for (; dialog && num--; dialog++) { | ||||
|                 mov_text_dialog(s, dialog); | ||||
|                 ff_ass_split_override_codes(&mov_text_callbacks, s, dialog->text); | ||||
|             } | ||||
|         } else { | ||||
| #endif | ||||
|             dialog = ff_ass_split_dialog2(s->ass_ctx, ass); | ||||
|             if (!dialog) | ||||
|                 return AVERROR(ENOMEM); | ||||
|             mov_text_dialog(s, dialog); | ||||
|             ff_ass_split_override_codes(&mov_text_callbacks, s, dialog->text); | ||||
|             ff_ass_free_dialog(&dialog); | ||||
| #if FF_API_ASS_TIMING | ||||
|         } | ||||
| #endif | ||||
|  | ||||
|         for (j = 0; j < box_count; j++) { | ||||
|             box_types[j].encode(s); | ||||
|   | ||||
| @@ -366,15 +366,8 @@ static const AVOption avcodec_options[] = { | ||||
| {"auto",        NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_SUB_CHARENC_MODE_AUTOMATIC},   INT_MIN, INT_MAX, S|D, "sub_charenc_mode"}, | ||||
| {"pre_decoder", NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_SUB_CHARENC_MODE_PRE_DECODER}, INT_MIN, INT_MAX, S|D, "sub_charenc_mode"}, | ||||
| {"ignore",      NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_SUB_CHARENC_MODE_IGNORE},      INT_MIN, INT_MAX, S|D, "sub_charenc_mode"}, | ||||
| #if FF_API_ASS_TIMING | ||||
| {"sub_text_format", "set decoded text subtitle format", OFFSET(sub_text_format), AV_OPT_TYPE_INT, {.i64 = FF_SUB_TEXT_FMT_ASS_WITH_TIMINGS}, 0, 1, S|D, "sub_text_format"}, | ||||
| #else | ||||
| {"sub_text_format", "set decoded text subtitle format", OFFSET(sub_text_format), AV_OPT_TYPE_INT, {.i64 = FF_SUB_TEXT_FMT_ASS}, 0, 1, S|D, "sub_text_format"}, | ||||
| #endif | ||||
| {"ass",              NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_SUB_TEXT_FMT_ASS},              INT_MIN, INT_MAX, S|D, "sub_text_format"}, | ||||
| #if FF_API_ASS_TIMING | ||||
| {"ass_with_timings", NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_SUB_TEXT_FMT_ASS_WITH_TIMINGS}, INT_MIN, INT_MAX, S|D, "sub_text_format"}, | ||||
| #endif | ||||
| #if FF_API_OLD_ENCDEC | ||||
| {"refcounted_frames", NULL, OFFSET(refcounted_frames), AV_OPT_TYPE_BOOL, {.i64 = 0}, 0, 1, A|V|D }, | ||||
| #endif | ||||
|   | ||||
| @@ -244,18 +244,6 @@ static int encode_frame(AVCodecContext *avctx, | ||||
|             return AVERROR(EINVAL); | ||||
|         } | ||||
|  | ||||
| #if FF_API_ASS_TIMING | ||||
|         if (!strncmp(ass, "Dialogue: ", 10)) { | ||||
|             int num; | ||||
|             dialog = ff_ass_split_dialog(s->ass_ctx, ass, 0, &num); | ||||
|             for (; dialog && num--; dialog++) { | ||||
|                 s->alignment_applied = 0; | ||||
|                 if (avctx->codec_id == AV_CODEC_ID_SUBRIP) | ||||
|                     srt_style_apply(s, dialog->style); | ||||
|                 ff_ass_split_override_codes(cb, s, dialog->text); | ||||
|             } | ||||
|         } else { | ||||
| #endif | ||||
|             dialog = ff_ass_split_dialog2(s->ass_ctx, ass); | ||||
|             if (!dialog) | ||||
|                 return AVERROR(ENOMEM); | ||||
| @@ -264,9 +252,6 @@ static int encode_frame(AVCodecContext *avctx, | ||||
|                 srt_style_apply(s, dialog->style); | ||||
|             ff_ass_split_override_codes(cb, s, dialog->text); | ||||
|             ff_ass_free_dialog(&dialog); | ||||
| #if FF_API_ASS_TIMING | ||||
|         } | ||||
| #endif | ||||
|     } | ||||
|  | ||||
|     if (!av_bprint_is_complete(&s->buffer)) | ||||
|   | ||||
| @@ -94,42 +94,6 @@ static int ttml_encode_frame(AVCodecContext *avctx, uint8_t *buf, | ||||
|             return AVERROR(EINVAL); | ||||
|         } | ||||
|  | ||||
| #if FF_API_ASS_TIMING | ||||
|         if (!strncmp(ass, "Dialogue: ", 10)) { | ||||
|             int num; | ||||
|             dialog = ff_ass_split_dialog(s->ass_ctx, ass, 0, &num); | ||||
|  | ||||
|             for (; dialog && num--; dialog++) { | ||||
|                 if (dialog->style) { | ||||
|                     av_bprintf(&s->buffer, "<span region=\""); | ||||
|                     av_bprint_escape(&s->buffer, dialog->style, NULL, | ||||
|                                      AV_ESCAPE_MODE_XML, | ||||
|                                      AV_ESCAPE_FLAG_XML_DOUBLE_QUOTES); | ||||
|                     av_bprintf(&s->buffer, "\">"); | ||||
|                 } | ||||
|  | ||||
|                 { | ||||
|                     int ret = ff_ass_split_override_codes(&ttml_callbacks, s, | ||||
|                                                           dialog->text); | ||||
|                     int log_level = (ret != AVERROR_INVALIDDATA || | ||||
|                                      avctx->err_recognition & AV_EF_EXPLODE) ? | ||||
|                                     AV_LOG_ERROR : AV_LOG_WARNING; | ||||
|  | ||||
|                     if (ret < 0) { | ||||
|                         av_log(avctx, log_level, | ||||
|                                "Splitting received ASS dialog failed: %s\n", | ||||
|                                av_err2str(ret)); | ||||
|  | ||||
|                         if (log_level == AV_LOG_ERROR) | ||||
|                             return ret; | ||||
|                     } | ||||
|                 } | ||||
|  | ||||
|                 if (dialog->style) | ||||
|                     av_bprintf(&s->buffer, "</span>"); | ||||
|             } | ||||
|         } else { | ||||
| #endif | ||||
|             dialog = ff_ass_split_dialog2(s->ass_ctx, ass); | ||||
|             if (!dialog) | ||||
|                 return AVERROR(ENOMEM); | ||||
| @@ -166,9 +130,6 @@ static int ttml_encode_frame(AVCodecContext *avctx, uint8_t *buf, | ||||
|  | ||||
|                 ff_ass_free_dialog(&dialog); | ||||
|             } | ||||
| #if FF_API_ASS_TIMING | ||||
|         } | ||||
| #endif | ||||
|     } | ||||
|  | ||||
|     if (!av_bprint_is_complete(&s->buffer)) | ||||
|   | ||||
| @@ -63,9 +63,6 @@ | ||||
| #ifndef FF_API_VBV_DELAY | ||||
| #define FF_API_VBV_DELAY         (LIBAVCODEC_VERSION_MAJOR < 59) | ||||
| #endif | ||||
| #ifndef FF_API_ASS_TIMING | ||||
| #define FF_API_ASS_TIMING       (LIBAVCODEC_VERSION_MAJOR < 59) | ||||
| #endif | ||||
| #ifndef FF_API_COPY_CONTEXT | ||||
| #define FF_API_COPY_CONTEXT     (LIBAVCODEC_VERSION_MAJOR < 59) | ||||
| #endif | ||||
|   | ||||
| @@ -171,26 +171,12 @@ static int webvtt_encode_frame(AVCodecContext *avctx, | ||||
|             return AVERROR(EINVAL); | ||||
|         } | ||||
|  | ||||
| #if FF_API_ASS_TIMING | ||||
|         if (!strncmp(ass, "Dialogue: ", 10)) { | ||||
|             int num; | ||||
|             dialog = ff_ass_split_dialog(s->ass_ctx, ass, 0, &num); | ||||
|             // TODO reindent | ||||
|         for (; dialog && num--; dialog++) { | ||||
|             webvtt_style_apply(s, dialog->style); | ||||
|             ff_ass_split_override_codes(&webvtt_callbacks, s, dialog->text); | ||||
|         } | ||||
|         } else { | ||||
| #endif | ||||
|             dialog = ff_ass_split_dialog2(s->ass_ctx, ass); | ||||
|             if (!dialog) | ||||
|                 return AVERROR(ENOMEM); | ||||
|             webvtt_style_apply(s, dialog->style); | ||||
|             ff_ass_split_override_codes(&webvtt_callbacks, s, dialog->text); | ||||
|             ff_ass_free_dialog(&dialog); | ||||
| #if FF_API_ASS_TIMING | ||||
|         } | ||||
| #endif | ||||
|     } | ||||
|  | ||||
|     if (!av_bprint_is_complete(&s->buffer)) | ||||
|   | ||||
		Reference in New Issue
	
	Block a user