4 * Copyright 1993, 1994 Alexandre Julliard
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
27 #include "wine/wingdi16.h"
29 #include "wine/debug.h"
31 WINE_DEFAULT_DEBUG_CHANNEL(gdi
);
33 /* GDI logical brush object */
40 #define NB_HATCH_STYLES 6
42 static HGDIOBJ
BRUSH_SelectObject( HGDIOBJ handle
, void *obj
, HDC hdc
);
43 static INT
BRUSH_GetObject16( HGDIOBJ handle
, void *obj
, INT count
, LPVOID buffer
);
44 static INT
BRUSH_GetObject( HGDIOBJ handle
, void *obj
, INT count
, LPVOID buffer
);
45 static BOOL
BRUSH_DeleteObject( HGDIOBJ handle
, void *obj
);
47 static const struct gdi_obj_funcs brush_funcs
=
49 BRUSH_SelectObject
, /* pSelectObject */
50 BRUSH_GetObject16
, /* pGetObject16 */
51 BRUSH_GetObject
, /* pGetObjectA */
52 BRUSH_GetObject
, /* pGetObjectW */
53 NULL
, /* pUnrealizeObject */
54 BRUSH_DeleteObject
/* pDeleteObject */
57 static HGLOBAL16
dib_copy(BITMAPINFO
*info
, UINT coloruse
)
63 if (info
->bmiHeader
.biCompression
)
64 size
= info
->bmiHeader
.biSizeImage
;
66 size
= DIB_GetDIBImageBytes(info
->bmiHeader
.biWidth
,
67 info
->bmiHeader
.biHeight
,
68 info
->bmiHeader
.biBitCount
);
69 size
+= DIB_BitmapInfoSize( info
, coloruse
);
71 if (!(hmem
= GlobalAlloc16( GMEM_MOVEABLE
, size
)))
75 newInfo
= (BITMAPINFO
*) GlobalLock16( hmem
);
76 memcpy( newInfo
, info
, size
);
77 GlobalUnlock16( hmem
);
83 static BOOL
create_brush_indirect(BRUSHOBJ
*brushPtr
, BOOL v16
)
85 LOGBRUSH
*brush
= &brushPtr
->logbrush
;
87 switch (brush
->lbStyle
)
90 brush
->lbStyle
= BS_PATTERN
;
92 brush
->lbHatch
= (LONG
)BITMAP_CopyBitmap( (HBITMAP
) brush
->lbHatch
);
98 brush
->lbStyle
= BS_DIBPATTERN
;
99 brush
->lbHatch
= (LONG
)dib_copy( (BITMAPINFO
*) brush
->lbHatch
,
101 if (! brush
->lbHatch
)
105 case BS_DIBPATTERN8X8
:
109 HGLOBAL h
= brush
->lbHatch
;
111 brush
->lbStyle
= BS_DIBPATTERN
;
114 if (!(bmi
= (BITMAPINFO
*)GlobalLock16( h
)))
119 if (!(bmi
= (BITMAPINFO
*)GlobalLock( h
)))
123 brush
->lbHatch
= dib_copy( bmi
, brush
->lbColor
);
125 if (v16
) GlobalUnlock16( h
);
126 else GlobalUnlock( h
);
135 if( brush
->lbStyle
<= BS_MONOPATTERN
)
143 /***********************************************************************
144 * CreateBrushIndirect (GDI.50)
146 HBRUSH16 WINAPI
CreateBrushIndirect16( const LOGBRUSH16
* brush
)
152 if (!(brushPtr
= GDI_AllocObject( sizeof(BRUSHOBJ
), BRUSH_MAGIC
, &hbrush
, &brush_funcs
)))
154 brushPtr
->logbrush
.lbStyle
= brush
->lbStyle
;
155 brushPtr
->logbrush
.lbColor
= brush
->lbColor
;
156 brushPtr
->logbrush
.lbHatch
= brush
->lbHatch
;
157 success
= create_brush_indirect(brushPtr
, TRUE
);
160 GDI_FreeObject( hbrush
, brushPtr
);
163 else GDI_ReleaseObj( hbrush
);
164 TRACE("%04x\n", hbrush
);
169 /***********************************************************************
170 * CreateBrushIndirect (GDI32.@)
173 * As for Windows 95 and Windows 98:
174 * Creating brushes from bitmaps or DIBs larger than 8x8 pixels
175 * is not supported. If a larger bitmap is given, only a portion
176 * of the bitmap is used.
178 HBRUSH WINAPI
CreateBrushIndirect( const LOGBRUSH
* brush
)
183 if (!(brushPtr
= GDI_AllocObject( sizeof(BRUSHOBJ
), BRUSH_MAGIC
, &hbrush
, &brush_funcs
)))
185 brushPtr
->logbrush
.lbStyle
= brush
->lbStyle
;
186 brushPtr
->logbrush
.lbColor
= brush
->lbColor
;
187 brushPtr
->logbrush
.lbHatch
= brush
->lbHatch
;
188 success
= create_brush_indirect(brushPtr
, FALSE
);
191 GDI_FreeObject( hbrush
, brushPtr
);
194 else GDI_ReleaseObj( hbrush
);
195 TRACE("%08x\n", hbrush
);
200 /***********************************************************************
201 * CreateHatchBrush (GDI.58)
203 HBRUSH16 WINAPI
CreateHatchBrush16( INT16 style
, COLORREF color
)
205 return CreateHatchBrush( style
, color
);
209 /***********************************************************************
210 * CreateHatchBrush (GDI32.@)
212 HBRUSH WINAPI
CreateHatchBrush( INT style
, COLORREF color
)
216 TRACE("%d %06lx\n", style
, color
);
218 logbrush
.lbStyle
= BS_HATCHED
;
219 logbrush
.lbColor
= color
;
220 logbrush
.lbHatch
= style
;
222 return CreateBrushIndirect( &logbrush
);
226 /***********************************************************************
227 * CreatePatternBrush (GDI.60)
229 HBRUSH16 WINAPI
CreatePatternBrush16( HBITMAP16 hbitmap
)
231 return (HBRUSH16
)CreatePatternBrush( hbitmap
);
235 /***********************************************************************
236 * CreatePatternBrush (GDI32.@)
238 HBRUSH WINAPI
CreatePatternBrush( HBITMAP hbitmap
)
240 LOGBRUSH logbrush
= { BS_PATTERN
, 0, 0 };
241 TRACE("%04x\n", hbitmap
);
243 logbrush
.lbHatch
= hbitmap
;
244 return CreateBrushIndirect( &logbrush
);
248 /***********************************************************************
249 * CreateDIBPatternBrush (GDI.445)
251 HBRUSH16 WINAPI
CreateDIBPatternBrush16( HGLOBAL16 hbitmap
, UINT16 coloruse
)
255 TRACE("%04x\n", hbitmap
);
257 logbrush
.lbStyle
= BS_DIBPATTERN
;
258 logbrush
.lbColor
= coloruse
;
259 logbrush
.lbHatch
= hbitmap
;
261 return CreateBrushIndirect16( &logbrush
);
265 /***********************************************************************
266 * CreateDIBPatternBrush (GDI32.@)
268 * Create a logical brush which has the pattern specified by the DIB
270 * Function call is for compatibility only. CreateDIBPatternBrushPt should be used.
274 * Handle to a logical brush on success, NULL on failure.
279 HBRUSH WINAPI
CreateDIBPatternBrush(
280 HGLOBAL hbitmap
, /* [in] Global object containg BITMAPINFO structure */
281 UINT coloruse
/* [in] Specifies color format, if provided */
286 TRACE("%04x\n", hbitmap
);
288 logbrush
.lbStyle
= BS_DIBPATTERN
;
289 logbrush
.lbColor
= coloruse
;
291 logbrush
.lbHatch
= (LONG
)hbitmap
;
293 return CreateBrushIndirect( &logbrush
);
297 /***********************************************************************
298 * CreateDIBPatternBrushPt (GDI32.@)
300 * Create a logical brush which has the pattern specified by the DIB
304 * Handle to a logical brush on success, NULL on failure.
309 HBRUSH WINAPI
CreateDIBPatternBrushPt(
310 const void* data
, /* [in] Pointer to a BITMAPINFO structure followed by more data */
311 UINT coloruse
/* [in] Specifies color format, if provided */
314 BITMAPINFO
*info
=(BITMAPINFO
*)data
;
317 TRACE("%p %ldx%ld %dbpp\n", info
, info
->bmiHeader
.biWidth
,
318 info
->bmiHeader
.biHeight
, info
->bmiHeader
.biBitCount
);
320 logbrush
.lbStyle
= BS_DIBPATTERNPT
;
321 logbrush
.lbColor
= coloruse
;
322 logbrush
.lbHatch
= (LONG
) data
;
324 return CreateBrushIndirect( &logbrush
);
328 /***********************************************************************
329 * CreateSolidBrush (GDI.66)
331 HBRUSH16 WINAPI
CreateSolidBrush16( COLORREF color
)
333 return CreateSolidBrush( color
);
337 /***********************************************************************
338 * CreateSolidBrush (GDI32.@)
340 HBRUSH WINAPI
CreateSolidBrush( COLORREF color
)
344 TRACE("%06lx\n", color
);
346 logbrush
.lbStyle
= BS_SOLID
;
347 logbrush
.lbColor
= color
;
348 logbrush
.lbHatch
= 0;
350 return CreateBrushIndirect( &logbrush
);
354 /***********************************************************************
355 * SetBrushOrg (GDI.148)
357 DWORD WINAPI
SetBrushOrg16( HDC16 hdc
, INT16 x
, INT16 y
)
360 DC
*dc
= DC_GetDCPtr( hdc
);
361 if (!dc
) return FALSE
;
362 retval
= dc
->brushOrgX
| (dc
->brushOrgY
<< 16);
365 GDI_ReleaseObj( hdc
);
370 /***********************************************************************
371 * SetBrushOrgEx (GDI32.@)
373 BOOL WINAPI
SetBrushOrgEx( HDC hdc
, INT x
, INT y
, LPPOINT oldorg
)
375 DC
*dc
= DC_GetDCPtr( hdc
);
377 if (!dc
) return FALSE
;
380 oldorg
->x
= dc
->brushOrgX
;
381 oldorg
->y
= dc
->brushOrgY
;
385 GDI_ReleaseObj( hdc
);
389 /***********************************************************************
390 * FixBrushOrgEx (GDI32.@)
391 * SDK says discontinued, but in Win95 GDI32 this is the same as SetBrushOrgEx
393 BOOL WINAPI
FixBrushOrgEx( HDC hdc
, INT x
, INT y
, LPPOINT oldorg
)
395 return SetBrushOrgEx(hdc
,x
,y
,oldorg
);
399 /***********************************************************************
402 static HGDIOBJ
BRUSH_SelectObject( HGDIOBJ handle
, void *obj
, HDC hdc
)
404 BRUSHOBJ
*brush
= obj
;
406 DC
*dc
= DC_GetDCPtr( hdc
);
410 if (brush
->logbrush
.lbStyle
== BS_PATTERN
)
411 BITMAP_SetOwnerDC( (HBITMAP
)brush
->logbrush
.lbHatch
, dc
);
414 if (dc
->funcs
->pSelectBrush
) handle
= dc
->funcs
->pSelectBrush( dc
->physDev
, handle
);
415 if (handle
) dc
->hBrush
= handle
;
417 GDI_ReleaseObj( hdc
);
422 /***********************************************************************
425 static BOOL
BRUSH_DeleteObject( HGDIOBJ handle
, void *obj
)
427 BRUSHOBJ
*brush
= obj
;
429 switch(brush
->logbrush
.lbStyle
)
432 DeleteObject( (HGDIOBJ
)brush
->logbrush
.lbHatch
);
435 GlobalFree16( (HGLOBAL16
)brush
->logbrush
.lbHatch
);
438 return GDI_FreeObject( handle
, obj
);
442 /***********************************************************************
445 static INT
BRUSH_GetObject16( HGDIOBJ handle
, void *obj
, INT count
, LPVOID buffer
)
447 BRUSHOBJ
*brush
= obj
;
450 logbrush
.lbStyle
= brush
->logbrush
.lbStyle
;
451 logbrush
.lbColor
= brush
->logbrush
.lbColor
;
452 logbrush
.lbHatch
= brush
->logbrush
.lbHatch
;
453 if (count
> sizeof(logbrush
)) count
= sizeof(logbrush
);
454 memcpy( buffer
, &logbrush
, count
);
459 /***********************************************************************
462 static INT
BRUSH_GetObject( HGDIOBJ handle
, void *obj
, INT count
, LPVOID buffer
)
464 BRUSHOBJ
*brush
= obj
;
466 if (count
> sizeof(brush
->logbrush
)) count
= sizeof(brush
->logbrush
);
467 memcpy( buffer
, &brush
->logbrush
, count
);
472 /***********************************************************************
473 * SetSolidBrush (GDI.604)
475 * If hBrush is a solid brush, change its color to newColor.
478 * TRUE on success, FALSE on failure.
480 * FIXME: untested, not sure if correct.
482 BOOL16 WINAPI
SetSolidBrush16(HBRUSH16 hBrush
, COLORREF newColor
)
487 TRACE("(hBrush %04x, newColor %08lx)\n", hBrush
, (DWORD
)newColor
);
488 if (!(brushPtr
= (BRUSHOBJ
*) GDI_GetObjPtr( hBrush
, BRUSH_MAGIC
)))
491 if (brushPtr
->logbrush
.lbStyle
== BS_SOLID
)
493 brushPtr
->logbrush
.lbColor
= newColor
;
497 GDI_ReleaseObj( hBrush
);