和C#中的两个位图

时间:2010-09-09 17:52:33

标签: c# graphics bitmap gdi+ gdi

我正在尝试和两个这样的位图:

        [DllImport("gdi32.dll")]
        public static extern int SetROP2(IntPtr hDC, int nDrawMode);

        const int SRCAND = 0x008800C6;    // AND raster op.

        lock (g.Clip)
        {
            IntPtr pDC = g.GetHdc ();
            SetROP2 (pDC, SRCAND);
            g.DrawImageUnscaled (currentBitmap, bound.Location);
            g.ReleaseHdc (pDC);
        }

但是我从Draw语句中获得了“Object目前正在使用其他地方”的异常。在Draw语句运行之前移动ReleaseHdc语句,但不使用指定的栅格操作。

LockBits方法太慢,因为它复制了整个位图两次,其中一个位图很大,而且每秒钟都会发生很多次。

我是如何将.NET引入ANDing位图的?

2 个答案:

答案 0 :(得分:3)

    lock (g.Clip)

这不起作用。您将获得此异常,因为您在多个线程中使用位图。我想在另一个绘制位图的线程。要做到这一点,您必须确保两个线程不能同时使用位图。这确实需要lock关键字。但是在相同的锁定对象上。您使用的Graphics实例将不相同。锁不起作用。

创建两个线程都使用的专用锁定对象。

答案 1 :(得分:1)

虽然您找到了解决方法,但值得注意的是异常的实际来源。 GDI和GDI +操作不能交错 - 一个或另一个可以同时运行,但不能同时运行。

在您的代码中,调用g.GetHdc()会将Graphics对象切换到新创建的HDC可用于GDI渲染的状态。然后,在调用g.ReleaseHdc()之前,Graphics对象将“正在使用”。此时,HDC被破坏,然后可以再次使用Graphics对象进行渲染。

注意到GetHdc()调用返回的HDC是ney创建的,只有在调用ReleaseHdc()之后才会存在,在那里它被销毁,很明显为什么ROP不适用于以后由Graphics对象执行的操作。

如果您需要使用GDI ROP,则必须在纯GDI上下文中执行所有关联渲染 - 使用Bitmap.GetHbitmap()来获取必要的句柄。请注意,与Graphics.GetHdc()类似,HBITMAP是从Bitmap新创建的,但与其共享状态。

有关GDI / GDI +互操作的更多详细信息,请参见KB 311221