예제 #1
0
파일: stockobj.c 프로젝트: GYGit/reactos
static
HPEN
FASTCALL
IntCreateStockPen(DWORD dwPenStyle,
                  DWORD dwWidth,
                  ULONG ulBrushStyle,
                  ULONG ulColor)
{
    HPEN hPen;
    PBRUSH pbrushPen;

    pbrushPen = PEN_AllocPenWithHandle();
    if (pbrushPen == NULL) return NULL;

    if ((dwPenStyle & PS_STYLE_MASK) == PS_NULL) dwWidth = 1;

    pbrushPen->iHatch = 0;
    pbrushPen->lWidth = abs(dwWidth);
    pbrushPen->eWidth = (FLOAT)pbrushPen->lWidth;
    pbrushPen->ulPenStyle = dwPenStyle;
    pbrushPen->BrushAttr.lbColor = ulColor;
    pbrushPen->iBrushStyle = ulBrushStyle;
    pbrushPen->hbmClient = (HANDLE)NULL;
    pbrushPen->dwStyleCount = 0;
    pbrushPen->pStyle = 0;
    pbrushPen->flAttrs = BR_IS_OLDSTYLEPEN;

    switch (dwPenStyle & PS_STYLE_MASK)
    {
        case PS_NULL:
            pbrushPen->flAttrs |= BR_IS_NULL;
            break;

        case PS_SOLID:
            pbrushPen->flAttrs |= BR_IS_SOLID;
            break;
    }
    hPen = pbrushPen->BaseObject.hHmgr;
    PEN_UnlockPen(pbrushPen);
    return hPen;
}
예제 #2
0
HPEN
APIENTRY
IntGdiExtCreatePen(
    DWORD dwPenStyle,
    DWORD dwWidth,
    IN ULONG ulBrushStyle,
    IN ULONG ulColor,
    IN ULONG_PTR ulClientHatch,
    IN ULONG_PTR ulHatch,
    DWORD dwStyleCount,
    PULONG pStyle,
    IN ULONG cjDIB,
    IN BOOL bOldStylePen,
    IN OPTIONAL HBRUSH hbrush)
{
    HPEN hPen;
    PBRUSH pbrushPen;
    static const BYTE PatternAlternate[] = {0x55, 0x55, 0x55, 0};
    static const BYTE PatternDash[] = {0xFF, 0xFF, 0xC0, 0};
    static const BYTE PatternDot[] = {0xE3, 0x8E, 0x38, 0};
    static const BYTE PatternDashDot[] = {0xFF, 0x81, 0xC0, 0};
    static const BYTE PatternDashDotDot[] = {0xFF, 0x8E, 0x38, 0};

    dwWidth = abs(dwWidth);

    if ( (dwPenStyle & PS_STYLE_MASK) == PS_NULL)
    {
        return StockObjects[NULL_PEN];
    }

    if (bOldStylePen)
    {
        pbrushPen = PEN_AllocPenWithHandle();
    }
    else
    {
        pbrushPen = PEN_AllocExtPenWithHandle();
    }

    if (!pbrushPen)
    {
        EngSetLastError(ERROR_NOT_ENOUGH_MEMORY);
        DPRINT("Can't allocate pen\n");
        return 0;
    }
    hPen = pbrushPen->BaseObject.hHmgr;

    // If nWidth is zero, the pen is a single pixel wide, regardless of the current transformation.
    if ((bOldStylePen) && (!dwWidth) && ((dwPenStyle & PS_STYLE_MASK) != PS_SOLID))
        dwWidth = 1;

    pbrushPen->lWidth = dwWidth;
    pbrushPen->eWidth = (FLOAT)pbrushPen->lWidth;
    pbrushPen->ulPenStyle = dwPenStyle;
    pbrushPen->BrushAttr.lbColor = ulColor;
    pbrushPen->iBrushStyle = ulBrushStyle;
    // FIXME: Copy the bitmap first ?
    pbrushPen->hbmClient = (HANDLE)ulClientHatch;
    pbrushPen->dwStyleCount = dwStyleCount;
    pbrushPen->pStyle = pStyle;

    pbrushPen->flAttrs = bOldStylePen ? BR_IS_OLDSTYLEPEN : BR_IS_PEN;

    // If dwPenStyle is PS_COSMETIC, the width must be set to 1.
    if ( !(bOldStylePen) && ((dwPenStyle & PS_TYPE_MASK) == PS_COSMETIC) && ( dwWidth != 1) )
        goto ExitCleanup;

    switch (dwPenStyle & PS_STYLE_MASK)
    {
    case PS_NULL:
        pbrushPen->flAttrs |= BR_IS_NULL;
        break;

    case PS_SOLID:
        pbrushPen->flAttrs |= BR_IS_SOLID;
        break;

    case PS_ALTERNATE:
        pbrushPen->flAttrs |= BR_IS_BITMAP;
        pbrushPen->hbmPattern = GreCreateBitmap(24, 1, 1, 1, (LPBYTE)PatternAlternate);
        break;

    case PS_DOT:
        pbrushPen->flAttrs |= BR_IS_BITMAP;
        pbrushPen->hbmPattern = GreCreateBitmap(24, 1, 1, 1, (LPBYTE)PatternDot);
        break;

    case PS_DASH:
        pbrushPen->flAttrs |= BR_IS_BITMAP;
        pbrushPen->hbmPattern = GreCreateBitmap(24, 1, 1, 1, (LPBYTE)PatternDash);
        break;

    case PS_DASHDOT:
        pbrushPen->flAttrs |= BR_IS_BITMAP;
        pbrushPen->hbmPattern = GreCreateBitmap(24, 1, 1, 1, (LPBYTE)PatternDashDot);
        break;

    case PS_DASHDOTDOT:
        pbrushPen->flAttrs |= BR_IS_BITMAP;
        pbrushPen->hbmPattern = GreCreateBitmap(24, 1, 1, 1, (LPBYTE)PatternDashDotDot);
        break;

    case PS_INSIDEFRAME:
        pbrushPen->flAttrs |= (BR_IS_SOLID | BR_IS_INSIDEFRAME);
        break;

    case PS_USERSTYLE:
        if ((dwPenStyle & PS_TYPE_MASK) == PS_COSMETIC)
        {
            /* FIXME: PS_USERSTYLE workaround */
            DPRINT1("PS_COSMETIC | PS_USERSTYLE not handled\n");
            pbrushPen->flAttrs |= BR_IS_SOLID;
            break;
        }
        else
        {
            UINT i;
            BOOL has_neg = FALSE, all_zero = TRUE;

            for(i = 0; (i < dwStyleCount) && !has_neg; i++)
            {
                has_neg = has_neg || (((INT)(pStyle[i])) < 0);
                all_zero = all_zero && (pStyle[i] == 0);
            }

            if(all_zero || has_neg)
            {
                goto ExitCleanup;
            }
        }
        /* FIXME: What style here? */
        pbrushPen->flAttrs |= 0;
        break;

    default:
        DPRINT1("IntGdiExtCreatePen unknown penstyle %x\n", dwPenStyle);
    }

    PEN_UnlockPen(pbrushPen);
    return hPen;

ExitCleanup:
    EngSetLastError(ERROR_INVALID_PARAMETER);
    pbrushPen->pStyle = NULL;
    GDIOBJ_vDeleteObject(&pbrushPen->BaseObject);

    return NULL;
}