You've already forked lazarus-ccr
git-svn-id: https://svn.code.sf.net/p/lazarus-ccr/svn@1748 8e941d3f-bd1b-0410-a28a-d453659cc2b4
248 lines
7.2 KiB
ObjectPascal
248 lines
7.2 KiB
ObjectPascal
//******************************************************************************
|
|
//*** Cactus Jukebox ***
|
|
//*** ***
|
|
//*** (c) 2006-2009 ***
|
|
//*** ***
|
|
//*** Massimo Magnano, maxm.dev@gmail.com ***
|
|
//*** ***
|
|
//******************************************************************************
|
|
// File : cj_pluginslist.pas
|
|
//
|
|
// Description : List of Plugins and other plugins functions.
|
|
//
|
|
//******************************************************************************
|
|
unit cj_pluginslist;
|
|
{$mode delphi}{$H+}
|
|
interface
|
|
|
|
uses dynlibs, global_vars, MGList, cj_plugin, cj_interfaces, cj_interfaces_impl;
|
|
|
|
type
|
|
TCJ_PluginDescr = record
|
|
DllHandle :TLibHandle;
|
|
DllPath :String;
|
|
Enabled :Boolean;
|
|
pClass :TCJ_Plugin;
|
|
Info :TCJ_PluginInfo;
|
|
end;
|
|
PCJ_PluginDescr = ^TCJ_PluginDescr;
|
|
|
|
TCJ_PluginsList = class (TMGList)
|
|
protected
|
|
function allocData :Pointer; override;
|
|
procedure deallocData(pData :Pointer); override;
|
|
public
|
|
destructor Destroy; override;
|
|
procedure LoadFromINI;
|
|
function CanClose :Boolean;
|
|
function ExtFind(PluginName :String): PCJ_PluginDescr; overload;
|
|
function Find(PluginName :String) :Boolean; overload;
|
|
procedure SettingsChanged;
|
|
end;
|
|
|
|
Var
|
|
PluginsList :TCJ_PluginsList=Nil;
|
|
|
|
implementation
|
|
|
|
uses Classes, Controls, SysUtils, Forms, Dialogs, inifiles;
|
|
|
|
const
|
|
ERR_LOAD_PLUGIN ='Error Loading %s'#13#10'%s'#13#10'Try to Load at next time?';
|
|
ERR_LOAD_INVALID ='Invalid Plugin...';
|
|
ERR_LOAD_CAPT ='Plugins loading..';
|
|
|
|
destructor TCJ_PluginsList.Destroy;
|
|
var
|
|
curPlugin :PCJ_PluginDescr;
|
|
|
|
begin
|
|
try
|
|
curPlugin :=Self.FindFirst;
|
|
while (curPlugin<>Nil) do
|
|
begin
|
|
if (curPlugin^.pClass<>Nil)
|
|
then try
|
|
if curPlugin^.Enabled
|
|
then curPlugin^.pClass.SetEnabled(False);
|
|
curPlugin^.pClass.OnDestroy;
|
|
curPlugin^.pClass.Free;
|
|
except
|
|
On E:Exception do begin end;
|
|
end;
|
|
|
|
FreeLibrary(curPlugin^.DllHandle);
|
|
|
|
curPlugin :=Self.FindNext;
|
|
end;
|
|
Self.FindClose;
|
|
except
|
|
On E:Exception do begin end;
|
|
end;
|
|
|
|
inherited Destroy;
|
|
end;
|
|
|
|
function TCJ_PluginsList.allocData :Pointer;
|
|
begin
|
|
GetMem(Result, SizeOf(TCJ_PluginDescr));
|
|
FillChar(Result^, SizeOf(TCJ_PluginDescr), 0);
|
|
PCJ_PluginDescr(Result)^.DllPath :=''; //Avoid strange String problems
|
|
end;
|
|
|
|
procedure TCJ_PluginsList.deallocData(pData :Pointer);
|
|
begin
|
|
PCJ_PluginDescr(pData)^.DllPath :='';
|
|
FreeMem(pData, SizeOf(TCJ_PluginDescr));
|
|
end;
|
|
|
|
procedure TCJ_PluginsList.LoadFromINI;
|
|
var
|
|
curPlugin :PCJ_PluginDescr;
|
|
theINI :TIniFile;
|
|
INIpackList :TStringList;
|
|
curSect :String;
|
|
i :Integer;
|
|
xDllHandle :HModule;
|
|
xDllPath :String;
|
|
xEnabled :Boolean;
|
|
xGetPluginInfo :Tfunction_GetPluginInfo;
|
|
xGetPlugin :Tfunction_GetPlugin;
|
|
|
|
procedure DoInClass;
|
|
Var
|
|
tmpInfo :TCJ_PluginInfo;
|
|
|
|
begin
|
|
if (curPlugin^.pClass<>Nil) then
|
|
begin
|
|
try
|
|
curPlugin^.pClass.OnCreate(cj_interfaces_impl.CJ_Interface);
|
|
except
|
|
end;
|
|
|
|
try
|
|
tmpInfo :=curPlugin^.pClass.GetInfo;
|
|
curPlugin^.Info :=tmpInfo;
|
|
except
|
|
end;
|
|
|
|
try
|
|
if xEnabled
|
|
then curPlugin^.pClass.SetEnabled(True);
|
|
except
|
|
end;
|
|
end;
|
|
end;
|
|
|
|
begin
|
|
theINI :=TIniFile.Create(PATH_Config+INI_PLUGINS);
|
|
INIpackList :=TStringList.Create;
|
|
try
|
|
theINI.ReadSections(INIpackList);
|
|
|
|
for i :=0 to INIpackList.Count-1 do
|
|
begin
|
|
curPlugin :=Nil;
|
|
try
|
|
CurSect :=Uppercase(INIpackList.Strings[i]);
|
|
curPlugin := Self.ExtFind(CurSect);
|
|
if (curPlugin=Nil) then
|
|
begin
|
|
curPlugin :=self.Add;
|
|
//xDllPath :=ProcessVarValue(theINI.ReadString(CurSect, 'DLL', ''));
|
|
xDllPath :=PATH_Plugins+theINI.ReadString(CurSect, 'DLL', '');
|
|
xEnabled :=theINI.ReadBool(CurSect, 'ENABLED', True);
|
|
xDllHandle := LoadLibrary(PChar(xDllPath));
|
|
if (xDllHandle=0)
|
|
then raise Exception.Create(ERR_LOAD_INVALID);
|
|
|
|
curPlugin^.DllHandle :=xDllHandle;
|
|
curPlugin^.DllPath :=xDllPath;
|
|
curPlugin^.Enabled :=xEnabled;
|
|
|
|
xGetPluginInfo :=GetProcAddress(xDllHandle, 'GetPluginInfo');
|
|
if not(Assigned(xGetPluginInfo))
|
|
then raise Exception.Create(ERR_LOAD_INVALID);
|
|
|
|
//Move(xGetPluginInfo, curPlugin^.Info, SizeOf(TCJ_PluginInfo));
|
|
curPlugin^.Info :=xGetPluginInfo;
|
|
|
|
Case curPlugin^.Info.pType of
|
|
PLUGIN_TYPE_NONE : begin end;
|
|
PLUGIN_TYPE_STD : begin
|
|
xGetPlugin :=GetProcAddress(xDllHandle, 'GetPlugin');
|
|
if Assigned(xGetPlugin)
|
|
then curPlugin^.pClass := xGetPlugin;
|
|
end;
|
|
else raise Exception.Create(ERR_LOAD_INVALID);
|
|
end;
|
|
|
|
DoInClass;
|
|
end;
|
|
except
|
|
On E:Exception do
|
|
begin
|
|
if (MessageDlg(ERR_LOAD_CAPT, Format(ERR_LOAD_PLUGIN, [xDllPath, E.Message]),
|
|
mtError, [mbYes, mbNo], 0)=mrNo)
|
|
then theINI.EraseSection(CurSect);
|
|
|
|
if (curPlugin<>Nil)
|
|
then self.Delete(curPlugin, 0);
|
|
end;
|
|
end;
|
|
end;
|
|
finally
|
|
theINI.Free;
|
|
INIpackList.Free;
|
|
end;
|
|
end;
|
|
|
|
function TCJ_PluginsList.CanClose :Boolean;
|
|
var
|
|
curPlugin :PCJ_PluginDescr;
|
|
|
|
begin
|
|
Result :=True;
|
|
try
|
|
curPlugin :=Self.FindFirst;
|
|
while (curPlugin<>Nil) and (Result=True) do
|
|
begin
|
|
if (curPlugin^.pClass<>Nil)
|
|
then try
|
|
Result :=curPlugin^.pClass.CanClose;
|
|
except
|
|
Result :=True;
|
|
end
|
|
else Result :=True;
|
|
|
|
curPlugin :=Self.FindNext;
|
|
end;
|
|
Self.FindClose;
|
|
except
|
|
Result :=True;
|
|
end;
|
|
end;
|
|
|
|
function TCJ_PluginsList.ExtFind(PluginName :String): PCJ_PluginDescr;
|
|
|
|
function FindByName(Tag :Integer; ptData1, ptData2 :Pointer) :Boolean;
|
|
begin
|
|
Result := (String(PChar(ptData1)) = PCJ_PluginDescr(ptData2)^.Info.pPackName);
|
|
end;
|
|
|
|
begin
|
|
Result :=Self.ExtFind(PChar(Uppercase(PluginName)), 0, @FindByName);
|
|
end;
|
|
|
|
function TCJ_PluginsList.Find(PluginName :String) :Boolean;
|
|
begin
|
|
Result := (ExtFind(PluginName)<>Nil);
|
|
end;
|
|
|
|
procedure TCJ_PluginsList.SettingsChanged;
|
|
begin
|
|
end;
|
|
|
|
end.
|