CreateCompatibleBitmap返回重叠I/O操作正在进行中

本文关键字:操作 进行中 返回 重叠 CreateCompatibleBitmap | 更新日期: 2023-09-27 17:54:13

这是一个使用BitBlt的相当标准的屏幕捕获函数,可以在网上找到:

主要功能:

while(true)
{
    printscreen = GetDesktopImage(X, Y, secMonitorSize.Width, secMonitorSize.Height);
    Thread.Sleep(1000);
}

Capture Desktop功能:

public Bitmap GetDesktopImage(int X, int Y, int width, int height)
{
    IntPtr hDC = WIN32_API.GetDC(WIN32_API.GetDesktopWindow());
    IntPtr hMemDC = WIN32_API.CreateCompatibleDC(hDC);
    IntPtr m_HBitmap = WIN32_API.CreateCompatibleBitmap(hDC, width, height);
    if (m_HBitmap != IntPtr.Zero)
    {
        IntPtr hOld = (IntPtr)WIN32_API.SelectObject(hMemDC, m_HBitmap);
        WIN32_API.BitBlt(hMemDC, 0, 0, width, height, hDC, X, Y, WIN32_API.SRCCOPY | WIN32_API.CAPTURE_BLT);
        WIN32_API.SelectObject(hMemDC, hOld);
        WIN32_API.DeleteDC(hMemDC);
        WIN32_API.ReleaseDC(WIN32_API.GetDesktopWindow(), hDC);
        Bitmap printscreen = System.Drawing.Image.FromHbitmap(m_HBitmap);
        WIN32_API.DeleteObject(m_HBitmap);
        return printscreen;
    }
    return null;
}

问题是代码运行良好大约20分钟,然后CreateCompatibleBitmap将继续返回0。在CreateCompatibleBitmap上使用setlasterror=true,它会显示错误代码997(重叠I/O操作正在进行中)。

只有赛门铁克在后台运行。有人知道如何开始故障排除吗?

CreateCompatibleBitmap返回重叠I/O操作正在进行中

GDI函数不使用GetLastError(),因此使用setlasterror=true将报告来自早期API调用的错误。

试试这个:

public Bitmap GetDesktopImage(int X, int Y, int width, int height)
{
    Bitmap printscreen = null;
    IntPtr hWnd = WIN32_API.GetDesktopWindow();
    IntPtr hDC = WIN32_API.GetDC(hWnd);
    if (hDC != IntPtr.Zero)
    { 
        IntPtr hMemDC = WIN32_API.CreateCompatibleDC(hDC);
        if (hMemDC != IntPtr.Zero)
        {
            IntPtr m_HBitmap = WIN32_API.CreateCompatibleBitmap(hDC, width, height);
            if (m_HBitmap != IntPtr.Zero)
            {
                IntPtr hOld = (IntPtr)WIN32_API.SelectObject(hMemDC, m_HBitmap);
                WIN32_API.BitBlt(hMemDC, 0, 0, width, height, hDC, X, Y, WIN32_API.SRCCOPY | WIN32_API.CAPTURE_BLT);
                WIN32_API.SelectObject(hMemDC, hOld);
                printscreen = System.Drawing.Image.FromHbitmap(m_HBitmap);
                WIN32_API.DeleteObject(m_HBitmap);
            }
            WIN32_API.DeleteDC(hMemDC);
        }
        WIN32_API.ReleaseDC(hWnd, hDC);
    }
    return printscreen;
}