Autor Beitrag
Gausi
ontopic starontopic starontopic starontopic starontopic starontopic starofftopic starofftopic star
Beiträge: 8535
Erhaltene Danke: 473

Windows 7, Windows 10
D7 PE, Delphi XE3 Prof, Delphi 10.3 CE
BeitragVerfasst: Fr 11.11.05 14:59 
MP3FileUtils, v0.6a

Diese Unit liest aus einer MP3-Datei alle (?) gängigen Informationen aus. Wie bei vielen anderen auch wird der ID3v1-Tag gelesen, fast alle Teile des ID3v2-Tags und diverse Informationen über die Datei ansich, wie z.B. Bitrate und Spieldauer.

Download:
  • Mp3FileUtils - Quellcode inkl. der Demoprogramme. Zip-Archiv, ca. 0.5mb
  • Demos. - Komplilierte Demo-Programme zum Ausprobieren. Zip-Archiv, ca. 1.9mb
  • Lazarus-Portierung von Version 0.6 - Überarbeitung von Frank Plagge für Lazarus, inkl. Demo für Windows und Mac. Details in den Kommentaren der Unit.
  • Zum Thema Unsynchronisation: "Das Gewitterrätsel - Reloaded" (Version 1, Version 2) - Wo war das Gewitter? (Tip: beide Varianten mit dem VLC abspielen und am Scrollbalken spielen ;-))


Bugfix in 0.6a:
Da war ein fieser Copy&Paste-Bug in SetPersonalPlayCounter drin, wenn zur Bewertung einer Datei ein neuer Frame angelegt werden muss: Statt
ausblenden Delphi-Quelltext
1:
2:
if aRating <> -1 then newFrame.SetRating(aEMail, newRating);
if aCounter <> -1 then newFrame.SetRating(aEMail, newCounter);

muss es natürlich heißen
ausblenden Delphi-Quelltext
1:
2:
if aRating <> -1 then newFrame.SetRating(aEMail, newRating);
if aCounter <> -1 then newFrame.SetPersonalPlayCounter(aEMail, newCounter);

Und ich wunder mich die ganze Zeit, warum Nemp neue Alben beim Abspielen do schlecht bewertet... :autsch:

Änderungen in 0.6:
  • Methoden SetRating und SetPersonalPlayCounter zusammengefasst zu SetRatingAndCounter. Der Code in den eigenen Anwendungen muss da ggf. angepasst werden
  • Unterstützung von "Private Frames"
  • Erkennung des VBRI-Header
  • ein paar neue Genres in der Genre-Liste für ID3v1
  • neue Methoden Get/SetUserText, GetAllUsertextFrames
  • ID3v2Tag.ReadfromStream schneller: Tag wird zuerst komplett geladen, aus dem Memorystream dann die Einzelframes
  • Bugfix: Korrektes Lesen von UTF8-kodierten Textframes mit Delphi 2009
  • Bugfix: ExtendedHeader-Größe wurde falsch interpretiert
  • Bugfix: User-definierte Textframes (TXXX) haben eine andere Struktur als normale Textframes
  • Bugfix: Typ-Gemisch bei GetFrameLength behoben


Folgendes leisten die in dieser Unit implementierten Klassen:
  1. TID3v1Tag:
    • Lesen und Schreiben des ID3v1-Tags
    • Unterscheidung von v1- und v1.1-Tags

  2. TMpegInfo:
    • Lesen/Berechnen der MPEG-Informationen eines mp3-Files - z.B. Bitrate, Channelmode, Samplerate, vbr/cbr, Dauer
    • Schnelles Ermitteln der Daten: Auch bei vbr wird die Spieldauer (fast) immer korrekt ermittelt, ohne die ganze Datei lesen zu müssen

  3. TID3v2Tag:
    • Lesen und Schreiben des ID3v2-Tags
    • Unterstützung aller existierenden Versionen: v2.2, v2.3 und v2.4
    • Unterstützung der Standard-Frames wie Titel, Artist, Album
    • Unterstützung einiger weiterer Text-Frames wie orig. Artist, Composer, Mediatype, Encoder
    • Lesen und schreiben von Lyrics, Bildern, Bewertungen, URLs
    • Lesen und schreiben beliebiger Daten
    • Unterstützung von Unsynchronisation, GroupIDs und Datalength-Bytes
    • Unterstützung von Unicode
    • Unbekannte Frames (~ Informationsfelder) im Tag bleiben erhalten

