Top.Mail.Ru
Мастера DELPHI, Delphi programming community Титульная страница Поиск, карта сайта Написать письмо 
| Новости | Поиск | FAQ | Статьи | Книги | Новости VCL |
| Форумы ЧАТ | Орешник | KOL и MCK |
Форумы -» Основная («Начинающим»)/ Базы / WinAPI / Компоненты / Сети / Media / Игры / Corba и COM / KOL / FreePascal / .Net / Прочее / RSDN.ORG

« предыдущая ветвь | форум | следующая ветвь »

например в чужое окно можно записать значение, а как прочесть из


Страницы:   1 2

Zert ©   (2005-10-11 08:16:00) 

например в чужое окно можно записать значение, а как прочесть из чужого окна?

procedure TForm1.Button5Click(Sender: TObject);
var
df :   PChar;
begin

df := '55';

 SendMessage(591438,  WM_SETTEXT, 0, lParam(PChar(df)));
  Edit1.Text := df;

end;


Digitman   (2005-10-11 13:20:00) [1]

По поводу объекта разделяемой памяти - согласен, ошибку признаю .. мне следовало бы уточнить этот важный момент перед своим утверждением.


Игорь Шевченко   (2005-10-11 12:59:00) [2]

WM_SET(GET)TEXT, CB_GETLBTEXT, LB_GETTEXT и прочие, при обработке создают объект разделяемой памяти, в которую переписывают данные из структуры окна целевого процесса, после чего переписывают данные из этой разделяемой памяти в буфер вызывающего процесса.


begin...end   (2005-10-11 12:46:00) [3]

> Digitman ©   (11.10.05 12:26) [22]

Вы бы Рихтера почитали, что ли...


ShiFT   (2005-10-11 12:43:00) [4]

2 Digitman
Проверь.

program TestText;
uses Windows, Messages;
const
ClsName : PChar  = 'classTMP';
appCapt : PChar  = 'TMP';
var
pWnd  : HWND;
pMsg  : TMsg;
pCls  : TWndClassEx;
pCtrl : Array[1..1] of HWND;
function WndProc( wnd: HWnd; msg: LongInt; wParam: wParam; lParam: lParam): LongInt; stdcall;
begin
Result := 0;
case msg of
 wm_Destroy : begin
  PostQuitMessage( 0);
  Exit;
 end;
else
 Result := DefWindowProc( wnd, msg, wparam, lparam);
end;
end;
begin
with pCls do begin
 cbSize        := sizeof( pCls);
 style         := cs_hredraw or cs_vredraw;
 lpfnWndProc   := @WndProc;
 cbClsExtra    := 0;
 cbWndExtra    := 0;
 hInstance     := HInstance;
 hIcon         := LoadIcon (0, idi_Application);
 hCursor       := LoadCursor( 0, idc_arrow);
 hbrBackground := COLOR_BTNFACE +1;
 lpszMenuName  := nil;
 lpszClassName := ClsName;
end;
RegisterClassEx( pCls);
pWnd := CreateWindowEx( 0, ClsName, '', ws_overlappedwindow, 100, 100, 250, 45, $0, 0, hInstance, nil);
if pWnd = 0 then Halt;
pCtrl[1] := CreateWindowEx( $0, 'edit', 'Text', ws_visible or ws_child or ws_border, 0, 0, 242, 18, pWnd, 0, hInstance, nil);
SetWindowText( pWnd,     appCapt);
ShowWindow( pWnd, SW_SHOW);
UpdateWindow( pWnd);
while GetMessage( pMsg, 0, 0, 0) do begin
 TranslateMessage( pMsg);
 DispatchMessage( pMsg);
end;
end.


и

