1. Open the audio file for reading in binary mode.
2. Check if the last 128 bytes contain the "TAG" header that identifies the ID3 tag.
3. Extract the following fields from the ID3 tag:
- Title: 30 characters
- Artist: 30 characters
- Album: 30 characters
- Year: 4 characters
- Comment: 30 characters
- Genre: 1 byte (integer representing a predefined genre)
4. Display the extracted data in a human-readable format, converting the genre number into its corresponding music genre.
5. Handle cases where the file does not contain an ID3 tag.
ID3 specifications apply to any file or audiovisual container, but they are primarily used with audio containers. There are three compatible versions of the specification. For example, a file may contain both version 1.1 and version 2.0 tags simultaneously, and in this case, the media player must determine which tags are relevant.
ID3 version 1 is a very simple specification. It involves appending a fixed block size of 128 bytes to the end of the file in question. This block contains the following tags:
A header that identifies the presence of the ID3 block and its version. Specifically, this header comprises the characters "TAG".
- Title: 30 characters.
- Artist: 30 characters.
- Album: 30 characters.
- Year: 4 characters.
- Comment: 30 characters.
- Genre (music): 1 character.
All tags use ASCII characters, except for genre, which is an integer stored within a single byte. The musical genre associated with each byte is predefined in the standard definitions and includes 80 genres numbered from 0 to 79. Some tagging programs have expanded the predefined genres beyond 79.
using System;
using System.IO;
using System.Text;
class ID3Reader
{
// Main method to execute the reading and parsing of ID3 version 1 tags
static void Main(string[] args)
{
// Prompt the user for the audio file path
Console.WriteLine("Please enter the path of the audio file:");
string filePath = Console.ReadLine();
// Check if the file exists
if (!File.Exists(filePath))
{
Console.WriteLine("File does not exist.");
return; // Exit the program if the file doesn't exist
}
try
{
// Open the audio file in read-only mode using FileStream
using (FileStream fs = new FileStream(filePath, FileMode.Open, FileAccess.Read))
{
// Move to the last 128 bytes of the file (ID3v1 tag location)
fs.Seek(-128, SeekOrigin.End);
// Read the last 128 bytes into a byte array
byte[] id3Tag = new byte[128];
fs.Read(id3Tag, 0, 128);
// Check if the tag header contains "TAG" (ID3v1 identifier)
if (Encoding.ASCII.GetString(id3Tag, 0, 3) == "TAG")
{
// Extract the title, artist, album, year, comment, and genre
string title = Encoding.ASCII.GetString(id3Tag, 3, 30).Trim();
string artist = Encoding.ASCII.GetString(id3Tag, 33, 30).Trim();
string album = Encoding.ASCII.GetString(id3Tag, 63, 30).Trim();
string year = Encoding.ASCII.GetString(id3Tag, 93, 4).Trim();
string comment = Encoding.ASCII.GetString(id3Tag, 97, 30).Trim();
byte genreByte = id3Tag[127]; // Genre is stored in the last byte
// Define a list of predefined genres (just a few as an example)
string[] genres = new string[]
{
"Blues", "Classic Rock", "Country", "Dance", "Disco", "Funk", "Grunge", "Hip-Hop",
"Jazz", "Metal", "New Age", "Oldies", "Other", "Pop", "R&B", "Rap", "Reggae",
"Rock", "Techno", "Industrial", "Alternative", "Ska", "Death Metal", "Pranks",
"Soundtrack", "Euro-Techno", "Pop/Funk", "Jungle", "Native American", "Cabaret",
"New Wave", "Psychadelic", "Rave", "Showtunes", "Trailer", "Lo-Fi", "Trance",
"Classical", "Instrumental", "Acid", "House", "Game", "Sound Clip", "Gospel",
"Noise", "AlternRock", "Bass", "Soul", "Punk", "Space", "Meditative", "Instrumental"
};
// Display the extracted metadata
Console.WriteLine("Title: " + title);
Console.WriteLine("Artist: " + artist);
Console.WriteLine("Album: " + album);
Console.WriteLine("Year: " + year);
Console.WriteLine("Comment: " + comment);
Console.WriteLine("Genre: " + (genreByte >= 0 && genreByte < genres.Length ? genres[genreByte] : "Unknown"));
}
else
{
Console.WriteLine("No ID3v1 tag found in the file.");
}
}
}
catch (Exception ex)
{
// Handle any errors that occur during file reading or parsing
Console.WriteLine("An error occurred: " + ex.Message);
}
}
}
Output
//Given the audio file contains an ID3 tag, the program will display:
Please enter the path of the audio file:
C:\path\to\audio.mp3
Title: My Song
Artist: Some Artist
Album: My Album
Year: 2021
Comment: Great song!
Genre: Rock
//If no ID3 tag is found, the program will output:
Please enter the path of the audio file:
C:\path\to\audio.mp3
No ID3v1 tag found in the file.