diff options
author | Tobias Rapp <t.rapp@noa-audio.com> | 2011-11-02 14:50:14 +0400 |
---|---|---|
committer | Michael Niedermayer <michaelni@gmx.at> | 2011-11-02 17:33:55 +0400 |
commit | f2e7ee9bf968d82dbcdc08837fc56db27923694f (patch) | |
tree | ce3805c8ba75379feb662e86db47226b8ed9c751 | |
parent | 971e7104381fbb30686041506ff0ed752d9d1697 (diff) |
id3v2enc: add support for year and day/month tags when writing id3v2 version 3 metadata
Adds support for year (TYER) and day/month (TDAT) tags when writing
id3v2 version 3 metadata by splitting the "date" tag. The date tag
should have a format of "YYYY-MM-DD" or "YYYY".
Signed-off-by: Michael Niedermayer <michaelni@gmx.at>
-rw-r--r-- | libavformat/id3v2enc.c | 43 |
1 files changed, 42 insertions, 1 deletions
diff --git a/libavformat/id3v2enc.c b/libavformat/id3v2enc.c index 4e1cd75c79..d50a751b26 100644 --- a/libavformat/id3v2enc.c +++ b/libavformat/id3v2enc.c @@ -20,6 +20,7 @@ #include <stdint.h> +#include "libavutil/avstring.h" #include "libavutil/dict.h" #include "libavutil/intreadwrite.h" #include "avformat.h" @@ -97,6 +98,44 @@ static int id3v2_check_write_tag(AVFormatContext *s, AVDictionaryEntry *t, const return -1; } +static void id3v2_3_metadata_split_date(AVDictionary **pm) +{ + AVDictionaryEntry *mtag = NULL; + AVDictionary *dst = NULL; + const char *key, *value; + char year[5] = {0}, day_month[5] = {0}; + int i; + + while ((mtag = av_dict_get(*pm, "", mtag, AV_DICT_IGNORE_SUFFIX))) { + key = mtag->key; + if (!strcasecmp(key, "date")) { + /* split date tag using "YYYY-MM-DD" format into year and month/day segments */ + value = mtag->value; + i = 0; + while (value[i] >= '0' && value[i] <= '9') i++; + if (value[i] == '\0' || value[i] == '-') { + av_strlcpy(year, value, sizeof(year)); + av_dict_set(&dst, "TYER", year, 0); + + if (value[i] == '-' && + value[i+1] >= '0' && value[i+1] <= '1' && + value[i+2] >= '0' && value[i+2] <= '9' && + value[i+3] == '-' && + value[i+4] >= '0' && value[i+4] <= '3' && + value[i+5] >= '0' && value[i+5] <= '9' && + (value[i+6] == '\0' || value[i+6] == ' ')) { + snprintf(day_month, sizeof(day_month), "%.2s%.2s", value + i + 4, value + i + 1); + av_dict_set(&dst, "TDAT", day_month, 0); + } + } else + av_dict_set(&dst, key, value, 0); + } else + av_dict_set(&dst, key, mtag->value, 0); + } + av_dict_free(pm); + *pm = dst; +} + int ff_id3v2_write(struct AVFormatContext *s, int id3v2_version, const char *magic) { @@ -116,7 +155,9 @@ int ff_id3v2_write(struct AVFormatContext *s, int id3v2_version, avio_wb32(s->pb, 0); ff_metadata_conv(&s->metadata, ff_id3v2_34_metadata_conv, NULL); - if (id3v2_version == 4) + if (id3v2_version == 3) + id3v2_3_metadata_split_date(&s->metadata); + else if (id3v2_version == 4) ff_metadata_conv(&s->metadata, ff_id3v2_4_metadata_conv, NULL); while ((t = av_dict_get(s->metadata, "", t, AV_DICT_IGNORE_SUFFIX))) { |