複数のデータ項目のデルファイ/リストの音楽プレーヤーのプレイリスト

StackOverflow https://stackoverflow.com/questions/2259537

質問

私は、Delphi / Pascalで自分の音楽プレーヤーのプレイリストを持っていると思います。

さらに - - 曲の名前でTListBoxコンポーネント

私はMP3ファイルのパスとTStringListのを持っているための最善の解決策になるだろうと思いました。両方のリスト内の一致する文字列が同じ位置にある必要があります。ユーザーがTListBoxコンポーネントの項目5を選択した場合だから、僕はTStringListのでは5位にパスを取ることができます。

これは正常に動作します。

しかし、今、私は2つのカラムを持つプレイリスト必要があります。「アーティスト」と「曲名」を。あなたは、アーティスト(昇順と降順)によってだけでなく、曲のタイトル(昇順と降順)でプレイリストを並べ替えることができるはず - 。アルファベット順、もちろん

私はこれをどのように行うことができますか? TStringListにの二つのオブジェクト持つ? - アーティストによってソート1と歌のタイトルでソートされたものを

役に立ちましたか?

解決

私は時間をかけてこれらの「リスト」の数をやったし、最後に私はいつも控えめに言っても「挑戦」であることが証明されたクラスはかなり容易になりますが、保存すると、特にディスクからリストを読み込むことがわかりました。

の課題は、このように発生しやすいリストのエラーを読んで作り、ユーザーが実際に外部エディタでリストを操作された場合にはなっています。

// schworak:

普遍的に受け入れプレイリスト形式(M3U)の場合は、のhttpを見てみましょう。 COM /プログラミング/音楽/ playlist_m3u.aspするます。

複数のフォーマットを読み出すソースとVCLコンポーネントは、Torryのいわゆる「プレイリストv.0.5.1」で入手可能です。 http://www.torry.net/quicksearchd。 PHP?文字列=プレイリスト+ v.0.5.1&タイトル=はい

他のヒント

私は1以上のソート方法を提供する少なくともアーティストやタイトルのプロパティ、およびTSongListを含むTSongクラスを行うだろう(sの適切なソートフィールドを使用して(一般的なことができます)。
確かに...あなたは、管理ソートするときの同期や改造に維持する必要があります2つの別々のStringListsを維持していない

ちょっとそれを実施する1つの安価な方法は、あなたが別の列に並べ替えることができますグリッドに表示アーティストとパスを含むレコードを持つメモリのDataSetに持っている可能性があります。
現在の行が直接両方の情報を与える。

一つの簡単な解決策は、TCollectionのように自分の曲リスト/曲情報を実装することになります。

あなたはVCLがロードを処理させることができ、コレクションを使用してディスクに保存すること。

これは機能的に完全ではありませんのでご注意ください、私はあなたにそれを任せる、と私は私の頭の上からこれを書いたので、私はめちゃめちゃ何かを持っているかもしれません。それはあなたが始めるための唯一の例です。

{...}
interface

Type
  TSongCollectionItem = class(TCollectionItem)
  public
    constructor create(Owner:TCollection); override;
    procedure assign(source : TPersistent); override;
  published
    property FileName : String read fFileName Write fFileName;
    property Artist : string read fArtist write fArtist;
    property Title : string read fTitle write fTitle;
    {...}
    property Album : string read fAlbum write fAlbum;
  end;

  TSongCollection = class(TOwnedCollection)
  private
    function GetItem(Index: Integer): TSongCollectionItem;
    procedure SetItem(Index: Integer; Value: TSongCollectionItem);
  public
    constructor Create(AOwner: TPersistent);
    function Add: TSongCollectionItem;
    property Songs[Index: Integer]: TSongCollectionItem read GetItem write SetItem; default;
  end;

  procedure SaveSongList(Songs : TSongCollection; FileName:string; Binary:boolean);
  procedure LoadSongList(Songs : TSongCollection; FileName:string; Binary:boolean);

{...}

implementation

{...}

type  
  TSongComponent = class(TComponent)
  published
    property SongList : TSongCollection read fsonglist write SetSongList;
  end;

  procedure SaveSongList(Songs : TSongCollection; FileName:string; Binary:boolean);
  var
    wFile : TFileStream;
    wConvert : TMemoryStream;
    wSongList : TSongComponent;
  begin
    RegisterClass(TSongComponent);
    Try
      wConvert := TMemoryStream.Create;
      wFile := TFileStream.Create(filename, fmcreate);
      wSongList := TSongComponent.create(nil);
      try
        wSongList.SongList.Assign(Songs);
        if not Binary then
        begin
          wConvert.WriteComponent(wSongList);
          wConvert.Position := 0;
          ObjectBinaryToText(wConvert, wFile);
        end
        else
          wFile.WriteComponent(wSongList);
      finally
        wConvert.Free;
        wFile.Free;
        wSongList.free;
      end;
    finally
      Unregisterclass(TSongComponent);
    end;
  end;

  procedure LoadSongList(Songs : TSongCollection; FileName:string; Binary:boolean);
  var
    wFile : TFileStream;
    wConvert : TMemoryStream;
    wSongList : TSongComponent;
  begin
    RegisterClass(TSongComponent);
    Try
      wConvert := TMemoryStream.Create;
      wFile := TFileStream.Create(filename, fmOpenRead);
      try
        if not Binary then
        begin
          ObjectTextToBinary(wFile, wConvert);
          wConvert.Position := 0;
          wSongList := TSongComponent(wConvert.ReadComponent(Nil));
        end
        else
          wSongList := TSongComponent(wFile.ReadComponent(Nil));

        if assigned(Songs) and assigned(wSongList) then
          Songs.Assign(wSongList.Songs);

        if assigned(wSongList) then
          wSongList.free; 
      finally
        wConvert.Free;
        wFile.Free;
      end;
    finally
      Unregisterclass(TSongComponent);
    end;
  end;
あなたはグローバルオブジェクト構造を構築したくない場合は、

、あなたはオールウェイズレポートモードでTListViewの構造を使用することができます。 あなたは下位項目で、そこにリストを持っています。 あなたは、列でソート、およびCSVまたは任意の形式に保存することができます。 あなたは簡単にアイコンなどを追加することができます.....

あなたがトリガする権利イベントがあります。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top