如何获取其他程序里的PictureBox的的内容,放到我写的程序中的PictureBox显示

uk340721 2012-04-14 08:08:17
我要写的程序是这样的,启动一个别人写的程序,最小化运行,他的窗口里的一个picturebox的图片我希望能显示在我的程序里。通过api能获取到那个图片控件的句柄,但是怎么把显示过来一直搞不定,一个晚上了,求高人指点
...全文
247 15 打赏 收藏 转发到动态 举报
写回复
用AI写文章
15 条回复
切换为时间正序
请发表友善的回复…
发表回复
东方之珠 2012-04-16
  • 打赏
  • 举报
回复
是可以抓图的,抓图的时候一定要让源窗口恢复原来大小(不能最小化)。
嗷嗷叫的老马 2012-04-16
  • 打赏
  • 举报
回复
最小化的话,应该不会再进程界面绘制了,所以取到的都是黑的.

只能把它以显示的状态移出屏幕可视区以外.....
worldy 2012-04-14
  • 打赏
  • 举报
回复
[Quote=引用 3 楼 的回复:]
lngHwnd = FindWindowEx '获取句柄
画到你的picture里
SendMessage lngHwnd, WM_PRINT, Picture1.hDC, PRF_CHILDREN Or PRF_CLIENT Or PRF_ERASEBKGND Or PRF_NONCLIENT Or PRF_OWNED

或者用 printwindow 这个api
[/Quote]

老兄,你的SendMessage 我怎么无法打印出来,是不是有什么技巧,指点一下
worldy 2012-04-14
  • 打赏
  • 举报
回复
我做了实验,是可以获取到另有个程序A里的PictureBox里的位图,但是,PictureBox被遮挡,则,该位图将是遮挡它的窗口的位图,如果将程序A最小化,获得的位图是一片漆黑

Private Sub Command1_Click() '本函数相关定义见我的博文
Dim b() As Byte
Dim BitmapInfo As BitmapInfo
dim hWnd as long
hwnd=......... '我直接拷贝窗口句柄,你使用你的方法获取

b = GetWindowBmp(hWnd, BitmapInfo, 32&)
SetDIBits 0, Me.Image, 0, BitmapInfo.bmiHeader.biHeight, b(0), BitmapInfo, BI_RGB
Refresh
End Sub


eslbs 2012-04-14
  • 打赏
  • 举报
回复
Private Declare Function PrintWindow Lib "user32" (ByVal hWnd As Long, ByVal hdcBlt As Long, ByVal nFlags As Long) As Long
Private Declare Function FindWindow Lib "user32" Alias "FindWindowA" (ByVal lpClassName As String, ByVal lpWindowName As String) As Long

Private Sub Command1_Click()
Dim mWnd As Long
'launch notepad
'Shell "notepad.exe", vbNormalNoFocus
DoEvents
'set the graphics mode to persistent
Me.AutoRedraw = True
'search the handle of the notepad window
mWnd = FindWindow("Notepad", vbNullString)
If mWnd = 0 Then
Me.Print "NotePad window not found!"
Else
'draw the image of the notepad window on our form
PrintWindow mWnd, Me.hDC, 0
End If
End Sub

这个代码是查找记事本的句柄,然后画在FORM窗体的代码。
改一改就可以变成 查找pictruebox的句柄,然后画到你的pictruebox里了
贝隆 2012-04-14
  • 打赏
  • 举报
回复
问题的关键在于获取源图片框的设备场景,及区域。然后再使用BitBlt来获取即可。
eslbs 2012-04-14
  • 打赏
  • 举报
回复
lngHwnd = FindWindowEx '获取句柄
画到你的picture里
SendMessage lngHwnd, WM_PRINT, Picture1.hDC, PRF_CHILDREN Or PRF_CLIENT Or PRF_ERASEBKGND Or PRF_NONCLIENT Or PRF_OWNED

或者用 printwindow 这个api
PctGL 2012-04-14
  • 打赏
  • 举报
回复
给那个picturebox截图,然后在自己的picturebox显示出来不就行了吗
bcrun 2012-04-14
  • 打赏
  • 举报
回复
用SetParent可能行,但毕竟是两个进程不稳定啊。
worldy 2012-04-14
  • 打赏
  • 举报
回复
[Quote=引用 8 楼 的回复:]
http://www.puritydate.com/download/Crawlpicture20120414.rar

写了一个样例,使用 PrintWindow 的,你看看。

SendMessage 可能涉及了一个不同程序的权限问题,同一个程序是可用的,不同程序要加个复杂处理。
[/Quote]

试了一下,SendMessage 没成功,PrintWindow成功,如果源窗口被别的窗口遮盖,也能正确的拷贝图像,如果源窗口最小化,则和我9L的方法相同,拷贝到的是图像也是一片漆黑。
贝隆 2012-04-14
  • 打赏
  • 举报
回复
[Quote=引用 11 楼 的回复:]
sendmessage wm_print 跨进程不可用, 当前进程的 hdc,传给其他进程后是无效的
开始我也想说 wm_print 来着,后来看lz这意思就是跨进程的就放弃了,确实忘了printwindow了
就用printwindow
[/Quote]
也可以使用DirectX来实现,参阅:

Option Explicit