Für Details verweise ich auf die beiliegende Dokumentation und die verschiedenen Demoprojekte.

Evtl. benötigte Zusatzkomponenten/Units:
Nur für Delphi 2007 oder früher. Verwendung kann in der Datei Config.inc geändert werden.
Für Fehlermeldungen oder Codeoptimierungen bin ich jederzeit offen - hier im Thread, per PN oder per Mail.

Edit: Text an die neue Version angepasst.

_________________
We are, we were and will not be.


Zuletzt bearbeitet von Gausi am Sa 03.12.11 19:18, insgesamt 17-mal bearbeitet

Für diesen Beitrag haben gedankt: Chatfix, juergen63
retnyg
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 2754

SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
BeitragVerfasst: Fr 11.11.05 15:14 
der code ist ja riesig ^^
kann mir nicht vorstellen dass das alles benötigt wird....naja

vielleicht könntest du die exe und die 2. kopie der unit weglassen dann wird die datei n stück kleiner

_________________
es gibt leute, die sind genetisch nicht zum programmieren geschaffen.
in der regel haben diese leute die regel...
Gausi Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starofftopic starofftopic star
Beiträge: 8535
Erhaltene Danke: 473

Windows 7, Windows 10
D7 PE, Delphi XE3 Prof, Delphi 10.3 CE
BeitragVerfasst: Fr 11.11.05 16:26 
user profile iconretnyg hat folgendes geschrieben:
der code ist ja riesig ^^
kann mir nicht vorstellen dass das alles benötigt wird....naja

Wenn man den Krempel weglässt, den man zur Unterscheidung der diversen v2-Tag-Versionen weglässt, und den Teil mit Bildern und Lyrics, und ein paar Kommentare, dann kann man sich einiges sparen, ja.
Die eine oder andere Funktion kann man sicherlich noch kürzen/optimieren, aber prinzipiell braucht man das alles. (Ok, die Language-Codes am Ende könnte man weglassen ^^) Wie gesagt: Für Code-Optimierungen bin ich jederzeit offen!

user profile iconretnyg hat folgendes geschrieben:
vielleicht könntest du die exe und die 2. kopie der unit weglassen dann wird die datei n stück kleiner
Zum schnellen Ausprobieren der Demo finde ich eine mitgelieferte exe eigentlich ganz praktisch, und so riesig ist der Download ja nun auch nicht. Selbst mit nem Modem dürfte das in 2 Minuten erledigt sein.

_________________
We are, we were and will not be.
retnyg
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 2754

SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
BeitragVerfasst: Fr 11.11.05 21:15 
auf delphi.about.com gibts nen mp3player mit eingebautem id3-editor zum download, der id3 code ist dort ca. 200 zeilen lang...
weiss jetzt allerdings nicht mehr auswendig, ob damit auch id3v2 funktioniert.

_________________
es gibt leute, die sind genetisch nicht zum programmieren geschaffen.
in der regel haben diese leute die regel...
Luckie
Ehemaliges Mitglied
Erhaltene Danke: 1



BeitragVerfasst: Fr 11.11.05 21:57 
Und ich darf den Moderator noch mal daraufhinweisen, dass man verpflichtet ist, die Unit komplett als Source im Posting zu posten. :mrgreen:
Gausi Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starofftopic starofftopic star
Beiträge: 8535
Erhaltene Danke: 473

Windows 7, Windows 10
D7 PE, Delphi XE3 Prof, Delphi 10.3 CE
BeitragVerfasst: Fr 11.11.05 22:27 
Der 200 Zeilen Code ist nur id3v1. Dieser ist sehr einfach gehalten und benötigt auch bei mir nicht wesentlich mehr.

