Einzelnen Beitrag anzeigen

EWeiss
(Gast)

n/a Beiträge
 
#51

Re: Dynamisches Array oder Klasse als Array auslegen

  Alt 27. Sep 2006, 08:00
Hier fängt die geschichte an.

Delphi-Quellcode:
// Initialisiert das BASS_WADSP add-on
Function BASS_WADSP_Init(hwndMain: HWND): DWORD; stdcall;

begin
   mainhwnd := hwndMain;

  Result:= mainhwnd;
end;
Ist OK !!

Plugins werden eingeladen

Delphi-Quellcode:
 // Läd ein Winamp DSP Plugin und übergibt das handle
 // Koordinaten und ein User Callback können übergeben werden
function BASS_WADSP_Load(const dspfile: PChar; x, y, Width, Height: integer;
                         proc: WINAMPWINPROC): HDSP; stdcall;

var
  winampDsp: WINAMPPLUGINPROPDSP;
  cnt: integer;

begin
  winampDsp := AllocMem(sizeof(WINAMPPLUGINPROPDSP));
  FillChar(winampDsp, 0, sizeof(winampDsp));

  Saved8087CW := Default8087CW;
  //FPU - Exceptions deaktivieren
  Set8087CW($133f);

  // Library laden
  // zuerst mit unicode versuchen
  winampDsp^.hDll := LoadLibraryW(PWideChar(dspfile));
  if (not winampDsp^.hDll) <> 0 then
  begin
    // ansonsten Ansi
    winampDsp^.hDll := LoadLibrary(dspfile);
  end;

  // Exceptions zurück auf Defaultwert
  Set8087CW(Saved8087CW);

  Result := 0;

  if winampDsp^.hDll <> 0 then
  begin
    FreeMem(winampDsp);

    pGetMod := GetProcAddress(winampDsp^.hDll, 'winampDSPGetHeader2');
    if pGetMod <> nil then
    begin
      // Fake Winamp Window erstellen
      if (Create_Winamp_Window(winampDsp, x, y, Width, Height, proc)) = True then
      begin
        cnt := 0;
        winampDsp^.pModule := pGetMod;
        if winampDsp^.pModule <> nil then
        begin
          // Schleife durchlaufen bis kein Modul mehr gefunden wurde
          repeat
            Inc(cnt);
          until winampDsp^.pModule^.getModule(cnt) = nil;
          // Anzahl der Module speichern
          winampDsp^.NumberOfModules := cnt;
          winampDsp^.module := -1;
          InitializeCriticalSection(winampDsp^.csh);
          // Addiere ein neues Winamp DSP Plugin
          AddDSP(winampDsp);
          // Übergebe das Handle
          Result := winampDsp^.handle
      end else
        // Bei Fehler Winamp Fake Window beenden
        Destroy_Winamp_Window(winampDsp);
    end else
      // Library freigeben
      FreeLibrary(winampDsp^.hDll);
    end
  end
end;
Ist OK !!

FakeWindow wird erstellt! Für jedes Plugin einzeln.
Delphi-Quellcode:
// Erstellt ein Fake Winamp window
function Create_Winamp_Window(winampDsp: WINAMPPLUGINPROPDSP; x, y, width, height: integer; proc: WINAMPWINPROC): Boolean; stdcall;
var
  wndclass: WNDCLASSEX;
  dspCount : DWORD;
  AppClass : Pchar;