Private Sub Command1_Click()
Dim lngSDC As Long
Dim picRect As RECT
' DDSFront.BltToDC Picture1.hDC, picRect, picRect
With Picture1
'获得与主显示平面兼容的图形设备句柄
lngSDC = DDSFront.GetDC '获取桌面句柄
' lngSDC = DDSBack.GetDC
' lngSDC = Me.hDC '带入指定窗口的句柄,可以获取窗口内的图形
' lngSDC = GetDC(0)
'保存图像
Set .Picture = SaveTohBmp(lngSDC, 0, 0, 1024, 768)
'释放图形句柄
DDSFront.ReleaseDC lngSDC
' DDSBack.ReleaseDC lngSDC
SavePicture Picture1, "c:\a.bmp"
End With
End Sub

Private Sub Form_Load()
'建立DirectDraw对象
Set DDraw = DX.DirectDrawCreate("")
'设定DirectDraw对象的协作层
DDraw.SetCooperativeLevel Me.hwnd, DDSCL_EXCLUSIVE Or DDSCL_FULLSCREEN ' DDSCL_NORMAL
'设定显示模式位1024×768×32位颜色 此处最好设置为你的电脑的分辨率和颜色位数,不然程序将更改你的设置
DDraw.SetDisplayMode 1024, 768, 32, 0, DDSDM_DEFAULT

'设定DDSFrontDesc为主平面
With DDSFrontDesc
.lFlags = DDSD_CAPS
.ddsCaps.lCaps = DDSCAPS_PRIMARYSURFACE 'Or DDSCAPS_SYSTEMMEMORY
End With
'设定DDSBackDesc为后台缓冲平面
With DDSBackDesc
.ddsCaps.lCaps = DDSCAPS_SYSTEMMEMORY
.lFlags = DDSD_CAPS Or DDSD_WIDTH Or DDSD_HEIGHT
.lWidth = 1920
.lHeight = 1080
End With
'建立平面
Set DDSFront = DDraw.CreateSurface(DDSFrontDesc)
Set DDSBack = DDraw.CreateSurface(DDSBackDesc)
Set Clipper = DDraw.CreateClipper(0)
Clipper.SetHWnd Me.hwnd
DDSFront.SetClipper Clipper
DDSBack.SetClipper Clipper
DDSBack.SetForeColor RGB(255, 255, 255)
End Sub

Private Sub Form_QueryUnload(Cancel As Integer, UnloadMode As Integer)
'恢复原来的显示模式并且释放所有的DirectDraw有关对象
DDraw.RestoreDisplayMode
DDraw.SetCooperativeLevel Me.hwnd, DDSCL_NORMAL
DoEvents
Set Clipper = Nothing
Set DDSBack = Nothing
Set DDSFront = Nothing
Set DDraw = Nothing
Set DX = Nothing
End Sub

Private Sub Timer1_Timer()
Call Command1_Click
' End
End Sub

PctGL 2012-04-14
  • 打赏
  • 举报
回复
sendmessage wm_print 跨进程不可用, 当前进程的 hdc,传给其他进程后是无效的
开始我也想说 wm_print 来着,后来看lz这意思就是跨进程的就放弃了,确实忘了printwindow了
就用printwindow
eslbs 2012-04-14
  • 打赏
  • 举报
回复
Dim rv As Long
Picture1.SetFocus ' So that the button doesn't look pressed
Picture2.AutoRedraw = True

' rv = SendMessage(Picture1.hwnd, WM_PAINT, Picture2.hDC, 0)
' rv = SendMessage(Picture1.hwnd, WM_PRINT, Picture2.hDC, _
' PRF_CHILDREN + PRF_CLIENT + PRF_OWNED)
rv = SendMessage(Text1.Text, WM_PAINT, Picture2.hDC, 0)
rv = SendMessage(Text1.Text, WM_PRINT, Picture2.hDC, _
PRF_CHILDREN + PRF_CLIENT + PRF_OWNED)
Picture2.Picture = Picture2.Image
Picture2.AutoRedraw = False

如果是同一个程序的hwnd 比如picture1.hwnd 这个代码就有效
如果是其他程序的 picture1.hwnd 这个代码就不行
关键是 SendMessage 的参数 Picture2.hDC 对其他程序无效

PrintWindow 本质也是 SendMessage 但是对Picture2.hDC 做了特殊处理以后才给了其他程序。
worldy 2012-04-14
  • 打赏
  • 举报
回复
[Quote=引用 8 楼 的回复:]
http://www.puritydate.com/download/Crawlpicture20120414.rar

写了一个样例,使用 PrintWindow 的,你看看。

SendMessage 可能涉及了一个不同程序的权限问题,同一个程序是可用的,不同程序要加个复杂处理。
[/Quote]

能否写个SendMessage 的方法的范例啊?呵呵

eslbs 2012-04-14
  • 打赏
  • 举报
回复
http://www.puritydate.com/download/Crawlpicture20120414.rar

写了一个样例,使用 PrintWindow 的,你看看。

SendMessage 可能涉及了一个不同程序的权限问题,同一个程序是可用的,不同程序要加个复杂处理。

1,486

社区成员

发帖
与我相关
我的任务
社区描述
VB API
社区管理员
  • API
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