我实在想不明白我的问题所以来请教一下您希望能给个明灯。。 其实也就是句柄问题.我的程序上面有一个StatusBar1控件.增加了3个Panels.现在我想再另外写一个软件来实时监控第二个Panels的text。可是我在网上找了很多都没解决掉。也试过用EnumChildWindows(hFrm, @TryGetText, LPARAM(Self))获取父窗口然后列举所有子窗口也没有成功。。
所以想请大哥帮帮忙看看如何才能获取得到,晚上可以再加分
所以想请大哥帮帮忙看看如何才能获取得到,晚上可以再加分
解决方案 »
- 如何在combobox中添加数据并显示检索到的第一条记录
- InternetExplorer中的消息框如何去掉
- 我想问下进销存软件的基本流程?
- 想请教一个关于DELPHI能否跨平台运行呢?
- 怎样调整TTreeView控件中每个节点DisplayRect(false)区域的高度?
- 学习Delphi的好书!
- 请问,如何将combobox作为stringgrid每一个单元格的元素?
- 如何改变Hint提示的背景颜色?
- Windows消息中经常用到inherited;inherited语句到底是什么意思,怎样工作的。
- 请教:如何显示数据库中指定文件名的图片?
- 为什么我的组件上放不了其他组件.高手帮忙
- 问一个简单问题;
如果SPY++都看不到,你再怎么Enum也是没用的2.那个程序能不能给个下载地址,方便我们试试
1:用SPY++也看不到~~只看到panels的第一个值.第二个和第三个都看不到。。但是既然程序都能找到相应的方式更新那一个值。应该有相关的句柄才对呀。。难道panels后二个值是画上去的?不明白...
2:就是在delphi上面增加一个StatusBar1控件,然后建几个子就可以测试了呀。没有下载地址
谢谢你的思路
但是我想的是在不改变"被监控"的软件结构就能由监控软件来获取得到他的值
我也知道除了直接找到他的相关位置然后取他用getwindowtext方式取得他的值之外还可以用读取他的内取来获得相关值。
我只是想知道为什么没有找不到他的句柄
楼上的朋友不好意思呀刚刚洗了个澡..我看了一下SB_GETTEXT这个参数..但是不知道怎么将值读出来.下面是我写的。如何才能改成我需要的效果呢(是不是要将DLL注入到某窗体上呢?)
function HandleTEXT(Handlea:THandle):string;
var
s:array[0..255] of Char;
dw:DWORD;
begin
SendMessage(Handlea, SB_GETTEXT,Length(S), Integer(@S));
Result:=S;
end;procedure TForm1.Button1Click(Sender: TObject);
var
HWindow,hedit: THandle; //句本柄变量
szText: string; //得到的字符串
begin
HWindow:=0;
HWindow:=FindWindow(nil,'学习句柄');
HWindow:=FindWindowEx(HWindow,0,'TStatusBar',nil);//找Sta句柄
szText:=HandleTEXT(HWindow); //将sta的pan值取出来
ShowMessage(IntToStr(HWindow));
ShowMessage(szText);
end;
我这里有一段C++的代码,你自己翻译成Delphi代码就可以了:void __stdcall CrnGetStatusBarItem(HANDLE hStatusBar, TStrings *pList)
{
DWORD dwProcessID;
HANDLE hProcess;
LPVOID lpCommon;
int nAllocSize = 255;
int nPnlLen;
char szBuf[255];
DWORD dwBytesRead;
int nPnlCount = SendMessage(hStatusBar, SB_GETPARTS, 0, 0);
pList->Add("StatusBar的项目数: " + String(nPnlCount)); GetWindowThreadProcessId(hStatusBar, &dwProcessID);
hProcess = OpenProcess(PROCESS_VM_OPERATION | PROCESS_VM_READ |
PROCESS_VM_WRITE, false, dwProcessID);
lpCommon = VirtualAllocEx(hProcess, NULL, nAllocSize,
MEM_RESERVE | MEM_COMMIT, PAGE_READWRITE); for(int i=0; i<nPnlCount; i++)
{
SendMessage(hStatusBar, SB_GETTEXT, i, LPARAM(lpCommon));
ReadProcessMemory(hProcess, lpCommon, szBuf, 255, &dwBytesRead);
pList->Add(szBuf);
}
VirtualFreeEx(hProcess, lpCommon, 0, MEM_RELEASE);
CloseHandle(hProcess);
}
uses commctrl;procedure CrnGetStatusBarItem(hStatusBar: THandle; pList: TStrings);
var
dwProcessID: DWORD;
hProcess: THandle;
lpCommon: Pointer;
nAllocSize: integer;// = 255;
szBuf: array [0..255] of char;
dwBytesRead: DWORD;
nPnlCount: integer;
i: integer;
begin
nAllocSize := 255;
nPnlCount := SendMessage(hStatusBar, SB_GETPARTS, 0, 0);
pList.Add('StatusBar的项目数: ' + IntToStr(nPnlCount)); GetWindowThreadProcessId(hStatusBar, @dwProcessID);
hProcess := OpenProcess(PROCESS_VM_OPERATION or PROCESS_VM_READ, false, dwProcessID);
lpCommon := VirtualAllocEx(hProcess, nil, nAllocSize,
MEM_RESERVE or MEM_COMMIT, PAGE_READWRITE); for i := 0 to nPnlCount - 1 do
begin
SendMessage(hStatusBar, SB_GETTEXT, i, LPARAM(lpCommon));
ReadProcessMemory(hProcess, lpCommon, @szBuf, 255, dwBytesRead);
pList.Add(szBuf);
end; VirtualFreeEx(hProcess, lpCommon, 0, MEM_RELEASE);
CloseHandle(hProcess);
end;procedure TForm1.Button1Click(Sender: TObject);
var
hTopWnd, hWnd: THandle;
begin
hTopWnd := FindWindow('MSPaintApp', nil);
if IsWindow(hTopWnd) then
begin
hWnd := FindWindowEx(hTopWnd, 0, 'msctls_statusbar32', nil);
if IsWindow(hWnd) then
CrnGetStatusBarItem(hWnd, Memo1.Lines);
end;
end;在窗体上添加一个按钮和一个Memo,然后打开画笔(mspaint.exe),编译并运行这个程序,点击按钮就可以看到效果。
是的,VCL中的状态栏,类名是TStatusBar,而Windows的状态栏原生类名是msctls_statusbar32