brush.c 5.89 KB
Newer Older
Alexandre Julliard's avatar
Alexandre Julliard committed
1 2 3 4 5
/*
 *	PostScript brush handling
 *
 * Copyright 1998  Huw D M Davies
 *
6 7 8 9 10 11 12 13 14 15 16 17
 * 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
18
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
Alexandre Julliard's avatar
Alexandre Julliard committed
19 20 21
 */

#include "psdrv.h"
22
#include "wine/debug.h"
23
#include "winbase.h"
Alexandre Julliard's avatar
Alexandre Julliard committed
24

25
WINE_DEFAULT_DEBUG_CHANNEL(psdrv);
26

Alexandre Julliard's avatar
Alexandre Julliard committed
27
/***********************************************************************
28
 *           SelectBrush   (WINEPS.@)
Alexandre Julliard's avatar
Alexandre Julliard committed
29
 */
30
HBRUSH PSDRV_SelectBrush( PHYSDEV dev, HBRUSH hbrush, const struct brush_pattern *pattern )
Alexandre Julliard's avatar
Alexandre Julliard committed
31
{
32
    PSDRV_PDEVICE *physDev = get_psdrv_dev( dev );
33
    LOGBRUSH logbrush;
Alexandre Julliard's avatar
Alexandre Julliard committed
34

35 36
    if (!GetObjectA( hbrush, sizeof(logbrush), &logbrush )) return 0;

37
    TRACE("hbrush = %p\n", hbrush);
Alexandre Julliard's avatar
Alexandre Julliard committed
38

39
    if (hbrush == GetStockObject( DC_BRUSH ))
40
        logbrush.lbColor = GetDCBrushColor( dev->hdc );
41

42
    switch(logbrush.lbStyle) {
Alexandre Julliard's avatar
Alexandre Julliard committed
43 44

    case BS_SOLID:
45
        PSDRV_CreateColor(dev, &physDev->brush.color, logbrush.lbColor);
Alexandre Julliard's avatar
Alexandre Julliard committed
46 47 48 49 50 51
	break;

    case BS_NULL:
        break;

    case BS_HATCHED:
52
        PSDRV_CreateColor(dev, &physDev->brush.color, logbrush.lbColor);
53 54
        break;

Alexandre Julliard's avatar
Alexandre Julliard committed
55
    case BS_PATTERN:
56
    case BS_DIBPATTERN:
57
        physDev->brush.pattern = *pattern;
Alexandre Julliard's avatar
Alexandre Julliard committed
58 59 60
	break;

    default:
61
        FIXME("Unrecognized brush style %d\n", logbrush.lbStyle);
Alexandre Julliard's avatar
Alexandre Julliard committed
62 63 64 65
	break;
    }

    physDev->brush.set = FALSE;
66
    return hbrush;
Alexandre Julliard's avatar
Alexandre Julliard committed
67 68 69
}


70 71 72
/***********************************************************************
 *           SetDCBrushColor (WINEPS.@)
 */
73
COLORREF PSDRV_SetDCBrushColor( PHYSDEV dev, COLORREF color )
74
{
75 76
    PSDRV_PDEVICE *physDev = get_psdrv_dev( dev );

77
    if (GetCurrentObject( dev->hdc, OBJ_BRUSH ) == GetStockObject( DC_BRUSH ))
78
    {
79
        PSDRV_CreateColor( dev, &physDev->brush.color, color );
80 81 82 83 84 85
        physDev->brush.set = FALSE;
    }
    return color;
}


Alexandre Julliard's avatar
Alexandre Julliard committed
86 87 88 89 90
/**********************************************************************
 *
 *	PSDRV_SetBrush
 *
 */
91
static BOOL PSDRV_SetBrush( PHYSDEV dev )
Alexandre Julliard's avatar
Alexandre Julliard committed
92
{
93
    PSDRV_PDEVICE *physDev = get_psdrv_dev( dev );
94
    LOGBRUSH logbrush;
95
    BOOL ret = TRUE;
Alexandre Julliard's avatar
Alexandre Julliard committed
96

97
    if (!GetObjectA( GetCurrentObject(dev->hdc,OBJ_BRUSH), sizeof(logbrush), &logbrush ))
98
    {
99
        ERR("Can't get BRUSHOBJ\n");
100 101
	return FALSE;
    }
102 103

    switch (logbrush.lbStyle) {
Alexandre Julliard's avatar
Alexandre Julliard committed
104
    case BS_SOLID:
105
    case BS_HATCHED:
106
        PSDRV_WriteSetColor(dev, &physDev->brush.color);
Alexandre Julliard's avatar
Alexandre Julliard committed
107 108
	break;

109 110 111
    case BS_NULL:
        break;

Alexandre Julliard's avatar
Alexandre Julliard committed
112
    default:
113
        ret = FALSE;
Alexandre Julliard's avatar
Alexandre Julliard committed
114 115 116 117
        break;

    }
    physDev->brush.set = TRUE;
118
    return ret;
Alexandre Julliard's avatar
Alexandre Julliard committed
119
}
120 121 122 123 124 125 126


