diff options
Diffstat (limited to 'plugins/Watrack/players/pl_foobar.pas')
-rw-r--r-- | plugins/Watrack/players/pl_foobar.pas | 534 |
1 files changed, 534 insertions, 0 deletions
diff --git a/plugins/Watrack/players/pl_foobar.pas b/plugins/Watrack/players/pl_foobar.pas new file mode 100644 index 0000000000..f861db6327 --- /dev/null +++ b/plugins/Watrack/players/pl_foobar.pas @@ -0,0 +1,534 @@ +{Foobar2000 player}
+unit pl_Foobar;
+{$include compilers.inc}
+
+interface
+
+implementation
+uses {$IFDEF KOL_MCK}err,{$ENDIF}
+ windows,common,syswin,wrapper,srv_player,messages,wat_api,winampapi
+ {$IFDEF DELPHI_7_UP}
+ ,variants
+ {$ENDIF}
+ {$IFDEF KOL_MCK}
+ ,kolcomobj
+ {$ELSE}
+ ,ComObj
+ {$ENDIF}
+;
+
+const
+ COMName:PAnsiChar = 'Foobar2000.Application.0.7';
+const
+ dummywnd = 'uninteresting';
+const
+ FooExe = 'FOOBAR2000.EXE';
+ FooPrefix = 'foobar2000 v';
+const
+ FooBarClassExt = '{97E27FAA-C0B3-4b8e-A693-ED7881E99FC1}';
+ FooBarClassNew = '{DA7CD0DE-1602-45e6-89A1-C2CA151E008E}';
+ FooBarClassAdd = '{E7076D1C-A7BF-4f39-B771-BCBE88F2A2A8}';
+(*
+ class1='{B73733CA-9B0A-4f53-93FA-AC95D4FF2166}';
+ text1='Cthulhu fhtagn!';
+
+ '{53229DFC-A273-45cd-A3A4-161FA9FC6414}';
+ '{641C2469-355C-4d6f-9663-E714382DA462}';
+*)
+var
+ WinampWindow:HWND;
+
+function proc(awnd:hwnd;param:pdword):boolean; stdcall;
+var
+ s:array [0..255] of AnsiChar;
+begin
+ result:=true;
+ if (awnd<>param^) and (GetClassNameA(awnd,s,255)>0) then
+ begin
+ s[Length(FooBarClassNew)]:=#0;
+ if (StrCmp(s,FooBarClassExt)=0) or
+ (StrCmp(s,FooBarClassNew)=0) or
+ (StrCmp(s,FooBarClassAdd)=0) then
+ begin
+ GetWindowTextA(awnd,s,255);
+ if StrCmp(s,dummywnd)<>0 then
+ param^:=awnd;
+// if WinampWindow<>0 then
+// result:=false;
+ end
+
+ else if (WinampWindow=0) and (StrCmp(s,WinampClass)=0) then
+ begin
+ WinampWindow:=awnd;
+ end;
+
+ end;
+end;
+
+function Check(wnd:HWND;flags:integer):HWND;cdecl;
+var
+ tmp,EXEName:PAnsiChar;
+ lwnd:HWND;
+ ltmp:bool;
+begin
+ if wnd<>0 then
+ begin
+ result:=0;
+ exit;
+ end;
+ lwnd:=0;
+ repeat
+ lwnd:=FindWindowEx(0,lwnd,nil,dummywnd);
+ if lwnd=0 then
+ break;
+ tmp:=Extract(GetEXEByWnd(lwnd,EXEName),true);
+ mFreeMem(EXEName);
+ ltmp:=lstrcmpia(tmp,FooExe)=0;
+ mFreeMem(tmp);
+ if ltmp then
+ begin
+ WinampWindow:=0;
+ EnumThreadWindows(GetWindowThreadProcessId(lwnd,nil),@proc,int_ptr(@lwnd));
+ break;
+ end;
+ until false;
+ result:=lwnd;
+end;
+
+function GetYear(const v:variant):PWideChar;
+begin
+ try
+ StrDupW(result,PWideChar(WideString(v.Playback.FormatTitle('[%year%]'))));
+ except
+ result:=nil;
+ end;
+end;
+
+function GetArtist(const v:variant):PWideChar;
+begin
+ try
+ StrDupW(result,PWideChar(WideString(v.Playback.FormatTitle('[%artist%]'))));
+ except
+ result:=nil;
+ end;
+end;
+
+function GetTitle(const v:variant):PWideChar;
+begin
+ try
+ StrDupW(result,PWideChar(WideString(v.Playback.FormatTitle('[%title%]'))));
+ except
+ result:=nil;
+ end;
+end;
+
+function GetAlbum(const v:variant):PWideChar;
+begin
+ try
+ StrDupW(result,PWideChar(WideString(v.Playback.FormatTitle('[%album%]'))));
+ except
+ result:=nil;
+ end;
+end;
+
+function GetGenre(const v:variant):PWideChar;
+begin
+ try
+ StrDupW(result,PWideChar(WideString(v.Playback.FormatTitle('[%genre%]'))));
+ except
+ result:=nil;
+ end;
+end;
+
+function GetBitrate(const v:variant):integer;
+begin
+ try
+ result:=v.Playback.FormatTitle('%bitrate%');
+ except
+ result:=0;
+ end;
+end;
+
+function GetSamplerate(const v:variant):integer;
+begin
+ try
+ result:=v.Playback.FormatTitle('%samplerate%');
+ except
+ result:=0;
+ end;
+end;
+
+function GetChannels(const v:variant):integer;
+var
+ s:WideString;
+begin
+ result:=0;
+ try
+ s:=v.Playback.FormatTitle('%channels%');
+ if StrCmpW(pWideChar(s),'mono')=0 then
+ result:=1
+ else if StrCmpW(pWideChar(s),'Stereo')=0 then
+ result:=2;
+ except
+ end;
+end;
+
+function GetCodec(const v:variant):integer;
+var
+ s:WideString;
+ i:integer;
+begin
+ result:=0;
+ try
+ s:=v.Playback.FormatTitle('%codec%');
+ i:=Length(s);
+ if i>0 then result:=ORD(s[1]);
+ if i>1 then result:=result+(ORD(s[2]) shl 8);
+ if i>2 then result:=result+(ORD(s[3]) shl 16);
+ if i>3 then result:=result+(ORD(s[4]) shl 24);
+ except
+ end;
+end;
+
+function SplitVersion(p:pWideChar):integer;
+begin
+ result:=StrToInt(p);
+ while (p^>='0') and (p^<='9') do inc(p); inc(p);
+ result:=result*16+StrToInt(p);
+ while (p^>='0') and (p^<='9') do inc(p); inc(p);
+ result:=result*16+StrToInt(p);
+ while (p^>='0') and (p^<='9') do inc(p);
+ if p^<>#0 then inc(p);
+ if (p^>='0') and (p^<='9') then
+ begin
+ result:=result*16+StrToInt(p);
+ while (p^>='0') and (p^<='9') do inc(p);
+ end;
+ if p^<>#0 then
+ begin
+ inc(p);
+ while (p^<>#0) and (p^<>' ') do inc(p);
+ if p^=' ' then
+ begin
+ inc(p);
+ result:=result*16+StrToInt(p);
+ end;
+ end;
+end;
+
+function GetVersion(const ver:pWideChar):integer;
+begin
+ if (ver=nil) or (ver^=#0) then
+ result:=0
+ else
+ result:=SplitVersion(ver);
+end;
+
+function GetVersionText(const v:variant):PWideChar;
+begin
+ try
+ StrDupW(result,PWideChar(WideString(v.Name))+length(FooPrefix));
+ except
+ result:=nil;
+ end;
+end;
+
+function GetTotalTime(const v:variant):integer;
+begin
+ try
+ result:=v.Playback.Length;
+ except
+ result:=0;
+ end;
+end;
+
+function GetElapsedTime(const v:variant):integer;
+begin
+ try
+ result:=v.Playback.Position;
+ except
+ result:=0;
+ end;
+end;
+
+function GetStatus(wnd:HWND):integer; cdecl;
+var
+ tmp:boolean;
+ v:variant;
+ winampwnd:HWND;
+begin
+ try
+ result:=WAT_MES_STOPPED;
+ v:=GetActiveOleObject(COMName);
+ tmp:=v.Playback.IsPaused;
+ if tmp then
+ result:=WAT_MES_PAUSED
+ else
+ begin
+ tmp:=v.Playback.IsPlaying;
+ if tmp then
+ result:=WAT_MES_PLAYING;
+ end;
+ except
+ winampwnd:=WinampFindWindow(wnd);
+ if winampwnd<>0 then
+ result:=WinampGetStatus(winampwnd)
+ else
+ result:=WAT_MES_UNKNOWN;
+ end;
+ v:=null;
+end;
+
+function GetWndText(wnd:HWND):pWideChar;
+var
+ i:integer;
+begin
+ result:=GetDlgText(wnd);
+ if result<>nil then
+ begin
+ i:=StrIndexW(result,'[foobar');
+ if i<>0 then
+ begin
+ dec(i);
+ repeat
+ dec(i);
+ if ord(result[i])>ord(' ') then break;
+ until i<0;
+ result[i+1]:=#0;//if at end
+ end;
+ end;
+end;
+
+function GetFileName(wnd:HWND;flags:integer):PWideChar;cdecl;
+var
+ v:variant;
+begin
+ try
+ v:=GetActiveOleObject(COMName);
+// v:=CreateOleObject(COMName);
+ StrDupW(result,PWideChar(WideString(v.Playback.FormatTitle('%path%'))));
+ except
+ result:=nil;
+ end;
+ v:=Null;
+end;
+
+function Play(const v:variant;fname:PWideChar=nil):integer;
+begin
+ try
+ result:=v.Playback.Start(false);
+ except
+ result:=0;
+ end;
+end;
+
+function Pause(const v:variant):integer;
+begin
+ try
+ result:=v.Playback.Pause;
+ except
+ result:=0;
+ end;
+end;
+
+function Stop(const v:variant):integer;
+begin
+ try
+ result:=v.Playback.Stop;
+ except
+ result:=0;
+ end;
+end;
+
+function Next(const v:variant):integer;
+begin
+ try
+ result:=v.Playback.Next;
+ except
+ result:=0;
+ end;
+end;
+
+function Prev(const v:variant):integer;
+begin
+ try
+ result:=v.Playback.Previous;
+ except
+ result:=0;
+ end;
+end;
+
+function GetVolume(const v:variant):cardinal;
+begin
+ try
+ result:=v.Playback.Settings.Volume+100;
+ result:=(result shl 16)+round((result shl 4) / 100);
+ except
+ result:=0;
+ end;
+end;
+
+procedure SetVolume(const v:variant;value:cardinal);
+begin
+ try
+ v.Playback.Settings.Volume:=integer(((loword(value)*100) shr 4)-100);
+ except
+ end;
+end;
+
+function VolDn(const v:variant):integer;
+var
+ val:integer;
+begin
+ result:=GetVolume(v);
+ val:=loword(result);
+ if val>0 then
+ SetVolume(v,val-1);
+end;
+
+function VolUp(const v:variant):integer;
+var
+ val:integer;
+begin
+ result:=GetVolume(v);
+ val:=loword(result);
+ if val<16 then
+ SetVolume(v,val+1);
+end;
+
+function Seek(const v:variant;value:integer):integer;
+begin
+ try
+ result:=v.Playback.Position;
+ if (value>0) and (v.Playback.CanSeek) and (value<v.Playback.Length) then
+ v.Playback.Seek(value)
+ else
+ result:=0;
+ except
+ result:=0;
+ end;
+end;
+
+function GetInfo(var SongInfo:tSongInfo;flags:integer):integer;cdecl;
+var
+ v:variant;
+begin
+ result:=0;
+ with SongInfo do
+ begin
+ try
+ v:=GetActiveOleObject(COMName);
+// v:=CreateOleObject(COMName);
+ if (flags and WAT_OPT_PLAYERDATA)<>0 then
+ begin
+ if SongInfo.plyver=0 then
+ begin
+ SongInfo.txtver:=GetVersionText(v);
+ SongInfo.plyver:=GetVersion(txtver);
+ end;
+ end
+ else if (flags and WAT_OPT_CHANGES)<>0 then
+ begin
+ volume:=GetVolume(v);
+ if status<>WAT_MES_STOPPED then
+ time:=GetElapsedTime(v);
+ end
+ else
+ begin
+ if kbps =0 then kbps :=GetBitrate(v);
+ if khz =0 then khz :=GetSamplerate(v);
+ if channels=0 then channels:=GetChannels(v);
+ if codec =0 then codec :=GetCodec(v);
+ if total =0 then total :=GetTotalTime(v);
+ if year =NIL then year :=GetYear(v);
+ if artist =NIL then artist :=GetArtist(v);
+ if title =NIL then title :=GetTitle(v);
+ if album =NIL then album :=GetAlbum(v);
+ if genre =NIL then genre :=GetGenre(v);
+ end;
+ except
+ SongInfo.winampwnd:=WinampWindow;
+ if SongInfo.winampwnd<>0 then
+ begin
+ result:=WinampGetInfo(int_ptr(@SongInfo),flags);
+ end;
+ end;
+ v:=Null;
+ if (flags and WAT_OPT_CHANGES)<>0 then
+ wndtext:=GetWndText(SongInfo.plwnd);
+ end;
+end;
+
+function Command(wnd:HWND;cmd:integer;value:int_ptr):integer;cdecl;
+//var
+// c:integer;
+var
+ v:Variant;
+begin
+ result:=0;
+ try
+ v:=GetActiveOleObject(COMName);
+ case cmd of
+ WAT_CTRL_PREV : result:=Prev (v);
+ WAT_CTRL_PLAY : result:=Play (v,pWideChar(value));
+ WAT_CTRL_PAUSE: result:=Pause(v);
+ WAT_CTRL_STOP : result:=Stop (v);
+ WAT_CTRL_NEXT : result:=Next (v);
+ WAT_CTRL_VOLDN: result:=VolDn(v);
+ WAT_CTRL_VOLUP: result:=VolUp(v);
+ WAT_CTRL_SEEK : result:=Seek (v,value);
+ end;
+ except
+ if WinampWindow<>0 then
+ result:=WinampCommand(WinampWindow,cmd+(value shl 16))
+{
+ else
+ begin
+ case cmd of
+ WAT_CTRL_PREV : c:=ORD('B');
+ WAT_CTRL_PLAY : c:=ORD('C');
+ WAT_CTRL_PAUSE: c:=ORD('X');
+ WAT_CTRL_STOP : c:=ORD('Z');
+ WAT_CTRL_NEXT : c:=ORD('V');
+ WAT_CTRL_VOLDN: c:=VK_SUBTRACT;
+ WAT_CTRL_VOLUP: c:=VK_ADD;
+ else
+ exit;
+ end;
+ PostMessageW(wnd,WM_KEYDOWN,c,1);
+ end;
+}
+ end;
+ v:=Null;
+end;
+
+const
+ plRec:tPlayerCell=(
+ Desc :'foobar2000';
+ flags :WAT_OPT_SINGLEINST or WAT_OPT_HASURL;
+ Icon :0;
+ Init :nil;
+ DeInit :nil;
+ Check :@Check;
+ GetStatus:@GetStatus;
+ GetName :@GetFileName;
+ GetInfo :@GetInfo;
+ Command :@Command;
+ URL :'http://www.foobar2000.org/';
+ Notes :'For more full info WinampSpam or foo_comserver (more powerful) '#13#10+
+ 'components needs to be installed.');
+
+var
+ LocalPlayerLink:twPlayer;
+
+procedure InitLink;
+begin
+ LocalPlayerLink.Next:=PlayerLink;
+ LocalPlayerLink.This:=@plRec;
+ PlayerLink :=@LocalPlayerLink;
+end;
+
+initialization
+// ServicePlayer(WAT_ACT_REGISTER,dword(@plRec));
+ InitLink;
+end.
|