SendMessage基本认识
函数功能:该函数将指定的消息发送到一个或多个窗口。此函数为指定的窗口调用窗口程序,直到窗口程序处理完消息再返回。而函数PostMessage不同,将一个消息寄送到一个线程的消息队列后立即返回。
函数原型:LRESULT SendMessage(HWND hWnd,UINT Msg,WPARAM wParam,LPARAM IParam);
参数:
hWnd:其窗口程序将接收消息的窗口的句柄。如果此参数为HWND_BROADCAST,则消息将被发送到系统中所有顶层窗口,包括无效或不可见的非自身拥有的窗口、被覆盖的窗口和弹出式窗口,但消息不被发送到子窗口。
Msg:指定被发送的消息。
wParam:指定附加的消息指定信息。
IParam:指定附加的消息指定信息。
返回值:返回值指定消息处理的结果,依赖于所发送的消息。
备注:需要用HWND_BROADCAST通信的应用程序应当使用函数RegisterWindowMessage来为应用程序间的通信取得一个唯一的消息。
如果指定的窗口是由调用线程创建的,则窗口程序立即作为子程序调用。如果指定的窗口是由不同线程创建的,则系统切换到该线程并调用恰当的窗口程序。线程间的消息只有在线程执行消息检索代码时才被处理。发送线程被阻塞直到接收线程处理完消息为止。
Windows CE:Windows CE不支持Windows桌面平台支持的所有消息。使用SendMesssge之前,要检查发送的消息是否被支持。
附:Delphi中SendMessage使用技巧
用SendMessage向控件发送消息
在编程中,有时需要控件以特殊的风格显示,而这种要求又无法通过设置控件属性实现。例如,读取客户列表并显示在下拉框供用户选择,如果下拉框宽度太窄,则不能全部显示;如果将宽度定得太宽,界面又有不紧凑之感。因此希望能在运行期动态地确定下拉框显示区域的宽度,这种要求如果不用SendMessage函数就很难实现。
解决办法是,在读数据库时计算字符串的显示宽度,用显示宽度的最大值确定下拉框显示区域的宽度。再用SendMessage函数向下拉框发送CB_SETDROPPEDWIDTH消息和宽度值,下拉框根据消息中传来的信息,就可以进行正确显示。
部分源程序代码如下:
i:=0; //计数
MaxWidth:=0;
Query1.SQL.Clear;
Query1.SQL.Add(‘select Company from Customer’);
Query1.Open;
//读客户列表到下拉框
while not Query1.Eof do begin
ComboBox1.Items.add(Query1.FieldByName
(‘Company’).AsString);
Width:=ComboBox1.Font.Size * Length
(ComboBox1.Items[i]);
if Width>MaxWidth then
MaxWidth:=Width; //找出最大值
Query1.Next;
i:=i+1;
end;
Query1.Close;
ComboBox1.Text:=ComboBox1.Items[0];
//发送消息以确定显示区域的宽度
SendMessage(ComboBox1.Handle,
CB_SETDROPPEDWIDTH,MaxWidth,0);
利用SendMessage函数还可以实现一些有趣的效果,例如在按钮的Click事件中加入如下语句:
SendMessage(Button.Handle,BM_SETSTYLE,
BS_RADIOBUTTON,1);
运行后点击按钮,就可以把按钮变成一个收音机按钮。
控件接收SendMessage消息
上面讨论了用SendMessage向控件发送消息的过程。但凡事有利就有弊,用SendMessage发送的消息在处理上存在着一定困难。因为该消息不经过消息队列,所以无法用OnMessage方式来指定对消息的响应,甚至用HookMainWindow也不行,因为消息直接发送到控件,绕过了主窗体。要对这种类型的消息作出响应,需要重载控件的WndProc方法。
例如,对于一个列表框,滚动条的滚动消息就是用SendMessage方式发送的,因此该消息不在TlistBox的事件列表中。下面是处理控件响应该滚动消息的具体步骤。
1.首先从TlistBox继承一个TmyListBox类,并重载WndProc方法。在程序中加入下列定义:
type
TMyListBox=class(TListBox)
private
procedure WndProc(var Msg: TMessage);
override;
//重载WndProc,处理发送到控件的消息
public
end;
其中WndProc方法指定控件对消息的响应,输入参数是TMessage类型,该数据类型是一个记录,包含了消息代码和消息的参数,消息参数可以用Longint或Word方式获得。
2.对滚动事件做出响应,在WndProc方法中加入如下处理代码:
if (Msg.Msg=WM_VSCROLL) and
(Msg.WParamLo=SB_ENDSCROLL) then
//获得鼠标位置对应的列
ItemIndex:=ItemAtPos(Point,true);
Form1.Edit1.Text:=inttostr(ItemIndex);
inherited;
end
else
inherited;
当程序接收到WM_VSCROLL消息,且WParamLo参数为SB_ENDSCROLL时,表示竖直滚动条停止滚动,就可以用ItemAtPos方法确定与鼠标位置对应的ItemIndex。ItemAtPos方法的Point参数是一个TPoint类型的变量,用来保存鼠标的位置。
3.定义方法ListBoxMouseMove,在鼠标移动时,将当前位置保存在Point中:
procedure TForm1.ListBoxMouseMove(Sender:
TObject; Shift: TShiftState; X,Y: Integer);
begin
Point.X:=X;
Point.Y:=Y;
end;
4.在运行期创建和初始化列表框,并指定列表框的MouseMove事件对应上一步定义的ListBoxMouseMove方法。在主窗体的Create事件中输入下面的代码:begin
Point.X:=0;
Point.Y:=0;
//创建自定义列表框
List:=TMyListBox.Create(Form1);
List.Parent:=Form1;
List.Left:=5;
List.Top:=30;
List.Width:=150;
List.Height:=200;
for i:=0 to 300 do
begin
List.Items.Add(inttostr(i)); //初始化
end;
//指定处理MouseMove事件的方法
List.OnMouseMove := ListBoxMouseMove; end;
TTreeView:
(引用CommCtrl)
SendMessage(TreeView.Handle,TVM_SETBKCOLOR,0,RGB(255,0,0)); 设置TV背景颜色
SendMessage(Button.Handle,WM_LBUTTONDOWN,0,0); 鼠标左键按下
SendMessage(Button.Handle,WM_LBUTTONUP,0,0); 鼠标左键抬起
SendMessage(Edit.Handle,WM_SETTEXT,255,Integer(PChar('abc'))); 传递文本
SendMessage(Edit.Handle,WM_Char,Wparam('Q'),2); 传递字符
SendMessage(Button.Handle,BM_SETSTYLE,BS_RADIOBUTTON,1); 改变Button风格
SendMessage(ComboBox.Handle,CB_SETDROPPEDWIDTH,300,0); 改变CBDownWidth
WM_CUT、WM_COPY和WM_PASTE 剪切,复制,粘帖
实现任意组合键
keybd_event(VK_Control, MapVirtualKey(VK_Control, 0), 0, 0);
keybd_event(ord('V'), MapVirtualKey(ord('V'), 0), 0, 0);
keybd_event(ord('V'), MapVirtualKey(ord('V'), 0), KEYEVENTF_KEYUP, 0);
keybd_event(VK_Control, MapVirtualKey(VK_Control, 0), KEYEVENTF_KEYUP, 0);
SendMessage基本认识的更多相关文章
- C#调用SendMessage 用法
函数功能:该函数将指定的消息发送到一个或多个窗口.此函数为指定的窗口调用窗口程序,直到窗口程序处理完消息再返回.该函数是应用程序和应用程序之间进行消息传递的主要手段之一. 函数原型:LRESUL ...
- Handler sendMessage 与 obtainMessage (sendToTarget)比较
转自:http://iaiai.iteye.com/blog/1992196 obtainmessage()是从消息池中拿来一个msg 不需要另开辟空间new new需要重新申请,效率低,obtian ...
- Handler.sendMessage 与 Handler.obtainMessage.sendToTarget比较
原文地址: http://www.cnblogs.com/android007/archive/2012/05/10/2494766.html 话说在工作中第一次接触android 的Handler ...
- winform窗体之间通过 windows API SendMessage函数传值
-----------------------------------------------------------‘接收窗体’代码.cs------------------------------ ...
- [C#.net]PostMessage与SendMessage的区别
用 PostMessage.SendNotifyMessage.SendMessageCallback 等异步函数发送系统消息时,参数里不可以使用指针,因为发送者并不等待消息的处理就返回,接受者还没处 ...
- [C#.net] SendMessage
函数功能:该函数将指定的消息发送到一个或多个窗口.此函数为指定的窗口调用窗口程序,直到窗口程序处理完消息再返回.该函数是应用程序和应用程序之间进行消息传递的主要手段之一. 函数原型:LRESU ...
- android wifi obtainmessage sendmessage解析
obtainmessage 从message pool获取一个对象 sendmessage 将message插入message queue java中wait和notify是一对,wait进入睡眠等待 ...
- 【转】在C#中使用SendMessage
SendMessage是一个在user32.dll中声明的API函数,在C#中导入如下: using System.Runtime.InteropServices; [DllImport(" ...
- [外挂6]在指定位置下棋 SendMessage函数
a.鼠标软件模拟,函数SendMessage b.分析窗口内棋子相对坐标X,Y c.软件模拟点击棋盘坐标x,y处的棋子 ::SendMessage(hwnd,WM_LBUTTOMDOWN,0,YX); ...
- C_中使用SendMessage
SendMessage是一个在user32.dll中声明的API函数,在C#中导入如下: using System.Runtime.InteropServices; [DllImport(" ...
随机推荐
- sql 聚合函数用法,及执行顺序
聚合函数无法用在where子句中 , 聚合函数包括count avg sum min max 子句执行顺序from -> where -> group by -> having -& ...
- Android之 compileSdkVersion, minSdkVersion, and targetSdkVersion
在一年之中,也有可能只是几个月后,你会发布你的Android应用程序.但是这中间有可能会发布新的版本的Android系统,比如:6.0+. 你肯定希望你的应用可以向前兼容,当用户升级到新的Androi ...
- Android WebView 小结
1.设置网页的缩放比例的时候,可以使用以下属性: mWebview.setInitialScale(25);//为25%,最小缩放等级 WebSettings setting = mWebview.g ...
- android:versionCode和android:versionName
Android的版本可以在androidmainfest.xml中定义,主要有android:versionCode和android:versionName android:versionCode:主 ...
- inux网卡与MAC地址绑定方法总结
使用linux系统时会出现这样的情况,当你安装了某个网卡的驱动程序时,或者安装了与网卡相关的程序后. 网卡会出现所谓的漂移现象.(注意:不是飘逸).可能的表象为: (1):网卡顺序颠倒,比如之 ...
- python 学习day5(模块)
一.模块介绍 模块,用一砣代码实现了某个功能的代码集合. 类似于函数式编程和面向过程编程,函数式编程则完成一个功能,其他代码用来调用即可,提供了代码的重用性和代码间的耦合.而对于一个复杂的功能来,可能 ...
- 异步方式向WPF ListBox控件中一条一条添加记录
向ListBox绑定数据源时,如果数据量过大,可能会使得程序卡死,这是就需要一条一条的向ListBox的数据源中添加记录了,下面是个小Demo: 1.前台代码,就是一个ListBox控件 <Wi ...
- javascript instanceof
object instanceof constructor instanceof运算符用来检测constructor.prototype是否存在于参数object的原型链上. 对于instanceof ...
- JavaEE Tutorials (21) - Java EE安全:高级主题
21.1使用数字证书331 21.1.1创建服务器证书332 21.1.2向证书安全域增加用户334 21.1.3为GlassFish服务器使用一个不同的服务器证书33421.2认证机制335 21. ...
- POJ 3111 K Best(二分答案)
[题目链接] http://poj.org/problem?id=3111 [题目大意] 选取k个物品,最大化sum(ai)/sum(bi) [题解] 如果答案是x,那么有sigma(a)>=s ...