在C#中聲明API函數(shù)
如果你已經(jīng)了解了Visual Basic或者Delphi等語言是如何來實(shí)現(xiàn)對屏幕圖象捕獲的。那么對于C#來說就簡單多了,是如何實(shí)現(xiàn)這種功能的?本文就來探討一下這個問題。
一.程序設(shè)計(jì)開發(fā)及運(yùn)行環(huán)境:
1)微軟視窗2000服務(wù)器版
2).Net FrameWork SDK Beta 2
二.程序設(shè)計(jì)的關(guān)鍵步驟以及具體的實(shí)現(xiàn)方法:
1)首先要創(chuàng)建一個和當(dāng)前屏幕大小相同的Bitmap對象:
要實(shí)現(xiàn)此操作,首先就要現(xiàn)獲得當(dāng)前顯示器的DC,然后根據(jù)此DC來創(chuàng)建Graphic對象,再由此Graphic對象產(chǎn)生此位圖對象。這樣產(chǎn)生的位圖對象才是和當(dāng)前屏幕大小相一致的。由于要獲得顯示器的DC,利用.Net的類庫是無法實(shí)現(xiàn)的,這需要調(diào)用一個Windows的 API函數(shù)。我們知道視窗所有API都封裝在"Kernel"、"User "和"GDI"三個庫中文件中:其中"Kernel",他的庫名為 "KERNEL32.DLL"。"User "這個類庫在Win32中名叫 "USER32.DLL"。 它主要管理全部的用戶接口。譬如:窗口、菜單 、對話框、圖標(biāo)等等。"GDI"(圖象設(shè)備接口),它在Win32中的庫名為:"GDI32.dll",要獲得顯示器的DC,所調(diào)用的API函數(shù) --CreateDC ( ),就被封裝在此類庫中。而要在C#中聲明API函數(shù)需要使用.Net FrameWork SDK中的名字空間"System.Runtime.InteropServices",此名字空間提供了一系列的類來訪問COM對象,和調(diào)用本地的API函數(shù)。下面是在C#中聲明API函數(shù):
- [ System.Runtime.InteropServices.DllImportAttribute ( "gdi32.dll" ) ]
- private static extern IntPtr CreateDC (
- string lpszDriver , // 驅(qū)動名稱
- string lpszDevice , // 設(shè)備名稱
- string lpszOutput , // 無用,可以設(shè)定位"NULL"
- IntPtr lpInitData // 任意的打印機(jī)數(shù)據(jù)
- ) ;
在C#中聲明API函數(shù),就可以創(chuàng)建和顯示器大小一致的位圖對象,具體實(shí)現(xiàn)語句如下:
- IntPtr dc1 = CreateDC ( "DISPLAY" , null , null , ( IntPtr ) null ) ;
- //創(chuàng)建顯示器的DC
- Graphics g1 = Graphics.FromHdc ( dc1 ) ;
- //由一個指定設(shè)備的句柄創(chuàng)建一個新的Graphics對象
- MyImage = new Bitmap ( Screen.PrimaryScreen.Bounds.Width ,
Screen.PrimaryScreen.Bounds.Height , g1 ) ;- //根據(jù)屏幕大小創(chuàng)建一個與之相同大小的Bitmap對象
2)根據(jù)此位圖創(chuàng)建一個和其一樣的Graphic對象:
通過下面代碼就可以實(shí)現(xiàn)此功能:
- Graphics g2 = Graphics.FromImage ( MyImage ) ;
3)獲得當(dāng)前屏幕和位圖的句柄:
獲得此二個對象的句柄是為了下一步實(shí)現(xiàn)對當(dāng)前屏幕圖象的捕獲,程序中實(shí)現(xiàn)的具體捕獲的方法是把當(dāng)前屏幕捕獲到已經(jīng)創(chuàng)建的位圖對象中。具體實(shí)現(xiàn)代碼如下:
- //獲得屏幕的句柄
- IntPtr dc3 = g1.GetHdc ( ) ;
- //獲得位圖的句柄
- IntPtr dc2 = g2.GetHdc ( ) ;
- //把當(dāng)前屏幕捕獲到位圖對象中
4)捕獲當(dāng)前屏幕:
我們是通過當(dāng)前屏幕保存到創(chuàng)建的位圖對象中來實(shí)現(xiàn)的,具體的實(shí)現(xiàn)過程中是通過Windows的一個API函數(shù)--Bitblt。我想大多數(shù)程序員對此API函數(shù)一定不陌生,因?yàn)樵赪indows的圖象編程中,會在很多地方使用到此函數(shù)。這個API函數(shù)和上面介紹的那個API函數(shù)一樣,也是被封裝在"GDI32.dll"中的,下面是在C#中聲明API函數(shù):
- [ System.Runtime.InteropServices.DllImportAttribute ( "gdi32.dll" ) ]
- private static extern bool BitBlt (
- IntPtr hdcDest , // 目標(biāo)設(shè)備的句柄
- int nXDest , // 目標(biāo)對象的左上角的X坐標(biāo)
- int nYDest , // 目標(biāo)對象的左上角的X坐標(biāo)
- int nWidth , // 目標(biāo)對象的矩形的寬度
- int nHeight , // 目標(biāo)對象的矩形的長度
- IntPtr hdcSrc , // 源設(shè)備的句柄
- int nXSrc , // 源對象的左上角的X坐標(biāo)
- int nYSrc , // 源對象的左上角的X坐標(biāo)
- System.Int32 dwRop // 光柵的操作值
- ) ;
5)把當(dāng)前屏幕保存到硬盤,并釋放句柄:
- g1.ReleaseHdc ( dc3 ) ;
- //釋放屏幕句柄
- g2.ReleaseHdc ( dc2 ) ;
- //釋放位圖句柄
- MyImage.Save ( "c:\\MyJpeg.jpg" , ImageFormat.Jpeg ) ;
我們可以根據(jù)自己的要求把當(dāng)前屏幕以不同的文件格式來保存,在本文中介紹的程序是以"jpg"文件來保存的,你可以通過修改"Save"方法的第二個參數(shù)來改變保存到硬盤的文件類型,譬如,如果第二個參數(shù)為"ImageFormat.Gif",那么你保存到硬盤的文件就為"GIF"文件了。對于其他文件格式可以參考.Net FrameWork SDK,里面有詳細(xì)的介紹。
【編輯推薦】