C# 使用 WDM 驱动接口调用摄像头
在 C# 中调用摄像头需要使用 Windows 的多媒体设备 (Windows Multimedia Device,简称 WDM) 驱动接口。以下是一个使用 WDM 驱动接口调用摄像头的示例代码:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Runtime.InteropServices;
namespace CameraCapture
{
class Program
{
// 定义 WDM 设备的相关常量
const int WM_CAP = 0x400;
const int WM_CAP_DRIVER_CONNECT = WM_CAP + 10;
const int WM_CAP_DRIVER_DISCONNECT = WM_CAP + 11;
const int WM_CAP_EDIT_COPY = WM_CAP + 30;
const int WM_CAP_SET_PREVIEW = WM_CAP + 50;
const int WM_CAP_SET_PREVIEWRATE = WM_CAP + 52;
const int WM_CAP_SET_SCALE = WM_CAP + 53;
const int WS_CHILD = 0x40000000;
const int WS_VISIBLE = 0x10000000;
const short SWP_NOMOVE = 0x2;
const short SWP_NOSIZE = 1;
const short SWP_NOZORDER = 0x4;
const short HWND_BOTTOM = 1;
// 导入 Windows API 函数
[DllImport('user32.dll', EntryPoint = 'SendMessageA')]
static extern int SendMessage(IntPtr hwnd, int wMsg, int wParam, [MarshalAs(UnmanagedType.AsAny)] object lParam);
[DllImport('user32.dll', EntryPoint = 'SetWindowPos')]
static extern int SetWindowPos(int hwnd, int hWndInsertAfter, int x, int y, int cx, int cy, int wFlags);
[DllImport('user32.dll')]
static extern bool DestroyWindow(IntPtr hwnd);
[DllImport('avicap32.dll')]
static extern bool capGetDriverDescriptionA(short wDriverIndex, string lpszName, int cbName, string lpszVer, int cbVer);
static void Main(string[] args)
{
// 获取摄像头驱动的数量
int deviceCount = 0;
for (short i = 0; i < 10; i++)
{
string name = new string(' ', 100);
string version = new string(' ', 100);
if (capGetDriverDescriptionA(i, name, 100, version, 100))
{
deviceCount++;
Console.WriteLine('摄像头驱动名称:' + name.Trim());
}
else
{
break;
}
}
// 如果有摄像头驱动,则调用摄像头
if (deviceCount > 0)
{
// 创建窗口并显示摄像头画面
IntPtr hWnd = IntPtr.Zero;
hWnd = capCreateCaptureWindowA('Webcam', WS_VISIBLE | WS_CHILD, 0, 0, 640, 480, 0, 0);
SendMessage(hWnd, WM_CAP_DRIVER_CONNECT, 0, 0);
SendMessage(hWnd, WM_CAP_SET_PREVIEWRATE, 30, 0);
SendMessage(hWnd, WM_CAP_SET_PREVIEW, -1, 0);
// 等待用户按下任意键停止摄像头
Console.WriteLine('按下任意键停止摄像头...');
Console.ReadKey();
// 停止摄像头,并释放资源
SendMessage(hWnd, WM_CAP_DRIVER_DISCONNECT, 0, 0);
DestroyWindow(hWnd);
}
else
{
Console.WriteLine('未找到摄像头驱动!');
}
Console.WriteLine('按下任意键退出程序...');
Console.ReadKey();
}
}
}
以上代码中,我们首先通过capGetDriverDescriptionA函数获取摄像头驱动的数量,并打印出驱动的名称。然后,我们使用capCreateCaptureWindowA函数创建一个窗口,并通过SendMessage函数调用一系列消息来连接摄像头、设置预览速率和显示预览画面。最后,我们等待用户按下任意键停止摄像头,然后停止摄像头并释放资源。
请注意,以上代码使用的是32位版本的 WDM 驱动接口。如果你使用的是 64 位操作系统,请使用capGetDriverDescriptionW、capCreateCaptureWindowW 等函数,并将DllImport 的EntryPoint 属性值改为'SendMessageW'、'SetWindowPos' 等。
此外,以上代码仅仅是一个简单的示例,只能显示摄像头的预览画面。如果想要实现更复杂的功能,如拍照、录像等,可能需要使用更多的 WDM 函数和消息。您可以参考 MSDN 文档 (https://docs.microsoft.com/en-us/windows/win32/multimedia/capture-graph-builder) 来了解更多关于 WDM 驱动接口的信息。
原文地址: https://www.cveoy.top/t/topic/qqSb 著作权归作者所有。请勿转载和采集!