Delphi-PRAXiS
Seite 1 von 3  1 23      

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Multimedia (https://www.delphipraxis.net/16-multimedia/)
-   -   Delphi ID3Tag einer String-Variable zuweisen (https://www.delphipraxis.net/15589-id3tag-einer-string-variable-zuweisen.html)

Lordnightmaere 31. Jan 2004 22:12


ID3Tag einer String-Variable zuweisen
 
Hallöchen...

Habe hier folgendes Szenario:

Delphi-Quellcode:

...

type
  TID3Tag = Record
    ID: String[3];
    Titel: String;
    Artist: String;
    Album: String;
    Year: String;
    Comment: String;
    Genre: Byte;
  end;

...

function ReadID3Tag(FileName: String): TID3Tag;
var
  FS: TFileStream;
  Buffer: Array [1..128] of Char;
begin
  FS := TFileStream.Create(FileName, fmOpenRead or fmShareDenyWrite);
  try
    FS.Seek(-128, soFromEnd);
    FS.Read(Buffer, 128);
    with Result do
    begin
      ID := Copy(Buffer, 1, 3);
      Titel := Copy(Buffer, 4, 30);
      Artist := Copy(Buffer, 34, 30);
      Album := Copy(Buffer, 64, 30);
      Year := Copy(Buffer, 94, 4);
      Comment := Copy(Buffer, 98, 30);
      Genre := Ord(Buffer[128]);
    end;
  finally
    FS.Free;
  end;
end;

...

procedure TForm1.Button1Click(Sender: TObject);
var
  S: String;
begin
  with ReadID3Tag('c:\lied.mp3') do
  begin
    S := Artist + ' - ' + Titel;
  end;
end;

...
So... Wenn ich das ganze jetzt so laufen lasse steht in der Variable S nur der Artist. Der Bindestrich und der Titel fehlen. Einem Label kann ich das so auch nicht zuordnen. Folgender Code funktioniert wiederrum:

Delphi-Quellcode:

...

procedure TForm1.Button1Click(Sender: TObject);
var
  S: String;
begin
  with ReadID3Tag('c:\lied.mp3') do
  begin
    Label1.Caption := Artist;
    Label2.Caption := Titel;
    S := Label1.Caption + ' - ' + Label2.Caption;
  end;
end;

...
Wie kann ich der Variable S ohne diesen Umweg das ganze zuweisen?


mfg

~Lordnightmaere~

chris 1. Feb 2004 09:32

Re: ID3Tag einer String-Variable zuweisen
 
hi,

ich verstehe zwar nicht warum das nicht funktionieren soll, aber
ich würde sagen mit zwei weiteren variablen anstelle der labels.

Delphi-Quellcode:
var
  S, A, T: String;
begin
  with ReadID3Tag('c:\lied.mp3') do
  begin
    A := Artist;
    T := Titel;
    S := A + ' - ' + T
  end
end

Lordnightmaere 1. Feb 2004 11:16

Re: ID3Tag einer String-Variable zuweisen
 
Hi...

habe es jetzt mit den 2 zusätzlichen Variablen probiert aber geht leider immer noch nicht.

Delphi-Quellcode:
...

var
  S, A, T: String;
begin
  with ReadID3Tag('c:\lied.mp3') do
  begin
    A := Artist;
    T := Titel;
    S := A + ' - ' + T
    ShowMessage(S); // <--- Ergebnis ist nur der Artist
    S := T + ' - ' + A;
    ShowMessage(S); // <--- Ergebnis ist nur der Titel
  end
end

...
Wenn ich jetzt versuche die Länge des Strings (S) mit StrLen zu ermitteln:

Delphi-Quellcode:
...

ShowMessage(IntToStr(StrLen(S)));

...
dann Kommt folgende Fehlermeldung:

Inkompatibele Typen: 'String' und 'PAnsiChar'

Vieleicht weiss jemand ne Lösung dafür.


mfg

~Lordnightmaere~

chris 1. Feb 2004 11:28

Re: ID3Tag einer String-Variable zuweisen
 
hi,

probiers hiermit

Delphi-Quellcode:
str(s)
dann sollte es auch im ersten fall klappen, würde ich sagen

gothic_mike 1. Feb 2004 11:40

Re: ID3Tag einer String-Variable zuweisen
 
Zitat:

Zitat von Lordnightmaere
Hallöchen...

Habe hier folgendes Szenario:

Delphi-Quellcode:
    S := Artist + ' - ' + Titel;
Wie kann ich der Variable S ohne diesen Umweg das ganze zuweisen?


mfg

~Lordnightmaere~

versuch mal folgenden code, ich glaube, dass du irgendwelche steuerzeichen aus dem ID3-Tag mit kopierst:

Delphi-Quellcode:
    S := Trim(Artist) + ' - ' + Trim(Titel);

Lordnightmaere 1. Feb 2004 11:42

Re: ID3Tag einer String-Variable zuweisen
 
:wall: :wall: :wall: !?#?! Argh !?#?! :wall: :wall: :wall:

Mit Str(S) gehts leider immernoch nicht *verzweifel*. Wenn ich...

S := Str(Artist)

versuche kommt eine sehr ausführliche Fehlermeldung -> "Inkompatible Typen".

HILFÄÄÄ!!


mfg

~Lordnightmaere~

Lordnightmaere 1. Feb 2004 11:47

Re: ID3Tag einer String-Variable zuweisen
 
Ups da war einer schneller ;-) :hello: DANKE gothic_mike!!!!! Damit funktioniert es!!! :dancer: DANKE DANKE DANKE

negaH 1. Feb 2004 12:01

Re: ID3Tag einer String-Variable zuweisen
 
Wenn ich deinen Code richtig vestanden habe, dann sind die ID3 Tag felder alle mit fester Länge codiert ?

Dann müsste die hier funktionieren:

Delphi-Quellcode:
type
  PID3Tag = ^TID3Tag;
  TID3Tag = record
    ID: String;
    Title: String;
    Artist: String;
    Album: String;
    Year: String;
    Comment: String;
    Genre: Byte;  
  end;


function ReadID3Tag(const FileName: String): TID3Tag;

  function StrLPas(Value: PChar; Len: Integer): String;
   
    function Min(A,B: Integer): Integer;
    begin
      if A <= B then Result := A
        else Result := B;
    end;

  begin
    SetString(Result, Value, Min(Len, StrLen(Value)));
    Result := Trim(Result);
  end;
 
type
  TID3Struct = packed record
    ID: array[0..2] of Char;          //   3
    Title: array[0..29] of Char;      //  33
    Artist: array[0..29] of Char;     //  63
    Album: array[0..29] of Char;      //  93 
    Year: array[0..3] of Char;        //  97
    Comment: array[0..29] of Char;    // 127
    Genre: Byte;                      // 128
  end;

var
  Tag: TID3Struct;
begin
  with TFileStream.Create(FileName, fmOpenRead or fmShareDenyNone) do
  try
    Position := Size - SizeOf(Tag);
    Read(Tag, SizeOf(Tag));
  finally
    Free;
  end;
  with Tag do
  begin
    Result.ID := StrLPas(ID, SizeOf(ID));
    Result.Title := StrLPas(Title, SizeOf(Title));
    Result.Artist := StrLPas(Artist, SizeOf(Artist));
    Result.Album := StrLPas(Album, SizeOf(Album));
    Result.Year := StrLPas(Year, SizeOf(Year));
    Result.Comment := StrLPas(Comment, SizeOf(Comment));
    Result.Genre := Genre;
  end;
end;
Leider ist der MP3 ID3 Tag so ziemlich die schlechteste Struktur die ein Programmierer sich einfallen lassen kann. Sie benutzt keine Variable Length Felder, keine Null Terminierten Chars oder eben keine PASCAL typischen Längenbasierten Strings. D.h. egal ob man in C/C++ oder PASCAL oder sonstwas programmiert, man muß IMMER eine Konvertierung der gelesenen Daten vorsehen. Dabei ist es zusätzlich noch wichtig Leerzeichen oder eventuelle Nullterminatoren zu berücksichtigen. Der ID3 ist eben eine ziemlich unprofessionelle Sache, dies merkt man auch daran das am ID3 "Standard" so viele Änderungen vorgenommen wurden.

Hier eine Version die eher C Typisch ist:

Delphi-Quellcode:
type
  TID3Tag = record
   // diese Struktur erweitert die Char arrays um ein Zeichen für Nullterminator,
   // somit muß sie Feld für Feld gelesen und geschrieben werden, da ID3 eben diese Terminatoren NICHT speichert.
    ID: array[0..3] of Char;          
    Title: array[0..30] of Char;      
    Artist: array[0..30] of Char;    
    Album: array[0..30] of Char;      
    Year: array[0..4] of Char;        
    Comment: array[0..30] of Char;    
    Genre: Byte;                      
  end;

function ReadID3Tag(const FileName: String): TID3Tag;
begin
  FillChar(Result, SizeOf(Result), 0);
  with TFileStream.Create(FileName, fmOpenRead or fmShareDenyNone) do
  try
    Position := Size - 128;
    Read(Result.ID, 3);
    Read(Result.Title, 30);
    Read(Result.Artist, 30);
    Read(Result.Album, 30);
    Read(Result.Year, 4);
    Read(Result.Comment, 30);
    Read(Result.Genre, 1);
  finally
    Free;
  end;
end;
Gruß Hagen

edosoft 25. Sep 2004 09:12

Re: ID3Tag einer String-Variable zuweisen
 
Das geht ganz einfach:
(wenn du aus einer datei mit nem TFileStream was innen String auslesen willst musst dus IMMER so machen)

Delphi-Quellcode:
var
fs:tfilestream;
s:string;
begin
[..]
fs.seek(-128,sofromend);
//jetzt musst du eben net gleich in den string lesen sondern erst mal den stringso lang machen wieviel text du auslesen willst - z.b. 3 bytes, da die erste info von id3 3 bytes lang ist ("TAG")
SetLength(S, 3);
//oder S:=stringofchar(#0, 3);
// oder s:='  ';
//ist auch egal welchen buchstaben S enthält kannst also z.b. auch S:='ABC', wird ja eh überschrieben
fs.read(s[1], 3);
//du musst halt unbedingt "S[1]" angeben, sonst gehts net, weis au net warum aber es ist halt so...
showmessage(s);
edit1.text:=s;
[..]
end
und wie gesagt, so musst dus immer machen wenn du ne datei innen sting lesen willst.
:mrgreen:

-hope it helps

Muetze1 25. Sep 2004 20:31

Re: ID3Tag einer String-Variable zuweisen
 
Moin!

Zitat:

Zitat von negaH
Leider ist der MP3 ID3 Tag so ziemlich die schlechteste Struktur die ein Programmierer sich einfallen lassen kann. Sie benutzt keine Variable Length Felder, keine Null Terminierten Chars oder eben keine PASCAL typischen Längenbasierten Strings. D.h. egal ob man in C/C++ oder PASCAL oder sonstwas programmiert, man muß IMMER eine Konvertierung der gelesenen Daten vorsehen. Dabei ist es zusätzlich noch wichtig Leerzeichen oder eventuelle Nullterminatoren zu berücksichtigen. Der ID3 ist eben eine ziemlich unprofessionelle Sache, dies merkt man auch daran das am ID3 "Standard" so viele Änderungen vorgenommen wurden.

Das trifft nur auf den ID3 Tag v1.0 und v1.1 zu!

MfG
Muetze1


Alle Zeitangaben in WEZ +1. Es ist jetzt 14:37 Uhr.
Seite 1 von 3  1 23      

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz