Найти окно и нажать кнопку

Тема в разделе "Delphi - Компоненты", создана пользователем Shouldercannon, 28 апр 2011.

  1. Shouldercannon

    Shouldercannon Well-Known Member

    Регистрация:
    25 май 2010
    Сообщения:
    125
    Симпатии:
    0
    Если кнопка находится на Panel1 или PageControl1 и возмжно где-то ещё, то она не нажимается. Из-за чего это происходит?
    Код (Delphi):
     if FindWindow(nil, 'Form1') <> 0 then
    begin
    Wind := FindWindow(nil, 'Form1');
    Btn := FindWindowEx(Wind, 0, nil, 'Кнопка');
    SendMessage(Btn, BM_CLICK, 0, 0);
    end;
     
  2. sinkopa

    sinkopa Well-Known Member

    Регистрация:
    17 июн 2009
    Сообщения:
    344
    Симпатии:
    9
    Не уверен, что Ваша кнопка действительно нашлась...
    Чтобы до нее добраться нужно "перелопанить" все дерево вложенных (дочерних к Form1 ) окон...

    Я бы сделал так

    Код (Delphi):
    ...

    implementation

    {$R *.dfm}


    function EnumChildProc(Wnd: HWND; CaptList: TStrings): BOOL; stdcall;
    var
    captBuf: array[0..260] of Char;
    begin
    Result := (Wnd <> 0); // условие завершения обхода дерева окон
    if Result then
    begin
    GetWindowText(Wnd, captBuf, SizeOf(captBuf)); // получаем заголовок (текст) окна
    if (Pos(CaptList[0], StrPas(captBuf)) > 0)  // проверяем не наше ли это окно
    and (CaptList.IndexOfObject(TObject(Wnd)) < 0) // проверяем не заглядывали ли мы уже в это окошко
    then CaptList.AddObject(StrPas(captBuf), TObject(Wnd)); // Добавляем в список заголовок и хэндл окна
    EnumChildWindows(Wnd, @EnumChildProc, Longint(CaptList)); // Рекурсивный обход дочерних окон
    end;
    end;

    function ClickButton(ParentWindow: HWND; ButtonCaption: string): Boolean;
    var
    Btn: HWND;
    CaptList: TStringList; // В items-ы будем класть заголовки окон;
    // в objects-ы будем класть хэндлы окон;
    begin
    CaptList := TStringList.Create;
    try
    // В первый item листа кладем заголовок кнопки
    CaptList.AddObject(ButtonCaption, nil);

    // обходим все дочерние окна (ищем кнопку с указанным ButtonCaption )
    EnumChildWindows(ParentWindow, @EnumChildProc, Longint(CaptList));

    // Убеждаемся что нашлась ТОЛЬКО ОДНА КНОПКА с указанным ButtonCaption
    Result := ((CaptList.Count = 2) and (HWND(CaptList.Objects[1]) <> 0));

    if Result then
    begin
    Btn := HWND(CaptList.Objects[1]);
    PostMessage(Btn, BM_CLICK, 0, 0);
    { //или лучше
    SendMessage(Btn, WM_LBUTTONDOWN, 1, 1);
    SendMessage(Btn, WM_LBUTTONUP, 1, 1);
    }

    end;
    finally
    CaptList.Free;
    end;
    end;

    ...
    Пример использования:

    Код (Delphi):
    procedure TMyForm.btn1Click(Sender: TObject);
    begin
    Wind := FindWindow(nil, 'Form1');
    if (Wind <> 0) then
    begin

    if ClickButton(Wind,'Кнопка') then
    begin
    ShowMessage('вроде нажали');
    end
    else
    begin
    ShowMessage('нету такой кнопки (или больше одной с таким капшеном)');
    end;

    end
    begin
    ShowMessage('нету окна с капшеном "Form1"');
    end;
    end;
     
  3. Shouldercannon

    Shouldercannon Well-Known Member

    Регистрация:
    25 май 2010
    Сообщения:
    125
    Симпатии:
    0
    Код (Delphi):
    procedure TForm1.Button1Click(Sender: TObject);
    var
    Wind: HWND;
    begin
    Wind := FindWindow(nil, PChar(Edit1.Text));
    if (Wind <> 0) then
    begin
    if ClickButton(Wind, Edit2.Text) then ShowMessage('Вроде нажали') else ShowMessage('Нету такой кнопки или больше одной с таким Caption');
    end
    else ShowMessage('Нет окна с Caption "' + Edit1.Text + '"');
    end;
    SendMessage возвращает результат, а PostMessage нет. Нужен отчёт об успешном нажатии кнопки, значит нужно всётаки использовать SendMessage, как вы предложили в закоментированном участке кода, если я не ошибаюсь.
     
Загрузка...

Поделиться этой страницей