Saturday, November 14, 2015

Working example of how to fix ID3v1 and ID3v2 tags with TagLib#

Introduction

I bought a bunch of albums from Japan recently for an excellent band named Maximum The Hormone - (マキシマム ザ ホルモン) aka MTH. If you have watched Season 2 of Death Note then you have heard their music. Since I, like everyone else on the planet, do not use CDs anymore I ripped all of the songs for my personal use on my electronic devices. I ripped the songs by using an excellent program I have been using for years named "EZ CD-DA Extractor" by Poikosoft. It really is a great program, but it of course will have problems with lesser known or less popular music because the grouping of databases they use for obtaining the tags for music just doesn't have records of the more obscure things. The good news is it named all of the albums and tracks appropriately. Therefore I got the idea to use that data to populate the ID3v1 and ID3v2 tags of my albums. It is just a bunch repetitive information.

Projects

I uploaded all of my code for review and use in my GitHub repository located here: https://github.com/dyslexicanaboko/dyslexic-code/tree/master/Id3v1Tags
This includes two projects, a unit testing project (runner) and the library with all of the code.

I named the project Id3v1Tags because at first I didn't think I would be able to modify the ID3v2 tags, well to my surprise the library that I ended up using did the trick.

Code Example

The most important part of the code is below which is the one example that everyone is usually looking for.

//It is important that you use the version of TagLib that isn't the 
//Portable version so that you get all of the overloads provided by the 
//Create method
using TagLib;

File f = null;

var arrArtists = new string[] { artist.Name };
var arrGenres = new string[] { "Metal", "Punk Rock" };

foreach (Album a in artist.Albums)
{
 foreach (Track t in a.Tracks)
 {
  f = File.Create(t.FullPath);
  //This property is deprecated, but I don't know how else to fix this field
  f.Tag.Artists = arrArtists; 
  f.Tag.AlbumArtists = arrArtists;
  f.Tag.Year = (uint)a.Year;
  f.Tag.Album = a.Name;
  f.Tag.Track = (uint)t.TrackNumber;
  f.Tag.Title = t.Title;
  f.Tag.Genres = arrGenres;
  f.Save();
 }
}

Please note the following

  • The above example is a very biased example, if you used it you would have to modify it for your needs
  • I am hard coding the genres because I just needed to do a one time fix, this should obviously be a parameter or somehow configurable
  • The Artists property is deprecated, but I used it anyhow because it was the only way I could figure out how to fix some of the mp3s that I had that just wouldn't cooperate. Supposedly the AlbumArtists property is the replacement, but it didn't work. Hence why I ignored the warning and used that property anyhow.
  • When getting the TagLib# library from NuGet, make sure to avoid the Portable version because it reduces the number of overloads available for the File.Create() method.

My code's methodology

I wrote this code in like 2 hours with testing with the intention of just fixing my 6 albums for MTH. This code is far from complete and generically usable, but it can definitely be used as a starting point for other people to use. The methodology I used was to build the metadata using the directory and file's as my source of metadata. I have to say it did work for my purposes, but it doesn't mean it will work for everyone, at least not without adjustments. This is clearly biased code.

The object hierarchy is as follows:
  1. Artist
    1. top most directory
    2. an artist has a list of albums
  2. Albums
    1. subdirectory inside of artist directory
    2. an album has a list of tracks
    3. folder string format: "[year] [Album Name]"
      1. Example: "2007 Bu Ikikaesu"
  3. Tracks
    1. files inside of album directory
    2. linked to a physical file
    3. file name string format: "[Track Number] - [Track Title].mp3"
      1. Example: "10 - What's Up, People!.mp3"
Folder hierarchy example:
  1. Artist Directory: C:\Music\Maximum The Hormone - マキシマム ザ ホルモン
  2. Album Subdirectory: C:\Music\Maximum The Hormone - マキシマム ザ ホルモン\2008 爪爪爪「F」- Tsume Tsume Tsume [f]
  3. Track File: C:\Music\Maximum The Hormone - マキシマム ザ ホルモン\02 - 「F」.mp3
Therefore all of the above information is basically all of the metadata I need in order to fill up the ID3v1 and ID3v2 tags. I used winamp to verify that the information was filled in after running my program.

Resources

  1. http://stackoverflow.com/questions/68283/view-edit-id3-data-for-mp3-files
  2. https://taglib.github.io/
  3. http://taglib.github.io/api/


A common mistake when installing ASpell

The Problem

There is that once in a blue moon chance you will need to install ASpell manually and each time it is easy to forget how to do it properly. Simply put this is more of a Gotcha due to a small mistake that a lot of people make when installing ASpell.

The Gotcha

The Gotcha is - you probably did indeed install ASpell, but you forgot to install a dictionary. Tadahhhh - yep that's it. Just forgot one step.

The Solution

The solution as mentioned in the previous section is to simply install the dictionary with your choice of language. 

General Steps for v0.60.6.1

  1. Download the latest ASpell core program: ftp://ftp.gnu.org/gnu/aspell/aspell-0.60.6.1.tar.gz (always make sure to get the latest, this link was put here on 11/14/2015)
  2. Install the core program.
  3. Download your dictionary of choice such as the English dictionary:
    1. List of dictionaries: ftp://ftp.gnu.org/gnu/aspell/dict/0index.html
    2. English dictionary: ftp://ftp.gnu.org/gnu/aspell/dict/en/aspell6-en-2015.04.24-0.tar.bz2

Steps if you are using Notepad++ (uses ASpell Win32 v0.50.3)

If you are trying to use ASpell in conjunction with Notepad++, then follow the same template of steps as above, except use this link instead to get all of your binaries: http://aspell.net/win32/

First and foremost make sure your installation of Notepad++ and ASpell are going to be on the same drive. This important because Notepad++ assumes that ASpell is installed relative to its location.
  1. Download the ASpell v0.50.3 installer http://ftp.gnu.org/gnu/aspell/w32/Aspell-0-50-3-3-Setup.exe 
  2. Install ASpell v0.50.3
  3. Download your dictionary, this is the English dictionary for example: http://ftp.gnu.org/gnu/aspell/w32/Aspell-en-0.50-2-3.exe
  4. Verify that the path used for Notepad++ to ASpell is actually pointing to the right place. This can be verified simply by doing the following:
    1. Go to your Notepad++ directory, Example: "C:\Program Files (x86)\Notepad++"
    2. Take the relative path shown under the ASpell plugin help (Figure 1), Example: "..\Aspell\bin"
    3. Combine the two and try to navigate there using the Run command or equivalent method, Example: "C:\Program Files (x86)\Notepad++\..\Aspell\bin"
      1. If this takes you to your location, then everything should be fine. Restart Notepad++ and you should be able to use the plugin.
      2. If this doesn't take you to your location - then you need to figure out why your relative path is wrong and correct it until the aforementioned trick works
Figure 1 - Help dialogue for Spell-Checker plugin that uses ASpell

Conclusion

I think it is safe for me to say that, from an American perspective we usually assume everything is geared towards our American English. Obviously the ASpell program has broken that habit and forced the end user to actually choose instead of assume.