@Luckie: Ich weiss. Ich nehme mir auch nicht das Recht heraus, den Code hier nicht direkt zu posten, weil ich Moderator bin, sondern weil der komplette Code sehr lang ist, und der Code auch bei eingeklappten Quelltext-Fenster komplett geladen wird.
Insgesamt hat die Unit gut 130kB, und das möchte ich einem Modem User nur ungern beim Laden einer Webseite zumuten. Daher habe ich von der Einhaltung dieser Regel Abstand gehalten.


Und nochmal zu dem zugegebenermaßen enormen Umfang des Codes: Da steckt auch ne ganze Menge drin. Mir ist bisher keine ID3-Unit über den Weg gelaufen, die alle Sub-Versionen des v2 Tags lesen und schreiben kann und das Lesen und Schreiben von Bildern und Lyrics unterstützt. Selbst die von mir hochgeschätzten AudioTools unterstützen nur v2.3 lesend und schreibend - die anderen Versionen werden nur gelesen. Und nicht erkannte Frames gehen dort beim Speichern verloren. (Zumindest in der Version, die ich kürzlich runtergeladen habe.)
Außerdem denke ich, dass auch die Kommentare recht ausführlich sind.

_________________
We are, we were and will not be.
Daniel G
Hält's aus hier
Beiträge: 7



BeitragVerfasst: Mo 14.11.05 23:35 
user profile iconGausi hat folgendes geschrieben:

Insgesamt hat die Unit gut 130kB, und das möchte ich einem Modem User nur ungern beim Laden einer Webseite zumuten. Daher habe ich von der Einhaltung dieser Regel Abstand gehalten.


Dafür dankt dir der Daniel :lol: .
Dolles Ding!
larshgf
Hält's aus hier
Beiträge: 6

Windows XP

BeitragVerfasst: Do 17.11.05 21:44 
Hi everybody,

Sorry, but my german language is even vorse than my english.
I just want to thank the creator of this Mp3FileUtils. It's a fantastic work you've done here! I have only programmed a little with the mp3 files as object, and that was only concerning the ID3v1, which is - as you all probably know - a lot simpler than the complex ID3v2 data format.
I wonder if it's possible to build som unicode support into this mp3fileUtils? Maybee with the help from the free TNTWare by Troy Wolbrink in USA. (www.tntware.com/delphicontrols/unicode/). Have the author considered to do that?

Kindest Regards
Lars
Gausi Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starofftopic starofftopic star
Beiträge: 8535
Erhaltene Danke: 473

Windows 7, Windows 10
D7 PE, Delphi XE3 Prof, Delphi 10.3 CE
BeitragVerfasst: Do 17.11.05 22:07 
Hi,

Yes, there is _some_ unicode support in this Unit. It is possible to read unicode-formatted strings from the tags. These strings are automatically converted to ANSII (or better: I hope they are...;-)) - just because the DelphiVCL (without third-party components) has no support for Unicode strings.

I did not found many mp3Files with Unicode-tags (and do not know how to search for them), so this is not well tested.
I tested it with some unicode-files, but the contained chars are only pseudo-unicode - one byte of the two-byte-chars was always $00. I have absolutely no idea what happens, when this is used with japanese or chinese mp3files.

It is (yet) not supported to write Unicode formatted strings to the tag. One of the reasons is: I dont know any taggers with full unicode support, so I cant test wether the things i write to the file are correct. And another: There is afaik no way to type unicode formatted strings into a VCl-component...

_________________
We are, we were and will not be.
oern
ontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic starofftopic star
Beiträge: 142

Linux, Win XP
D7
BeitragVerfasst: So 12.02.06 18:40 
Zitat:
Diese Unit liest aus einer MP3-Datei alle (?) gängigen Informationen aus. Wie bei vielen anderen auch wird der ID3v1-Tag gelesen, einige Teile des ID3v2-Tags und diverse Informationen über die Datei ansich, wie z.B. Bitrate und Spieldauer.


