From patchwork Wed Apr 14 06:57:23 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Jan_Ekstr=C3=B6m?= X-Patchwork-Id: 26904 Return-Path: X-Original-To: patchwork@ffaux-bg.ffmpeg.org Delivered-To: patchwork@ffaux-bg.ffmpeg.org Received: from ffbox0-bg.mplayerhq.hu (ffbox0-bg.ffmpeg.org [79.124.17.100]) by ffaux.localdomain (Postfix) with ESMTP id 9DB3944A19D for ; Wed, 14 Apr 2021 10:06:00 +0300 (EEST) Received: from [127.0.1.1] (localhost [127.0.0.1]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTP id 766A868A761; Wed, 14 Apr 2021 10:06:00 +0300 (EEST) X-Original-To: ffmpeg-devel@ffmpeg.org Delivered-To: ffmpeg-devel@ffmpeg.org Received: from mail-wr1-f51.google.com (mail-wr1-f51.google.com [209.85.221.51]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTPS id 512C168A71D for ; Wed, 14 Apr 2021 10:05:54 +0300 (EEST) Received: by mail-wr1-f51.google.com with SMTP id j5so17790775wrn.4 for ; Wed, 14 Apr 2021 00:05:54 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=W2muOHdSrbSS04FtduUOCnHO6V4VHxF9ge7uIw5Jg+8=; b=rI9IM4af2rP3ETyPPCoyq/T4ghNEw6pILkvMNZlXfZzapvzhpDK8huoyw4C5CEBC2/ kLBRtXvxjjF3VwXQFufd91BCvesmvoVu85rBL3jm8DwBiQ6oPcS4hoQ99xF9Sz1LqJ6r uMUnTEGJ7b2Kdu4orcXaTFCIFvJyvuu5HEd2MTubelA8taYqO6ubjYNMGp5JGQCMH9Q1 mceIRwxlRUpiusUHqJOAPkav+4JPlHu1U9k1xn1nM4km4yr2AMqWguN3wpCvZh3JgaOC NPgI0cIWd5LSCdobtZK8yjanf9c5om58ZKCvQTdpzN9kvlM2rZML7MNw4PiTiEmV6hb8 grgA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=W2muOHdSrbSS04FtduUOCnHO6V4VHxF9ge7uIw5Jg+8=; b=sCS3lEw0n3raYilgKJ6583chtjkj9yzAwCxkVY8Zz1zl9ZND/BpNFtl0nCilEFceMB NGkmOjz+Nj0dZqKpGjmwJxGF2un4TIhxvN5MgZqUqw0n5IofEcHup4K7gQt2Keaqfd/J LP5USzcC/09kUsoBWPl+enm8A6hKqpuPh1aj3Pe5K5glGUXlbFZAYVjI3nJCIBUy9LMK h82qf4EcRvdC4O2eLmo24qATyrkCsbB2vrkO1Y0lnpcQva5kdpvDPorLdhm8lKL21bb9 NQFvwdBkmMNLDSWmhSuX8Ik7cugQw1kNwPov0hWWEVcnvA7PhWmuz3iTqGtjOkfV9Xxm lWkg== X-Gm-Message-State: AOAM5316I2zfJYJTP4aIkLSeMnpdBOMmXbBoxlrthN64Tzi14K3ao/3W 9ICukaxYE8yMZd461wx08wQ15usWCHY= X-Google-Smtp-Source: ABdhPJy5FKkv+9shvt7iIBB5B73QRocqoj3lMgDBsw5je1M1lQ9iFy8MvbnfClx2czG4iIuBfj9ABg== X-Received: by 2002:a19:3849:: with SMTP id d9mr6410253lfj.388.1618383449802; Tue, 13 Apr 2021 23:57:29 -0700 (PDT) Received: from localhost.localdomain (91-159-194-103.elisa-laajakaista.fi. [91.159.194.103]) by smtp.gmail.com with ESMTPSA id w5sm4960167ljo.11.2021.04.13.23.57.29 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 13 Apr 2021 23:57:29 -0700 (PDT) From: =?utf-8?q?Jan_Ekstr=C3=B6m?= To: ffmpeg-devel@ffmpeg.org Date: Wed, 14 Apr 2021 09:57:23 +0300 Message-Id: <20210414065725.8828-3-jeebjp@gmail.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20210414065725.8828-1-jeebjp@gmail.com> References: <20210414065725.8828-1-jeebjp@gmail.com> MIME-Version: 1.0 Subject: [FFmpeg-devel] [PATCH v2 2/4] avformat/ttmlenc: enable writing out additional header values X-BeenThere: ffmpeg-devel@ffmpeg.org X-Mailman-Version: 2.1.20 Precedence: list List-Id: FFmpeg development discussions and patches List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Reply-To: FFmpeg development discussions and patches Errors-To: ffmpeg-devel-bounces@ffmpeg.org Sender: "ffmpeg-devel" From: Jan Ekström This way the encoder may pass on the following values to the muxer: 1) Additional root "tt" element attributes, such as the subtitle canvas reference size. 2) Anything before the body element of the document, such as regions in the head element, which can configure styles. Signed-off-by: Jan Ekström --- libavcodec/ttmlenc.h | 5 ++++ libavformat/ttmlenc.c | 70 +++++++++++++++++++++++++++++++++++++++---- 2 files changed, 70 insertions(+), 5 deletions(-) diff --git a/libavcodec/ttmlenc.h b/libavcodec/ttmlenc.h index c1dd5ec990..c3bb11478d 100644 --- a/libavcodec/ttmlenc.h +++ b/libavcodec/ttmlenc.h @@ -25,4 +25,9 @@ #define TTMLENC_EXTRADATA_SIGNATURE "lavc-ttmlenc" #define TTMLENC_EXTRADATA_SIGNATURE_SIZE (sizeof(TTMLENC_EXTRADATA_SIGNATURE) - 1) +static const char ttml_default_namespacing[] = +" xmlns=\"http://www.w3.org/ns/ttml\"\n" +" xmlns:ttm=\"http://www.w3.org/ns/ttml#metadata\"\n" +" xmlns:tts=\"http://www.w3.org/ns/ttml#styling\"\n"; + #endif /* AVCODEC_TTMLENC_H */ diff --git a/libavformat/ttmlenc.c b/libavformat/ttmlenc.c index 940f8bbd4e..34a0107a14 100644 --- a/libavformat/ttmlenc.c +++ b/libavformat/ttmlenc.c @@ -37,6 +37,11 @@ enum TTMLPacketType { PACKET_TYPE_DOCUMENT, }; +struct TTMLHeaderParameters { + const char *tt_element_params; + const char *pre_body_elements; +}; + typedef struct TTMLMuxContext { enum TTMLPacketType input_type; unsigned int document_written; @@ -45,10 +50,9 @@ typedef struct TTMLMuxContext { static const char ttml_header_text[] = "\n" "\n" +"%s" " \n" "
\n"; @@ -72,6 +76,48 @@ static void ttml_write_time(AVIOContext *pb, const char tag[], tag, hour, min, sec, millisec); } +static int ttml_set_header_values_from_extradata( + AVCodecParameters *par, struct TTMLHeaderParameters *header_params) +{ + size_t additional_data_size = + par->extradata_size - TTMLENC_EXTRADATA_SIGNATURE_SIZE; + char *value = + (char *)par->extradata + TTMLENC_EXTRADATA_SIGNATURE_SIZE; + size_t value_size = av_strnlen(value, additional_data_size); + struct TTMLHeaderParameters local_params = { 0 }; + + if (!additional_data_size) { + // simple case, we don't have to go through local_params and just + // set default fall-back values (for old extradata format). + header_params->tt_element_params = ttml_default_namespacing; + header_params->pre_body_elements = ""; + + return 0; + } + + if (value_size == additional_data_size || + value[value_size] != '\0') + return AVERROR_INVALIDDATA; + + local_params.tt_element_params = value; + + additional_data_size -= value_size + 1; + value += value_size + 1; + if (!additional_data_size) + return AVERROR_INVALIDDATA; + + value_size = av_strnlen(value, additional_data_size); + if (value_size == additional_data_size || + value[value_size] != '\0') + return AVERROR_INVALIDDATA; + + local_params.pre_body_elements = value; + + *header_params = local_params; + + return 0; +} + static int ttml_write_header(AVFormatContext *ctx) { TTMLMuxContext *ttml_ctx = ctx->priv_data; @@ -103,8 +149,22 @@ static int ttml_write_header(AVFormatContext *ctx) avpriv_set_pts_info(st, 64, 1, 1000); - if (ttml_ctx->input_type == PACKET_TYPE_PARAGRAPH) - avio_printf(pb, ttml_header_text, printed_lang); + if (ttml_ctx->input_type == PACKET_TYPE_PARAGRAPH) { + struct TTMLHeaderParameters header_params; + int ret = ttml_set_header_values_from_extradata( + st->codecpar, &header_params); + if (ret < 0) { + av_log(ctx, AV_LOG_ERROR, + "Failed to parse TTML header values from extradata: " + "%s!\n", av_err2str(ret)); + return ret; + } + + avio_printf(pb, ttml_header_text, + header_params.tt_element_params, + printed_lang, + header_params.pre_body_elements); + } } return 0;