Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

464 lines
12 KiB

  1. //
  2. // cuishadw.cpp
  3. //
  4. #include "private.h"
  5. #include "cuishadw.h"
  6. #include "cuisys.h"
  7. #include "cuiutil.h"
  8. /*=============================================================================*/
  9. /* */
  10. /* C U I F S H A D O W */
  11. /* */
  12. /*=============================================================================*/
  13. /* C U I F S H A D O W */
  14. /*------------------------------------------------------------------------------
  15. Constructor of CUIFShadow
  16. ------------------------------------------------------------------------------*/
  17. CUIFShadow::CUIFShadow( HINSTANCE hInst, DWORD dwStyle, CUIFWindow *pWndOwner ) : CUIFWindow( hInst, dwStyle | UIWINDOW_TOOLWINDOW )
  18. {
  19. m_pWndOwner = pWndOwner;
  20. m_color = RGB( 0, 0, 0 );
  21. m_iGradWidth = 0;
  22. m_iAlpha = 0;
  23. m_sizeShift.cx = 0;
  24. m_sizeShift.cy = 0;
  25. m_fGradient = FALSE;
  26. }
  27. /* ~ C U I F S H A D O W */
  28. /*------------------------------------------------------------------------------
  29. Destructor of CUIFShadow
  30. ------------------------------------------------------------------------------*/
  31. CUIFShadow::~CUIFShadow( void )
  32. {
  33. if (m_pWndOwner) {
  34. m_pWndOwner->ClearShadowWnd();
  35. }
  36. }
  37. /* I N I T I A L I Z E */
  38. /*------------------------------------------------------------------------------
  39. Initialize UI window object
  40. (UIFObject method)
  41. ------------------------------------------------------------------------------*/
  42. CUIFObject *CUIFShadow::Initialize( void )
  43. {
  44. InitSettings();
  45. return CUIFWindow::Initialize();
  46. }
  47. /* G E T W N D S T Y L E E X */
  48. /*------------------------------------------------------------------------------
  49. ------------------------------------------------------------------------------*/
  50. DWORD CUIFShadow::GetWndStyleEx( void )
  51. {
  52. DWORD dwWndStyleEx = CUIFWindow::GetWndStyleEx();
  53. if (m_fGradient) {
  54. dwWndStyleEx |= WS_EX_LAYERED;
  55. }
  56. return dwWndStyleEx;
  57. }
  58. /* O N C R E A T E */
  59. /*------------------------------------------------------------------------------
  60. ------------------------------------------------------------------------------*/
  61. void CUIFShadow::OnCreate( HWND hWnd )
  62. {
  63. CUIFWindow::OnCreate( hWnd );
  64. }
  65. /* P A I N T O B J E C T */
  66. /*------------------------------------------------------------------------------
  67. Paint window object
  68. (UIFObject method)
  69. ------------------------------------------------------------------------------*/
  70. void CUIFShadow::OnPaint( HDC hDC )
  71. {
  72. HBRUSH hBrush;
  73. RECT rc = GetRectRef();
  74. //
  75. hBrush = CreateSolidBrush( m_color );
  76. FillRect( hDC, &rc, hBrush );
  77. DeleteObject( hBrush );
  78. }
  79. /* O N S E T T I N G C H A N G E */
  80. /*------------------------------------------------------------------------------
  81. ------------------------------------------------------------------------------*/
  82. LRESULT CUIFShadow::OnSettingChange( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam )
  83. {
  84. InitSettings();
  85. if (m_fGradient) {
  86. DWORD dwWndStyleEx = GetWindowLong( GetWnd(), GWL_EXSTYLE );
  87. SetWindowLong( GetWnd(), GWL_EXSTYLE, (dwWndStyleEx | WS_EX_LAYERED) );
  88. }
  89. else {
  90. DWORD dwWndStyleEx = GetWindowLong( GetWnd(), GWL_EXSTYLE );
  91. SetWindowLong( GetWnd(), GWL_EXSTYLE, (dwWndStyleEx & ~WS_EX_LAYERED) );
  92. }
  93. AdjustWindowPos();
  94. InitShadow();
  95. return CUIFWindow::OnSettingChange( hWnd, uMsg, wParam, lParam );
  96. }
  97. /* S H O W */
  98. /*------------------------------------------------------------------------------
  99. ------------------------------------------------------------------------------*/
  100. void CUIFShadow::Show( BOOL fShow )
  101. {
  102. if (fShow) {
  103. if (IsWindow( m_hWnd ) && !IsWindowVisible( m_hWnd )) {
  104. AdjustWindowPos();
  105. InitShadow();
  106. }
  107. }
  108. if (IsWindow( m_hWnd )) {
  109. m_fVisible = fShow;
  110. ShowWindow( m_hWnd, fShow ? SW_SHOWNOACTIVATE : SW_HIDE );
  111. }
  112. }
  113. /* O N O W N E R W N D M O V E D */
  114. /*------------------------------------------------------------------------------
  115. ------------------------------------------------------------------------------*/
  116. void CUIFShadow::OnOwnerWndMoved( BOOL fResized )
  117. {
  118. if (IsWindow( m_hWnd ) && IsWindowVisible( m_hWnd )) {
  119. AdjustWindowPos();
  120. if (fResized) {
  121. InitShadow();
  122. }
  123. }
  124. }
  125. /* G E T S H I F T */
  126. /*-----------------------------------------------------------------------------
  127. -----------------------------------------------------------------------------*/
  128. void CUIFShadow::GetShift( SIZE *psize )
  129. {
  130. *psize = m_sizeShift;
  131. }
  132. /* O N W I N D O W P O S C H A N G I N G
  133. /*------------------------------------------------------------------------------
  134. ------------------------------------------------------------------------------*/
  135. LRESULT CUIFShadow::OnWindowPosChanging(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
  136. {
  137. WINDOWPOS *pwp = (WINDOWPOS *)lParam;
  138. pwp->hwndInsertAfter = m_pWndOwner->GetWnd();
  139. return DefWindowProc(hWnd, uMsg, wParam, lParam);
  140. }
  141. /* I N I T S E T T I N G S */
  142. /*------------------------------------------------------------------------------
  143. ------------------------------------------------------------------------------*/
  144. void CUIFShadow::InitSettings( void )
  145. {
  146. m_fGradient = !UIFIsLowColor() && CUIIsUpdateLayeredWindowAvail();
  147. if (m_fGradient) {
  148. m_color = RGB( 0, 0, 0 );
  149. m_iGradWidth = 4;
  150. m_iAlpha = 25;
  151. m_sizeShift.cx = 4;
  152. m_sizeShift.cy = 4;
  153. }
  154. else {
  155. m_color = RGB( 128, 128, 128 );
  156. m_iGradWidth = 0;
  157. m_iAlpha = 0;
  158. m_sizeShift.cx = 2;
  159. m_sizeShift.cy = 2;
  160. }
  161. }
  162. /* A D J U S T W I N D O W P O S */
  163. /*------------------------------------------------------------------------------
  164. ------------------------------------------------------------------------------*/
  165. void CUIFShadow::AdjustWindowPos( void )
  166. {
  167. HWND hWndOwner = m_pWndOwner->GetWnd();
  168. RECT rc;
  169. if (!IsWindow( GetWnd() )) {
  170. return;
  171. }
  172. GetWindowRect( hWndOwner, &rc );
  173. SetWindowPos( GetWnd(),
  174. hWndOwner,
  175. rc.left + m_sizeShift.cx,
  176. rc.top + m_sizeShift.cy,
  177. rc.right - rc.left,
  178. rc.bottom - rc.top,
  179. SWP_NOOWNERZORDER | SWP_NOACTIVATE );
  180. }
  181. /* I N I T S H A D O W */
  182. /*------------------------------------------------------------------------------
  183. ------------------------------------------------------------------------------*/
  184. void CUIFShadow::InitShadow( void )
  185. {
  186. typedef struct _RGBAPLHA {
  187. BYTE rgbBlue;
  188. BYTE rgbGreen;
  189. BYTE rgbRed;
  190. BYTE rgbAlpha;
  191. } RGBALPHA;
  192. HDC hdcScreen = NULL;
  193. HDC hdcLayered = NULL;
  194. RECT rcWindow;
  195. SIZE size;
  196. BITMAPINFO BitmapInfo;
  197. HBITMAP hBitmapMem = NULL;
  198. HBITMAP hBitmapOld = NULL;
  199. void *pDIBits;
  200. int i;
  201. int j;
  202. int iAlphaStep;
  203. POINT ptSrc;
  204. POINT ptDst;
  205. BLENDFUNCTION Blend;
  206. //
  207. if (!m_fGradient) {
  208. return;
  209. }
  210. // The extended window style, WS_EX_LAYERED, that has been set in CreateWindowEx
  211. // will be cleared on Access (why?). reset it again
  212. SetWindowLong( GetWnd(), GWL_EXSTYLE, (GetWindowLong( GetWnd(), GWL_EXSTYLE ) | WS_EX_LAYERED) );
  213. //
  214. Assert( CUIIsUpdateLayeredWindowAvail() );
  215. Assert( m_iGradWidth != 0 );
  216. iAlphaStep = ((255 * m_iAlpha / 100) / m_iGradWidth);
  217. //
  218. GetWindowRect( GetWnd(), &rcWindow );
  219. size.cx = rcWindow.right - rcWindow.left;
  220. size.cy = rcWindow.bottom - rcWindow.top;
  221. hdcScreen = GetDC( NULL );
  222. if (hdcScreen == NULL) {
  223. return;
  224. }
  225. hdcLayered = CreateCompatibleDC( hdcScreen );
  226. if (hdcLayered == NULL) {
  227. ReleaseDC( NULL, hdcScreen );
  228. return;
  229. }
  230. // create bitmap
  231. BitmapInfo.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
  232. BitmapInfo.bmiHeader.biWidth = size.cx;
  233. BitmapInfo.bmiHeader.biHeight = size.cy;
  234. BitmapInfo.bmiHeader.biPlanes = 1;
  235. BitmapInfo.bmiHeader.biBitCount = 32;
  236. BitmapInfo.bmiHeader.biCompression = BI_RGB;
  237. BitmapInfo.bmiHeader.biSizeImage = 0;
  238. BitmapInfo.bmiHeader.biXPelsPerMeter = 100;
  239. BitmapInfo.bmiHeader.biYPelsPerMeter = 100;
  240. BitmapInfo.bmiHeader.biClrUsed = 0;
  241. BitmapInfo.bmiHeader.biClrImportant = 0;
  242. hBitmapMem = CreateDIBSection( hdcScreen, &BitmapInfo, DIB_RGB_COLORS, &pDIBits, NULL, 0 );
  243. if (pDIBits == NULL) {
  244. ReleaseDC( NULL, hdcScreen );
  245. DeleteDC( hdcLayered );
  246. return;
  247. }
  248. MemSet( pDIBits, 0, ((((32 * size.cx) + 31) & ~31) / 8) * size.cy );
  249. // face
  250. for (i = 0; i < size.cy; i++) {
  251. RGBALPHA *ppxl = (RGBALPHA *)pDIBits + i * size.cx;
  252. BYTE bAlpha = iAlphaStep * m_iGradWidth;
  253. for (j = 0; j < size.cx; j++) {
  254. ppxl->rgbAlpha = bAlpha;
  255. ppxl++;
  256. }
  257. }
  258. // edges
  259. for (i = 0; i < m_iGradWidth; i++) {
  260. RGBALPHA *ppxl;
  261. BYTE bAlpha = iAlphaStep * (i + 1);
  262. // top
  263. if (i <= (size.cy + 1)/2) {
  264. for (j = m_iGradWidth; j < size.cx - m_iGradWidth; j++) {
  265. ppxl = (RGBALPHA *)pDIBits + (size.cy - 1 - i) * size.cx + j;
  266. ppxl->rgbAlpha = bAlpha;
  267. }
  268. }
  269. // bottom
  270. if (i <= (size.cy + 1)/2) {
  271. for (j = m_iGradWidth; j < size.cx - m_iGradWidth; j++) {
  272. ppxl = (RGBALPHA *)pDIBits + i * size.cx + j;
  273. ppxl->rgbAlpha = bAlpha;
  274. }
  275. }
  276. // left
  277. if (i <= (size.cx + 1)/2) {
  278. for (j = m_iGradWidth; j < size.cy - m_iGradWidth; j++) {
  279. ppxl = (RGBALPHA *)pDIBits + j * size.cx + i;
  280. ppxl->rgbAlpha = bAlpha;
  281. }
  282. }
  283. // right
  284. if (i <= (size.cx + 1)/2) {
  285. for (j = m_iGradWidth; j < size.cy - m_iGradWidth; j++) {
  286. ppxl = (RGBALPHA *)pDIBits + j * size.cx + (size.cx - 1 - i);
  287. ppxl->rgbAlpha = bAlpha;
  288. }
  289. }
  290. }
  291. // corners
  292. for (i = 0; i < m_iGradWidth; i++) {
  293. RGBALPHA *ppxl;
  294. BYTE bAlpha;
  295. for (j = 0; j < m_iGradWidth; j++) {
  296. bAlpha = iAlphaStep * (i + 1) * (j + 1) / (m_iGradWidth + 1);
  297. // top-left
  298. if ((i <= (size.cy + 1)/2) && (j <= (size.cx + 1)/2)) {
  299. ppxl = (RGBALPHA *)pDIBits + (size.cy - 1 - i) * size.cx + j;
  300. ppxl->rgbAlpha = bAlpha;
  301. }
  302. // top-right
  303. if ((i <= (size.cy + 1)/2) && (j <= (size.cx + 1)/2)) {
  304. ppxl = (RGBALPHA *)pDIBits + (size.cy - 1 - i) * size.cx + (size.cx - 1 - j);
  305. ppxl->rgbAlpha = bAlpha;
  306. }
  307. // bottom-left
  308. if ((i <= (size.cy + 1)/2) && (j <= (size.cx + 1)/2)) {
  309. ppxl = (RGBALPHA *)pDIBits + i * size.cx + j;
  310. ppxl->rgbAlpha = bAlpha;
  311. }
  312. // bottom-right
  313. if ((i <= (size.cy + 1)/2) && (j <= (size.cx + 1)/2)) {
  314. ppxl = (RGBALPHA *)pDIBits + i * size.cx + (size.cx - 1 - j);
  315. ppxl->rgbAlpha = bAlpha;
  316. }
  317. }
  318. }
  319. //
  320. ptSrc.x = 0;
  321. ptSrc.y = 0;
  322. ptDst.x = rcWindow.left;
  323. ptDst.y = rcWindow.top;
  324. Blend.BlendOp = AC_SRC_OVER;
  325. Blend.BlendFlags = 0;
  326. Blend.SourceConstantAlpha = 255;
  327. Blend.AlphaFormat = AC_SRC_ALPHA;
  328. hBitmapOld = (HBITMAP)SelectObject( hdcLayered, hBitmapMem );
  329. CUIUpdateLayeredWindow( GetWnd(), hdcScreen, NULL, &size, hdcLayered, &ptSrc, 0, &Blend, ULW_ALPHA );
  330. SelectObject( hdcLayered, hBitmapOld );
  331. // done
  332. ReleaseDC( NULL, hdcScreen );
  333. DeleteDC( hdcLayered );
  334. DeleteObject( hBitmapMem );
  335. }