Wie lese ich denn die Spieldauer aus ? Das find ich irgentwie nicht :(

_________________
Ich hab eine Signatur
Gausi Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starofftopic starofftopic star
Beiträge: 8535
Erhaltene Danke: 473

Windows 7, Windows 10
D7 PE, Delphi XE3 Prof, Delphi 10.3 CE
BeitragVerfasst: So 12.02.06 18:45 
Die Dauer steht nicht im ID3 Tag, sondern wird aus den MPEG-Headern ermittelt. Daher steckt die Dauer in den MpegInfos mit drin:
ausblenden Delphi-Quelltext
1:
2:
3:
4:
mpegInfo := TMpegInfo.create;
mpeginfo.loadFromFile(meineDatei);
showmessage(inttostr(mpeginfo.dauer));
mpegInfo.Free;

_________________
We are, we were and will not be.
oern
ontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic starofftopic star
Beiträge: 142

Linux, Win XP
D7
BeitragVerfasst: So 12.02.06 21:02 
Danke klappt wunderbar :)

_________________
Ich hab eine Signatur
Ironwulf
ontopic starontopic starontopic starontopic starontopic starontopic starofftopic starofftopic star
Beiträge: 733
Erhaltene Danke: 2



BeitragVerfasst: Mo 13.02.06 19:04 
unter delphi 3 kann ich das leider nich compilieren, das einige probleme gibt
z.b. hier:
ausblenden Delphi-Quelltext
1:
TBuffer = Array of byte;					


ich vermute mal das man sowas als dynamischen array bezeichnet="?" kp zumindest kann das mein delphi nit

oder der teil hier:
ausblenden Delphi-Quelltext
1:
2:
3:
function GetFrameIndex(ID:integer):integer; Overload;
    function GetFrameIndex(ID:integer;Language:string;Description:string):integer; Overload;
    function GetFrameIndex(Description:TPictureFrameDesription):integer; Overload;


und mit Longword und Int64 kanns auch nichts anfangene aber ich glaub die könnte man notfalls noch durch normales word und integer ersetzen

gibts da alternativen für oder muss ich mir selbst eine ähnliche unit ausm kopf drücken
Gausi Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starofftopic starofftopic star
Beiträge: 8535
Erhaltene Danke: 473

Windows 7, Windows 10
D7 PE, Delphi XE3 Prof, Delphi 10.3 CE
BeitragVerfasst: Mo 13.02.06 19:21 
Ja, TBuffer ist ein dynamisches Array, und die gabs bei D3 noch nicht. Evtl. kannst du das so umbauen, dass du da auch ne statische Größe dafür verwenden kannst. Hab das jetzt nicht genau im Kopf, wo ich welche Buffer-Länge brauche. Evtl. nimmst du anstelle eines Types TBuffer mehrere verschiedene, die sich in der Länge unterscheiden.
Die Int64-Variablen kannst du durch Integer ersetzen, bekommst dann aber unter Umständen Probleme bei großen Dateien, die theoretisch möglich sind (die Grenze war da glaube ich 2 oder 4 GB).
Die LongWords könnten Probleme machen, da z.B. die Funktion "Int28ToInt32" auf die interne Struktur des Longwords zurückgreift, um die Werte schnell zu konvertieren. Da musst du dann ggf. diese Routinen ändern, damit hinterher die Größenangaben im ID3v2-Header und den einzelnen Frames stimmt.

Also: das Umbauen auf D3 ist mit Sicherheit möglich, aber nicht trivial.

_________________
We are, we were and will not be.
Jakob Schöttl
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 929
Erhaltene Danke: 1


Delphi 7 Professional
BeitragVerfasst: Di 11.07.06 07:56 
Sehr gut!
Ich hab nur eine Frage dazu: Wenn ich nicht weiß, ob meine mp3 version 1 oder 2 ist, was mach ich dann. Zeigt Id3v2Tag auch die Tags einer Version 1 an?
Gausi Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starofftopic starofftopic star
Beiträge: 8535
Erhaltene Danke: 473

