Fork me on GitHub

C#学习笔记——摄像头

界面:

image

源码:

   1: using System;
   2: using System.Collections.Generic;
   3: using System.ComponentModel;
   4: using System.Data;
   5: using System.Drawing;
   6: using System.Linq;
   7: using System.Text;
   8: using System.Windows.Forms;
   9:  
  10: //添加引用
  11: using System.Runtime.InteropServices;
  12: using System.Drawing.Imaging; 
  13:  
  14:  
  15: namespace Camera
  16: {
  17:  
  18:     public partial class FormMain : Form
  19:     {
  20:         WebCamera wc;
  21:         //声明一个API函数 
  22:         [System.Runtime.InteropServices.DllImportAttribute("gdi32.dll")]
  23:          private static extern bool BitBlt(
  24:             IntPtr hdcDest, // 目标 DC的句柄 
  25:             int nXDest,
  26:             int nYDest,
  27:             int nWidth,
  28:             int nHeight,
  29:             IntPtr hdcSrc, // 源DC的句柄 
  30:             int nXSrc,
  31:             int nYSrc,
  32:             System.Int32 dwRop // 光栅的处理数值 
  33:             ); 
  34:  
  35:         public FormMain()
  36:         {
  37:             InitializeComponent();
  38:         }
  39:  
  40:         private void btnPlay_Click(object sender, EventArgs e)
  41:         {
  42:             btnPlay.Enabled = false;
  43:             btnStop.Enabled = true;
  44:             //panelPreview.Size = new Size(330, 330);
  45:             wc = new WebCamera(panelPreview.Handle, panelPreview.Width, panelPreview.Height);
  46:             wc.StartWebCam();
  47:         }
  48:  
  49:         private void FormMain_Load(object sender, EventArgs e)
  50:         {
  51:             btnPlay.Enabled = false;
  52:             btnStop.Enabled = true;
  53:             //panelPreview.Size = new Size(330, 330);
  54:             wc = new WebCamera(panelPreview.Handle, panelPreview.Width, panelPreview.Height);
  55:             wc.StartWebCam();
  56:         }
  57:  
  58:         private void btnStop_Click(object sender, EventArgs e)
  59:         {
  60:             btnPlay.Enabled = true;
  61:             btnStop.Enabled = false;
  62:             wc.CloseWebcam();
  63:         }
  64:  
  65:         private void btnPhoto_Click(object sender, EventArgs e)
  66:         {
  67:             //创建一个以当前控件区域屏幕为模板的图象 
  68:             Graphics gPanel = this.panelPreview.CreateGraphics(); 
  69:  
  70:             Bitmap bmSave = new Bitmap(this.panelPreview.Width, this.panelPreview.Height);     //用于保存图片的位图对象
  71:             Graphics gSave = Graphics.FromImage(bmSave);
  72:             //得到屏幕的DC 
  73:             IntPtr dcPanel = gPanel.GetHdc();
  74:             //得到Bitmap的DC 
  75:             IntPtr dcSave = gSave.GetHdc();
  76:             //调用此API函数,实现屏幕捕获 
  77:             BitBlt(dcSave, 0, 0, this.panelPreview.Width, this.panelPreview.Height, dcPanel, 0, 0, 13369376);
  78:             //释放掉屏幕的DC 
  79:             gPanel.ReleaseHdc(dcPanel);
  80:             //释放掉Bitmap的DC 
  81:             gSave.ReleaseHdc(dcSave);
  82:             //以JPG文件格式来保存 
  83:             bmSave.Save(@"D:/Photo.jpg", ImageFormat.Jpeg);
  84:             MessageBox.Show("当前图像已经保存为D盘Photo文件!"); 
  85:         }
  86:     }
  87:  
  88:  
  89:  //show Video class
  90:  public class showVideo
  91:  {
  92:   // showVideo calls
  93:   [DllImport("avicap32.dll")] 
  94:   public static extern IntPtr capCreateCaptureWindowA(byte[] lpszWindowName, int dwStyle, int x, int y, int nWidth, int nHeight, IntPtr hWndParent, int nID);
  95:   [DllImport("avicap32.dll")] 
  96:   public static extern bool capGetDriverDescriptionA(short wDriver, byte[] lpszName, int cbName, byte[] lpszVer, int cbVer);
  97:   [DllImport("User32.dll")] 
  98:   public static extern bool SendMessage(IntPtr hWnd, int wMsg, bool wParam, int lParam); 
  99:   [DllImport("User32.dll")] 
 100:   public static extern bool SendMessage(IntPtr hWnd, int wMsg, short wParam, int lParam); 
 101:   [DllImport("User32.dll")] 
 102:   public static extern bool SendMessage(IntPtr hWnd, int wMsg, short wParam, FrameEventHandler lParam); 
 103:   [DllImport("User32.dll")] 
 104:   public static extern bool SendMessage(IntPtr hWnd, int wMsg, int wParam, ref BITMAPINFO lParam);
 105:   [DllImport("User32.dll")] 
 106:   public static extern int SetWindowPos(IntPtr hWnd, int hWndInsertAfter, int x, int y, int cx, int cy, int wFlags);
 107:   [DllImport("avicap32.dll")]
 108:   public static extern int capGetVideoFormat(IntPtr hWnd, IntPtr psVideoFormat, int wSize );
 109:  
 110:   // Constants
 111:   public const int WM_USER = 0x400;
 112:   public const int WS_CHILD = 0x40000000;
 113:   public const int WS_VISIBLE = 0x10000000;
 114:   public const int SWP_NOMOVE = 0x2;
 115:   public const int SWP_NOZORDER = 0x4;
 116:   public const int WM_CAP_DRIVER_CONNECT = WM_USER + 10;
 117:   public const int WM_CAP_DRIVER_DISCONNECT = WM_USER + 11;
 118:   public const int WM_CAP_SET_CALLBACK_FRAME = WM_USER + 5;
 119:   public const int WM_CAP_SET_PREVIEW = WM_USER + 50;
 120:   public const int WM_CAP_SET_PREVIEWRATE = WM_USER + 52;
 121:   public const int WM_CAP_SET_VIDEOFORMAT = WM_USER + 45;
 122:      
 123:   // Structures
 124:   [StructLayout(LayoutKind.Sequential)] public struct VIDEOHDR
 125:   {
 126:    [MarshalAs(UnmanagedType.I4)] public int lpData;
 127:    [MarshalAs(UnmanagedType.I4)] public int dwBufferLength;
 128:    [MarshalAs(UnmanagedType.I4)] public int dwBytesUsed;
 129:    [MarshalAs(UnmanagedType.I4)] public int dwTimeCaptured;
 130:    [MarshalAs(UnmanagedType.I4)] public int dwUser;
 131:    [MarshalAs(UnmanagedType.I4)] public int dwFlags;
 132:    [MarshalAs(UnmanagedType.ByValArray, SizeConst=4)] public int[] dwReserved;
 133:   }
 134:  
 135:   [StructLayout(LayoutKind.Sequential)] public struct BITMAPINFOHEADER
 136:   {
 137:    [MarshalAs(UnmanagedType.I4)] public Int32 biSize ;
 138:    [MarshalAs(UnmanagedType.I4)] public Int32 biWidth ;
 139:    [MarshalAs(UnmanagedType.I4)] public Int32 biHeight ;
 140:    [MarshalAs(UnmanagedType.I2)] public short biPlanes;
 141:    [MarshalAs(UnmanagedType.I2)] public short biBitCount ;
 142:    [MarshalAs(UnmanagedType.I4)] public Int32 biCompression;
 143:    [MarshalAs(UnmanagedType.I4)] public Int32 biSizeImage;
 144:    [MarshalAs(UnmanagedType.I4)] public Int32 biXPelsPerMeter;
 145:    [MarshalAs(UnmanagedType.I4)] public Int32 biYPelsPerMeter;
 146:    [MarshalAs(UnmanagedType.I4)] public Int32 biClrUsed;
 147:    [MarshalAs(UnmanagedType.I4)] public Int32 biClrImportant;
 148:   } 
 149:  
 150:   [StructLayout(LayoutKind.Sequential)] public struct BITMAPINFO
 151:   {
 152:    [MarshalAs(UnmanagedType.Struct, SizeConst=40)] public BITMAPINFOHEADER bmiHeader;
 153:    [MarshalAs(UnmanagedType.ByValArray, SizeConst=1024)] public Int32[] bmiColors;
 154:   }
 155:      
 156:   public delegate void FrameEventHandler(IntPtr lwnd, IntPtr lpVHdr);
 157:      
 158:   // Public methods
 159:   public static object GetStructure(IntPtr ptr,ValueType structure)
 160:   {
 161:    return Marshal.PtrToStructure(ptr,structure.GetType());
 162:   }
 163:   
 164:   public static object GetStructure(int ptr,ValueType structure)
 165:   {
 166:    return GetStructure(new IntPtr(ptr),structure);
 167:   }
 168:      
 169:   public static void Copy(IntPtr ptr,byte[] data)
 170:   {
 171:    Marshal.Copy(ptr,data,0,data.Length);
 172:   }
 173:      
 174:   public static void Copy(int ptr,byte[] data)
 175:   {
 176:    Copy(new IntPtr(ptr),data);
 177:   }
 178:      
 179:   public static int SizeOf(object structure)
 180:   {
 181:    return Marshal.SizeOf(structure); 
 182:   }
 183:  }
 184:  
 185:   //Web Camera Class
 186:  public class WebCamera
 187:  {
 188:   // Constructur
 189:   public WebCamera(IntPtr handle, int width,int height)
 190:   {
 191:    mControlPtr = handle;
 192:    mWidth = width;
 193:    mHeight = height;
 194:   }
 195:      
 196:   // delegate for frame callback
 197:   public delegate void RecievedFrameEventHandler(byte[] data);
 198:   public event RecievedFrameEventHandler RecievedFrame;
 199:      
 200:   private IntPtr lwndC; // Holds the unmanaged handle of the control
 201:   private IntPtr mControlPtr; // Holds the managed pointer of the control
 202:   private int mWidth;
 203:   private int mHeight;
 204:      
 205:   private showVideo.FrameEventHandler mFrameEventHandler; // Delegate instance for the frame callback - must keep alive! gc should NOT collect it
 206:      
 207:   // Close the web camera
 208:   public void CloseWebcam()
 209:   {
 210:    this.capDriverDisconnect(this.lwndC);
 211:   }
 212:      
 213:   // start the web camera
 214:   public void StartWebCam()
 215:   {
 216:    byte[] lpszName = new byte[100];
 217:    byte[] lpszVer = new byte[100];
 218:           
 219:    showVideo.capGetDriverDescriptionA(0, lpszName, 100,lpszVer, 100);
 220:    this.lwndC = showVideo.capCreateCaptureWindowA(lpszName, showVideo.WS_VISIBLE + showVideo.WS_CHILD, 0, 0, mWidth, mHeight, mControlPtr, 0);
 221:           
 222:    if (this.capDriverConnect(this.lwndC, 0))
 223:    {
 224:     this.capPreviewRate(this.lwndC, 66);
 225:     this.capPreview(this.lwndC, true);
 226:     showVideo.BITMAPINFO bitmapinfo = new showVideo.BITMAPINFO(); 
 227:     bitmapinfo.bmiHeader.biSize = showVideo.SizeOf(bitmapinfo.bmiHeader);
 228:     bitmapinfo.bmiHeader.biWidth = 352;
 229:     bitmapinfo.bmiHeader.biHeight = 288;
 230:     bitmapinfo.bmiHeader.biPlanes = 1;
 231:     bitmapinfo.bmiHeader.biBitCount = 24;
 232:     this.capSetVideoFormat(this.lwndC, ref bitmapinfo, showVideo.SizeOf(bitmapinfo));
 233:     this.mFrameEventHandler = new showVideo.FrameEventHandler(FrameCallBack);
 234:     this.capSetCallbackOnFrame(this.lwndC, this.mFrameEventHandler);
 235:     showVideo.SetWindowPos(this.lwndC, 0, 0, 0, mWidth , mHeight , 6);
 236:    } 
 237:   }
 238:  
 239:   // private functions
 240:   private bool capDriverConnect(IntPtr lwnd, short i)
 241:   {
 242:    return showVideo.SendMessage(lwnd, showVideo.WM_CAP_DRIVER_CONNECT, i, 0);
 243:   }
 244:  
 245:   private bool capDriverDisconnect(IntPtr lwnd)
 246:   {
 247:    return showVideo.SendMessage(lwnd, showVideo.WM_CAP_DRIVER_DISCONNECT, 0, 0);
 248:   }
 249:      
 250:   private bool capPreview(IntPtr lwnd, bool f)
 251:   {
 252:    return showVideo.SendMessage(lwnd, showVideo.WM_CAP_SET_PREVIEW , f, 0);
 253:   }
 254:  
 255:   private bool capPreviewRate(IntPtr lwnd, short wMS)
 256:   {
 257:    return showVideo.SendMessage(lwnd, showVideo.WM_CAP_SET_PREVIEWRATE, wMS, 0);
 258:   }
 259:      
 260:   private bool capSetCallbackOnFrame(IntPtr lwnd, showVideo.FrameEventHandler lpProc)
 261:   {     
 262:    return showVideo.SendMessage(lwnd, showVideo.WM_CAP_SET_CALLBACK_FRAME, 0, lpProc);
 263:   }
 264:  
 265:   private bool capSetVideoFormat(IntPtr hCapWnd, ref showVideo.BITMAPINFO BmpFormat, int CapFormatSize)
 266:   {
 267:    return showVideo.SendMessage(hCapWnd, showVideo.WM_CAP_SET_VIDEOFORMAT, CapFormatSize, ref BmpFormat);
 268:   }
 269:  
 270:   private void FrameCallBack(IntPtr lwnd, IntPtr lpVHdr)
 271:   {
 272:    showVideo.VIDEOHDR videoHeader = new showVideo.VIDEOHDR();
 273:    byte[] VideoData;
 274:    videoHeader = (showVideo.VIDEOHDR)showVideo.GetStructure(lpVHdr,videoHeader);
 275:    VideoData = new byte[videoHeader.dwBytesUsed];
 276:    showVideo.Copy(videoHeader.lpData ,VideoData);
 277:    if (this.RecievedFrame != null)
 278:     this.RecievedFrame (VideoData);
 279:   }
 280:  }
 281:  
 282: }
posted @ 2013-02-09 13:22  韩兆新  阅读(4610)  评论(0编辑  收藏  举报