From 762581fe3f48075cbaef094c9888481577f298ac Mon Sep 17 00:00:00 2001 From: Tsuda Kageyu Date: Fri, 12 Jun 2015 15:12:58 +0900 Subject: [PATCH 1/3] Add a method to check if an MP4 file on disk actually has a tag. --- taglib/mp4/mp4file.cpp | 26 +++++++++++++++++++++----- taglib/mp4/mp4file.h | 5 +++++ tests/test_mp4.cpp | 4 ++++ 3 files changed, 30 insertions(+), 5 deletions(-) diff --git a/taglib/mp4/mp4file.cpp b/taglib/mp4/mp4file.cpp index 1fc1524f..566a5e32 100644 --- a/taglib/mp4/mp4file.cpp +++ b/taglib/mp4/mp4file.cpp @@ -34,7 +34,7 @@ using namespace TagLib; namespace { - bool checkValid(const MP4::AtomList &list) + inline bool checkValid(const MP4::AtomList &list) { for(MP4::AtomList::ConstIterator it = list.begin(); it != list.end(); ++it) { @@ -55,7 +55,8 @@ public: FilePrivate() : tag(0), atoms(0), - properties(0) {} + properties(0), + hasMP4Tag(false) {} ~FilePrivate() { @@ -67,6 +68,8 @@ public: MP4::Tag *tag; MP4::Atoms *atoms; MP4::Properties *properties; + + bool hasMP4Tag; }; MP4::File::File(FileName file, bool readProperties, AudioProperties::ReadStyle) : @@ -130,12 +133,15 @@ MP4::File::read(bool readProperties) } // must have a moov atom, otherwise consider it invalid - MP4::Atom *moov = d->atoms->find("moov"); - if(!moov) { + if(!d->atoms->find("moov")) { setValid(false); return; } + if(d->atoms->find("moov", "udta", "meta", "ilst")) { + d->hasMP4Tag = true; + } + d->tag = new Tag(this, d->atoms); if(readProperties) { d->properties = new Properties(this, d->atoms); @@ -155,6 +161,16 @@ MP4::File::save() return false; } - return d->tag->save(); + const bool success = d->tag->save(); + if(success) { + d->hasMP4Tag = true; + } + + return success; } +bool +MP4::File::hasMP4Tag() const +{ + return d->hasMP4Tag; +} diff --git a/taglib/mp4/mp4file.h b/taglib/mp4/mp4file.h index 791a0192..8c049301 100644 --- a/taglib/mp4/mp4file.h +++ b/taglib/mp4/mp4file.h @@ -117,6 +117,11 @@ namespace TagLib { */ bool save(); + /*! + * Returns whether or not the file on disk actually has an MP4 tag. + */ + bool hasMP4Tag() const; + private: void read(bool readProperties); diff --git a/tests/test_mp4.cpp b/tests/test_mp4.cpp index 6841c43f..ed93f043 100644 --- a/tests/test_mp4.cpp +++ b/tests/test_mp4.cpp @@ -69,6 +69,10 @@ public: CPPUNIT_ASSERT(!f.isValid()); MP4::File f2(TEST_FILE_PATH_C("has-tags.m4a")); CPPUNIT_ASSERT(f2.isValid()); + CPPUNIT_ASSERT(f2.hasMP4Tag()); + MP4::File f3(TEST_FILE_PATH_C("no-tags.m4a")); + CPPUNIT_ASSERT(f3.isValid()); + CPPUNIT_ASSERT(!f3.hasMP4Tag()); } void testIsEmpty() From 69921b80906172a031f7771ea90d501a535dd912 Mon Sep 17 00:00:00 2001 From: Tsuda Kageyu Date: Wed, 18 Nov 2015 14:17:29 +0900 Subject: [PATCH 2/3] Amend the comment on MP4::File::hasMP4Tag(). --- taglib/mp4/mp4file.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/taglib/mp4/mp4file.h b/taglib/mp4/mp4file.h index 8c049301..40fcde78 100644 --- a/taglib/mp4/mp4file.h +++ b/taglib/mp4/mp4file.h @@ -118,7 +118,8 @@ namespace TagLib { bool save(); /*! - * Returns whether or not the file on disk actually has an MP4 tag. + * Returns whether or not the file on disk actually has an MP4 tag, or the + * file has a Metadata Item List (ilst) atom. */ bool hasMP4Tag() const; From b01fecd280ca290b7cb41eba48dc25a112b555b7 Mon Sep 17 00:00:00 2001 From: Tsuda Kageyu Date: Wed, 18 Nov 2015 14:25:22 +0900 Subject: [PATCH 3/3] Separate some tests for MP4::File::hasMP4Tag(). --- tests/test_mp4.cpp | 31 +++++++++++++++++++++++++------ 1 file changed, 25 insertions(+), 6 deletions(-) diff --git a/tests/test_mp4.cpp b/tests/test_mp4.cpp index ed93f043..c110a612 100644 --- a/tests/test_mp4.cpp +++ b/tests/test_mp4.cpp @@ -19,6 +19,7 @@ class TestMP4 : public CppUnit::TestFixture CPPUNIT_TEST(testPropertiesALAC); CPPUNIT_TEST(testFreeForm); CPPUNIT_TEST(testCheckValid); + CPPUNIT_TEST(testHasTag); CPPUNIT_TEST(testIsEmpty); CPPUNIT_TEST(testUpdateStco); CPPUNIT_TEST(testSaveExisingWhenIlstIsLast); @@ -67,12 +68,30 @@ public: { MP4::File f(TEST_FILE_PATH_C("empty.aiff")); CPPUNIT_ASSERT(!f.isValid()); - MP4::File f2(TEST_FILE_PATH_C("has-tags.m4a")); - CPPUNIT_ASSERT(f2.isValid()); - CPPUNIT_ASSERT(f2.hasMP4Tag()); - MP4::File f3(TEST_FILE_PATH_C("no-tags.m4a")); - CPPUNIT_ASSERT(f3.isValid()); - CPPUNIT_ASSERT(!f3.hasMP4Tag()); + } + + void testHasTag() + { + { + MP4::File f(TEST_FILE_PATH_C("has-tags.m4a")); + CPPUNIT_ASSERT(f.isValid()); + CPPUNIT_ASSERT(f.hasMP4Tag()); + } + + ScopedFileCopy copy("no-tags", ".m4a"); + + { + MP4::File f(copy.fileName().c_str()); + CPPUNIT_ASSERT(f.isValid()); + CPPUNIT_ASSERT(!f.hasMP4Tag()); + f.tag()->setTitle("TITLE"); + f.save(); + } + { + MP4::File f(copy.fileName().c_str()); + CPPUNIT_ASSERT(f.isValid()); + CPPUNIT_ASSERT(f.hasMP4Tag()); + } } void testIsEmpty()