Windows 7, Windows 10
D7 PE, Delphi XE3 Prof, Delphi 10.3 CE
BeitragVerfasst: Di 11.07.06 08:33 
Nein. ID3v1 und v2 sind ja nicht nur einfach unterschiedliche Versionen ein und deselben Dings, sondern vollkommen unterschiedlich in ihrem Aufbau, Umfang, und vor allem auch erstmal ihrer Position in der Datei.
Daher kann TID3v2Tag die Tags der Version 1 nicht anzeigen, da die beiden nichts gemeinsam haben (wenn man mal davon absieht, dass beide Konstrukte zur Speicherung gewisser Informationen genutzt werden). Das macht auch eigentlich keinen Sinn, denn:
Es können in einer mp3-Datei immer auch beide Versionen vorhanden sein - v2 am Anfang, und v1 am Ende der Datei. Ob und welche Tags vorhanden sind, kann man mit dem Exists-Flag abfragen, der True ist, wenn der Tag vorhanden ist.

Für eine bloße Anzeige der Meta-Informationen (z.B. in einem mp3-Player) ist evtl. dieser Beitrag noch hilfreich, wo ein System vorgestellt wird, das sich auch recht leicht auf andere Dateitypen (ogg, wma,..) erweitern lässt, ohne den eigentlichen Code des Players später verändern zu müssen.
Bei einen Tag-Editor sollte man einstellen können, welche Version (ggf. beide oder nur die vorhandene(n)) geschrieben werden soll. Außerdem ist da eine separate Anzeige beider Tags sinnvoll.

Nochwas: Deine "mp3 Version" dürfte fast immer 1 sein - aber das hat mit dem ID3-Tag nichts zu tun, sondern mit dem MPEG-Codec dahinter. Und der dürfte in 99% aller Fälle MPEG1, Layer 3 sein ;-)

_________________
We are, we were and will not be.
Jakob Schöttl
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 929
Erhaltene Danke: 1


Delphi 7 Professional
BeitragVerfasst: Di 11.07.06 10:06 
Ok, Vielen dank!
der Link hat mir schon geholfen. Ich muss mir den Quellcode noch genauer anschauen, vielleicht kann ich dann auch diese AudioTags schreiben, nicht nur lesen.
Gausi Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starofftopic starofftopic star
Beiträge: 8535
Erhaltene Danke: 473

Windows 7, Windows 10
D7 PE, Delphi XE3 Prof, Delphi 10.3 CE
BeitragVerfasst: Di 11.07.06 10:32 
Zum schreiben kannst du die Routinen aus Mp3FileUtils benutzen. Wie man die benutzt, sollte in dem Demo-Projekt klar werden. Das Vorgehen sollte prinzipiell so sein:

- Lesen des alten Tags aus der Datei,
- Setzen/Ändern der Informationen,
- Schreiben in die Datei.

Zuerst Lesen ist deshalb dringend empfohlen, weil im ID3v2Tag jede Menge Informationen stecken können, die nicht "standard" sind. Diese würden verloren gehen, wenn du einfach einen neues Objekt TID3v2Tag erstellst, mit ein paar Informationen füllst und dann in die Datei reinschreibst.
Wenn du zuerst das vorhandene aus der Datei ausliest und dann einige Sachen änderst, bleiben die anderen Informationen erhalten.

_________________
We are, we were and will not be.
Jakob Schöttl
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 929
Erhaltene Danke: 1


Delphi 7 Professional
BeitragVerfasst: Di 11.07.06 13:26 
Ja, aber mein Problem ist ja auch wieder, dass ich nicht weiß, wann ich TId3v1Tag und TId3v2Tag zum schreiben der Tags nehmen muss. Wenn ich das wüsste, könnte ich ja auch gleich mit diesen Objekten die Tags lesen.
Gausi Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starofftopic starofftopic star
Beiträge: 8535
Erhaltene Danke: 473

Windows 7, Windows 10
D7 PE, Delphi XE3 Prof, Delphi 10.3 CE
BeitragVerfasst: Di 11.07.06 14:29 
Hmmm...ich versuche, es mal von Anfang an zu erklären. Also. Eine mp3-Datei sieht - sehr stark vereinfacht - so aus:
ausblenden Quelltext
1:
2:
3:
[optional] ID3-Tag (Version 2)
[immer] Audiodaten
[optional] ID3-Tag (Version 1)


