예제 #1
0
파일: taglib_ext.cpp 프로젝트: pft/taggit
/**
 * Get the various artist information form a tag.
 *
 * @param filetype the type-id for the file that is being processed
 * @param tagtype  the tag-type to use (if more than one are used per filetype)
 * @param tag      the tag-data from taglib
 *
 * @return      a proper multi-artist data field or a NULL pointer.
 * @sideeffects none
 */
const char *
taggit_tag_va(enum file_type filetype, int tagtype, TagLib_Tag *tag)
{
    /*
     * At this point, we already figured out the file type *and* decided which
     * tag to read from the file. `filetype' and `tagtype' give us hints into
     * the right direction. We *must* follow these hints or things will blow
     * up.
     */
    TagLib::APE::Tag *ape;
    TagLib::ID3v2::Tag *v2;
    TagLib::Ogg::XiphComment *ogg;
    const char *ret;

    ret = (const char *)NULL;
    switch (filetype) {
    case FT_MPEG:
        if (tagtype & MP3_ID3V2) {
            /**
             * @TODO Add support for TCMP (and maybe TCP) frames.
             * It's probably best to only check for those if TPE2 is empty,
             * because otherwise we already consider the track part of a
             * compilation.
             */
            v2 = reinterpret_cast<TagLib::ID3v2::Tag *>(tag);
            if (v2->frameListMap()["TPE2"].isEmpty())
                break;
            ret = xstrdup(
                v2->frameListMap()["TPE2"].front()->toString().toCString());
        } else if (tagtype & MP3_APE) {
            ape = reinterpret_cast<TagLib::APE::Tag *>(tag);
            if (ape->itemListMap()["ALBUMARTIST"].isEmpty())
                break;
            ret = xstrdup(
                ape->itemListMap()["ALBUMARTIST"].toString().toCString());
        }
        /* Don't care about ID3v1 */
        break;
    case FT_OGGVORBIS:
        /* @FALLTHROUGH@ */
    case FT_OGGFLAC:
        /* ogg* files share the same tag format */
        ogg = reinterpret_cast<TagLib::Ogg::XiphComment *>(tag);
        if (ogg->fieldListMap()["ALBUMARTIST"].isEmpty())
            break;
        ret = xstrdup(
            ogg->fieldListMap()["ALBUMARTIST"].toString().toCString());
        break;
    case FT_FLAC:
        /* AFAIK, there is no native FLAC tag format */
        break;
    default:
        break;
    }
    return ret;
}
예제 #2
0
파일: taglib_ext.cpp 프로젝트: pft/taggit
/**
 * Change tag type informmation in a struct taggit_list
 *
 * A string is created for the tagtypes entry. It will be a comma seperated
 * list of tags found within the given mp3 file. This string is dynamically
 * allocated and needs to be freed if it is not in use anymore (which will be
 * taken care of when taglist_destroy() is called).
 *
 * Secondly, the readmap is checked for which of the existing tag types should
 * be read. This information is then stored in the tagtype entry of the struct.
 *
 * @param   f       TagLib_File pointer to check
 * @param   lst     A pointer to the taggit_list structure to change
 *
 * @return      void (see description)
 * @sideeffects none
 */
void
mp3_tagtypes(TagLib_File *f, struct taggit_list *lst)
{
    TagLib::MPEG::File::File *file;
    TagLib::ID3v1::Tag *v1;
    TagLib::ID3v2::Tag *v2;
    TagLib::APE::Tag *ape;
    std::string tmp;
    int types;
    char *rc;

    file = reinterpret_cast<TagLib::MPEG::File::File *>(f);
    types = MP3_NO_TAGS;
    tmp = "";
    ape = file->APETag();
    if (ape != NULL &&
        !(ape->isEmpty() && ape->itemListMap()["ALBUMARTIST"].isEmpty()))
    {
        tmp += "apetag";
        types |= MP3_APE;
    }

    v1 = file->ID3v1Tag();
    if (v1 != NULL && !v1->isEmpty()) {
        if (tmp != "")
            tmp += ",";
        tmp = "id3v1";
        types |= MP3_ID3V1;
    }

    v2 = file->ID3v2Tag();
    if (v2 != NULL && !v2->isEmpty()) {
        if (tmp != "")
            tmp += ",";
        tmp += "id3v2";
        types |= MP3_ID3V2;
    }

    if (tmp == "")
        tmp = "(no tags)";

    rc = xstrdup(tmp.c_str());
    if (errno == ENOMEM) {
        fprintf(stderr, "Out of memory. Aborting.\n");
        exit(EXIT_FAILURE);
    }
    lst->tagtypes = rc;
    lst->tagtype = setup_please_read((char*)"mp3", types);
}
예제 #3
0
파일: taglib_ext.cpp 프로젝트: pft/taggit
/**
 * Set the file-type specific `compilation' tag.
 *
 * See the discussion on top of this file about which tag is used
 * for which file-type.
 *
 * @param file  taggit's file-data structure for the processed file
 * @param tag   the tag-data decoded by `taglib_file_tag()'
 * @param value the string the user wants to set this tag to
 *
 * @return      void
 * @sideeffects none
 */