/**********************************************************************
 *
 *	PSDRV_Fill
 *
 */
127
static BOOL PSDRV_Fill(PHYSDEV dev, BOOL EO)
128 129
{
    if(!EO)
130
        return PSDRV_WriteFill(dev);
131
    else
132
        return PSDRV_WriteEOFill(dev);
133 134 135 136 137 138 139 140
}


/**********************************************************************
 *
 *	PSDRV_Clip
 *
 */
141
static BOOL PSDRV_Clip(PHYSDEV dev, BOOL EO)
142 143
{
    if(!EO)
144
        return PSDRV_WriteClip(dev);
145
    else
146
        return PSDRV_WriteEOClip(dev);
147 148 149 150 151 152 153
}

/**********************************************************************
 *
 *	PSDRV_Brush
 *
 */
154
BOOL PSDRV_Brush(PHYSDEV dev, BOOL EO)
155
{
156
    PSDRV_PDEVICE *physDev = get_psdrv_dev( dev );
157
    LOGBRUSH logbrush;
158
    BOOL ret = TRUE;
159

160 161 162
    if(physDev->pathdepth)
        return FALSE;

163
    if (!GetObjectA( GetCurrentObject(dev->hdc,OBJ_BRUSH), sizeof(logbrush), &logbrush ))
164
    {
165
        ERR("Can't get BRUSHOBJ\n");
166 167 168
	return FALSE;
    }

169
    switch (logbrush.lbStyle) {
170
    case BS_SOLID:
171 172 173 174
	PSDRV_WriteGSave(dev);
        PSDRV_SetBrush(dev);
        PSDRV_Fill(dev, EO);
	PSDRV_WriteGRestore(dev);
175 176 177
	break;

    case BS_HATCHED:
178 179
        PSDRV_WriteGSave(dev);
        PSDRV_SetBrush(dev);
180

181
	switch(logbrush.lbHatch) {
182 183
	case HS_VERTICAL:
	case HS_CROSS:
184 185 186 187 188
            PSDRV_WriteGSave(dev);
	    PSDRV_Clip(dev, EO);
	    PSDRV_WriteHatch(dev);
	    PSDRV_WriteStroke(dev);
	    PSDRV_WriteGRestore(dev);
189
	    if(logbrush.lbHatch == HS_VERTICAL)
190 191 192 193
	        break;
	    /* else fallthrough for HS_CROSS */

	case HS_HORIZONTAL:
194 195 196 197 198 199
            PSDRV_WriteGSave(dev);
	    PSDRV_Clip(dev, EO);
	    PSDRV_WriteRotate(dev, 90.0);
	    PSDRV_WriteHatch(dev);
	    PSDRV_WriteStroke(dev);
	    PSDRV_WriteGRestore(dev);
200 201 202 203
	    break;

	case HS_FDIAGONAL:
	case HS_DIAGCROSS:
204 205 206 207 208 209
	    PSDRV_WriteGSave(dev);
	    PSDRV_Clip(dev, EO);
	    PSDRV_WriteRotate(dev, -45.0);
	    PSDRV_WriteHatch(dev);
	    PSDRV_WriteStroke(dev);
	    PSDRV_WriteGRestore(dev);
210
	    if(logbrush.lbHatch == HS_FDIAGONAL)
211 212
	        break;
	    /* else fallthrough for HS_DIAGCROSS */
213

214
	case HS_BDIAGONAL:
215 216 217 218 219 220
	    PSDRV_WriteGSave(dev);
	    PSDRV_Clip(dev, EO);
	    PSDRV_WriteRotate(dev, 45.0);
	    PSDRV_WriteHatch(dev);
	    PSDRV_WriteStroke(dev);
	    PSDRV_WriteGRestore(dev);
221 222 223
	    break;

	default:
224
	    ERR("Unknown hatch style\n");
225 226
	    ret = FALSE;
            break;
227
	}
228
        PSDRV_WriteGRestore(dev);
229 230 231 232 233
	break;

    case BS_NULL:
	break;

234
    case BS_PATTERN:
235
    case BS_DIBPATTERN:
236 237
        if(physDev->pi->ppd->LanguageLevel > 1) {
            PSDRV_WriteGSave(dev);
238 239
            ret = PSDRV_WriteDIBPatternDict(dev, physDev->brush.pattern.info,
                                            physDev->brush.pattern.bits.ptr, physDev->brush.pattern.usage );
240 241 242 243 244
            PSDRV_Fill(dev, EO);
            PSDRV_WriteGRestore(dev);
        } else {
            FIXME("Trying to set a pattern brush on a level 1 printer\n");
            ret = FALSE;
245 246 247
	}
	break;

248
    default:
249
        ret = FALSE;
250 251
	break;
    }
252
    return ret;
253
}