Program tmp;
uses Windows, Messages, SysUtils;
var
ndx : word;
p   : PChar;
h,h2: THandle;
cls : PChar;
begin
h := FindWindow( 'classTMP', 'TMP');
if h = 0 then Halt(0);
h2 := FindWindowEx( h, 0, 'edit', nil);
if h2 = 0 then Halt(0);
GetMem( cls, 256);
GetClassName( h2, cls, 256);
MessageBox( 0, cls, 'tmp', 0);
ndx := SendMessage( h2, WM_GETTEXTLENGTH, 0, 0);
GetMem( p, ndx+1);
SendMessage( h2, WM_GETTEXT, ndx+1, integer(p));
MessageBox( 0, p, 'tmp', 0);
MessageBox( 0, PChar( IntToStr( Length( p))), 'tmp', 0);
end.


ANB   (2005-10-11 12:39:00) [5]


> Digitman ©   (11.10.05 12:26) [22]

WM_GET/SETTEXT, так же как и WM_COPYDATA умеют работать с разными адресными пространствами в разных процессах. Т.е. параметрами могут служить локальные адреса, винда все разрулит.
ЗЫ. У меня целый кусок проекта на этих сообщениях построен и все работает.


Digitman   (2005-10-11 12:26:00) [6]


> ShiFT   (11.10.05 12:07) [18]
> проверял как раз в разных процессах.
> У меня работало


не выдумывай небылиц.

В lParam должно быть передано значение адреса в АП именно "чужого", а не "своего" процесса... т.е. того процесса, который создал окно и владеет им, а не того произвольно взятого процесса, который выполняет SendMessage().

В твоем же примере , который якобы "работает", переменная P после вызова GetMem() хранит адрес выделенного блока памяти в "своем", а не "чужом" процессе.


ShiFT   (2005-10-11 12:21:00) [7]

> Возвращается ровно 254 символа из 260.
из Эдита при использовании GetWindowText( Handle_из_Чужого_Эдита);

GetMem(p,256);
ndx := SendMessage( h, WM_GETTEXTLENGTH, 0, 0);
SendMessage( h, WM_GETTEXT, ndx+1, integer(p));
MessageBox( 0, p, 'tmp', 0);
MessageBox( 0, PChar( IntToStr( Length( p))), 'tmp', 0);

При Этом Возвращаются все 260 символов.


ShiFT   (2005-10-11 12:16:00) [8]


> han_malign ©   (11.10.05 11:30) [11]

AV не вылетает.
Возвращается ровно 254 символаиз 260.


Digitman   (2005-10-11 12:11:00) [9]


> ShiFT   (11.10.05 12:05) [17]


Перечитай [2] и [4] и тему вопроса.

Непосредственная отправка WM_GET/SETTEXT окну чужогоприложения бессмысленна !

Смысл имеет лишь отправка такого сообщения именно при посредничестве Get/SetWindowText, и то - далеко не во всех, а лишь в ряде случаев .. в том самом ряде случаев, который оговорен разработчиками ОС как ряд допустимых случаев успешной работы этих ф-ций.


ShiFT   (2005-10-11 12:07:00) [10]

Я проверял как раз в разныхпроцессах.
У меня работало (и в Эдитах тоже).

Насчёт 256 символов Знаю.


ShiFT   (2005-10-11 12:05:00) [11]


> Digitman ©   (11.10.05 11:50) [16]

Перечиай Первый и Второй Пост.
Где ты там увидел Get/SetWindowText?


Digitman   (2005-10-11 11:50:00) [12]


> han_malign ©   (11.10.05 11:38) [13]


> где?


известно где - в Караганде !)

речь шла про Get/SetWindowText, а не про WM_GET/SETTEXT


Digitman   (2005-10-11 11:47:00) [13]


> ShiFT   (11.10.05 11:36) [12]


речь идет о том, что интересующее автора окно - ЧУЖОЕ !

и процесс, создавший интересующее окно, соответственно, - ЧУЖОЙ !

и у этого ЧУЖОГО процесса - свое собственное виртуальное адресное пространство !