begin
  dspCount := GetActiveDSPs;

  if dspCount > 0 then
      begin
      AppClass := PChar(Format(Pchar('Winamp v1.x : %d'), [winampDSPcounter + 1]));
  end else
   AppClass := 'Winamp v1.x';

  Inst := GetModuleHandle(nil);

  with wndclass do
  begin
     cbSize := sizeof(wndclass);
     style := CS_PARENTDC or CS_VREDRAW;
     cbClsExtra := 0;
     cbWndExtra := 0;
     hInstance := Inst;
     hIcon := 0;
     hCursor := LoadCursor(0, IDC_ARROW);
     hbrBackground := 0;
     lpszMenuName := nil;
     lpszClassName := AppClass;
   if proc = 0 then
      lpfnWndProc := @WinampWndProc
   else
      lpfnWndProc := @proc;
     hIconSm := 0;
  end;

   winampDsp^.DSP_Atom_Emu := RegisterClassEx(wndclass);
   if winampDsp^.DSP_Atom_Emu <> 0 then

   winampDsp^.DSP_Atom_Emu := CreateWindowEx(0, // DWORD dwExStyle
                                                    AppClass, // LPCTSTR lpClassName
                                            'Winamp 2.40', // LPCTSTR lpWindowName
                                                    WS_POPUP, // DWORD dwStyle
                                                    x, // int x
                                            y, // int y
                                            width, // int nWidth
                                            height, // int nHeight
                                                    mainhwnd, // HWND hWndParent
                                            0, // HMENU hMenu
                                            Inst, // // HINSTANCE hInstance
                                            nil); // LPVOID lpParam

   if winampDsp^.DSP_Window_Emu = 0 then
    begin
      UnRegisterClass(PChar(WORD(winampDsp^.DSP_Atom_Emu)), Inst);
      MessageBox(mainhwnd, 'Unable to emulate Winamp Window!', 'BASS DSP Error!', MB_ICONEXCLAMATION or MB_ICONWARNING);
      Result := false
    end
  else
   Result := true;
end;
Ist OK!

Aus der Winproc wird die Funktion GetActiveDSPs aufgerufen welche
den Counter hochzählt und abhängig davon den ClassenNamen ändert

AppClass := PChar(Format(Pchar('Winamp v1.x : %d'), [winampDSPcounter + 1]));
damit nicht zwei die gleichen Windows erstellt werden.

Delphi-Quellcode:
function GetActiveDSPs(): DWORD; stdcall;
var
  a: DWORD;
  cnt: DWORD;
  winampDSP: WINAMPPLUGINPROPDSP;

begin
  cnt := 0;

  if Winamp_DSP <> nil then

  for a := 0 to winampDSPcounter do
  begin
    winampDSP := Winamp_DSP[a];
    if winampDSP <> nil then
      Inc(cnt);
  end;
  Result := cnt;
end;
Das ist auch in Ornung!


Dann wir das gewählte Plugin addiert.

Delphi-Quellcode:
Procedure AddDSP(winampDsp: WINAMPPLUGINPROPDSP); stdcall;

var
  a: DWORD;

begin

  Winamp_DSP := DspPtrArray(winampDsp);

  for a := 0 to winampDSPcounter do
    if not Assigned(Winamp_DSP[a]) then
      Break;

  if a = winampDSPcounter then
  begin
    // Array nicht leer, füge ein neues hinzu
    ReallocMem(Winamp_DSP, (winampDSPcounter + 1) * SizeOf(WINAMPPLUGINPROPDSP));
    Dec(winampDSPcounter);
  end;
  Inc(winampDSPhandle);
  winampDsp^.handle := winampDSPhandle;
  // addiere ein Winamp DSP Plugin zum Array
  Winamp_DSP[a] := winampDsp;

end;
Scheint OK zu sein. Obwohl bisher noch nie in ReallocMem reingesprungen wurde.

Nun wird der Name des Moduls übergeben

Delphi-Quellcode:
// Returns the name of a loaded Winamp DSP plugin
function BASS_WADSP_GetName(plugin: HDSP): LPTSTR; stdcall;
Var
  strRet: PChar;
  winampDSP: WINAMPPLUGINPROPDSP;

begin
  strRet := nil;
  winampDsp := GetDSP(plugin);
   if winampDsp <> nil then
   begin
       strRet := winampDsp^.pModule^.description;
   end;
   Result := strRet;
end;
ist auch OK!

GetDSP übergibt den wert aus dem ArrayWinamp_DSP[a]

Delphi-Quellcode:
function GetDSP(handle: DWORD): WINAMPPLUGINPROPDSP;
var
  a: DWORD;

begin
  if handle <> 0 then
    for a := 0 to Pred(winampDSPcounter) do
    begin
      Result := Winamp_DSP[a];
      if Assigned(Result) and (Result^.handle = handle)
        then Exit;
    end;
  Result := nil;
end;
ist auch in Ordnung!

Dann wird das Plugin entladen und das nächste eingeladen falls vorhanden.

Delphi-Quellcode:
// Entlade das übergebene Winamp DSP Plugin
Procedure BASS_WADSP_FreeDSP(plugin: HDSP); stdcall ;
begin
   FreeDSP(plugin);
end;
So bis hier ist alles OK!

gruß
  Mit Zitat antworten Zitat