gdi32: Draw single pixel wide, horizontal or vertical lines with the dib driver.
This commit is contained in:
parent
d5d4603062
commit
1e27c95125
|
@ -15,6 +15,7 @@ C_SRCS = \
|
|||
dc.c \
|
||||
dib.c \
|
||||
dibdrv/dc.c \
|
||||
dibdrv/graphics.c \
|
||||
dibdrv/objects.c \
|
||||
dibdrv/primitives.c \
|
||||
driver.c \
|
||||
|
|
|
@ -29,19 +29,6 @@
|
|||
WINE_DEFAULT_DEBUG_CHANNEL(clipping);
|
||||
|
||||
|
||||
/***********************************************************************
|
||||
* get_clip_region
|
||||
*
|
||||
* Return the total clip region (if any).
|
||||
*/
|
||||
static inline HRGN get_clip_region( DC * dc )
|
||||
{
|
||||
if (dc->hMetaClipRgn) return dc->hMetaClipRgn;
|
||||
if (dc->hMetaRgn) return dc->hMetaRgn;
|
||||
return dc->hClipRgn;
|
||||
}
|
||||
|
||||
|
||||
/***********************************************************************
|
||||
* get_clip_rect
|
||||
*
|
||||
|
|
|
@ -192,7 +192,7 @@ const DC_FUNCTIONS dib_driver =
|
|||
NULL, /* pGetTextMetrics */
|
||||
NULL, /* pIntersectClipRect */
|
||||
NULL, /* pInvertRgn */
|
||||
NULL, /* pLineTo */
|
||||
dibdrv_LineTo, /* pLineTo */
|
||||
NULL, /* pModifyWorldTransform */
|
||||
NULL, /* pMoveTo */
|
||||
NULL, /* pOffsetClipRgn */
|
||||
|
|
|
@ -18,6 +18,7 @@
|
|||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
*/
|
||||
|
||||
extern BOOL CDECL dibdrv_LineTo( PHYSDEV dev, INT x, INT y ) DECLSPEC_HIDDEN;
|
||||
extern HPEN CDECL dibdrv_SelectPen( PHYSDEV dev, HPEN hpen ) DECLSPEC_HIDDEN;
|
||||
extern COLORREF CDECL dibdrv_SetDCPenColor( PHYSDEV dev, COLORREF color ) DECLSPEC_HIDDEN;
|
||||
|
||||
|
@ -26,6 +27,11 @@ static inline dibdrv_physdev *get_dibdrv_pdev( PHYSDEV dev )
|
|||
return (dibdrv_physdev *)dev;
|
||||
}
|
||||
|
||||
static inline DC *get_dibdrv_dc( PHYSDEV dev )
|
||||
{
|
||||
return CONTAINING_RECORD( dev, DC, dibdrv );
|
||||
}
|
||||
|
||||
typedef struct primitive_funcs
|
||||
{
|
||||
void (* solid_rects)(const dib_info *dib, int num, RECT *rc, DWORD and, DWORD xor);
|
||||
|
|
|
@ -0,0 +1,47 @@
|
|||
/*
|
||||
* DIB driver graphics operations.
|
||||
*
|
||||
* Copyright 2011 Huw Davies
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2.1 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
*/
|
||||
|
||||
#include "gdi_private.h"
|
||||
#include "dibdrv.h"
|
||||
|
||||
#include "wine/debug.h"
|
||||
|
||||
WINE_DEFAULT_DEBUG_CHANNEL(dib);
|
||||
|
||||
/***********************************************************************
|
||||
* dibdrv_LineTo
|
||||
*/
|
||||
BOOL CDECL dibdrv_LineTo( PHYSDEV dev, INT x, INT y )
|
||||
{
|
||||
PHYSDEV next = GET_NEXT_PHYSDEV( dev, pLineTo );
|
||||
dibdrv_physdev *pdev = get_dibdrv_pdev(dev);
|
||||
POINT pts[2];
|
||||
|
||||
GetCurrentPositionEx(dev->hdc, pts);
|
||||
pts[1].x = x;
|
||||
pts[1].y = y;
|
||||
|
||||
LPtoDP(dev->hdc, pts, 2);
|
||||
|
||||
if(pdev->defer || !pdev->pen_line(pdev, pts, pts + 1))
|
||||
return next->funcs->pLineTo( next, x, y );
|
||||
|
||||
return TRUE;
|
||||
}
|
|
@ -89,6 +89,54 @@ void calc_and_xor_masks(INT rop, DWORD color, DWORD *and, DWORD *xor)
|
|||
*xor = (color & rop2_xor_array[rop-1][0]) | ((~color) & rop2_xor_array[rop-1][1]);
|
||||
}
|
||||
|
||||
static inline void order_end_points(int *s, int *e)
|
||||
{
|
||||
if(*s > *e)
|
||||
{
|
||||
int tmp;
|
||||
tmp = *s + 1;
|
||||
*s = *e + 1;
|
||||
*e = tmp;
|
||||
}
|
||||
}
|
||||
|
||||
static inline BOOL pt_in_rect( const RECT *rect, POINT pt )
|
||||
{
|
||||
return ((pt.x >= rect->left) && (pt.x < rect->right) &&
|
||||
(pt.y >= rect->top) && (pt.y < rect->bottom));
|
||||
}
|
||||
|
||||
static BOOL solid_pen_line(dibdrv_physdev *pdev, POINT *start, POINT *end)
|
||||
{
|
||||
RECT rc;
|
||||
DC *dc = get_dibdrv_dc( &pdev->dev );
|
||||
|
||||
if(get_clip_region(dc) || !pt_in_rect(&dc->vis_rect, *start) || !pt_in_rect(&dc->vis_rect, *end))
|
||||
return FALSE;
|
||||
|
||||
rc.left = start->x;
|
||||
rc.top = start->y;
|
||||
rc.right = end->x;
|
||||
rc.bottom = end->y;
|
||||
|
||||
if(rc.top == rc.bottom)
|
||||
{
|
||||
order_end_points(&rc.left, &rc.right);
|
||||
rc.bottom++;
|
||||
pdev->dib.funcs->solid_rects(&pdev->dib, 1, &rc, pdev->pen_and, pdev->pen_xor);
|
||||
return TRUE;
|
||||
}
|
||||
else if(rc.left == rc.right)
|
||||
{
|
||||
order_end_points(&rc.top, &rc.bottom);
|
||||
rc.right++;
|
||||
pdev->dib.funcs->solid_rects(&pdev->dib, 1, &rc, pdev->pen_and, pdev->pen_xor);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/***********************************************************************
|
||||
* dibdrv_SelectPen
|
||||
*/
|
||||
|
@ -133,6 +181,7 @@ HPEN CDECL dibdrv_SelectPen( PHYSDEV dev, HPEN hpen )
|
|||
case PS_SOLID:
|
||||
if(logpen.lopnStyle & PS_GEOMETRIC) break;
|
||||
if(logpen.lopnWidth.x > 1) break;
|
||||
pdev->pen_line = solid_pen_line;
|
||||
pdev->defer &= ~DEFER_PEN;
|
||||
break;
|
||||
default:
|
||||
|
|
|
@ -101,6 +101,7 @@ typedef struct dibdrv_physdev
|
|||
|
||||
/* pen */
|
||||
DWORD pen_color, pen_and, pen_xor;
|
||||
BOOL (* pen_line)(struct dibdrv_physdev *pdev, POINT *start, POINT *end);
|
||||
} dibdrv_physdev;
|
||||
|
||||
#define DEFER_FORMAT 1
|
||||
|
@ -399,6 +400,14 @@ extern INT BITMAP_GetWidthBytes( INT bmWidth, INT bpp ) DECLSPEC_HIDDEN;
|
|||
/* clipping.c */
|
||||
extern void CLIPPING_UpdateGCRegion( DC * dc ) DECLSPEC_HIDDEN;
|
||||
|
||||
/* Return the total clip region (if any) */
|
||||
static inline HRGN get_clip_region( DC * dc )
|
||||
{
|
||||
if (dc->hMetaClipRgn) return dc->hMetaClipRgn;
|
||||
if (dc->hMetaRgn) return dc->hMetaRgn;
|
||||
return dc->hClipRgn;
|
||||
}
|
||||
|
||||
/* dc.c */
|
||||
extern DC *alloc_dc_ptr( WORD magic ) DECLSPEC_HIDDEN;
|
||||
extern void free_dc_ptr( DC *dc ) DECLSPEC_HIDDEN;
|
||||
|
|
Loading…
Reference in New Issue