и адрес буфера, переданный lParam-параметром сообщения WM_GETTEXT, соответственно, должен быть адресом в ЧУЖОМ (а не СВОЁМ !) адресном пространстве !

так что думай головой, когда советы раздаешь а-ля "Проверено. Работает."


ANB   (2005-10-11 11:41:00) [14]

WM_GETTEXT работает не всегда (она читает заголовок окна). А вот GetText() - почему то работает.


han_malign   (2005-10-11 11:38:00) [15]


> вчитайся в [5]
> там черным по белому написано про случай с EDIT-контролом.

- где?

An application sends a WM_GETTEXT message to copy the text that corresponds to a window into a buffer provided by the caller.
.......................
Note, for non-textstatic controls this gives you the text with which the control was originally created, that is, the ID number.
.......................
For other windows, the text is the window title . To copy the text of an item in a list box, an application can use the LB_GETTEXTmessage.
.......................
When the WM_GETTEXT message is sent to a static control with the SS_ICON style, a handle to the icon will be returned in the first four bytes of the bufferpointed to by lParam. This is true only if the WM_SETTEXT message has been used to set the icon.
.......................
Rich Edit:If the text to be copied exceeds 64K, use either the EM_STREAMOUT or EM_GETSELTEXT message.
.......................
Windows 2000/XP:Sending a WM_GETTEXT message to a non-textstatic control, such as a static bitmap or static icon control, does not return a string value. Instead, it returns zero.


ShiFT   (2005-10-11 11:36:00) [16]


> читай справку :
> GetWindowText
> This function cannot retrieve the text of an edit control
> in another application.


Справка для WM_GETTEXT

For an edit control, the text to be copied is the content of the edit control. For a combo box, the text is the content of the edit control (or static-text) portion of the combo box. For a button, the text is the button name. For other windows, the text is the window title. To copy the text of an item in a list box, an application can use the LB_GETTEXT message.

When the WM_GETTEXT message is sent to a static control with the SS_ICON style, the handle of the icon will be returned in the first four bytes of the buffer pointed to by lpszText. This is true only if the WM_SETTEXT message has been used to set the icon.

In a rich edit control, if the text to be copied exceeds 64K, use either the message EM_STREAMOUT or EM_GETSELTEXT


han_malign   (2005-10-11 11:30:00) [17]


> ShiFT   (11.10.05 11:15) [9]

GetMem(p, 256);
ndx:= SendMessage( 590592, WM_GETTEXTLENGTH, 0, 0);
SendMessage( 590592, WM_GETTEXT, ndx, integer(p));


> Проверено. Работает.

- ну-ну, а если длинна текста больше 256, что будет?
Можно даже не гадать - AV будет... И зачем вообще запрашивать длинну, если буфер от балды выделять?


Digitman   (2005-10-11 11:22:00) [18]


> ShiFT   (11.10.05 11:15) [9]


вчитайся в [5]

там черным по белому написано про случай с EDIT-контролом.


> Проверено. Работает


работает, но лишь в частных случаях.


ShiFT   (2005-10-11 11:15:00) [19]

procedure TForm1.Button5Click(Sender: TObject);
var
 ndx : word;
 p : PChar;
begin
 GetMem(p,256);
 ndx := SendMessage( 590592, WM_GETTEXTLENGTH, 0, 0);
 SendMessage( 590592, WM_GETTEXT, ndx, integer(p));
 MessageBox( 0, p, 'tmp', 0);
end;

Проверено. Работает.


Digitman   (2005-10-11 10:51:00) [20]


> Zert   (11.10.05 10:38) [6]


> что такая невыполнимая задача


ну отчего ж невыполнимая ? выполнимая)

но для решения тех данных, которыми ты владеешь (известен только хэндл окна), недостаточно - нужно как минимум знать класс окна.. от этого и решение и сложность решения будет напрямую зависеть ..


Страницы:   1 2

Наверх

Титульная страница Поиск, карта сайта Написать письмо