Made im/export functions nonvirtual. Added similar functions to File and

its subclasses. TagLib::File contains a bunch of dynamic_casts to call
the correct specializations.
This commit is contained in:
Michael Helmling
2011-08-28 22:58:40 +02:00
parent fa8159a9d0
commit 5647b2e293
20 changed files with 297 additions and 9 deletions

View File

@ -109,6 +109,25 @@ TagLib::Tag *APE::File::tag() const
return &d->tag;
}
TagLib::TagDict APE::File::toDict(void) const
{
if (d->hasAPE)
return d->tag.access<APE::Tag>(APEIndex, false)->toDict();
if (d->hasID3v1)
return d->tag.access<ID3v1::Tag>(ID3v1Index, false)->toDict();
return TagLib::TagDict();
}
void APE::File::fromDict(const TagDict &dict)
{
if (d->hasAPE)
d->tag.access<APE::Tag>(APEIndex, false)->fromDict(dict);
else if (d->hasID3v1)
d->tag.access<ID3v1::Tag>(ID3v1Index, false)->fromDict(dict);
else
d->tag.access<APE::Tag>(APE, true)->fromDict(dict);
}
APE::Properties *APE::File::audioProperties() const
{
return d->properties;

View File

@ -110,6 +110,19 @@ namespace TagLib {
*/
virtual TagLib::Tag *tag() const;
/*!
* Implements the unified tag dictionary interface -- export function.
* If the file contains both an APE and an ID3v1 tag, only APE
* will be converted to the TagDict.
*/
TagDict toDict() const;
/*!
* Implements the unified tag dictionary interface -- import function.
* As for the export, only one tag is taken into account. If the file
* has no tag at all, APE will be created.
*/
void fromDict(const TagDict &);
/*!
* Returns the APE::Properties for this file. If no audio properties
* were read then this will return a null pointer.

View File

@ -114,13 +114,13 @@ namespace TagLib {
* TRACK to TRACKNUMBER and YEAR to DATE, respectively, in order to be compliant
* with the names used in other formats.
*/
virtual TagDict toDict() const;
TagDict toDict() const;
/*!
* Implements the unified tag dictionary interface -- import function. The same
* comments as for the export function apply.
*/
virtual void fromDict(const TagDict &);
void fromDict(const TagDict &);
/*!
* Returns a pointer to the tag's footer.

View File

@ -138,6 +138,31 @@ TagLib::Tag *FLAC::File::tag() const
return &d->tag;
}
TagLib::TagDict FLAC::File::toDict(void) const
{
// once Tag::toDict() is virtual, this case distinction could actually be done
// within TagUnion.
if (d->hasXiphComment)
return d->tag.access<Ogg::XiphComment>(XiphIndex, false)->toDict();
if (d->hasID3v2)
return d->tag.access<ID3v2::Tag>(ID3v2Index, false)->toDict();
if (d->hasID3v1)
return d->tag.access<ID3v1::Tag>(ID3v1Index, false)->toDict();
return TagLib::TagDict();
}
void FLAC::File::fromDict(const TagDict &dict)
{
if (d->hasXiphComment)
d->tag.access<Ogg::XiphComment>(XiphIndex, false)->fromDict(dict);
else if (d->hasID3v2)
d->tag.access<ID3v2::Tag>(ID3v2Index, false)->fromDict(dict);
else if (d->hasID3v1)
d->tag.access<ID3v1::Tag>(ID3v1Index, false)->fromDict(dict);
else
d->tag.access<Ogg::XiphComment>(XiphIndex, true)->fromDict(dict);
}
FLAC::Properties *FLAC::File::audioProperties() const
{
return d->properties;

View File

@ -29,6 +29,7 @@
#include "taglib_export.h"
#include "tfile.h"
#include "tlist.h"
#include "tag.h"
#include "flacpicture.h"
#include "flacproperties.h"
@ -36,7 +37,6 @@
namespace TagLib {
class Tag;
namespace ID3v2 { class FrameFactory; class Tag; }
namespace ID3v1 { class Tag; }
namespace Ogg { class XiphComment; }
@ -118,6 +118,21 @@ namespace TagLib {
*/
virtual TagLib::Tag *tag() const;
/*!
* Implements the unified tag dictionary interface -- export function.
* If the file contains more than one tag (e.g. XiphComment and ID3v1),
* only the first one (in the order XiphComment, ID3v2, ID3v1) will be
* converted to the TagDict.
*/
TagDict toDict() const;
/*!
* Implements the unified tag dictionary interface -- import function.
* As with the export, only one tag is taken into account. If the file
* has no tag at all, a XiphComment will be created.
*/
void fromDict(const TagDict &);
/*!
* Returns the FLAC::Properties for this file. If no audio properties
* were read then this will return a null pointer.

View File

@ -113,6 +113,27 @@ TagLib::Tag *MPC::File::tag() const
return &d->tag;
}
TagLib::TagDict MPC::File::toDict(void) const
{
// once Tag::toDict() is virtual, this case distinction could actually be done
// within TagUnion.
if (d->hasAPE)
return d->tag.access<APE::Tag>(APEIndex, false)->toDict();
if (d->hasID3v1)
return d->tag.access<ID3v1::Tag>(ID3v1Index, false)->toDict();
return TagLib::TagDict();
}
void MPC::File::fromDict(const TagDict &dict)
{
if (d->hasAPE)
d->tag.access<APE::Tag>(APEIndex, false)->fromDict(dict);
else if (d->hasID3v1)
d->tag.access<ID3v1::Tag>(ID3v1Index, false)->fromDict(dict);
else
d->tag.access<APE::Tag>(APEIndex, true)->fromDict(dict);
}
MPC::Properties *MPC::File::audioProperties() const
{
return d->properties;

View File

@ -28,6 +28,7 @@
#include "taglib_export.h"
#include "tfile.h"
#include "tag.h"
#include "mpcproperties.h"
@ -107,6 +108,20 @@ namespace TagLib {
*/
virtual TagLib::Tag *tag() const;
/*!
* Implements the unified tag dictionary interface -- export function.
* If the file contains both an APE and an ID3v1 tag, only the APE
* tag will be converted to the TagDict.
*/
TagDict toDict() const;
/*!
* Implements the unified tag dictionary interface -- import function.
* As with the export, only one tag is taken into account. If the file
* has no tag at all, APE will be created.
*/
void fromDict(const TagDict &);
/*!
* Returns the MPC::Properties for this file. If no audio properties
* were read then this will return a null pointer.

View File

@ -265,13 +265,13 @@ namespace TagLib {
* This function does some work to translate the hard-specified ID3v2
* frame types into a free-form string-to-stringlist dictionary.
*/
virtual TagDict toDict() const;
TagDict toDict() const;
/*!
* Implements the unified tag dictionary interface -- import function.
* See the comments in toDict().
*/
virtual void fromDict(const TagDict &);
void fromDict(const TagDict &);
/*!
* Render the tag back to binary data, suitable to be written to disk.

View File

@ -133,6 +133,31 @@ TagLib::Tag *MPEG::File::tag() const
return &d->tag;
}
TagLib::TagDict MPEG::File::toDict(void) const
{
// once Tag::toDict() is virtual, this case distinction could actually be done
// within TagUnion.
if (d->hasID3v2)
return d->tag.access<ID3v2::Tag>(ID3v2Index, false)->toDict();
if (d->hasAPE)
return d->tag.access<APE::Tag>(APEIndex, false)->toDict();
if (d->hasID3v1)
return d->tag.access<ID3v1::Tag>(ID3v1Index, false)->toDict();
return TagLib::TagDict();
}
void MPEG::File::fromDict(const TagDict &dict)
{
if (d->hasID3v2)
d->tag.access<ID3v2::Tag>(ID3v2Index, false)->fromDict(dict);
else if (d->hasAPE)
d->tag.access<APE::Tag>(APEIndex, false)->fromDict(dict);
else if (d->hasID3v1)
d->tag.access<ID3v1::Tag>(ID3v1Index, false)->fromDict(dict);
else
d->tag.access<ID3v2::Tag>(ID3v2Index, true)->fromDict(dict);
}
MPEG::Properties *MPEG::File::audioProperties() const
{
return d->properties;

View File

@ -28,6 +28,7 @@
#include "taglib_export.h"
#include "tfile.h"
#include "tag.h"
#include "mpegproperties.h"
@ -128,6 +129,21 @@ namespace TagLib {
*/
virtual Tag *tag() const;
/*!
* Implements the unified tag dictionary interface -- export function.
* If the file contains more than one tag (e.g. ID3v2 and v1), only the
* first one (in the order ID3v2, APE, ID3v1) will be converted to the
* TagDict.
*/
TagDict toDict() const;
/*!
* Implements the unified tag dictionary interface -- import function.
* As with the export, only one tag is taken into account. If the file
* has no tag at all, ID3v2 will be created.
*/
void fromDict(const TagDict &);
/*!
* Returns the MPEG::Properties for this file. If no audio properties
* were read then this will return a null pointer.

View File

@ -92,6 +92,16 @@ Ogg::XiphComment *Ogg::FLAC::File::tag() const
return d->comment;
}
TagLib::TagDict Ogg::FLAC::File::toDict(void) const
{
return d->comment->toDict();
}
void Ogg::FLAC::File::fromDict(const TagDict &dict)
{
d->comment->fromDict(dict);
}
Properties *Ogg::FLAC::File::audioProperties() const
{
return d->properties;

View File

@ -89,6 +89,18 @@ namespace TagLib {
*/
virtual XiphComment *tag() const;
/*!
* Implements the unified tag dictionary interface -- export function.
* Returns the contents of the Ogg::XiphComment as TagDict.
*/
TagDict toDict() const;
/*!
* Implements the unified tag dictionary interface -- import function.
* Matches the TagDict's contents to the XiphComment of the file.
*/
void fromDict(const TagDict &);
/*!
* Returns the FLAC::Properties for this file. If no audio properties
* were read then this will return a null pointer.

View File

@ -82,6 +82,16 @@ Ogg::XiphComment *Speex::File::tag() const
return d->comment;
}
TagLib::TagDict Ogg::Speex::File::toDict(void) const
{
return d->comment->toDict();
}
void Ogg::Speex::File::fromDict(const TagDict &dict)
{
d->comment->fromDict(dict);
}
Speex::Properties *Speex::File::audioProperties() const
{
return d->properties;

View File

@ -82,6 +82,17 @@ namespace TagLib {
* TagLib::File::tag().
*/
virtual Ogg::XiphComment *tag() const;
/*!
* Implements the unified tag dictionary interface -- export function.
* Returns the contents of the Ogg::XiphComment as TagDict.
*/
TagDict toDict() const;
/*!
* Implements the unified tag dictionary interface -- import function.
* Matches the TagDict's contents to the XiphComment of the file.
*/
void fromDict(const TagDict &);
/*!
* Returns the Speex::Properties for this file. If no audio properties

View File

@ -85,6 +85,16 @@ Ogg::XiphComment *Vorbis::File::tag() const
return d->comment;
}
TagLib::TagDict Ogg::Vorbis::File::toDict(void) const
{
return d->comment->toDict();
}
void Ogg::Vorbis::File::fromDict(const TagDict &dict)
{
d->comment->fromDict(dict);
}
Vorbis::Properties *Vorbis::File::audioProperties() const
{
return d->properties;

View File

@ -90,6 +90,17 @@ namespace TagLib {
*/
virtual Ogg::XiphComment *tag() const;
/*!
* Implements the unified tag dictionary interface -- export function.
* Returns the contents of the Ogg::XiphComment as TagDict.
*/
TagDict toDict() const;
/*!
* Implements the unified tag dictionary interface -- import function.
* Matches the TagDict's contents to the XiphComment of the file.
*/
void fromDict(const TagDict &);
/*!
* Returns the Vorbis::Properties for this file. If no audio properties
* were read then this will return a null pointer.

View File

@ -147,13 +147,13 @@ namespace TagLib {
* comment is nothing more than a map from tag names to list of values,
* as is the dict interface).
*/
virtual TagDict toDict() const;
TagDict toDict() const;
/*!
* Implements the unified tag dictionary interface -- import function.
* The tags from the given dict will be stored one-to-one in the file.
*/
virtual void fromDict(const TagDict &);
void fromDict(const TagDict &);
/*!
* Returns the vendor ID of the Ogg Vorbis encoder. libvorbis 1.0 as the

View File

@ -63,7 +63,7 @@ namespace TagLib {
* of the specific metadata format into a "human-readable" map of strings
* to lists of strings, being as precise as possible.
*/
virtual TagDict toDict() const;
TagDict toDict() const;
/*!
* Unified tag dictionary interface -- import function. Converts a map
@ -72,7 +72,7 @@ namespace TagLib {
* be lost by this operation. Especially the default implementation handles
* only single values of the default tags specified in this class.
*/
virtual void fromDict(const TagDict &);
void fromDict(const TagDict &);
/*!
* Returns the track name; if no track name is present in the tag

View File

@ -50,6 +50,24 @@
# define W_OK 2
#endif
#include "asffile.h"
#include "mpegfile.h"
#include "vorbisfile.h"
#include "flacfile.h"
#include "oggflacfile.h"
#include "mpcfile.h"
#include "mp4file.h"
#include "wavpackfile.h"
#include "speexfile.h"
#include "trueaudiofile.h"
#include "aifffile.h"
#include "wavfile.h"
#include "apefile.h"
#include "modfile.h"
#include "s3mfile.h"
#include "itfile.h"
#include "xmfile.h" \
using namespace TagLib;
class File::FilePrivate
@ -95,6 +113,48 @@ FileName File::name() const
return d->stream->name();
}
TagDict File::toDict() const
{
// ugly workaround until this method is virtual
if (dynamic_cast<const APE::File* >(this))
return dynamic_cast<const APE::File* >(this)->toDict();
if (dynamic_cast<const FLAC::File* >(this))
return dynamic_cast<const FLAC::File* >(this)->toDict();
if (dynamic_cast<const MPC::File* >(this))
return dynamic_cast<const MPC::File* >(this)->toDict();
if (dynamic_cast<const MPEG::File* >(this))
return dynamic_cast<const MPEG::File* >(this)->toDict();
if (dynamic_cast<const Ogg::FLAC::File* >(this))
return dynamic_cast<const Ogg::FLAC::File* >(this)->toDict();
if (dynamic_cast<const Ogg::Speex::File* >(this))
return dynamic_cast<const Ogg::Speex::File* >(this)->toDict();
if (dynamic_cast<const Ogg::Vorbis::File* >(this))
return dynamic_cast<const Ogg::Vorbis::File* >(this)->toDict();
// no specialized implementation available -> use generic one
return tag()->toDict();
}
void File::fromDict(const TagDict &dict)
{
if (dynamic_cast<const APE::File* >(this))
dynamic_cast< APE::File* >(this)->fromDict(dict);
else if (dynamic_cast<const FLAC::File* >(this))
dynamic_cast< FLAC::File* >(this)->fromDict(dict);
else if (dynamic_cast<const MPC::File* >(this))
dynamic_cast< MPC::File* >(this)->fromDict(dict);
else if (dynamic_cast<const MPEG::File* >(this))
dynamic_cast< MPEG::File* >(this)->fromDict(dict);
else if (dynamic_cast<const Ogg::FLAC::File* >(this))
dynamic_cast< Ogg::FLAC::File* >(this)->fromDict(dict);
else if (dynamic_cast<const Ogg::Speex::File* >(this))
dynamic_cast< Ogg::Speex::File* >(this)->fromDict(dict);
else if (dynamic_cast<const Ogg::Vorbis::File* >(this))
dynamic_cast< Ogg::Vorbis::File* >(this)->fromDict(dict);
else
tag()->fromDict(dict);
}
ByteVector File::readBlock(ulong length)
{
return d->stream->readBlock(length);

View File

@ -28,6 +28,7 @@
#include "taglib_export.h"
#include "taglib.h"
#include "tag.h"
#include "tbytevector.h"
#include "tiostream.h"
@ -76,6 +77,20 @@ namespace TagLib {
*/
virtual Tag *tag() const = 0;
/*!
* Exports the tags of the file as dictionary mapping (human readable) tag
* names (Strings) to StringLists of tag values. Calls the according specialization
* in the File subclasses.
* Will be made virtual in future releases.
*/
TagDict toDict() const;
/*!
* Sets the tags of this File to those specified by the given TagDict. Calls the
* according specialization method in the subclasses of File to do the translation
* into the format-specific details.
*/
void fromDict(const TagDict &);
/*!
* Returns a pointer to this file's audio properties. This should be
* reimplemented in the concrete subclasses. If no audio properties were