鼠标取词相关
来源:互联网 发布:ipad上软件hd 编辑:程序博客网 时间:2024/04/28 01:48
序1撷取自WinObject.cs,针对部份输入文字型的控件,可使用WM_SETTEXT指定文字内容
//由类别名称识别是否为特定的文字输入控件对象
public bool IsEditControl
{
get
{
string cn=ClassName.ToUpper();
return (cn=="EDIT" || cn=="THUNDERRT5TEXTBOX" || cn=="RICHCNTL" || cn=="RICHEDIT");
}
}
const uint WM_GETTEXTLENGTH=0x0e;
const uint WM_GETTEXT=0x0d;
const uint WM_SETTEXT=0x0c;
//窗口对象的标题或控件的文字内容
public string Text
{
get
{
if (IsEditControl)
{
int l=(int) SendMessage(hWnd,WM_GETTEXTLENGTH,0,0);
StringBuilder sb=new StringBuilder(l+1);
l=(int) SendMessage(hWnd,WM_GETTEXT,sb.Capacity,sb);
return sb.ToString();
}
else
{
int length = GetWindowTextLength(hWnd);
StringBuilder sb = new StringBuilder(length + 1);
GetWindowText(hWnd, sb, sb.Capacity);
return sb.ToString();
}
}
set
{
if (IsEditControl)
SendMessage(hWnd,WM_SETTEXT,0,value);
else
SetWindowText(hWnd, value);
}
}
-----end-----
-----box-----
#程序2 与下拉选单互动的范例
[DllImport("USER32.DLL", SetLastError=true)]
public static extern long SendMessage(IntPtr hWnd, uint msg, int wparam, StringBuilder sb);
private void button2_Click(object sender, System.EventArgs e)
{
//由Spy++观察该下拉选单控件的从属关系,以FindChild方式锁定之。
//由于同一层有多个TadvCityCbBox控件,因此使用FindChildren再由数组中取出第2个(户籍地)。
//原理及细节说明请参见前期文章。
WinObject cb = (WinObject)
WinObject.FindWindow("TBasicForm","财政部九十二年度综合所得税二维条形码结算申报系统")
.FindChild("TNotebook","").FindChild("TPage","Basic").FindChild("TPanel","Panel2")
.FindChild("TPanel","").FindChildren("TadvCityCbBox",null)[1];
int itemCount = (int) cb.SendMessage(0x0146,0,0); //CB_GETCOUNT=0x146
string[] itemValues=new string[itemCount];
Debug.Write("共有"+itemCount.ToString()+"个选项,包含有:");
int idxTaipei=-1;
for (int i=0; i<itemCount; i++)
{
//先取得字符串长度 CB_GETLBTEXTLEN 0x0149
int len=(int) cb.SendMessage(0x0149,(uint) i,0);
//取回字符串 CB_GETLBTEXT 0x0148
StringBuilder sb=new StringBuilder(len);
SendMessage(cb.Handle,0x0148, i, sb);
itemValues[i]=sb.ToString();
if (itemValues[i]=="台北市") idxTaipei=i;
if (i % 10==0) Debug.WriteLine("");
Debug.Write(itemValues[i]+" ");
}
Debug.WriteLine("");
//取得目前的选取索引值 CB_GETCURSEL 0x0147
int idxNow=(int) cb.SendMessage(0x0147,0,0);
Debug.WriteLine("目前的选取值="+idxNow.ToString()+"."+itemValues[idxNow]);
//改变选取索引值至台北市的选项,CB_SETCURSEL 0x014E
cb.SendMessage(0x014E,(uint) idxTaipei,0);
Debug.WriteLine("已设定为"+idxTaipei.ToString()+"."+itemValues[idxTaipei]);
}
-----end-----
-----box-----
#程序3 跨程序远程记忆体操作 RemoteMemory.cs
public class RemoteMemory
{
private uint lpMem=0;
private int size=0;
private IntPtr hProcess;
[DllImport("kernel32.dll")]
public static extern IntPtr OpenProcess(uint dwDesiredAccess, int bInheritHandle, uint dwProcessId);
uint PROCESS_VM_OPERATION = (0x0008);
uint PROCESS_VM_READ = (0x0010);
uint PROCESS_VM_WRITE = (0x0020);
uint MEM_COMMIT = 0x1000;
uint MEM_RESERVE = 0x2000;
uint MEM_RELEASE = 0x8000;
uint PAGE_READWRITE = 0x04;
[DllImport("kernel32.dll")]
public static extern uint VirtualAllocEx(IntPtr hProcess, uint lpAddress, uint dwSize, uint flAllocationType, uint flProtect);
[DllImport("kernel32.dll")]
public static extern int WriteProcessMemory(IntPtr hProcess, uint lpBaseAddress, uint lpObject, uint nSize, ref uint lpNumberOfBytesWritten);
[DllImport("kernel32.dll")]
public static extern int ReadProcessMemory(IntPtr hProccess, uint lpBaseAddress, uint lpObject, uint nSize, ref uint lpNumberOfBytesRead);
[DllImport("kernel32.dll")]
public static extern int ReadProcessMemory(IntPtr hProcess, uint lpBaseAddress,[In, Out] byte[] buffer, uint nSize, ref uint lpNumberOfBytesRead);
[DllImport("kernel32.dll")]
public static extern int VirtualFreeEx(IntPtr hProcess, uint lpAddress, int dwSize, uint dwFreeType);
[DllImport("USER32.DLL", SetLastError=true)]
public static extern uint SendMessage(IntPtr hWnd, uint Msg, uint wParam, uint lParam);
[DllImport("user32.dll")]
static extern uint GetWindowThreadProcessId(IntPtr hWnd, ref uint processId);
//在指定的Process中,取得一段指定大小的内存
public RemoteMemory(IntPtr hWnd, int size)
{
uint dwProcessId=0;
GetWindowThreadProcessId(hWnd,ref dwProcessId);
hProcess = OpenProcess(PROCESS_VM_OPERATION | PROCESS_VM_READ | PROCESS_VM_WRITE, 0, dwProcessId);
lpMem=VirtualAllocEx(hProcess, 0, (uint) size, MEM_RESERVE | MEM_COMMIT, PAGE_READWRITE);
this.size=size;
}
//释放原先取得的内存
public void Unallocate()
{
VirtualFreeEx(hProcess, lpMem, 0, MEM_RELEASE);
}
//将对象的内容抄写到先前取得的内存中
public void Write(object o)
{
if (Marshal.SizeOf(o)>size)
throw new ApplicationException("RemoteMemory.Write method error: allocated memory size is not enough!");
GCHandle gc=GCHandle.Alloc(o,GCHandleType.Pinned);
uint bytesWritten=0;
int ret=WriteProcessMemory(hProcess, lpMem, (uint) gc.AddrOfPinnedObject(), (uint) Marshal.SizeOf(o), ref bytesWritten);
}
//将内存中的内容还原至对象
public void Read(ref object o)
{
GCHandle gc=GCHandle.Alloc(o,GCHandleType.Pinned);
uint bytesRead=0;
int ret=ReadProcessMemory(hProcess, lpMem, (uint) gc.AddrOfPinnedObject(), (uint) Marshal.SizeOf(o), ref bytesRead);
}
//将内存中的某一段解析成为字符串
public string ReadCString(uint offset, int stringLen)
{
uint bytesRead=0;
byte[] buffer=new byte[stringLen];
int ret=ReadProcessMemory(hProcess, lpMem+offset, buffer, (uint) stringLen, ref bytesRead);
return szToString(buffer);
}
//将整块内存解析成为字符串
public string ReadCString()
{
return ReadCString(0,size);
}
//将字节转成字符串
private string szToString(byte[] byteArray)
{
int length=0;
for (int i=0; i<byteArray.Length; i++)
{
if (byteArray[i]==0)
{
length=i;
break;
}
}
return System.Text.Encoding.GetEncoding("big5").GetString(byteArray,0,length);
}
//传回内存地址
public uint MemoryAddress
{
get { return lpMem; }
}
}-----end-----
-----box-----
#程序4 将List View的Grid内容,转为DataTable: ListViewSpy.cs
public class ListViewSpy
{
[StructLayout(LayoutKind.Sequential)]
public struct LVITEM //List View的Item数据结构
{
public uint mask;
public int iItem;
public int iSubItem;
public uint state;
public uint stateMask;
public IntPtr pszText; //struct中不可使用StringBuilder
public int cchTextMax;
public int iImage;
public IntPtr lParam;
}
[StructLayout(LayoutKind.Sequential)]
public struct HDITEM //List View的Header数据结构
{
public uint mask;
public int cxy;
public IntPtr pszText;
public uint hbm;
public int cchTextMax;
public int fmt;
public IntPtr lParam;
}
[DllImport("USER32.DLL", SetLastError=true)]
public static extern uint SendMessage(IntPtr hWnd, uint msg, uint wparam, uint lparam);
private IntPtr hWnd;
private int columnCount,rowCount;
private const int MAX_STR_SIZE=256;
private DataTable table=new DataTable();
public ListViewSpy(IntPtr hWnd)
{
this.hWnd=hWnd;
//取得Header(SysHeader32)
uint LVM_GETHEADER=0x1000+31;
IntPtr header=new IntPtr(SendMessage(hWnd,LVM_GETHEADER,0,0));
if (header==IntPtr.Zero) return;
//取得Column数
uint HDM_GETITEMCOUNT=0x1200+0;
columnCount=(int) SendMessage(header,HDM_GETITEMCOUNT,0,0);
//取得Column Header Text
HDITEM hdi=new HDITEM();
uint HDI_TEXT=0x0002;
hdi.mask=HDI_TEXT;
hdi.cchTextMax=MAX_STR_SIZE;
int iStructSize=Marshal.SizeOf(hdi);
//在目的地Process取得一块用来存放HDITEM的内存空间
//并额外多要一些用来放字符串
RemoteMemory rm=new RemoteMemory(hWnd,iStructSize+MAX_STR_SIZE);
//指向额外的空间
hdi.pszText=new IntPtr(rm.MemoryAddress+iStructSize);
//将hdi的内容复制到目的地Process的内存上
rm.Write(hdi);
//SendMessage
uint HDM_GETITEMA=0x1200+3;
byte[] buffer=new byte[MAX_STR_SIZE];
table=new DataTable();
for (int i=0; i<columnCount; i++)
{
int r=(int) SendMessage(header,HDM_GETITEMA, (uint) i,rm.MemoryAddress);
//以字段名称建立DataTable的字段
table.Columns.Add(rm.ReadCString((uint) iStructSize,MAX_STR_SIZE),Type.GetType("System.String"));
}
rm.Unallocate();
//取得ListView资料笔数
uint LVM_GETITEMCOUNT=0x1000+4;
rowCount=(int) SendMessage(hWnd,LVM_GETITEMCOUNT,0,0);
LVITEM lvi=new LVITEM();
uint LVIF_TEXT = 0x0001;
lvi.mask=LVIF_TEXT;
lvi.cchTextMax=MAX_STR_SIZE;
//在目的地Process建立LVITEM,原理同HDITEM
iStructSize=Marshal.SizeOf(lvi);
rm=new RemoteMemory(hWnd,(int) iStructSize+MAX_STR_SIZE);
lvi.pszText=new IntPtr(rm.MemoryAddress+iStructSize);
//SendMessage
uint LVM_GETITEMTEXTA=0x1000+45;
for (int i=0; i<rowCount; i++)
{
lvi.iItem=i;
DataRow row=table.NewRow();
for (int j=0; j<columnCount; j++)
{
lvi.iSubItem=j;
rm.Write(lvi);
int ret=(int) SendMessage(hWnd,LVM_GETITEMTEXTA, (uint) i,rm.MemoryAddress);
row[j]=rm.ReadCString((uint) iStructSize,MAX_STR_SIZE);
}
table.Rows.Add(row);
}
rm.Unallocate();
}
public DataTable Data
{
get { return table;}
}
}
-----end-----
-----box-----
程序5 将Task Manager Processes List View的数据在DataGrid还原, 结果如图3
private void button1_Click(object sender, System.EventArgs e)
{
//使用SPY++时,看到Task Manager的Class Name是#32770 (Dialog)
//寻找时记得只要指定#32770即可,加上(Dialog)后会找不到
WinObject lvProcesses=WinObject.FindWindow("#32770","Windows Task Manager")
.FindChild("#32770","").FindChild("SysListView32","Processes");
ListViewSpy lvs=new ListViewSpy(lvProcesses.Handle);
dataGrid1.DataSource=lvs.Data;
dataGrid1.Refresh();
}
- 鼠标取词相关
- 鼠标屏幕取词
- 鼠标取词
- 鼠标屏幕取词原理
- “鼠标屏幕取词”技术
- 鼠标屏幕取词 原理
- Chrome鼠标取词解决方案
- “鼠标屏幕取词”技术
- 鼠标屏幕取词的原码!
- 鼠标屏幕取词的原码
- 电子词典中鼠标取词的原理
- 鼠标屏幕取词原理 (VC++)
- 鼠标屏幕取词原理 (VC++)
- Linux桌面鼠标取词自动翻译
- 鼠标相关
- 鼠标屏幕取词技术的原理和实现
- 鼠标取词功能的问题与进展
- “鼠标屏幕取词”技术——zhuantie
- 一个类似于Logic与Bean的Jsp标签示例
- Visual C# HTTP协议开发
- Jruby 开发部署 Web Service
- The Grey Lens Man: Scala In The Enterprise
- 使用c语言解析字符串"176x144"中的数字
- 鼠标取词相关
- C/C++类型系统
- 传输格式 TB/TBS/TTI/TF/TFS/TFC/TFCS/TFI/TFCI
- Java编程琐事(1)——日期的处理
- C++析构函数的使用--异常安全
- 工作帮——职场上令人刮目相看的21种修养!
- 生活帮——交朋友的8个小技巧,供大家社交参考。
- 介绍一款针对三岁以上儿童的操作系统
- 关于请求