BOOL CenterWallpaper(HDC hdc, LPCRECT lprcMonitor) { RECT rc; HBITMAP hbmT; BOOL f = TRUE; HRGN hrgn; POINT pt; if (GetWallpaperCenterRect(&rc, &pt, lprcMonitor)) { /* * This used to call TileWallpaper, but this really * slowed up the system for small dimension bitmaps. * We really only need to blt it once for centered * bitmaps. */ if (hbmT = GreSelectBitmap(ghdcMem, ghbmWallpaper)) { GreBitBlt(hdc, rc.left, rc.top, rc.right - rc.left, rc.bottom - rc.top, ghdcMem, pt.x, pt.y, SRCCOPY, 0); GreSelectBitmap(ghdcMem, hbmT); } else { f = FALSE; } } /* * Fill the bacground (excluding the bitmap) with the desktop * brush. Save the DC with the cliprect. */ if (hrgn = CreateEmptyRgn()) { if (GreGetRandomRgn(hdc, hrgn, 1) != -1) { GreExcludeClipRect(hdc, rc.left, rc.top, rc.right, rc.bottom); FillRect(hdc, lprcMonitor, SYSHBR(DESKTOP)); GreExtSelectClipRgn(hdc, hrgn, RGN_COPY); } else { f = FALSE; } GreDeleteObject(hrgn); } else { f = FALSE; } return f; }
BOOL TooltipAnimate(PTOOLTIPWND pttwnd) { int y, yMem, yReal, ny, iy, cx, cy; DWORD dwElapsed; HDC hdc; BOOL fRet = FALSE; if (pttwnd->pstr == NULL) return TRUE; hdc = GetTooltipDC(pttwnd); cx = pttwnd->rcWindow.right - pttwnd->rcWindow.left; cy = pttwnd->rcWindow.bottom - pttwnd->rcWindow.top; dwElapsed = NtGetTickCount() - pttwnd->dwAnimStart; iy = MultDiv(cy, dwElapsed, CMS_TOOLTIP); if (dwElapsed > CMS_TOOLTIP || iy == cy) { GreBitBlt(hdc, 0, 0, cx, cy, pttwnd->hdcMem, 0, 0, SRCCOPY | NOMIRRORBITMAP, 0); fRet = TRUE; goto Cleanup; } else if (pttwnd->iyAnim == iy) { goto Cleanup; } if (pttwnd->dwFlags & TTF_POSITIVE) { y = 0; ny = 0; } else { y = cy; ny = -1; } yReal = y + ny * iy; yMem = (pttwnd->dwFlags & TTF_POSITIVE) ? cy - iy : 0; pttwnd->iyAnim = iy; GreBitBlt(hdc, 0, yReal, cx, iy, pttwnd->hdcMem, 0, yMem, SRCCOPY | NOMIRRORBITMAP, 0); Cleanup: _ReleaseDC(hdc); return fRet; }
BOOL _InternalGetIconInfo( IN PCURSOR pcur, OUT PICONINFO piconinfo, OUT OPTIONAL PUNICODE_STRING pstrInstanceName, OUT OPTIONAL PUNICODE_STRING pstrResName, OUT OPTIONAL LPDWORD pbpp, IN BOOL fInternalCursor) { HBITMAP hbmBitsT; HBITMAP hbmDstT; HBITMAP hbmMask; HBITMAP hbmColor; /* * If this is an animated cursor, just grab the first frame and return * the info for it. */ if (pcur->CURSORF_flags & CURSORF_ACON) pcur = ((PACON)pcur)->aspcur[0]; /* * Make copies of the bitmaps * * If the color bitmap is around, then there is no XOR mask in the * hbmMask bitmap. */ hbmMask = GreCreateBitmap( pcur->cx, (pcur->hbmColor && !fInternalCursor) ? pcur->cy / 2 : pcur->cy, 1, 1, NULL); if (hbmMask == NULL) return FALSE; hbmColor = NULL; if (pcur->hbmColor != NULL) { hbmColor = GreCreateCompatibleBitmap(gpDispInfo->hdcBits, pcur->cx, pcur->cy / 2); if (hbmColor == NULL) { GreDeleteObject(hbmMask); return FALSE; } } hbmBitsT = GreSelectBitmap(ghdcMem2, pcur->hbmMask); hbmDstT = GreSelectBitmap(ghdcMem, hbmMask); GreBitBlt(ghdcMem, 0, 0, pcur->cx, (pcur->hbmColor && !fInternalCursor) ? pcur->cy / 2 : pcur->cy, ghdcMem2, 0, 0, SRCCOPY, 0x00ffffff); if (hbmColor != NULL) { GreSelectBitmap(ghdcMem2, pcur->hbmColor); GreSelectBitmap(ghdcMem, hbmColor); GreBitBlt(ghdcMem, 0, 0, pcur->cx, pcur->cy / 2, ghdcMem2, 0, 0, SRCCOPY, 0); } GreSelectBitmap(ghdcMem2, hbmBitsT); GreSelectBitmap(ghdcMem, hbmDstT); /* * Fill in the iconinfo structure. make copies of the bitmaps. */ try { piconinfo->fIcon = (pcur->rt == LOWORD(RT_ICON)); piconinfo->xHotspot = pcur->xHotspot; piconinfo->yHotspot = pcur->yHotspot; piconinfo->hbmMask = hbmMask; piconinfo->hbmColor = hbmColor; if (pstrInstanceName != NULL) { if (pcur->atomModName) { pstrInstanceName->Length = UserGetAtomName(pcur->atomModName, pstrInstanceName->Buffer, pstrInstanceName->MaximumLength / sizeof(WCHAR)) * sizeof(WCHAR); } else { pstrInstanceName->Length = 0; } } if (pstrResName != NULL) { if (HIWORD(pcur->strName.Buffer)) { RtlCopyUnicodeString(pstrResName, &pcur->strName); } else { *pstrResName = pcur->strName; } } if (pbpp) *pbpp = pcur->bpp; } except (EXCEPTION_EXECUTE_HANDLER) { GreDeleteObject(hbmMask); GreDeleteObject(hbmColor); return FALSE; } return TRUE; }
/***************************************************************************\ * DrawIconEx * * Draws icon in desired size. * \***************************************************************************/ BOOL _DrawIconEx( HDC hdc, int x, int y, PCURSOR pcur, int cx, int cy, UINT istepIfAniCur, HBRUSH hbr, UINT diFlags) { BOOL fSuccess = FALSE; /* * If this is an animated cursor, just grab the ith frame and use it * for drawing. */ if (pcur->CURSORF_flags & CURSORF_ACON) { if ((int)istepIfAniCur >= ((PACON)pcur)->cicur) { RIPERR0(ERROR_INVALID_PARAMETER, RIP_WARNING, "DrawIconEx, icon step out of range."); goto Done; } pcur = ((PACON)pcur)->aspcur[((PACON)pcur)->aicur[istepIfAniCur]]; } /* * Setup defaults. */ cx = GetCWidth(cx, diFlags, pcur->cx); cy = GetCHeight(cy, diFlags, (pcur->cy / 2)); if (hbr) { HBITMAP hbmpT = NULL; HDC hdcT; HBITMAP hbmpOld; POLYPATBLT PolyData; if (hdcT = GreCreateCompatibleDC(hdc)) { if (hbmpT = GreCreateCompatibleBitmap(hdc, cx, cy)) { POINT pt; BOOL bRet; hbmpOld = GreSelectBitmap(hdcT, hbmpT); /* * Set new dc's brush origin in same relative * location as passed-in dc's. */ bRet = GreGetBrushOrg(hdc, &pt); /* * Bug 292396 - joejo * Stop overactive asserts by replacing with RIPMSG. */ if (bRet != TRUE) { RIPMSG0(RIP_WARNING, "DrawIconEx, GreGetBrushOrg failed."); } bRet = GreSetBrushOrg(hdcT, pt.x, pt.y, NULL); if (bRet != TRUE) { RIPMSG0(RIP_WARNING, "DrawIconEx, GreSetBrushOrg failed."); } PolyData.x = 0; PolyData.y = 0; PolyData.cx = cx; PolyData.cy = cy; PolyData.BrClr.hbr = hbr; bRet = GrePolyPatBlt(hdcT, PATCOPY, &PolyData, 1, PPB_BRUSH); if (bRet != TRUE) { RIPMSG0(RIP_WARNING, "DrawIconEx, GrePolyPatBlt failed."); } /* * Output the image to the temporary memoryDC. */ BltIcon(hdcT, 0, 0, cx, cy, ghdcMem, pcur, TRUE, SRCAND); BltIcon(hdcT, 0, 0, cx, cy, ghdcMem, pcur, FALSE, SRCINVERT); /* * Blt the bitmap to the original DC. */ GreBitBlt(hdc, x, y, cx, cy, hdcT, 0, 0, SRCCOPY, (COLORREF)-1); GreSelectBitmap(hdcT, hbmpOld); bRet = GreDeleteObject(hbmpT); if (bRet != TRUE) { RIPMSG0(RIP_WARNING, "DrawIconEx, GreDeleteObject failed. Possible Leak"); } fSuccess = TRUE; } GreDeleteDC(hdcT); } } else { if (diFlags & DI_MASK) { BltIcon(hdc, x, y, cx, cy, ghdcMem, pcur, TRUE, ((diFlags & DI_IMAGE) ? SRCAND : SRCCOPY)); } if (diFlags & DI_IMAGE) { BltIcon(hdc, x, y, cx, cy, ghdcMem, pcur, FALSE, ((diFlags & DI_MASK) ? SRCINVERT : SRCCOPY)); } fSuccess = TRUE; } Done: return fSuccess; }
BOOL TileWallpaper(HDC hdc, LPCRECT lprc, BOOL fOffset) { int xO; int yO; int x; int y; BITMAP bm; HBITMAP hbmT = NULL; POINT ptOffset; if (fOffset) { ptOffset.x = gsrcWallpaper.x; ptOffset.y = gsrcWallpaper.y; } else { ptOffset.x = 0; ptOffset.y = 0; } /* * We need to get the dimensions of the bitmap here rather than rely on * the dimensions in srcWallpaper because this function may * be called as part of ExpandBitmap, before srcWallpaper is * set. */ if (GreExtGetObjectW(ghbmWallpaper, sizeof(BITMAP), (PBITMAP)&bm)) { xO = lprc->left - (lprc->left % bm.bmWidth) + (ptOffset.x % bm.bmWidth); if (xO > lprc->left) { xO -= bm.bmWidth; } yO = lprc->top - (lprc->top % bm.bmHeight) + (ptOffset.y % bm.bmHeight); if (yO > lprc->top) { yO -= bm.bmHeight; } /* * Tile the bitmap to the surface. */ if (hbmT = GreSelectBitmap(ghdcMem, ghbmWallpaper)) { for (y = yO; y < lprc->bottom; y += bm.bmHeight) { for (x = xO; x < lprc->right; x += bm.bmWidth) { GreBitBlt(hdc, x, y, bm.bmWidth, bm.bmHeight, ghdcMem, 0, 0, SRCCOPY, 0); } } GreSelectBitmap(ghdcMem, hbmT); } } return (hbmT != NULL); }
BOOL xxxSnapWindow( PWND pwnd) { PTHREADINFO ptiCurrent; RECT rc; HDC hdcScr = NULL; HDC hdcMem = NULL; BOOL fRet; HBITMAP hbmOld; HBITMAP hbm; HANDLE hPal; LPLOGPALETTE lppal; int palsize; int iFixedPaletteEntries; BOOL fSuccess; PWND pwndT; TL tlpwndT; PWINDOWSTATION pwinsta; TL tlpwinsta; CheckLock(pwnd); UserAssert(pwnd); ptiCurrent = PtiCurrent(); /* * If this is a thread of winlogon, don't do the snapshot. */ if (GetCurrentProcessId() == gpidLogon) return FALSE; /* * Get the affected windowstation */ if (!NT_SUCCESS(ReferenceWindowStation( PsGetCurrentThread(), NULL, WINSTA_READSCREEN, &pwinsta, TRUE)) || pwinsta->dwWSF_Flags & WSF_NOIO) { return FALSE; } /* * If the window is on another windowstation, do nothing */ if (pwnd->head.rpdesk->rpwinstaParent != pwinsta) return FALSE; /* * Get the parent of any child windows. */ while ((pwnd != NULL) && TestWF(pwnd, WFCHILD)) { pwnd = pwnd->spwndParent; } /* * Lock the windowstation before we leave the critical section */ ThreadLockWinSta(ptiCurrent, pwinsta, &tlpwinsta); /* * Open the clipboard and empty it. * * pwndDesktop is made the owner of the clipboard, instead of the * currently active window; -- SANKAR -- 20th July, 1989 -- */ pwndT = ptiCurrent->rpdesk->pDeskInfo->spwnd; ThreadLockWithPti(ptiCurrent, pwndT, &tlpwndT); fSuccess = xxxOpenClipboard(pwndT, NULL); ThreadUnlock(&tlpwndT); if (!fSuccess) { ThreadUnlockWinSta(ptiCurrent, &tlpwinsta); return FALSE; } xxxEmptyClipboard(pwinsta); /* * Use the whole window. */ CopyRect(&rc, &pwnd->rcWindow); /* * Only snap what is on the screen. */ if (!IntersectRect(&rc, &rc, &gpDispInfo->rcScreen)) { fRet = FALSE; goto SnapExit; } rc.right -= rc.left; rc.bottom -= rc.top; /* * Figure out how far offset from window origin visible part is */ if (pwnd != PWNDDESKTOP(pwnd)) { rc.left -= pwnd->rcWindow.left; rc.top -= pwnd->rcWindow.top; } /* * Get the entire window's DC. */ hdcScr = _GetWindowDC(pwnd); if (!hdcScr) goto MemoryError; /* * Create the memory DC. */ hdcMem = GreCreateCompatibleDC(hdcScr); if (!hdcMem) goto MemoryError; /* * Create the destination bitmap. If it fails, then attempt * to create a monochrome bitmap. * Did we have enough memory? */ if (SYSMET(SAMEDISPLAYFORMAT)) { hbm = GreCreateCompatibleBitmap(hdcScr, rc.right, rc.bottom); } else { hbm = GreCreateBitmap(rc.right, rc.bottom, 1, gpDispInfo->BitCountMax, NULL); } if (!hbm) { hbm = GreCreateBitmap(rc.right, rc.bottom, 1, 1, NULL); if (!hbm) goto MemoryError; } /* * Select the bitmap into the memory DC. */ hbmOld = GreSelectBitmap(hdcMem, hbm); /* * Snap!!! * Check the return value because the process taking the snapshot * may not have access to read the screen. */ fRet = GreBitBlt(hdcMem, 0, 0, rc.right, rc.bottom, hdcScr, rc.left, rc.top, SRCCOPY | CAPTUREBLT, 0); /* * Restore the old bitmap into the memory DC. */ GreSelectBitmap(hdcMem, hbmOld); /* * If the blt failed, leave now. */ if (!fRet) goto SnapExit; _SetClipboardData(CF_BITMAP, hbm, FALSE, TRUE); /* * If this is a palette device, let's throw the current system palette * into the clipboard also. Useful if the user just snapped a window * containing palette colors... */ if (TEST_PUSIF(PUSIF_PALETTEDISPLAY)) { int i; int iPalSize; palsize = GreGetDeviceCaps(hdcScr, SIZEPALETTE); /* * Determine the number of system colors. */ if (GreGetSystemPaletteUse(hdcScr) == SYSPAL_STATIC) iFixedPaletteEntries = GreGetDeviceCaps(hdcScr, NUMRESERVED); else iFixedPaletteEntries = 2; lppal = (LPLOGPALETTE)UserAllocPoolWithQuota( (LONG)(sizeof(LOGPALETTE) + sizeof(PALETTEENTRY) * palsize), TAG_CLIPBOARD); if (lppal != NULL) { lppal->palVersion = 0x300; lppal->palNumEntries = (WORD)palsize; if (GreGetSystemPaletteEntries(hdcScr, 0, palsize, lppal->palPalEntry)) { iPalSize = palsize - iFixedPaletteEntries / 2; for (i = iFixedPaletteEntries / 2; i < iPalSize; i++) { /* * Any non system palette enteries need to have the NOCOLLAPSE * flag set otherwise bitmaps containing different palette * indices but same colors get messed up. */ lppal->palPalEntry[i].peFlags = PC_NOCOLLAPSE; } if (hPal = GreCreatePalette(lppal)) _SetClipboardData(CF_PALETTE, hPal, FALSE, TRUE); } UserFreePool(lppal); } } PlayEventSound(USER_SOUND_SNAPSHOT); fRet = TRUE; SnapExit: /* * Release the window/client DC. */ if (hdcScr) { _ReleaseDC(hdcScr); } xxxCloseClipboard(pwinsta); Unlock(&pwinsta->spwndClipOwner); /* * Delete the memory DC. */ if (hdcMem) { GreDeleteDC(hdcMem); } ThreadUnlockWinSta(ptiCurrent, &tlpwinsta); return fRet; MemoryError: /* * Display an error message box. */ ClientNoMemoryPopup(); fRet = FALSE; goto SnapExit; }