Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Win32/Win64 API (native code) (https://www.delphipraxis.net/17-win32-win64-api-native-code/)
-   -   Delphi Probleme mit EnumWindows (https://www.delphipraxis.net/56360-probleme-mit-enumwindows.html)

idontwantaname 4. Nov 2005 15:10


Probleme mit EnumWindows
 
Hi !!

Anlässlich dieses Threads verwende ich jetzt EnumWindows bzw. ich habe es versucht ^^

Ich hab den Code eigentlich eh schon im anderen Thread, aber es ist ja im Prinzip eine neue Frage ... also der neue Thread ;-)

Seltsamerweise bekomme ich eine AV wenn ich 2 String vergleichen will:
Delphi-Quellcode:
type
  THandleArray = array of THandle;

function FindAllWindows(const WindowCaption: String): THandleArray;
var
  Res: THandleArray;
  function _EnumWindowProc(_hwnd: HWND; _lparam: LPARAM): Boolean; // stdcall; braucht man das ?? es geht mit und ohne nicht
  var
    Title: String;
    Len: Integer;
  begin
    if(_hwnd = 0) then
    begin
      Result := False;
      Exit;
    end;

    Len := GetWindowTextLength(_hwnd)+1;
    SetLength(Title, Len);
    GetWindowText(_hwnd, PChar(Title), Len);
    Title := Trim(Title);
    if (Title = WindowCaption) then // Hier kommt eine AV
    begin
      SetLength(Res, Length(Res)+1);
      Res[Length(Res)-1] := _hwnd;
    end;
  end;
begin
  SetLength(Res, 0);
  EnumWindows(@_EnumWindowProc, 0); // was muss man als 2. Parameter übergeben ??
  Result := Res;
end;

himitsu 4. Nov 2005 15:47

Re: Probleme mit EnumWindows
 
Versuch es mal mit

Delphi-Quellcode:
GetWindowText(_hwnd, Pointer(Title), Len);
oder
Delphi-Quellcode:
GetWindowText(_hwnd, @Title[1], Len);
Es könnte einfach nur sein, daß es beim Casten von String auf PChar ein Problem gibt.
Die beiden oberenVarianten geben jedenfalls den echten Pointer auf das erste Zeichen zurück, wobei das mit dem Pointer sogar noch den kleineren Code erzeugt :roll:


Und ja StdCall wird benötigt ... schau mal in der OH nach, was das macht. :warn:


Und zum Letzten fällt mir gerade nichts ein, aber im Win32-SDK, oder MSDN sollte ja drinstehen was da rein muß :zwinker:


Ansonsten ist mir jetzt auf die Schnelle nicht aufgefallen.

shmia 4. Nov 2005 16:03

Re: Probleme mit EnumWindows
 
Kennst du schon:
http://www.delphipraxis.net/internal...ct.php?t=30883
Damit wird die Arbeit mit EnumWindows deutlich erleichtert.

neolithos 5. Nov 2005 03:32

Re: Probleme mit EnumWindows
 
Mehrer Anfängerfehler, aber nix schlimmes!

Delphi-Quellcode:
type
  THandleArray = array of THandle;

function FindAllWindows(const WindowCaption: String): THandleArray;
type
  PParams = ^TParams;
  TParams = record
    Res : THandleArray;
    WindowCaption : String;
  end;

var params : TParams;

  function _EnumWindowProc(_hwnd: HWND; _lparam: LPARAM): LongBool; stdcall; // ja,
// denn es beschreibt die reihenfolge und art wie parameter übergeben werden
  var
    cTitle : array [0..1023] of Char; // sollte reichen
  begin
    with PParams(_lparam)^ do
      begin
        if(_hwnd = 0) then // es wird immer ein gültiges Handle übergeben --> unnötig
          begin
            Result := False;
            Exit;
          end;
(* Warum so kompliziert
    Len := GetWindowTextLength(_hwnd)+1;
    SetLength(Title, Len);
    GetWindowText(_hwnd, PChar(Title), Len);
    Title := Trim(Title);
    if (Title = WindowCaption) then // Hier kommt eine AV
    begin
      SetLength(Res, Length(Res)+1); // hier kommt die nächste AV
      Res[Length(Res)-1] := _hwnd;
    end; *)

        GetWindowText(_hwnd, cTitle, SizeOf(cTitle);
        if CompareText(cTitle, WindowCaption) = 0 then
           begin
             SetLength(Res, Length(Res)+1);
             Res[Length(Res)-1] := _hwnd;
           end;
      end;
  end;
begin
  SetLength(params.Res, 0);
  params.WindowCaption := WindowCaption;
  EnumWindows(@_EnumWindowProc, @params); // der zweite Parameter dient als Platzhalter für
// zusätzliche Parameter, da nicht auf die andere localen Variablen von FindAllWindows
// zugegriffen werden kann. Das ganze hat was mit dem Runtime-Stack zu tun.
  Result := Res;
end;
Das sollte Funktionieren. Ist aber ungetestet. :zwinker:

idontwantaname 5. Nov 2005 10:20

Re: Probleme mit EnumWindows
 
Hey, danke :-D

Beim Debuggen bin ich dann eh draufgekommen, dass er irgendwie nicht auf WindowCaption selbst zugreifen kann ...
Ich werds gleich mal testen :-)

[edit] so, ich habs mir jetzt angeschaut ... und hier eine funktionierende Version
Delphi-Quellcode:
type THandleArray = array of HWND;

function FindAllWindows(const WindowCaption: String): THandleArray;
type
  PParam = ^TParam;
  TParam = record
    WindowCaption: String;
    Res: THandleArray;
  end;
var
  Rec: TParam;
  function _EnumProc(_hWnd: HWND; _LParam: LPARAM): LongBool; stdcall;
  var
    cTitle: array[0..1023] of Char;
  begin
    with PParam(_LParam)^ do
    begin
      GetWindowText(_hWnd, cTitle, SizeOf(cTitle));
      if (CompareText(cTitle, WindowCaption) = 0) then
      begin
        SetLength(Res, Length(Res)+1);
        Res[Length(Res)-1] := _hWnd;
      end;
      Result := True;
    end;
  end;
begin
  Rec.WindowCaption := WindowCaption;
  SetLength(Rec.Res, 0);
  EnumWindows(@_EnumProc, Integer(@Rec)); // hier hat das Integer gefehlt
  Result := Rec.Res;
end;

neolithos 7. Nov 2005 01:33

Re: Probleme mit EnumWindows
 
Mir fällt da noch was auf.

Delphi-Quellcode:
type THandleArray = array of HWND;

function FindAllWindows(const WindowCaption: String): THandleArray;
type
  PParam = ^TParam;
  TParam = record
    WindowCaption: String;
    Res: THandleArray;
  end;
var
  Rec: TParam;
  function _EnumProc(_hWnd: HWND; _LParam: PParam): LongBool; stdcall; // so spart man sich ein Typ-Casting
  var
    cTitle: array[0..1023] of Char;
  begin
    with _LParam^ do
    begin
      GetWindowText(_hWnd, cTitle, SizeOf(cTitle));
      if (CompareText(cTitle, WindowCaption) = 0) then
      begin
        SetLength(Res, Length(Res)+1);
        Res[Length(Res)-1] := _hWnd;
      end;
      Result := True;
    end;
  end;
begin
  Rec.WindowCaption := WindowCaption;
  SetLength(Rec.Res, 0);
  EnumWindows(@_EnumProc, Integer(@Rec)); // hier hat das Integer gefehlt
  Result := Rec.Res;
end;


Alle Zeitangaben in WEZ +1. Es ist jetzt 23:33 Uhr.

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