最近做一个VB升级到.NET的项目,发现 SetWindowText对.NET的Button控件无效,但是同样的代码,对于TextBox却是有效的。这个问题困扰了我好几天,最后通过对.NET的类库反编译之后发现,原来.NET的Button控件有两个极其相似的属性,WindowText和Text,SetWindowText只能更改WindowText的属性,而不是Text属性,但是重画窗体的时候,却是使用Text属性的值,因此SetWindowText对Button控件无效。下面的代码可以进行测试。
Private
Declare
Function SetWindowText()
Function SetWindowText Lib "user32" Alias "SetWindowTextA"(ByVal hWnd As Integer, ByVal lpString As String) As Integer
<DllImport("user32.dll", SetLastError:=True, CharSet:=CharSet.Auto)> _
Private Shared Function GetWindowText()Function GetWindowText(ByVal hwnd As IntPtr, _
ByVal lpString As StringBuilder, _
ByVal cch As Integer) As Integer
End Function
Private Sub Button3_Click()Sub Button3_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button3.Click
Call SetWindowText(Button1.Handle, "aaaa")
Dim c As String = Space(1024)
Dim d As Integer
Call GetWindowText(Button1.Handle, c, 1024)
MsgBox(c)
MsgBox(Button1.Text)
End Sub
<DllImport("user32.dll", SetLastError:=True, CharSet:=CharSet.Auto)> _
Private Shared Function GetWindowText()Function GetWindowText(ByVal hwnd As IntPtr, _
ByVal lpString As StringBuilder, _
ByVal cch As Integer) As Integer
End Function
Private Sub Button3_Click()Sub Button3_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button3.Click
Call SetWindowText(Button1.Handle, "aaaa")
Dim c As String = Space(1024)
Dim d As Integer
Call GetWindowText(Button1.Handle, c, 1024)
MsgBox(c)
MsgBox(Button1.Text)
End Sub
那么,该如何才能动态地修改其它Button的文字呢?
如果是同一个应用程序的话,当然可以直接使用Button1.Text = "XXXXX"来修改,跨进程间的这种操作就比较麻烦了。.NET为了提高进程间的稳定性,基本上是不允许跨进程访问各自的对象的。
客户的需求就是命令,经过查找资料,可以采用HOOK的方式,把两个进程联系在一起,通过.NET调用SetWindowsHookEx函数能否实现呢?????HOOK处理必须编译成DLL的方式才能正常工作,而且.NET只能处理键盘消息和鼠标消息这两种全局消息,其他的消息钩子是无效的,这真是让人头疼的事情。本人对于C++还一窍不通,最后上MSDN找到了一个现成的类库,而且还有代码,据说是一个在微软工作十几年的老大爷写得,看得我一头雾水,最后索性直接拿过来用了(反正也提供代码,就不能说是盗版了,微软应该不能告我吧)。
有同样问题的人可以从下面的URL下载,想学习HOOK处理的人也可以拿过来作为参考哦!