Wenn du nun bei einer gegebenen mp3-Datei den ID3-Tag in der Version 1 auslesen willst, dann geht das mit dieser Klasse hier ganz einfach so:
ausblenden Delphi-Quelltext
1:
2:
3:
meinID3v1Tag := TID3v1Tag.create;
// evtl. heißen die Routinen etwas anders
meinID3v1Tag.ReadfromFile('c:\meinmp3.mp3');

Version 2 geht ganz analog:
ausblenden Delphi-Quelltext
1:
2:
3:
meinID3v2Tag := TID3v2Tag.create;
// evtl. heißen die Routinen etwas anders
meinID3v2Tag.ReadfromFile('c:\meinmp3.mp3');

Wenn du wissen willst, ob überhaupt ein ID3-Tag vorhanden ist, kannst du anschließend sowas machen:
ausblenden Delphi-Quelltext
1:
2:
if meinID3v1Tag.exists then showmessage('ID3-Tag in Version 1 vorhanden');
if meinID3v2Tag.exists then showmessage('ID3-Tag in Version 2 vorhanden');

Zum Schreiben kannst du dann entweder den Tag nehmen, der schon vorhanden ist, oder einfach immer v1 oder immer v2 nehmen. Das is vollkommen egal. Beide Tags können in jede mp3-Datei geschrieben werden. Es muss keiner geschrieben werden, und welche Version, ist vollkommen dir (bzw. besser dem User) überlassen.
Ein meinID3v2Tag.WriteToFile('c:\meinmp3.mp3') schreibt das Objekt an den Anfang der Datei genauso wie ein meinID3v1Tag.WriteToFile('c:\meinmp3.mp3') ein etwas anders aufgebautes Objekt ans Ende schreibt. Das die Informationen in diesen Objekten, die da geschrieben werden, einigermaßen sinnvoll sind, dafür ist der Programmierer der Enduser-Software verantwortlich. Es ist mit den Methoden aus MP3FileUtils durchaus so etwas möglich:
ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
meinID3v1Tag := TID3v1Tag.create;
meinID3v2Tag := TID3v2Tag.create;
meinID3v1Tag.ReadFromFile('C:\Klassik\Eine kleine Nachtmusik.mp3')
meinID3v2Tag.ReadFromFile('C:\Kinderlieder\Hänschen klein.mp3');
meinID3v1Tag.WriteToFile('C:\Metal\Metallica\Nothing Else Matters.mp3');
meinID3v2Tag.WriteToFile('C:\Metal\Metallica\Nothing Else Matters.mp3');

Aber ob das nun sinnvoll ist, ist eine ganz andere Frage. Das Ergebnis wäre hier wahrscheinlich, dass die Datei im Autoradio als "eine kleine nachtmusik" erscheint, und in Winamp als "Hänschen klein", obwohl beidesmal "Nothing else matters" gespielt wird.

Daher empfiehlt sich z.B. sowas:
ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
//alte Tags lesen
meinid3v1.ReadfromFile('c:\meinmp3.mp3');
meinid3v2.ReadfromFile('c:\meinmp3.mp3');
// Informationen setzen
meinid3v1.Titel := Edit1.text;
meinid3v2.Titel := Edit1.text;
meinid3v1.Artist := Edit2.text;
meinid3v2.Artist := Edit2.text;
// schreiben
meinid3v1.WriteToFile('c:\meinmp3.mp3');
meinid3v2.WriteToFile('c:\meinmp3.mp3');


Alternativ zu den letzten beiden Zeilen kann man auch sowas machen:
ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
if meinid3v1.exists then meinid3v1.WriteToFile('c:\meinmp3.mp3');
if meinid3v2.exists then meinid3v2.WriteToFile('c:\meinmp3.mp3');
//oder auch:
if WriteID3v1Checkbox.Checked then meinid3v1.WriteToFile('c:\meinmp3.mp3');
if WriteID3v2Checkbox.Checked then meinid3v2.WriteToFile('c:\meinmp3.mp3');

Ich hoffe, es wird langsam etwas klarer ;-)