Reading metadata information

This topic describes how to use the MediaInfo class to read metadata like ID3 tags, OGG attributes, and Windows Media attributes from a file.

read_metadata_any_file Sample

The code snippets in this article are from the read_metadata_any_file AVBlocks sample. The complete source code of the read_metadata_any_file sample is available in the AVBlocks Samples repository.

Create a MediaInfo object

Use the createXyz functions from the primo::avblocks::Library namespace to create new AVBlocks objects. For example, the createMediaInfo function creates a new MediaInfo object.


auto info = primo::make_ref(Library::createMediaInfo());

// Code that uses MediaInfo goes here

Load metadata from file

Call setFile for the default input socket and then call open.


auto info = primo::make_ref(Library::createMediaInfo());

info->inputs()->at(0)->setFile(opt.avfile.c_str());

if(info->open())
{   
    printMetadata(info.get(), opt.avfile.c_str());
    return true;
}
else
{
    printError(info->error());
    return false;
}

List attributes and pictures

Call the MediaSocket::metadata method of the default input socket to obtain a Metadata object. If there is no metadata, the MediaSocket::metadata method will return NULL.


void printMetadata(MediaInfo* info, const wchar_t* inputFile)
{
    Metadata* meta = NULL;
    if(info->outputs()->count() > 0)
        meta = info->outputs()->at(0)->metadata();

    if (!meta)
    {
        wcout << L"Could not find any metadata." << endl;
        return;
    }

    printMetaAttributes(meta);
    savePictures(meta, inputFile);
}

Enumerate attributes

  1. Call the Metadata::attributes method to get a MetaAttributeList object.
  2. Call the MetaAttributeList::at to get a MetaAttribute object.
  3. Get the name and the value of each attribute with the MetaAttribute::name and MetaAttribute::value methods.

void printMetaAttributes(Metadata* meta)
{
    stdout_utf16 mode;  

    wcout << L"Metadata\r\n--------" << endl;

    MetaAttributeList* attlist = meta->attributes();
    wcout << attlist->count() << L" attributes:" << endl;

    for (int i=0; i < attlist->count(); ++i)
    {
        MetaAttribute* attrib = attlist->at(i);
        wcout << setw(15) << left << attrib->name() << L": " << attrib->value() << endl;
    }
    wcout << endl;
}

Enumerate pictures

  1. Call the Metadata::pictures method to get a MetaPictureList object.
  2. Call the MetaPictureList::at to get a MetaPicture object for each picture.
  3. Call the methods of the MetaPicture interface to get the picture properties.

void printMetaAttributes(Metadata* meta)
{
    stdout_utf16 mode;  

    MetaPictureList* piclist = meta->pictures();
    wcout << piclist->count() << L" pictures:" << endl;

    for (int i=0; i < piclist->count(); ++i)
    {
        MetaPicture* pic = piclist->at(i);
        wcout << L"#" << (i+1) << L" mime: " << pic->mimeType() << L"; size: " << pic->dataSize();

        wcout << L"; type: " << getMetaPictureTypeName(pic->pictureType()) << endl;
        wcout << L"description: " << pic->description() << endl;
    }
    wcout << endl;
}

Save pictures

To save a picture to a file:

  1. Get the image type with the MetaPicture::mimeType method.
  2. Call the MetaPicture::data and MetaPicture::dataSize methods to get the image data and size.
  3. Write the image data to a file.

void savePicture(primo::codecs::MetaPicture* pic, const wstring& baseFilename)
{
    wstring filename(baseFilename);

    if (0 == strcmp( pic->mimeType(), primo::codecs::MimeType::Jpeg))
    {
        filename += L".jpg";
    }
    else if (0 == strcmp( pic->mimeType(), primo::codecs::MimeType::Png))
    {
        filename += L".png";
    }
    else if (0 == strcmp( pic->mimeType(), primo::codecs::MimeType::Gif))
    {
        filename += L".gif";
    }
    else if (0 == strcmp( pic->mimeType(), primo::codecs::MimeType::Tiff))
    {
        filename += L".tiff";
    }
    else
    {
        // unexpected picture mime type
        return;
    }

    ofstream out(filename.c_str(), ios::out | ios::binary | ios::trunc);

    if (out)
    {
        out.write((const char*)pic->data(), pic->dataSize());
    }
}


Last updated on December 5th, 2017 04:43:53 PM