About Monkey 2 › Forums › Monkey 2 Programming Help › Capturing screen
This topic contains 7 replies, has 3 voices, and was last updated by 
 Mark Sibly
 1 year, 11 months ago.
- 
		AuthorPosts
 - 
		
			
				
April 28, 2017 at 11:48 am #8068
Is there any way to capture the screen (Windows)?
I’m thinking the entire screen, not just of the application, I want the desktop and everything to be part of the picture.April 28, 2017 at 10:00 pm #8070This is as far I as go with it, now I need to figure out the datatype conversions. Whoever can continue it, will help a lot.
Monkey12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455#Import "<windows.h>"#Import "<libuser32.a>"ExternFunction MessageBoxA:Int(hWnd:Int, lpText:CString, lpCaption:CString, uType:Int)Function GetDesktopWindow:Int Ptr()Function GetForegroundWindow:Int Ptr()Function GetWindowRect:Bool(hWnd:Int Ptr, rect:Rect Ptr)PublicStruct Rect ' StructLayout(LayoutKind.Sequential)Field Left:IntField Top:IntField Right:IntField Bottom:IntMethod To:String()Return "Rect (" + Left + ", " + Top + ", " + Right + ", " + Bottom + ")"EndEndFunction CaptureWindow(handle:Int Ptr) ' should return BitmapLocal rect := New RectGetWindowRect(handle, Varptr rect)'http://www.pinvoke.net/search.aspx?search=GetWindowRect&namespace=[All]'Print(rect)' var bounds = new Rectangle(rect.Left, rect.Top, rect.Right - rect.Left, rect.Bottom - rect.Top);' var result = new Bitmap(bounds.Width, bounds.Height);' using (var graphics = Graphics.FromImage(result))' {' graphics.CopyFromScreen(new Point(bounds.Left, bounds.Top), Point.Empty, bounds.Size);' }' return result;EndFunction CaptureDesktop()CaptureWindow(GetDesktopWindow())EndFunction CaptureActiveWindow()CaptureWindow(GetForegroundWindow())EndFunction Main:Void()' Tests'MessageBoxA(Null, "Test", "Test", 0)'Print(Cast<Int>(GetDesktopWindow())) ' OK'Print(Cast<Int>(GetForegroundWindow())) ' OKCaptureDesktop()EndApril 30, 2017 at 4:28 pm #8082Yeah I can’t figure it out either… :/
That’s for the help though!May 1, 2017 at 12:22 am #8084There’s this, but it appears to be c++14 only. I have asked the author if he can backport it to c++11 for us (I’m not moving to c++14 just yet…) but I don’t like our chances.
In the meantime, here’s some Windows only source…
Monkey123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110#Import "<std>"Using std..#Import "<windows.h>"#Import "<libuser32.a>"ExternAlias DWORD:UIntAlias HGDIOBJ:Void PtrStruct HDC__EndAlias HDC:HDC__ PtrStruct HWND__EndAlias HWND:HWND__ PtrStruct HBITMAP__EndAlias HBITMAP:HBITMAP__ PtrStruct BITMAPINFOHEADERField biSize:DWORDField biWidth:IntField biHeight:IntField biPlanes:ShortField biBitCount:ShortField biCompression:DWORDEndStruct BITMAPINFOField bmiHeader:BITMAPINFOHEADEREndConst SM_CYVIRTUALSCREEN:IntConst SM_CXVIRTUALSCREEN:IntConst SRCCOPY:DWORDConst NOTSRCCOPY:DWORDConst CAPTUREBLT:DWORDConst DIB_PAL_COLORS:UIntConst DIB_RGB_COLORS:UIntConst BI_RGB:DWORDFunction GetDesktopWindow:HWND()Function GetDC:HDC(hwnd:HWND)Function CreateCompatibleDC:HDC(hdc:HDC)Function GetSystemMetrics:int(index:Int)Function CreateCompatibleBitmap:HBITMAP(hdc:HDC,width:Int,height:Int)Function SelectObject:HGDIOBJ(hdc:HDC,hgdiobj:HGDIOBJ)Function DeleteObject:Int( hgdiobj:HGDIOBJ )Function BitBlt:Int(hdcDest:HDC,nXDest:Int,nYDest:Int,nWidth:Int,nHeight:Int,hdcSrc:HDC,nXSrc:Int,nYSrc:Int,dwRop:DWORD)Function ReleaseDC:Int(hwnd:HWND,hdc:HDC)Function DeleteDC:Int(hdc:HDC)Function GetDIBits:Int( hdc:HDC,hbmp:HBITMAP,firstLine:UInt,numlines:UInt,bitmapData:Void Ptr,bitmapInfo:BITMAPINFO Ptr,usage:UInt )PublicFunction CaptureWindow:Pixmap()Local hwnd:=GetDesktopWindow()Local w:=GetSystemMetrics( SM_CXVIRTUALSCREEN )Local h:=GetSystemMetrics( SM_CYVIRTUALSCREEN )Local hwnddc:=GetDC( hwnd )Local hcapturedc:=CreateCompatibleDC( hwnddc )Local hcapturebmp:=CreateCompatibleBitmap( hwnddc,w,h )SelectObject( hcapturedc,hcapturebmp )BitBlt( hcapturedc,0,0,w,h,hwnddc,0,0,SRCCOPY|CAPTUREBLT )Local bmpInfo:BITMAPINFOlibc.memset( Varptr bmpInfo,0,libc.sizeof( bmpInfo ) )bmpInfo.bmiHeader.biSize = libc.sizeof( bmpInfo.bmiHeader )bmpInfo.bmiHeader.biWidth = wbmpInfo.bmiHeader.biHeight = -hbmpInfo.bmiHeader.biPlanes = 1bmpInfo.bmiHeader.biBitCount = 24bmpInfo.bmiHeader.biCompression = BI_RGBLocal pixmap:=New Pixmap( w,h,PixelFormat.RGB8 )pixmap.Clear( Color.Red )GetDIBits( hcapturedc,hcapturebmp,0,h,pixmap.Data,Varptr bmpInfo,DIB_RGB_COLORS )DeleteDC( hcapturedc )DeleteObject( hcapturebmp )Return pixmapEndFunction Main()Local pm:=CaptureWindow()Print "Captured! w="+pm.Width+", h="+pm.Heightpm.Save( DesktopDir()+"test.png" )EndWindows only…
May 1, 2017 at 6:16 pm #8090Ah, so that’s why you added some more pixelformats.
I always get weird colours with it though, almost inverted colours.May 1, 2017 at 10:06 pm #8091Actually, PixelFormat.RGB8 is just an alias I added for RGB24 – should probably have used RGB24 in the above code to prevent confusion. I recently added a number of GL depth/float pixel formats recently (which aren’t well supported in the Pixmap class yet) and decided I quite like the GL ‘notation’ (which is very similar to mx2 anyway) so have been playing around with switching to it (but leaving the old ones in there). Haven’t decided what to do here in general though.
But I’m surprised the code doesn’t work for you. What OS are you using? What desktop mode? Can you post a pic?
May 2, 2017 at 6:14 pm #8097May 2, 2017 at 10:10 pm #8098> I’m not sure, but I think Red and Blue’s been switched.
Haha!
It’s actually doing the same thing here, only my desktop is so psychedelic I didn’t notice!
Fixed code:
Monkey123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119#Import "<std>"Using std..#Import "<windows.h>"#Import "<libuser32.a>"ExternAlias DWORD:UIntAlias HGDIOBJ:Void PtrStruct HDC__EndAlias HDC:HDC__ PtrStruct HWND__EndAlias HWND:HWND__ PtrStruct HBITMAP__EndAlias HBITMAP:HBITMAP__ PtrStruct BITMAPINFOHEADERField biSize:DWORDField biWidth:IntField biHeight:IntField biPlanes:ShortField biBitCount:ShortField biCompression:DWORDEndStruct BITMAPINFOField bmiHeader:BITMAPINFOHEADEREndConst SM_CYVIRTUALSCREEN:IntConst SM_CXVIRTUALSCREEN:IntConst SRCCOPY:DWORDConst NOTSRCCOPY:DWORDConst CAPTUREBLT:DWORDConst DIB_PAL_COLORS:UIntConst DIB_RGB_COLORS:UIntConst BI_RGB:DWORDFunction GetDesktopWindow:HWND()Function GetDC:HDC(hwnd:HWND)Function CreateCompatibleDC:HDC(hdc:HDC)Function GetSystemMetrics:int(index:Int)Function CreateCompatibleBitmap:HBITMAP(hdc:HDC,width:Int,height:Int)Function SelectObject:HGDIOBJ(hdc:HDC,hgdiobj:HGDIOBJ)Function DeleteObject:Int( hgdiobj:HGDIOBJ )Function BitBlt:Int(hdcDest:HDC,nXDest:Int,nYDest:Int,nWidth:Int,nHeight:Int,hdcSrc:HDC,nXSrc:Int,nYSrc:Int,dwRop:DWORD)Function ReleaseDC:Int(hwnd:HWND,hdc:HDC)Function DeleteDC:Int(hdc:HDC)Function GetDIBits:Int( hdc:HDC,hbmp:HBITMAP,firstLine:UInt,numlines:UInt,bitmapData:Void Ptr,bitmapInfo:BITMAPINFO Ptr,usage:UInt )PublicFunction CaptureWindow:Pixmap()Local hwnd:=GetDesktopWindow()Local w:=GetSystemMetrics( SM_CXVIRTUALSCREEN )Local h:=GetSystemMetrics( SM_CYVIRTUALSCREEN )Local hwnddc:=GetDC( hwnd )Local hcapturedc:=CreateCompatibleDC( hwnddc )Local hcapturebmp:=CreateCompatibleBitmap( hwnddc,w,h )SelectObject( hcapturedc,hcapturebmp )BitBlt( hcapturedc,0,0,w,h,hwnddc,0,0,SRCCOPY|CAPTUREBLT )Local bmpInfo:BITMAPINFOlibc.memset( Varptr bmpInfo,0,libc.sizeof( bmpInfo ) )bmpInfo.bmiHeader.biSize = libc.sizeof( bmpInfo.bmiHeader )bmpInfo.bmiHeader.biWidth = wbmpInfo.bmiHeader.biHeight = -hbmpInfo.bmiHeader.biPlanes = 1bmpInfo.bmiHeader.biBitCount = 24bmpInfo.bmiHeader.biCompression = BI_RGBLocal pixmap:=New Pixmap( w,h,PixelFormat.RGB8 )GetDIBits( hcapturedc,hcapturebmp,0,h,pixmap.Data,Varptr bmpInfo,DIB_RGB_COLORS )For Local y:=0 Until hLocal p:=pixmap.PixelPtr( 0,y )For Local x:=0 Until wLocal t:=p[0]p[0]=p[2]p[2]=tp+=3NextNextDeleteDC( hcapturedc )DeleteObject( hcapturebmp )Return pixmapEndFunction Main()Local pm:=CaptureWindow()Print "Captured! w="+pm.Width+", h="+pm.Heightpm.Save( DesktopDir()+"test.png" )End - 
		AuthorPosts
 
You must be logged in to reply to this topic.
