/*********************************************************************** * dibdrv_SelectBrush */ HBRUSH CDECL dibdrv_SelectBrush( PHYSDEV dev, HBRUSH hbrush ) { PHYSDEV next = GET_NEXT_PHYSDEV( dev, pSelectBrush ); dibdrv_physdev *pdev = get_dibdrv_pdev(dev); LOGBRUSH logbrush; TRACE("(%p, %p)\n", dev, hbrush); if (!GetObjectW( hbrush, sizeof(logbrush), &logbrush )) return 0; if (hbrush == GetStockObject( DC_BRUSH )) logbrush.lbColor = GetDCBrushColor( dev->hdc ); pdev->brush_style = logbrush.lbStyle; pdev->defer |= DEFER_BRUSH; free_pattern_brush( pdev ); switch(logbrush.lbStyle) { case BS_SOLID: pdev->brush_color = pdev->dib.funcs->colorref_to_pixel(&pdev->dib, logbrush.lbColor); calc_and_xor_masks(GetROP2(dev->hdc), pdev->brush_color, &pdev->brush_and, &pdev->brush_xor); pdev->brush_rects = solid_brush; pdev->defer &= ~DEFER_BRUSH; break; case BS_NULL: pdev->brush_rects = null_brush; pdev->defer &= ~DEFER_BRUSH; break; case BS_DIBPATTERN: { BITMAPINFOHEADER *bi = GlobalLock((HGLOBAL)logbrush.lbHatch); dib_info orig_dib; if(!bi) return NULL; if(init_dib_info_from_packed(&orig_dib, bi, LOWORD(logbrush.lbColor))) { copy_dib_color_info(&pdev->brush_dib, &pdev->dib); if(convert_dib(&pdev->brush_dib, &orig_dib)) { pdev->brush_rects = pattern_brush; pdev->defer &= ~DEFER_BRUSH; } free_dib_info(&orig_dib, FALSE); } GlobalUnlock((HGLOBAL)logbrush.lbHatch); break; } default: break; } return next->funcs->pSelectBrush( next, hbrush ); }
static BOOL create_hatch_brush_bits(dibdrv_physdev *pdev) { dib_info hatch; rop_mask fg_mask, bg_mask; rop_mask_bits mask_bits; DWORD size; BOOL ret; assert(pdev->brush_and_bits == NULL); assert(pdev->brush_xor_bits == NULL); /* Just initialise brush_dib with the color / sizing info. We don't need the bits as we'll calculate the rop masks straight from the hatch patterns. */ copy_dib_color_info(&pdev->brush_dib, &pdev->dib); pdev->brush_dib.width = 8; pdev->brush_dib.height = 8; pdev->brush_dib.stride = ((pdev->brush_dib.width * pdev->brush_dib.bit_count + 31) >> 3) & ~3; size = pdev->brush_dib.height * pdev->brush_dib.stride; mask_bits.and = pdev->brush_and_bits = HeapAlloc(GetProcessHeap(), 0, size); mask_bits.xor = pdev->brush_xor_bits = HeapAlloc(GetProcessHeap(), 0, size); if(!mask_bits.and || !mask_bits.xor) { ERR("Failed to create pattern brush bits\n"); free_pattern_brush_bits( pdev ); return FALSE; } hatch.bit_count = 1; hatch.height = hatch.width = 8; hatch.stride = 4; hatch.bits = (void *) hatches[pdev->brush_hatch]; fg_mask.and = pdev->brush_and; fg_mask.xor = pdev->brush_xor; get_brush_bkgnd_masks( pdev, &bg_mask.and, &bg_mask.xor ); ret = pdev->brush_dib.funcs->create_rop_masks( &pdev->brush_dib, &hatch, &fg_mask, &bg_mask, &mask_bits ); if(!ret) free_pattern_brush_bits( pdev ); return ret; }
/*********************************************************************** * dibdrv_SelectBrush */ HBRUSH dibdrv_SelectBrush( PHYSDEV dev, HBRUSH hbrush ) { PHYSDEV next = GET_NEXT_PHYSDEV( dev, pSelectBrush ); dibdrv_physdev *pdev = get_dibdrv_pdev(dev); LOGBRUSH logbrush; TRACE("(%p, %p)\n", dev, hbrush); if (!GetObjectW( hbrush, sizeof(logbrush), &logbrush )) return 0; if (hbrush == GetStockObject( DC_BRUSH )) logbrush.lbColor = GetDCBrushColor( dev->hdc ); pdev->brush_style = logbrush.lbStyle; pdev->defer |= DEFER_BRUSH; free_pattern_brush( pdev ); switch(logbrush.lbStyle) { case BS_SOLID: pdev->brush_colorref = logbrush.lbColor; pdev->brush_color = get_fg_color( pdev, pdev->brush_colorref ); calc_and_xor_masks(GetROP2(dev->hdc), pdev->brush_color, &pdev->brush_and, &pdev->brush_xor); pdev->brush_rects = solid_brush; pdev->defer &= ~DEFER_BRUSH; break; case BS_NULL: pdev->brush_rects = null_brush; pdev->defer &= ~DEFER_BRUSH; break; case BS_DIBPATTERN: { BITMAPINFOHEADER *bi = GlobalLock((HGLOBAL)logbrush.lbHatch); dib_info orig_dib; WORD usage = LOWORD(logbrush.lbColor); HPALETTE pal = (usage == DIB_PAL_COLORS) ? GetCurrentObject(dev->hdc, OBJ_PAL) : NULL; if(!bi) return NULL; if(init_dib_info_from_packed(&orig_dib, bi, usage, pal)) { copy_dib_color_info(&pdev->brush_dib, &pdev->dib); if(convert_dib(&pdev->brush_dib, &orig_dib)) { pdev->brush_rects = pattern_brush; pdev->defer &= ~DEFER_BRUSH; } free_dib_info(&orig_dib); } GlobalUnlock((HGLOBAL)logbrush.lbHatch); break; } case BS_HATCHED: { if(logbrush.lbHatch > HS_DIAGCROSS) return 0; pdev->brush_hatch = logbrush.lbHatch; pdev->brush_colorref = logbrush.lbColor; pdev->brush_color = get_fg_color( pdev, pdev->brush_colorref ); calc_and_xor_masks(GetROP2(dev->hdc), pdev->brush_color, &pdev->brush_and, &pdev->brush_xor); pdev->brush_rects = pattern_brush; pdev->defer &= ~DEFER_BRUSH; break; } default: break; } return next->funcs->pSelectBrush( next, hbrush ); }