d32coder
asked on
API SendMessage Help
I'm trying to learn about sendmessage. I see this in all my books and all over the web but nowhere is it explained..
SendMessage(...)
LRESULT SendMessage(
HWND hWnd, // handle to destination window
UINT Msg, // message
WPARAM wParam, // first message parameter
LPARAM lParam // second message parameter
);
--------
From mIRC's help file
--------
SendMessage(mHwnd, WM_MCOMMAND, cMethod, 0L)
mHwnd - the handle of the main mIRC window, or the handle of a Channel, Query, etc. window.
WM_MCOMMAND - which should be defined as WM_USER + 200
cMethod - the way in which you want mIRC to process the message, where:
1 = As if typed in editbox
2 = As if typed in editbox, send as plain text
4 = Use flood protection if turned on, can be or'd with 1 or 2
Returns - 1 if success, 0 if fail
---
{Parameters}
1. I have no problem with the handle, My target app (mIRC) is ready to receive a message and I have it's handle.
2. WM_MCOMMAND = UINT Msg....
I want to send a string here, I assume it must be a pointer but "which should be defined as WM_USER+200"
is killing me. What does that mean?
3. No help needed
4. "0L", do you suppose this is just expecting a 0 as if it were not used?
---------
Also, does my app have to be a COM Object to use Sendmessage?
Example source would help but my primary need is an explanation of the second parameter.
Thanks in advance.
Don
SendMessage(...)
LRESULT SendMessage(
HWND hWnd, // handle to destination window
UINT Msg, // message
WPARAM wParam, // first message parameter
LPARAM lParam // second message parameter
);
--------
From mIRC's help file
--------
SendMessage(mHwnd, WM_MCOMMAND, cMethod, 0L)
mHwnd - the handle of the main mIRC window, or the handle of a Channel, Query, etc. window.
WM_MCOMMAND - which should be defined as WM_USER + 200
cMethod - the way in which you want mIRC to process the message, where:
1 = As if typed in editbox
2 = As if typed in editbox, send as plain text
4 = Use flood protection if turned on, can be or'd with 1 or 2
Returns - 1 if success, 0 if fail
---
{Parameters}
1. I have no problem with the handle, My target app (mIRC) is ready to receive a message and I have it's handle.
2. WM_MCOMMAND = UINT Msg....
I want to send a string here, I assume it must be a pointer but "which should be defined as WM_USER+200"
is killing me. What does that mean?
3. No help needed
4. "0L", do you suppose this is just expecting a 0 as if it were not used?
---------
Also, does my app have to be a COM Object to use Sendmessage?
Example source would help but my primary need is an explanation of the second parameter.
Thanks in advance.
Don
type sendmessage in delphi. press F1 and you will get help on the function.
Now you should know what message you want to send(receive).
If you dont, tell what you want to do and may be I can help
Now you should know what message you want to send(receive).
If you dont, tell what you want to do and may be I can help
:) I seen that it's 500 point question (too big for what I mean). May be I misunderstand the question, so you should ask more clearly :)
ASKER
I want to pass a string to mirc.exe in a mapped file via Sendmessage.
Mirc wants it in this format..
SendMessage(mHwnd, WM_MCOMMAND, cMethod, 0L)
...
WM_MCOMMAND - which should be defined as WM_USER + 200
^^ this is causing me some trouble, need to declare some kind of varible to use there.
I tried.. wmC: LongInt = WM_USER + 200;
but it doesn't seem to work.
----------
Second half.
I created a mapped file as instructed, now I need to set a string of variable length as data inside the mapped file. The mapped file needs to be 1024 bytes in length.
Here is what I tried.
hMapFile := CreateFileMapping($FFFFFFF F,
nil, Page_ReadWrite, 0,
SizeOf(byte) * 1024, 'mIRC');
if hMapFile = 0 then
raise Exception.Create('Error creating Mapped File.');
ShareData := MapViewOfFile(hMapFile,
File_Map_Write, 0, 0, SizeOf(byte) * 1024);
-------
That part SEEMS to work.
Now I want to...
ShareData^ := 'My text string';
^^ This is very wrong.
-------
500 points for being a multipart question.
_________________________
APPENDIX from the mirc help file
The following call to SendMessage() makes mIRC perform the commands that you specify.
SendMessage(mHwnd, WM_MCOMMAND, cMethod, 0L)
mHwnd - the handle of the main mIRC window, or the handle of a Channel, Query, etc. window.
WM_MCOMMAND - which should be defined as WM_USER + 200
cMethod - the way in which you want mIRC to process the message, where:
1 = As if typed in editbox
2 = As if typed in editbox, send as plain text
4 = Use flood protection if turned on, can be or'd with 1 or 2
Returns - 1 if success, 0 if fail
The application that sends these messages must create a mapped file named mIRC with CreateFileMapping().
When mIRC receives the above messages, it will open this file and use the data that this mapped file contains to perform the command or evaluation. In the case of an evaluation, mIRC will output the results to the mapped file.
The mapped file must be at least 1024 bytes in length.
Mirc wants it in this format..
SendMessage(mHwnd, WM_MCOMMAND, cMethod, 0L)
...
WM_MCOMMAND - which should be defined as WM_USER + 200
^^ this is causing me some trouble, need to declare some kind of varible to use there.
I tried.. wmC: LongInt = WM_USER + 200;
but it doesn't seem to work.
----------
Second half.
I created a mapped file as instructed, now I need to set a string of variable length as data inside the mapped file. The mapped file needs to be 1024 bytes in length.
Here is what I tried.
hMapFile := CreateFileMapping($FFFFFFF
nil, Page_ReadWrite, 0,
SizeOf(byte) * 1024, 'mIRC');
if hMapFile = 0 then
raise Exception.Create('Error creating Mapped File.');
ShareData := MapViewOfFile(hMapFile,
File_Map_Write, 0, 0, SizeOf(byte) * 1024);
-------
That part SEEMS to work.
Now I want to...
ShareData^ := 'My text string';
^^ This is very wrong.
-------
500 points for being a multipart question.
_________________________
APPENDIX from the mirc help file
The following call to SendMessage() makes mIRC perform the commands that you specify.
SendMessage(mHwnd, WM_MCOMMAND, cMethod, 0L)
mHwnd - the handle of the main mIRC window, or the handle of a Channel, Query, etc. window.
WM_MCOMMAND - which should be defined as WM_USER + 200
cMethod - the way in which you want mIRC to process the message, where:
1 = As if typed in editbox
2 = As if typed in editbox, send as plain text
4 = Use flood protection if turned on, can be or'd with 1 or 2
Returns - 1 if success, 0 if fail
The application that sends these messages must create a mapped file named mIRC with CreateFileMapping().
When mIRC receives the above messages, it will open this file and use the data that this mapped file contains to perform the command or evaluation. In the case of an evaluation, mIRC will output the results to the mapped file.
The mapped file must be at least 1024 bytes in length.
it's weird that lParam isn't used
var ShareData: PChar = nil;
ShareData := MapViewOfFile(hMapFile,
File_Map_Write, 0, 0, SizeOf(byte) * 1024);
StrPLCopy(ShareData, MyString, Length(MyString));
if SendMessage(hWinMirc, WM_MCOMMAND, cMethod, 0) = 1 then
ResultString:=string(Share Data); // in case of a query function
hope it helps :)
var ShareData: PChar = nil;
ShareData := MapViewOfFile(hMapFile,
File_Map_Write, 0, 0, SizeOf(byte) * 1024);
StrPLCopy(ShareData, MyString, Length(MyString));
if SendMessage(hWinMirc, WM_MCOMMAND, cMethod, 0) = 1 then
ResultString:=string(Share
hope it helps :)
ASKER
Still not working.. here's my code.
-------------------------- ---------- ---
var
Form1: TForm1;
ChanList: TStringlist;
MircHandle: LongInt;
hMapFile: THandle;
ShareData: PChar = nil;
mCOMMAND: LongInt = WM_USER + 200;
MC: LongInt;
const
VirtualName = 'mIRC';
implementation
{$R *.dfm}
Procedure TForm1.FormCreate(Sender: TObject);
Begin
ChanList := TStringlist.Create;
UpdateActives1Click(self);
MC := WM_USER + 200;
hMapFile := CreateFileMapping($FFFFFFF F, nil, Page_ReadWrite, 0, SizeOf(byte) * 1024, virtualname);
if hMapFile = 0 then
raise Exception.Create('Error creating Memory Mapped File, this program can only be run in WinNT, 2000 or XP');
ShareData := MapViewOfFile(hMapFile, File_Map_Write, 0, 0, SizeOf(byte) * 1024);
End;
Procedure TForm1.FormClose(Sender: TObject; var Action: TCloseAction);
Begin
ChanList.Free;
UnMapViewOfFile(Sharedata) ;
CloseHandle(hMapFile);
End;
function TForm1.TaskList(FirstHandl e: THandle; ListAll: Boolean): string;
var
lngLen:longint;
strBuffer, This, All:string;
TaskHandle: THandle;
begin
MircHandle := 0;
cbChans.ItemIndex := -1;
cbChans.Items.Clear;
ChanList.Clear;
TaskHandle := GetWindow(FirstHandle,GW_H WNDFIRST);
while TaskHandle > 0 do
begin
if (TaskHandle <> FirstHandle) and (TaskHandle <> Application.Handle) then
begin
lngLen := GetWindowTextLength(TaskHa ndle) + 1;
SetLength(strBuffer,lngLen );
lngLen := GetWindowText(TaskHandle,P Char(strBu ffer),lngL en);
if lngLen > 0 then
begin
This := TrimRight(strBuffer);
if pos('#',This) = 1 then
begin
ChanList.Append(IntToStr(T askHandle) );
cbChans.Items.Append(Copy( This,1,(po s(' ',This)-1)));
end;
if pos('mIRC',This) = 1 then MircHandle := TaskHandle;
end;
end;
TaskHandle := GetWindow(TaskHandle,GW_HW NDNEXT);
end;
if MircHandle = 0 then ShowMessage('Mirc Handle Not found!');
end;
Procedure TForm1.UpdateActives1Click (Sender: TObject);
Begin
TaskList(Application.Handl e,TRUE);
if cbChans.Items.Count > 0 then cbChans.ItemIndex := 0;
End;
procedure TForm1.buttonSendThisClick (Sender: TObject);
var T: String;
Begin
T := '/msg _Psych Hello!';
StrPLCopy(ShareData, T,Length(T));
if SendMessage(mirchandle,MC, 2,0) = 0
then Showmessage('SendMessage returned ERROR!');
End;
procedure TForm1.GetShareData(P: Pchar);
Begin
// TODO
End;
procedure TForm1.SetShareData(P: PChar);
Begin
// TODO
End;
procedure TForm1.Exit1Click(Sender: TObject);
Begin
Application.Terminate;
End;
END.
--------------------------
var
Form1: TForm1;
ChanList: TStringlist;
MircHandle: LongInt;
hMapFile: THandle;
ShareData: PChar = nil;
mCOMMAND: LongInt = WM_USER + 200;
MC: LongInt;
const
VirtualName = 'mIRC';
implementation
{$R *.dfm}
Procedure TForm1.FormCreate(Sender: TObject);
Begin
ChanList := TStringlist.Create;
UpdateActives1Click(self);
MC := WM_USER + 200;
hMapFile := CreateFileMapping($FFFFFFF
if hMapFile = 0 then
raise Exception.Create('Error creating Memory Mapped File, this program can only be run in WinNT, 2000 or XP');
ShareData := MapViewOfFile(hMapFile, File_Map_Write, 0, 0, SizeOf(byte) * 1024);
End;
Procedure TForm1.FormClose(Sender: TObject; var Action: TCloseAction);
Begin
ChanList.Free;
UnMapViewOfFile(Sharedata)
CloseHandle(hMapFile);
End;
function TForm1.TaskList(FirstHandl
var
lngLen:longint;
strBuffer, This, All:string;
TaskHandle: THandle;
begin
MircHandle := 0;
cbChans.ItemIndex := -1;
cbChans.Items.Clear;
ChanList.Clear;
TaskHandle := GetWindow(FirstHandle,GW_H
while TaskHandle > 0 do
begin
if (TaskHandle <> FirstHandle) and (TaskHandle <> Application.Handle) then
begin
lngLen := GetWindowTextLength(TaskHa
SetLength(strBuffer,lngLen
lngLen := GetWindowText(TaskHandle,P
if lngLen > 0 then
begin
This := TrimRight(strBuffer);
if pos('#',This) = 1 then
begin
ChanList.Append(IntToStr(T
cbChans.Items.Append(Copy(
end;
if pos('mIRC',This) = 1 then MircHandle := TaskHandle;
end;
end;
TaskHandle := GetWindow(TaskHandle,GW_HW
end;
if MircHandle = 0 then ShowMessage('Mirc Handle Not found!');
end;
Procedure TForm1.UpdateActives1Click
Begin
TaskList(Application.Handl
if cbChans.Items.Count > 0 then cbChans.ItemIndex := 0;
End;
procedure TForm1.buttonSendThisClick
var T: String;
Begin
T := '/msg _Psych Hello!';
StrPLCopy(ShareData, T,Length(T));
if SendMessage(mirchandle,MC,
then Showmessage('SendMessage returned ERROR!');
End;
procedure TForm1.GetShareData(P: Pchar);
Begin
// TODO
End;
procedure TForm1.SetShareData(P: PChar);
Begin
// TODO
End;
procedure TForm1.Exit1Click(Sender: TObject);
Begin
Application.Terminate;
End;
END.
ASKER CERTIFIED SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
You simply send a message to mIRC and it starts to handle the mapped file.
"WM_MCOMMAND - which should be defined as WM_USER + 200"
is simply the Windows message to send.
const
WM_MCOMMAND = WM_USER+200;
There is NO way to send a string through any Windows message parameter except WM_COPYDATA.
"WM_MCOMMAND - which should be defined as WM_USER + 200"
is simply the Windows message to send.
const
WM_MCOMMAND = WM_USER+200;
There is NO way to send a string through any Windows message parameter except WM_COPYDATA.
Check this out
http://necroman.wot.net/dllhelp.htm#_SendMessage
It seems to use WM_USER + 201 instead, though.
http://necroman.wot.net/dllhelp.htm#_SendMessage
It seems to use WM_USER + 201 instead, though.
ASKER
Works fine. Thank you!
Thanks to everyone else as well. If I had enough points to spread around I'd give you all the same.
Don
Thanks to everyone else as well. If I had enough points to spread around I'd give you all the same.
Don
ASKER
Still could use an example though...