def _create_bitmap(self, width, height): self._black = gdi32.GetStockObject(BLACK_BRUSH) self._white = gdi32.GetStockObject(WHITE_BRUSH) if self._dc: gdi32.ReleaseDC(self._dc) if self._bitmap: gdi32.DeleteObject(self._bitmap) pitch = width * 4 data = POINTER(c_byte * (height * pitch))() info = BITMAPINFO() info.bmiHeader.biSize = sizeof(info.bmiHeader) info.bmiHeader.biWidth = width info.bmiHeader.biHeight = height info.bmiHeader.biPlanes = 1 info.bmiHeader.biBitCount = 32 info.bmiHeader.biCompression = BI_RGB self._dc = gdi32.CreateCompatibleDC(None) self._bitmap = gdi32.CreateDIBSection(None, byref(info), DIB_RGB_COLORS, byref(data), None, 0) # Spookiness: the above line causes a "not enough storage" error, # even though that error cannot be generated according to docs, # and everything works fine anyway. Call SetLastError to clear it. kernel32.SetLastError(0) self._bitmap_data = data.contents self._bitmap_rect = RECT() self._bitmap_rect.left = 0 self._bitmap_rect.right = width self._bitmap_rect.top = 0 self._bitmap_rect.bottom = height self._bitmap_height = height if _debug_font: _debug('%r._create_dc(%d, %d)' % (self, width, height)) _debug('_dc = %r' % self._dc) _debug('_bitmap = %r' % self._bitmap) _debug('pitch = %r' % pitch) _debug('info.bmiHeader.biSize = %r' % info.bmiHeader.biSize)
def get_icon(image): # Alpha-blended icon: see http://support.microsoft.com/kb/318876 format = 'BGRA' pitch = len(format) * image.width header = BITMAPV5HEADER() header.bV5Size = sizeof(header) header.bV5Width = image.width header.bV5Height = image.height header.bV5Planes = 1 header.bV5BitCount = 32 header.bV5Compression = BI_BITFIELDS header.bV5RedMask = 0x00ff0000 header.bV5GreenMask = 0x0000ff00 header.bV5BlueMask = 0x000000ff header.bV5AlphaMask = 0xff000000 hdc = _user32.GetDC(None) dataptr = c_void_p() bitmap = _gdi32.CreateDIBSection(hdc, byref(header), DIB_RGB_COLORS, byref(dataptr), None, 0) _user32.ReleaseDC(None, hdc) image = image.get_image_data() data = image.get_data(format, pitch) memmove(dataptr, data, len(data)) mask = _gdi32.CreateBitmap(image.width, image.height, 1, 1, None) iconinfo = ICONINFO() iconinfo.fIcon = True iconinfo.hbmMask = mask iconinfo.hbmColor = bitmap icon = _user32.CreateIconIndirect(byref(iconinfo)) _gdi32.DeleteObject(mask) _gdi32.DeleteObject(bitmap) return icon
def _create_cursor_from_image(self, cursor): """Creates platform cursor from an ImageCursor instance.""" fmt = 'BGRA' image = cursor.texture pitch = len(fmt) * image.width header = BITMAPINFOHEADER() header.biSize = sizeof(header) header.biWidth = image.width header.biHeight = image.height header.biPlanes = 1 header.biBitCount = 32 hdc = _user32.GetDC(None) dataptr = c_void_p() bitmap = _gdi32.CreateDIBSection(hdc, byref(header), DIB_RGB_COLORS, byref(dataptr), None, 0) _user32.ReleaseDC(None, hdc) image = image.get_image_data() data = image.get_data(fmt, pitch) memmove(dataptr, data, len(data)) mask = _gdi32.CreateBitmap(image.width, image.height, 1, 1, None) iconinfo = ICONINFO() iconinfo.fIcon = False iconinfo.hbmMask = mask iconinfo.hbmColor = bitmap iconinfo.xHotspot = int(cursor.hot_x) iconinfo.yHotspot = int(image.height - cursor.hot_y) icon = _user32.CreateIconIndirect(byref(iconinfo)) _gdi32.DeleteObject(mask) _gdi32.DeleteObject(bitmap) return icon