void
taggit_tag_set_compilation(struct taggit_file *file,
                           TagLib_Tag *tag, const char *value)
{
    TagLib::APE::Tag *ape;
    TagLib::ID3v2::Tag *v2;
    TagLib::Ogg::XiphComment *ogg;
    const char *ret;
    TagLib::MPEG::File::File *f;
    int mask;

    ret = (const char *)NULL;
    switch (file->type) {
    case FT_MPEG:
        f = reinterpret_cast<TagLib::MPEG::File::File *>(file->data);
        mask = setup_get_write_mask(FT_MPEG);
        if (mask & MP3_ID3V2) {
            v2 = f->ID3v2Tag();
            v2->removeFrames("TPE2");
            /*
             * @TODO: I don't know how to figure out the proper `encoding'
             *        value here. Should we look at the `unicodeStrings'
             *        variable from taglib?
             */
            TagLib::ID3v2::TextIdentificationFrame *frame =
                new TagLib::ID3v2::TextIdentificationFrame(
                    "TPE2", TagLib::String::Latin1);
            frame->setText(value);
            v2->addFrame(frame);
        }
        if (mask & MP3_APE) {
            ape = f->APETag();
            ape->addValue("ALBUMARTIST", value, true);
        }
        break;
    case FT_OGGVORBIS:
        /* @FALLTHROUGH@ */
    case FT_OGGFLAC:
        ogg = reinterpret_cast<TagLib::Ogg::XiphComment *>(tag);
        ogg->addField("ALBUMARTIST", value, true);
        break;
    default:
        break;
    }
}
예제 #4
0
파일: taksrc.cpp 프로젝트: mcanthony/qaac
void TakSource::fetchTags()
{
    int fd = fileno(m_fp.get());
    util::FilePositionSaver _(fd);
    lseek(fd, 0, SEEK_SET);
    TagLibX::FDIOStreamReader stream(fd);
    TagLib::APE::File file(&stream, false);

    std::map<std::string, std::string> tags;
    std::wstring cuesheet;

    TagLib::APE::Tag *tag = file.APETag(false);
    const TagLib::APE::ItemListMap &itemListMap = tag->itemListMap();
    TagLib::APE::ItemListMap::ConstIterator it;
    for (it = itemListMap.begin(); it != itemListMap.end(); ++it) {
        if (it->second.type() != TagLib::APE::Item::Text)
            continue;
        std::string key = it->first.toCString();
        std::wstring value = it->second.toString().toWString();
        tags[key] = strutil::w2us(value);
    }
    TextBasedTag::normalizeTags(tags, &m_tags);
}
예제 #5
0
QList<FileInfo *> DecoderMPCFactory::createPlayList(const QString &fileName, bool useMetaData, QStringList *)
{
    FileInfo *info = new FileInfo(fileName);

#if (TAGLIB_MAJOR_VERSION > 1) || ((TAGLIB_MAJOR_VERSION == 1) && (TAGLIB_MINOR_VERSION >= 8))
    TagLib::FileStream stream(fileName.toLocal8Bit().constData(), true);
    TagLib::MPC::File fileRef(&stream);
#else
    TagLib::MPC::File fileRef(fileName.toLocal8Bit().constData());
#endif

    TagLib::APE::Tag *tag = useMetaData ? fileRef.APETag() : 0;
    if (tag && !tag->isEmpty())
    {
        info->setMetaData(Qmmp::ALBUM,
                       QString::fromUtf8(tag->album().toCString(true)).trimmed());
        info->setMetaData(Qmmp::ARTIST,
                       QString::fromUtf8(tag->artist().toCString(true)).trimmed());
        info->setMetaData(Qmmp::COMMENT,
                       QString::fromUtf8(tag->comment().toCString(true)).trimmed());
        info->setMetaData(Qmmp::GENRE,
                       QString::fromUtf8(tag->genre().toCString(true)).trimmed());
        info->setMetaData(Qmmp::TITLE,
                       QString::fromUtf8(tag->title().toCString(true)).trimmed());
        info->setMetaData(Qmmp::YEAR, tag->year());
        info->setMetaData(Qmmp::TRACK, tag->track());
    }
    if (fileRef.audioProperties())
        info->setLength(fileRef.audioProperties()->length());
    //additional metadata
    if(tag)
    {
        TagLib::APE::Item fld;
        if(!(fld = tag->itemListMap()["ALBUM ARTIST"]).isEmpty())
            info->setMetaData(Qmmp::ALBUMARTIST,
                              QString::fromUtf8(fld.toString().toCString(true)).trimmed());
        if(!(fld = tag->itemListMap()["COMPOSER"]).isEmpty())
            info->setMetaData(Qmmp::COMPOSER,
                              QString::fromUtf8(fld.toString().toCString(true)).trimmed());
    }

    QList <FileInfo*> list;
    list << info;
    return list;
}
예제 #6
0
int TagLibMetadata::setGrouping(const QString& grp){

  if(f == NULL || !f->isValid()){
    qDebug("Cannot set grouping tag on invalid file object");
    return 1;
  }

  TagLib::MPEG::File* fileTestMpeg = dynamic_cast<TagLib::MPEG::File*>(f);
  if(fileTestMpeg != NULL){
    TagLib::ID3v2::Tag* tagTestId3v2 = fileTestMpeg->ID3v2Tag();
    if(tagTestId3v2 != NULL){
      TagLib::ID3v2::Frame* frm = new TagLib::ID3v2::TextIdentificationFrame("TIT1");
      frm->setText(TagLib::String(grp.toUtf8().data()));
      tagTestId3v2->removeFrames("TIT1");
      tagTestId3v2->addFrame(frm);
      f->save();
      return 0;
    }else{
      TagLib::ID3v1::Tag* tagTestId3v1 = fileTestMpeg->ID3v1Tag();
      if(tagTestId3v1 != NULL){
        #ifdef Q_OS_WIN
          qDebug("ID3v1 does not support the Grouping tag");
        #else
          qDebug("ID3v1 does not support the Grouping tag (%s)",f->name());
        #endif
        return 1;
      }
    }
  }

  TagLib::RIFF::AIFF::File* fileTestAiff = dynamic_cast<TagLib::RIFF::AIFF::File*>(f);
  if(fileTestAiff != NULL){
    TagLib::ID3v2::Tag* tagTestId3v2 = fileTestAiff->tag();
    if(tagTestId3v2 != NULL){
      TagLib::ID3v2::Frame* frm = new TagLib::ID3v2::TextIdentificationFrame("TIT1");
      frm->setText(TagLib::String(grp.toUtf8().data()));
      tagTestId3v2->removeFrames("TIT1");
      tagTestId3v2->addFrame(frm);
      f->save();
      return 0;
    }
  }

  TagLib::RIFF::WAV::File* fileTestWav = dynamic_cast<TagLib::RIFF::WAV::File*>(f);
  if(fileTestWav != NULL){
    TagLib::ID3v2::Tag* tagTestId3v2 = fileTestWav->tag();
    if(tagTestId3v2 != NULL){
      TagLib::ID3v2::Frame* frm = new TagLib::ID3v2::TextIdentificationFrame("TIT1");
      frm->setText(TagLib::String(grp.toUtf8().data()));
      tagTestId3v2->removeFrames("TIT1");
      tagTestId3v2->addFrame(frm);
      f->save();
      return 0;
    }
  }

  TagLib::MP4::Tag* tagTestMp4 = dynamic_cast<TagLib::MP4::Tag*>(f->tag());
  if(tagTestMp4 != NULL){
    TagLib::StringList sl(TagLib::String(grp.toUtf8().data()));
    tagTestMp4->itemListMap()["\251grp"] = sl;
    tagTestMp4->save();
    f->save();
    return 0;
  }

  TagLib::ASF::Tag* tagTestAsf = dynamic_cast<TagLib::ASF::Tag*>(f->tag());
  if(tagTestAsf != NULL){
    tagTestAsf->setAttribute("WM/ContentGroupDescription",TagLib::String(grp.toUtf8().data()));
    f->save();
    return 0;
  }

  TagLib::APE::Tag* tagTestApe = dynamic_cast<TagLib::APE::Tag*>(f->tag());
  if(tagTestApe != NULL){
    tagTestApe->addValue("GROUPING",TagLib::String(grp.toUtf8().data()));
    f->save();
    return 0;
  }

  #ifdef Q_OS_WIN
    qDebug("Grouping tag write failed all tests");
  #else
    qDebug("Grouping tag write failed all tests on %s",f->name());
  #endif
  return 1;
}
예제 #7
0
QString TagLibMetadata::getGrouping() const{

  if(f == NULL || !f->isValid())
    return "";

  TagLib::MPEG::File* fileTestMpeg = dynamic_cast<TagLib::MPEG::File*>(f);
  if(fileTestMpeg != NULL){
    TagLib::ID3v2::Tag* tagTestId3v2 = fileTestMpeg->ID3v2Tag();
    if(tagTestId3v2 != NULL){
      TagLib::ID3v2::FrameList l = tagTestId3v2->frameListMap()["TIT1"];
      if(!l.isEmpty()){
        TagLib::String out = l.front()->toString();
        return QString::fromUtf8((out.toCString()));
      }
      return "";
    }
    TagLib::ID3v1::Tag* tagTestId3v1 = fileTestMpeg->ID3v1Tag();
    if(tagTestId3v1 != NULL){
      #ifdef Q_OS_WIN
        qDebug("ID3v1 does not support the Grouping tag");
      #else
        qDebug("ID3v1 does not support the Grouping tag (%s)",f->name());
      #endif
      return "N/A";
    }
  }

  TagLib::RIFF::AIFF::File* fileTestAiff = dynamic_cast<TagLib::RIFF::AIFF::File*>(f);
  if(fileTestAiff != NULL){
    TagLib::ID3v2::Tag* tagTestId3v2 = fileTestAiff->tag();
    if(tagTestId3v2 != NULL){
      TagLib::ID3v2::FrameList l = tagTestId3v2->frameListMap()["TIT1"];
      if(!l.isEmpty()){
        TagLib::String out = l.front()->toString();
        return QString::fromUtf8((out.toCString()));
      }
      return "";
    }
  }

  TagLib::RIFF::WAV::File* fileTestWav = dynamic_cast<TagLib::RIFF::WAV::File*>(f);
  if(fileTestWav != NULL){
    TagLib::ID3v2::Tag* tagTestId3v2 = fileTestWav->tag();
    if(tagTestId3v2 != NULL){
      TagLib::ID3v2::FrameList l = tagTestId3v2->frameListMap()["TIT1"];
      if(!l.isEmpty()){
        TagLib::String out = l.front()->toString();
        return QString::fromUtf8((out.toCString()));
      }
      return "";
    }
  }

  TagLib::MP4::Tag* tagTestMp4 = dynamic_cast<TagLib::MP4::Tag*>(f->tag());
  if(tagTestMp4 != NULL){
    TagLib::MP4::Item m = tagTestMp4->itemListMap()["\251grp"];
    if(m.isValid()){
      TagLib::String out = m.toStringList().front();
      return QString::fromUtf8((out.toCString()));
    }
    return "";
  }

  TagLib::ASF::Tag* tagTestAsf = dynamic_cast<TagLib::ASF::Tag*>(f->tag());
  if(tagTestAsf != NULL){
    TagLib::ASF::AttributeList l = tagTestAsf->attributeListMap()["WM/ContentGroupDescription"];
    if(!l.isEmpty()){
      TagLib::String out = l.front().toString();
      return QString::fromUtf8((out.toCString()));
    }
    return "";
  }

  TagLib::APE::Tag* tagTestApe = dynamic_cast<TagLib::APE::Tag*>(f->tag());
  if(tagTestApe != NULL){
    TagLib::APE::Item m = tagTestApe->itemListMap()["Grouping"];
    if(!m.isEmpty()){
      TagLib::String out = m.toStringList().front();
      return QString::fromUtf8((out.toCString()));
    }
    return "";
  }

  #ifdef Q_OS_WIN
    qDebug("Grouping tag read failed all tests");
  #else
    qDebug("Grouping tag read failed all tests on %s",f->name());
  #endif
  return "N/A";
}